]> git.localhorst.tv Git - blobs.git/blobdiff - src/math/geometry.hpp
allow clicking celestial bodies
[blobs.git] / src / math / geometry.hpp
index 4d1b07bbf2f1e93c61f97f5a6fbf685c56f6b724..b4a9f50bb43c86c283691a65736f90981b62368a 100644 (file)
@@ -4,6 +4,8 @@
 #include "glm.hpp"
 
 #include <algorithm>
+#include <ostream>
+#include <glm/gtx/io.hpp>
 
 
 namespace blobs {
@@ -26,6 +28,9 @@ struct AABB {
 
 };
 
+inline std::ostream &operator <<(std::ostream &out, const AABB &b) {
+       return out << "AABB(" << b.min << ", " << b.max << ")";
+}
 /// matrices must not scale
 bool Intersect(
        const AABB &a_box,
@@ -35,6 +40,70 @@ bool Intersect(
        glm::dvec3 &normal,
        double &depth) noexcept;
 
+
+class Ray {
+
+public:
+       Ray(const glm::dvec3 &orig, const glm::dvec3 &dir)
+       : orig(orig), dir(dir), inv_dir(1.0 / dir) { }
+
+       void Origin(const glm::dvec3 &o) noexcept { orig = o; }
+       const glm::dvec3 &Origin() const noexcept { return orig; }
+       void Direction(const glm::dvec3 &d) noexcept { dir = d; inv_dir = 1.0 / d; }
+       const glm::dvec3 &Direction() const noexcept { return dir; }
+       const glm::dvec3 &InverseDirection() const noexcept { return inv_dir; }
+
+private:
+       glm::dvec3 orig;
+       glm::dvec3 dir;
+       glm::dvec3 inv_dir;
+
+};
+
+inline Ray operator *(const glm::dmat4 &m, const Ray &r) noexcept {
+       glm::dvec4 o(m * glm::dvec4(r.Origin(), 1.0));
+       glm::dvec4 d(m * glm::dvec4(r.Origin() + r.Direction(), 1.0));
+       return Ray(glm::dvec3(o) / o.w, glm::normalize((glm::dvec3(d) / d.w) - (glm::dvec3(o) / o.w)));
+}
+
+inline std::ostream &operator <<(std::ostream &out, const Ray &r) {
+       return out << "Ray(" << r.Origin() << ", " << r.Direction() << ")";
+}
+
+/// oriented ray/box intersection test
+bool Intersect(
+       const Ray &,
+       const AABB &,
+       const glm::dmat4 &M,
+       glm::dvec3 &normal,
+       double &dist) noexcept;
+
+
+struct Sphere {
+
+       glm::dvec3 origin;
+       double radius;
+
+};
+
+/// matrix may scale, but only uniformly
+inline Sphere operator *(const glm::dmat4 &m, const Sphere &s) noexcept {
+       glm::dvec4 o(m * glm::dvec4(s.origin, 1.0));
+       glm::dvec4 p(m * glm::dvec4(s.origin + glm::dvec3(s.radius, 0.0, 0.0), 1.0));
+       return Sphere{glm::dvec3(o) / o.w, glm::length((glm::dvec3(p) / p.w) - (glm::dvec3(o) / o.w))};
+}
+
+inline std::ostream &operator <<(std::ostream &out, const Sphere &s) {
+       return out << "Sphere(" << s.origin << ", " << s.radius << ")";
+}
+
+/// oriented ray/sphere intersection test
+bool Intersect(
+       const Ray &,
+       const Sphere &,
+       glm::dvec3 &normal,
+       double &dist) noexcept;
+
 }
 }