Skip to content

Commit 0de8618

Browse files
committed
Fixed a math error in Newton, add the new math to PointIntersectingLine() and PointOnSurfaces()
1 parent ae86f49 commit 0de8618

File tree

1 file changed

+20
-14
lines changed

1 file changed

+20
-14
lines changed

src/srf/ratpoly.cpp

Lines changed: 20 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -504,22 +504,19 @@ bool SSurface::ClosestPointNewton(Vector p, double *u, double *v, bool mustConve
504504
Vector tu, tv, tx, ty;
505505
TangentsAt(*u, *v, &tu, &tv);
506506
Vector n = tu.Cross(tv);
507-
double tu2 = tu.MagSquared(),
508-
tv2 = tv.MagSquared(),
509-
s = sqrt(n.MagSquared() / (tu2 * tv2));
510507
// since tu and tv may not be orthogonal, use y in place of v.
511508
// |y| = |v|sin(theta) where theta is the angle between tu and tv.
512-
ty = n.Cross(tu).ScaledBy(1.0/tu2);
513-
tx = tv.Cross(n).ScaledBy(1.0/tv2);
509+
ty = n.Cross(tu).ScaledBy(1.0/tu.MagSquared());
510+
tx = tv.Cross(n).ScaledBy(1.0/tv.MagSquared());
514511

515512
// Project the point into a plane through p0, with basis tu, tv; a
516513
// second-order thing would converge faster but needs second
517514
// derivatives.
518515
Vector dp = p.Minus(p0);
519516
double du = dp.Dot(tx),
520517
dv = dp.Dot(ty);
521-
*u += du / (tu2*s);
522-
*v += dv / (tv2*s);
518+
*u += du / (tx.MagSquared());
519+
*v += dv / (ty.MagSquared());
523520

524521
if (*u < 0.0) *u = 0.0;
525522
else if (*u > 1.0) *u = 1.0;
@@ -555,13 +552,17 @@ bool SSurface::PointIntersectingLine(Vector p0, Vector p1, double *u, double *v)
555552
// Check for convergence
556553
if(pi.Equals(p, RATPOLY_EPS)) return true;
557554

555+
n = tu.Cross(tv);
556+
Vector ty = n.Cross(tu).ScaledBy(1.0/tu.MagSquared());
557+
Vector tx = tv.Cross(n).ScaledBy(1.0/tv.MagSquared());
558+
558559
// Adjust our guess and iterate
559560
Vector dp = pi.Minus(p);
560-
double du = dp.Dot(tu), dv = dp.Dot(tv);
561-
*u += du / (tu.MagSquared());
562-
*v += dv / (tv.MagSquared());
561+
double du = dp.Dot(tx), dv = dp.Dot(ty);
562+
*u += du / tx.MagSquared();
563+
*v += dv / ty.MagSquared();
563564
}
564-
// dbp("didn't converge (surface intersecting line)");
565+
dbp("didn't converge (surface intersecting line)");
565566
return false;
566567
}
567568

@@ -652,10 +653,15 @@ void SSurface::PointOnSurfaces(SSurface *s1, SSurface *s2, double *up, double *v
652653
if(parallel) break;
653654

654655
for(j = 0; j < 3; j++) {
656+
Vector n = tu[j].Cross(tv[j]);
657+
Vector ty = n.Cross(tu[j]).ScaledBy(1.0/tu[j].MagSquared());
658+
Vector tx = tv[j].Cross(n).ScaledBy(1.0/tv[j].MagSquared());
659+
655660
Vector dp = pi.Minus(p[j]);
656-
double du = dp.Dot(tu[j]), dv = dp.Dot(tv[j]);
657-
u[j] += du / (tu[j]).MagSquared();
658-
v[j] += dv / (tv[j]).MagSquared();
661+
double du = dp.Dot(tx), dv = dp.Dot(ty);
662+
663+
u[j] += du / tx.MagSquared();
664+
v[j] += dv / ty.MagSquared();
659665
}
660666
}
661667
dbp("didn't converge (three surfaces intersecting)");

0 commit comments

Comments
 (0)