summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDan Goodliffe <dan@randomdan.homeip.net>2024-01-07 13:04:31 +0000
committerDan Goodliffe <dan@randomdan.homeip.net>2024-01-07 13:04:31 +0000
commit6a1df3dfbae98a05e74c646cc216fbc19ffdb6d6 (patch)
tree46c42bcbef1f12c4f46d53b4e0c4736bea506b51
parentUnified crossProduct (diff)
downloadilt-6a1df3dfbae98a05e74c646cc216fbc19ffdb6d6.tar.bz2
ilt-6a1df3dfbae98a05e74c646cc216fbc19ffdb6d6.tar.xz
ilt-6a1df3dfbae98a05e74c646cc216fbc19ffdb6d6.zip
Template Ray on position type
-rw-r--r--assetFactory/faceController.cpp2
-rw-r--r--game/geoData.cpp12
-rw-r--r--game/geoData.h4
-rw-r--r--game/network/link.cpp9
-rw-r--r--game/network/link.h8
-rw-r--r--game/network/network.cpp7
-rw-r--r--game/network/network.h8
-rw-r--r--game/network/network.impl.h2
-rw-r--r--game/selectable.h5
-rw-r--r--game/vehicles/railVehicle.cpp6
-rw-r--r--game/vehicles/railVehicle.h4
-rw-r--r--game/vehicles/train.cpp4
-rw-r--r--game/vehicles/train.h4
-rw-r--r--gfx/gl/camera.cpp2
-rw-r--r--gfx/gl/camera.h2
-rw-r--r--lib/geometricPlane.h2
-rw-r--r--lib/ray.cpp36
-rw-r--r--lib/ray.h78
-rw-r--r--test/test-geoData.cpp4
-rw-r--r--test/test-maths.cpp2
-rw-r--r--ui/builders/freeExtend.cpp6
-rw-r--r--ui/builders/freeExtend.h6
-rw-r--r--ui/builders/join.cpp5
-rw-r--r--ui/builders/join.h6
-rw-r--r--ui/builders/straight.cpp6
-rw-r--r--ui/builders/straight.h6
-rw-r--r--ui/editNetwork.cpp4
-rw-r--r--ui/editNetwork.h10
-rw-r--r--ui/gameMainSelector.cpp6
-rw-r--r--ui/gameMainSelector.h8
30 files changed, 153 insertions, 111 deletions
diff --git a/assetFactory/faceController.cpp b/assetFactory/faceController.cpp
index d045b3c..10a0c1e 100644
--- a/assetFactory/faceController.cpp
+++ b/assetFactory/faceController.cpp
@@ -90,7 +90,7 @@ FaceController::split(
const size_t nextIdx = (curIdx + 1) % vertexRelations.size();
const auto &current = vertexRelations[curIdx], next = vertexRelations[nextIdx];
if (GeometricPlane::isIntersect(current.second, next.second)) {
- const auto ray = Ray::fromPoints(mesh.point(current.first), mesh.point(next.first));
+ const auto ray = RayFactory::fromPoints(mesh.point(current.first), mesh.point(next.first));
const auto intersect = split.getRayIntersectPosition(ray);
assert(intersect);
const auto newv = mesh.add_vertex(intersect->position);
diff --git a/game/geoData.cpp b/game/geoData.cpp
index 816733f..b30a35b 100644
--- a/game/geoData.cpp
+++ b/game/geoData.cpp
@@ -194,23 +194,23 @@ GeoData::positionAt(const PointFace & p) const
}
[[nodiscard]] std::optional<GlobalPosition3D>
-GeoData::intersectRay(const Ray & ray) const
+GeoData::intersectRay(const Ray<GlobalPosition3D> & ray) const
{
return intersectRay(ray, findPoint(ray.start));
}
[[nodiscard]] std::optional<GlobalPosition3D>
-GeoData::intersectRay(const Ray & ray, FaceHandle face) const
+GeoData::intersectRay(const Ray<GlobalPosition3D> & ray, FaceHandle face) const
{
std::optional<GlobalPosition3D> out;
walkUntil(PointFace {ray.start, face},
- ray.start.xy() + (ray.direction.xy() * RelativePosition2D(upperExtent.xy() - lowerExtent.xy())),
+ ray.start.xy()
+ + GlobalPosition2D(ray.direction.xy() * RelativePosition2D(upperExtent.xy() - lowerExtent.xy())),
[&out, &ray, this](FaceHandle face) {
BaryPosition bari {};
- float dist {};
+ RelativeDistance dist {};
const auto t = triangle<3>(face);
- if (glm::intersectRayTriangle<RelativePosition3D::value_type, glm::defaultp>(
- ray.start, ray.direction, t[0], t[1], t[2], bari, dist)) {
+ if (ray.intersectTriangle(t.x, t.y, t.z, bari, dist)) {
out = t * bari;
return true;
}
diff --git a/game/geoData.h b/game/geoData.h
index d4d0fb3..e234bfe 100644
--- a/game/geoData.h
+++ b/game/geoData.h
@@ -74,8 +74,8 @@ public:
[[nodiscard]] FaceHandle findPoint(GlobalPosition2D, FaceHandle start) const;
[[nodiscard]] GlobalPosition3D positionAt(const PointFace &) const;
- [[nodiscard]] std::optional<GlobalPosition3D> intersectRay(const Ray &) const;
- [[nodiscard]] std::optional<GlobalPosition3D> intersectRay(const Ray &, FaceHandle start) const;
+ [[nodiscard]] std::optional<GlobalPosition3D> intersectRay(const Ray<GlobalPosition3D> &) const;
+ [[nodiscard]] std::optional<GlobalPosition3D> intersectRay(const Ray<GlobalPosition3D> &, FaceHandle start) const;
void walk(const PointFace & from, const GlobalPosition2D to, const std::function<void(FaceHandle)> & op) const;
void walkUntil(const PointFace & from, const GlobalPosition2D to, const std::function<bool(FaceHandle)> & op) const;
diff --git a/game/network/link.cpp b/game/network/link.cpp
index 703a1ca..e8eaea2 100644
--- a/game/network/link.cpp
+++ b/game/network/link.cpp
@@ -33,9 +33,10 @@ LinkStraight::positionAt(float dist, unsigned char start) const
}
bool
-LinkStraight::intersectRay(const Ray & ray) const
+LinkStraight::intersectRay(const Ray<GlobalPosition3D> & ray) const
{
- return ray.passesCloseToEdges(std::array {ends.front().node->pos, ends.back().node->pos}, 1.F);
+ return ray.passesCloseToEdges(
+ std::array {GlobalPosition3D {ends.front().node->pos}, GlobalPosition3D {ends.back().node->pos}}, 1000);
}
Location
@@ -54,7 +55,7 @@ LinkCurve::positionAt(float dist, unsigned char start) const
}
bool
-LinkCurve::intersectRay(const Ray & ray) const
+LinkCurve::intersectRay(const Ray<GlobalPosition3D> & ray) const
{
const auto & e0p {ends[0].node->pos};
const auto & e1p {ends[1].node->pos};
@@ -64,7 +65,7 @@ LinkCurve::intersectRay(const Ray & ray) const
const auto trans {glm::translate(centreBase)};
auto segCount = static_cast<std::size_t>(std::lround(segs)) + 1;
- std::vector<Position3D> points;
+ std::vector<GlobalPosition3D> points;
points.reserve(segCount);
for (Position3D swing = {arc.first, centreBase.z - e0p.z, 0.F}; segCount; swing += step, --segCount) {
const auto t {trans * glm::rotate(half_pi - swing.x, up) * glm::translate(Position3D {radius, 0.F, swing.y})};
diff --git a/game/network/link.h b/game/network/link.h
index 78d3e91..95c141e 100644
--- a/game/network/link.h
+++ b/game/network/link.h
@@ -10,7 +10,7 @@
#include <utility>
#include <vector>
-class Ray;
+template<typename> class Ray;
// Generic network node
// something that can be travelled to
@@ -45,7 +45,7 @@ public:
NO_MOVE(Link);
[[nodiscard]] virtual Location positionAt(float dist, unsigned char start) const = 0;
- [[nodiscard]] virtual bool intersectRay(const Ray &) const = 0;
+ [[nodiscard]] virtual bool intersectRay(const Ray<GlobalPosition3D> &) const = 0;
std::array<End, 2> ends;
float length;
@@ -69,7 +69,7 @@ public:
NO_MOVE(LinkStraight);
[[nodiscard]] Location positionAt(float dist, unsigned char start) const override;
- [[nodiscard]] bool intersectRay(const Ray &) const override;
+ [[nodiscard]] bool intersectRay(const Ray<GlobalPosition3D> &) const override;
};
LinkStraight::~LinkStraight() = default;
@@ -82,7 +82,7 @@ public:
NO_MOVE(LinkCurve);
[[nodiscard]] Location positionAt(float dist, unsigned char start) const override;
- [[nodiscard]] bool intersectRay(const Ray &) const override;
+ [[nodiscard]] bool intersectRay(const Ray<GlobalPosition3D> &) const override;
Position3D centreBase;
float radius;
diff --git a/game/network/network.cpp b/game/network/network.cpp
index 1ff5b26..d52e804 100644
--- a/game/network/network.cpp
+++ b/game/network/network.cpp
@@ -49,13 +49,14 @@ Network::candidateNodeAt(Position3D pos) const
}
Node::Ptr
-Network::intersectRayNodes(const Ray & ray) const
+Network::intersectRayNodes(const Ray<GlobalPosition3D> & ray) const
{
// Click within 2m of a node
if (const auto node = std::find_if(nodes.begin(), nodes.end(),
[&ray](const Node::Ptr & node) {
- Position3D ipos, inorm;
- return glm::intersectRaySphere(ray.start, ray.direction, node->pos, 2.F, ipos, inorm);
+ GlobalPosition3D ipos;
+ Normal3D inorm;
+ return ray.intersectSphere(node->pos, 2000, ipos, inorm);
});
node != nodes.end()) {
return *node;
diff --git a/game/network/network.h b/game/network/network.h
index 8af06a9..9ce6e81 100644
--- a/game/network/network.h
+++ b/game/network/network.h
@@ -14,7 +14,7 @@
class Texture;
class SceneShader;
-class Ray;
+template<typename> class Ray;
template<size_t... n> using GenDef = std::tuple<glm::vec<n, Distance>...>;
using GenCurveDef = GenDef<3, 3, 2>;
@@ -32,8 +32,8 @@ public:
using NodeInsertion = std::pair<Node::Ptr, NodeIs>;
[[nodiscard]] NodeInsertion newNodeAt(Position3D);
[[nodiscard]] NodeInsertion candidateNodeAt(Position3D) const;
- [[nodiscard]] virtual Link::Ptr intersectRayLinks(const Ray &) const = 0;
- [[nodiscard]] virtual Node::Ptr intersectRayNodes(const Ray &) const;
+ [[nodiscard]] virtual Link::Ptr intersectRayLinks(const Ray<GlobalPosition3D> &) const = 0;
+ [[nodiscard]] virtual Node::Ptr intersectRayNodes(const Ray<GlobalPosition3D> &) const;
[[nodiscard]] Link::Nexts routeFromTo(const Link::End &, Position3D) const;
[[nodiscard]] Link::Nexts routeFromTo(const Link::End &, const Node::Ptr &) const;
@@ -66,7 +66,7 @@ protected:
void joinLinks(const Link::Ptr &) const;
protected:
- [[nodiscard]] Link::Ptr intersectRayLinks(const Ray &) const override;
+ [[nodiscard]] Link::Ptr intersectRayLinks(const Ray<GlobalPosition3D> &) const override;
public:
template<typename L, typename... Params>
diff --git a/game/network/network.impl.h b/game/network/network.impl.h
index 8e9e85c..4acbb6d 100644
--- a/game/network/network.impl.h
+++ b/game/network/network.impl.h
@@ -24,7 +24,7 @@ NetworkOf<T>::joinLinks(const Link::Ptr & l) const
template<typename T>
Link::Ptr
-NetworkOf<T>::intersectRayLinks(const Ray & ray) const
+NetworkOf<T>::intersectRayLinks(const Ray<GlobalPosition3D> & ray) const
{
// Click link
if (const auto link = std::find_if(links.objects.begin(), links.objects.end(),
diff --git a/game/selectable.h b/game/selectable.h
index c794461..fc6af4e 100644
--- a/game/selectable.h
+++ b/game/selectable.h
@@ -4,7 +4,7 @@
#include <glm/glm.hpp>
#include <special_members.h>
-class Ray;
+template<typename> class Ray;
class Selectable {
public:
@@ -12,5 +12,6 @@ public:
virtual ~Selectable() = default;
DEFAULT_MOVE_COPY(Selectable);
- [[nodiscard]] virtual bool intersectRay(const Ray &, BaryPosition &, RelativeDistance &) const = 0;
+ [[nodiscard]] virtual bool intersectRay(const Ray<GlobalPosition3D> &, BaryPosition &, RelativeDistance &) const
+ = 0;
};
diff --git a/game/vehicles/railVehicle.cpp b/game/vehicles/railVehicle.cpp
index c720eb6..985e9f2 100644
--- a/game/vehicles/railVehicle.cpp
+++ b/game/vehicles/railVehicle.cpp
@@ -44,7 +44,7 @@ RailVehicle::move(const Train * t, float & trailBy)
}
bool
-RailVehicle::intersectRay(const Ray & ray, BaryPosition & baryPos, RelativeDistance & distance) const
+RailVehicle::intersectRay(const Ray<GlobalPosition3D> & ray, BaryPosition & baryPos, RelativeDistance & distance) const
{
constexpr const auto X = 1350.F;
const auto Y = this->rvClass->length / 2.F;
@@ -73,7 +73,7 @@ RailVehicle::intersectRay(const Ray & ray, BaryPosition & baryPos, RelativeDista
}};
return std::any_of(
triangles.begin(), triangles.end(), [&cornerVertices, &ray, &baryPos, &distance](const auto & idx) {
- return glm::intersectRayTriangle(ray.start, ray.direction, cornerVertices[idx[0]],
- cornerVertices[idx[1]], cornerVertices[idx[2]], baryPos, distance);
+ return ray.intersectTriangle(
+ cornerVertices[idx[0]], cornerVertices[idx[1]], cornerVertices[idx[2]], baryPos, distance);
});
}
diff --git a/game/vehicles/railVehicle.h b/game/vehicles/railVehicle.h
index f6e4764..bf1e782 100644
--- a/game/vehicles/railVehicle.h
+++ b/game/vehicles/railVehicle.h
@@ -7,7 +7,7 @@
#include <glm/glm.hpp>
#include <memory>
-class Ray;
+template<typename> class Ray;
class Train;
class RailVehicle : Selectable, RailVehicleClass::Instance {
@@ -16,7 +16,7 @@ public:
void move(const Train *, float & trailBy);
- [[nodiscard]] bool intersectRay(const Ray &, BaryPosition &, RelativeDistance &) const override;
+ [[nodiscard]] bool intersectRay(const Ray<GlobalPosition3D> &, BaryPosition &, RelativeDistance &) const override;
RailVehicleClassPtr rvClass;
using LV = RailVehicleClass::LocationVertex;
diff --git a/game/vehicles/train.cpp b/game/vehicles/train.cpp
index 05b2d8a..5bddd61 100644
--- a/game/vehicles/train.cpp
+++ b/game/vehicles/train.cpp
@@ -9,7 +9,7 @@
#include <optional>
#include <utility>
-class Ray;
+template<typename> class Ray;
Location
Train::getBogiePosition(float linkDist, float dist) const
@@ -20,7 +20,7 @@ Train::getBogiePosition(float linkDist, float dist) const
}
bool
-Train::intersectRay(const Ray & ray, BaryPosition & baryPos, RelativeDistance & distance) const
+Train::intersectRay(const Ray<GlobalPosition3D> & ray, BaryPosition & baryPos, RelativeDistance & distance) const
{
return applyOne(&RailVehicle::intersectRay, ray, baryPos, distance) != end();
}
diff --git a/game/vehicles/train.h b/game/vehicles/train.h
index bb668ed..4320103 100644
--- a/game/vehicles/train.h
+++ b/game/vehicles/train.h
@@ -13,7 +13,7 @@
class SceneShader;
class ShadowMapper;
-class Ray;
+template<typename> class Ray;
class Train : public Vehicle, public Collection<RailVehicle, false>, public Can<Go>, public Can<Idle> {
public:
@@ -25,7 +25,7 @@ public:
return objects.front()->location;
}
- [[nodiscard]] bool intersectRay(const Ray &, BaryPosition &, RelativeDistance &) const override;
+ [[nodiscard]] bool intersectRay(const Ray<GlobalPosition3D> &, BaryPosition &, RelativeDistance &) const override;
void tick(TickDuration elapsed) override;
void doActivity(Go *, TickDuration) override;
diff --git a/gfx/gl/camera.cpp b/gfx/gl/camera.cpp
index 0bc911a..fb711dd 100644
--- a/gfx/gl/camera.cpp
+++ b/gfx/gl/camera.cpp
@@ -13,7 +13,7 @@ Camera::Camera(GlobalPosition3D pos, Angle fov, Angle aspect, GlobalDistance zNe
updateView();
}
-Ray
+Ray<GlobalPosition3D>
Camera::unProject(const ScreenRelCoord & mouse) const
{
static constexpr const glm::vec4 screen {0, 0, 1, 1};
diff --git a/gfx/gl/camera.h b/gfx/gl/camera.h
index eca7b8f..8d53261 100644
--- a/gfx/gl/camera.h
+++ b/gfx/gl/camera.h
@@ -15,7 +15,7 @@ public:
return viewProjection;
}
- [[nodiscard]] Ray unProject(const ScreenRelCoord &) const;
+ [[nodiscard]] Ray<GlobalPosition3D> unProject(const ScreenRelCoord &) const;
void
setPosition(const GlobalPosition3D & p)
diff --git a/lib/geometricPlane.h b/lib/geometricPlane.h
index fd3a1d7..3f95d3c 100644
--- a/lib/geometricPlane.h
+++ b/lib/geometricPlane.h
@@ -32,7 +32,7 @@ public:
}
[[nodiscard]] inline std::optional<DistAndPosition>
- getRayIntersectPosition(const Ray & ray) const
+ getRayIntersectPosition(const Ray<PositionType> & ray) const
{
float dist {};
if (!glm::intersectRayPlane(ray.start, ray.direction, origin, normal, dist)) {
diff --git a/lib/ray.cpp b/lib/ray.cpp
deleted file mode 100644
index 254ad14..0000000
--- a/lib/ray.cpp
+++ /dev/null
@@ -1,36 +0,0 @@
-#include "ray.h"
-#include "maths.h"
-#include <algorithm>
-
-Ray
-Ray::fromPoints(Position3D start, Position3D p)
-{
- return {start, glm::normalize(p - start)};
-}
-
-float
-Ray::distanceToLine(const Position3D & p1, const Position3D & e1) const
-{
- // https://en.wikipedia.org/wiki/Skew_lines
- const auto diff = p1 - e1;
- const auto d1 = glm::normalize(diff);
- const auto &p2 = start, &d2 = direction;
- const auto n = crossProduct(d1, d2);
- const auto n2 = crossProduct(d2, n);
- const auto c1 = p1 + (glm::dot((p2 - p1), n2) / glm::dot(d1, n2)) * d1;
- const auto difflength = glm::length(diff);
- if (glm::length(c1 - p1) > difflength || glm::length(c1 - e1) > difflength) {
- return std::numeric_limits<float>::infinity();
- }
- return glm::abs(glm::dot(n, p1 - p2));
-}
-
-bool
-Ray::passesCloseToEdges(const std::span<const Position3D> positions, float distance) const
-{
- return std::adjacent_find(positions.begin(), positions.end(),
- [this, distance](const Position3D & a, const Position3D & b) {
- return distanceToLine(a, b) <= distance;
- })
- != positions.end();
-}
diff --git a/lib/ray.h b/lib/ray.h
index bc70c74..e1f43c3 100644
--- a/lib/ray.h
+++ b/lib/ray.h
@@ -1,20 +1,84 @@
#pragma once
#include "config/types.h"
+#include "maths.h"
+
+#include <algorithm>
#include <glm/glm.hpp>
+#include <glm/gtx/intersect.hpp>
#include <span>
-class Ray {
+template<typename PositionType> class Ray {
public:
#ifndef __cpp_aggregate_paren_init
- Ray(Position3D start, Direction3D direction) : start {start}, direction {direction} { }
+ Ray(PositionType start, Direction3D direction) : start {start}, direction {direction} { }
#endif
- static Ray fromPoints(Position3D, Position3D);
-
- Position3D start;
+ PositionType start;
Direction3D direction;
- [[nodiscard]] float distanceToLine(const Position3D & a, const Position3D & b) const;
- [[nodiscard]] bool passesCloseToEdges(const std::span<const Position3D> positions, float distance) const;
+ [[nodiscard]] PositionType::value_type
+ distanceToLine(const PositionType & p1, const PositionType & e1) const
+ {
+ // https://en.wikipedia.org/wiki/Skew_lines
+ const RelativePosition3D diff = p1 - e1;
+ const auto d1 = glm::normalize(diff);
+ const auto n = crossProduct(d1, direction);
+ const auto n2 = crossProduct(direction, n);
+ const auto c1 = p1 + PositionType((glm::dot(RelativePosition3D(start - p1), n2) / glm::dot(d1, n2)) * d1);
+ const auto difflength = glm::length(diff);
+ if (glm::length(RelativePosition3D(c1 - p1)) > difflength
+ || glm::length(RelativePosition3D(c1 - e1)) > difflength) {
+ return std::numeric_limits<typename PositionType::value_type>::infinity();
+ }
+ return static_cast<PositionType::value_type>(glm::abs(glm::dot(n, RelativePosition3D(p1 - start))));
+ }
+
+ [[nodiscard]] bool
+ passesCloseToEdges(const std::span<const PositionType> positions, const PositionType::value_type distance) const
+ {
+ return std::adjacent_find(positions.begin(), positions.end(), [this, distance](const auto & a, const auto & b) {
+ return distanceToLine(a, b) <= distance;
+ }) != positions.end();
+ }
+
+ bool
+ intersectTriangle(const PositionType t0, const PositionType t1, const PositionType t2, BaryPosition & bary,
+ RelativeDistance & distance) const
+ {
+ if constexpr (std::is_floating_point_v<typename PositionType::value_type>) {
+ return glm::intersectRayTriangle(start, direction, t0, t1, t2, bary, distance);
+ }
+ else {
+ const RelativePosition3D t0r = t0 - start, t1r = t1 - start, t2r = t2 - start;
+ return glm::intersectRayTriangle({}, direction, t0r, t1r, t2r, bary, distance);
+ }
+ }
+
+ bool
+ intersectSphere(const PositionType centre, const PositionType::value_type size, PositionType & position,
+ Normal3D & normal) const
+ {
+ if constexpr (std::is_floating_point_v<typename PositionType::value_type>) {
+ return glm::intersectRaySphere(start, direction, centre, size, position, normal);
+ }
+ else {
+ const RelativePosition3D cr = centre - start;
+ RelativePosition3D positionF {};
+ const auto r = glm::intersectRaySphere(
+ {}, direction, cr, static_cast<RelativeDistance>(size), positionF, normal);
+ position = GlobalPosition3D(positionF) + start;
+ return r;
+ }
+ }
+};
+
+class RayFactory {
+public:
+ template<typename PositionType>
+ static Ray<PositionType>
+ fromPoints(PositionType start, PositionType p)
+ {
+ return {start, glm::normalize(p - start)};
+ }
};
diff --git a/test/test-geoData.cpp b/test/test-geoData.cpp
index d1c6b8b..efe845c 100644
--- a/test/test-geoData.cpp
+++ b/test/test-geoData.cpp
@@ -109,8 +109,8 @@ using FindRayIntersectData = std::tuple<GlobalPosition3D, Direction3D, GlobalPos
BOOST_DATA_TEST_CASE(findRayIntersect,
boost::unit_test::data::make<FindRayIntersectData>({
- {{310000000, 490000000, 50000}, {1, 1, -2}, {310008585, 490008585, 32834}},
- {{310000000, 490000000, 50000}, {1, 1, -1}, {310017136, 490017136, 32868}},
+ {{310000000, 490000000, 50000}, {1, 1, -2}, {310008582, 490008582, 32834}},
+ {{310000000, 490000000, 50000}, {1, 1, -1}, {310017131, 490017131, 32868}},
}),
p, d, i)
{
diff --git a/test/test-maths.cpp b/test/test-maths.cpp
index b363c17..8680409 100644
--- a/test/test-maths.cpp
+++ b/test/test-maths.cpp
@@ -265,7 +265,7 @@ BOOST_AUTO_TEST_CASE(camera_clicks)
Camera camera {{}, ::half_pi, 1.25F, 1000, 10000000};
constexpr float centre {0.5F}, right {0.9F}, left {0.1F}, top {1.F}, bottom {0.F};
camera.setForward(::north);
- BOOST_CHECK_EQUAL(camera.unProject({centre, centre}).start, RelativePosition3D {});
+ BOOST_CHECK_EQUAL(camera.unProject({centre, centre}).start, GlobalPosition3D {});
BOOST_CHECK_CLOSE_VEC(camera.unProject({centre, centre}).direction, ::north);
BOOST_CHECK_CLOSE_VEC(camera.unProject({left, centre}).direction, glm::normalize(::north + ::west));
BOOST_CHECK_CLOSE_VEC(camera.unProject({right, centre}).direction, glm::normalize(::north + ::east));
diff --git a/ui/builders/freeExtend.cpp b/ui/builders/freeExtend.cpp
index 1520421..47356c3 100644
--- a/ui/builders/freeExtend.cpp
+++ b/ui/builders/freeExtend.cpp
@@ -11,7 +11,8 @@ BuilderFreeExtend::hint() const
}
void
-BuilderFreeExtend::move(Network * network, const GeoData * geoData, const SDL_MouseMotionEvent &, const Ray & ray)
+BuilderFreeExtend::move(
+ Network * network, const GeoData * geoData, const SDL_MouseMotionEvent &, const Ray<GlobalPosition3D> & ray)
{
if (p1) {
if (const auto p = network->intersectRayNodes(ray)) {
@@ -30,7 +31,8 @@ BuilderFreeExtend::move(Network * network, const GeoData * geoData, const SDL_Mo
}
void
-BuilderFreeExtend::click(Network * network, const GeoData * geoData, const SDL_MouseButtonEvent & e, const Ray & ray)
+BuilderFreeExtend::click(
+ Network * network, const GeoData * geoData, const SDL_MouseButtonEvent & e, const Ray<GlobalPosition3D> & ray)
{
switch (e.button) {
case SDL_BUTTON_LEFT:
diff --git a/ui/builders/freeExtend.h b/ui/builders/freeExtend.h
index b276426..127fdc6 100644
--- a/ui/builders/freeExtend.h
+++ b/ui/builders/freeExtend.h
@@ -6,8 +6,10 @@ class GeoData;
class BuilderFreeExtend : public EditNetwork::Builder {
std::string hint() const override;
- void click(Network * network, const GeoData * geoData, const SDL_MouseButtonEvent & e, const Ray & ray) override;
- void move(Network * network, const GeoData * geoData, const SDL_MouseMotionEvent & e, const Ray & ray) override;
+ void click(Network * network, const GeoData * geoData, const SDL_MouseButtonEvent & e,
+ const Ray<GlobalPosition3D> & ray) override;
+ void move(Network * network, const GeoData * geoData, const SDL_MouseMotionEvent & e,
+ const Ray<GlobalPosition3D> & ray) override;
std::optional<Position3D> p1;
};
diff --git a/ui/builders/join.cpp b/ui/builders/join.cpp
index caa635f..7474c5b 100644
--- a/ui/builders/join.cpp
+++ b/ui/builders/join.cpp
@@ -11,7 +11,7 @@ BuilderJoin::hint() const
}
void
-BuilderJoin::move(Network * network, const GeoData *, const SDL_MouseMotionEvent &, const Ray & ray)
+BuilderJoin::move(Network * network, const GeoData *, const SDL_MouseMotionEvent &, const Ray<GlobalPosition3D> & ray)
{
if (p1) {
if (const auto p = network->intersectRayNodes(ray)) {
@@ -24,7 +24,8 @@ BuilderJoin::move(Network * network, const GeoData *, const SDL_MouseMotionEvent
}
void
-BuilderJoin::click(Network * network, const GeoData *, const SDL_MouseButtonEvent & e, const Ray & ray)
+BuilderJoin::click(
+ Network * network, const GeoData *, const SDL_MouseButtonEvent & e, const Ray<GlobalPosition3D> & ray)
{
switch (e.button) {
case SDL_BUTTON_LEFT:
diff --git a/ui/builders/join.h b/ui/builders/join.h
index bb0bd4c..dd57895 100644
--- a/ui/builders/join.h
+++ b/ui/builders/join.h
@@ -6,8 +6,10 @@ class GeoData;
class BuilderJoin : public EditNetwork::Builder {
std::string hint() const override;
- void click(Network * network, const GeoData * geoData, const SDL_MouseButtonEvent & e, const Ray & ray) override;
- void move(Network * network, const GeoData * geoData, const SDL_MouseMotionEvent & e, const Ray & ray) override;
+ void click(Network * network, const GeoData * geoData, const SDL_MouseButtonEvent & e,
+ const Ray<GlobalPosition3D> & ray) override;
+ void move(Network * network, const GeoData * geoData, const SDL_MouseMotionEvent & e,
+ const Ray<GlobalPosition3D> & ray) override;
void create(Network * network, const Node::Ptr & p1, const Node::Ptr & p2) const;
diff --git a/ui/builders/straight.cpp b/ui/builders/straight.cpp
index 9b262bb..866705a 100644
--- a/ui/builders/straight.cpp
+++ b/ui/builders/straight.cpp
@@ -11,7 +11,8 @@ BuilderStraight::hint() const
}
void
-BuilderStraight::move(Network * network, const GeoData * geoData, const SDL_MouseMotionEvent &, const Ray & ray)
+BuilderStraight::move(
+ Network * network, const GeoData * geoData, const SDL_MouseMotionEvent &, const Ray<GlobalPosition3D> & ray)
{
if (p1) {
if (const auto p = geoData->intersectRay(ray)) {
@@ -24,7 +25,8 @@ BuilderStraight::move(Network * network, const GeoData * geoData, const SDL_Mous
}
void
-BuilderStraight::click(Network * network, const GeoData * geoData, const SDL_MouseButtonEvent & e, const Ray & ray)
+BuilderStraight::click(
+ Network * network, const GeoData * geoData, const SDL_MouseButtonEvent & e, const Ray<GlobalPosition3D> & ray)
{
switch (e.button) {
case SDL_BUTTON_LEFT:
diff --git a/ui/builders/straight.h b/ui/builders/straight.h
index cf99a1d..63f9a40 100644
--- a/ui/builders/straight.h
+++ b/ui/builders/straight.h
@@ -6,8 +6,10 @@ class GeoData;
class BuilderStraight : public EditNetwork::Builder {
std::string hint() const override;
- void click(Network * network, const GeoData * geoData, const SDL_MouseButtonEvent & e, const Ray & ray) override;
- void move(Network * network, const GeoData * geoData, const SDL_MouseMotionEvent & e, const Ray & ray) override;
+ void click(Network * network, const GeoData * geoData, const SDL_MouseButtonEvent & e,
+ const Ray<GlobalPosition3D> & ray) override;
+ void move(Network * network, const GeoData * geoData, const SDL_MouseMotionEvent & e,
+ const Ray<GlobalPosition3D> & ray) override;
void create(Network * network, Position3D p1, Position3D p2) const;
diff --git a/ui/editNetwork.cpp b/ui/editNetwork.cpp
index 754053b..7fbde32 100644
--- a/ui/editNetwork.cpp
+++ b/ui/editNetwork.cpp
@@ -22,7 +22,7 @@ EditNetwork::EditNetwork(Network * n) :
}
bool
-EditNetwork::click(const SDL_MouseButtonEvent & e, const Ray & ray)
+EditNetwork::click(const SDL_MouseButtonEvent & e, const Ray<GlobalPosition3D> & ray)
{
if (builder && (e.button == SDL_BUTTON_LEFT || e.button == SDL_BUTTON_MIDDLE)) {
builder->click(network, gameState->geoData.get(), e, ray);
@@ -32,7 +32,7 @@ EditNetwork::click(const SDL_MouseButtonEvent & e, const Ray & ray)
}
bool
-EditNetwork::move(const SDL_MouseMotionEvent & e, const Ray & ray)
+EditNetwork::move(const SDL_MouseMotionEvent & e, const Ray<GlobalPosition3D> & ray)
{
if (builder) {
builder->move(network, gameState->geoData.get(), e, ray);
diff --git a/ui/editNetwork.h b/ui/editNetwork.h
index e1aaa61..c8a2f13 100644
--- a/ui/editNetwork.h
+++ b/ui/editNetwork.h
@@ -9,14 +9,14 @@
#include <gfx/models/texture.h>
#include <optional>
-class Ray;
+template<typename> class Ray;
class EditNetwork : public GameMainSelector::Component, public WorldOverlay {
public:
explicit EditNetwork(Network *);
- bool click(const SDL_MouseButtonEvent & e, const Ray &) override;
- bool move(const SDL_MouseMotionEvent & e, const Ray &) override;
+ bool click(const SDL_MouseButtonEvent & e, const Ray<GlobalPosition3D> &) override;
+ bool move(const SDL_MouseMotionEvent & e, const Ray<GlobalPosition3D> &) override;
bool handleInput(const SDL_Event & e, const UIComponent::Position &) override;
void render(const SceneShader &) const override;
void render(const UIShader & shader, const UIComponent::Position & pos) const override;
@@ -28,8 +28,8 @@ public:
virtual ~Builder() = default;
virtual void render(const SceneShader & shader) const;
virtual std::string hint() const = 0;
- virtual void click(Network *, const GeoData *, const SDL_MouseButtonEvent &, const Ray &) = 0;
- virtual void move(Network *, const GeoData *, const SDL_MouseMotionEvent &, const Ray &) = 0;
+ virtual void click(Network *, const GeoData *, const SDL_MouseButtonEvent &, const Ray<GlobalPosition3D> &) = 0;
+ virtual void move(Network *, const GeoData *, const SDL_MouseMotionEvent &, const Ray<GlobalPosition3D> &) = 0;
using Ptr = std::unique_ptr<Builder>;
diff --git a/ui/gameMainSelector.cpp b/ui/gameMainSelector.cpp
index 703cfab..a577838 100644
--- a/ui/gameMainSelector.cpp
+++ b/ui/gameMainSelector.cpp
@@ -71,7 +71,7 @@ GameMainSelector::handleInput(const SDL_Event & e, const Position & parentPos)
}
void
-GameMainSelector::defaultClick(const Ray & ray)
+GameMainSelector::defaultClick(const Ray<GlobalPosition3D> & ray)
{
BaryPosition baryPos {};
RelativeDistance distance {};
@@ -90,13 +90,13 @@ GameMainSelector::defaultClick(const Ray & ray)
}
bool
-GameMainSelector::Component::click(const SDL_MouseButtonEvent &, const Ray &)
+GameMainSelector::Component::click(const SDL_MouseButtonEvent &, const Ray<GlobalPosition3D> &)
{
return false;
}
bool
-GameMainSelector::Component::move(const SDL_MouseMotionEvent &, const Ray &)
+GameMainSelector::Component::move(const SDL_MouseMotionEvent &, const Ray<GlobalPosition3D> &)
{
return false;
}
diff --git a/ui/gameMainSelector.h b/ui/gameMainSelector.h
index 88db34b..cc30707 100644
--- a/ui/gameMainSelector.h
+++ b/ui/gameMainSelector.h
@@ -10,7 +10,7 @@
#include <string>
class SceneShader;
-class Ray;
+template<typename> class Ray;
class UIShader;
class Camera;
@@ -20,8 +20,8 @@ public:
public:
virtual ~Component() = default;
- virtual bool click(const SDL_MouseButtonEvent &, const Ray &);
- virtual bool move(const SDL_MouseMotionEvent &, const Ray &);
+ virtual bool click(const SDL_MouseButtonEvent &, const Ray<GlobalPosition3D> &);
+ virtual bool move(const SDL_MouseMotionEvent &, const Ray<GlobalPosition3D> &);
virtual bool handleInput(const SDL_Event &, const Position & pos);
virtual void render(const UIShader & shader, const Position & pos) const;
virtual void render(const SceneShader &) const;
@@ -34,7 +34,7 @@ public:
bool handleInput(const SDL_Event & e, const Position &) override;
- void defaultClick(const Ray & ray);
+ void defaultClick(const Ray<GlobalPosition3D> & ray);
std::unique_ptr<Component> target;