public static AxisAlignedBox3d BoundsT(IMesh mesh, IEnumerable <int> triangleIndices, Func <Vector3d, Vector3d> TransformF = null) { AxisAlignedBox3d bounds = AxisAlignedBox3d.Empty; if (TransformF == null) { foreach (int tid in triangleIndices) { Index3i tri = mesh.GetTriangle(tid); for (int j = 0; j < 3; ++j) { bounds.Contain(mesh.GetVertex(tri[j])); } } } else { foreach (int tid in triangleIndices) { Index3i tri = mesh.GetTriangle(tid); for (int j = 0; j < 3; ++j) { bounds.Contain(TransformF(mesh.GetVertex(tri[j]))); } } } return(bounds); }
public AxisAlignedBox3d Bounds() { Vector3d o = Radius * Vector3d.One, p0 = Segment.P0, p1 = Segment.P1; AxisAlignedBox3d box = new AxisAlignedBox3d(p0 - o, p0 + o); box.Contain(p1 - o); box.Contain(p1 + o); return(box); }
int split_point_set_sorted(int[] pt_indices, Vector3d[] positions, int iStart, int iCount, int depth, int minIndexCount, boxes_set leafs, boxes_set nodes, out AxisAlignedBox3d box) { box = AxisAlignedBox3d.Empty; int iBox = -1; if (iCount < minIndexCount) { // append new points box iBox = leafs.iBoxCur++; leafs.box_to_index.insert(leafs.iIndicesCur, iBox); leafs.index_list.insert(iCount, leafs.iIndicesCur++); for (int i = 0; i < iCount; ++i) { leafs.index_list.insert(pt_indices[iStart + i], leafs.iIndicesCur++); box.Contain(points.GetVertex(pt_indices[iStart + i])); } leafs.box_centers.insert(box.Center, iBox); leafs.box_extents.insert(box.Extents, iBox); return(-(iBox + 1)); } AxisComp c = new AxisComp() { Axis = depth % 3 }; Array.Sort(positions, pt_indices, iStart, iCount, c); int mid = iCount / 2; int n0 = mid; int n1 = iCount - mid; // create child boxes AxisAlignedBox3d box1; int child0 = split_point_set_sorted(pt_indices, positions, iStart, n0, depth + 1, minIndexCount, leafs, nodes, out box); int child1 = split_point_set_sorted(pt_indices, positions, iStart + mid, n1, depth + 1, minIndexCount, leafs, nodes, out box1); box.Contain(box1); // append new box iBox = nodes.iBoxCur++; nodes.box_to_index.insert(nodes.iIndicesCur, iBox); nodes.index_list.insert(child0, nodes.iIndicesCur++); nodes.index_list.insert(child1, nodes.iIndicesCur++); nodes.box_centers.insert(box.Center, iBox); nodes.box_extents.insert(box.Extents, iBox); return(iBox); }
public AxisAlignedBox3d GetBounds() { AxisAlignedBox3d box = AxisAlignedBox3d.Empty; for (int i = 0; i < Vertices.Length; ++i) box.Contain(Mesh.GetVertex(Vertices[i])); return box; }
public AxisAlignedBox3d Bounds() { AxisAlignedBox3d box = A.Bounds(); box.Contain(B.Bounds()); box.Expand(0.25 * box.MaxDim); return(box); }
public static AxisAlignedBox3d Bounds(IEnumerable <DMesh3> meshes) { AxisAlignedBox3d bounds = AxisAlignedBox3d.Empty; foreach (DMesh3 mesh in meshes) { bounds.Contain(mesh.CachedBounds); } return(bounds); }
/// <summary> /// compute axis-aligned bounds of set of points after transforming into frame f /// </summary> public static AxisAlignedBox3d BoundsInFrame(IEnumerable <Vector3d> values, Frame3f f) { AxisAlignedBox3d box = AxisAlignedBox3d.Empty; foreach (Vector3d v in values) { box.Contain(f.ToFrameP(v)); } return(box); }
public static AxisAlignedBox3d Bounds <T>(IEnumerable <T> values, Func <T, Vector3d> PositionF) { AxisAlignedBox3d box = AxisAlignedBox3d.Empty; foreach (T t in values) { box.Contain(PositionF(t)); } return(box); }
public static AxisAlignedBox3d Bounds(IEnumerable <Vector3d> positions) { AxisAlignedBox3d box = AxisAlignedBox3d.Empty; foreach (Vector3d v in positions) { box.Contain(v); } return(box); }
/// <summary> /// compute axis-aligned bounds of set of points after transforming /// </summary> public static AxisAlignedBox3d Bounds(IEnumerable <Vector3d> values, TransformSequence xform) { AxisAlignedBox3d box = AxisAlignedBox3d.Empty; foreach (Vector3d v in values) { box.Contain(xform.TransformP(v)); } return(box); }
public AxisAlignedBox3d GetBoundingBox() { AxisAlignedBox3d box = AxisAlignedBox3d.Empty; foreach (Vector3d v in vertices) { box.Contain(v); } return(box); }
public static AxisAlignedBox3d Bounds(IPointSet source) { AxisAlignedBox3d bounds = AxisAlignedBox3d.Empty; foreach (int vid in source.VertexIndices()) { bounds.Contain(source.GetVertex(vid)); } return(bounds); }
public static AxisAlignedBox3d BoundsV(IMesh mesh, IEnumerable <int> vertexIndices, Func <Vector3d, Vector3d> TransformF = null) { AxisAlignedBox3d bounds = AxisAlignedBox3d.Empty; if (TransformF == null) { foreach (int vid in vertexIndices) { bounds.Contain(mesh.GetVertex(vid)); } } else { foreach (int vid in vertexIndices) { bounds.Contain(TransformF(mesh.GetVertex(vid))); } } return(bounds); }
public static AxisAlignedBox3d Bounds(DMesh3 mesh, Func <Vector3d, Vector3d> TransformF) { AxisAlignedBox3d bounds = AxisAlignedBox3d.Empty; if (TransformF == null) { foreach (Vector3d v in mesh.Vertices()) { bounds.Contain(v); } } else { foreach (Vector3d v in mesh.Vertices()) { Vector3d vT = TransformF(v); bounds.Contain(ref vT); } } return(bounds); }
public static AxisAlignedBox3d Bounds(IMesh mesh, Func <Vector3d, Vector3d> TransformF) { AxisAlignedBox3d bounds = AxisAlignedBox3d.Empty; if (TransformF == null) { foreach (int vID in mesh.VertexIndices()) { bounds.Contain(mesh.GetVertex(vID)); } } else { foreach (int vID in mesh.VertexIndices()) { Vector3d vT = TransformF(mesh.GetVertex(vID)); bounds.Contain(ref vT); } } return(bounds); }
public AxisAlignedBox3d GetBoundingBox() { // [RMS] problem w/ readonly because vector is a class... //AxisAlignedBox3d box = AxisAlignedBox3d.Empty; AxisAlignedBox3d box = new AxisAlignedBox3d(false); foreach (Vector3d v in vertices) { box.Contain(v); } return(box); }
/// <summary> /// calculate extents of mesh along axes of frame, with optional transform /// </summary> public static AxisAlignedBox3d BoundsInFrame(DMesh3 mesh, Frame3f frame, Func <Vector3d, Vector3d> TransformF = null) { AxisAlignedBox3d bounds = AxisAlignedBox3d.Empty; if (TransformF == null) { foreach (Vector3d v in mesh.Vertices()) { Vector3d fv = frame.ToFrameP(v); bounds.Contain(ref fv); } } else { foreach (Vector3d v in mesh.Vertices()) { Vector3d vT = TransformF(v); Vector3d fv = frame.ToFrameP(ref vT); bounds.Contain(ref fv); } } return(bounds); }
public AxisAlignedBox3d GetBounds() { if (vertices.Count == 0) { return(AxisAlignedBox3d.Empty); } AxisAlignedBox3d box = new AxisAlignedBox3d(vertices[0]); for (int i = 1; i < vertices.Count; ++i) { box.Contain(vertices[i]); } return(box); }
// AABB of transformed AABB (corners) public static AxisAlignedBox3d Bounds(ref AxisAlignedBox3d boxIn, Func <Vector3d, Vector3d> TransformF) { if (TransformF == null) { return(boxIn); } AxisAlignedBox3d box = new AxisAlignedBox3d(TransformF(boxIn.Corner(0))); for (int i = 1; i < 8; ++i) { box.Contain(TransformF(boxIn.Corner(i))); } return(box); }
public AxisAlignedBox3d ToAABB() { // [TODO] probably more efficient way to do this...at minimum can move center-shift // to after the containments... Vector3d extAxis0 = Extent.x * AxisX; Vector3d extAxis1 = Extent.y * AxisY; Vector3d extAxis2 = Extent.z * AxisZ; AxisAlignedBox3d result = new AxisAlignedBox3d(Center - extAxis0 - extAxis1 - extAxis2); result.Contain(Center + extAxis0 - extAxis1 - extAxis2); result.Contain(Center + extAxis0 + extAxis1 - extAxis2); result.Contain(Center - extAxis0 + extAxis1 - extAxis2); result.Contain(Center - extAxis0 - extAxis1 + extAxis2); result.Contain(Center + extAxis0 - extAxis1 + extAxis2); result.Contain(Center + extAxis0 + extAxis1 + extAxis2); result.Contain(Center - extAxis0 + extAxis1 + extAxis2); return(result); }
protected virtual DMesh3 BuildMesh_TolerantWeld(STLSolid solid, double weld_tolerance) { var builder = new DMesh3Builder(); builder.AppendNewMesh(false, false, false, false); DVectorArray3f vertices = solid.Vertices; int N = vertices.Count; int[] mapV = new int[N]; AxisAlignedBox3d bounds = AxisAlignedBox3d.Empty; for (int i = 0; i < N; ++i) { bounds.Contain(vertices[i]); } // [RMS] because we are only searching within tiny radius, there is really no downside to // using lots of bins here, except memory usage. If we don't, and the mesh has a ton of triangles // very close together (happens all the time on big meshes!), then this step can start // to take an *extremely* long time! int num_bins = 256; if (N > 100000) { num_bins = 512; } if (N > 1000000) { num_bins = 1024; } if (N > 2000000) { num_bins = 2048; } if (N > 5000000) { num_bins = 4096; } var uniqueV = new PointHashGrid3d <int>(bounds.MaxDim / (float)num_bins, -1); var pos = new Vector3f[N]; for (int vi = 0; vi < N; ++vi) { Vector3f v = vertices[vi]; var pair = uniqueV.FindNearestInRadius(v, weld_tolerance, (vid) => { return(v.Distance(pos[vid])); }); if (pair.Key == -1) { int vid = builder.AppendVertex(v.x, v.y, v.z); uniqueV.InsertPoint(vid, v); mapV[vi] = vid; pos[vid] = v; } else { mapV[vi] = pair.Key; } } append_mapped_triangles(solid, builder, mapV); return(builder.Meshes[0]); }
int split_point_set_midpoint(int[] pt_indices, Vector3d[] positions, int iStart, int iCount, int depth, int minIndexCount, boxes_set leafs, boxes_set nodes, out AxisAlignedBox3d box) { box = AxisAlignedBox3d.Empty; int iBox = -1; if (iCount < minIndexCount) { // append new points box iBox = leafs.iBoxCur++; leafs.box_to_index.insert(leafs.iIndicesCur, iBox); leafs.index_list.insert(iCount, leafs.iIndicesCur++); for (int i = 0; i < iCount; ++i) { leafs.index_list.insert(pt_indices[iStart + i], leafs.iIndicesCur++); box.Contain(points.GetVertex(pt_indices[iStart + i])); } leafs.box_centers.insert(box.Center, iBox); leafs.box_extents.insert(box.Extents, iBox); return(-(iBox + 1)); } //compute interval along an axis and find midpoint int axis = depth % 3; Interval1d interval = Interval1d.Empty; for (int i = 0; i < iCount; ++i) { interval.Contain(positions[iStart + i][axis]); } double midpoint = interval.Center; int n0, n1; if (Math.Abs(interval.a - interval.b) > MathUtil.ZeroTolerance) { // we have to re-sort the centers & indices lists so that centers < midpoint // are first, so that we can recurse on the two subsets. We walk in from each side, // until we find two out-of-order locations, then we swap them. int l = 0; int r = iCount - 1; while (l < r) { // [RMS] is <= right here? if v.axis == midpoint, then this loop // can get stuck unless one of these has an equality test. But // I did not think enough about if this is the right thing to do... while (positions[iStart + l][axis] <= midpoint) { l++; } while (positions[iStart + r][axis] > midpoint) { r--; } if (l >= r) { break; //done! } //swap Vector3d tmpc = positions[iStart + l]; positions[iStart + l] = positions[iStart + r]; positions[iStart + r] = tmpc; int tmpt = pt_indices[iStart + l]; pt_indices[iStart + l] = pt_indices[iStart + r]; pt_indices[iStart + r] = tmpt; } n0 = l; n1 = iCount - n0; Debug.Assert(n0 >= 1 && n1 >= 1); } else { // interval is near-empty, so no point trying to do sorting, just split half and half n0 = iCount / 2; n1 = iCount - n0; } // create child boxes AxisAlignedBox3d box1; int child0 = split_point_set_midpoint(pt_indices, positions, iStart, n0, depth + 1, minIndexCount, leafs, nodes, out box); int child1 = split_point_set_midpoint(pt_indices, positions, iStart + n0, n1, depth + 1, minIndexCount, leafs, nodes, out box1); box.Contain(box1); // append new box iBox = nodes.iBoxCur++; nodes.box_to_index.insert(nodes.iIndicesCur, iBox); nodes.index_list.insert(child0, nodes.iIndicesCur++); nodes.index_list.insert(child1, nodes.iIndicesCur++); nodes.box_centers.insert(box.Center, iBox); nodes.box_extents.insert(box.Extents, iBox); return(iBox); }