Simbody
3.7
|
This class provides a description of a mesh made of polygonal faces (not limited to triangles). More...
Public Member Functions | |
PolygonalMesh () | |
Create an empty PolygonalMesh, with no vertices or faces. More... | |
void | clear () |
Restore this PolygonalMesh to its default-constructed state, meaning that it will contain no vertices or faces after this call. More... | |
int | getNumFaces () const |
Get the number of faces in the mesh. More... | |
int | getNumVertices () const |
Get the number of vertices in the mesh. More... | |
const Vec3 & | getVertexPosition (int vertex) const |
Get the position of a vertex in the mesh. More... | |
int | getNumVerticesForFace (int face) const |
Get the number of vertices that make up a particular face. More... | |
int | getFaceVertex (int face, int vertex) const |
Get the index of one of the vertices of a face. More... | |
int | addVertex (const Vec3 &position) |
Add a vertex to the mesh. More... | |
int | addFace (const Array_< int > &vertices) |
Add a face to the mesh. More... | |
PolygonalMesh & | scaleMesh (Real scale) |
Scale a mesh by multiplying every vertex by a fixed value. More... | |
PolygonalMesh & | transformMesh (const Transform &X_AM) |
Transform a mesh by applying the given Transform to every vertex, leaving the mesh permanently changed. More... | |
void | loadFile (const String &pathname) |
Attempt to interpret the given file as a mesh file, with the format determined from the file name extension. More... | |
void | loadObjFile (const String &pathname) |
Load a Wavefront OBJ (.obj) file, adding the vertices and faces it contains to this mesh, and ignoring anything else in the file. More... | |
void | loadObjFile (std::istream &file) |
Alternate signature for Wavefront OBJ format that takes an already-open istream rather than a pathname. More... | |
void | loadVtpFile (const String &pathname) |
Load a VTK PolyData (.vtp) file, adding the vertices and faces it contains to this mesh and ignoring anything else in the file. More... | |
void | loadStlFile (const String &pathname) |
Load an STL file, adding the vertices and faces it contains to this mesh and ignoring anything else in the file. More... | |
Public Member Functions inherited from SimTK::PIMPLHandle< PolygonalMesh, PolygonalMeshImpl, true > | |
bool | isEmptyHandle () const |
Returns true if this handle is empty, that is, does not refer to any implementation object. More... | |
bool | isOwnerHandle () const |
Returns true if this handle is the owner of the implementation object to which it refers. More... | |
bool | isSameHandle (const PolygonalMesh &other) const |
Determine whether the supplied handle is the same object as "this" PIMPLHandle. More... | |
void | disown (PolygonalMesh &newOwner) |
Give up ownership of the implementation to an empty handle. More... | |
PIMPLHandle & | referenceAssign (const PolygonalMesh &source) |
"Copy" assignment but with shallow (pointer) semantics. More... | |
PIMPLHandle & | copyAssign (const PolygonalMesh &source) |
This is real copy assignment, with ordinary C++ object ("value") semantics. More... | |
void | clearHandle () |
Make this an empty handle, deleting the implementation object if this handle is the owner of it. More... | |
const PolygonalMeshImpl & | getImpl () const |
Get a const reference to the implementation associated with this Handle. More... | |
PolygonalMeshImpl & | updImpl () |
Get a writable reference to the implementation associated with this Handle. More... | |
int | getImplHandleCount () const |
Return the number of handles the implementation believes are referencing it. More... | |
Static Public Member Functions | |
static PolygonalMesh | createSphereMesh (Real radius, int resolution=1) |
Create a sphere-shaped mesh, with roughly uniform mesh elements. More... | |
static PolygonalMesh | createBrickMesh (const Vec3 &halfDims, int resolution=1) |
Create a brick-shaped mesh. More... | |
static PolygonalMesh | createCylinderMesh (const UnitVec3 &axis, Real radius, Real halfLength, int resolution=1) |
Create a cylinder-shaped mesh, with the long axis in a given direction. More... | |
Additional Inherited Members | |
Public Types inherited from SimTK::PIMPLHandle< PolygonalMesh, PolygonalMeshImpl, true > | |
typedef PIMPLHandle< PolygonalMesh, PolygonalMeshImpl, PTR > | HandleBase |
typedef HandleBase | ParentHandle |
Protected Member Functions inherited from SimTK::PIMPLHandle< PolygonalMesh, PolygonalMeshImpl, true > | |
PIMPLHandle () | |
The default constructor makes this an empty handle. More... | |
PIMPLHandle (PolygonalMeshImpl *p) | |
This provides consruction of a handle referencing an existing implementation object. More... | |
PIMPLHandle (const PIMPLHandle &source) | |
The copy constructor makes either a deep (value) or shallow (reference) copy of the supplied source PIMPL object, based on whether this is a "pointer
semantics" (PTR=true) or "object (value) semantics" (PTR=false, default) class. More... | |
~PIMPLHandle () | |
Note that the destructor is non-virtual. More... | |
PIMPLHandle & | operator= (const PIMPLHandle &source) |
Copy assignment makes the current handle either a deep (value) or shallow (reference) copy of the supplied source PIMPL object, based on whether this is a "pointer sematics" (PTR=true) or "object (value) semantics" (PTR=false, default) class. More... | |
void | setImpl (PolygonalMeshImpl *p) |
Set the implementation for this empty handle. More... | |
bool | hasSameImplementation (const PolygonalMesh &other) const |
Determine whether the supplied handle is a reference to the same implementation object as is referenced by "this" PIMPLHandle. More... | |
This class provides a description of a mesh made of polygonal faces (not limited to triangles).
Its primary purpose is for loading geometry from files, which can then be used for visualization or collision detection. For example, the following lines load a mesh from a Wavefront OBJ file, then create a DecorativeMesh from it.
You can also read a polygon mesh from a VTK PolyData (.vtp) file, or an STL file (.stl) that is in ascii or binary format. You can also build meshes programmatically, and some static methods are provided here for generating some common shapes. If you don't know what kind of file you have, you can attempt to read it with the loadFile() method which will examine the file extension to determine the expected format.
The mesh has its own local frame and vertex locations are given in that frame. You can scale and transform the vertices relative to that frame (changing the values stored in the mesh) but more commonly the mesh will be placed on a body relative to that body's frame, meaning you can re-use the same mesh in various places.
We expect this to be a large object so give it shared (reference) semantics; that is, the copy constructor and copy assignment default to shallow copies (both handles will refer to the same data). If you want to make a deep (non-shared) copy of a PolygonalMesh, use the copyAssign() method provided by the PIMPLHandle base class.
|
inline |
Create an empty PolygonalMesh, with no vertices or faces.
|
static |
Create a sphere-shaped mesh, with roughly uniform mesh elements.
[in] | radius | The radius of the underlying sphere. Vertices of the mesh will be on the sphere, with mesh elements somewhat inside. |
[in] | resolution | Control for how dense a mesh to produce. Resolution 0 will produce an octahedron (8 triangular faces). Resolution 1 (the default) gives 32 faces, resolution 2 gives 128. In general for resolution n there will be 2*4^(n+1) faces. |
|
static |
Create a brick-shaped mesh.
A brick is a rectangular solid (a box) centered at and aligned with the mesh local frame. Note that its size is given with half dimensions. By default you will just get two mesh faces along the longest edge of the brick, with all other edges roughly the same size. You can control the mesh density with the resolution parameter.
[in] | halfDims | The half-dimensions of the brick. The extreme vertices are at -halfDims and +halfDims, so the brick is centered around the mesh local frame. |
[in] | resolution | Control for how dense a mesh to produce. For this shape, resolution is interpreted as the number of extra vertices to insert in the longest edge of the brick. Extra vertices are inserted into the shorter edges if needed to keep the edge lengths approximately uniform for every mesh face. resolution=0 gives only vertices at the corners; the default is 1 meaning that the longest edge is split once. |
If you want a brick mesh where all the edges in the mesh are roughly the same length, say wantEdgeLength
, set resolution like this:
If you want a brick mesh where all the edges are roughly the same length as the shortest edge of the brick, just set wantEdgeLength=min(halfDims)
in the above calculation.
|
static |
Create a cylinder-shaped mesh, with the long axis in a given direction.
By default you'll get a 12 sided polygon as the base and elements of roughly similar dimension along the edges. You can control the mesh density with the resolution parameter.
[in] | axis | The central axis direction of the cylinder, in the mesh local frame. This can be provided using the constants XAxis, YAxis, or ZAxis, or you can provide a unit vector in any direction. |
[in] | radius | The cylinder radius. |
[in] | halfLength | Half the length of the cylinder along its axis. The bases are at -halfLength and +halfLength along the axis, so the cylinder is centered around the mesh local frame origin. |
[in] | resolution | Control for how dense a mesh to produce (see below for details). |
At resolution 0 the base is a hexagon with six triangular faces, and the tube is meshed with quad faces that are about as long as the diameter of the base. Resolution 1 (the default) makes the base a 12-sided polygon and introduces an intermediate 12-sided polygon of have the diameter. There will be triangles in the center still, but quad faces between the polygons. The length of the tube faces will be reduced to match. Higher resolutions refine the mesh similarly.
void SimTK::PolygonalMesh::clear | ( | ) |
Restore this PolygonalMesh to its default-constructed state, meaning that it will contain no vertices or faces after this call.
int SimTK::PolygonalMesh::getNumFaces | ( | ) | const |
Get the number of faces in the mesh.
int SimTK::PolygonalMesh::getNumVertices | ( | ) | const |
Get the number of vertices in the mesh.
const Vec3& SimTK::PolygonalMesh::getVertexPosition | ( | int | vertex | ) | const |
Get the position of a vertex in the mesh.
[in] | vertex | The index of the vertex (as returned by addVertex()). |
int SimTK::PolygonalMesh::getNumVerticesForFace | ( | int | face | ) | const |
Get the number of vertices that make up a particular face.
[in] | face | The index of the face (as returned by addFace()). |
int SimTK::PolygonalMesh::getFaceVertex | ( | int | face, |
int | vertex | ||
) | const |
Get the index of one of the vertices of a face.
[in] | face | The index of the face (as returned by addFace()). |
[in] | vertex | The index of the vertex within the face (from 0, 1, or 2 for a triangular face, etc.) These are ordered the same way as when the face was defined. |
int SimTK::PolygonalMesh::addVertex | ( | const Vec3 & | position | ) |
Add a vertex to the mesh.
[in] | position | The position of the vertex to add, measured and expressed in the mesh local frame. |
int SimTK::PolygonalMesh::addFace | ( | const Array_< int > & | vertices | ) |
Add a face to the mesh.
Note that the ordering of the vertices defines the outward normal for the face; they must be counterclockwise around the desired normal.
[in] | vertices | Indices of the vertices which make up the new face, in counterclockwise order with respect to the face normal. |
PolygonalMesh& SimTK::PolygonalMesh::scaleMesh | ( | Real | scale | ) |
Scale a mesh by multiplying every vertex by a fixed value.
Note that this permanently modifies the vertex locations within the mesh. Since the vertices are measured in the mesh local frame, scaling will appear to occur around the mesh origin (that is, the origin will remain where it was while everything else changes.
[in] | scale | The scale factor. Can be any value except zero. |
PolygonalMesh& SimTK::PolygonalMesh::transformMesh | ( | const Transform & | X_AM | ) |
Transform a mesh by applying the given Transform to every vertex, leaving the mesh permanently changed.
This has the effect of replacing the mesh local frame M with a new frame A.
[in] | X_AM | The transform giving the pose of the mesh local frame in the new frame A. Every vertex v_M becomes v_A=X_AM*v_M. |
void SimTK::PolygonalMesh::loadFile | ( | const String & | pathname | ) |
Attempt to interpret the given file as a mesh file, with the format determined from the file name extension.
If we recognize the extension we'll call one of the specialized methods below; see the descriptions for more information. Ignoring case, we recognize:
.obj
: Wavefront OBJ file.stl
: 3D Systems Stereolithography file (ascii or binary).stla
: ascii-only stl extension.vtp
: VTK PolyData file (we can only read the ascii version)[in] | pathname | The name of a mesh file with a recognized extension. |
void SimTK::PolygonalMesh::loadObjFile | ( | const String & | pathname | ) |
Load a Wavefront OBJ (.obj) file, adding the vertices and faces it contains to this mesh, and ignoring anything else in the file.
The suffix for these files is typically ".obj" but we don't check here.
[in] | pathname | The name of a .obj file. |
void SimTK::PolygonalMesh::loadObjFile | ( | std::istream & | file | ) |
Alternate signature for Wavefront OBJ format that takes an already-open istream rather than a pathname.
This is useful for testing since it can be supplied by a stringstream rather than a file.
[in,out] | file | An input stream from which to load the file contents. |
void SimTK::PolygonalMesh::loadVtpFile | ( | const String & | pathname | ) |
Load a VTK PolyData (.vtp) file, adding the vertices and faces it contains to this mesh and ignoring anything else in the file.
The suffix for these files is typically ".vtp" but we don't check here.
[in] | pathname | The name of a .vtp file. |
void SimTK::PolygonalMesh::loadStlFile | ( | const String & | pathname | ) |
Load an STL file, adding the vertices and faces it contains to this mesh and ignoring anything else in the file.
The file may be in ascii or binary format. If the suffix is ".stla" then it can only be ascii. Otherwise, including ".stl" or anything else, we'll examine the contents to determine which format is used. STL files include many repeated vertices; we will collapse any that coincide to within a small tolerance so that there is some hope of getting a connected surface.
[in] | pathname | The name of a .stl or .stla file. |