diff options
author | Dan Goodliffe <dan@randomdan.homeip.net> | 2022-08-29 21:51:11 +0100 |
---|---|---|
committer | Dan Goodliffe <dan@randomdan.homeip.net> | 2022-08-29 21:51:11 +0100 |
commit | 945a951aec17a7fbc6d69e4492a3a4a75f480ae8 (patch) | |
tree | 6856421c78662de1603e9a33166f1e5b71e7d06a /game/network/link.cpp | |
parent | Ray function to test if it passes close to a sequence of edges defined by nod... (diff) | |
download | ilt-945a951aec17a7fbc6d69e4492a3a4a75f480ae8.tar.bz2 ilt-945a951aec17a7fbc6d69e4492a3a4a75f480ae8.tar.xz ilt-945a951aec17a7fbc6d69e4492a3a4a75f480ae8.zip |
Link functions for testing if a ray clicks them
Diffstat (limited to 'game/network/link.cpp')
-rw-r--r-- | game/network/link.cpp | 28 |
1 files changed, 28 insertions, 0 deletions
diff --git a/game/network/link.cpp b/game/network/link.cpp index f3a79a6..19b60ab 100644 --- a/game/network/link.cpp +++ b/game/network/link.cpp @@ -1,7 +1,9 @@ #include "link.h" #include <compare> +#include <glm/gtx/transform.hpp> #include <location.hpp> #include <maths.h> +#include <ray.hpp> #include <tuple> Link::Link(End a, End b, float l) : ends {{std::move(a), std::move(b)}}, length {l} { } @@ -30,6 +32,12 @@ LinkStraight::positionAt(float dist, unsigned char start) const return Location {es.first->pos + vehiclePositionOffset() + dir * dist, {vector_pitch(dir), vector_yaw(dir), 0}}; } +bool +LinkStraight::intersectRay(const Ray & ray) const +{ + return ray.passesCloseToEdges(std::array {ends.front().node->pos, ends.back().node->pos}, 1.F); +} + Location LinkCurve::positionAt(float dist, unsigned char start) const { @@ -44,3 +52,23 @@ LinkCurve::positionAt(float dist, unsigned char start) const const auto pitch {vector_pitch({0, 0, (es.second->pos.z - es.first->pos.z) / length})}; return Location {relPos + relClimb + centreBase, {pitch, normalize(ang + dirOffset[start]), 0}}; } + +bool +LinkCurve::intersectRay(const Ray & ray) const +{ + const auto & e0p {ends[0].node->pos}; + const auto & e1p {ends[1].node->pos}; + const auto slength = round_frac(length / 2.F, 5.F); + const auto segs = std::round(15.F * slength / std::pow(radius, 0.7F)); + const auto step {glm::vec3 {arc_length(arc), e1p.z - e0p.z, slength} / segs}; + const auto trans {glm::translate(centreBase)}; + + auto segCount = static_cast<std::size_t>(std::lround(segs)) + 1; + std::vector<glm::vec3> points; + points.reserve(segCount); + for (glm::vec3 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(glm::vec3 {radius, 0.F, swing.y})}; + points.push_back(t * glm::vec4 {0, 0, 0, 1}); + } + return ray.passesCloseToEdges(points, 1.F); +} |