public char SegTriInt(tPointi T, tPointi q, tPointi r, tPointd p) { char code = '?'; m = -1; code = SegPlaneInt(T, q, r, p, m); System.Diagnostics.Debug.WriteLine("****M is now after segplaneint: " + m); System.Diagnostics.Debug.WriteLine("SegPlaneInt code= " + code + " , m= " + m + "; p=()" + p.p[Xindex] + " , " + p.p[Yindex] + " , " + p.p[Zindex]); if (code == '0') { return('0'); } else if (code == 'q') { return(InTri3D(T, m, q)); } else if (code == 'r') { return(InTri3D(T, m, r)); } else if (code == 'p') { return(InPlane(T, m, q, r, p)); } else if (code == '1') { return(SegTriCross(T, q, r)); } else /* Error */ { return(code); } }
/*--------------------------------------------------------------------- * Computes N & D and returns index m of largest component. * ---------------------------------------------------------------------*/ public int PlaneCoeff(tPointi T, tPointd N, double D0) { int i; double t; /* Temp storage */ double biggest = 0.0; /* Largest component of normal vector. */ m = 0; /* Index of largest component. */ NormalVec(Vertices[T.p[0]], Vertices[T.p[1]], Vertices[T.p[2]], N); System.Diagnostics.Debug.WriteLine("PlaneCoeff: N=()" + N.p[Xindex] + " , " + N.p[Yindex] + " , " + N.p[Zindex]); D = Dot(Vertices[T.p[0]], N); System.Diagnostics.Debug.WriteLine("D should be in planecoeff" + D); /* Find the largest component of N. */ for (i = 0; i < DIM; i++) { t = (float)(Math.Abs(N.p[i])); if (t > biggest) { biggest = t; m = i; } } return(m); }
/*--------------------------------------------------------------------- * Compute the cross product of (b-a)x(c-a) and place into N. * ---------------------------------------------------------------------*/ public void NormalVec(tPointi a, tPointi b, tPointi c, tPointd N) { N.p[Xindex] = (c.p[Zindex] - a.p[Zindex]) * (b.p[Yindex] - a.p[Yindex]) - (b.p[Zindex] - a.p[Zindex]) * (c.p[Yindex] - a.p[Yindex]); N.p[Yindex] = (b.p[Zindex] - a.p[Zindex]) * (c.p[Xindex] - a.p[Xindex]) - (b.p[Xindex] - a.p[Xindex]) * (c.p[Zindex] - a.p[Zindex]); N.p[Zindex] = (b.p[Xindex] - a.p[Xindex]) * (c.p[Yindex] - a.p[Yindex]) - (b.p[Yindex] - a.p[Yindex]) * (c.p[Xindex] - a.p[Xindex]); }
/*--------------------------------------------------------------------- * Returns the dot product of the two input vectors. * ---------------------------------------------------------------------*/ public double Dot(tPointi a, tPointd b) { int i; double sum = 0.0; for (i = 0; i < DIM; i++) { sum += a.p[i] * b.p[i]; } return(sum); }
public char InPlane(tPointi T, int m, tPointi q, tPointi r, tPointd p) { /* NOT IMPLEMENTED */ return('p'); }
/*--------------------------------------------------------------------- * 'p': The segment lies wholly within the plane. * 'q': The q endpoint is on the plane (but not 'p'). * 'r': The r endpoint is on the plane (but not 'p'). * '0': The segment lies strictly to one side or the other of the plane. * '1': The segement intersects the plane, and 'p' does not hold. * ---------------------------------------------------------------------*/ public char SegPlaneInt(tPointi T, tPointi q, tPointi r, tPointd p, int m) { tPointd N; int D0 = 0; tPointi rq; double num, denom, t; int i; N = new tPointd(); rq = new tPointi(); m = PlaneCoeff(T, N, D0); System.Diagnostics.Debug.WriteLine("m= " + m + "; plane=( " + N.p[Xindex] + " , " + N.p[Yindex] + " , " + N.p[Zindex] + " , " + D + " )"); num = D - Dot(q, N); SubVec(r, q, rq); denom = Dot(rq, N); System.Diagnostics.Debug.WriteLine("SegPlaneInt: num=" + num + " , denom= " + denom); if (denom == 0.0) { /* Segment is parallel to plane. */ if (num == 0.0) /* q is on plane. */ { return('p'); } else { return('0'); } } else { t = num / denom; } System.Diagnostics.Debug.WriteLine("SegPlaneInt: t= " + t); System.Diagnostics.Debug.WriteLine("p in seg plane int is: p=()"); for (i = 0; i < DIM; i++) { p.p[i] = q.p[i] + t * (r.p[i] - q.p[i]); System.Diagnostics.Debug.WriteLine(p.p[i]); } if ((0.0 < t) && (t < 1.0)) { return('1'); } else if (num == 0.0) /* t == 0 */ { return('q'); } else if (num == denom) /* t == 1 */ { return('r'); } else { return('0'); } }
//*********************** /* * This function returns a char: * 'V': the query point a coincides with a Vertex of polyhedron P. * 'E': the query point a is in the relative interior of an Edge of polyhedron P. * 'F': the query point a is in the relative interior of a Face of polyhedron P. * 'i': the query point a is strictly interior to polyhedron P. * 'o': the query point a is strictly exterior to( or outside of) polyhedron P. */ char InPolyhedron(int F, tPointi q, tPointi bmin, tPointi bmax, int radius) { tPointi r; /* Ray endpoint. */ tPointd p; /* Intersection point; not used. */ int f, k = 0, crossings = 0; char code = '?'; r = new tPointi(); p = new tPointd(); /* If query point is outside bounding box, finished. */ if (!InBox(q, bmin, bmax)) { return('o'); } while (k++ < F) { crossings = 0; RandomRay(r, radius); AddVec(q, r); System.Diagnostics.Debug.WriteLine("Ray endpoint: (" + r.p[0] + " , " + r.p[1] + " , " + r.p[2] + " )"); for (f = 0; f < F; f++) { /* Begin check each face */ if (BoxTest(f, q, r) == '0') { code = '0'; System.Diagnostics.Debug.WriteLine("BoxTest = 0!"); } else { code = SegTriInt(Faces[f], q, r, p); } System.Diagnostics.Debug.WriteLine("Face = " + f + ": BoxTest/SegTriInt returns " + code); /* If ray is degenerate, then goto outer while to generate another. */ if (code == 'p' || code == 'v' || code == 'e') { System.Diagnostics.Debug.WriteLine("Degenerate ray"); continue; } /* If ray hits face at interior point, increment crossings. */ else if (code == 'f') { crossings++; System.Diagnostics.Debug.WriteLine("crossings = " + crossings); } /* If query endpoint q sits on a V/E/F, return that code. */ else if (code == 'V' || code == 'E' || code == 'F') { return(code); } /* If ray misses triangle, do nothing. */ else if (code == '0') { continue; } else { System.Diagnostics.Debug.WriteLine("Error"); return(' '); } } /* End check each face */ /* No degeneracies encountered: ray is generic, so finished. */ break; } /* End while loop */ System.Diagnostics.Debug.WriteLine("Crossings at the end = " + crossings); /* q strictly interior to polyhedron iff an odd number of crossings. */ if ((crossings % 2) == 1) { return('i'); } else { return('o'); } }