TriangleMeshWall Class Reference

#include <TriangleMeshWall.h>

+ Inheritance diagram for TriangleMeshWall:

Classes

struct  Triangle
 
struct  Vertex
 

Public Member Functions

 TriangleMeshWall ()=default
 Default constructor. More...
 
 TriangleMeshWall (const TriangleMeshWall &other)
 Copy constructor. More...
 
 TriangleMeshWall (const std::vector< Vec3D > &points, const std::vector< std::array< unsigned, 3 >> &cells, const ParticleSpecies *species=nullptr)
 Constructor creating triangles. More...
 
 TriangleMeshWall (const Vec3D &P0, const Vec3D &P1, const Vec3D &P, Mdouble resolutionU, Mdouble resolutionV, const ParticleSpecies *species=nullptr, bool periodicInU=false, bool periodicInV=false)
 Constructor creating parallelogram shaped mesh with a given resolution in u- and v-direction. More...
 
 ~TriangleMeshWall () override=default
 Destructor. More...
 
TriangleMeshWalloperator= (const TriangleMeshWall &other)
 Copy assignment operator. More...
 
TriangleMeshWallcopy () const override
 Wall copy method. More...
 
void read (std::istream &is) override
 Reads a TriangleMeshWall from an input stream, for example a restart file. More...
 
void write (std::ostream &os) const override
 Writes a TriangleMeshWall to an output stream, for example a restart file. More...
 
std::string getName () const override
 Returns the name of the object. More...
 
void set (const std::vector< Vec3D > &points, const std::vector< std::array< unsigned, 3 >> &cells)
 Set function creating triangles. More...
 
bool getDistanceAndNormal (const BaseParticle &p, Mdouble &distance, Vec3D &normal_return) const override
 Checks if a collision is happening with any of the TriangleWalls. NOTE: this does not handle actual interactions, but can only be used to know IF one (of possible many) interaction occurs. More...
 
BaseInteractiongetInteractionWith (BaseParticle *p, unsigned timeStamp, InteractionHandler *interactionHandler) override
 Gets the interaction between a given BaseParticle and all TriangleWalls in this mesh at a given time. In case of multiple contacts, chooses the one with greatest overlap. More...
 
void resetForceTorque (int numberOfOMPthreads) override
 
void writeVTK (VTKContainer &vtk) const override
 
void setSpecies (const ParticleSpecies *species)
 
void moveVertex (unsigned index, const Vec3D &dP)
 Updates a vertex by a given change in position. More...
 
void removeTriangle (unsigned index, bool removeFreeVertex=true)
 Removes a single triangle from the mesh. More...
 
void refineTriangle (unsigned index, unsigned numberOfTimes=1)
 Makes a really basic refinement by adding a vertex in the middle of the triangle to create 3 new ones. Note: Multiple refinements will definitely NOT create a nice mesh. More...
 
void setPeriodicCompanions (const std::vector< std::pair< unsigned, unsigned >> &periodicCompanions)
 Sets the vector with pairs of indices of vertices which lie on a periodic boundary and are each others 'companion'. E.g. when moving one vertex, the other is also moved the same amount. A vertex can have multiple companions (when lying on multiple periodic boundaries) and those should be in the vector as multiple pairs. More...
 
void moveVerticesToMatchVolume (std::vector< Vec3D > displacements, Mdouble targetVolume, int maxNumRecursiveCalls=15)
 Moves all vertices by given displacements and corrects to match the change in volume with the target volume. The final displacements will be proportional to the initial ones, but their actual values will have change. More...
 
Mdouble getVolumeTetrahedron (const Vec3D &a, const Vec3D &b, const Vec3D &c, const Vec3D &d)
 Calculates the volume of a tetrahedron formed by 4 vertices. More...
 
void addToMesh (TriangleMeshWall mesh)
 Adds a mesh to this mesh. When vertices share a position, only the one in the current mesh is kept and both meshes are then "connected" at that point. More...
 
void createParallelogramMesh (const Vec3D &P0, const Vec3D &P1, const Vec3D &P2, Mdouble resolutionU, Mdouble resolutionV, bool periodicInU=false, bool periodicInV=false)
 Creates a parallelogram shaped mesh with a given resolution in u- and v-direction. More...
 
void createFourPointMesh (const Vec3D &P0, const Vec3D &P1, const Vec3D &P2, const Vec3D &P3, int numSegmentsU, int numSegmentsV)
 Creates mesh consisting of four points, with linearly interpolated segments. The points therefore don't necessarily have to lie in plane. More...
 
bool isLocal (Vec3D &min, Vec3D &max) const override
 
void setPosition (const Vec3D &position) override
 Sets the position of this BaseInteractable. More...
 
void setOrientation (const Quaternion &orientation) override
 Sets the orientation of this BaseInteractable. More...
 
void move (const Vec3D &move) override
 Moves this BaseInteractable by adding an amount to the position. More...
 
void rotate (const Vec3D &angularVelocity) override
 Rotates this BaseInteractable. More...
 
- Public Member Functions inherited from BaseWall
 BaseWall ()
 Default constructor. More...
 
 BaseWall (const BaseWall &w)
 Copy constructor. More...
 
 ~BaseWall () override
 Default destructor. More...
 
virtual bool getDistanceNormalOverlap (const BaseParticle &P, Mdouble &distance, Vec3D &normal_return, Mdouble &overlap) const
 
virtual bool getDistanceNormalOverlapSuperquadric (const SuperQuadricParticle &p, Mdouble &distance, Vec3D &normal_return, Mdouble &overlap) const
 
virtual Vec3D getFurthestPointSuperQuadric (const Vec3D &normalBodyFixed, const Vec3D &axes, Mdouble eps1, Mdouble eps2) const
 
virtual void setHandler (WallHandler *handler)
 A function which sets the WallHandler for this BaseWall. More...
 
WallHandlergetHandler () const
 A function which returns the WallHandler that handles this BaseWall. More...
 
void setIndSpecies (unsigned int indSpecies) override
 Define the species of this wall using the index of the species in the SpeciesHandler in this DPMBase. More...
 
void setSpecies (const ParticleSpecies *species)
 Defines the species of the current wall. More...
 
bool isFixed () const override
 
void setForceControl (Vec3D forceGoal, Vec3D gainFactor, Vec3D baseVelocity={0, 0, 0})
 Slowly adjusts the force on a wall towards a specified goal, by adjusting (prescribing) the velocity of the wall. More...
 
bool getLinePlaneIntersect (Vec3D &intersect, const Vec3D &p0, const Vec3D &p1, const Vec3D &n, const Vec3D &p)
 
bool isInsideWallVTK (const Vec3D &point, const Vec3D &normal, const Vec3D &position) const
 
void projectOntoWallVTK (Vec3D &point0, const Vec3D &point1, const Vec3D &normal, const Vec3D &position) const
 
void intersectVTK (std::vector< Vec3D > &points, Vec3D normal, Vec3D position) const
 
virtual BaseInteractiongetInteractionWithSuperQuad (SuperQuadricParticle *p, unsigned timeStamp, InteractionHandler *interactionHandler)
 
void getVTK (std::vector< Vec3D > &points, std::vector< std::vector< double >> &triangleStrips)
 
const Vec3D getAxis () const
 
virtual void actionsOnRestart ()
 No implementation but can be overidden in its derived classes. More...
 
virtual void actionsAfterParticleGhostUpdate ()
 No implementation but can be overidden in its derived classes. More...
 
virtual void handleParticleAddition (unsigned int id, BaseParticle *p)
 Handles the addition of particles to the particleHandler. More...
 
virtual void handleParticleRemoval (unsigned int id)
 Handles the addition of particles to the particleHandler. More...
 
virtual void checkInteractions (InteractionHandler *interactionHandler, unsigned int timeStamp)
 Check if all interactions are valid. More...
 
bool getVTKVisibility () const
 
void setVTKVisibility (bool vtkVisibility)
 
void addRenderedWall (BaseWall *w)
 
BaseWallgetRenderedWall (size_t i) const
 
std::vector< BaseWall * > getRenderedWalls () const
 
void removeRenderedWalls ()
 
void renderWall (VTKContainer &vtk)
 
void addParticlesAtWall (unsigned numElements=50)
 
void setVelocityControl (Vec3D forceGoal, Vec3D gainFactor, Vec3D baseVelocity)
 
virtual void writeWallDetailsVTK (VTKData &data) const
 
virtual void computeWear ()
 
- Public Member Functions inherited from BaseInteractable
 BaseInteractable ()
 Default BaseInteractable constructor. More...
 
 BaseInteractable (const BaseInteractable &p)
 Copy constructor. More...
 
 ~BaseInteractable () override
 Destructor, it simply destructs the BaseInteractable and all the objects it contains. More...
 
unsigned int getIndSpecies () const
 Returns the index of the species associated with the interactable object. More...
 
const ParticleSpeciesgetSpecies () const
 Returns a pointer to the species of this BaseInteractable. More...
 
void setSpecies (const ParticleSpecies *species)
 Sets the species of this BaseInteractable. More...
 
const Vec3DgetForce () const
 Returns the force on this BaseInteractable. More...
 
const Vec3DgetTorque () const
 Returns the torque on this BaseInteractable. More...
 
void setForce (const Vec3D &force)
 Sets the force on this BaseInteractable. More...
 
void setTorque (const Vec3D &torque)
 Sets the torque on this BaseInteractable. More...
 
void addForce (const Vec3D &addForce)
 Adds an amount to the force on this BaseInteractable. More...
 
void addTorque (const Vec3D &addTorque)
 Adds an amount to the torque on this BaseInteractable. More...
 
