#pragma once #include #include #include #include #include #include namespace J3ML::Geometry { using J3ML::LinearAlgebra::Matrix3x3; using J3ML::LinearAlgebra::Matrix4x4; // A mathematical representation of a 3-dimensional sphere class Sphere : public Shape { public: Vector3 Position; float Radius; public: Sphere() {} Sphere(const Vector3& pos, float radius) : Position(pos), Radius(radius) {} /// Quickly returns an arbitrary point inside this Sphere. Used in GJK intersection test. Vector3 AnyPointFast() const { return Position; } /// Computes the extreme point of this Sphere in the given direction. /** An extreme point is a farthest point of this Sphere in the given direction. For a Sphere, this point is unique. @param direction The direction vector of the direction to find the extreme point. This vector may be unnormalized, but may not be null. @return The extreme point of this Sphere in the given direction. */ Vector3 ExtremePoint(const Vector3 &direction) const; Vector3 ExtremePoint(const Vector3 &direction, float &projectionDistance) const; void Translate(const Vector3& offset) { Position = Position + offset; } void Transform(const Matrix3x3& transform) { Position = transform * Position; } void Transform(const Matrix4x4& transform) { Position = transform * Position; } inline float Cube(float inp) const { return inp*inp*inp; } float Volume() const { return 4.f * M_PI * Cube(Radius) / 3.f; } float SurfaceArea() const { return 4.f * M_PI * Cube(Radius) / 3.f; } bool IsFinite() const { return Position.IsFinite() && std::isfinite(Radius); } bool IsDegenerate() { return !(Radius > 0.f) || !Position.IsFinite(); } bool Contains(const Vector3& point) const { return Position.DistanceSquared(point) <= Radius*Radius; } bool Contains(const Vector3& point, float epsilon) const { return Position.DistanceSquared(point) <= Radius*Radius + epsilon; } bool Contains(const LineSegment& lineseg) const; TriangleMesh GenerateUVSphere() const {} TriangleMesh GenerateIcososphere() const {} void ProjectToAxis(const Vector3 &direction, float &outMin, float &outMax) const; }; }