Commit: 9643b2e5b50399c8224d6de8d150d88c0d3e2848
Author: Sergey Sharybin
Date:   Mon Feb 24 17:58:56 2014 +0600
https://developer.blender.org/rB9643b2e5b50399c8224d6de8d150d88c0d3e2848

Preserve non-flat faces in boolean modifier

This commit implements dissolving of edges which were used
to triangulate non-flat faces. This slows things down a bit
(around 5% on heave mesh with all faces triangulated).

We could improve speed of dissolve a bit here (so not a bell
to add an option for triangulation yet).

Also fixed wrong edge origindex mapping.

===================================================================

M       extern/carve/CMakeLists.txt
M       extern/carve/bundle.sh
M       extern/carve/carve-capi.cc
M       extern/carve/carve-util.cc
M       extern/carve/files.txt
M       extern/carve/include/carve/mesh_simplify.hpp
A       extern/carve/include/carve/triangle_intersection.hpp
M       extern/carve/include/carve/win32.h
A       extern/carve/patches/mesh_simplify_dissolve_edges.patch
M       extern/carve/patches/series

===================================================================

diff --git a/extern/carve/CMakeLists.txt b/extern/carve/CMakeLists.txt
index 11a92f9..5754290 100644
--- a/extern/carve/CMakeLists.txt
+++ b/extern/carve/CMakeLists.txt
@@ -140,6 +140,7 @@ set(SRC
        include/carve/tag.hpp
        include/carve/timing.hpp
        include/carve/tree.hpp
+       include/carve/triangle_intersection.hpp
        include/carve/triangulator.hpp
        include/carve/triangulator_impl.hpp
        include/carve/util.hpp
diff --git a/extern/carve/bundle.sh b/extern/carve/bundle.sh
index 91d5f44..2a3e621 100755
--- a/extern/carve/bundle.sh
+++ b/extern/carve/bundle.sh
@@ -111,6 +111,7 @@ cat > SConscript << EOF
 Import ('env')
 
 sources = env.Glob('lib/*.cpp')
+sources += env.Glob('*.cc')
 
 defs = []
 incs = ['include']
diff --git a/extern/carve/carve-capi.cc b/extern/carve/carve-capi.cc
index ed46d19..319a201 100644
--- a/extern/carve/carve-capi.cc
+++ b/extern/carve/carve-capi.cc
@@ -30,6 +30,7 @@
 #include <carve/interpolator.hpp>
 #include <carve/rescale.hpp>
 #include <carve/csg_triangulator.hpp>
+#include <carve/mesh_simplify.hpp>
 
 using carve::mesh::MeshSet;
 
@@ -38,6 +39,7 @@ typedef std::pair<MeshSet<3>::vertex_t *, 
MeshSet<3>::vertex_t *> VertexPair;
 typedef carve::interpolate::VertexAttr<OrigIndex> OrigVertMapping;
 typedef carve::interpolate::FaceAttr<OrigIndex> OrigFaceMapping;
 typedef carve::interpolate::FaceEdgeAttr<OrigIndex> OrigFaceEdgeMapping;
+typedef carve::interpolate::FaceEdgeAttr<bool> FaceEdgeTriangulatedFlag;
 
 typedef struct CarveMeshDescr {
        // Stores mesh data itself.
@@ -57,6 +59,8 @@ typedef struct CarveMeshDescr {
        // Mapping from the face edges back to (original edge index, original 
loop index).
        OrigFaceEdgeMapping orig_face_edge_mapping;
 
+       FaceEdgeTriangulatedFlag face_edge_triangulated_flag;
+
        // Mapping from the faces back to original poly index.
        OrigFaceMapping orig_face_mapping;
 } CarveMeshDescr;
@@ -131,6 +135,7 @@ void initOrigIndexMeshFaceMapping(CarveMeshDescr *mesh,
                                   const std::vector<int> &orig_poly_index_map,
                                   OrigVertMapping *orig_vert_mapping,
                                   OrigFaceEdgeMapping *orig_face_edge_mapping,
+                                  FaceEdgeTriangulatedFlag 
*face_edge_triangulated_flag,
                                   OrigFaceMapping *orig_face_attr)
 {
        MeshSet<3> *poly = mesh->poly;
@@ -169,6 +174,9 @@ void initOrigIndexMeshFaceMapping(CarveMeshDescr *mesh,
                                                                     
std::make_pair(which_mesh,
                                                                                
    orig_loop_index));
                        }
+                       else {
+                               face_edge_triangulated_flag->setAttribute(face, 
edge_iter.idx(), true);
+                       }
                }
        }
 }