void sumForceTorqueOMP ()
 
const Vec3DgetPosition () const
 Returns the position of this BaseInteractable. More...
 
const QuaterniongetOrientation () const
 Returns the orientation of this BaseInteractable. More...
 
void setOrientationViaNormal (Vec3D normal)
 Sets the orientation of this BaseInteractable by defining the vector that results from the rotation of the (1,0,0) vector. More...
 
void setOrientationViaEuler (Vec3D eulerAngle)
 Sets the orientation of this BaseInteractable by defining the euler angles. More...
 
const std::vector< BaseInteraction * > & getInteractions () const
 Returns a list of interactions which belong to this interactable. More...
 
void addInteraction (BaseInteraction *I)
 Adds an interaction to this BaseInteractable. More...
 
bool removeInteraction (BaseInteraction *I)
 Removes an interaction from this BaseInteractable. More...
 
void copyInteractionsForPeriodicParticles (const BaseInteractable &p)
 Copies interactions to this BaseInteractable whenever a periodic copy made. More...
 
void setVelocity (const Vec3D &velocity)
 set the velocity of the BaseInteractable. More...
 
void setAngularVelocity (const Vec3D &angularVelocity)
 set the angular velocity of the BaseInteractble. More...
 
void addVelocity (const Vec3D &velocity)
 adds an increment to the velocity. More...
 
void addAngularVelocity (const Vec3D &angularVelocity)
 add an increment to the angular velocity. More...
 
virtual const Vec3DgetVelocity () const
 Returns the velocity of this interactable. More...
 
virtual const Vec3DgetAngularVelocity () const
 Returns the angular velocity of this interactable. More...
 
void setPrescribedPosition (const std::function< Vec3D(double)> &prescribedPosition)
 Allows the position of an infinite mass interactable to be prescribed. More...
 
void applyPrescribedPosition (double time)
 Computes the position from the user defined prescribed position function. More...
 
void setPrescribedVelocity (const std::function< Vec3D(double)> &prescribedVelocity)
 Allows the velocity of an infinite mass interactable to be prescribed. More...
 
void applyPrescribedVelocity (double time)
 Computes the velocity from the user defined prescribed velocity function. More...
 
void setPrescribedOrientation (const std::function< Quaternion(double)> &prescribedOrientation)
 Allows the orientation of the infinite mass interactbale to be prescribed. More...
 
void applyPrescribedOrientation (double time)
 Computes the orientation from the user defined prescribed orientation function. More...
 
void setPrescribedAngularVelocity (const std::function< Vec3D(double)> &prescribedAngularVelocity)
 Allows the angular velocity of the infinite mass interactable to be prescribed. More...
 
void applyPrescribedAngularVelocity (double time)
 Computes the angular velocity from the user defined prescribed angular velocity. More...
 
virtual const Vec3D getVelocityAtContact (const Vec3D &contact) const
 Returns the velocity at the contact point, use by many force laws. More...
 
void integrateBeforeForceComputation (double time, double timeStep)
 This is part of integrate routine for objects with infinite mass. More...
 
void integrateAfterForceComputation (double time, double timeStep)
 This is part of the integration routine for objects with infinite mass. More...
 
virtual Mdouble getInvMass () const
 
virtual Mdouble getCurvature (const Vec3D &labFixedCoordinates) const
 
virtual bool isFaceContact (const Vec3D &normal) const
 
- Public Member Functions inherited from BaseObject
 BaseObject ()=default
 Default constructor. More...
 
 BaseObject (const BaseObject &p)=default
 Copy constructor, copies all the objects BaseObject contains. More...
 
virtual ~BaseObject ()=default
 virtual destructor More...
 
virtual void moveInHandler (unsigned int index)
 Except that it is virtual, it does the same thing as setIndex() does. More...
 
void setIndex (unsigned int index)
 Allows one to assign an index to an object in the handler/container. More...
 
void setId (unsigned long id)
 Assigns a unique identifier to each object in the handler (container) which remains constant even after the object is deleted from the container/handler. More...
 
unsigned int getIndex () const
 Returns the index of the object in the handler. More...
 
unsigned int getId () const
 Returns the unique identifier of any particular object. More...
 
void setGroupId (unsigned groupId)
 
unsigned getGroupId () const
 

Protected Attributes

std::vector< Triangletriangles_
 
std::vector< Vertexvertices_
 

Private Member Functions

std::vector< unsigned > getPeriodicCompanions (unsigned index)
 Looks up the companions belonging to a vertex index, if it has any. More...
 
bool isWithinBoundingBox (const Vec3D &position, Mdouble radius) const
 Checks whether or not a part of the particle is within the bounding box. More...
 
void updateBoundingBox ()
 Sets the local and global bounding boxes. This method should be called any time a vertex is updated in lab frame. More...
 
void updateBoundingBoxGlobal ()
 Sets the global bounding box, using the bounding box in lab frame. This method should be called when there are changes in global frame, but not in lab frame. E.g. when calling setPosition(). More...
 
int getNumberOfSegmentsAndResolution (Mdouble length, Mdouble &resolution)
 Finds the number of segments and the resolution needed to perfectly fit a length. More...
 
void addZigZagDiagonalCells (std::vector< std::array< unsigned, 3 >> &cells, int numU, int numV, int i, int j)
 Helper function that adds two cells (triangles) to the provided cells vector. Used by createParallelogramMesh and createFourPointMesh. More...
 

Private Attributes

std::vector< std::pair< unsigned, unsigned > > periodicCompanions_
 
Vec3D boundingBoxMin_
 Bounding box corners in lab frame and global frame. Used to speed up contact detection. HGrid uses the global frame min max. More...
 
Vec3D boundingBoxMax_
 
Vec3D boundingBoxMinGlobal_
 
Vec3D boundingBoxMaxGlobal_
 

Additional Inherited Members

- Static Public Member Functions inherited from BaseWall
static void addToVTK (const std::vector< Vec3D > &points, VTKContainer &vtk)
 Takes the points provided and adds a triangle strip connecting these points to the vtk container. More...
 

Constructor & Destructor Documentation

◆ TriangleMeshWall() [1/4]

TriangleMeshWall::TriangleMeshWall ( )
default

Default constructor.

Referenced by copy().

◆ TriangleMeshWall() [2/4]

TriangleMeshWall::TriangleMeshWall ( const TriangleMeshWall other)

Copy constructor.

Parameters
otherThe TriangleMeshWall that must be copied.
30  : BaseWall(other)
31 {
32  triangles_ = other.triangles_;
33  vertices_ = other.vertices_;
35 
40 }
BaseWall()
Default constructor.
Definition: BaseWall.cc:36
Vec3D boundingBoxMax_
Definition: TriangleMeshWall.h:272
Vec3D boundingBoxMinGlobal_
Definition: TriangleMeshWall.h:273
Vec3D boundingBoxMaxGlobal_
Definition: TriangleMeshWall.h:273
std::vector< std::pair< unsigned, unsigned > > periodicCompanions_
Definition: TriangleMeshWall.h:262
Vec3D boundingBoxMin_
Bounding box corners in lab frame and global frame. Used to speed up contact detection....
Definition: TriangleMeshWall.h:272
std::vector< Triangle > triangles_
Definition: TriangleMeshWall.h:258
std::vector< Vertex > vertices_
Definition: TriangleMeshWall.h:259

References boundingBoxMax_, boundingBoxMaxGlobal_, boundingBoxMin_, boundingBoxMinGlobal_, periodicCompanions_, triangles_, and vertices_.

◆ TriangleMeshWall() [3/4]

TriangleMeshWall::TriangleMeshWall ( const std::vector< Vec3D > &  points,
const std::vector< std::array< unsigned, 3 >> &  cells,
const ParticleSpecies species = nullptr 
)

Constructor creating triangles.

Parameters
pointsVector of vertices
cellsVector of cells, each cell holds three indices to the points vector
species
44 {
45  // Set the species of the main wall first, as the set function will use it.
46  setSpecies(species);
47  set(points, cells);
48 }
void setSpecies(const ParticleSpecies *species)
Definition: TriangleMeshWall.cc:319
void set(const std::vector< Vec3D > &points, const std::vector< std::array< unsigned, 3 >> &cells)
Set function creating triangles.
Definition: TriangleMeshWall.cc:133

References set(), and setSpecies().

◆ TriangleMeshWall() [4/4]

TriangleMeshWall::TriangleMeshWall ( const Vec3D P0,
const Vec3D P1,
const Vec3D P,
Mdouble  resolutionU,
Mdouble  resolutionV,
const ParticleSpecies species = nullptr,
bool  periodicInU = false,
bool  periodicInV = false 
)

Constructor creating parallelogram shaped mesh with a given resolution in u- and v-direction.

Parameters
P0,P1,P2The three points, in clockwise order, forming the parallelogram (fourth point is implied).
resolutionUMaximum length of a segment in u-direction.
resolutionVMaximum length of a segment in v-direction.
species
periodicInUWhether or not the first and last column of vertices lie in a periodic boundary and should be set as periodic companions.
periodicInVWhether or not the first and last row of vertices lie in a periodic boundary and should be set as periodic companions.
53 {
54  // Set the species first, as it is used in other methods.
55  setSpecies(species);
56  createParallelogramMesh(P0, P1, P2, resolutionU, resolutionV, periodicInU, periodicInV);
57 }
void createParallelogramMesh(const Vec3D &P0, const Vec3D &P1, const Vec3D &P2, Mdouble resolutionU, Mdouble resolutionV, bool periodicInU=false, bool periodicInV=false)
Creates a parallelogram shaped mesh with a given resolution in u- and v-direction.
Definition: TriangleMeshWall.cc:731

