diff --git a/src/Physics/Sphere.cpp b/src/Physics/Sphere.cpp index 8e01bd1f4..ffbdf6aff 100644 --- a/src/Physics/Sphere.cpp +++ b/src/Physics/Sphere.cpp @@ -23,4 +23,16 @@ void Sphere::applyTransformation(const Matrix4& transformation) { _transformedRadius = scaling*_radius; } +bool Sphere::collides(const AbstractShape* other) const { + if(other->type() == Type::Point) + return *this % *static_cast(other); + + return AbstractShape::collides(other); +} + +bool Sphere::operator%(const Point& other) const { + return (other.transformedPosition()-transformedPosition()).lengthSquared() < + Math::pow<2>(transformedRadius()); +} + }} diff --git a/src/Physics/Sphere.h b/src/Physics/Sphere.h index 87eef0e91..c898ba27e 100644 --- a/src/Physics/Sphere.h +++ b/src/Physics/Sphere.h @@ -20,6 +20,7 @@ */ #include "AbstractShape.h" +#include "Point.h" namespace Magnum { namespace Physics { @@ -36,6 +37,8 @@ class PHYSICS_EXPORT Sphere: public AbstractShape { void applyTransformation(const Matrix4& transformation); + bool collides(const AbstractShape* other) const; + /** @brief Position */ inline Vector3 position() const { return _position; } @@ -58,6 +61,9 @@ class PHYSICS_EXPORT Sphere: public AbstractShape { return _transformedRadius; } + /** @brief Collision with point */ + bool operator%(const Point& other) const; + protected: inline Type type() const { return Type::Sphere; } @@ -66,6 +72,10 @@ class PHYSICS_EXPORT Sphere: public AbstractShape { float _radius, _transformedRadius; }; +#ifndef DOXYGEN_GENERATING_OUTPUT +inline bool operator%(const Point& a, const Sphere& b) { return b % a; } +#endif + }} #endif diff --git a/src/Physics/Test/SphereTest.cpp b/src/Physics/Test/SphereTest.cpp index 6846616af..bb43c6f71 100644 --- a/src/Physics/Test/SphereTest.cpp +++ b/src/Physics/Test/SphereTest.cpp @@ -41,4 +41,17 @@ void SphereTest::applyTransformation() { QCOMPARE(sphere.transformedRadius(), Math::Constants::Sqrt3*7.0f); } +void SphereTest::collisionPoint() { + Physics::Sphere sphere({1.0f, 2.0f, 3.0f}, 2.0f); + Physics::Point point({1.0f, 3.0f, 3.0f}); + Physics::Point point2({1.0f, 3.0f, 1.0f}); + + randomTransformation(sphere); + randomTransformation(point); + randomTransformation(point2); + + VERIFY_COLLIDES(sphere, point); + VERIFY_NOT_COLLIDES(sphere, point2); +} + }}} diff --git a/src/Physics/Test/SphereTest.h b/src/Physics/Test/SphereTest.h index 370873e07..fe61390da 100644 --- a/src/Physics/Test/SphereTest.h +++ b/src/Physics/Test/SphereTest.h @@ -15,15 +15,16 @@ GNU Lesser General Public License version 3 for more details. */ -#include +#include "AbstractShapeTest.h" namespace Magnum { namespace Physics { namespace Test { -class SphereTest: public QObject { +class SphereTest: public AbstractShapeTest { Q_OBJECT private slots: void applyTransformation(); + void collisionPoint(); }; }}}