#define BLANK_AI_AICONTROLLER_HPP_
#include "../app/IntervalTimer.hpp"
-#include "../model/geometry.hpp"
+#include "../geometry/primitive.hpp"
#include "../world/EntityController.hpp"
#include <glm/glm.hpp>
#include "IdleState.hpp"
#include "RoamState.hpp"
-#include "../model/geometry.hpp"
+#include "../geometry/distance.hpp"
+#include "../geometry/rotation.hpp"
#include "../rand/GaloisLFSR.hpp"
#include "../world/Entity.hpp"
#include "../world/World.hpp"
#include "NetworkedInput.hpp"
#include "../app/init.hpp"
+#include "../geometry/distance.hpp"
#include "../io/WorldSave.hpp"
#include "../net/Packet.hpp"
#include "../world/Chunk.hpp"
--- /dev/null
+#ifndef BLANK_GEOMETRY_CONST_HPP_
+#define BLANK_GEOMETRY_CONST_HPP_
+
+
+namespace blank {
+
+constexpr float PI = 3.141592653589793238462643383279502884;
+constexpr float PI_0p25 = PI * 0.25f;
+constexpr float PI_0p5 = PI * 0.5f;
+constexpr float PI_1p5 = PI * 1.5f;
+constexpr float PI_2p0 = PI * 2.0f;
+
+constexpr float PI_inv = 1.0f / PI;
+constexpr float PI_0p5_inv = 1.0f / PI_0p5;
+
+}
+
+#endif
--- /dev/null
+#ifndef BLANK_GEOMETRY_DISTANCE_HPP_
+#define BLANK_GEOMETRY_DISTANCE_HPP_
+
+#include <algorithm>
+#include <limits>
+#include <glm/glm.hpp>
+
+
+namespace blank {
+
+inline float length_squared(const glm::vec3 &v) noexcept {
+ return dot(v, v);
+}
+
+inline float distance_squared(const glm::vec3 &a, const glm::vec3 &b) noexcept {
+ return length_squared(a - b);
+}
+
+template <class T>
+inline bool iszero(const T &v) noexcept {
+ return length_squared(v) < std::numeric_limits<typename T::value_type>::epsilon();
+}
+
+template<class T>
+T manhattan_distance(const glm::tvec3<T> &a, const glm::tvec3<T> &b) noexcept {
+ glm::tvec3<T> diff(abs(a - b));
+ return diff.x + diff.y + diff.z;
+}
+
+template<class T>
+T manhattan_radius(const glm::tvec3<T> &v) noexcept {
+ glm::tvec3<T> a(abs(v));
+ return std::max(a.x, std::max(a.y, a.z));
+}
+
+}
+
+#endif
--- /dev/null
+#include "const.hpp"
+#include "distance.hpp"
+#include "primitive.hpp"
+#include "rotation.hpp"
+
+#include <limits>
+#include <glm/gtx/matrix_cross_product.hpp>
+#include <glm/gtx/optimum_pow.hpp>
+#include <glm/gtx/transform.hpp>
+
+
+namespace blank {
+
+glm::mat3 find_rotation(const glm::vec3 &a, const glm::vec3 &b) noexcept {
+ glm::vec3 v(cross(a, b));
+ if (iszero(v)) {
+ // a and b are parallel
+ if (iszero(a - b)) {
+ // a and b are identical
+ return glm::mat3(1.0f);
+ } else {
+ // a and b are opposite
+ // create arbitrary unit vector perpendicular to a and
+ // rotate 180° around it
+ glm::vec3 arb(a);
+ if (std::abs(a.x - 1.0f) > std::numeric_limits<float>::epsilon()) {
+ arb.x += 1.0f;
+ } else {
+ arb.y += 1.0f;
+ }
+ glm::vec3 axis(normalize(cross(a, arb)));
+ return glm::mat3(glm::rotate(PI, axis));
+ }
+ }
+ float mv = length_squared(v);
+ float c = dot(a, b);
+ float f = (1 - c) / mv;
+ glm::mat3 vx(matrixCross3(v));
+ return glm::mat3(1.0f) + vx + (pow2(vx) * f);
+}
+
+bool Intersection(
+ const Ray &ray,
+ const AABB &aabb,
+ const glm::mat4 &M,
+ float *dist,
+ glm::vec3 *normal
+) noexcept {
+ float t_min = 0.0f;
+ float t_max = std::numeric_limits<float>::infinity();
+ const glm::vec3 aabb_pos(M[3].x, M[3].y, M[3].z);
+ const glm::vec3 delta = aabb_pos - ray.orig;
+
+ glm::vec3 t1(t_min, t_min, t_min), t2(t_max, t_max, t_max);
+
+ for (int i = 0; i < 3; ++i) {
+ const glm::vec3 axis(M[i].x, M[i].y, M[i].z);
+ const float e = glm::dot(axis, delta);
+ const float f = glm::dot(axis, ray.dir);
+
+ if (std::abs(f) > std::numeric_limits<float>::epsilon()) {
+ t1[i] = (e + aabb.min[i]) / f;
+ t2[i] = (e + aabb.max[i]) / f;
+
+ t_min = std::max(t_min, std::min(t1[i], t2[i]));
+ t_max = std::min(t_max, std::max(t1[i], t2[i]));
+
+ if (t_max < t_min) {
+ return false;
+ }
+ } else {
+ if (aabb.min[i] - e > 0.0f || aabb.max[i] - e < 0.0f) {
+ return false;
+ }
+ }
+ }
+
+ glm::vec3 min_all(min(t1, t2));
+
+ if (dist) {
+ *dist = t_min;
+ }
+ if (normal) {
+ if (min_all.x > min_all.y) {
+ if (min_all.x > min_all.z) {
+ normal->x = t2.x < t1.x ? 1 : -1;
+ } else {
+ normal->z = t2.z < t1.z ? 1 : -1;
+ }
+ } else if (min_all.y > min_all.z) {
+ normal->y = t2.y < t1.y ? 1 : -1;
+ } else {
+ normal->z = t2.z < t1.z ? 1 : -1;
+ }
+ }
+ return true;
+}
+
+
+bool Intersection(
+ const AABB &a_box,
+ const glm::mat4 &a_m,
+ const AABB &b_box,
+ const glm::mat4 &b_m,
+ float &depth,
+ glm::vec3 &normal
+) noexcept {
+ glm::vec3 a_corners[8] = {
+ glm::vec3(a_m * glm::vec4(a_box.min.x, a_box.min.y, a_box.min.z, 1)),
+ glm::vec3(a_m * glm::vec4(a_box.min.x, a_box.min.y, a_box.max.z, 1)),
+ glm::vec3(a_m * glm::vec4(a_box.min.x, a_box.max.y, a_box.min.z, 1)),
+ glm::vec3(a_m * glm::vec4(a_box.min.x, a_box.max.y, a_box.max.z, 1)),
+ glm::vec3(a_m * glm::vec4(a_box.max.x, a_box.min.y, a_box.min.z, 1)),
+ glm::vec3(a_m * glm::vec4(a_box.max.x, a_box.min.y, a_box.max.z, 1)),
+ glm::vec3(a_m * glm::vec4(a_box.max.x, a_box.max.y, a_box.min.z, 1)),
+ glm::vec3(a_m * glm::vec4(a_box.max.x, a_box.max.y, a_box.max.z, 1)),
+ };
+
+ glm::vec3 b_corners[8] = {
+ glm::vec3(b_m * glm::vec4(b_box.min.x, b_box.min.y, b_box.min.z, 1)),
+ glm::vec3(b_m * glm::vec4(b_box.min.x, b_box.min.y, b_box.max.z, 1)),
+ glm::vec3(b_m * glm::vec4(b_box.min.x, b_box.max.y, b_box.min.z, 1)),
+ glm::vec3(b_m * glm::vec4(b_box.min.x, b_box.max.y, b_box.max.z, 1)),
+ glm::vec3(b_m * glm::vec4(b_box.max.x, b_box.min.y, b_box.min.z, 1)),
+ glm::vec3(b_m * glm::vec4(b_box.max.x, b_box.min.y, b_box.max.z, 1)),
+ glm::vec3(b_m * glm::vec4(b_box.max.x, b_box.max.y, b_box.min.z, 1)),
+ glm::vec3(b_m * glm::vec4(b_box.max.x, b_box.max.y, b_box.max.z, 1)),
+ };
+
+ glm::vec3 axes[6] = {
+ glm::vec3(a_m * glm::vec4(1, 0, 0, 0)),
+ glm::vec3(a_m * glm::vec4(0, 1, 0, 0)),
+ glm::vec3(a_m * glm::vec4(0, 0, 1, 0)),
+ glm::vec3(b_m * glm::vec4(1, 0, 0, 0)),
+ glm::vec3(b_m * glm::vec4(0, 1, 0, 0)),
+ glm::vec3(b_m * glm::vec4(0, 0, 1, 0)),
+ };
+
+ depth = std::numeric_limits<float>::infinity();
+ int min_axis = 0;
+
+ int cur_axis = 0;
+ for (const glm::vec3 &axis : axes) {
+ float a_min = std::numeric_limits<float>::infinity();
+ float a_max = -std::numeric_limits<float>::infinity();
+ for (const glm::vec3 &corner : a_corners) {
+ float val = glm::dot(corner, axis);
+ a_min = std::min(a_min, val);
+ a_max = std::max(a_max, val);
+ }
+
+ float b_min = std::numeric_limits<float>::infinity();
+ float b_max = -std::numeric_limits<float>::infinity();
+ for (const glm::vec3 &corner : b_corners) {
+ float val = glm::dot(corner, axis);
+ b_min = std::min(b_min, val);
+ b_max = std::max(b_max, val);
+ }
+
+ if (a_max < b_min || b_max < a_min) return false;
+
+ float overlap = std::min(a_max, b_max) - std::max(a_min, b_min);
+ if (overlap < depth) {
+ depth = overlap;
+ min_axis = cur_axis;
+ }
+
+ ++cur_axis;
+ }
+
+ normal = axes[min_axis];
+ return true;
+}
+
+
+bool CullTest(const AABB &box, const glm::mat4 &MVP) noexcept {
+ // transform corners into clip space
+ glm::vec4 corners[8] = {
+ { box.min.x, box.min.y, box.min.z, 1.0f },
+ { box.min.x, box.min.y, box.max.z, 1.0f },
+ { box.min.x, box.max.y, box.min.z, 1.0f },
+ { box.min.x, box.max.y, box.max.z, 1.0f },
+ { box.max.x, box.min.y, box.min.z, 1.0f },
+ { box.max.x, box.min.y, box.max.z, 1.0f },
+ { box.max.x, box.max.y, box.min.z, 1.0f },
+ { box.max.x, box.max.y, box.max.z, 1.0f },
+ };
+ for (glm::vec4 &corner : corners) {
+ corner = MVP * corner;
+ corner /= corner.w;
+ }
+
+ int hits[6] = { 0, 0, 0, 0, 0, 0 };
+
+ // check how many corners lie outside
+ for (const glm::vec4 &corner : corners) {
+ if (corner.x > 1.0f) ++hits[0];
+ if (corner.x < -1.0f) ++hits[1];
+ if (corner.y > 1.0f) ++hits[2];
+ if (corner.y < -1.0f) ++hits[3];
+ if (corner.z > 1.0f) ++hits[4];
+ if (corner.z < -1.0f) ++hits[5];
+ }
+
+ // if all corners are outside any given clip plane, the test is true
+ for (int hit : hits) {
+ if (hit == 8) return true;
+ }
+
+ // otherwise the box might still get culled completely, but can't say for sure ;)
+ return false;
+}
+
+}
--- /dev/null
+#ifndef BLANK_GEOMETRY_PRIMITIVE_HPP_
+#define BLANK_GEOMETRY_PRIMITIVE_HPP_
+
+#include <algorithm>
+#include <glm/glm.hpp>
+
+
+namespace blank {
+
+struct AABB {
+ glm::vec3 min;
+ glm::vec3 max;
+
+ void Adjust() noexcept {
+ if (max.x < min.x) std::swap(max.x, min.x);
+ if (max.y < min.y) std::swap(max.y, min.y);
+ if (max.z < min.z) std::swap(max.z, min.z);
+ }
+
+ glm::vec3 Center() const noexcept {
+ return min + (max - min) * 0.5f;
+ }
+};
+
+struct Ray {
+ glm::vec3 orig;
+ glm::vec3 dir;
+};
+
+bool Intersection(
+ const Ray &,
+ const AABB &,
+ const glm::mat4 &M,
+ float *dist = nullptr,
+ glm::vec3 *normal = nullptr) noexcept;
+
+bool Intersection(
+ const AABB &a_box,
+ const glm::mat4 &a_m,
+ const AABB &b_box,
+ const glm::mat4 &b_m,
+ float &depth,
+ glm::vec3 &normal) noexcept;
+
+bool CullTest(const AABB &box, const glm::mat4 &MVP) noexcept;
+
+}
+
+#endif
--- /dev/null
+#ifndef BLANK_GEOMETRY_ROTATION_HPP_
+#define BLANK_GEOMETRY_ROTATION_HPP_
+
+#include <glm/glm.hpp>
+
+
+namespace blank {
+
+glm::mat3 find_rotation(const glm::vec3 &a, const glm::vec3 &b) noexcept;
+
+}
+
+#endif
#include "SkyBoxMesh.hpp"
#include "SpriteMesh.hpp"
-#include "../model/geometry.hpp"
+#include "../geometry/primitive.hpp"
#include <algorithm>
#include <iostream>
#include "Viewport.hpp"
#include "../app/init.hpp"
-#include "../model/geometry.hpp"
+#include "../geometry/const.hpp"
#include <GL/glew.h>
#include <glm/gtc/matrix_transform.hpp>
#ifndef BLAMK_MODEL_PART_HPP_
#define BLAMK_MODEL_PART_HPP_
-#include "geometry.hpp"
-
#include <cstdint>
#include <list>
#include <memory>
#define BLANK_MODEL_SHAPE_HPP_
#include "CollisionBounds.hpp"
-#include "geometry.hpp"
+#include "../geometry/primitive.hpp"
#include "../graphics/BlockMesh.hpp"
#include "../graphics/EntityMesh.hpp"
#include "../world/Block.hpp"
#define BLANK_MODEL_BOUNDS_HPP_
#include "CollisionBounds.hpp"
-#include "geometry.hpp"
+#include "../geometry/primitive.hpp"
#include <vector>
#include <glm/glm.hpp>
+++ /dev/null
-#include "geometry.hpp"
-
-#include <limits>
-#include <glm/gtx/matrix_cross_product.hpp>
-#include <glm/gtx/optimum_pow.hpp>
-#include <glm/gtx/transform.hpp>
-
-
-namespace blank {
-
-glm::mat3 find_rotation(const glm::vec3 &a, const glm::vec3 &b) noexcept {
- glm::vec3 v(cross(a, b));
- if (iszero(v)) {
- // a and b are parallel
- if (iszero(a - b)) {
- // a and b are identical
- return glm::mat3(1.0f);
- } else {
- // a and b are opposite
- // create arbitrary unit vector perpendicular to a and
- // rotate 180° around it
- glm::vec3 arb(a);
- if (std::abs(a.x - 1.0f) > std::numeric_limits<float>::epsilon()) {
- arb.x += 1.0f;
- } else {
- arb.y += 1.0f;
- }
- glm::vec3 axis(normalize(cross(a, arb)));
- return glm::mat3(glm::rotate(PI, axis));
- }
- }
- float mv = length_squared(v);
- float c = dot(a, b);
- float f = (1 - c) / mv;
- glm::mat3 vx(matrixCross3(v));
- return glm::mat3(1.0f) + vx + (pow2(vx) * f);
-}
-
-bool Intersection(
- const Ray &ray,
- const AABB &aabb,
- const glm::mat4 &M,
- float *dist,
- glm::vec3 *normal
-) noexcept {
- float t_min = 0.0f;
- float t_max = std::numeric_limits<float>::infinity();
- const glm::vec3 aabb_pos(M[3].x, M[3].y, M[3].z);
- const glm::vec3 delta = aabb_pos - ray.orig;
-
- glm::vec3 t1(t_min, t_min, t_min), t2(t_max, t_max, t_max);
-
- for (int i = 0; i < 3; ++i) {
- const glm::vec3 axis(M[i].x, M[i].y, M[i].z);
- const float e = glm::dot(axis, delta);
- const float f = glm::dot(axis, ray.dir);
-
- if (std::abs(f) > std::numeric_limits<float>::epsilon()) {
- t1[i] = (e + aabb.min[i]) / f;
- t2[i] = (e + aabb.max[i]) / f;
-
- t_min = std::max(t_min, std::min(t1[i], t2[i]));
- t_max = std::min(t_max, std::max(t1[i], t2[i]));
-
- if (t_max < t_min) {
- return false;
- }
- } else {
- if (aabb.min[i] - e > 0.0f || aabb.max[i] - e < 0.0f) {
- return false;
- }
- }
- }
-
- glm::vec3 min_all(min(t1, t2));
-
- if (dist) {
- *dist = t_min;
- }
- if (normal) {
- if (min_all.x > min_all.y) {
- if (min_all.x > min_all.z) {
- normal->x = t2.x < t1.x ? 1 : -1;
- } else {
- normal->z = t2.z < t1.z ? 1 : -1;
- }
- } else if (min_all.y > min_all.z) {
- normal->y = t2.y < t1.y ? 1 : -1;
- } else {
- normal->z = t2.z < t1.z ? 1 : -1;
- }
- }
- return true;
-}
-
-
-bool Intersection(
- const AABB &a_box,
- const glm::mat4 &a_m,
- const AABB &b_box,
- const glm::mat4 &b_m,
- float &depth,
- glm::vec3 &normal
-) noexcept {
- glm::vec3 a_corners[8] = {
- glm::vec3(a_m * glm::vec4(a_box.min.x, a_box.min.y, a_box.min.z, 1)),
- glm::vec3(a_m * glm::vec4(a_box.min.x, a_box.min.y, a_box.max.z, 1)),
- glm::vec3(a_m * glm::vec4(a_box.min.x, a_box.max.y, a_box.min.z, 1)),
- glm::vec3(a_m * glm::vec4(a_box.min.x, a_box.max.y, a_box.max.z, 1)),
- glm::vec3(a_m * glm::vec4(a_box.max.x, a_box.min.y, a_box.min.z, 1)),
- glm::vec3(a_m * glm::vec4(a_box.max.x, a_box.min.y, a_box.max.z, 1)),
- glm::vec3(a_m * glm::vec4(a_box.max.x, a_box.max.y, a_box.min.z, 1)),
- glm::vec3(a_m * glm::vec4(a_box.max.x, a_box.max.y, a_box.max.z, 1)),
- };
-
- glm::vec3 b_corners[8] = {
- glm::vec3(b_m * glm::vec4(b_box.min.x, b_box.min.y, b_box.min.z, 1)),
- glm::vec3(b_m * glm::vec4(b_box.min.x, b_box.min.y, b_box.max.z, 1)),
- glm::vec3(b_m * glm::vec4(b_box.min.x, b_box.max.y, b_box.min.z, 1)),
- glm::vec3(b_m * glm::vec4(b_box.min.x, b_box.max.y, b_box.max.z, 1)),
- glm::vec3(b_m * glm::vec4(b_box.max.x, b_box.min.y, b_box.min.z, 1)),
- glm::vec3(b_m * glm::vec4(b_box.max.x, b_box.min.y, b_box.max.z, 1)),
- glm::vec3(b_m * glm::vec4(b_box.max.x, b_box.max.y, b_box.min.z, 1)),
- glm::vec3(b_m * glm::vec4(b_box.max.x, b_box.max.y, b_box.max.z, 1)),
- };
-
- glm::vec3 axes[6] = {
- glm::vec3(a_m * glm::vec4(1, 0, 0, 0)),
- glm::vec3(a_m * glm::vec4(0, 1, 0, 0)),
- glm::vec3(a_m * glm::vec4(0, 0, 1, 0)),
- glm::vec3(b_m * glm::vec4(1, 0, 0, 0)),
- glm::vec3(b_m * glm::vec4(0, 1, 0, 0)),
- glm::vec3(b_m * glm::vec4(0, 0, 1, 0)),
- };
-
- depth = std::numeric_limits<float>::infinity();
- int min_axis = 0;
-
- int cur_axis = 0;
- for (const glm::vec3 &axis : axes) {
- float a_min = std::numeric_limits<float>::infinity();
- float a_max = -std::numeric_limits<float>::infinity();
- for (const glm::vec3 &corner : a_corners) {
- float val = glm::dot(corner, axis);
- a_min = std::min(a_min, val);
- a_max = std::max(a_max, val);
- }
-
- float b_min = std::numeric_limits<float>::infinity();
- float b_max = -std::numeric_limits<float>::infinity();
- for (const glm::vec3 &corner : b_corners) {
- float val = glm::dot(corner, axis);
- b_min = std::min(b_min, val);
- b_max = std::max(b_max, val);
- }
-
- if (a_max < b_min || b_max < a_min) return false;
-
- float overlap = std::min(a_max, b_max) - std::max(a_min, b_min);
- if (overlap < depth) {
- depth = overlap;
- min_axis = cur_axis;
- }
-
- ++cur_axis;
- }
-
- normal = axes[min_axis];
- return true;
-}
-
-
-bool CullTest(const AABB &box, const glm::mat4 &MVP) noexcept {
- // transform corners into clip space
- glm::vec4 corners[8] = {
- { box.min.x, box.min.y, box.min.z, 1.0f },
- { box.min.x, box.min.y, box.max.z, 1.0f },
- { box.min.x, box.max.y, box.min.z, 1.0f },
- { box.min.x, box.max.y, box.max.z, 1.0f },
- { box.max.x, box.min.y, box.min.z, 1.0f },
- { box.max.x, box.min.y, box.max.z, 1.0f },
- { box.max.x, box.max.y, box.min.z, 1.0f },
- { box.max.x, box.max.y, box.max.z, 1.0f },
- };
- for (glm::vec4 &corner : corners) {
- corner = MVP * corner;
- corner /= corner.w;
- }
-
- int hits[6] = { 0, 0, 0, 0, 0, 0 };
-
- // check how many corners lie outside
- for (const glm::vec4 &corner : corners) {
- if (corner.x > 1.0f) ++hits[0];
- if (corner.x < -1.0f) ++hits[1];
- if (corner.y > 1.0f) ++hits[2];
- if (corner.y < -1.0f) ++hits[3];
- if (corner.z > 1.0f) ++hits[4];
- if (corner.z < -1.0f) ++hits[5];
- }
-
- // if all corners are outside any given clip plane, the test is true
- for (int hit : hits) {
- if (hit == 8) return true;
- }
-
- // otherwise the box might still get culled completely, but can't say for sure ;)
- return false;
-}
-
-}
+++ /dev/null
-#ifndef BLANK_MODEL_GEOMETRY_H_
-#define BLANK_MODEL_GEOMETRY_H_
-
-#include <algorithm>
-#include <limits>
-#include <glm/glm.hpp>
-
-
-namespace blank {
-
-constexpr float PI = 3.141592653589793238462643383279502884;
-constexpr float PI_0p25 = PI * 0.25f;
-constexpr float PI_0p5 = PI * 0.5f;
-constexpr float PI_1p5 = PI * 1.5f;
-constexpr float PI_2p0 = PI * 2.0f;
-
-constexpr float PI_inv = 1.0f / PI;
-constexpr float PI_0p5_inv = 1.0f / PI_0p5;
-
-constexpr float DEG_RAD_FACTOR = PI / 180.0f;
-constexpr float RAD_DEG_FACTOR = 180.0f / PI;
-
-constexpr float deg2rad(float d) noexcept {
- return d * DEG_RAD_FACTOR;
-}
-
-constexpr float rad2deg(float r) noexcept {
- return r * RAD_DEG_FACTOR;
-}
-
-
-inline float length_squared(const glm::vec3 &v) noexcept {
- return dot(v, v);
-}
-
-inline float distance_squared(const glm::vec3 &a, const glm::vec3 &b) noexcept {
- return length_squared(a - b);
-}
-
-
-template <class T>
-inline bool iszero(const T &v) noexcept {
- return length_squared(v) < std::numeric_limits<typename T::value_type>::epsilon();
-}
-
-
-template<class T>
-T manhattan_distance(const glm::tvec3<T> &a, const glm::tvec3<T> &b) noexcept {
- glm::tvec3<T> diff(abs(a - b));
- return diff.x + diff.y + diff.z;
-}
-
-template<class T>
-T manhattan_radius(const glm::tvec3<T> &v) noexcept {
- glm::tvec3<T> a(abs(v));
- return std::max(a.x, std::max(a.y, a.z));
-}
-
-
-glm::mat3 find_rotation(const glm::vec3 &a, const glm::vec3 &b) noexcept;
-
-
-struct AABB {
- glm::vec3 min;
- glm::vec3 max;
-
- void Adjust() noexcept {
- if (max.x < min.x) std::swap(max.x, min.x);
- if (max.y < min.y) std::swap(max.y, min.y);
- if (max.z < min.z) std::swap(max.z, min.z);
- }
-
- glm::vec3 Center() const noexcept {
- return min + (max - min) * 0.5f;
- }
-};
-
-struct Ray {
- glm::vec3 orig;
- glm::vec3 dir;
-};
-
-bool Intersection(
- const Ray &,
- const AABB &,
- const glm::mat4 &M,
- float *dist = nullptr,
- glm::vec3 *normal = nullptr) noexcept;
-
-bool Intersection(
- const AABB &a_box,
- const glm::mat4 &a_m,
- const AABB &b_box,
- const glm::mat4 &b_m,
- float &depth,
- glm::vec3 &normal) noexcept;
-
-bool CullTest(const AABB &box, const glm::mat4 &MVP) noexcept;
-
-}
-
-#endif
#include "Packet.hpp"
#include "../app/init.hpp"
+#include "../geometry/const.hpp"
#include "../model/Model.hpp"
#include "../world/Entity.hpp"
#include "../world/EntityState.hpp"
#include "Server.hpp"
#include "../app/init.hpp"
+#include "../geometry/distance.hpp"
#include "../io/WorldSave.hpp"
#include "../model/Model.hpp"
#include "../world/ChunkIndex.hpp"
#include "../app/init.hpp"
#include "../audio/Audio.hpp"
#include "../audio/SoundBank.hpp"
+#include "../geometry/distance.hpp"
#include "../graphics/Font.hpp"
#include "../graphics/Viewport.hpp"
#include "../io/TokenStreamReader.hpp"
void HUD::UpdateOrientation() {
std::stringstream s;
- s << std::setprecision(3) << "pitch: " << rad2deg(player.GetEntity().Pitch())
- << ", yaw: " << rad2deg(player.GetEntity().Yaw());
+ s << std::setprecision(3) << "pitch: " << glm::degrees(player.GetEntity().Pitch())
+ << ", yaw: " << glm::degrees(player.GetEntity().Yaw());
orientation_text.Set(env.assets.small_ui_font, s.str());
}
#include "Block.hpp"
#include "BlockTypeRegistry.hpp"
-#include "../model/geometry.hpp"
+#include "../geometry/primitive.hpp"
#include <vector>
#include <glm/glm.hpp>
#include "Chunk.hpp"
#include "EntityState.hpp"
+#include "../geometry/primitive.hpp"
#include "../model/Instance.hpp"
-#include "../model/geometry.hpp"
#include <cstdint>
#include <string>
#include "BlockType.hpp"
#include "BlockTypeRegistry.hpp"
-#include "../model/geometry.hpp"
-
#include <ostream>
#include <glm/gtx/euler_angles.hpp>
#include <glm/gtx/transform.hpp>
#include "Generator.hpp"
#include "WorldCollision.hpp"
#include "../app/Assets.hpp"
+#include "../geometry/distance.hpp"
#include "../graphics/BlockLighting.hpp"
#include "../graphics/BlockMesh.hpp"
#include "../graphics/Viewport.hpp"
#include "EntityCollision.hpp"
#include "WorldCollision.hpp"
#include "../app/Assets.hpp"
+#include "../geometry/const.hpp"
+#include "../geometry/distance.hpp"
#include "../graphics/Format.hpp"
#include "../graphics/Viewport.hpp"
std::cout << "forward: " << forward << std::endl;
std::cout << "facing: " << facing << std::endl;
std::cout << "direction: " << direction << std::endl;
- std::cout << "difference: " << rad2deg(relative_difference) << "°" << std::endl;
- std::cout << "correction: " << rad2deg(correction) << "°" << std::endl;
+ std::cout << "difference: " << glm::degrees(relative_difference) << "°" << std::endl;
+ std::cout << "correction: " << glm::degrees(correction) << "°" << std::endl;
std::cout << std::endl;
}
// now rotate body by correction and head by -correction
--- /dev/null
+#include "IntersectionTest.hpp"
+
+#include "geometry/const.hpp"
+#include "geometry/primitive.hpp"
+
+#include <limits>
+#include <glm/gtx/io.hpp>
+#include <glm/gtx/transform.hpp>
+
+CPPUNIT_TEST_SUITE_REGISTRATION(blank::test::IntersectionTest);
+
+
+namespace blank {
+namespace test {
+
+void IntersectionTest::setUp() {
+}
+
+void IntersectionTest::tearDown() {
+}
+
+
+void IntersectionTest::testRayBoxIntersection() {
+ Ray ray{ { 0, 0, 0 }, { 1, 0, 0 } }; // at origin, pointing right
+ AABB box{ { -1, -1, -1 }, { 1, 1, 1 } }; // 2x2x2 cube centered around origin
+ glm::mat4 M(1); // no transformation
+
+ const float delta = std::numeric_limits<float>::epsilon();
+
+ float distance = 0;
+ glm::vec3 normal(0);
+
+ CPPUNIT_ASSERT_MESSAGE(
+ "ray at origin not intersecting box at origin",
+ Intersection(ray, box, M, &distance)
+ );
+ CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
+ "intersection distance way off",
+ 0.0f, distance, delta
+ );
+ // normal undefined, so can't test
+
+ // move ray outside the box, but have it still point at it
+ // should be 4 units to the left now
+ ray.orig.x = -5;
+ CPPUNIT_ASSERT_MESSAGE(
+ "ray pointing at box doesn't intersect",
+ Intersection(ray, box, M, &distance, &normal)
+ );
+ CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
+ "intersection distance way off",
+ 4.0f, distance, delta
+ );
+ CPPUNIT_ASSERT_EQUAL_MESSAGE(
+ "wrong surface normal at intersection point",
+ glm::vec3(-1, 0, 0), normal
+ );
+
+ // move ray to the other side, so it's pointing away now
+ ray.orig.x = 5;
+ CPPUNIT_ASSERT_MESSAGE(
+ "ray pointing away from box still intersects",
+ !Intersection(ray, box, M)
+ );
+}
+
+void IntersectionTest::testBoxBoxIntersection() {
+ const float delta = std::numeric_limits<float>::epsilon();
+ float depth = 0;
+ glm::vec3 normal(0);
+
+ AABB box{ { -1, -1, -1 }, { 1, 1, 1 } }; // 2x2x2 cube centered around origin
+ glm::mat4 Ma(1); // identity
+ glm::mat4 Mb(1); // identity
+ // they're identical, so should probably intersect ^^
+
+ CPPUNIT_ASSERT_MESSAGE(
+ "identical OBBs don't intersect",
+ Intersection(box, Ma, box, Mb, depth, normal)
+ );
+ // depth is two, but normal can be any
+ // (will probably be the first axis of box a, but any is valid)
+ CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
+ "penetration depth of coincidental 2x2x2 boxes is not 2",
+ 2.0f, depth, delta
+ );
+
+ Ma = glm::translate(glm::vec3(-2, 0, 0)); // 2 to the left
+ Mb = glm::translate(glm::vec3(2, 0, 0)); // 2 to the right
+ CPPUNIT_ASSERT_MESSAGE(
+ "distant OBBs intersect (2 apart, no rotation)",
+ !Intersection(box, Ma, box, Mb, depth, normal)
+ );
+ // depth and normal undefined for non-intersecting objects
+
+ Ma = glm::rotate(PI_0p25, glm::vec3(0, 0, 1)); // rotated 45° around Z
+ Mb = glm::translate(glm::vec3(2.4, 0, 0)); // 2.4 to the right
+ // they should barely touch. intersect by about sqrt(2) - 1.4 if my head works
+ CPPUNIT_ASSERT_MESSAGE(
+ "OBBs don't intersect (one rotated by 45°)",
+ Intersection(box, Ma, box, Mb, depth, normal)
+ );
+ CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
+ "bad penetration depth (with rotation)",
+ 0.01421356237309504880f, depth, delta
+ );
+ CPPUNIT_ASSERT_EQUAL_MESSAGE(
+ "bad intersection normal (with rotation)",
+ glm::vec3(1, 0, 0), abs(normal) // normal can be in + or - x, therefore abs()
+ );
+
+ Mb = glm::translate(glm::vec3(3, 0, 0)); // 3 to the right
+ CPPUNIT_ASSERT_MESSAGE(
+ "OBBs intersect (one rotated by 45°)",
+ !Intersection(box, Ma, box, Mb, depth, normal)
+ );
+}
+
+}
+}
--- /dev/null
+#ifndef BLANK_TEST_GEOMETRY_INTERSECTIONTEST_H_
+#define BLANK_TEST_GEOMETRY_INTERSECTIONTEST_H_
+
+#include <cppunit/extensions/HelperMacros.h>
+
+
+namespace blank {
+namespace test {
+
+class IntersectionTest
+: public CppUnit::TestFixture {
+
+CPPUNIT_TEST_SUITE(IntersectionTest);
+
+CPPUNIT_TEST(testRayBoxIntersection);
+CPPUNIT_TEST(testBoxBoxIntersection);
+
+CPPUNIT_TEST_SUITE_END();
+
+public:
+ void setUp();
+ void tearDown();
+
+ void testRayBoxIntersection();
+ void testBoxBoxIntersection();
+
+};
+
+}
+}
+
+#endif
+++ /dev/null
-#include "GeometryTest.hpp"
-
-#include "model/geometry.hpp"
-
-#include <limits>
-#include <glm/gtx/io.hpp>
-#include <glm/gtx/transform.hpp>
-
-CPPUNIT_TEST_SUITE_REGISTRATION(blank::test::GeometryTest);
-
-
-namespace blank {
-namespace test {
-
-void GeometryTest::setUp() {
-}
-
-void GeometryTest::tearDown() {
-}
-
-
-void GeometryTest::testRayBoxIntersection() {
- Ray ray{ { 0, 0, 0 }, { 1, 0, 0 } }; // at origin, pointing right
- AABB box{ { -1, -1, -1 }, { 1, 1, 1 } }; // 2x2x2 cube centered around origin
- glm::mat4 M(1); // no transformation
-
- const float delta = std::numeric_limits<float>::epsilon();
-
- float distance = 0;
- glm::vec3 normal(0);
-
- CPPUNIT_ASSERT_MESSAGE(
- "ray at origin not intersecting box at origin",
- Intersection(ray, box, M, &distance)
- );
- CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
- "intersection distance way off",
- 0.0f, distance, delta
- );
- // normal undefined, so can't test
-
- // move ray outside the box, but have it still point at it
- // should be 4 units to the left now
- ray.orig.x = -5;
- CPPUNIT_ASSERT_MESSAGE(
- "ray pointing at box doesn't intersect",
- Intersection(ray, box, M, &distance, &normal)
- );
- CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
- "intersection distance way off",
- 4.0f, distance, delta
- );
- CPPUNIT_ASSERT_EQUAL_MESSAGE(
- "wrong surface normal at intersection point",
- glm::vec3(-1, 0, 0), normal
- );
-
- // move ray to the other side, so it's pointing away now
- ray.orig.x = 5;
- CPPUNIT_ASSERT_MESSAGE(
- "ray pointing away from box still intersects",
- !Intersection(ray, box, M)
- );
-}
-
-void GeometryTest::testBoxBoxIntersection() {
- const float delta = std::numeric_limits<float>::epsilon();
- float depth = 0;
- glm::vec3 normal(0);
-
- AABB box{ { -1, -1, -1 }, { 1, 1, 1 } }; // 2x2x2 cube centered around origin
- glm::mat4 Ma(1); // identity
- glm::mat4 Mb(1); // identity
- // they're identical, so should probably intersect ^^
-
- CPPUNIT_ASSERT_MESSAGE(
- "identical OBBs don't intersect",
- Intersection(box, Ma, box, Mb, depth, normal)
- );
- // depth is two, but normal can be any
- // (will probably be the first axis of box a, but any is valid)
- CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
- "penetration depth of coincidental 2x2x2 boxes is not 2",
- 2.0f, depth, delta
- );
-
- Ma = glm::translate(glm::vec3(-2, 0, 0)); // 2 to the left
- Mb = glm::translate(glm::vec3(2, 0, 0)); // 2 to the right
- CPPUNIT_ASSERT_MESSAGE(
- "distant OBBs intersect (2 apart, no rotation)",
- !Intersection(box, Ma, box, Mb, depth, normal)
- );
- // depth and normal undefined for non-intersecting objects
-
- Ma = glm::rotate(PI_0p25, glm::vec3(0, 0, 1)); // rotated 45° around Z
- Mb = glm::translate(glm::vec3(2.4, 0, 0)); // 2.4 to the right
- // they should barely touch. intersect by about sqrt(2) - 1.4 if my head works
- CPPUNIT_ASSERT_MESSAGE(
- "OBBs don't intersect (one rotated by 45°)",
- Intersection(box, Ma, box, Mb, depth, normal)
- );
- CPPUNIT_ASSERT_DOUBLES_EQUAL_MESSAGE(
- "bad penetration depth (with rotation)",
- 0.01421356237309504880f, depth, delta
- );
- CPPUNIT_ASSERT_EQUAL_MESSAGE(
- "bad intersection normal (with rotation)",
- glm::vec3(1, 0, 0), abs(normal) // normal can be in + or - x, therefore abs()
- );
-
- Mb = glm::translate(glm::vec3(3, 0, 0)); // 3 to the right
- CPPUNIT_ASSERT_MESSAGE(
- "OBBs intersect (one rotated by 45°)",
- !Intersection(box, Ma, box, Mb, depth, normal)
- );
-}
-
-}
-}
+++ /dev/null
-#ifndef BLANK_TEST_MODEL_GEOMETRYTEST_H_
-#define BLANK_TEST_MODEL_GEOMETRYTEST_H_
-
-#include <cppunit/extensions/HelperMacros.h>
-
-
-namespace blank {
-namespace test {
-
-class GeometryTest
-: public CppUnit::TestFixture {
-
-CPPUNIT_TEST_SUITE(GeometryTest);
-
-CPPUNIT_TEST(testRayBoxIntersection);
-CPPUNIT_TEST(testBoxBoxIntersection);
-
-CPPUNIT_TEST_SUITE_END();
-
-public:
- void setUp();
- void tearDown();
-
- void testRayBoxIntersection();
- void testBoxBoxIntersection();
-
-};
-
-}
-}
-
-#endif
#include "PacketTest.hpp"
+#include "geometry/const.hpp"
#include "model/Model.hpp"
#include "world/Entity.hpp"
#ifndef BLANK_TEST_NET_PACKETTEST_HPP_
#define BLANK_TEST_NET_PACKETTEST_HPP_
-#include "model/geometry.hpp"
+#include "geometry/primitive.hpp"
#include "net/Packet.hpp"
#include "world/EntityState.hpp"