Exemplo n.º 1
0
 public HashSet<TopoTriangle> FindIntersectionCandidates(TopoTriangle triangle)
 {
     if (tree == null) PrepareFastSearch();
     HashSet<TopoTriangle> result = new HashSet<TopoTriangle>();
     tree.FindIntersectionCandidates(triangle, result);
     return result;
 }
Exemplo n.º 2
0
 public TopoTriangle AddTriangle(TopoTriangle triangle)
 {
     if (triangle.IsDegenerated())
         triangle.Unlink(this);
     else
         triangles.Add(triangle);
     return triangle;
 }
Exemplo n.º 3
0
 public TopoTriangle addTriangle(RHVector3 p1,RHVector3 p2,RHVector3 p3,RHVector3 normal)
 {
     TopoVertex v1 = addVertex(p1);
     TopoVertex v2 = addVertex(p2);
     TopoVertex v3 = addVertex(p3);
     TopoTriangle triangle = new TopoTriangle(this, v1, v2, v3, normal.x, normal.y, normal.z);
     return AddTriangle(triangle);
 }
Exemplo n.º 4
0
 public TopoTriangle addTriangle(double p1x, double p1y, double p1z, double p2x, double p2y, double p2z,
     double p3x, double p3y, double p3z, double nx, double ny, double nz)
 {
     TopoVertex v1 = addVertex(new RHVector3(p1x, p1y, p1z));
     TopoVertex v2 = addVertex(new RHVector3(p2x, p2y, p2z));
     TopoVertex v3 = addVertex(new RHVector3(p3x, p3y, p3z));
     TopoTriangle triangle = new TopoTriangle(this, v1, v2, v3, nx, ny, nz);
     return AddTriangle(triangle);
 }
Exemplo n.º 5
0
 public int testTriangleSide(TopoTriangle triangle)
 {
     double d1 = VertexDistance(triangle.vertices[0].pos);
     double d2 = VertexDistance(triangle.vertices[1].pos);
     double d3 = VertexDistance(triangle.vertices[2].pos);
     if (d1 >= 0 && d2 >= 0 && d3 >= 0) return 1;
     if (d1 <= 0 && d2 <= 0 && d3 <= 0) return -1;
     return 0;
 }
Exemplo n.º 6
0
 public int testTriangleSideFast(TopoTriangle triangle)
 {
      
     bool d1 = VertexDistance(triangle.vertices[0].pos)>0;
     bool d2 = VertexDistance(triangle.vertices[1].pos)>0;
     bool d3 = VertexDistance(triangle.vertices[2].pos)>0;
     if (d1 && d2 && d3) return 1;
     if (d1 == d2 && d2 == d3) return -1;
     return 0;
 }
Exemplo n.º 7
0
 public bool containTri(TopoTriangle triangle)
 {
     foreach (TopoVertex ver in triangle.vertices)
     {
         if (ContainsPoint(ver.pos))
         {
             return(true);
         }
     }
     return(false);
 }
Exemplo n.º 8
0
 public void AddTriangle(TopoTriangle triangle) {
     if(left == null && triangles == null) {
         triangles = new HashSet<TopoTriangle>();
     }
     if (triangles != null)
     {
         triangles.Add(triangle);
         box.Add(triangle.boundingBox);
         if (triangles.Count > nextTrySplit) TrySplit();
     }
     else
     {
         if (triangle.boundingBox.maxPoint[dimension] < middlePosition)
             left.AddTriangle(triangle);
         else if (triangle.boundingBox.minPoint[dimension] > middlePosition)
             right.AddTriangle(triangle);
         else
             middle.AddTriangle(triangle);
     }
 }
