132 std::vector<PlainPolygonElement> polygonize( |
132 std::vector<PlainPolygonElement> polygonize( |
133 std::vector<glm::vec3>::const_iterator begin, |
133 std::vector<glm::vec3>::const_iterator begin, |
134 std::vector<glm::vec3>::const_iterator end) |
134 std::vector<glm::vec3>::const_iterator end) |
135 { |
135 { |
136 std::vector<PlainPolygonElement> result; |
136 std::vector<PlainPolygonElement> result; |
137 const glm::vec3 xvec = *begin - *(begin + 1); |
137 // Transform the polygon into XY plane |
138 const glm::vec3 yvec = *(begin + 2) - *(begin + 1); |
138 opt<glm::mat3> normal = calculateNormal(begin, end); |
139 const glm::vec3 zvec = glm::cross(xvec, yvec); |
139 if (normal.has_value()) { |
140 const glm::mat3 inverseMatrix = glm::inverse(glm::mat3{xvec, yvec, zvec}); |
140 const glm::mat3 normalInverse = glm::inverse(*normal); |
141 std::vector<std::vector<glm::vec3>> polygons{1}; |
141 std::vector<std::vector<glm::vec3>> polygons{1}; |
142 std::vector<glm::vec3>& polygon2d = polygons.back(); |
142 std::vector<glm::vec3>& polygon2d = polygons.back(); |
143 polygon2d.reserve(static_cast<std::size_t>(end - begin)); |
143 polygon2d.reserve(static_cast<std::size_t>(end - begin)); |
144 for (std::vector<glm::vec3>::const_iterator it = begin; it != end; ++it) { |
144 for (std::vector<glm::vec3>::const_iterator it = begin; it != end; ++it) { |
145 polygon2d.push_back(inverseMatrix * glm::vec4{*it, 1}); |
145 polygon2d.push_back(normalInverse * glm::vec4{*it, 1}); |
146 } |
146 } |
147 const std::vector<triangulate::index_t> indices = mapbox::earcut<triangulate::index_t>(polygons); |
147 const std::vector<triangulate::index_t> indices = mapbox::earcut<triangulate::index_t>(polygons); |
148 triangulate::MergedTriangles mergedTriangles = triangulate::mergeTriangles(indices, begin); |
148 triangulate::MergedTriangles mergedTriangles = triangulate::mergeTriangles(indices, begin); |
149 for (Quadrilateral& quad : mergedTriangles.quadrilaterals) { |
149 for (Quadrilateral& quad : mergedTriangles.quadrilaterals) { |
150 result.push_back(quad); |
150 result.push_back(quad); |
151 } |
151 } |
152 for (std::size_t i = 0; i < indices.size(); i += 3) { |
152 for (std::size_t i = 0; i < indices.size(); i += 3) { |
153 if (not mergedTriangles.cutTriangles.contains({i})) { |
153 if (not mergedTriangles.cutTriangles.contains({i})) { |
154 Triangle tri = triangle( |
154 Triangle tri = triangle( |
155 *(begin + indices[i]), |
155 *(begin + indices[i]), |
156 *(begin + indices[i + 1]), |
156 *(begin + indices[i + 1]), |
157 *(begin + indices[i + 2])); |
157 *(begin + indices[i + 2])); |
158 result.push_back(tri); |
158 result.push_back(tri); |
|
159 } |
159 } |
160 } |
160 } |
161 } |
161 return result; |
162 return result; |
162 } |
163 } |