@@ -177,6 +185,7 @@ void initOrigIndexMapping(CarveMeshDescr *left_mesh,
                           CarveMeshDescr *right_mesh,
                           OrigVertMapping *orig_vert_mapping,
                           OrigFaceEdgeMapping *orig_face_edge_mapping,
+                          FaceEdgeTriangulatedFlag 
*face_edge_triangulated_flag,
                           OrigFaceMapping *orig_face_mapping)
 {
        initOrigIndexMeshFaceMapping(left_mesh,
@@ -185,6 +194,7 @@ void initOrigIndexMapping(CarveMeshDescr *left_mesh,
                                     left_mesh->orig_poly_index_map,
                                     orig_vert_mapping,
                                     orig_face_edge_mapping,
+                                    face_edge_triangulated_flag,
                                     orig_face_mapping);
 
        initOrigIndexMeshFaceMapping(right_mesh,
@@ -193,9 +203,119 @@ void initOrigIndexMapping(CarveMeshDescr *left_mesh,
                                     right_mesh->orig_poly_index_map,
                                     orig_vert_mapping,
                                     orig_face_edge_mapping,
+                                    face_edge_triangulated_flag,
                                     orig_face_mapping);
 }
 
+void origEdgeMappingForFace(MeshSet<3>::face_t *face,
+                            OrigFaceEdgeMapping *orig_face_edge_mapping,
+                            std::unordered_map<VertexPair, OrigIndex> 
*edge_origindex_map)
+{
+       OrigIndex origindex_none = std::make_pair((int)CARVE_MESH_NONE, -1);
+
+       MeshSet<3>::edge_t *edge = face->edge;
+       for (int i = 0;
+            i < face->n_edges;
+            ++i, edge = edge->next)
+       {
+               MeshSet<3>::vertex_t *v1 = edge->vert;
+               MeshSet<3>::vertex_t *v2 = edge->next->vert;
+
+               OrigIndex orig_edge_index =
+                       orig_face_edge_mapping->getAttribute(edge->face, i, 
origindex_none);
+
+               edgeIndexMap_put(edge_origindex_map, v1, v2, orig_edge_index);
+       }
+}
+
+void dissolveTriangulatedEdges(MeshSet<3>::mesh_t *mesh,
+                               OrigFaceEdgeMapping *orig_face_edge_mapping,
+                               FaceEdgeTriangulatedFlag 
*face_edge_triangulated_flag)
+{
+       typedef std::unordered_set<MeshSet<3>::edge_t *> edge_set_t;
+       typedef std::unordered_set<MeshSet<3>::face_t *> face_set_t;
+       edge_set_t triangulated_face_edges;
+
+       for (int face_index = 0; face_index < mesh->faces.size(); face_index++) 
{
+               MeshSet<3>::face_t *face = mesh->faces[face_index];
+               MeshSet<3>::edge_t *edge = face->edge;
+               for (int edge_index = 0;
+                    edge_index < face->n_edges;
+                    ++edge_index, edge = edge->next)
+               {
+                       const bool is_triangulated_edge =
+                               face_edge_triangulated_flag->getAttribute(face,
+                                                                         
edge_index,
+                                                                         
false);
+                       if (is_triangulated_edge) {
+                               MeshSet<3>::edge_t *e1 = std::min(edge, 
edge->rev);
+                               triangulated_face_edges.insert(e1);
+                       }
+               }
+       }
+
+       if (triangulated_face_edges.size()) {
+               face_set_t triangulated_faces;
+               std::unordered_map<VertexPair, OrigIndex> edge_origindex_map;
+
+               for (edge_set_t::iterator it = triangulated_face_edges.begin();
+                    it != triangulated_face_edges.end();
+                    ++it)
+               {
+                       MeshSet<3>::edge_t *edge = *it;
+
+                       origEdgeMappingForFace(edge->face,
+                                              orig_face_edge_mapping,
+                                              &edge_origindex_map);
+                       triangulated_faces.insert(edge->face);
+
+                       origEdgeMappingForFace(edge->rev->face,
+                                              orig_face_edge_mapping,
+                                              &edge_origindex_map);
+                       triangulated_faces.insert(edge->rev->face);
+               }
+
+               carve::mesh::MeshSimplifier simplifier;
+               simplifier.dissolveMeshEdges(mesh, triangulated_face_edges);
+
+               for (int face_index = 0; face_index < mesh->faces.size(); 
face_index++) {
+                       MeshSet<3>::face_t *face = mesh->faces[face_index];
+
+                       if (triangulated_faces.find(face) != 
triangulated_faces.end()) {
+                               MeshSet<3>::edge_t *edge = face->edge;
+                               for (int edge_index = 0;
+                                    edge_index < face->n_edges;
+                                    ++edge_index, edge = edge->next)
+                               {
+                                       MeshSet<3>::vertex_t *v1 = edge->vert;
+                                       MeshSet<3>::vertex_t *v2 = 
edge->next->vert;
+
+                                       OrigIndex orig_edge_index =
+                                               
edgeIndexMap_get(edge_origindex_map,
+                                                                v1,
+                                                                v2);
+
+                                       
orig_face_edge_mapping->setAttribute(face, edge_index, orig_edge_index);
+                               }
+                       }
+               }
+       }
+}
+
+void dissolveTriangulatedEdges(CarveMeshDescr *mesh_descr)
+{
+       MeshSet<3> *poly = mesh_descr->poly;
+       FaceEdgeTriangulatedFlag *face_edge_triangulated_flag =
+               &mesh_descr->face_edge_triangulated_flag;
+
+       for (int i = 0; i < poly->meshes.size(); ++i) {
+               MeshSet<3>::mesh_t *mesh = poly->meshes[i];
+               dissolveTriangulatedEdges(mesh,
+                                         &mesh_descr->orig_face_edge_mapping,
+                                         face_edge_triangulated_flag);
+       }
+}
+
 }  // namespace
 
 CarveMeshDescr *carve_addMesh(struct ImportMeshData *import_data,
@@ -271,6 +391,7 @@ CarveMeshDescr *carve_addMesh(struct ImportMeshData 
*import_data,
                                                              
&mesh_descr->orig_poly_index_map);
 
                        num_tessellated_polys += num_triangles;
+                       loop_index += verts_per_poly;
                }
                else {
                        face_indices.push_back(verts_per_poly);
@@ -345,6 +466,7 @@ bool carve_performBooleanOperation(CarveMeshDescr 
*left_mesh,
                initOrigIndexMapping(left_mesh, right_mesh,
                                     &output_descr->orig_vert_mapping,
                                     &output_descr->orig_face_edge_mapping,
+                                    &output_descr->face_edge_triangulated_flag,
                                     &output_descr->orig_face_mapping);
 
                carve::csg::CSG csg;
@@ -354,6 +476,7 @@ bool carve_performBooleanOperation(CarveMeshDescr 
*left_mesh,
 
                output_descr->orig_vert_mapping.installHooks(csg);
                output_descr->orig_face_edge_mapping.installHooks(csg);
+               output_descr->face_edge_triangulated_flag.installHooks(csg);
                output_descr->orig_face_mapping.installHooks(csg);
 
                // Prepare operands for actual boolean operation.
@@ -383,6 +506,8 @@ bool carve_performBooleanOperation(CarveMeshDescr 
*left_mesh,
                                                 
carve::csg::CSG::CLASSIFY_EDGE);
                if (output_descr->poly) {
                        output_descr->poly->transform(rev_r);
+
+                       dissolveTriangulatedEdges(output_descr);
                }
        }
        catch (carve::exception e) {
diff --git a/extern/carve/carve-util.cc b/extern/carve/carve-util.cc
index b9b7fb1..b1943a6 100644
--- a/extern/carve/carve-util.cc
+++ b/extern/carve/carve-util.cc
@@ -619,6 +619,7 @@ int triangulateNGon_carveTriangulator(const 
std::vector<Vector> &vertices,
        }
 
        carve::triangulate::triangulate(poly_2d, *triangles);
+       carve::triangulate::improve(poly_2d, *triangles);
 
        return triangles->size();
 }
@@ -737,9 +738,9 @@ int carve_triangulatePoly(struct ImportMeshData 
*import_data,
                }
 
                for (int i = 0; i < triangles.size(); ++i) {
-                       int v1 = triangles[i].c,
+                       int v1 = triangles[i].a,
                            v2 = triangles[i].b,
-                           v3 = triangles[i].a;
+                           v3 = triangles[i].c;
 
                        // Sanity check of the triangle.
                        assert(v1 != v2);
@@ -750,13 +751,15 @@ int carve_triangulatePoly(struct ImportMeshData 
*import_data,
                        assert(v3 < verts_per_poly);
 
                        face_indices->push_back(3);
-                       face_indices->push_back(verts_of_poly[v3]);
-                       face_indices->push_back(verts_of_poly[v2]);
                        face_indices->push_back(verts_of_poly[v1]);
+                       face_indices->push_back(verts_of_poly[v2]);
+                       face_indices->push_back(verts_of_poly[v3]);
 
 #define CHECK_

@@ Diff output truncated at 10240 characters. @@

_______________________________________________
Bf-blender-cvs mailing list
[email protected]
http://lists.blender.org/mailman/listinfo/bf-blender-cvs

Reply via email to