References createParallelogramMesh(), and setSpecies().

◆ ~TriangleMeshWall()

TriangleMeshWall::~TriangleMeshWall ( )
overridedefault

Destructor.

Member Function Documentation

◆ addToMesh()

void TriangleMeshWall::addToMesh ( TriangleMeshWall  mesh)

Adds a mesh to this mesh. When vertices share a position, only the one in the current mesh is kept and both meshes are then "connected" at that point.

Parameters
meshMesh to be added.
667 {
668  // All triangles are simply added to the triangles_ vector. When adding vertices, any triangle index of the added
669  // mesh simply becomes: updated index = index + number of triangles originally in this mesh.
670  // Similar for the vertices, however vertices which share their position with a vertex already in the mesh are
671  // ignored. So when adding triangles, the vertex indices can sometimes reference to a vertex already in the mesh.
672  // The easiest way to implement is to temporarily store the updated vertex indices, and to later assign them.
673 
674  // Remember the number of vertices and triangles originally in this mesh.
675  const int numVertices = vertices_.size();
676  const int numTriangles = triangles_.size();
677  // For each of the added vertices, their updated vertex is temporarily stored in a vector.
678  // This is the cleanest/easiest way to later update the vertex indices of each added triangle.
679  std::vector<unsigned> updatedVertexIndices;
680  updatedVertexIndices.reserve(mesh.vertices_.size());
681 
682  // Loop through the vertices to be added.
683  for (Vertex& v : mesh.vertices_)
684  {
685  // The triangle indices can simply be updated.
686  for (auto& p : v.triangleIndices)
687  p.first += numTriangles;
688 
689  // Initialize updated vertex index as -1, to later check if it has been set or not.
690  int index = -1;
691  // Loop through original vertices and compare vertex positions.
692  for (int i = 0; i < numVertices; i++)
693  {
694  if (v.position.isEqualTo(vertices_[i].position, std::numeric_limits<Mdouble>::epsilon()))
695  {
696  // When vertices share position, update vertex index.
697  index = i;
698  break;
699  }
700  }
701 
702  // When the updated index is not set, the vertex is not in the mesh yet and should be added.
703  if (index == -1)
704  {
705  index = vertices_.size();
706  vertices_.push_back(v);
707  }
708  else
709  {
710  // The vertex is already in the mesh, add the triangle indices of the added mesh to it.
711  for (auto& p : v.triangleIndices)
712  vertices_[index].triangleIndices.push_back(p);
713  }
714 
715  // Store the updated index.
716  updatedVertexIndices.push_back(index);
717  }
718 
719  // Loop through the triangles to be added.
720  for (Triangle& t : mesh.triangles_)
721  {
722  // Update the vertex indices.
723  for (unsigned& idx : t.vertexIndices)
724  idx = updatedVertexIndices[idx];
725  triangles_.push_back(t);
726  }
727 
729 }
void updateBoundingBox()
Sets the local and global bounding boxes. This method should be called any time a vertex is updated i...
Definition: TriangleMeshWall.cc:869
const std::complex< Mdouble > i
Definition: ExtendedMath.h:51

References constants::i, Vec3D::isEqualTo(), TriangleMeshWall::Vertex::position, TriangleMeshWall::Vertex::triangleIndices, triangles_, updateBoundingBox(), TriangleMeshWall::Triangle::vertexIndices, and vertices_.

◆ addZigZagDiagonalCells()

void TriangleMeshWall::addZigZagDiagonalCells ( std::vector< std::array< unsigned, 3 >> &  cells,
int  numU,
int  numV,
int  i,
int  j 
)
private

Helper function that adds two cells (triangles) to the provided cells vector. Used by createParallelogramMesh and createFourPointMesh.

Parameters
cellsThe vector to which the cells are added.
numUThe number of segments in u-direction.
numVThe number of segments in v-direction.
iThe cell index in u-direction.
jThe cell index in v-direction.
792 {
793  // Not in last row/column
794  if (i < numU - 1 && j < numV - 1)
795  {
796  // Bottom left
797  const unsigned baseIdx = i + j * numU;
798 
799  // Check moduli to create zigzag diagonals (both being odd or even)
800  if ((i % 2 == 0) != (j % 2 == 0))
801  {
802  // Diagonal from bottom left to top right
803  // Bottom left, top left, top right (clockwise)
804  cells.push_back({baseIdx, baseIdx + numU, baseIdx + numU + 1});
805  // Bottom left, top right, bottom right (clockwise)
806  cells.push_back({baseIdx, baseIdx + numU + 1, baseIdx + 1});
807  }
808  else
809  {
810  // Diagonal from top left to bottom right
811  // Bottom left, top left, bottom right (clockwise)
812  cells.push_back({baseIdx, baseIdx + numU, baseIdx + 1});
813  // Top left, top right, bottom right (clockwise)
814  cells.push_back({baseIdx + numU, baseIdx + numU + 1, baseIdx + 1});
815  }
816  }
817 }

References constants::i.

Referenced by createFourPointMesh(), and createParallelogramMesh().

◆ copy()

TriangleMeshWall * TriangleMeshWall::copy ( ) const
overridevirtual

Wall copy method.

Returns
Pointer to the copy.

Implements BaseWall.

Reimplemented in WearableTriangleMeshWall.

69 {
70  return new TriangleMeshWall(*this);
71 }
TriangleMeshWall()=default
Default constructor.

References TriangleMeshWall().

Referenced by operator=().

◆ createFourPointMesh()

void TriangleMeshWall::createFourPointMesh ( const Vec3D P0,
const Vec3D P1,
const Vec3D P2,
const Vec3D P3,
int  numSegmentsU,
int  numSegmentsV 
)

Creates mesh consisting of four points, with linearly interpolated segments. The points therefore don't necessarily have to lie in plane.

Parameters
P0,P1,P2,P3The four points, in clock-wise order.
numSegmentsUNumber of segments in u-direction.
numSegmentsVNumber of segments in v-direction.
820 {
821  // To get to a point in the mesh, all we need to do is to walk along the bottom edge and then walk up along the
822  // linearly interpolated vector between the left and right edge. We step with a certain fraction of the length of
823  // the vectors, dependent on the number of segments in that direction.
824 
825  // Bottom direction vector (u-direction)
826  const Vec3D dirU = P3 - P0;
827  // Left and right direction vector (v-direction)
828  const Vec3D dirV0 = P1 - P0;
829  const Vec3D dirV1 = P2 - P3;
830  // Step size for linear interpolation between left and right direction vectors
831  Vec3D deltaDirV = (dirV1 - dirV0) / numSegmentsU;
832 
833  // Number of points is 1 more than number of segments
834  const int numU = numSegmentsU + 1;
835  const int numV = numSegmentsV + 1;
836 
837  std::vector<Vec3D> points;
838  std::vector<std::array<unsigned, 3>> cells;
839 
840  for (int j = 0; j < numV; j++)
841  {
842  for (int i = 0; i < numU; i++)
843  {
844  // Update direction vector in v-direction
845  Vec3D dirV = dirV0 + i * deltaDirV;
846  const Vec3D p = P0 + dirU * i / numSegmentsU + dirV * j / numSegmentsV;
847  points.push_back(p);
848  addZigZagDiagonalCells(cells, numU, numV, i, j);
849  }
850  }
851 
852  set(points, cells);
853 }
void addZigZagDiagonalCells(std::vector< std::array< unsigned, 3 >> &cells, int numU, int numV, int i, int j)
Helper function that adds two cells (triangles) to the provided cells vector. Used by createParallelo...
Definition: TriangleMeshWall.cc:791
Definition: Vector.h:51

References addZigZagDiagonalCells(), constants::i, and set().

◆ createParallelogramMesh()

void TriangleMeshWall::createParallelogramMesh ( const Vec3D P0,
const Vec3D P1,
const Vec3D P2,
Mdouble  resolutionU,
Mdouble  resolutionV,
bool  periodicInU = false,
bool  periodicInV = false 
)

Creates a parallelogram shaped mesh with a given resolution in u- and v-direction.

Parameters
P0,P1,P2The three points, in clockwise order, forming the parallelogram (fourth point is implied).
resolutionUMaximum length of a segment in u-direction.
resolutionVMaximum length of a segment in v-direction.
periodicInUWhether or not the first and last column of vertices lie in a periodic boundary and should be set as periodic companions.
periodicInVWhether or not the first and last row of vertices lie in a periodic boundary and should be set as periodic companions.
733 {
734  // Length of the sides of the parallelogram
735  const Mdouble lengthU = (P2 - P0).getLength();
736  const Mdouble lengthV = (P1 - P0).getLength();
737  // Direction vectors of the parallelogram sides
738  const Vec3D dirU = (P2 - P0) / lengthU;
739  const Vec3D dirV = (P1 - P0) / lengthV;
740 
741  // Number of points is 1 more than number of segments
742  const int numU = getNumberOfSegmentsAndResolution(lengthU, resolutionU) + 1;
743  const int numV = getNumberOfSegmentsAndResolution(lengthV, resolutionV) + 1;
744 
745  std::vector<Vec3D> points;
746  std::vector<std::array<unsigned, 3>> cells;
747 
748  for (int j = 0; j < numV; j++)
749  {
750  for (int i = 0; i < numU; i++)
751  {
752  const Vec3D p = P0 + dirU * i * resolutionU + dirV * j * resolutionV;
753  points.push_back(p);
754  addZigZagDiagonalCells(cells, numU, numV, i, j);
755  }
756  }
757 
758  set(points, cells);
759 
760  // Set possible periodic companions for first/last row/column.
761  std::vector<std::pair<unsigned, unsigned>> periodic;
762  if (periodicInU)
763  {
764  // First/last column
765  for (int j = 0; j < numV; j++)
766  periodic.emplace_back(j * numU, (j+1) * numU - 1);
767  }
768  if (periodicInV)
769  {
770  // First/last row
771  for (int i = 0; i < numU; i++)
772  periodic.emplace_back(i, i + (numV-1) * numU);
773  }
774  if (periodicInU && periodicInV)
775  {
776  // Periodic in diagonals u/v
777  periodic.emplace_back(0, numU * numV - 1);
778  periodic.emplace_back(numU - 1, numU * (numV-1));
779  }
780  setPeriodicCompanions(periodic);
781 }
double Mdouble
Definition: GeneralDefine.h:34
int getNumberOfSegmentsAndResolution(Mdouble length, Mdouble &resolution)
Finds the number of segments and the resolution needed to perfectly fit a length.
Definition: TriangleMeshWall.cc:783
void setPeriodicCompanions(const std::vector< std::pair< unsigned, unsigned >> &periodicCompanions)
Sets the vector with pairs of indices of vertices which lie on a periodic boundary and are each other...
Definition: TriangleMeshWall.cc:532

