TerrainGen coverage


terraingen/
Coverage:
low: ≥ 0%
medium: ≥ 75.0%
high: ≥ 90.0%
Lines:
2 / 2
100.0%
Branches:
-
-%
Functions:
1 / 1
100.0%

mesh/mesh.h
Line Branch Exec Source
1 /// @file
2 /// @brief Triangle meshes, their measures, normals and rigid transforms.
3 #pragma once
4
5 #include "terraingen/util/geometry.h"
6
7 #include <array>
8 #include <cstdint>
9 #include <vector>
10
11 namespace terraingen {
12
13 /// A triangle mesh of shared vertices; triangles are counter-clockwise seen from outside,
14 /// so a closed mesh has a positive `Volume`.
15 struct TriangleMesh {
16 std::vector<Vec3d> positions; ///< Vertex positions.
17 std::vector<std::array<std::uint32_t, 3>> triangles; ///< Indices into `positions`.
18 };
19
20 /// An axis-aligned box.
21 struct Box3d {
22 Vec3d min; ///< Lowest corner.
23 Vec3d max; ///< Highest corner.
24
25 /// The box's size along each axis, `max` - `min`.
26 3735 Vec3d Extents() const {
27 3735 return max - min;
28 }
29 };
30
31 /// The smallest axis-aligned box around a mesh's vertices.
32 /// @throws std::invalid_argument for a mesh without vertices.
33 Box3d Bounds(const TriangleMesh& mesh);
34
35 /// Checks that every triangle indexes one of the mesh's vertices.
36 /// @throws std::invalid_argument for a triangle indexing past the vertices.
37 void ValidateMesh(const TriangleMesh& mesh);
38
39 /// The volume a closed mesh encloses, as a sum of signed tetrahedra from the origin; negative
40 /// when the triangles face inward.
41 /// @throws std::invalid_argument as `ValidateMesh`.
42 double Volume(const TriangleMesh& mesh);
43
44 /// The total area of a mesh's triangles.
45 /// @throws std::invalid_argument as `ValidateMesh`.
46 double SurfaceArea(const TriangleMesh& mesh);
47
48 /// The unit normal of each vertex: the area-weighted mean of its triangles' normals.
49 /// @throws std::invalid_argument as `ValidateMesh`.
50 std::vector<Vec3d> VertexNormals(const TriangleMesh& mesh);
51
52 /// A mesh with per-vertex normals, its vertices split along creases so fracture faces keep
53 /// hard edges while noisy surfaces stay smooth.
54 struct ShadedMesh {
55 TriangleMesh mesh; ///< The mesh, vertices split along creases.
56 std::vector<Vec3d> normals; ///< One per vertex of `mesh`.
57 };
58
59 /// A mesh with its vertices split along creases and normals averaged, weighted by area,
60 /// over the triangles that meet within the crease angle.
61 /// @param creaseAngle The largest angle between triangle normals that is smoothed, in radians.
62 /// @throws std::invalid_argument for a negative or non-finite `creaseAngle`, or as
63 /// `ValidateMesh`.
64 ShadedMesh WithCreases(const TriangleMesh& mesh, double creaseAngle);
65
66 /// A rotation followed by a translation.
67 struct RigidTransform {
68 /// Row-major 3 x 3.
69 std::array<double, 9> rotation{1.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 1.0};
70 /// Applied after the rotation.
71 Vec3d translation{};
72
73 /// The point rotated, then translated.
74 Vec3d Apply(const Vec3d& point) const;
75 /// The transform that applies `first`, then this one.
76 RigidTransform After(const RigidTransform& first) const;
77
78 /// A rotation by `angle` radians about x, counter-clockwise looking down the axis.
79 static RigidTransform RotationX(double angle);
80 /// A rotation by `angle` radians about y, counter-clockwise looking down the axis.
81 static RigidTransform RotationY(double angle);
82 /// A rotation by `angle` radians about z, counter-clockwise looking down the axis.
83 static RigidTransform RotationZ(double angle);
84 /// A pure translation by `offset`.
85 static RigidTransform Translation(const Vec3d& offset);
86 };
87
88 /// Checks that a matrix is a proper rotation: orthonormal to within 1e-9, without a
89 /// reflection.
90 /// @param rotation Row-major 3 x 3.
91 /// @throws std::invalid_argument otherwise.
92 void RequireRotation(const std::array<double, 9>& rotation);
93
94 /// The unit quaternion (x, y, z, w) of a proper rotation, row-major 3 x 3.
95 std::array<double, 4> RotationQuaternion(const std::array<double, 9>& rotation);
96
97 /// A mesh with every vertex moved by a transform.
98 TriangleMesh Transformed(const TriangleMesh& mesh, const RigidTransform& transform);
99
100 /// A mesh with every vertex scaled about the origin per axis; triangles flip when an odd
101 /// number of the factors are negative, so the mesh stays outward-facing.
102 /// @param scale The factor per axis, nonzero and finite.
103 /// @throws std::invalid_argument for a zero or non-finite factor.
104 TriangleMesh Scaled(const TriangleMesh& mesh, const Vec3d& scale);
105
106 } // namespace terraingen
107