36 #include "MeshBasedCellPopulationWithGhostNodes.hpp" 37 #include "CellLocationIndexWriter.hpp" 39 template<
unsigned DIM>
42 std::vector<CellPtr>& rCells,
43 const std::vector<unsigned> locationIndices,
45 double ghostSpringStiffness)
47 mGhostSpringStiffness(ghostSpringStiffness)
49 if (!locationIndices.empty())
52 std::set<unsigned> node_indices;
53 std::set<unsigned> location_indices;
54 std::set<unsigned> ghost_node_indices;
58 node_indices.insert(this->
GetNode(i)->GetIndex());
60 for (
unsigned i=0; i<locationIndices.size(); i++)
62 location_indices.insert(locationIndices[i]);
65 std::set_difference(node_indices.begin(), node_indices.end(),
66 location_indices.begin(), location_indices.end(),
67 std::inserter(ghost_node_indices, ghost_node_indices.begin()));
79 template<
unsigned DIM>
81 double ghostSpringStiffness)
87 template<
unsigned DIM>
92 template<
unsigned DIM>
95 EXCEPTION(
"Currently can't solve PDEs on meshes with ghost nodes");
99 template<
unsigned DIM>
105 template<
unsigned DIM>
111 template<
unsigned DIM>
114 std::set<unsigned> ghost_node_indices;
119 ghost_node_indices.insert(i);
122 return ghost_node_indices;
125 template<
unsigned DIM>
132 for (std::set<unsigned>::iterator iter=rGhostNodeIndices.begin(); iter!=rGhostNodeIndices.end(); ++iter)
140 template<
unsigned DIM>
143 assert(rNodeAGlobalIndex != rNodeBGlobalIndex);
144 c_vector<double, DIM> unit_difference;
145 const c_vector<double, DIM>& r_node_a_location = this->
GetNode(rNodeAGlobalIndex)->rGetLocation();
146 const c_vector<double, DIM>& r_node_b_location = this->
GetNode(rNodeBGlobalIndex)->rGetLocation();
149 unit_difference = this->
mrMesh.GetVectorFromAtoB(r_node_a_location, r_node_b_location);
151 double distance_between_nodes = norm_2(unit_difference);
152 unit_difference /= distance_between_nodes;
154 double rest_length = 1.0;
159 template<
unsigned DIM>
164 assert(p_created_cell == pNewCell);
176 return p_created_cell;
179 template<
unsigned DIM>
194 EXCEPTION(
"Node " << node_index <<
" is labelled as a ghost node and has a cell attached");
196 validated_node[node_index] =
true;
199 for (
unsigned i=0; i<validated_node.size(); i++)
201 if (!validated_node[i])
203 EXCEPTION(
"Node " << i <<
" does not appear to be a ghost node or have a cell associated with it");
208 template<
unsigned DIM>
212 std::vector<bool> ghost_nodes_before_remesh =
mIsGhostNode;
219 for (
unsigned old_index=0; old_index<rMap.
GetSize(); old_index++)
224 mIsGhostNode[new_index] = ghost_nodes_before_remesh[old_index];
229 template<
unsigned DIM>
236 for (std::set<unsigned>::iterator iter = neighbour_indices.begin();
237 iter != neighbour_indices.end();)
241 neighbour_indices.erase(iter++);
249 return neighbour_indices;
252 template<
unsigned DIM>
273 template<
unsigned DIM>
277 std::vector<c_vector<double, DIM> > drdt(this->
GetNumNodes());
278 for (
unsigned i=0; i<drdt.size(); i++)
280 drdt[i] = zero_vector<double>(DIM);
288 unsigned nodeA_global_index = edge_iterator.GetNodeA()->GetIndex();
289 unsigned nodeB_global_index = edge_iterator.GetNodeB()->GetIndex();
295 drdt[nodeB_global_index] -= force;
299 drdt[nodeA_global_index] += force;
303 drdt[nodeB_global_index] -= force;
309 node_iter != this->
mrMesh.GetNodeIteratorEnd();
312 unsigned node_index = node_iter->GetIndex();
315 node_iter->ClearAppliedForce();
316 node_iter->AddAppliedForceContribution(drdt[node_index]);
321 template<
unsigned DIM>
326 if (!this->
template HasWriter<CellLocationIndexWriter>())
328 this->
template AddCellWriter<CellLocationIndexWriter>();
335 template<
unsigned DIM>
342 std::stringstream time;
343 time << num_timesteps;
355 std::vector<double> vtk_cell_data(num_vtk_cells);
363 unsigned elem_index = elem_iter->GetIndex();
370 vtk_cell_data[elem_index] = -1.0;
378 vtk_cell_data[elem_index] = (*cell_writer_iter)->GetCellDataForVtkOutput(p_cell,
this);
382 mesh_writer.
AddCellData((*cell_writer_iter)->GetVtkCellDataName(), vtk_cell_data);
387 std::vector<double> ghosts(num_vtk_cells);
392 unsigned elem_index = elem_iter->GetIndex();
403 *(this->
mpVtkMetaFile) <<
"\" group=\"\" part=\"0\" file=\"results_";
410 template<
unsigned DIM>
413 *rParamsFile <<
"\t\t<GhostSpringStiffness>" <<
mGhostSpringStiffness <<
"</GhostSpringStiffness>\n";
virtual TetrahedralMesh< DIM, DIM > * GetTetrahedralMeshForPdeModifier()
void UpdateGhostNodesAfterReMesh(NodeMap &rMap)
void AddCellData(std::string dataName, std::vector< double > dataPayload)
unsigned GetDelaunayNodeIndexCorrespondingToVoronoiElementIndex(unsigned elementIndex)
virtual CellPtr AddCell(CellPtr pNewCell, CellPtr pParentCell)
std::set< unsigned > GetNeighbouringLocationIndices(CellPtr pCell)
virtual void WriteVtkResultsToFile(const std::string &rDirectory)
virtual CellPtr GetCellUsingLocationIndex(unsigned index)
virtual unsigned GetNumElements() const
unsigned GetLocationIndexUsingCell(CellPtr pCell)
std::vector< boost::shared_ptr< AbstractCellWriter< ELEMENT_DIM, SPACE_DIM > > > mCellWriters
std::set< unsigned > GetGhostNodeIndices()
virtual void AcceptCellWriter(boost::shared_ptr< AbstractCellWriter< ELEMENT_DIM, ELEMENT_DIM > > pCellWriter, CellPtr pCell)
virtual void OpenWritersFiles(OutputFileHandler &rOutputFileHandler)
#define EXCEPTION(message)
static SimulationTime * Instance()
bool IsGhostNode(unsigned index)
NodeIterator GetNodeIteratorEnd()
unsigned GetTimeStepsElapsed() const
virtual void AcceptCellWritersAcrossPopulation()
c_vector< double, DIM > CalculateForceBetweenGhostNodes(const unsigned &rNodeAGlobalIndex, const unsigned &rNodeBGlobalIndex)
bool mOutputResultsForChasteVisualizer
MutableMesh< ELEMENT_DIM, ELEMENT_DIM > & rGetMesh()
MeshBasedCellPopulationWithGhostNodes(MutableMesh< DIM, DIM > &rMesh, std::vector< CellPtr > &rCells, const std::vector< unsigned > locationIndices=std::vector< unsigned >(), bool deleteMesh=false, double ghostSpringStiffness=15.0)
CellPtr AddCell(CellPtr pNewCell, CellPtr pParentCell)
VertexElementIterator GetElementIteratorBegin(bool skipDeletedElements=true)
#define EXPORT_TEMPLATE_CLASS_SAME_DIMS(CLASS)
VertexMesh< ELEMENT_DIM, ELEMENT_DIM > * mpVoronoiTessellation
void SetGhostNodes(const std::set< unsigned > &rGhostNodeIndices)
void WriteVtkUsingMesh(VertexMesh< ELEMENT_DIM, SPACE_DIM > &rMesh, std::string stamp="")
std::set< unsigned > GetNeighbouringNodeIndices(unsigned index)
Node< ELEMENT_DIM > * GetNode(unsigned index)
bool IsDeleted(unsigned index)
unsigned GetNewIndex(unsigned oldIndex) const
std::vector< bool > & rGetGhostNodes()
double mGhostSpringStiffness
void OutputCellPopulationParameters(out_stream &rParamsFile)
VertexElementIterator GetElementIteratorEnd()
std::vector< bool > mIsGhostNode
AbstractMesh< ELEMENT_DIM, SPACE_DIM > & mrMesh
void OutputCellPopulationParameters(out_stream &rParamsFile)
virtual ~MeshBasedCellPopulationWithGhostNodes()
virtual void OpenWritersFiles(OutputFileHandler &rOutputFileHandler)