public static boolean contains( final WB_Coordinate p, final WB_Coordinate A, final WB_Coordinate B, final WB_Coordinate C) { if (WB_Epsilon.isZeroSq(WB_Distance.getSqDistanceToLine3D(A, B, C))) { return false; } if (sameSide(p, A, B, C) && sameSide(p, B, A, C) && sameSide(p, C, A, B)) { return true; } return false; }
public boolean isPlanar() { final WB_Plane P = getPlane(); HE_Halfedge he = getHalfedge(); do { if (!WB_Epsilon.isZero(WB_GeometryOp.getDistance3D(he.getVertex(), P))) { return false; } he = he.getNextInFace(); } while (he != getHalfedge()); return true; }
/** @return */ public WB_Plane getPlane() { WB_Coord fn = getFaceNormal(); if (WB_Vector.getSqLength3D(fn) < 0.5) { if (WB_Epsilon.isEqualAbs(_halfedge.getVertex().xd(), _halfedge.getEndVertex().xd())) { fn = new WB_Vector(1, 0, 0); } else { fn = new WB_Vector(0, 0, 1); } } return new WB_Plane(getFaceCenter(), fn); }
/** * @param X * @return */ private WB_RBSpline refineKnotRestricted(final double[] X) { final int r = X.length - 1; final int a = knot.span(X[0]); final int b = knot.span(X[r]) + 1; final WB_PointHomogeneous[] Q = new WB_PointHomogeneous[n + r + 2]; final WB_NurbsKnot Ubar = new WB_NurbsKnot(n + r + 2, p); for (int j = 0; j <= (a - p); j++) { Q[j] = new WB_PointHomogeneous(wpoints[j]); } for (int j = b - 1; j <= n; j++) { Q[j + r + 1] = new WB_PointHomogeneous(wpoints[j]); } for (int j = 0; j <= a; j++) { Ubar.setValue(j, knot.value(j)); } for (int j = b + p; j <= knot.m; j++) { Ubar.setValue(j + r + 1, knot.value(j)); } int i = (b + p) - 1; int k = b + p + r; for (int j = r; j >= 0; j--) { while ((X[j] <= knot.value(i)) && (i > a)) { Q[k - p - 1] = new WB_PointHomogeneous(wpoints[i - p - 1]); Ubar.setValue(k, knot.value(i)); k = k - 1; i = i - 1; } Q[k - p - 1] = new WB_PointHomogeneous(Q[k - p]); for (int el = 1; el <= p; el++) { final int ind = (k - p) + el; double alpha = Ubar.value(k + el) - X[j]; if (WB_Epsilon.isZero(alpha)) { Q[ind - 1] = new WB_PointHomogeneous(Q[ind]); } else { alpha /= (Ubar.value(k + el) - knot.value((i - p) + el)); Q[ind - 1] = WB_PointHomogeneous.interpolate(Q[ind], Q[ind - 1], alpha); } } Ubar.setValue(k, X[j]); k--; } return new WB_RBSpline(Q, Ubar); }
@Override public HE_Mesh apply(final HE_Mesh mesh) { if (mesh.selectAllBoundaryEdges().numberOfEdges() > 0) { throw new IllegalArgumentException("HES_DooSabin only supports closed meshes at this time."); } Iterator<HE_Face> fItr = mesh.fItr(); final FastMap<Integer, Integer> halfedgeCorrelation = new FastMap<Integer, Integer>(); final ArrayList<WB_Point> newVertices = new ArrayList<WB_Point>(); HE_Face f; HE_Halfedge he; WB_Point fc; int vertexCount = 0; double div = 1.0 + 2.0 * edgeFactor + faceFactor; if (WB_Epsilon.isZero(div)) { div = 1.0; } if (absolute) { div = 4.0; } while (fItr.hasNext()) { f = fItr.next(); he = f.getHalfedge(); fc = f.getFaceCenter(); do { final WB_Point p = fc.multAndCopy(faceFactor); p.add(he.getVertex()); p.add(he.getHalfedgeCenter().multAndCopy(edgeFactor)); p.add(he.getPrevInFace().getHalfedgeCenter().multAndCopy(edgeFactor)); p.div(div); if (absolute) { final double dcurrent = WB_Distance.distance(p, he.getVertex()); p.sub(he.getVertex()); p.mult(d / dcurrent); p.add(he.getVertex()); } halfedgeCorrelation.put(he.key(), vertexCount); vertexCount++; newVertices.add(p); he = he.getNextInFace(); } while (he != f.getHalfedge()); } final int[][] faces = new int[mesh.numberOfFaces() + mesh.numberOfEdges() + mesh.numberOfVertices()][]; final int[] labels = new int[mesh.numberOfFaces() + mesh.numberOfEdges() + mesh.numberOfVertices()]; final int[] noe = {mesh.numberOfFaces(), mesh.numberOfEdges(), mesh.numberOfVertices()}; int currentFace = 0; fItr = mesh.fItr(); while (fItr.hasNext()) { f = fItr.next(); faces[currentFace] = new int[f.getFaceOrder()]; he = f.getHalfedge(); int i = 0; labels[currentFace] = currentFace; do { faces[currentFace][i] = halfedgeCorrelation.get(he.key()); he = he.getNextInFace(); i++; } while (he != f.getHalfedge()); currentFace++; } final Iterator<HE_Edge> eItr = mesh.eItr(); HE_Edge e; int currentEdge = 0; while (eItr.hasNext()) { e = eItr.next(); faces[currentFace] = new int[4]; faces[currentFace][3] = halfedgeCorrelation.get(e.getHalfedge().key()); faces[currentFace][2] = halfedgeCorrelation.get(e.getHalfedge().getNextInFace().key()); faces[currentFace][1] = halfedgeCorrelation.get(e.getHalfedge().getPair().key()); faces[currentFace][0] = halfedgeCorrelation.get(e.getHalfedge().getPair().getNextInFace().key()); labels[currentFace] = currentEdge; currentEdge++; currentFace++; } final Iterator<HE_Vertex> vItr = mesh.vItr(); HE_Vertex v; int currentVertex = 0; while (vItr.hasNext()) { v = vItr.next(); faces[currentFace] = new int[v.getVertexOrder()]; he = v.getHalfedge(); int i = v.getVertexOrder() - 1; do { faces[currentFace][i] = halfedgeCorrelation.get(he.key()); he = he.getNextInVertex(); i--; } while (he != v.getHalfedge()); labels[currentFace] = currentVertex; currentVertex++; currentFace++; } final HEC_FromFacelist fl = new HEC_FromFacelist().setFaces(faces).setVertices(newVertices).setDuplicate(false); mesh.set(fl.create()); fItr = mesh.fItr(); currentFace = 0; faceFaces = new HE_Selection(mesh); edgeFaces = new HE_Selection(mesh); vertexFaces = new HE_Selection(mesh); while (fItr.hasNext()) { f = fItr.next(); f.setLabel(labels[currentFace]); if (currentFace < noe[0]) { faceFaces.add(f); } else if (currentFace < noe[0] + noe[1]) { edgeFaces.add(f); } else { vertexFaces.add(f); } currentFace++; } return mesh; }