Exemplo n.º 9
0
        //--- MODEL_SLA	// milton
        public TopoTriangle[] getBoundingTri()
        {
            TopoTriangle[] triangles = new TopoTriangle[12];
            TopoVertex[]   vertices  = getVertices();

            triangles[0] = new TopoTriangle(vertices[0], vertices[1], vertices[3]);
            triangles[1] = new TopoTriangle(vertices[0], vertices[3], vertices[2]);

            triangles[2] = new TopoTriangle(vertices[4], vertices[6], vertices[7]);
            triangles[3] = new TopoTriangle(vertices[4], vertices[7], vertices[5]);

            triangles[4] = new TopoTriangle(vertices[2], vertices[3], vertices[7]);
            triangles[5] = new TopoTriangle(vertices[2], vertices[7], vertices[6]);

            triangles[6] = new TopoTriangle(vertices[1], vertices[5], vertices[7]);
            triangles[7] = new TopoTriangle(vertices[1], vertices[7], vertices[3]);

            triangles[8] = new TopoTriangle(vertices[0], vertices[4], vertices[5]);
            triangles[9] = new TopoTriangle(vertices[0], vertices[5], vertices[1]);

            triangles[10] = new TopoTriangle(vertices[0], vertices[2], vertices[6]);
            triangles[11] = new TopoTriangle(vertices[0], vertices[6], vertices[4]);
            return(triangles);
        }
Exemplo n.º 10
0
 public bool Remove(TopoTriangle triangle)
 {
     if (tree != null)
         tree.RemoveTriangle(triangle);
     return triangles.Remove(triangle);
 }
Exemplo n.º 11
0
 public bool Contains(TopoTriangle test)
 {
     return triangles.Contains(test);
 }
Exemplo n.º 12
0
 public void FindIntersectionCandidates(TopoTriangle triangle,HashSet<TopoTriangle> resultList)
 {
     if (triangles != null) // end leaf, test all boxes for intersection
     {
         foreach (TopoTriangle test in triangles)
         {
             if(test!=triangle && test.boundingBox.IntersectsBox(triangle.boundingBox))
                 resultList.Add(test);
         }
         return;
     }
     if (left == null) return;
     if(triangle.boundingBox.minPoint[dimension]<middlePosition)
         left.FindIntersectionCandidates(triangle,resultList);
     if(triangle.boundingBox.maxPoint[dimension]>middlePosition)
         right.FindIntersectionCandidates(triangle,resultList);
     if(triangle.boundingBox.minPoint[dimension]<middlePosition && triangle.boundingBox.maxPoint[dimension]>middlePosition)
         middle.FindIntersectionCandidates(triangle,resultList);
 }
Exemplo n.º 13
0
 public void Add(TopoTriangle triangle) {
     triangles.Add(triangle);
     if (tree != null)
         tree.AddTriangle(triangle);
 }
Exemplo n.º 14
0
 public void disconnectFace(TopoTriangle triangle)
 {
     connectedFacesList.Remove(triangle);
 }
Exemplo n.º 15
0
 public void removeTriangle(TopoTriangle triangle)
 {
     triangle.Unlink(this);
     triangles.Remove(triangle);
 }
Exemplo n.º 16
0
 public void connectFace(TopoTriangle triangle)
 {
     connectedFacesList.AddLast(triangle);
 }
Exemplo n.º 17
0
 private void FloodFillPlanarRegions(TopoTriangle good, int marker)
 {
     good.algHelper = marker;
     HashSet<TopoTriangle> front = new HashSet<TopoTriangle>();
     front.Add(good);
     HashSet<TopoTriangle> newFront = new HashSet<TopoTriangle>();
     int i;
     while (front.Count > 0)
     {
         Application.DoEvents();
         foreach (TopoTriangle t in front)
         {
             for (i = 0; i < 3; i++)
             {
                 foreach (TopoTriangle test in t.edges[i].faces)
                 {
                     if (test.algHelper == 0)
                     {
                         if (t.normal.Angle(test.normal) < 1e-6)
                         {
                             test.algHelper = 1;
                             newFront.Add(test);
                         }
                     }
                 }
             }
         }
         front = newFront;
         newFront = new HashSet<TopoTriangle>();
     }
 }
