}//judge if a voxel is inside the surface public static void InitAdj6(Int16Triple[] adjPoints6, Int16Triple p) { adjPoints6[0].X = p.X; adjPoints6[0].Y = p.Y + 1; adjPoints6[0].Z = p.Z; adjPoints6[1].X = p.X; adjPoints6[1].Y = p.Y - 1; adjPoints6[1].Z = p.Z; adjPoints6[2].X = p.X + 1; adjPoints6[2].Y = p.Y; adjPoints6[2].Z = p.Z; adjPoints6[3].X = p.X - 1; adjPoints6[3].Y = p.Y; adjPoints6[3].Z = p.Z; adjPoints6[4].X = p.X; adjPoints6[4].Y = p.Y; adjPoints6[4].Z = p.Z + 1; adjPoints6[5].X = p.X; adjPoints6[5].Y = p.Y; adjPoints6[5].Z = p.Z - 1; }//initialize poistions of the 6-adjacency points
private int FindXLeft(int x, int y, int z) { int xleft = x - 1; while (true) { if (xleft == -1)// || flagsMap.GetFlagOn(xleft, y, z)) { break; } else { if (IncludePredicate(xleft, y, z)) { Int16Triple t = new Int16Triple(xleft, y, z); Process(xleft, y, z); xleft--; } else { break; } } } return(xleft + 1); }
private void ExtractSquare(int r, Int16Triple p, MeshBuilder_IntegerVertex mb) { int p0x, p0y, p0z, p1x, p1y, p1z, p2x, p2y, p2z;// Int16Triple deltaA0 = VertexIndexToPositionDelta[AdjIndexToVertexIndices[r][0].X]; Int16Triple deltaA1 = VertexIndexToPositionDelta[AdjIndexToVertexIndices[r][0].Y]; Int16Triple deltaA2 = VertexIndexToPositionDelta[AdjIndexToVertexIndices[r][0].Z]; p0x = p.X + deltaA0.X; p0y = p.Y + deltaA0.Y; p0z = p.Z + deltaA0.Z; p1x = p.X + deltaA1.X; p1y = p.Y + deltaA1.Y; p1z = p.Z + deltaA1.Z; p2x = p.X + deltaA2.X; p2y = p.Y + deltaA2.Y; p2z = p.Z + deltaA2.Z; mb.AddTriangle(new Int16Triple(p0x, p0y, p0z), new Int16Triple(p1x, p1y, p1z), new Int16Triple(p2x, p2y, p2z)); Int16Triple deltaB0 = VertexIndexToPositionDelta[AdjIndexToVertexIndices[r][1].X]; Int16Triple deltaB1 = VertexIndexToPositionDelta[AdjIndexToVertexIndices[r][1].Y]; Int16Triple deltaB2 = VertexIndexToPositionDelta[AdjIndexToVertexIndices[r][1].Z]; p0x = p.X + deltaB0.X; p0y = p.Y + deltaB0.Y; p0z = p.Z + deltaB0.Z; p1x = p.X + deltaB1.X; p1y = p.Y + deltaB1.Y; p1z = p.Z + deltaB1.Z; p2x = p.X + deltaB2.X; p2y = p.Y + deltaB2.Y; p2z = p.Z + deltaB2.Z; mb.AddTriangle(new Int16Triple(p0x, p0y, p0z), new Int16Triple(p1x, p1y, p1z), new Int16Triple(p2x, p2y, p2z)); }
private int FindXRight(int x, int y, int z) { int xright = x + 1; while (true) { if (xright == bmp.width)// || flagsMap.GetFlagOn(xright, y, z)) { break; } else { if (IncludePredicate(xright, y, z)) { Int16Triple t = new Int16Triple(xright, y, z); Process(xright, y, z); xright++; } else { break; } } } return(xright - 1); }
public void AddTriangle(Int16Triple p0, Int16Triple p1, Int16Triple p2) { int p0i; int p1i; int p2i; int index = 0; bool hasValue; hasValue = hashMap.GetHashValue(p0.X, p0.Y, p0.Z, ref index); if (!hasValue) { p0i = mesh.AddVertex(new Point3d(p0.X, p0.Y, p0.Z)); hashMap.SetHashValue(p0.X, p0.Y, p0.Z, p0i); } else { p0i = index; } hasValue = hashMap.GetHashValue(p1.X, p1.Y, p1.Z, ref index); if (!hasValue) { p1i = mesh.AddVertex(new Point3d(p1.X, p1.Y, p1.Z)); hashMap.SetHashValue(p1.X, p1.Y, p1.Z, p1i); } else { p1i = index; } hasValue = hashMap.GetHashValue(p2.X, p2.Y, p2.Z, ref index); if (!hasValue) { p2i = mesh.AddVertex(new Point3d(p2.X, p2.Y, p2.Z)); hashMap.SetHashValue(p2.X, p2.Y, p2.Z, p2i); } else { p2i = index; } Triangle t = new Triangle(p0i, p1i, p2i); mesh.AddFace(t); }
public Mesh GeneratorSurface() { int Width = bmp.width; int Height = bmp.height; int Depth = bmp.depth; Int16Triple[] adjPoints6 = new Int16Triple[6]; MeshBuilder_IntegerVertex mb = new MeshBuilder_IntegerVertex(bmp.width + 2, bmp.height + 2, bmp.depth + 2); for (int k = 0; k <= Depth - 1; k++) { for (int j = 0; j <= Height - 1; j++) { for (int i = 0; i <= Width - 1; i++) { if (IsInside(i, j, k)) { Int16Triple p = new Int16Triple(i, j, k); InitAdj6(adjPoints6, p); for (int r = 0; r < adjPoints6.Length; r++) { Int16Triple t = adjPoints6[r]; if (!IsInside(t.X, t.Y, t.Z)) { ExtractSquare(r, p, mb); } } } } } } Mesh m = mb.GetMesh(); for (int i = 0; i < m.Vertices.Count; i++) { Point3d p = m.Vertices[i]; p.X -= 0.5f; p.Y -= 0.5f; p.Z -= 0.5f; }//若需要真实位置,则都得平移回去 return(m); }
public List <Int16Triple> GetVoxels() { List <Int16Triple> list = new List <Int16Triple>(); ByteMatrix mat = FillMesh(); for (int k = 0; k < mat.depth; k++) { for (int j = 0; j < mat.height; j++) { for (int i = 0; i < mat.width; i++) { if (mat.GetValue(i, j, k) == 255) { Int16Triple t = new Int16Triple(i + mat.stx, j + mat.sty, k + mat.stz); list.Add(t); } } } } return(list); }
public virtual void ExcuteSpanFill(ByteMatrix data, Int16Triple seed, byte includeColor, byte replaceColor) { this.includeColor = includeColor; this.replaceColor = replaceColor; this.container = new Stack <Span>(); this.bmp = data; Process(seed.X, seed.Y, seed.Z); Span seedspan = new Span(); seedspan.XLeft = seed.X; seedspan.XRight = seed.X; seedspan.Y = seed.Y; seedspan.Z = seed.Z; seedspan.ParentDirection = ParentDirections.Non; seedspan.Extended = ExtendTypes.UnRez; container.Push(seedspan); while (container.Count != 0) { Span span = container.Pop(); #region AllRez if (span.Extended == ExtendTypes.AllRez) { if (span.ParentDirection == ParentDirections.Y2) { if (span.Y - 1 >= 0)//[spx-spy,y-1,z] { CheckRange(span.XLeft, span.XRight, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Z - 1 >= 0)//[spx-spy,y,z-1] { CheckRange(span.XLeft, span.XRight, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < data.depth)//[spx-spy,y,z+1] { CheckRange(span.XLeft, span.XRight, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Y0) { if (span.Y + 1 < bmp.height)//[spx-spy,y+1,z] { CheckRange(span.XLeft, span.XRight, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0)//[spx-spy,y,z-1] { CheckRange(span.XLeft, span.XRight, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < data.depth)//[spx-spy,y,z+1] { CheckRange(span.XLeft, span.XRight, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Z2) { if (span.Y - 1 >= 0)//[spx-spy,y-1,z] { CheckRange(span.XLeft, span.XRight, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height)//[spx-spy,y+1,z] { CheckRange(span.XLeft, span.XRight, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0)//[spx-spy,y,z-1] { CheckRange(span.XLeft, span.XRight, span.Y, span.Z - 1, ParentDirections.Z2); } continue; } if (span.ParentDirection == ParentDirections.Z0) { if (span.Y - 1 >= 0) { CheckRange(span.XLeft, span.XRight, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height) { CheckRange(span.XLeft, span.XRight, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z + 1 < data.depth) { CheckRange(span.XLeft, span.XRight, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } throw new Exception(); } #endregion #region UnRez if (span.Extended == ExtendTypes.UnRez) { int xl = FindXLeft(span.XLeft, span.Y, span.Z); int xr = FindXRight(span.XRight, span.Y, span.Z); if (span.ParentDirection == ParentDirections.Y2) { if (span.Y - 1 >= 0) { CheckRange(xl, xr, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height) { if (xl != span.XLeft) { CheckRange(xl, span.XLeft, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.XRight != xr) { CheckRange(span.XRight, xr, span.Y + 1, span.Z, ParentDirections.Y0); } } if (span.Z - 1 >= 0) { CheckRange(xl, xr, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth) { CheckRange(xl, xr, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Y0) { if (span.Y + 1 < bmp.height) { CheckRange(xl, xr, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Y - 1 >= 0) { if (xl != span.XLeft) { CheckRange(xl, span.XLeft, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.XRight != xr) { CheckRange(span.XRight, xr, span.Y - 1, span.Z, ParentDirections.Y2); } } if (span.Z - 1 >= 0) { CheckRange(xl, xr, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth) { CheckRange(xl, xr, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Z2) { if (span.Y - 1 >= 0) { CheckRange(xl, xr, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height) { CheckRange(xl, xr, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0) { CheckRange(xl, xr, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth) { if (xl != span.XLeft) { CheckRange(xl, span.XLeft, span.Y, span.Z + 1, ParentDirections.Z0); } if (span.XRight != xr) { CheckRange(span.XRight, xr, span.Y, span.Z + 1, ParentDirections.Z0); } } continue; } if (span.ParentDirection == ParentDirections.Z0) { if (span.Y - 1 >= 0) { CheckRange(xl, xr, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height) { CheckRange(xl, xr, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0) { if (xl != span.XLeft) { CheckRange(xl, span.XLeft, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.XRight != xr) { CheckRange(span.XRight, xr, span.Y, span.Z - 1, ParentDirections.Z2); } } if (span.Z + 1 < bmp.depth) { CheckRange(xl, xr, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Non) { if (span.Y + 1 < bmp.height) { CheckRange(xl, xr, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Y - 1 >= 0) { CheckRange(xl, xr, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Z - 1 >= 0) { CheckRange(xl, xr, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth) { CheckRange(xl, xr, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } throw new Exception(); } #endregion #region LeftRequired if (span.Extended == ExtendTypes.LeftRequired) { int xl = FindXLeft(span.XLeft, span.Y, span.Z); if (span.ParentDirection == ParentDirections.Y2) { if (span.Y - 1 >= 0) { CheckRange(xl, span.XRight, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height && xl != span.XLeft) { CheckRange(xl, span.XLeft, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0) { CheckRange(xl, span.XRight, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth) { CheckRange(xl, span.XRight, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Y0) { if (span.Y - 1 >= 0 && xl != span.XLeft) { CheckRange(xl, span.XLeft, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height) { CheckRange(xl, span.XRight, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0) { CheckRange(xl, span.XRight, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth) { CheckRange(xl, span.XRight, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Z2) { if (span.Y - 1 >= 0) { CheckRange(xl, span.XRight, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height) { CheckRange(xl, span.XRight, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0) { CheckRange(xl, span.XRight, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth && xl != span.XLeft) { CheckRange(xl, span.XLeft, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Z0) { if (span.Y - 1 >= 0) { CheckRange(xl, span.XRight, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height) { CheckRange(xl, span.XRight, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0 && xl != span.XLeft) { CheckRange(xl, span.XLeft, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth) { CheckRange(xl, span.XRight, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } throw new Exception(); } #endregion #region RightRequired if (span.Extended == ExtendTypes.RightRequired) { int xr = FindXRight(span.XRight, span.Y, span.Z); if (span.ParentDirection == ParentDirections.Y2) { if (span.Y - 1 >= 0) { CheckRange(span.XLeft, xr, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height && span.XRight != xr) { CheckRange(span.XRight, xr, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0) { CheckRange(span.XLeft, xr, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth) { CheckRange(span.XLeft, xr, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Y0) { if (span.Y + 1 < bmp.height) { CheckRange(span.XLeft, xr, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Y - 1 >= 0 && span.XRight != xr) { CheckRange(span.XRight, xr, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Z - 1 >= 0) { CheckRange(span.XLeft, xr, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth) { CheckRange(span.XLeft, xr, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Z2) { if (span.Y - 1 >= 0) { CheckRange(span.XLeft, xr, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height) { CheckRange(span.XLeft, xr, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0) { CheckRange(span.XLeft, xr, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth && span.XRight != xr) { CheckRange(span.XRight, xr, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } if (span.ParentDirection == ParentDirections.Z0) { if (span.Y - 1 >= 0) { CheckRange(span.XLeft, xr, span.Y - 1, span.Z, ParentDirections.Y2); } if (span.Y + 1 < bmp.height) { CheckRange(span.XLeft, xr, span.Y + 1, span.Z, ParentDirections.Y0); } if (span.Z - 1 >= 0 && span.XRight != xr) { CheckRange(span.XRight, xr, span.Y, span.Z - 1, ParentDirections.Z2); } if (span.Z + 1 < bmp.depth) { CheckRange(span.XLeft, xr, span.Y, span.Z + 1, ParentDirections.Z0); } continue; } throw new Exception(); } #endregion } }