References addZigZagDiagonalCells(), getNumberOfSegmentsAndResolution(), constants::i, set(), and setPeriodicCompanions().

Referenced by TriangleMeshWall().

◆ getDistanceAndNormal()

bool TriangleMeshWall::getDistanceAndNormal ( const BaseParticle p,
Mdouble distance,
Vec3D normal_return 
) const
overridevirtual

Checks if a collision is happening with any of the TriangleWalls. NOTE: this does not handle actual interactions, but can only be used to know IF one (of possible many) interaction occurs.

Parameters
p
distance
normal_return
Returns
Whether or not there is a collision.

Implements BaseWall.

174 {
175  // Input BaseParticle is constant, so copy the necessary properties and change to local coordinates.
176  SphericalParticle pLocal;
177  pLocal.setSpecies(p.getSpecies());
178  pLocal.setRadius(p.getRadius());
179  pLocal.setPosition(getOrientation().rotateBack(p.getPosition() - getPosition()));
180 
181  if (!isWithinBoundingBox(pLocal.getPosition(), pLocal.getWallInteractionRadius(this)))
182  return false;
183 
184  for (const Triangle& t : triangles_)
185  {
186  if (t.wall.getDistanceAndNormal(pLocal, distance, normal_return))
187  return true;
188  }
189  return false;
190 }
const Quaternion & getOrientation() const
Returns the orientation of this BaseInteractable.
Definition: BaseInteractable.h:230
virtual void setPosition(const Vec3D &position)
Sets the position of this BaseInteractable.
Definition: BaseInteractable.h:239
const ParticleSpecies * getSpecies() const
Returns a pointer to the species of this BaseInteractable.
Definition: BaseInteractable.h:108
const Vec3D & getPosition() const
Returns the position of this BaseInteractable.
Definition: BaseInteractable.h:218
Mdouble getRadius() const
Returns the particle's radius.
Definition: BaseParticle.h:348
Mdouble getWallInteractionRadius(const BaseWall *wall) const
returns the radius plus the interactionDistance
Definition: BaseParticle.h:386
virtual void setRadius(Mdouble radius)
Sets the particle's radius_ (and adjusts the mass_ accordingly, based on the particle's species)
Definition: BaseParticle.cc:553
void setSpecies(const ParticleSpecies *species)
Definition: BaseParticle.cc:818
A spherical particle is the most simple particle used in MercuryDPM.
Definition: SphericalParticle.h:37
bool isWithinBoundingBox(const Vec3D &position, Mdouble radius) const
Checks whether or not a part of the particle is within the bounding box.
Definition: TriangleMeshWall.cc:862

References BaseInteractable::getOrientation(), BaseInteractable::getPosition(), BaseParticle::getRadius(), BaseInteractable::getSpecies(), BaseParticle::getWallInteractionRadius(), isWithinBoundingBox(), BaseInteractable::setPosition(), BaseParticle::setRadius(), BaseParticle::setSpecies(), and triangles_.

◆ getInteractionWith()

BaseInteraction * TriangleMeshWall::getInteractionWith ( BaseParticle p,
unsigned  timeStamp,
InteractionHandler interactionHandler 
)
overridevirtual

Gets the interaction between a given BaseParticle and all TriangleWalls in this mesh at a given time. In case of multiple contacts, chooses the one with greatest overlap.

Parameters
p
timeStamp
interactionHandler
Returns
Note
Particle positions are rotated to lab frame, however the particle orientation itself is not considered, so most likely doesn't work properly for non-spherical particles.
Todo:
TW: I think this torque has the wrong sign

Reimplemented from BaseWall.

194 {
195  // In case of multiple contacts, we store the one with the maximum overlap and only calculate the forces for that interaction.
196  // Since the BaseWall::getInteractionWith() automatically adds interactions to the handler, any interactions which
197  // are not the one with greatest overlap should be removed from the handler.
198  Mdouble maxOverlap = 0.0;
199  BaseWall* maxWall = nullptr;
200 
201  // Change particle to local coordinates.
202  //\todo How to handle orientation of non-spherical particles
203  const Vec3D posOriginal = p->getPosition();
204  p->setPosition(getOrientation().rotateBack(posOriginal - getPosition()));
205 
207  {
208  p->setPosition(posOriginal);
209  return nullptr;
210  }
211 
212  // Loop through all triangles and find interactions and store the one with max overlap
213  // (the main idea and the force calculations are literally copied from DPMBase::computeForcesDueToWalls)
214  for (auto& t : triangles_)
215  {
216  // Checks if the particle is interacting with this triangle
217  BaseInteraction* i = t.wall.getInteractionWith(p, timeStamp, interactionHandler);
218 
219  // When an interaction exists
220  if (i != nullptr)
221  {
222  // When the overlap is greater than that of any previous interactions
223  if (i->getOverlap() > maxOverlap)
224  {
225  // Remove the previous maximum overlap interaction from the handler
226  if (maxWall != nullptr)
227  {
228  BaseInteraction* prevMaxI = interactionHandler->getInteraction(p, maxWall, timeStamp);
229  interactionHandler->removeObject(prevMaxI->getIndex());
230  }
231 
232  // Update the maximum overlap and store the interacting wall
233  maxOverlap = i->getOverlap();
234  maxWall = &t.wall;
235  }
236  else
237  {
238  // Remove the last added interaction, as it is not the one with maximum overlap and should be discarded.
239  interactionHandler->removeObject(i->getIndex());
240  }
241  }
242  }
243 
244  // Change particle back to its original coordinates, before doing any force calculations.
245  p->setPosition(posOriginal);
246 
247  // When an interaction exists
248  if (maxWall != nullptr)
249  {
250  // The interaction with maximum overlap
251  BaseInteraction* i = interactionHandler->getInteraction(p, maxWall, timeStamp);
252  // The TriangleWall which with the interaction occurred
253  BaseInteractable* w = maxWall;
254 
255  // Rotate normal and change contact point to global coordinates
256  i->setNormal(getOrientation().rotate(i->getNormal()));
257  i->setContactPoint(getOrientation().rotate(i->getContactPoint()) + getPosition());
258 
259  // Transform TriangleWall position from local to global coordinates. (Needed for torque calculations etc.)
260  const Vec3D wPosOriginal = w->getPosition();
261  w->setPosition(getOrientation().rotateBack(w->getPosition()) + getPosition());
262  // Add the mesh velocities to the TriangleWall velocities. Needed in the force calculations (relative velocity etc.).
263  w->addVelocity(getVelocity());
265  // At the moment the TriangleWalls in the mesh always have position, velocity and angular velocities equal to zero.
266  // In case of future changes, however, they are treated as if they do have an actual value and therefore at the
267  // end are also reset to those original values.
268 
269  //...calculates the forces between the two objects...
270  i->computeForce();
271 
272  //...and applies them to each of the two objects (wall and particle).
273  p->addForce(i->getForce());
274  w->addForce(-i->getForce());
275 
276  //If the rotation flag is on, also applies the relevant torques (getRotation() returns a boolean).
277  if (getHandler()->getDPMBase()->getRotation())
278  {
279  p->addTorque(i->getTorque() - Vec3D::cross(p->getPosition() - i->getContactPoint(), i->getForce()));
281  w->addTorque(-i->getTorque() + Vec3D::cross(w->getPosition() - i->getContactPoint(), i->getForce()));
282  }
283 
284  // Set the TriangleWall position and velocities back to their original (local) values.
285  w->setPosition(wPosOriginal);
286  w->addVelocity(-getVelocity());
288  }
289 
290  // Return no interaction for the main wall itself.
291  return nullptr;
292 }
virtual void removeObject(unsigned const int index)
Removes an Object from the BaseHandler.
Definition: BaseHandler.h:472
Defines the basic properties that a interactable object can have.
Definition: BaseInteractable.h:55
virtual const Vec3D & getAngularVelocity() const
Returns the angular velocity of this interactable.
Definition: BaseInteractable.cc:341
void addTorque(const Vec3D &addTorque)
Adds an amount to the torque on this BaseInteractable.
Definition: BaseInteractable.cc:132
void addAngularVelocity(const Vec3D &angularVelocity)
add an increment to the angular velocity.
Definition: BaseInteractable.cc:370
void addVelocity(const Vec3D &velocity)
adds an increment to the velocity.
Definition: BaseInteractable.h:312
virtual const Vec3D & getVelocity() const
Returns the velocity of this interactable.
Definition: BaseInteractable.cc:329
void addForce(const Vec3D &addForce)
Adds an amount to the force on this BaseInteractable.
Definition: BaseInteractable.cc:116
Stores information about interactions between two interactable objects; often particles but could be ...
Definition: BaseInteraction.h:60
unsigned int getIndex() const
Returns the index of the object in the handler.
Definition: BaseObject.h:118
Basic class for walls.
Definition: BaseWall.h:49
WallHandler * getHandler() const
A function which returns the WallHandler that handles this BaseWall.
Definition: BaseWall.cc:134
BaseInteraction * getInteraction(BaseInteractable *P, BaseInteractable *I, unsigned timeStamp)
Returns the Interaction between the BaseInteractable's P and I.
Definition: InteractionHandler.cc:146
void rotate(const Vec3D &angularVelocity) override
Rotates this BaseInteractable.
Definition: TriangleMeshWall.cc:942
static Vec3D cross(const Vec3D &a, const Vec3D &b)
Calculates the cross product of two Vec3D: .
Definition: Vector.cc:163

