From 0e0256284a546f64d460f5cd0a828c5599175ce2 Mon Sep 17 00:00:00 2001 From: Mocki <34432001+Morcki@users.noreply.github.com> Date: Tue, 26 Jul 2022 09:45:23 +0800 Subject: [PATCH] [gui] Support rendering lines from a part of VBO (#5495) * add extra args to support users to draw part of lines they want * [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci * Update python/taichi/ui/scene.py Co-authored-by: YuZhang * fix notes format for docs using * [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci * Update python/taichi/ui/scene.py Co-authored-by: Vissidarte-Herman <93570324+Vissidarte-Herman@users.noreply.github.com> * Update python/taichi/ui/scene.py Co-authored-by: Vissidarte-Herman <93570324+Vissidarte-Herman@users.noreply.github.com> * Update python/taichi/ui/scene.py Co-authored-by: Vissidarte-Herman <93570324+Vissidarte-Herman@users.noreply.github.com> * Update python/taichi/ui/scene.py Co-authored-by: Vissidarte-Herman <93570324+Vissidarte-Herman@users.noreply.github.com> * imporve the notes of functions in Scene * skip some tests * [pre-commit.ci] auto fixes from pre-commit.com hooks for more information, see https://pre-commit.ci * test is no problem, github runner goes wrong * improve notes format Co-authored-by: pre-commit-ci[bot] <66853113+pre-commit-ci[bot]@users.noreply.github.com> Co-authored-by: YuZhang Co-authored-by: Vissidarte-Herman <93570324+Vissidarte-Herman@users.noreply.github.com> --- python/taichi/ui/scene.py | 71 +++++++++++++++---- taichi/python/export_ggui.cpp | 11 ++- .../vulkan/renderables/scene_lines.cpp | 6 +- 3 files changed, 72 insertions(+), 16 deletions(-) diff --git a/python/taichi/ui/scene.py b/python/taichi/ui/scene.py index bbaa2b21dfa03..f01a14f4c681c 100644 --- a/python/taichi/ui/scene.py +++ b/python/taichi/ui/scene.py @@ -93,8 +93,18 @@ def lines(self, width, indices=None, color=(0.5, 0.5, 0.5), - per_vertex_color=None): + per_vertex_color=None, + vertex_offset: int = 0, + vertex_count: int = None, + index_offset: int = 0, + index_count: int = None): """Declare multi-lines inside the scene. + + Note that under current situation, for example, there you have 4 vertices, + vertices.shape[0] is 4. So there will be 2 lines, the first line's two points + are vertices[0] and vertices[1], and the second line's two points are + vertices[2] and vertices[3]. + Args: vertices: a taichi 3D Vector field, where each element indicate the 3D location of points of lines. @@ -106,7 +116,39 @@ def lines(self, If `per_vertex_color` is provided, this is ignored. per_vertex_color (Tuple[float]): a taichi 3D vector field, where each element indicate the RGB color of the line. + vertex_offset (int, optional): + if 'indices' is provided, this refers to the value added to the vertex + index before indexing into the vertex buffer, else this refers to the + index of the first vertex to draw. + vertex_count (int, optional): + only available when `indices` is not provided, which is the number + of vertices to draw. There are 2 cases that we will change your + `vertex_count`. [1] If the `vertex_count` is an odd number, then we + will change it to `vertex_count` - 1. [2] If `vertex_offset` plus + `vertex_count` greater than vertices.shape[0], then we will reduce + `vertex_count` to no more than vertices.shape[0]. + index_offset (int, optional): + Only available when `indices` is provided, which is the base index + within the index buffer. + index_count (int, optional): + Only available when `indices` is provided, which is the number + of vertices to draw. """ + if vertex_count is None: + vertex_count = vertices.shape[0] + if index_count is None: + if indices is None: + index_count = vertex_count + else: + index_count = indices.shape[0] + if vertex_count % 2: + print( + "Warning! Odd drawing count will be cut to neast even number") + vertex_count -= 1 + if vertex_count + vertex_offset > vertices.shape[0]: + print("Warning! Drawing count greater than shape will be cut") + vertex_count = vertices.shape[0] - vertex_offset + vertex_count -= vertex_count % 2 vbo = get_vbo_field(vertices) copy_vertices_to_vbo(vbo, vertices) has_per_vertex_color = per_vertex_color is not None @@ -115,7 +157,8 @@ def lines(self, vbo_info = get_field_info(vbo) indices_info = get_field_info(indices) self.scene.lines(vbo_info, indices_info, has_per_vertex_color, color, - width) + width, index_count, index_offset, vertex_count, + vertex_offset) def mesh(self, vertices, @@ -129,9 +172,11 @@ def mesh(self, index_offset: int = 0, index_count: int = None): """Declare a mesh inside the scene. + if you indicate the index_offset and index_count, the normals will also be sliced by the args, and the shading resultes will not be affected. (It is equal to make a part of the mesh visible) + Args: vertices: a taichi 3D Vector field, where each element indicate the 3D location of a vertex. @@ -147,18 +192,18 @@ def mesh(self, element indicate the RGB color of a vertex. two_sided (bool): whether or not the triangles should be able to be seen from both sides. - vertex_offset: int type(ohterwise float type will be floored to int), - if 'indices' is provided, this means the value added to the vertex - index before indexing into the vertex buffer, else this means the + vertex_offset (int, optional): + if 'indices' is provided, this refers to the value added to the vertex + index before indexing into the vertex buffer, else this refers to the index of the first vertex to draw. - vertex_count: int type(ohterwise float type will be floored to int), - only avaliable when `indices` is not provided, which is the number + vertex_count (int, optional): + only available when `indices` is not provided, which is the number of vertices to draw. - index_offset: int type(ohterwise float type will be floored to int), - only avaliable when `indices` is provided, which is the base index + index_offset (int, optional): + only available when `indices` is provided, which is the base index within the index buffer. - index_count: int type(ohterwise float type will be floored to int), - only avaliable when `indices` is provided, which is the the number + index_count (int, optional): + only available when `indices` is provided, which is the the number of vertices to draw. """ vbo = get_vbo_field(vertices) @@ -199,9 +244,9 @@ def particles(self, values. If `per_vertex_color` is provided, this is ignored. per_vertex_color (Tuple[float]): a taichi 3D vector field, where each element indicate the RGB color of a particle. - index_offset: int type(ohterwise float type will be floored to int), + index_offset (int, optional): the index of the first vertex to draw. - index_count: int type(ohterwise float type will be floored to int), + index_count (int, optional): the number of vertices to draw. """ vbo = get_vbo_field(centers) diff --git a/taichi/python/export_ggui.cpp b/taichi/python/export_ggui.cpp index 0468ebdc9ca9f..3f1665ebe015d 100644 --- a/taichi/python/export_ggui.cpp +++ b/taichi/python/export_ggui.cpp @@ -140,11 +140,20 @@ struct PyScene { FieldInfo indices, bool has_per_vertex_color, py::tuple color_, - float width) { + float width, + float draw_index_count, + float draw_first_index, + float draw_vertex_count, + float draw_first_vertex) { RenderableInfo renderable_info; renderable_info.vbo = vbo; renderable_info.indices = indices; renderable_info.has_per_vertex_color = has_per_vertex_color; + renderable_info.has_user_customized_draw = true; + renderable_info.draw_index_count = (int)draw_index_count; + renderable_info.draw_first_index = (int)draw_first_index; + renderable_info.draw_vertex_count = (int)draw_vertex_count; + renderable_info.draw_first_vertex = (int)draw_first_vertex; SceneLinesInfo info; info.renderable_info = renderable_info; diff --git a/taichi/ui/backends/vulkan/renderables/scene_lines.cpp b/taichi/ui/backends/vulkan/renderables/scene_lines.cpp index f49b4bcb16c04..49c9507614d36 100644 --- a/taichi/ui/backends/vulkan/renderables/scene_lines.cpp +++ b/taichi/ui/backends/vulkan/renderables/scene_lines.cpp @@ -69,9 +69,11 @@ void SceneLines::record_this_frame_commands(CommandList *command_list) { command_list->set_line_width(curr_width_); if (indexed_) { - command_list->draw_indexed(config_.indices_count, 0, 0); + command_list->draw_indexed(config_.draw_index_count, + config_.draw_first_vertex, + config_.draw_first_index); } else { - command_list->draw(config_.vertices_count, 0); + command_list->draw(config_.draw_vertex_count, config_.draw_first_vertex); } }