Exemplo n.º 18
0
 private bool FloodFillCheckNormals(TopoTriangle good)
 {
     good.algHelper = 1;
     HashSet<TopoTriangle> front = new HashSet<TopoTriangle>();
     front.Add(good);
     HashSet<TopoTriangle> newFront = new HashSet<TopoTriangle>();
     int i;
     int cnt = 0;
     while (front.Count > 0)
     {
         foreach (TopoTriangle t in front)
         {
             cnt++;
             if((cnt % 2000) == 0)
                 Application.DoEvents();
             for (i = 0; i < 3; i++)
             {
                 foreach (TopoTriangle test in t.edges[i].faces)
                 {
                     if (t != test && test.algHelper == 0)
                     {
                         test.algHelper = 1;
                         newFront.Add(test);
                         test.RecomputeNormal();
                         if (!t.SameNormalOrientation(test))
                         {
                             return false;
                         }
                     }
                 }
             }
         }
         front = newFront;
         newFront = new HashSet<TopoTriangle>();
     }
     return true;
 }
Exemplo n.º 19
0
 public bool RemoveTriangle(TopoTriangle triangle)
 {
     TopoTriangleNode node = FindNodeForTriangle(triangle);
     if (node != null)
         return node.triangles.Remove(triangle);
     return false;
 }
Exemplo n.º 20
0
 public bool importObj(string filename)
 {
     clear();
     bool error = false;
     try
     {
         string[] text = System.IO.File.ReadAllText(filename).Split(new string[] { "\r\n", "\n" }, StringSplitOptions.None);
         int vPos = 0;
         int vnPos = 0;
         int count = 0,countMax = text.Length;
         List<TopoVertex> vList = new List<TopoVertex>();
         List<RHVector3> vnList = new List<RHVector3>();
         foreach (string currentLine in text)
         {
             count++;
             Progress((double)count / countMax);
             if (count % 2000 == 0)
             {
                 Application.DoEvents();
                 if (IsActionStopped()) return true;
             }
             string line = currentLine.Trim().ToLower();
             if (line.Length == 0 || line.StartsWith("#")) continue;
             int p = line.IndexOf(" ");
             if (p < 0) continue;
             string cmd = line.Substring(0, p);
             if (cmd == "v")
             {
                 RHVector3 vert = extractVector(line.Substring(p + 1));
                 vList.Add(addVertex(vert));
                 vPos++;
             }
             else if (cmd == "vn")
             {
                 RHVector3 vert = extractVector(line.Substring(p + 1));
                 vnList.Add(vert);
                 vnPos++;
             }
             else if (cmd == "f")
             {
                 line = line.Substring(p + 1).Replace("  ", " ");
                 string[] parts = line.Split(new char[] { ' ' });
                 int[] vidx = new int[parts.Length];
                 int[] nidx = new int[parts.Length];
                 RHVector3 norm = null;
                 p = 0;
                 foreach (string part in parts)
                 {
                     string[] sp = part.Split('/');
                     if (sp.Length > 0)
                     {
                         int.TryParse(sp[0], out vidx[p]);
                         if (vidx[p] < 0) vidx[p] += vPos;
                         else vidx[p]--;
                         if (vidx[p] < 0 || vidx[p] >= vPos)
                         {
                             error = true;
                             break;
                         }
                     }
                     if (sp.Length > 2 && norm == null)
                     {
                         int.TryParse(sp[0], out nidx[p]);
                         if (nidx[p] < 0) nidx[p] += vnPos;
                         else nidx[p]--;
                         if (nidx[p] >= 0 && nidx[p] < vnPos)
                             norm = vnList[nidx[p]];
                     }
                     p++;
                 }
                 for (int i = 2; i < parts.Length; i++)
                 {
                     TopoTriangle triangle = new TopoTriangle(this, vList[vidx[0]], vList[vidx[1]], vList[vidx[2]]);
                     if (norm != null && norm.ScalarProduct(triangle.normal) < 0)
                         triangle.FlipDirection();
                     AddTriangle(triangle);
                 }
             }
             if (error) break;
         }
     }
     catch
     {
         error = true;
     }
     if (error)
     {
         clear();
     }
     return error;
 }
