181 lines
4.5 KiB
C
181 lines
4.5 KiB
C
|
/**
|
||
|
@file ConvexPolyhedron.h
|
||
|
|
||
|
@maintainer Morgan McGuire, http://graphics.cs.williams.edu
|
||
|
|
||
|
@created 2001-11-11
|
||
|
@edited 2006-04-10
|
||
|
|
||
|
Copyright 2000-2006, Morgan McGuire.
|
||
|
All rights reserved.
|
||
|
*/
|
||
|
|
||
|
#ifndef G3D_CONVEXPOLYHEDRON_H
|
||
|
#define G3D_CONVEXPOLYHEDRON_H
|
||
|
|
||
|
#include "G3D/platform.h"
|
||
|
#include "G3D/Vector3.h"
|
||
|
#include "G3D/Vector2.h"
|
||
|
#include "G3D/CoordinateFrame.h"
|
||
|
#include "G3D/Plane.h"
|
||
|
#include "G3D/Line.h"
|
||
|
#include "G3D/Array.h"
|
||
|
|
||
|
namespace G3D {
|
||
|
|
||
|
class DirectedEdge {
|
||
|
public:
|
||
|
Vector3 start;
|
||
|
Vector3 stop;
|
||
|
};
|
||
|
|
||
|
class ConvexPolygon {
|
||
|
private:
|
||
|
|
||
|
friend class ConvexPolyhedron;
|
||
|
|
||
|
Array<Vector3> _vertex;
|
||
|
|
||
|
public:
|
||
|
|
||
|
ConvexPolygon() {}
|
||
|
ConvexPolygon(const Vector3& v0, const Vector3& v1, const Vector3& v2);
|
||
|
ConvexPolygon(const Array<Vector3>& __vertex);
|
||
|
virtual ~ConvexPolygon() {}
|
||
|
|
||
|
/**
|
||
|
Counter clockwise winding order.
|
||
|
*/
|
||
|
inline const Vector3& vertex(int i) const {
|
||
|
return _vertex[i];
|
||
|
}
|
||
|
|
||
|
inline void setVertex(int i, const Vector3& v) {
|
||
|
_vertex[i] = v;
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
Zero vertices indicates an empty polygon (zero area).
|
||
|
*/
|
||
|
inline int numVertices() const {
|
||
|
return _vertex.size();
|
||
|
}
|
||
|
|
||
|
inline void setNumVertices(int n) {
|
||
|
_vertex.resize(n);
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
O(n) in the number of edges
|
||
|
*/
|
||
|
bool isEmpty() const;
|
||
|
|
||
|
/**
|
||
|
Cuts the polygon at the plane. If the polygon is entirely above or below
|
||
|
the plane, one of the returned polygons will be empty.
|
||
|
|
||
|
@param above The part of the polygon above (on the side the
|
||
|
normal points to or in the plane) the plane
|
||
|
@param below The part of the polygon below the plane.
|
||
|
@param newEdge If a new edge was introduced, this is that edge (on the above portion; the below portion is the opposite winding.
|
||
|
*/
|
||
|
void cut(const Plane& plane, ConvexPolygon &above, ConvexPolygon &below, DirectedEdge& newEdge);
|
||
|
void cut(const Plane& plane, ConvexPolygon &above, ConvexPolygon &below);
|
||
|
|
||
|
/**
|
||
|
When a cut plane grazes a vertex in the polygon, two near-identical vertices may be created.
|
||
|
The closeness of these two points can cause a number of problems, such as ConvexPolygon::normal()
|
||
|
returning an infinite vector. It should be noted, however, that not all applications are
|
||
|
sensitive to near-identical vertices.
|
||
|
|
||
|
removeDuplicateVertices() detects and eliminates redundant vertices.
|
||
|
*/
|
||
|
void removeDuplicateVertices();
|
||
|
|
||
|
/**
|
||
|
O(n) in the number of edges
|
||
|
*/
|
||
|
float getArea() const;
|
||
|
|
||
|
inline Vector3 normal() const {
|
||
|
debugAssert(_vertex.length() >= 3);
|
||
|
return (_vertex[1] - _vertex[0]).cross(_vertex[2] - _vertex[0]).direction();
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
Returns the same polygon with inverse winding.
|
||
|
*/
|
||
|
ConvexPolygon inverse() const;
|
||
|
};
|
||
|
|
||
|
|
||
|
|
||
|
class ConvexPolyhedron {
|
||
|
public:
|
||
|
/**
|
||
|
Zero faces indicates an empty polyhedron
|
||
|
*/
|
||
|
Array<ConvexPolygon> face;
|
||
|
|
||
|
ConvexPolyhedron() {}
|
||
|
ConvexPolyhedron(const Array<ConvexPolygon>& _face);
|
||
|
|
||
|
/**
|
||
|
O(n) in the number of edges
|
||
|
*/
|
||
|
bool isEmpty() const;
|
||
|
|
||
|
/**
|
||
|
O(n) in the number of edges
|
||
|
*/
|
||
|
float getVolume() const;
|
||
|
|
||
|
/**
|
||
|
Cuts the polyhedron at the plane. If the polyhedron is entirely above or below
|
||
|
the plane, one of the returned polyhedra will be empty.
|
||
|
|
||
|
@param above The part of the polyhedron above (on the side the
|
||
|
normal points to or in the plane) the plane
|
||
|
@param below The part of the polyhedron below the plane.
|
||
|
*/
|
||
|
void cut(const Plane& plane, ConvexPolyhedron &above, ConvexPolyhedron &below);
|
||
|
};
|
||
|
|
||
|
/**
|
||
|
|
||
|
*/
|
||
|
class ConvexPolygon2D {
|
||
|
private:
|
||
|
|
||
|
Array<Vector2> m_vertex;
|
||
|
|
||
|
public:
|
||
|
|
||
|
ConvexPolygon2D() {}
|
||
|
|
||
|
/**
|
||
|
Points are counter-clockwise in a Y = down, X = right coordinate
|
||
|
system.
|
||
|
|
||
|
@param reverse If true, the points are reversed (i.e. winding direction is changed)
|
||
|
before the polygon is created.
|
||
|
*/
|
||
|
ConvexPolygon2D(const Array<Vector2>& pts, bool reverse = false);
|
||
|
|
||
|
inline int numVertices() const {
|
||
|
return m_vertex.size();
|
||
|
}
|
||
|
|
||
|
inline const Vector2& vertex(int index) const {
|
||
|
debugAssert((index >= 0) && (index <= m_vertex.size()));
|
||
|
return m_vertex[index];
|
||
|
}
|
||
|
|
||
|
/** @param reverseWinding If true, the winding direction of the polygon is reversed for this test.*/
|
||
|
bool contains(const Vector2& p, bool reverseWinding = false) const;
|
||
|
};
|
||
|
|
||
|
|
||
|
} // namespace
|
||
|
#endif
|