36 #include "AbstractMesh.hpp"
43 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
45 : mpDistributedVectorFactory(nullptr),
46 mMeshFileBaseName(
""),
47 mMeshChangesDuringSimulation(false)
51 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
55 for (
unsigned i = 0; i < mNodes.size(); i++)
59 if (mpDistributedVectorFactory)
61 delete mpDistributedVectorFactory;
65 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
71 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
74 return mBoundaryNodes.size();
77 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
83 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
88 assert(mNodes.size() != 0u);
89 return mNodes[0]->GetNumNodeAttributes();
92 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
95 unsigned local_index = SolveNodeMapping(index);
96 return mNodes[local_index];
99 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
102 return GetNode(index);
105 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
108 if (mNodePermutation.empty())
110 return GetNode(index);
114 return GetNode(mNodePermutation[index]);
119 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
126 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
132 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
135 if (mpDistributedVectorFactory ==
nullptr)
140 SetElementOwnerships();
143 return mpDistributedVectorFactory;
146 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
149 if (mpDistributedVectorFactory)
151 EXCEPTION(
"Cannot change the mesh's distributed vector factory once it has been set.");
155 EXCEPTION(
"The distributed vector factory provided to the mesh is for the wrong number of processes.");
157 mpDistributedVectorFactory = pFactory;
161 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
168 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
171 return mBoundaryNodes.begin();
174 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
177 return mBoundaryNodes.end();
180 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
185 EXCEPTION(
"This mesh was not constructed from a file.");
188 return mMeshFileBaseName;
191 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
194 return (mMeshFileBaseName !=
"");
197 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
200 return mNodePermutation;
203 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
205 const c_vector<double, SPACE_DIM>& rLocationA,
const c_vector<double, SPACE_DIM>& rLocationB)
207 c_vector<double, SPACE_DIM> vector = rLocationB - rLocationA;
211 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
214 c_vector<double, SPACE_DIM> vector = GetVectorFromAtoB(mNodes[indexA]->rGetLocation(),
215 mNodes[indexB]->rGetLocation());
216 return norm_2(vector);
219 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
222 assert(rDimension < SPACE_DIM);
223 return CalculateBoundingBox(mNodes).GetWidth(rDimension);
226 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
230 c_vector<double, SPACE_DIM> minimum_point;
231 c_vector<double, SPACE_DIM> maximum_point;
236 minimum_point = scalar_vector<double>(SPACE_DIM, 0.0);
237 maximum_point = scalar_vector<double>(SPACE_DIM, 0.0);
241 minimum_point = scalar_vector<double>(SPACE_DIM, DBL_MAX);
242 maximum_point = scalar_vector<double>(SPACE_DIM, -DBL_MAX);
246 for (
unsigned index = 0; index < rNodes.size(); index++)
248 if (!rNodes[index]->IsDeleted())
251 c_vector<double, SPACE_DIM> position;
252 position = rNodes[index]->rGetLocation();
255 for (
unsigned i = 0; i < SPACE_DIM; i++)
257 if (position[i] < minimum_point[i])
259 minimum_point[i] = position[i];
261 if (position[i] > maximum_point[i])
263 maximum_point[i] = position[i];
276 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
281 return bounding_cuboid;
284 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
298 unsigned best_node_index = 0u;
299 double best_node_point_distance = DBL_MAX;
301 const c_vector<double, SPACE_DIM>& test_location = rTestPoint.
rGetLocation();
303 for (
unsigned node_index = 0; node_index < mNodes.size(); node_index++)
306 double node_point_distance = norm_2(GetVectorFromAtoB(mNodes[node_index]->rGetLocation(), test_location));
308 if (node_point_distance < best_node_point_distance)
310 best_node_index = node_index;
311 best_node_point_distance = node_point_distance;
318 return mNodes[best_node_index]->GetIndex();
321 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
324 unsigned num_nodes = mNodes.size();
326 for (
unsigned i = 0; i < num_nodes; i++)
328 c_vector<double, SPACE_DIM>& r_location = mNodes[i]->rGetModifiableLocation();
331 r_location[2] *= zScale;
335 r_location[1] *= yScale;
337 r_location[0] *= xScale;
343 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
345 const double xMovement,
346 const double yMovement,
347 const double zMovement)
349 c_vector<double, SPACE_DIM> displacement;
354 displacement[2] = zMovement;
358 displacement[1] = yMovement;
361 displacement[0] = xMovement;
365 Translate(displacement);
368 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
371 unsigned num_nodes = this->mNodes.size();
373 for (
unsigned i = 0; i < num_nodes; i++)
375 c_vector<double, SPACE_DIM>& r_location = this->mNodes[i]->rGetModifiableLocation();
376 r_location += rDisplacement;
382 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
385 unsigned num_nodes = this->mNodes.size();
387 for (
unsigned i = 0; i < num_nodes; i++)
389 c_vector<double, SPACE_DIM>& r_location = this->mNodes[i]->rGetModifiableLocation();
390 r_location = prod(rotationMatrix, r_location);
396 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
399 assert(SPACE_DIM == 3);
400 double norm = norm_2(axis);
401 c_vector<double, 3> unit_axis = axis / norm;
403 c_matrix<double, SPACE_DIM, SPACE_DIM> rotation_matrix;
405 double c = cos(angle);
406 double s = sin(angle);
408 rotation_matrix(0, 0) = unit_axis(0) * unit_axis(0) + c * (1 - unit_axis(0) * unit_axis(0));
409 rotation_matrix(0, 1) = unit_axis(0) * unit_axis(1) * (1 - c) - unit_axis(2) * s;
410 rotation_matrix(1, 0) = unit_axis(0) * unit_axis(1) * (1 - c) + unit_axis(2) * s;
411 rotation_matrix(1, 1) = unit_axis(1) * unit_axis(1) + c * (1 - unit_axis(1) * unit_axis(1));
412 rotation_matrix(0, 2) = unit_axis(0) * unit_axis(2) * (1 - c) + unit_axis(1) * s;
413 rotation_matrix(1, 2) = unit_axis(1) * unit_axis(2) * (1 - c) - unit_axis(0) * s;
414 rotation_matrix(2, 0) = unit_axis(0) * unit_axis(2) * (1 - c) - unit_axis(1) * s;
415 rotation_matrix(2, 1) = unit_axis(1) * unit_axis(2) * (1 - c) + unit_axis(0) * s;
416 rotation_matrix(2, 2) = unit_axis(2) * unit_axis(2) + c * (1 - unit_axis(2) * unit_axis(2));
418 Rotate(rotation_matrix);
421 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
426 EXCEPTION(
"This rotation is only valid in 3D");
428 c_matrix<double, SPACE_DIM, SPACE_DIM> x_rotation_matrix = identity_matrix<double>(SPACE_DIM);
430 x_rotation_matrix(1, 1) = cos(theta);
431 x_rotation_matrix(1, 2) = sin(theta);
432 x_rotation_matrix(2, 1) = -sin(theta);
433 x_rotation_matrix(2, 2) = cos(theta);
434 Rotate(x_rotation_matrix);
437 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
442 EXCEPTION(
"This rotation is only valid in 3D");
444 c_matrix<double, SPACE_DIM, SPACE_DIM> y_rotation_matrix = identity_matrix<double>(SPACE_DIM);
446 y_rotation_matrix(0, 0) = cos(theta);
447 y_rotation_matrix(0, 2) = -sin(theta);
448 y_rotation_matrix(2, 0) = sin(theta);
449 y_rotation_matrix(2, 2) = cos(theta);
451 Rotate(y_rotation_matrix);
454 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
459 EXCEPTION(
"This rotation is not valid in less than 2D");
461 c_matrix<double, SPACE_DIM, SPACE_DIM> z_rotation_matrix = identity_matrix<double>(SPACE_DIM);
463 z_rotation_matrix(0, 0) = cos(theta);
464 z_rotation_matrix(0, 1) = sin(theta);
465 z_rotation_matrix(1, 0) = -sin(theta);
466 z_rotation_matrix(1, 1) = cos(theta);
468 Rotate(z_rotation_matrix);
471 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
477 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
482 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
485 return mMeshChangesDuringSimulation;
488 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
491 unsigned max_num = 0u;
492 for (
unsigned local_node_index = 0; local_node_index < mNodes.size(); local_node_index++)
494 unsigned num = mNodes[local_node_index]->GetNumContainingElements();
503 template <
unsigned ELEMENT_DIM,
unsigned SPACE_DIM>
507 mMeshFileBaseName =
"";
virtual DistributedVectorFactory * GetDistributedVectorFactory()
virtual void ReadNodesPerProcessorFile(const std::string &rNodesPerProcessorFile)
virtual unsigned GetNearestNodeIndex(const ChastePoint< SPACE_DIM > &rTestPoint)
c_vector< double, DIM > & rGetLocation()
virtual void RefreshMesh()
virtual Node< SPACE_DIM > * GetNodeOrHaloNode(unsigned index) const
const std::vector< unsigned > & rGetNodePermutation() const
bool IsMeshChanging() const
virtual void Translate(const c_vector< double, SPACE_DIM > &rDisplacement)
Node< SPACE_DIM > * GetNode(unsigned index) const
#define EXCEPTION(message)
unsigned CalculateMaximumContainingElementsPerProcess() const
std::string GetMeshFileBaseName() const
virtual ChasteCuboid< SPACE_DIM > CalculateBoundingBox() const
virtual unsigned GetNumNodes() const
virtual void PermuteNodes()
BoundaryNodeIterator GetBoundaryNodeIteratorBegin() const
virtual unsigned GetNumAllNodes() const
virtual void SetElementOwnerships()
double GetDistanceBetweenNodes(unsigned indexA, unsigned indexB)
unsigned GetNumBoundaryNodes() const
unsigned GetNumNodeAttributes() const
std::vector< Node< SPACE_DIM > * >::const_iterator BoundaryNodeIterator
bool IsMeshOnDisk() const
void SetMeshHasChangedSinceLoading()
virtual double GetWidth(const unsigned &rDimension) const
virtual void Rotate(c_matrix< double, SPACE_DIM, SPACE_DIM > rotationMatrix)
virtual c_vector< double, SPACE_DIM > GetVectorFromAtoB(const c_vector< double, SPACE_DIM > &rLocationA, const c_vector< double, SPACE_DIM > &rLocationB)
BoundaryNodeIterator GetBoundaryNodeIteratorEnd() const
virtual void Scale(const double xFactor=1.0, const double yFactor=1.0, const double zFactor=1.0)
virtual void SetDistributedVectorFactory(DistributedVectorFactory *pFactory)
void RotateY(const double theta)
void RotateZ(const double theta)
unsigned GetNumProcs() const
Node< SPACE_DIM > * GetNodeFromPrePermutationIndex(unsigned index) const
void RotateX(const double theta)