References BaseInteractable::addAngularVelocity(), BaseInteractable::addForce(), BaseInteractable::addTorque(), BaseInteractable::addVelocity(), Vec3D::cross(), BaseInteractable::getAngularVelocity(), BaseWall::getHandler(), BaseObject::getIndex(), InteractionHandler::getInteraction(), BaseInteractable::getOrientation(), BaseInteractable::getPosition(), BaseInteractable::getVelocity(), BaseParticle::getWallInteractionRadius(), constants::i, isWithinBoundingBox(), BaseHandler< T >::removeObject(), rotate(), BaseInteractable::setPosition(), and triangles_.

◆ getName()

std::string TriangleMeshWall::getName ( ) const
overridevirtual

Returns the name of the object.

Returns
"TriangleMeshWall"

Implements BaseObject.

Reimplemented in WearableTriangleMeshWall.

129 {
130  return "TriangleMeshWall";
131 }

◆ getNumberOfSegmentsAndResolution()

int TriangleMeshWall::getNumberOfSegmentsAndResolution ( Mdouble  length,
Mdouble resolution 
)
private

Finds the number of segments and the resolution needed to perfectly fit a length.

Parameters
lengthTotal length
resolutionMaximum length of a segment, will be made smaller when needed.
Returns
Resulting number of segments.
784 {
785  // Round up to get a whole number of segments, then update the resolution (might remain unchanged).
786  double num = std::ceil(length / resolution);
787  resolution = length / num;
788  return static_cast<int>(num);
789 }

Referenced by createParallelogramMesh().

◆ getPeriodicCompanions()

std::vector< unsigned > TriangleMeshWall::getPeriodicCompanions ( unsigned  index)
private

Looks up the companions belonging to a vertex index, if it has any.

Parameters
indexIndex of the vertex to lookup the companions for.
Returns
Vector of vertex indices of the companions.
538 {
539  std::vector<unsigned> indices;
540 
541  // Loop through the companions, compare the index with both pair values and add the other to the return vector in case of a match.
542  for (auto& p : periodicCompanions_)
543  {
544  if (p.first == index)
545  indices.push_back(p.second);
546  else if (p.second == index)
547  indices.push_back(p.first);
548  }
549 
550  return indices;
551 }

References periodicCompanions_.

Referenced by moveVertex().

◆ getVolumeTetrahedron()

Mdouble TriangleMeshWall::getVolumeTetrahedron ( const Vec3D a,
const Vec3D b,
const Vec3D c,
const Vec3D d 
)

Calculates the volume of a tetrahedron formed by 4 vertices.

Returns
Volume of tetrahedron
662 {
663  return std::fabs(Vec3D::dot((a-d), Vec3D::cross((b-d), (c-d)))) / 6.0;
664 }
static Mdouble dot(const Vec3D &a, const Vec3D &b)
Calculates the dot product of two Vec3D: .
Definition: Vector.cc:76

References Vec3D::cross(), and Vec3D::dot().

Referenced by moveVerticesToMatchVolume().

◆ isLocal()

bool TriangleMeshWall::isLocal ( Vec3D min,
Vec3D max 
) const
overridevirtual

if isLocal returns true and the DPM class derived from MercuryBase, the hGrid will be used to find wall-particle contacts, using min/max.

Reimplemented from BaseWall.

856 {
857  min = boundingBoxMinGlobal_;
858  max = boundingBoxMaxGlobal_;
859  return true;
860 }

References boundingBoxMaxGlobal_, and boundingBoxMinGlobal_.

◆ isWithinBoundingBox()

bool TriangleMeshWall::isWithinBoundingBox ( const Vec3D position,
Mdouble  radius 
) const
private

Checks whether or not a part of the particle is within the bounding box.

Parameters
positionPosition of the particle
radiusInteraction radius of the particle
Returns
True when within the box
863 {
864  const Vec3D min = boundingBoxMin_ - Vec3D(radius, radius, radius);
865  const Vec3D max = boundingBoxMax_ + Vec3D(radius, radius, radius);
866  return position >= min && max >= position;
867 }

References boundingBoxMax_, and boundingBoxMin_.

Referenced by getDistanceAndNormal(), and getInteractionWith().

◆ move()

void TriangleMeshWall::move ( const Vec3D move)
overridevirtual

Moves this BaseInteractable by adding an amount to the position.

Moves (displaces) the interacable a given distance. Note, this just updates the position by the move.

Parameters
[in]moveReference to Vec3D which is the distance to move the interactable.

Reimplemented from BaseInteractable.

937 {
940 }
virtual void move(const Vec3D &move)
Moves this BaseInteractable by adding an amount to the position.
Definition: BaseInteractable.cc:215
void move(const Vec3D &move) override
Moves this BaseInteractable by adding an amount to the position.
Definition: TriangleMeshWall.cc:936
void updateBoundingBoxGlobal()
Sets the global bounding box, using the bounding box in lab frame. This method should be called when ...
Definition: TriangleMeshWall.cc:889

References BaseInteractable::move(), and updateBoundingBoxGlobal().

◆ moveVertex()

void TriangleMeshWall::moveVertex ( unsigned  index,
const Vec3D dP 
)

Updates a vertex by a given change in position.

Parameters
indexIndex of vertex to move.
dPChange in position.
329 {
330  // Update position of Vertex in vector.
331  vertices_[index].position += dP;
332 
333  // Update each Triangle wall of the triangles who share this Vertex.
334  for (auto& ti : vertices_[index].triangleIndices)
335  triangles_[ti.first].wall.moveVertex(ti.second, dP);
336 
337  // Do the same for each of the possible companions of this index.
338  for (unsigned idx : getPeriodicCompanions(index))
339  {
340  // Update position of Vertex in vector.
341  vertices_[idx].position += dP;
342 
343  // Update each Triangle wall of the triangles who share this Vertex.
344  for (auto& ti : vertices_[idx].triangleIndices)
345  triangles_[ti.first].wall.moveVertex(ti.second, dP);
346  }
347 
349 }
std::vector< unsigned > getPeriodicCompanions(unsigned index)
Looks up the companions belonging to a vertex index, if it has any.
Definition: TriangleMeshWall.cc:537

References getPeriodicCompanions(), triangles_, updateBoundingBox(), and vertices_.

◆ moveVerticesToMatchVolume()

void TriangleMeshWall::moveVerticesToMatchVolume ( std::vector< Vec3D displacements,
Mdouble  targetVolume,
int  maxNumRecursiveCalls = 15 
)

Moves all vertices by given displacements and corrects to match the change in volume with the target volume. The final displacements will be proportional to the initial ones, but their actual values will have change.

