Skip to content

Commit

Permalink
Add test for self intersection
Browse files Browse the repository at this point in the history
  • Loading branch information
stephomi committed Jul 26, 2023
1 parent d66df2b commit c95f83d
Show file tree
Hide file tree
Showing 5 changed files with 32 additions and 11 deletions.
28 changes: 18 additions & 10 deletions src/manifold/src/edge_op.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -223,9 +223,11 @@ void Manifold::Impl::SimplifyTopology() {
for_each_n(policy, countAt(0), nbEdges,
[=] __host__ __device__(int i) { bflagsPtr[i] = se(i); });
std::vector<int> visited(halfedge_.size(), -1);
int tag = 0;
for (int i = 0; i < nbEdges; ++i) {
if (bflags[i]) {
RecursiveEdgeSwap(i, visited);
tag++;
RecursiveEdgeSwap(i, visited, tag);
numFlagged++;
}
}
Expand Down Expand Up @@ -485,14 +487,15 @@ void Manifold::Impl::CollapseEdge(const int edge) {
}

void Manifold::Impl::RecursiveEdgeSwap(const int edge,
std::vector<int>& visited) {
std::vector<int>& visited, int& tag) {
VecDH<TriRef>& triRef = meshRelation_.triRef;

if (edge < 0) return;
const int pair = halfedge_[edge].pairedHalfedge;
if (pair < 0) return;
if (visited[edge] == pair) return;
visited[edge] = pair;

// avoid infinite recursion
if (visited[edge] == tag && visited[pair] == tag) return;

const glm::ivec3 tri0edge = TriOf(edge);
const glm::ivec3 tri1edge = TriOf(pair);
Expand Down Expand Up @@ -572,12 +575,15 @@ void Manifold::Impl::RecursiveEdgeSwap(const int edge,
SwapEdge();
const glm::vec2 e23 = v[3] - v[2];
if (glm::dot(e23, e23) < precision_ * precision_) {
tag++;
CollapseEdge(tri0edge[2]);
} else {
RecursiveEdgeSwap(tri0edge[0], visited);
RecursiveEdgeSwap(tri0edge[1], visited);
RecursiveEdgeSwap(tri1edge[0], visited);
RecursiveEdgeSwap(tri1edge[1], visited);
visited[edge] = tag;
visited[pair] = tag;
RecursiveEdgeSwap(tri0edge[0], visited, tag);
RecursiveEdgeSwap(tri0edge[1], visited, tag);
RecursiveEdgeSwap(tri1edge[0], visited, tag);
RecursiveEdgeSwap(tri1edge[1], visited, tag);
}
return;
} else if (CCW(v[0], v[3], v[2], precision_) <= 0 ||
Expand All @@ -586,8 +592,10 @@ void Manifold::Impl::RecursiveEdgeSwap(const int edge,
}
// Normal path
SwapEdge();
RecursiveEdgeSwap(halfedge_[tri0edge[1]].pairedHalfedge, visited);
RecursiveEdgeSwap(halfedge_[tri1edge[0]].pairedHalfedge, visited);
visited[edge] = tag;
visited[pair] = tag;
RecursiveEdgeSwap(halfedge_[tri0edge[1]].pairedHalfedge, visited, tag);
RecursiveEdgeSwap(halfedge_[tri1edge[0]].pairedHalfedge, visited, tag);
}

void Manifold::Impl::SplitPinchedVerts() {
Expand Down
2 changes: 1 addition & 1 deletion src/manifold/src/impl.h
Original file line number Diff line number Diff line change
Expand Up @@ -121,7 +121,7 @@ struct Manifold::Impl {
void SimplifyTopology();
void DedupeEdge(int edge);
void CollapseEdge(int edge);
void RecursiveEdgeSwap(int edge, std::vector<int>& visited);
void RecursiveEdgeSwap(int edge, std::vector<int>& visited, int& tag);
void RemoveIfFolded(int edge);
void PairUp(int edge0, int edge1);
void UpdateVert(int vert, int startEdge, int endEdge);
Expand Down
Binary file added test/models/self_intersectA.glb
Binary file not shown.
Binary file added test/models/self_intersectB.glb
Binary file not shown.
13 changes: 13 additions & 0 deletions test/samples_test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -255,3 +255,16 @@ TEST(Samples, Sponge4) {
#endif
}
#endif

#ifdef MANIFOLD_EXPORT
TEST(Samples, SelfIntersect) {
manifold::PolygonParams().processOverlaps = true;
std::string file = __FILE__;
std::string dir = file.substr(0, file.rfind('/'));
Manifold m1 = ImportMesh(dir + "/models/self_intersectA.glb");
Manifold m2 = ImportMesh(dir + "/models/self_intersectB.glb");
Manifold res = m1 + m2;
res.GetMeshGL(); // test crash
manifold::PolygonParams().processOverlaps = false;
}
#endif

0 comments on commit c95f83d

Please sign in to comment.