Overte C++ Documentation
TriangleSet.h
1 //
2 // TriangleSet.h
3 // libraries/entities/src
4 //
5 // Created by Brad Hefta-Gaub on 3/2/2017.
6 // Copyright 2017 High Fidelity, Inc.
7 //
8 // Distributed under the Apache License, Version 2.0.
9 // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
10 //
11 
12 #pragma once
13 
14 #include <vector>
15 #include <memory>
16 
17 #include "AABox.h"
18 #include "GeometryUtil.h"
19 
20 class TriangleSet {
21 
22  class TriangleTreeCell {
23  public:
24  TriangleTreeCell(std::vector<Triangle>& allTriangles) : _allTriangles(allTriangles) {}
25  TriangleTreeCell(std::vector<Triangle>& allTriangles, const AABox& bounds, int depth);
26 
27  void insert(size_t triangleIndex);
28  void reset(const AABox& bounds, int depth = 0);
29  void clear();
30 
31  bool findRayIntersection(const glm::vec3& origin, const glm::vec3& direction, const glm::vec3& invDirection,
32  float& distance, BoxFace& face, Triangle& triangle, bool precision, int& trianglesTouched,
33  bool allowBackface = false);
34  bool findParabolaIntersection(const glm::vec3& origin, const glm::vec3& velocity, const glm::vec3& acceleration,
35  float& parabolicDistance, BoxFace& face, Triangle& triangle, bool precision, int& trianglesTouched,
36  bool allowBackface = false);
37 
38  const AABox& getBounds() const { return _bounds; }
39 
40  void debugDump();
41 
42  protected:
43  // checks our internal list of triangles
44  bool findRayIntersectionInternal(const glm::vec3& origin, const glm::vec3& direction,
45  float& distance, BoxFace& face, Triangle& triangle, bool precision, int& trianglesTouched,
46  bool allowBackface = false);
47  bool findParabolaIntersectionInternal(const glm::vec3& origin, const glm::vec3& velocity, const glm::vec3& acceleration,
48  float& parabolicDistance, BoxFace& face, Triangle& triangle, bool precision, int& trianglesTouched,
49  bool allowBackface = false);
50 
51  std::pair<AABox, AABox> getTriangleTreeCellChildBounds();
52 
53  std::vector<Triangle>& _allTriangles;
54  std::pair<std::shared_ptr<TriangleTreeCell>, std::shared_ptr<TriangleTreeCell>> _children;
55  int _depth { 0 };
56  int _population { 0 };
57  AABox _bounds;
58  std::vector<size_t> _triangleIndices;
59 
60  friend class TriangleSet;
61  };
62 
63  using SortedTriangleCell = std::pair<float, std::shared_ptr<TriangleTreeCell>>;
64 
65 public:
66  TriangleSet() : _triangleTree(_triangles) {}
67 
68  void debugDump();
69 
70  void insert(const Triangle& t);
71 
72  bool findRayIntersection(const glm::vec3& origin, const glm::vec3& direction, const glm::vec3& invDirection,
73  float& distance, BoxFace& face, Triangle& triangle, bool precision, bool allowBackface = false);
74  bool findParabolaIntersection(const glm::vec3& origin, const glm::vec3& velocity, const glm::vec3& acceleration,
75  float& parabolicDistance, BoxFace& face, Triangle& triangle, bool precision, bool allowBackface = false);
76 
77  void balanceTree();
78 
79  void reserve(size_t size) { _triangles.reserve(size); } // reserve space in the datastructure for size number of triangles
80  size_t size() const { return _triangles.size(); }
81  void clear();
82 
83  // Determine if a point is "inside" all the triangles of a convex hull. It is the responsibility of the caller to
84  // determine that the triangle set is indeed a convex hull. If the triangles added to this set are not in fact a
85  // convex hull, the result of this method is meaningless and undetermined.
86  bool convexHullContains(const glm::vec3& point) const;
87  const AABox& getBounds() const { return _bounds; }
88 
89 protected:
90  bool _isBalanced { false };
91  std::vector<Triangle> _triangles;
92  TriangleTreeCell _triangleTree;
93  AABox _bounds;
94 };