aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rwxr-xr-xjs/helper-classes/3D/StageLine.js384
-rwxr-xr-xjs/helper-classes/3D/math-utils.js12
2 files changed, 242 insertions, 154 deletions
diff --git a/js/helper-classes/3D/StageLine.js b/js/helper-classes/3D/StageLine.js
index 787a4568..069729d0 100755
--- a/js/helper-classes/3D/StageLine.js
+++ b/js/helper-classes/3D/StageLine.js
@@ -33,6 +33,7 @@ POSSIBILITY OF SUCH DAMAGE.
33// The line class represents a line intersected with all planes on the scene 33// The line class represents a line intersected with all planes on the scene
34/////////////////////////////////////////////////////////////////////// 34///////////////////////////////////////////////////////////////////////
35var vecUtils = require("js/helper-classes/3D/vec-utils").VecUtils; 35var vecUtils = require("js/helper-classes/3D/vec-utils").VecUtils;
36var viewUtils = require( "js/helper-classes/3D/view-utils").ViewUtils;
36var LinePlaneIntersectRec = require("js/helper-classes/3D/LinePlaneIntersectRec").LinePlaneIntersectRec; 37var LinePlaneIntersectRec = require("js/helper-classes/3D/LinePlaneIntersectRec").LinePlaneIntersectRec;
37 38
38var StageLine = exports.StageLine = Object.create(Object.prototype, { 39var StageLine = exports.StageLine = Object.create(Object.prototype, {
@@ -76,149 +77,211 @@ var StageLine = exports.StageLine = Object.create(Object.prototype, {
76 // Methods 77 // Methods
77 /////////////////////////////////////////////////////////////////////// 78 ///////////////////////////////////////////////////////////////////////
78 79
79 intersectWithPlane: { 80 intersectWithPlane: {
80 value: function( plane ) 81 value: function( plane )
81 { 82 {
82 // if the plane is edge-on, ignore it 83 // if the plane is edge-on, ignore it
83 if ( MathUtils.fpSign( plane.getPlaneEq()[2] ) == 0 ) return; 84 if ( MathUtils.fpSign( plane.getPlaneEq()[2] ) == 0 ) return;
84 85
85 // do some quick box tests. 86 // do some quick box tests.
86 var minPt = this.getMinPoint(), 87 var minPt = this.getMinPoint(),
87 maxPt = this.getMaxPoint(); 88 maxPt = this.getMaxPoint();
88 89
89 if (maxPt[0] < plane._rect.getLeft()) return; 90 if (maxPt[0] < plane._rect.getLeft()) return;
90 if (minPt[0] > plane._rect.getRight()) return; 91 if (minPt[0] > plane._rect.getRight()) return;
91 92
92 if (maxPt[1] < plane._rect.getTop()) return; 93 if (maxPt[1] < plane._rect.getTop()) return;
93 if (minPt[1] > plane._rect.getBottom()) return; 94 if (minPt[1] > plane._rect.getBottom()) return;
94 95
95 if (minPt[2] > plane.getZMax()) return; 96 if (minPt[2] > plane.getZMax()) return;
96 97
97 // get the boundary points for the plane 98 // get the boundary points for the plane
98 var boundaryPts = plane.getBoundaryPoints(); 99 var boundaryPts = plane.getBoundaryPoints().slice();
99 100
100 // get the points and direction vector for the current line 101 // get the points and direction vector for the current line
101 var pt0 = this.getPoint0(), pt1 = this.getPoint1(); 102 var pt0 = this.getPoint0(), pt1 = this.getPoint1();
102 //var lineDir = pt1.subtract( pt0 ); 103 //var lineDir = pt1.subtract( pt0 );
103 var lineDir = vecUtils.vecSubtract(3, pt1, pt0); 104 var lineDir = vecUtils.vecSubtract(3, pt1, pt0);
104 105
105 // intersect with the front plane 106 // intersect with the front plane
106 var planeEq = plane.getPlaneEq(); 107 var planeEq = plane.getPlaneEq();
107 var t = MathUtils.vecIntersectPlaneForParam( pt0, lineDir, planeEq ); 108 var t = MathUtils.vecIntersectPlaneForParam( pt0, lineDir, planeEq );
108 if (t != undefined) 109 if (t != undefined)
109 { 110 {
110 if ((MathUtils.fpSign(t) >= 0) && (MathUtils.fpCmp(t,1.0) <= 0)) 111 if ((MathUtils.fpSign(t) >= 0) && (MathUtils.fpCmp(t,1.0) <= 0))
111 { 112 {
112 // get the intersection point 113 // get the intersection point
113 var pt = MathUtils.interpolateLine3D( pt0, pt1, t ); 114 var pt = MathUtils.interpolateLine3D( pt0, pt1, t );
114 115
115 // see if the intersection point is contained in the bounds 116 // see if the intersection point is contained in the bounds
116 //var contains = this.boundaryContainsPoint( boundaryPts, plane.isBackFacing(), pt ); 117 //var contains = this.boundaryContainsPoint( boundaryPts, plane.isBackFacing(), pt );
117 var contains = MathUtils.boundaryContainsPoint( boundaryPts, pt, plane.isBackFacing() ); 118 var onEdge = [];
118 if (contains == MathUtils.INSIDE) 119 var contains = MathUtils.boundaryContainsPoint( boundaryPts, pt, plane.isBackFacing(), onEdge );
119 { 120 if (contains == MathUtils.INSIDE)
120 // add the intersection 121 {
121 var dot = MathUtils.dot3( pt0, planeEq ) + planeEq[3]; 122 // add the intersection
122 var deltaVis = (dot > 0) ? 1 : -1; 123 var dot = MathUtils.dot3( pt0, planeEq ) + planeEq[3];
124 var deltaVis = (dot > 0) ? 1 : -1;
123// if (plane.isBackFacing()) 125// if (plane.isBackFacing())
124// deltaVis = (dot < 0) ? 1 : -1; 126// deltaVis = (dot < 0) ? 1 : -1;
125 127
126 this.addIntersection( plane, t, deltaVis ); 128 this.addIntersection( plane, t, deltaVis );
127 } 129 }
128 else if (contains == MathUtils.ON) 130 else if (contains == MathUtils.ON)
129 { 131 {
130 if (MathUtils.fpCmp(t,1.0) < 0) 132 if (MathUtils.fpCmp(t,1.0) < 0)
131 { 133 {
132 // take the dot product between the line and the normal to the plane 134 // determine if the intersection is on a front side (no intersection) of the polygons
133 // to determine the change in visibility 135 //var ctr = [ 0.5*(boundaryPts[0][0] + boundaryPts[2][0]), 0.5*(boundaryPts[0][1] + boundaryPts[2][1]), 0.5*(boundaryPts[0][2] + boundaryPts[2][2]) ];
134 var vec = vecUtils.vecSubtract( 3, pt1, pt0 ); 136 //var vec = vecUtils.vecSubtract(3, pt, ctr );
135 var dot = vecUtils.vecDot( 3, vec, plane.getPlaneEq() ); 137 this.edgeIsFrontFacing2( plane );
136 var sign = MathUtils.fpSign( dot ); 138 if ( !this.edgeIsFrontFacing(boundaryPts, planeEq, plane.isBackFacing(), onEdge[0], onEdge[1]) )
137 if (sign == 0) 139 {
138 throw new Error( "coplanar intersection being treated as not coplanar" ); 140 // take the dot product between the line and the normal to the plane
139 if (!plane.isBackFacing()) 141 // to determine the change in visibility
140 { 142 var vec = vecUtils.vecSubtract( 3, pt1, pt0 );
141 if (sign < 0) 143 var dot = vecUtils.vecDot( 3, vec, planeEq );
142 this.addIntersection( plane, t, 1 ); 144 var sign = MathUtils.fpSign( dot );
143 } 145 if (sign == 0)
144 else 146 throw new Error( "coplanar intersection being treated as not coplanar" );
145 { 147 if (!plane.isBackFacing())
146 if (sign > 0) 148 {
147 this.addIntersection( plane, t, -1 ); 149 if (sign < 0)
148 } 150 this.addIntersection( plane, t, 1 );
149 } 151 }
150 } 152 else
151 } 153 {
152 } 154 if (sign > 0)
153 else 155 this.addIntersection( plane, t, -1 );
154 { 156 }
155 // the line must be parallel to the plane. If the line is in the plane, 157 }
156 // we need to do some special processing 158 }
157 var d0 = vecUtils.vecDot(3, planeEq, pt0) + planeEq[3], 159 }
158 d1 = vecUtils.vecDot(3, planeEq, pt1) + planeEq[3]; 160 }
159 if ((MathUtils.fpSign(d0) == 0) && (MathUtils.fpSign(d1) == 0)) 161 }
160 this.doCoplanarIntersection( plane ); 162 else
161 } 163 {
164 // the line must be parallel to the plane. If the line is in the plane,
165 // we need to do some special processing
166 var d0 = vecUtils.vecDot(3, planeEq, pt0) + planeEq[3],
167 d1 = vecUtils.vecDot(3, planeEq, pt1) + planeEq[3];
168 if ((MathUtils.fpSign(d0) == 0) && (MathUtils.fpSign(d1) == 0))
169 this.doCoplanarIntersection( plane );
170 }
162 171
163 // intersect with the 4 planes formed by the edges of the plane, going back in Z 172 // intersect with the 4 planes formed by the edges of the plane, going back in Z
164 var bPt1 = boundaryPts[3]; 173 var bPt1 = boundaryPts[3];
165 for (var i=0; i<4; i++) 174 for (var i=0; i<4; i++)
166 { 175 {
167 // get the 2 points that define the front edge of the plane 176 // get the 2 points that define the front edge of the plane
168 var bPt0 = bPt1; 177 var bPt0 = bPt1;
169 var bPt1 = boundaryPts[i]; 178 var bPt1 = boundaryPts[i];
170 179
171 // calculate the plane equation. The normal should point towards the OUTSIDE of the boundary 180 // calculate the plane equation. The normal should point towards the OUTSIDE of the boundary
172 //var vec = bPt1.subtract( bPt0 ); 181 //var vec = bPt1.subtract( bPt0 );
173 var vec = vecUtils.vecSubtract(3, bPt1, bPt0); 182 var vec = vecUtils.vecSubtract(3, bPt1, bPt0);
174 if (plane.isBackFacing()) 183 if (plane.isBackFacing())
175 MathUtils.negate( vec ); 184 MathUtils.negate( vec );
176 planeEq = [-vec[1], vec[0], 0]; 185 planeEq = [-vec[1], vec[0], 0];
177 var normal = [planeEq[0], planeEq[1], planeEq[2]]; 186 var normal = [planeEq[0], planeEq[1], planeEq[2]];
178// var d = -planeEq.dot(bPt0); 187// var d = -planeEq.dot(bPt0);
179 var d = -vecUtils.vecDot(3, planeEq, bPt0); 188 var d = -vecUtils.vecDot(3, planeEq, bPt0);
180 planeEq[3] = d; 189 planeEq[3] = d;
181 190
182 t = MathUtils.vecIntersectPlaneForParam( pt0, lineDir, planeEq ); 191 t = MathUtils.vecIntersectPlaneForParam( pt0, lineDir, planeEq );
183 if (t) 192 if (t)
184 { 193 {
185 if ((MathUtils.fpSign(t) > 0) && (MathUtils.fpCmp(t,1.0) <= 0)) // the strict vs not-strict inequality comparisons are IMPORTANT! 194 if ((MathUtils.fpSign(t) > 0) && (MathUtils.fpCmp(t,1.0) <= 0)) // the strict vs not-strict inequality comparisons are IMPORTANT!
186 { 195 {
187 // get the intersection point 196 // get the intersection point
188 var pt = MathUtils.interpolateLine3D( pt0, pt1, t ); 197 var pt = MathUtils.interpolateLine3D( pt0, pt1, t );
189 198
190 // we need to get the parameter on the edge of the projection 199 // we need to get the parameter on the edge of the projection
191 // of the intersection point onto the line. 200 // of the intersection point onto the line.
192 var index = (Math.abs(vec[0]) > Math.abs(vec[1])) ? 0 : 1; 201 var index = (Math.abs(vec[0]) > Math.abs(vec[1])) ? 0 : 1;
193 var tEdge = (pt[index] - bPt0[index])/(bPt1[index] - bPt0[index]); 202 var tEdge = (pt[index] - bPt0[index])/(bPt1[index] - bPt0[index]);
194 if ((MathUtils.fpSign(tEdge) > 0) && (MathUtils.fpCmp(tEdge,1.0) <= 0)) 203 if ((MathUtils.fpSign(tEdge) > 0) && (MathUtils.fpCmp(tEdge,1.0) <= 0))