Exemplo n.º 21
0
 public TopoModel Copy()
 {
     TopoModel newModel = new TopoModel();
     int nOld = vertices.Count;
     int i = 0;
     List<TopoVertex> vcopy = new List<TopoVertex>(vertices.Count);
     foreach (TopoVertex v in vertices)
     {
         v.id = i++;
         TopoVertex newVert = new TopoVertex(v.id, v.pos);
         newModel.addVertex(newVert);
         vcopy.Add(newVert);
     }
     foreach (TopoTriangle t in triangles)
     {
         TopoTriangle triangle = new TopoTriangle(newModel, vcopy[t.vertices[0].id], vcopy[t.vertices[1].id], vcopy[t.vertices[2].id], t.normal.x, t.normal.y, t.normal.z);
         newModel.triangles.Add(triangle);
     }
     UpdateVertexNumbers();
     newModel.UpdateVertexNumbers();
     newModel.badEdges = 0;
     newModel.badTriangles = badTriangles;
     newModel.shells = shells;
     newModel.updatedNormals = updatedNormals;
     newModel.loopEdges = loopEdges;
     newModel.manyShardEdges = 0;
     newModel.manifold = manifold;
     newModel.normalsOriented = normalsOriented;
     return newModel;
 }
Exemplo n.º 22
0
 private void FloodFillTriangles(TopoTriangle tri, int value)
 {
     tri.algHelper = value;
     HashSet<TopoTriangle> front = new HashSet<TopoTriangle>();
     front.Add(tri);
     HashSet<TopoTriangle> newFront = new HashSet<TopoTriangle>();
     int i;
     while (front.Count > 0)
     {
         foreach (TopoTriangle t in front)
         {
             for (i = 0; i < 3; i++)
             {
                 foreach (TopoTriangle test in t.edges[i].faces)
                 {
                     if (test.algHelper == 0)
                     {
                         test.algHelper = value;
                         newFront.Add(test);
                     }
                 }
             }
         }
         front = newFront;
         newFront = new HashSet<TopoTriangle>();
     }
 }