Warning
This calculates absolute volume and might cause unexpected results when volume is both 'added' and 'removed'.
Parameters
displacementsInitial change in position for each vertex.
targetVolumeVolume that the change in volume must match.
maxNumRecursiveCallsMaximum number of recursive calls allowed, in case certain tolerances are set too tight and infinite recursion occurs.
554 {
555  // Calculating the change in volume due to a moving triangle isn't analytically possible (not that I know of).
556  // This is because when two vertices are moved, they don't necessarily lie in a plane with the original positions.
557  // An approximation would be to split up the plane by picking one of the two diagonals, but which one to pick?
558  // Luckily we are in a mesh and therefore the choice doesn't matter, as the neighbour will correct for any errors.
559  // Only the edges of the mesh will then be an approximation, which is just something we have to live with.
560 
561  // The volume of the shape formed by the original and moved triangle can be calculated by splitting it up into 3
562  // tetrahedrons. Each of these tetrahedrons is automatically formed when moving and updating the vertices one by one.
563  // Therefore we simply loop through all the vertices in the mesh and for each of the triangles connected to it, we
564  // calculate the volume of the tetrahedron formed by the 3 original vertices and the current updated vertex. The
565  // latter is only actually updated after these volume calculations, so that they're not influenced by it. However
566  // when this vertex is referenced in the remainder of the loop, the updated version is used, since that then forms
567  // the second or third tetrahedron.
568 
569  // The total volume is kept track of and together with the target volume a ratio which is used to correct the vertex
570  // displacements. A recursive call is then made with the corrected displacements. The recursion is stopped when the
571  // ratio equals 1 and only then we actually know the displacements needed to get a change in volume matching the
572  // target volume, which is then used to actually update the real vertices, i.e. the privately stored ones.
573 
574  if (targetVolume == 0.0)
575  return;
576 
577  if (displacements.size() != vertices_.size())
578  {
579  logger(WARN, "Displacements vector must be equal in size as the number of vertices in the mesh.");
580  return;
581  }
582 
583  // In order to know if we are on the first run of this recursive method,
584  // we store a static boolean and reset it once the recursion ends.
585  static bool firstRecursiveCall = true;
586  if (firstRecursiveCall)
587  {
588  firstRecursiveCall = false;
589 
590  // The vertex periodic companions are handled by adding the displacements to each other (only done once, on first run).
591  // As one vertex can have multiple periodic companions, we first copy the displacements vector.
592  // To prevent unnecessarily copying, however, we first check if there are any periodic companions.
593  if (!periodicCompanions_.empty())
594  {
595  std::vector<Vec3D> disps = displacements;
596  for (auto& p : periodicCompanions_)
597  {
598  displacements[p.first] += disps[p.second];
599  displacements[p.second] += disps[p.first];
600  }
601  }
602  }
603 
604  // Every call a clean copy of the original real vertices is made, so that they can be updated without affecting anything.
605  std::vector<Vertex> vertices = vertices_;
606  Mdouble totalVolume = 0.0;
607 
608  // Loop through vertices to displace them and calculate the change in volume for each triangle connected to it.
609  for (int i = 0; i < vertices.size(); i++)
610  {
611  // Loop through each triangle connected to this vertex.
612  for (auto& p : vertices[i].triangleIndices)
613  {
614  Triangle& t = triangles_[p.first];
615  // Calculate the volume of the tetrahedron formed by each of the vertices of the triangle
616  // (one of which is the current vertex) and the updated position of the current vertex.
617  totalVolume += getVolumeTetrahedron(vertices[t.vertexIndices[0]].position,
618  vertices[t.vertexIndices[1]].position,
619  vertices[t.vertexIndices[2]].position,
620  vertices[i].position + displacements[i]);
621  }
622 
623  // Only now actually update the current vertex position.
624  vertices[i].position += displacements[i];
625  }
626 
627  // Ratio between the target volume and actual volume
628  Mdouble ratio = targetVolume / totalVolume;
629 
630  // Stop the recursive call when the ratio is equal to 1 (within certain tolerance).
631  // Or when the ratio does not have a finite value (totalVolume turned out to be 0).
632  Mdouble tol = 1.0e-6;
633  if (mathsFunc::isEqual(ratio, 1.0, tol) || !std::isfinite(ratio) || maxNumRecursiveCalls == 0)
634  {
635  if (maxNumRecursiveCalls == 0)
636  logger(WARN, "[TriangleMeshWall::moveVerticesToMatchVolume()] Maximum number of recursion calls reached for wall with id %.", getId());
637 
638  // Update the real vertices.
639  int num = vertices_.size();
640  for (int i = 0; i < num; i++)
641  vertices_[i].position += displacements[i];
642 
643  // Update the real triangles wall.
644  for (Triangle& t : triangles_)
645  t.wall.moveVertices({ displacements[t.vertexIndices[0]], displacements[t.vertexIndices[1]], displacements[t.vertexIndices[2]] });
646 
648 
649  // Reset static boolean for the next time this function is first called.
650  firstRecursiveCall = true;
651  return;
652  }
653 
654  // Multiply all displacements with the ratio.
655  for (Vec3D& d : displacements)
656  d *= ratio;
657  // Recursive call.
658  moveVerticesToMatchVolume(displacements, targetVolume, --maxNumRecursiveCalls);
659 }
Logger< MERCURYDPM_LOGLEVEL > logger("MercuryKernel")
Definition of different loggers with certain modules. A user can define its own custom logger here.
@ WARN
unsigned int getId() const
Returns the unique identifier of any particular object.
Definition: BaseObject.h:125
void moveVerticesToMatchVolume(std::vector< Vec3D > displacements, Mdouble targetVolume, int maxNumRecursiveCalls=15)
Moves all vertices by given displacements and corrects to match the change in volume with the target ...
Definition: TriangleMeshWall.cc:553
Mdouble getVolumeTetrahedron(const Vec3D &a, const Vec3D &b, const Vec3D &c, const Vec3D &d)
Calculates the volume of a tetrahedron formed by 4 vertices.
Definition: TriangleMeshWall.cc:661
bool isEqual(Mdouble v1, Mdouble v2, Mdouble absError)
Compares the difference of two Mdouble with an absolute error, useful in UnitTests.
Definition: ExtendedMath.cc:251

References BaseObject::getId(), getVolumeTetrahedron(), constants::i, mathsFunc::isEqual(), logger, periodicCompanions_, triangles_, updateBoundingBox(), TriangleMeshWall::Triangle::vertexIndices, vertices_, and WARN.

Referenced by WearableTriangleMeshWall::computeWear().

◆ operator=()

TriangleMeshWall & TriangleMeshWall::operator= ( const TriangleMeshWall other)

Copy assignment operator.

Parameters
otherThe TriangleMeshWall that must be copied.
Returns
60 {
61  if (this == &other)
62  {
63  return *this;
64  }
65  return *(other.copy());
66 }
TriangleMeshWall * copy() const override
Wall copy method.
Definition: TriangleMeshWall.cc:68

References copy().

◆ read()

void TriangleMeshWall::read ( std::istream &  is)
overridevirtual

Reads a TriangleMeshWall from an input stream, for example a restart file.

Reimplemented from BaseWall.

Reimplemented in WearableTriangleMeshWall.

74 {
75  BaseWall::read(is);
76 
77  std::string dummy;
78  int num;
79  is >> dummy >> num;
80 
81  std::vector<Vec3D> points(num);
82  for (int i = 0; i < num; i++)
83  {
84  Vec3D p;
85  is >> p;
86  points[i] = p;
87  }
88 
89  is >> dummy >> num;
90  std::vector<std::array<unsigned, 3>> cells(num);
91  for (int i = 0; i < num; i++)
92  {
93  std::array<unsigned, 3> c{};
94  is >> c[0] >> c[1] >> c[2];
95  cells[i] = c;
96  }
97 
98  is >> dummy >> num;
99  std::vector<std::pair<unsigned, unsigned>> periodicCompanions(num);
100  for (int i = 0; i < num; i ++)
101  {
102  std::pair<unsigned, unsigned> p;
103  is >> p.first >> p.second;
104  periodicCompanions[i] = p;
105  }
106 
107  set(points, cells);
108  setPeriodicCompanions(periodicCompanions);
109 
111 }
void read(std::istream &is) override
Function that reads a BaseWall from an input stream, usually a restart file.
Definition: BaseWall.cc:78

References constants::i, BaseWall::read(), set(), setPeriodicCompanions(), and updateBoundingBox().

Referenced by WearableTriangleMeshWall::read().

◆ refineTriangle()

void TriangleMeshWall::refineTriangle ( unsigned  index,
unsigned  numberOfTimes = 1 
)

Makes a really basic refinement by adding a vertex in the middle of the triangle to create 3 new ones. Note: Multiple refinements will definitely NOT create a nice mesh.

Warning
For now can only be used in initial setup, i.e. when there are no interactions yet. Interactions have to be projected onto newly formed triangles, which is not yet implemented.
Parameters
indexIndex of triangle to refine.
numberOfTimesHow many times to refine.
428 {
429  // A new vertex will be added in the middle of the triangle and 3 new triangles will be formed. The original triangle
430  // will not be deleted, as erasing items from a vector can be slow. Instead its vertices positions and indices will
431  // be updated to form one of the smaller triangles.
432  // The local vertex indices are 0, 1, 2 and the newly added 3. The original triangle will go from 0, 1, 2 to 0, 1, 3.
433  // The first new triangle will have indices 1, 2, 3, and the second 2, 0, 3.
434 
435  // (1) (2)
436  // _____________________________________
437  // \\ //
438  // \ \ / /
439  // \ \ / /
440  // \ \ / /
441  // \ \ / /
442  // \ \ / /
443  // \ \ / /
444  // \ |(3) /
445  // \ | /
446  // \ | /
447  // \ | /
448  // \ | /
449  // \ | /
450  // \ | /
451  // \ | /
452  // \ | /
453  // \ |/
454  // \/
455  // (0)
456 
457  // Reserve space for 2 new triangles and 1 new vertex, otherwise references will be broken when adding to vectors.
458  triangles_.reserve(triangles_.size() + 2);
459  vertices_.reserve(vertices_.size() + 1);
460 
461  // The triangle to refine.
462  Triangle& t = triangles_[index];
463 
464  // And its vertices.
465  Vertex& v0 = vertices_[t.vertexIndices[0]];
466  Vertex& v1 = vertices_[t.vertexIndices[1]];
467  Vertex& v2 = vertices_[t.vertexIndices[2]];
468 
469  // Center of triangle is position for new vertex.
470  const Vec3D p3 = (v0.position + v1.position + v2.position) / 3.0;
471  vertices_.emplace_back(p3);
472  const unsigned v3Index = vertices_.size() - 1;
473  Vertex& v3 = vertices_[v3Index];
474 
475  // First new triangle.
476  TriangleWall tw1;
477  tw1.setVertices(v1.position, v2.position, v3.position);
478  tw1.setSpecies(t.wall.getSpecies());
479  Triangle t1(tw1, { t.vertexIndices[1], t.vertexIndices[2], v3Index });
480  triangles_.push_back(t1);
481 
482  // Second new triangle.
483  TriangleWall tw2;
484  tw2.setVertices(v2.position, v0.position, v3.position);
485  tw2.setSpecies(t.wall.getSpecies());
486  Triangle t2(tw2, { t.vertexIndices[2], t.vertexIndices[0], v3Index });
487  triangles_.push_back(t2);
488 
489  // Their indices for access in the triangles vector.
490  const unsigned t2Index = triangles_.size() - 1;
491  const unsigned t1Index = t2Index - 1;
492 
493  // Store the new triangle index and its local vertex index in the vertices.
494  v0.triangleIndices.emplace_back(t2Index, 1);
495  v1.triangleIndices.emplace_back(t1Index, 0);
496  v2.triangleIndices.emplace_back(t1Index, 1);
497  // The original triangle does not share vertex 2 anymore, so overwrite its index with that of the second new triangle.
498  for (auto& p : v2.triangleIndices)
499  {
500  if (p.first == index)
501  {
502  p = std::pair<unsigned, unsigned>(t2Index, 0);
503  break;
504  }
505  }
506 
507  // Store the triangles indices and local vertex indices in the newly added vertex.
508  v3.triangleIndices.emplace_back(index, 2);
509  v3.triangleIndices.emplace_back(t1Index, 2);
510  v3.triangleIndices.emplace_back(t2Index, 2);
511 
512  // Overwrite the second vertex index of the original triangle with the newly added vertex.
513  t.vertexIndices[2] = v3Index;
514  // Update the original triangle vertex positions.
515  t.wall.setVertices(v0.position, v1.position, v3.position);
516 
517  // Recursion, for multiple refinements.
518  if (numberOfTimes > 1)
519  {
520  numberOfTimes--;
521  // The newly added vertex shares all three new triangles, so remember their indices.
522  const unsigned idx0 = v3.triangleIndices[0].first;
523  const unsigned idx1 = v3.triangleIndices[1].first;
524  const unsigned idx2 = v3.triangleIndices[2].first;
525  // Then refine each of the new triangles.
526  refineTriangle(idx0, numberOfTimes);
527  refineTriangle(idx1, numberOfTimes);
528  refineTriangle(idx2, numberOfTimes);
529  }
530 }
void setSpecies(const ParticleSpecies *species)
Defines the species of the current wall.
Definition: BaseWall.cc:169
void refineTriangle(unsigned index, unsigned numberOfTimes=1)
Makes a really basic refinement by adding a vertex in the middle of the triangle to create 3 new ones...
Definition: TriangleMeshWall.cc:427
A TriangleWall is convex polygon defined as an intersection of InfiniteWall's.
Definition: TriangleWall.h:57
void setVertices(Vec3D A, Vec3D B, Vec3D C)
Sets member variables such that the wall represents a triangle with vertices A, B,...
Definition: TriangleWall.cc:165

