// Copyright (c) 2023 Dominic Masters // // This software is released under the MIT License. // https://opensource.org/licenses/MIT #include "Ray3D.hpp" #include "assert/assert.hpp" using namespace Dawn; bool_t Dawn::raytestQuad( const struct Ray3D ray, const glm::vec2 min, const glm::vec2 max, const glm::mat4 transform, glm::vec3 &point, glm::vec3 &normal, float_t &distance ) { // transform ray into local space of the quad glm::mat4 inverseTransform = glm::inverse(transform); glm::vec3 localRayOrigin = glm::vec3( inverseTransform * glm::vec4(ray.origin, 1.0f) ); glm::vec3 localRayDirection = glm::vec3( inverseTransform * glm::vec4(ray.direction, 0.0f) ); // perform ray-quad intersection test float_t t = -localRayOrigin.z / localRayDirection.z; // intersection distance along ray if(t < 0) return false; // intersection is behind the ray origin glm::vec2 intersectionPoint = ( glm::vec2(localRayOrigin) + t * glm::vec2(localRayDirection) ); if( glm::any(glm::lessThan(intersectionPoint, min)) || glm::any(glm::greaterThan(intersectionPoint, max)) ) { return false; // intersection is outside the quad } distance = t; // compute point and normal of intersection in world space glm::vec3 localIntersectionPoint = glm::vec3(intersectionPoint, 0.0f); point = glm::vec3(transform * glm::vec4(localIntersectionPoint, 1.0f)); normal = glm::normalize( glm::vec3(transform * glm::vec4(0.0f, 0.0f, 1.0f, 0.0f)) ); return true; // intersection found }