Exemplo n.º 23
0
 public void addIntersectionToSubmesh(Submesh mesh, TopoTriangle triangle, bool addEdges,int color)
 {
     int[] outside = new int[3];
     int[] inside = new int[3];
     int nOutside = 0, nInside = 0;
     int i;
     for (i = 0; i < 3; i++)
     {
         if (VertexDistance(triangle.vertices[i].pos) > 0)
             outside[nOutside++] = i;
         else
             inside[nInside++] = i;
     }
     if (nOutside != 1 && nOutside != 2) return;
     RHVector3[] intersections = new RHVector3[3];
     int nIntersections = 0;
     for (int iInside = 0; iInside < nInside; iInside++)
     {
         for (int iOutside = 0; iOutside < nOutside; iOutside++)
         {
             RHVector3 v1 = triangle.vertices[inside[iInside]].pos;
             RHVector3 v2 = triangle.vertices[outside[iOutside]].pos;
             double dist1 = VertexDistance(v1);
             double dist2 = VertexDistance(v2);
             double pos = Math.Abs(dist1) / Math.Abs(dist2 - dist1);
             intersections[nIntersections++] = new RHVector3(
                 v1.x+pos*(v2.x-v1.x),
                 v1.y+pos*(v2.y-v1.y),
                 v1.z+pos*(v2.z-v1.z)
                 );
         }
     }
     if (nInside == 2)
     {
         if (outside[0] == 1)
         {
             mesh.AddTriangle(triangle.vertices[inside[1]].pos, triangle.vertices[inside[0]].pos, intersections[1], color);
             mesh.AddTriangle(triangle.vertices[inside[0]].pos, intersections[0], intersections[1], color);
         }
         else
         {
             mesh.AddTriangle(triangle.vertices[inside[0]].pos, triangle.vertices[inside[1]].pos, intersections[0], color);
             mesh.AddTriangle(triangle.vertices[inside[1]].pos, intersections[1], intersections[0], color);
         }
     }
     else
     {
         if(inside[0] == 1)
             mesh.AddTriangle(triangle.vertices[inside[0]].pos, intersections[1], intersections[0], color);
         else
             mesh.AddTriangle(triangle.vertices[inside[0]].pos, intersections[0], intersections[1], color);
     }
     if (addEdges)
     {
         if (nInside == 2)
         {
             mesh.AddEdge(triangle.vertices[inside[0]].pos, triangle.vertices[inside[1]].pos, triangle.edges[0].connectedFaces == 2 ? Submesh.MESHCOLOR_EDGE : Submesh.MESHCOLOR_ERROREDGE);
             mesh.AddEdge(triangle.vertices[inside[0]].pos, intersections[0], triangle.edges[1].connectedFaces == 2 ? Submesh.MESHCOLOR_EDGE : Submesh.MESHCOLOR_ERROREDGE);
             mesh.AddEdge(triangle.vertices[inside[1]].pos, intersections[1], triangle.edges[2].connectedFaces == 2 ? Submesh.MESHCOLOR_EDGE : Submesh.MESHCOLOR_ERROREDGE);
         }
         else
         {
             for (int iInter = 0; iInter < nIntersections; iInter++)
             {
                 mesh.AddEdge(triangle.vertices[inside[0]].pos, intersections[iInter], triangle.edges[(inside[0]+2*iInter) % 3].connectedFaces == 2 ? Submesh.MESHCOLOR_EDGE : Submesh.MESHCOLOR_ERROREDGE);
             }
         }
     }
     if (nIntersections == 2)
         mesh.AddEdge(intersections[0], intersections[1], Submesh.MESHCOLOR_CUT_EDGE);
 }
Exemplo n.º 24
0
        // Milton:  Efficient AABB/triangle intersection algoirthm
        // from http://stackoverflow.com/questions/17458562/efficient-aabb-triangle-intersection-in-c-sharp
        public bool overlapTri(TopoTriangle triangle)
        {
            double triangleMin, triangleMax;
            double boxMin, boxMax;

            /*// Test the box normals (x-, y- and z-axes)
             * var boxNormals = new IVector[] {
             *  new Vector(1,0,0),
             *  new Vector(0,1,0),
             *  new Vector(0,0,1)
             * };*/
            RHVector3[] boxNormals =
            {
                new RHVector3(1, 0, 0),
                new RHVector3(0, 1, 0),
                new RHVector3(0, 0, 1)
            };

            /*
             * for (int i = 0; i < 3; i++)
             * {
             *  RHVector3 n = boxNormals[i];
             *  Project(triangle.vertices, boxNormals[i], out triangleMin, out triangleMax);
             *  if (triangleMax < box.Start.Coords[i] || triangleMin > box.End.Coords[i])
             *      return false; // No intersection possible.
             * }*/
            Project(triangle.vertices, boxNormals[0], out triangleMin, out triangleMax);
            if (triangleMax < minPoint.x || triangleMin > maxPoint.x)
            {
                return(false);
            }
            Project(triangle.vertices, boxNormals[1], out triangleMin, out triangleMax);
            if (triangleMax < minPoint.y || triangleMin > maxPoint.y)
            {
                return(false);
            }
            Project(triangle.vertices, boxNormals[2], out triangleMin, out triangleMax);
            if (triangleMax < minPoint.z || triangleMin > maxPoint.z)
            {
                return(false);
            }

            /*// Test the triangle normal
             * double triangleOffset = triangle.Normal.Dot(triangle.A);
             * Project(box.Vertices, triangle.Normal, out boxMin, out boxMax);
             * if (boxMax < triangleOffset || boxMin > triangleOffset)
             *  return false; // No intersection possible.*/
            double triangleOffset = triangle.normal.ScalarProduct(triangle.vertices[0].pos);

            Project(getVertices(), triangle.normal, out boxMin, out boxMax);
            if (boxMin < triangleOffset || boxMax > triangleOffset)
            {
                return(false); // No intersection possible.
            }

            /*// Test the nine edge cross-products
             * IVector[] triangleEdges = new IVector[] {
             *  triangle.A.Minus(triangle.B),
             *  triangle.B.Minus(triangle.C),
             *  triangle.C.Minus(triangle.A)
             * }; */
            RHVector3[] triangleEdges =
            {
                triangle.vertices[0].pos.Subtract(triangle.vertices[1].pos),
                triangle.vertices[1].pos.Subtract(triangle.vertices[2].pos),
                triangle.vertices[2].pos.Subtract(triangle.vertices[0].pos)
            };

            for (int i = 0; i < 3; i++)
            {
                for (int j = 0; j < 3; j++)
                {
                    RHVector3 axis = triangleEdges[i].CrossProduct(boxNormals[j]);
                    Project(getVertices(), axis, out boxMin, out boxMax);
                    Project(triangle.vertices, axis, out triangleMin, out triangleMax);
                    if (boxMax < triangleMin || boxMin > triangleMax)
                    {
                        return(false); // No intersection possible
                    }
                }
            }

            return(true);
        }