References BaseInteractable::getSpecies(), TriangleMeshWall::Vertex::position, BaseWall::setSpecies(), TriangleWall::setVertices(), TriangleMeshWall::Vertex::triangleIndices, triangles_, TriangleMeshWall::Triangle::vertexIndices, vertices_, and TriangleMeshWall::Triangle::wall.

◆ removeTriangle()

void TriangleMeshWall::removeTriangle ( unsigned  index,
bool  removeFreeVertex = true 
)

Removes a single triangle from the mesh.

Parameters
indexIndex of triangle to remove.
removeFreeVertexRemoves a vertex when it has no more triangles attached to it.
352 {
353  // Remove any interactions the TriangleWall might have.
354  // Otherwise later when in DPMBase interactionHandler.eraseOldInteractions(getNumberOfTimeSteps()) is called it
355  // might cause crashes, since it might be trying to delete pointers which are already used for something else.
356  for (BaseInteraction* i : triangles_[index].wall.getInteractions())
357  i->removeFromHandler();
358 
359  // Swap to Triangle with the last Triangle in the vector and then simply pop_back. This is faster, cleaner and
360  // simpler then using erase and having to update all other Triangle indices, since every index higher than the
361  // removed one would have shifted one down. Now only the swapped Triangle index references have to be updated.
362  const unsigned lastIndex = triangles_.size() - 1;
363  Triangle triangleToRemove = triangles_[index];
364 
365  // Don't swap right way, since the swapped Triangle index references need to be updated, but since it's possible
366  // that a free Vertex will be removed this might cause wrong index referencing.
367  // So first remove the index reference to this Triangle, for each of its Vertices.
368  for (unsigned vi : triangleToRemove.vertexIndices)
369  {
370  // Get the Triangle indices from this Vertex.
371  auto& tis = vertices_[vi].triangleIndices;
372  // Erase the index of the removed Triangle. This is only a short vector so erase is fine.
373  // This will only remove one item, as it should only contain it once.
374  tis.erase(std::remove_if(tis.begin(), tis.end(),[index](auto& p) { return p.first == index; }));
375 
376  // When no other Triangles are connected to this Vertex, it might be erased from the vector.
377  if (removeFreeVertex && tis.empty())
378  {
379  // Removing a Vertex is done in a similar manner, by swapping and popping back.
380  const unsigned lastIndexV = vertices_.size() - 1;
381  Vertex vertexToRemove = vertices_[vi];
382  vertices_[vi] = vertices_[lastIndexV];
383  vertices_[lastIndexV] = vertexToRemove;
384  vertices_.pop_back();
385 
386  // No Triangles with index references to the removed Vertex exist.
387  // However, for every Triangle which is referencing the swapped Vertex, update the index with the removed index.
388  for (auto& ti : vertices_[vi].triangleIndices)
389  for (unsigned& tvi : triangles_[ti.first].vertexIndices)
390  if (tvi == lastIndexV)
391  {
392  tvi = vi;
393  break;
394  }
395 
396  // If this vertex has any periodic companions, those should be removed from the vector.
397  periodicCompanions_.erase(std::remove_if(periodicCompanions_.begin(), periodicCompanions_.end(),
398  [vi](auto& p) { return p.first == vi || p.second == vi; }), periodicCompanions_.end());
399  // Also the swapped index should be updated with the removed index.
400  for (auto& p : periodicCompanions_)
401  {
402  if (p.first == lastIndexV)
403  p.first = vi;
404  else if (p.second == lastIndexV)
405  p.second = vi;
406  }
407  }
408  }
409 
410  // Now swap the Triangles and pop back.
411  triangles_[index] = triangles_[lastIndex];
412  triangles_[lastIndex] = triangleToRemove;
413  triangles_.pop_back();
414 
415  // For every Vertex which is referencing the swapped Triangle, update the index with the removed index.
416  for (unsigned& vi : triangles_[index].vertexIndices)
417  for (auto& ti : vertices_[vi].triangleIndices)
418  if (ti.first == lastIndex)
419  {
420  ti.first = index;
421  break;
422  }
423 
425 }

References constants::i, periodicCompanions_, triangles_, updateBoundingBox(), TriangleMeshWall::Triangle::vertexIndices, and vertices_.

◆ resetForceTorque()

void TriangleMeshWall::resetForceTorque ( int  numberOfOMPthreads)
overridevirtual

Reimplemented from BaseInteractable.

295 {
296  BaseWall::resetForceTorque(numberOfOMPthreads);
297 
298  for (auto& t : triangles_)
299  t.wall.resetForceTorque(numberOfOMPthreads);
300 }
virtual void resetForceTorque(int numberOfOMPthreads)
Definition: BaseInteractable.cc:141

References BaseInteractable::resetForceTorque(), and triangles_.

◆ rotate()

void TriangleMeshWall::rotate ( const Vec3D angularVelocityDt)
overridevirtual

Rotates this BaseInteractable.

Rotates the interacable a given solid angle. Note, this just updates the orientation by the angle.

This function has been declared virtual, so it can be overridden for IntersectionOfWalls.

Parameters
[in]angularVelocityDtReference to Vec3D which is the solid angle through which the interactable is rotated.
Todo:
TW the move and rotate functions should only pass the time step, as teh velocity can be accessed directly by the object; this would simplify functions like Screw::rotate

Reimplemented from BaseInteractable.

943 {
944  BaseWall::rotate(angularVelocity);
946 }
virtual void rotate(const Vec3D &angularVelocityDt)
Rotates this BaseInteractable.
Definition: BaseInteractable.cc:230

References BaseInteractable::rotate(), and updateBoundingBoxGlobal().

Referenced by getInteractionWith(), and writeVTK().

◆ set()

void TriangleMeshWall::set ( const std::vector< Vec3D > &  points,
const std::vector< std::array< unsigned, 3 >> &  cells 
)

Set function creating triangles.

Parameters
pointsVector of vertices
cellsVector of cells, each cell holds three indices to the points vector
134 {
135  // The species for the triangles are the same as the main wall.
136  // Note: when the species have not been set yet, this will be a nullptr,
137  // so a check is done before actually setting the species for the triangles.
138  auto species = getSpecies();
139 
140  // Clear mesh, as set function can be called multiple times to create different meshes. Useful when creating a
141  // complicated mesh with the addToMesh() function.
142  triangles_.clear();
143  vertices_.clear();
144  triangles_.reserve(cells.size());
145  vertices_.reserve(points.size());
146 
147  // Add all the points as Vertex to the vector.
148  for (auto& p : points)
149  vertices_.emplace_back(p);
150 
151  for (auto& c : cells)
152  {
153  TriangleWall tw;
154  // The position is the origin of the local coordinate system, which is always (0, 0, 0) (not getPosition()!).
155  // This is needed in case the mesh has an angular velocity.
156  tw.setVertices(points[c[0]], points[c[1]], points[c[2]], Vec3D(0.0, 0.0, 0.0));
157  if (species != nullptr)
158  tw.setSpecies(species);
159 
160  // Add as Triangle with TriangleWall and vertexIndices to the vector.
161  triangles_.emplace_back(tw, c);
162 
163  // Add the Triangle index and the local vertex index to each of the Vertices.
164  const unsigned tIndex = triangles_.size() - 1;
165  vertices_[c[0]].triangleIndices.emplace_back(tIndex, 0);
166  vertices_[c[1]].triangleIndices.emplace_back(tIndex, 1);
167  vertices_[c[2]].triangleIndices.emplace_back(tIndex, 2);
168  }
169 
171 }

