|
62 | 62 | import org.locationtech.jts.geom.GeometryFactory; |
63 | 63 | import org.locationtech.jts.triangulate.polygon.ConstrainedDelaunayTriangulator; |
64 | 64 |
|
| 65 | + |
65 | 66 | //import earcut4j.Earcut; |
66 | 67 |
|
67 | 68 | /** |
@@ -512,31 +513,59 @@ private PolygonUtil() { |
512 | 513 | public static Transform calculateNormalTransform(Polygon concave) throws ColinearPointsException { |
513 | 514 | // Normalize inputs |
514 | 515 | Vector3d u = concave.getPlane().getNormal(); |
515 | | - Vector3d v = new Vector3d(0, 0, 1); |
| 516 | + Vector3d pureZVect = new Vector3d(0, 0, 1); |
| 517 | + Vector3d pureXVect = new Vector3d(1, 0, 0); |
516 | 518 |
|
517 | | - double dot = u.dot(v); |
| 519 | + double dotZ = u.dot(pureZVect); |
| 520 | + double dotX = u.dot(pureXVect); |
518 | 521 | // If u ≈ v → identity |
519 | | - if (dot > 1.0 - Plane.getEPSILON()) { |
| 522 | + if (dotZ > 1.0 - Plane.getEPSILON()) { |
520 | 523 | return new Transform(); |
521 | 524 | } |
522 | | - if (dot < -1.0 + Plane.getEPSILON()) { |
| 525 | + if (dotZ < -1.0 + Plane.getEPSILON()) { |
523 | 526 | return new Transform().rotX(180); |
524 | 527 | } |
| 528 | + if (dotX > 1.0 - Plane.getEPSILON()) { |
| 529 | + return new Transform().rotY(90); |
| 530 | + } |
| 531 | + if (dotX < -1.0 + Plane.getEPSILON()) { |
| 532 | + return new Transform().rotY(-90); |
| 533 | + } |
525 | 534 | double aboutZ = Math.toDegrees(Math.atan2(u.y, u.x)); |
526 | | - |
| 535 | + if(Double.isNaN(aboutZ)) |
| 536 | + throw new RuntimeException("Failed to creat a rotation angle"); |
527 | 537 | Transform transform1 = new Transform().rotZ(aboutZ); |
528 | 538 | Vector3d u2 = u.transformed(transform1); |
| 539 | + Transform transform; |
529 | 540 | double aboutY = Math.toDegrees(Math.atan2(u2.x, u2.z)); |
530 | | - Transform transform = new Transform().rotY(aboutY).apply(transform1); |
| 541 | + if(Double.isNaN(aboutY)) |
| 542 | + throw new RuntimeException("Failed to creat a rotation angle"); |
| 543 | + Transform rotY = new Transform().rotY(aboutY); |
| 544 | + transform = rotY.apply(transform1); |
| 545 | + |
| 546 | + |
531 | 547 | Vector3d u3 = u.transformed(transform).normalized(); |
532 | 548 |
|
533 | 549 | Polygon test = concave.transformed(transform); |
534 | | - double abs = Math.abs(test.plane.getNormal().z); |
| 550 | + Vector3d normal = test.plane.getNormal(); |
| 551 | + double abs = Math.abs(normal.z); |
535 | 552 | if (1 - abs > 0.1) { |
536 | 553 | System.out.println("Error with " + test); |
537 | 554 | // Plane p = Plane.createFromPoints(test.getVertices()); |
538 | | - new ColinearPointsException("Failed to reorent the polygon for processing! z off by "+abs+" "+test.plane.getNormal()).printStackTrace(); |
| 555 | + new ColinearPointsException("Failed to reorent the polygon for processing! z off by "+abs+" "+normal).printStackTrace(); |
| 556 | + } |
| 557 | + |
| 558 | + Matrix4d rotation = transform.getInternalMatrix(); |
| 559 | + Quat4d q1 = new Quat4d(); |
| 560 | + rotation.get(q1); |
| 561 | + javax.vecmath.Vector3d t1 = new javax.vecmath.Vector3d(); |
| 562 | + rotation.get(t1); |
| 563 | + List<Double> asList = Arrays.asList(t1.x, t1.y, t1.z, q1.w, q1.x, q1.y, q1.z); |
| 564 | + for(Double d:asList){ |
| 565 | + if(Double.isInfinite(d)||Double.isNaN(d)) |
| 566 | + throw new RuntimeException("Failed to produce a matrix"); |
539 | 567 | } |
| 568 | + |
540 | 569 | return transform; |
541 | 570 | } |
542 | 571 |
|
|
0 commit comments