Exemplo n.º 25
0
 public TopoTriangle IntersectsTriangleAnyTriangle(TopoTriangle test)
 {
     HashSet<TopoTriangle> candidates = triangles.FindIntersectionCandidates(test);
     foreach (TopoTriangle candidate in candidates)
     {
         if (test.Intersects(candidate)) return candidate;
     }
     return null;
 }
Exemplo n.º 26
0
 private void FloodFillNormals(TopoTriangle good)
 {
     good.algHelper = 1;
     HashSet<TopoTriangle> front = new HashSet<TopoTriangle>();
     front.Add(good);
     HashSet<TopoTriangle> newFront = new HashSet<TopoTriangle>();
     int i;
     int cnt = 0;
     while (front.Count > 0)
     {
         foreach (TopoTriangle t in front)
         {
             cnt++;
             if((cnt % 2000) == 0)
                 Application.DoEvents();
             for (i = 0; i < 3; i++)
             {
                 foreach (TopoTriangle test in t.edges[i].faces)
                 {
                     if (t != test && test.algHelper == 0)
                     {
                         test.algHelper = 1;
                         newFront.Add(test);
                         if (!t.SameNormalOrientation(test))
                         {
                             test.FlipDirection();
                             updatedNormals++;
                         }
                     }
                 }
             }
         }
         front = newFront;
         newFront = new HashSet<TopoTriangle>();
     }
 }
Exemplo n.º 27
0
 public TopoTriangleNode FindNodeForTriangle(TopoTriangle triangle)
 {
     if (triangles != null) return this;
     if (triangle.boundingBox.maxPoint[dimension] < middlePosition)
         return left.FindNodeForTriangle(triangle);
     else if (triangle.boundingBox.minPoint[dimension] > middlePosition)
         return right.FindNodeForTriangle(triangle);
     else
         return middle.FindNodeForTriangle(triangle);
 }
Exemplo n.º 28
0
 public void Merge(TopoModel model, Matrix4 trans)
 {
     int nOld = vertices.Count;
     int i = 0;
     List<TopoVertex> vcopy = new List<TopoVertex>(model.vertices.Count);
     foreach (TopoVertex v in model.vertices)
     {
         v.id = i++;
         TopoVertex newVert = new TopoVertex(v.id, v.pos, trans);
         addVertex(newVert);
         vcopy.Add(newVert);
     }
     foreach (TopoTriangle t in model.triangles)
     {
         TopoTriangle triangle = new TopoTriangle(this, vcopy[t.vertices[0].id], vcopy[t.vertices[1].id], vcopy[t.vertices[2].id]);
         triangle.RecomputeNormal();
         triangles.Add(triangle);
     }
     RemoveUnusedDatastructures();
     intersectionsUpToDate = false;
 }