References BaseInteractable::getSpecies(), BaseWall::setSpecies(), TriangleWall::setVertices(), triangles_, updateBoundingBox(), and vertices_.

Referenced by createFourPointMesh(), createParallelogramMesh(), read(), and TriangleMeshWall().

◆ setOrientation()

void TriangleMeshWall::setOrientation ( const Quaternion orientation)
overridevirtual

Sets the orientation of this BaseInteractable.

Interpretation depends on which interactable is being considered See also BaseInteractable::getOrientation.

Parameters
[in]orientationReference to Vec3D storing the orientation of the particle.

Reimplemented from BaseInteractable.

931 {
932  BaseWall::setOrientation(orientation);
934 }
virtual void setOrientation(const Quaternion &orientation)
Sets the orientation of this BaseInteractable.
Definition: BaseInteractable.h:260

References BaseInteractable::setOrientation(), and updateBoundingBoxGlobal().

◆ setPeriodicCompanions()

void TriangleMeshWall::setPeriodicCompanions ( const std::vector< std::pair< unsigned, unsigned >> &  periodicCompanions)

Sets the vector with pairs of indices of vertices which lie on a periodic boundary and are each others 'companion'. E.g. when moving one vertex, the other is also moved the same amount. A vertex can have multiple companions (when lying on multiple periodic boundaries) and those should be in the vector as multiple pairs.

Parameters
periodicCompanionsVector of pairs containing the companions.
533 {
534  periodicCompanions_ = periodicCompanions;
535 }

References periodicCompanions_.

Referenced by createParallelogramMesh(), and read().

◆ setPosition()

void TriangleMeshWall::setPosition ( const Vec3D position)
overridevirtual

Sets the position of this BaseInteractable.

Interpretation depends on which interactable is being considered See also BaseInteractable::getPosistion.

Parameters
[in]positionReference to Vec3D storing the position of the particle.

Reimplemented from BaseInteractable.

925 {
926  BaseWall::setPosition(position);
928 }

References BaseInteractable::setPosition(), and updateBoundingBoxGlobal().

◆ setSpecies()

void TriangleMeshWall::setSpecies ( const ParticleSpecies species)
320 {
321  if (species == nullptr)
322  return;
323  BaseWall::setSpecies(species);
324  for (auto& t : triangles_)
325  t.wall.setSpecies(species);
326 }

References BaseWall::setSpecies(), and triangles_.

Referenced by TriangleMeshWall().

◆ updateBoundingBox()

void TriangleMeshWall::updateBoundingBox ( )
private

Sets the local and global bounding boxes. This method should be called any time a vertex is updated in lab frame.

870 {
871  // Initialize min max.
874 
875  // Loop through vertices and store min max positions.
876  for (const Vertex& v : vertices_)
877  {
878  const Vec3D& pos = v.position;
879  min = Vec3D::min(min, pos);
880  max = Vec3D::max(max, pos);
881  }
882 
883  boundingBoxMin_ = min;
884  boundingBoxMax_ = max;
885 
887 }
static Vec3D max(const Vec3D &a, const Vec3D &b)
Calculates the pointwise maximum of two Vec3D.
Definition: Vector.cc:89
static Vec3D min(const Vec3D &a, const Vec3D &b)
Calculates the pointwise minimum of two Vec3D.
Definition: Vector.cc:102
const Mdouble inf
Definition: GeneralDefine.h:44

References boundingBoxMax_, boundingBoxMin_, constants::inf, Vec3D::max(), Vec3D::min(), updateBoundingBoxGlobal(), and vertices_.

Referenced by addToMesh(), moveVertex(), moveVerticesToMatchVolume(), read(), removeTriangle(), and set().

◆ updateBoundingBoxGlobal()

void TriangleMeshWall::updateBoundingBoxGlobal ( )
private

Sets the global bounding box, using the bounding box in lab frame. This method should be called when there are changes in global frame, but not in lab frame. E.g. when calling setPosition().

890 {
891  // This basically is putting a bounding box around the rotated and translated lab frame bounding box.
892 
893  // All corners of the lab frame bounding box. Using min max for clarity.
895  Vec3D v0 = Vec3D(min.X, min.Y, min.Z);
896  Vec3D v1 = Vec3D(min.X, min.Y, max.Z);
897  Vec3D v2 = Vec3D(max.X, min.Y, max.Z);
898  Vec3D v3 = Vec3D(max.X, min.Y, min.Z);
899  Vec3D v4 = Vec3D(min.X, max.Y, min.Z);
900  Vec3D v5 = Vec3D(min.X, max.Y, max.Z);
901  Vec3D v6 = Vec3D(max.X, max.Y, max.Z);
902  Vec3D v7 = Vec3D(max.X, max.Y, min.Z);
903 
904  // Store in array so we can do a auto loop by reference.
905  std::array<Vec3D, 8> corners = { v0, v1, v2, v3, v4, v5, v6, v7 };
906 
907  // Reinitialize min max to use in loop.
910 
911  // Loop through corners, rotate and translate them to global frame, get global min max position.
912  for (Vec3D& pos : corners)
913  {
914  getOrientation().rotate(pos);
915  pos += getPosition();
916  min = Vec3D::min(min, pos);
917  max = Vec3D::max(max, pos);
918  }
919 
920  boundingBoxMinGlobal_ = min;
921  boundingBoxMaxGlobal_ = max;
922 }
void rotate(Vec3D &position) const
Definition: Quaternion.cc:563
Mdouble Y
Definition: Vector.h:66
Mdouble Z
Definition: Vector.h:66
Mdouble X
the vector components
Definition: Vector.h:66

References boundingBoxMax_, boundingBoxMaxGlobal_, boundingBoxMin_, boundingBoxMinGlobal_, BaseInteractable::getOrientation(), BaseInteractable::getPosition(), constants::inf, Vec3D::max(), Vec3D::min(), Quaternion::rotate(), Vec3D::X, Vec3D::Y, and Vec3D::Z.

Referenced by move(), rotate(), setOrientation(), setPosition(), and updateBoundingBox().

◆ write()

void TriangleMeshWall::write ( std::ostream &  os) const
overridevirtual

Writes a TriangleMeshWall to an output stream, for example a restart file.

Reimplemented from BaseWall.

Reimplemented in WearableTriangleMeshWall.

114 {
115  BaseWall::write(os);
116 
117  os << " points " << vertices_.size();
118  for (const Vertex& v : vertices_)
119  os << ' ' << v.position;
120  os << " cells " << triangles_.size();
121  for (const Triangle& t : triangles_)
122  os << ' ' << t.vertexIndices[0] << ' ' << t.vertexIndices[1] << ' ' << t.vertexIndices[2];
123  os << " periodicCompanions " << periodicCompanions_.size();
124  for (auto& p : periodicCompanions_)
125  os << ' ' << p.first << ' ' << p.second;
126 }
void write(std::ostream &os) const override
Function that writes a BaseWall to an output stream, usually a restart file.
Definition: BaseWall.cc:100

References periodicCompanions_, triangles_, vertices_, and BaseWall::write().

Referenced by WearableTriangleMeshWall::write().

◆ writeVTK()

void TriangleMeshWall::writeVTK ( VTKContainer vtk) const
overridevirtual

adds extra information to the points and triangleStrips vectors needed to plot the wall in vtk format

Parameters
pointsCoordinates of the vertices of the triangulated surfaces (in the VTK file this is called POINTS)
triangleStripsIndices of three vertices forming one triangulated surface (in the VTK file this is called CELL)

Reimplemented from BaseWall.

303 {
304  const unsigned long s = vtk.points.size();
305 
306  for (auto& v : vertices_)
307  {
308  vtk.points.push_back(getOrientation().rotate(v.position) + getPosition());
309  }
310 
311  for (auto& t : triangles_)
312  {
313  vtk.triangleStrips.push_back({ static_cast<double>(s + t.vertexIndices[0]),
314  static_cast<double>(s + t.vertexIndices[1]),
315  static_cast<double>(s + t.vertexIndices[2]) });
316  }
317 }
std::vector< std::vector< double > > triangleStrips
Definition: BaseWall.h:40
std::vector< Vec3D > points
Definition: BaseWall.h:39

References BaseInteractable::getOrientation(), BaseInteractable::getPosition(), VTKContainer::points, rotate(), triangles_, VTKContainer::triangleStrips, and vertices_.

Member Data Documentation

◆ boundingBoxMax_

Vec3D TriangleMeshWall::boundingBoxMax_
private

◆ boundingBoxMaxGlobal_

Vec3D TriangleMeshWall::boundingBoxMaxGlobal_
private

◆ boundingBoxMin_

Vec3D TriangleMeshWall::boundingBoxMin_
private

Bounding box corners in lab frame and global frame. Used to speed up contact detection. HGrid uses the global frame min max.

Referenced by isWithinBoundingBox(), TriangleMeshWall(), updateBoundingBox(), and updateBoundingBoxGlobal().

◆ boundingBoxMinGlobal_

Vec3D TriangleMeshWall::boundingBoxMinGlobal_
private

◆ periodicCompanions_

std::vector<std::pair<unsigned, unsigned> > TriangleMeshWall::periodicCompanions_
private

◆ triangles_

◆ vertices_


The documentation for this class was generated from the following files: