compute centroid from surface as Point3dVector
| 67 | |
| 68 | /// compute centroid from surface as Point3dVector |
| 69 | OptionalPoint3d getCentroid(const Point3dVector& points) { |
| 70 | OptionalPoint3d result; |
| 71 | |
| 72 | if (points.size() >= 3) { |
| 73 | // convert to face coordinates |
| 74 | const Transformation alignFace = Transformation::alignFace(points); |
| 75 | Point3dVector surfacePoints = alignFace.inverse() * points; |
| 76 | |
| 77 | const size_t N = surfacePoints.size(); |
| 78 | double A = 0; |
| 79 | double cx = 0; |
| 80 | double cy = 0; |
| 81 | for (size_t i = 0; i < N; ++i) { |
| 82 | double x1 = 0.0; |
| 83 | double x2 = 0.0; |
| 84 | double y1 = 0.0; |
| 85 | double y2 = 0.0; |
| 86 | if (i == N - 1) { |
| 87 | x1 = surfacePoints[i].x(); |
| 88 | x2 = surfacePoints[0].x(); |
| 89 | y1 = surfacePoints[i].y(); |
| 90 | y2 = surfacePoints[0].y(); |
| 91 | } else { |
| 92 | x1 = surfacePoints[i].x(); |
| 93 | x2 = surfacePoints[i + 1].x(); |
| 94 | y1 = surfacePoints[i].y(); |
| 95 | y2 = surfacePoints[i + 1].y(); |
| 96 | } |
| 97 | |
| 98 | const double dA = (x1 * y2 - x2 * y1); |
| 99 | A += 0.5 * dA; |
| 100 | cx += (x1 + x2) * dA; |
| 101 | cy += (y1 + y2) * dA; |
| 102 | } |
| 103 | |
| 104 | if (A > 0) { |
| 105 | // centroid in face coordinates |
| 106 | const Point3d surfaceCentroid(cx / (6.0 * A), cy / (6.0 * A), 0.0); |
| 107 | |
| 108 | // centroid |
| 109 | result = alignFace * surfaceCentroid; |
| 110 | } |
| 111 | } |
| 112 | return result; |
| 113 | } |
| 114 | |
| 115 | /// reorder points to upper-left-corner convention |
| 116 | Point3dVector reorderULC(const Point3dVector& points) { |