diff --git a/include/box.h b/include/box.h new file mode 100644 index 0000000000000000000000000000000000000000..57a99adfcbb9a9ca32cedc6b2a3aa4d76ce927f1 --- /dev/null +++ b/include/box.h @@ -0,0 +1,6 @@ +#pragma once + +struct Box { + float minX, maxX, minY, maxY; + bool isIn(const Triangle &t) const; +}; \ No newline at end of file diff --git a/include/constants.h b/include/constants.h index 0ec927ff5a50bdc477c466fd376435550bbc613d..553fad2756aeba4a270a1aa8fb85a0ed6ab47663 100644 --- a/include/constants.h +++ b/include/constants.h @@ -1,3 +1,5 @@ #pragma once -#define MAX_TRIANGLE_INTERSECTION_POINTS 12 \ No newline at end of file +#define MAX_TRIANGLE_INTERSECTION_POINTS 12 + +#define NB_TRIANGLE_SIDES 3 \ No newline at end of file diff --git a/include/quad_tree.h b/include/quad_tree.h new file mode 100644 index 0000000000000000000000000000000000000000..f9cc89f167a86ad37890ccd6b6bec7efb7a2da99 --- /dev/null +++ b/include/quad_tree.h @@ -0,0 +1,31 @@ +#pragma once +#include <vector> +#include <triangle.h> +#include <box.h> + +enum Status { + Empty, + Single, + Quad +}; + +class QuadTree { + Box b; + Status status; + QuadContent q; + public: + void addTriangle(const Triangle &t); + QuadTree(Box b); + std::vector<Triangle> visibleSurface() const; + Triangle triangleIntersection(const Point &p) const; + +}; + +union QuadContent { + + Triangle t; + std::vector<QuadTree> children; + bool nothing; + QuadContent() {}; + ~QuadContent() {}; +}; \ No newline at end of file diff --git a/include/triangulation.h b/include/triangulation.h index ef2134e9502f80c5e641b6322305daff62e23295..670cb6f44d43e898e643f9e0526339ad0c034a09 100644 --- a/include/triangulation.h +++ b/include/triangulation.h @@ -10,3 +10,4 @@ std::optional<Triangle> removeEar(int &index, PointList &pointList, const std::v std::vector<Triangle> triangulate(std::vector<Point> points); +std::vector<Triangle> triangulate(Triangle t1, Triangle t2); \ No newline at end of file diff --git a/src/data_structures/box.cpp b/src/data_structures/box.cpp new file mode 100644 index 0000000000000000000000000000000000000000..8e5d5811252a1193cca20cee413d27a1c8324693 --- /dev/null +++ b/src/data_structures/box.cpp @@ -0,0 +1,14 @@ +#include <box.h> +#include <triangle.h> +#include <constants.h> + +bool Box::isIn(const Triangle &t) const { + for (int i = 0; i < NB_TRIANGLE_SIDES; i++) { + float x = t.points[i].x; + float y = t.points[i].y; + if (x > minX && x < maxX && y > minY && y < maxY) { + return true; + } + } + return false; +} \ No newline at end of file diff --git a/src/data_structures/quad_tree.cpp b/src/data_structures/quad_tree.cpp new file mode 100644 index 0000000000000000000000000000000000000000..dfc77dfa7c6e875d19f3a6d8a62f776c616addbb --- /dev/null +++ b/src/data_structures/quad_tree.cpp @@ -0,0 +1,53 @@ +#include <quad_tree.h> + +QuadTree::QuadTree(Box b) : b{b}, status{Empty} { + q.nothing = false; +} + +void QuadTree::addTriangle(const Triangle &t) +{ + if (!b.isIn(t)) { + return; + } + switch (status) + { + case Empty: + status = Single; + q.t = t; + break; + + case Single: + + Triangle old = q.t; + + + status = Quad; + q.children = { + QuadTree(Box{b.minX, b.maxX / 2, b.minY, b.maxY}), + QuadTree(Box{b.maxX / 2, b.maxX, b.minY, b.maxY / 2}), + QuadTree(Box{b.maxX / 2, b.maxX, b.maxY / 2, b.maxY}), + QuadTree(Box{b.minX, b.maxX / 2, b.minY, b.maxY / 2}) + }; + // if the old and new triangle intersect, we want to avoid infinite additions to the tree. + // create new set of triangles that don't intersect + std::vector<Triangle> newTriangles = triangulate(old, t); + for (int i = 0; i < q.children.size(); i++) { + for (int j = 0; j < newTriangles.size(); i++) { + q.children[i].addTriangle(newTriangles[i]); + } + } + break; + case Quad: + for (int i = 0; i < q.children.size(); i++) { + addTriangle(t); + } + break; + default: + break; + } +} + + +std::vector<Triangle> QuadTree::visibleSurface() const { + // for every +} \ No newline at end of file diff --git a/src/utilities/intersections.cpp b/src/utilities/intersections.cpp index 8b299f4ce682b917823c375b3723ba9fa83d58ea..b4b0e64be7198437d2f7f6ff4751ee46097c9d79 100644 --- a/src/utilities/intersections.cpp +++ b/src/utilities/intersections.cpp @@ -2,6 +2,7 @@ #include <optional> #include <edge.h> #include <triangle_edges.h> +#include <triangle.h> @@ -30,8 +31,14 @@ bool withinEdge(Edge e, Point p) { return minX <= p.x && p.x <= maxX && minY <= p.y && p.y <= maxY; } - void intersection(Edge e1, Edge e2, std::vector<Point> &results) { + auto point = intersection(e1, e2); + if (point.has_value()) { + results.push_back(point.value()); + } +} + +std::optional<Point> intersection(const Edge &e1, const Edge &e2) { auto slope1 = getSlope(e1); auto slope2 = getSlope(e2); @@ -41,39 +48,38 @@ void intersection(Edge e1, Edge e2, std::vector<Point> &results) { // ignore overlapping case if (!slope1.has_value() && !slope2.has_value()) { - return; + return {}; } if (!slope1.has_value()) { - results.push_back(Point{e1.p1.x, slope2.value() * e1.p1.x + b2.value()}); - return; + return Point{e1.p1.x, slope2.value() * e1.p1.x + b2.value()}; } if (!slope2.has_value()) { - results.push_back(Point{e2.p1.x, slope1.value() * e2.p1.x + b1.value()}); - return; + return Point{e2.p1.x, slope1.value() * e2.p1.x + b1.value()}; } float candX = (b2.value() - b1.value()) / (slope1.value() - slope2.value()); auto candPoint = Point{ candX, slope1.value() * candX + b1.value()}; if (withinEdge(e1, candPoint) && withinEdge(e2, candPoint)) { - results.push_back(candPoint); + return candPoint; } } -void intersections(Edge e1, TriangleEdges te, std::vector<Point> &results) { - intersection(e1, te.e1, results); - intersection(e1, te.e2, results); - intersection(e1, te.e3, results); +void intersections(const Edge &e1, const TriangleEdges &te, std::vector<Point> &results) { + for (int i = 0; i < NB_TRIANGLE_SIDES; i++) { + intersection(e1, te.edges[i], results); + } } -std::vector<Point> intersections(Triangle t1, Triangle t2) { +std::vector<Point> intersections(const Triangle &t1, const Triangle &t2) { TriangleEdges t1Edges = TriangleEdges(t1); TriangleEdges t2Edges = TriangleEdges(t2); std::vector<Point> results; - intersections(t1Edges.e1, t2Edges, results); - intersections(t1Edges.e2, t2Edges, results); - intersections(t1Edges.e3, t2Edges, results); + for (int i = 0; i < NB_TRIANGLE_SIDES; i++) { + intersections(t1Edges.edges[i], t2Edges, results); + } + return results; }