unsigned AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>::GetLocationIndexUsingCell(CellPtr pCell)
{
    // Check the cell is in the map
    assert(this->mCellLocationMap.find(pCell.get()) != this->mCellLocationMap.end());

    return mCellLocationMap[pCell.get()];
}
bool MeshTestUtility::constraintIsConsistent(MeshTopologyViewPtr meshTopo, AnnotatedEntity &constrainingEntity,
                                             int d, IndexType constrainedEntityIndex, bool requireConstrainingEntityBelongToActiveCell)
{
  int sideDim = meshTopo->getDimension() - 1;
  CellPtr constrainingCell = meshTopo->getCell(constrainingEntity.cellID);
  int constrainingSubcordInCell = CamelliaCellTools::subcellOrdinalMap(constrainingCell->topology(),
                                                                       sideDim, constrainingEntity.sideOrdinal,
                                                                       constrainingEntity.dimension, constrainingEntity.subcellOrdinal);
  
  IndexType constrainingEntityIndex = constrainingCell->entityIndex(constrainingEntity.dimension, constrainingSubcordInCell);
  bool isAncestor = meshTopo->entityIsGeneralizedAncestor(constrainingEntity.dimension, constrainingEntityIndex, d, constrainedEntityIndex);
  
  if (!isAncestor) return false;
  
  if (requireConstrainingEntityBelongToActiveCell)
  {
    set<pair<IndexType,unsigned>> cellEntries = meshTopo->getCellsContainingEntity(constrainingEntity.dimension, constrainingEntityIndex);
    auto activeCells = &meshTopo->getActiveCellIndices();
    for (auto cellEntry : cellEntries)
    {
      IndexType cellID = cellEntry.first;
      if (activeCells->find(cellID) != activeCells->end()) return true; // found an active cell, and isAncestor is true
    }
    return false;
  }
  
  return isAncestor;
}
void ApoptoticCellKiller<SPACE_DIM>::CheckAndLabelSingleCellForApoptosis(CellPtr pCell)
{
    if (pCell->HasCellProperty<ApoptoticCellProperty>() && !(pCell->HasApoptosisBegun()))
    {
        pCell->StartApoptosis();
    }
}
Exemple #4
0
bool consp(ExprPtr e)
{
	if (!dynamic_pointer_cast<Cell>(e))
		return false;
	CellPtr c = static_pointer_cast<Cell>(e);
	if (c->is_nil())
		return false;
	return true;
}
bool MeshTestUtility::checkConstraintConsistency(MeshPtr meshMinimumRule)
{
  MeshTopologyViewPtr meshTopo = meshMinimumRule->getTopology();
  GDAMinimumRule* minRule = dynamic_cast<GDAMinimumRule*>(meshMinimumRule->globalDofAssignment().get());
  
  bool consistent = true;
  
  for (IndexType cellID : meshMinimumRule->cellIDsInPartition())
  {
    CellConstraints constraints = minRule->getCellConstraints(cellID);
    CellPtr cell = meshTopo->getCell(cellID);
    CellTopoPtr cellTopo = cell->topology();
    
    for (int d=0; d<cellTopo->getDimension(); d++)
    {
      int scCount = cellTopo->getSubcellCount(d);
      for (int scord=0; scord<scCount; scord++)
      {
        IndexType entityIndex = cell->entityIndex(d, scord);
        
        AnnotatedEntity constrainingEntity = constraints.subcellConstraints[d][scord];
        bool isConsistent = constraintIsConsistent(meshTopo, constrainingEntity, d, entityIndex, true);
        
        if (!isConsistent)
        {
          cout << "Failed consistency test for standard constraints on cell " << cellID << ", " << CamelliaCellTools::entityTypeString(d) << " " << scord << endl;
          
          consistent = false;
          break;
        }
        
        // now, check space-only constraints (for space-time meshes), if these are defined for this subcell
        if (constraints.spatialSliceConstraints != Teuchos::null)
        {
          AnnotatedEntity constrainingEntityForSpatialSlice = constraints.spatialSliceConstraints->subcellConstraints[d][scord];
          if (constrainingEntityForSpatialSlice.cellID != -1) {
            isConsistent = constraintIsConsistent(meshTopo, constrainingEntityForSpatialSlice, d, entityIndex, true);
            
          }
          if (!isConsistent)
          {
            cout << "Failed consistency test for spatial slice on cell " << cellID << ", " << CamelliaCellTools::entityTypeString(d) << " " << scord << endl;
            
            consistent = false;
            break;
          }
        }
      }
      if (!consistent) break;
    }
    if (!consistent) break;
  }
  return consistent;
}
Exemple #6
0
MeshPtr MeshTools::timeSliceMesh(MeshPtr spaceTimeMesh, double t,
                                 map<GlobalIndexType, GlobalIndexType> &sliceCellIDToSpaceTimeCellID, int H1OrderForSlice) {
  MeshTopologyPtr meshTopo = spaceTimeMesh->getTopology();
  set<IndexType> cellIDsToCheck = meshTopo->getRootCellIndices();
  set<IndexType> activeCellIDsForTime;
  
  set<IndexType> allActiveCellIDs = meshTopo->getActiveCellIndices();
  
  int spaceDim = meshTopo->getSpaceDim() - 1;  // # of true spatial dimensions
  
  MeshTopologyPtr sliceTopo = Teuchos::rcp( new MeshTopology(spaceDim) );
  set<IndexType> rootCellIDs = meshTopo->getRootCellIndices();
  for (set<IndexType>::iterator rootCellIt = rootCellIDs.begin(); rootCellIt != rootCellIDs.end(); rootCellIt++) {
    IndexType rootCellID = *rootCellIt;
    FieldContainer<double> physicalNodes = spaceTimeMesh->physicalCellNodesForCell(rootCellID);
    if (cellMatches(physicalNodes, t)) { // cell and some subset of its descendents should be included in slice mesh
      vector< vector< double > > sliceNodes = timeSliceForCell(physicalNodes, t);
      CellTopoPtrLegacy cellTopo = getBottomTopology(meshTopo, rootCellID);
      CellPtr sliceCell = sliceTopo->addCell(cellTopo, sliceNodes);
      sliceCellIDToSpaceTimeCellID[sliceCell->cellIndex()] = rootCellID;
    }
  }
  
  MeshPtr sliceMesh = Teuchos::rcp( new Mesh(sliceTopo, spaceTimeMesh->bilinearForm(), H1OrderForSlice, spaceDim) );
  
  // process refinements.  For now, we assume isotropic refinements, which means that each refinement in spacetime induces a refinement in the spatial slice
  set<IndexType> sliceCellIDsToCheckForRefinement = sliceTopo->getActiveCellIndices();
  while (sliceCellIDsToCheckForRefinement.size() > 0) {
    set<IndexType>::iterator cellIt = sliceCellIDsToCheckForRefinement.begin();
    IndexType sliceCellID = *cellIt;
    sliceCellIDsToCheckForRefinement.erase(cellIt);
    
    CellPtr sliceCell = sliceTopo->getCell(sliceCellID);
    CellPtr spaceTimeCell = meshTopo->getCell(sliceCellIDToSpaceTimeCellID[sliceCellID]);
    if (spaceTimeCell->isParent()) {
      set<GlobalIndexType> cellsToRefine;
      cellsToRefine.insert(sliceCellID);
      sliceMesh->hRefine(cellsToRefine, RefinementPattern::regularRefinementPattern(sliceCell->topology()->getKey()));
      vector<IndexType> spaceTimeChildren = spaceTimeCell->getChildIndices();
      for (int childOrdinal=0; childOrdinal<spaceTimeChildren.size(); childOrdinal++) {
        IndexType childID = spaceTimeChildren[childOrdinal];
        FieldContainer<double> childNodes = meshTopo->physicalCellNodesForCell(childID);
        if (cellMatches(childNodes, t)) {
          vector< vector<double> > childSlice = timeSliceForCell(childNodes, t);
          CellPtr childSliceCell = sliceTopo->findCellWithVertices(childSlice);
          sliceCellIDToSpaceTimeCellID[childSliceCell->cellIndex()] = childID;
          sliceCellIDsToCheckForRefinement.insert(childSliceCell->cellIndex());
        }
      }
    }
  }
  
  return sliceMesh;
}
void AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>::SetCellUsingLocationIndex(unsigned index, CellPtr pCell)
{
    // Clear the maps
    mLocationCellMap[index].clear();
    mCellLocationMap.erase(pCell.get());

    // Replace with new cell
    mLocationCellMap[index].insert(pCell);

    // Do other half of the map
    mCellLocationMap[pCell.get()] = index;
}
bool MeshTopologyTests::testCellsForEntity()
{
  bool success = true;

  // to begin, a simple test that cellsForEntity()'s side ordinals are consistent

  MeshTopologyPtr mesh2D = makeRectMesh(0.0, 0.0, 1.0, 1.0, 1, 1);
  IndexType cellID = 0;
  CellPtr cell = mesh2D->getCell(cellID); // the only cell in the mesh

  int spaceDim = mesh2D->getDimension();
  int sideDim = spaceDim - 1;

  for (int d=0; d<spaceDim; d++)
  {
    int scCount = cell->topology()->getSubcellCount(d);
    for (int scord=0; scord<scCount; scord++)
    {
      IndexType scEntityIndex = cell->entityIndex(d, scord);
      set< pair<IndexType, unsigned> > cellsContainingEntity = mesh2D->getCellsContainingEntity(d, scEntityIndex);
      vector<IndexType> sidesContainingEntity = mesh2D->getSidesContainingEntity(d, scEntityIndex);
      if (cellsContainingEntity.size() != 1)
      {
        cout << "cellsContainingEntity should have exactly one entry, but has " << cellsContainingEntity.size() << endl;
        success = false;
      }
      else
      {
        pair<IndexType, unsigned> cellEntry = *(cellsContainingEntity.begin());
//        cout << "for d " << d << ", scord " << scord << ", cell containing entity is (" << cellEntry.first << ", " << cellEntry.second << ")\n";
        if (cellEntry.first != cellID)
        {
          cout << "Expected cellEntry.first = " << cellID << ", but is " << cellEntry.first << endl;
          success = false;
        }
        else
        {
          unsigned sideOrdinal = cellEntry.second;
          IndexType sideEntityIndex = cell->entityIndex(sideDim, sideOrdinal);
          if (std::find(sidesContainingEntity.begin(), sidesContainingEntity.end(), sideEntityIndex) == sidesContainingEntity.end())
          {
            cout << "The side returned by getCellsContainingEntity() does not contain the specified entity.\n";
            success = false;
          }
        }
      }
    }
  }

  return success;
}
Exemple #9
0
void Boundary::buildLookupTables()
{
  _boundaryElements.clear();

  const set<GlobalIndexType>* rankLocalCells = &_mesh->cellIDsInPartition();
  for (GlobalIndexType cellID : *rankLocalCells)
  {
    CellPtr cell = _mesh->getTopology()->getCell(cellID);
    vector<unsigned> boundarySides = cell->boundarySides();
    for (int i=0; i<boundarySides.size(); i++)
    {
      _boundaryElements.insert(make_pair(cellID, boundarySides[i]));
    }
  }
}
void CellMutationStatesWriter<ELEMENT_DIM, SPACE_DIM>::VisitCell(CellPtr pCell, AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>* pCellPopulation)
{
    double mutation_state = pCell->GetMutationState()->GetColour();

    CellPropertyCollection collection = pCell->rGetCellPropertyCollection();
    CellPropertyCollection label_collection = collection.GetProperties<CellLabel>();

    if (label_collection.GetSize() == 1)
    {
        boost::shared_ptr<CellLabel> p_label = boost::static_pointer_cast<CellLabel>(label_collection.GetProperty());
        mutation_state = p_label->GetColour();
    }

    *this->mpOutStream << mutation_state << " ";
}
double CellMutationStatesWriter<ELEMENT_DIM, SPACE_DIM>::GetCellDataForVtkOutput(CellPtr pCell, AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>* pCellPopulation)
{
    double mutation_state = pCell->GetMutationState()->GetColour();

    CellPropertyCollection collection = pCell->rGetCellPropertyCollection();
    CellPropertyCollection label_collection = collection.GetProperties<CellLabel>();

    if (label_collection.GetSize() == 1)
    {
        boost::shared_ptr<CellLabel> p_label = boost::static_pointer_cast<CellLabel>(label_collection.GetProperty());
        mutation_state = p_label->GetColour();
    }

    return mutation_state;
}
void UpdateRadius(CellPtr pCell){
  double MaxRad = GetMaxRadius(pCell);
  double Rad = pCell->GetCellData()->GetItem("Radius");
  if(Rad<MaxRad-0.1){
    SetRadius(pCell,Rad+=GetTimestep());
  }
};
Exemple #13
0
ListPtr Parser::read_list()
{

	CellPtr head = make_cell();
	CellPtr current = head;

	m_word = m_scanner->get_word();

	ExprPtr expr;
	if (m_word.type == ")") {
		return head;
	}
	else {
		expr = read_expr();
		head->setcar(expr);

		m_word = m_scanner->get_word();
	}

	while (m_word.type != ")") {
		if (m_word.type == ".") {
			m_word = m_scanner->get_word();
			expr = read_expr();
			current->setcdr(expr);

			m_word = m_scanner->get_word();
		}
		else if (m_word.type == ")") {
			break;
		}
		else {
			expr = read_expr();
			CellPtr new_cell = make_cell();
			new_cell->setcar(expr);
			current->setcdr(new_cell);
			current = new_cell;

			m_word = m_scanner->get_word();
		}
	}

	return head;
}
void CellIdWriter<ELEMENT_DIM, SPACE_DIM>::VisitCell(CellPtr pCell, AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>* pCellPopulation)
{
    unsigned cell_id = pCell->GetCellId();
    unsigned location_index = pCellPopulation->GetLocationIndexUsingCell(pCell);
    *this->mpOutStream << " " << cell_id << " " << location_index;

    c_vector<double, SPACE_DIM> coords = pCellPopulation->GetLocationOfCellCentre(pCell);
    for (unsigned i=0; i<SPACE_DIM; i++)
    {
        *this->mpOutStream << " " << coords[i];
    }
}
void CellDataItemWriter<ELEMENT_DIM, SPACE_DIM>::VisitCell(CellPtr pCell, AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>* pCellPopulation)
{
    // Output the location index corresponding to this cell
    unsigned location_index = pCellPopulation->GetLocationIndexUsingCell(pCell);
    *this->mpOutStream << location_index << " ";

    // Output this cell's ID
    unsigned cell_id = pCell->GetCellId();
    *this->mpOutStream << cell_id << " ";

    // Output the position of this cell's centre
    c_vector<double, SPACE_DIM> centre_location = pCellPopulation->GetLocationOfCellCentre(pCell);
    for (unsigned i=0; i<SPACE_DIM; i++)
    {
        *this->mpOutStream << centre_location[i] << " ";
    }

    // Output this cell's level of mCellDataVariableName
    double value = pCell->GetCellData()->GetItem(mCellDataVariableName);
    *this->mpOutStream << value << " ";
}
void FullSpiralStc::scan(CellPtr current) {
  std::cout << "\033[1;34mcurrent-\033[0m\033[1;32mBEGIN:\033[0m " << current->get_center()->x << ","
            << current->get_center()->y << "\n";
  VectorPtr direction = (current->get_parent()->get_center() - current->get_center()) / 2 / tool_size;
  VectorPtr initial_direction = direction++;
  // Check current cell has diagonally opposite obstacles or not
  PartiallyOccupiableCellPtr c = boost::static_pointer_cast<PartiallyOccupiableCell>(current);
  Quadrant q = c->get_current_quadrant();
  Orientation orientation;
  if (q == I)
    orientation = AT_LEFT_SIDE;
  else if (q == II)
    orientation = IN_BACK;
  else if (q == III)
    orientation = AT_RIGHT_SIDE;
  else if (q == IV)
    orientation = IN_FRONT;
  c->set_quadrants_state(+q, see_obstacle(~orientation, tool_size) ? OBSTACLE : NEW);
  c->set_quadrants_state(-q, see_obstacle(~++orientation, tool_size) ? OBSTACLE : NEW);
  // While current cell has a new obstacle-free neighboring cell
  bool is_starting_cell = current == starting_cell;
  do {
    // Scan for new neighbor of current cell in counterclockwise order
    PartiallyOccupiableCellPtr neighbor = PartiallyOccupiableCellPtr(
        new PartiallyOccupiableCell(current->get_center() + direction * 2 * tool_size, 2 * tool_size));
    std::cout << "  \033[1;33mneighbor:\033[0m " << neighbor->get_center()->x << "," << neighbor->get_center()->y;
    // go_from(current, DONT_PASS, neighbor); // Full Scan-STC preparing
    if (should_go_to(neighbor, direction)) {
      // Go to free subcell of neighbor
      bool successful = go_from(current, PASS, neighbor);
      if (!successful) { // Obstacle
      } else {           // New free neighbor
        // Construct a spanning-tree edge
        neighbor->set_parent(current);
        old_cells.insert(neighbor);
        scan(neighbor);
      }
    } else {
      // Go to next subcell
      go_from(current, DONT_PASS, neighbor);
      continue;
    }
  } while (direction++ % initial_direction != (is_starting_cell ? IN_FRONT : AT_RIGHT_SIDE));
  // Back to subcell of parent
  if (!is_starting_cell) {
    go_from(current, PASS, current->get_parent());
  }
  std::cout << "\033[1;34mcurrent-\033[0m\033[1;31mEND:\033[0m " << current->get_center()->x << ","
            << current->get_center()->y << "\n";
}
Exemple #17
0
void RandomCellKiller<DIM>::CheckAndLabelSingleCellForApoptosis(CellPtr pCell)
{
    /*
     * We assume a constant time step and that there are an integer number (n = 1/dt)
     * of time steps per hour. We also assume that this method is called every time step
     * and that the probabilities of dying at different times are independent.
     *
     * Let q=mProbabilityOfDeathInAnHour and p="probability of death in a given time step".
     *
     * Probability of not dying in an hour:
     * (1-q) = (1-p)^n = (1-p)^(1/dt).
     *
     * Rearranging for p:
     * p = 1 - (1-q)^dt.
     */
    double death_prob_this_timestep = 1.0 - pow((1.0 - mProbabilityOfDeathInAnHour), SimulationTime::Instance()->GetTimeStep());

    if (!pCell->HasApoptosisBegun() &&
        RandomNumberGenerator::Instance()->ranf() < death_prob_this_timestep)
    {
        pCell->StartApoptosis();
    }
}
void AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>::RemoveCellUsingLocationIndex(unsigned index, CellPtr pCell)
{
    std::set<CellPtr>::iterator cell_iter = mLocationCellMap[index].find(pCell);

    if (cell_iter == mLocationCellMap[index].end())
    {
        EXCEPTION("Tried to remove a cell which is not attached to the given location index");
    }
    else
    {
        mLocationCellMap[index].erase(cell_iter);
        mCellLocationMap.erase(pCell.get());
    }
}
double GetMaxRadius(CellPtr pCell){
    return pCell->GetCellData()->GetItem("MaxRadius");
};
double CellDataItemWriter<ELEMENT_DIM, SPACE_DIM>::GetCellDataForVtkOutput(CellPtr pCell, AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>* pCellPopulation)
{
    double value = pCell->GetCellData()->GetItem(mCellDataVariableName);
    return value;
}
void CellBetaCateninWriter<ELEMENT_DIM, SPACE_DIM>::VisitCell(CellPtr pCell, AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>* pCellPopulation)
{
    assert(SPACE_DIM == 2);

    unsigned global_index = pCellPopulation->GetLocationIndexUsingCell(pCell);
    double x = pCellPopulation->GetLocationOfCellCentre(pCell)[0];
    double y = pCellPopulation->GetLocationOfCellCentre(pCell)[1];

    AbstractVanLeeuwen2009WntSwatCellCycleModel* p_model = dynamic_cast<AbstractVanLeeuwen2009WntSwatCellCycleModel*>(pCell->GetCellCycleModel());
    double b_cat_membrane = p_model->GetMembraneBoundBetaCateninLevel();
    double b_cat_cytoplasm = p_model->GetCytoplasmicBetaCateninLevel();
    double b_cat_nuclear = p_model->GetNuclearBetaCateninLevel();

    *this->mpOutStream << global_index << " " << x << " " << y << " " << b_cat_membrane << " " << b_cat_cytoplasm << " " << b_cat_nuclear << " ";
}
void CellProliferativePhasesWriter<ELEMENT_DIM, SPACE_DIM>::VisitCell(CellPtr pCell, AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>* pCellPopulation)
{
    double phase = pCell->GetCellCycleModel()->GetCurrentCellCyclePhase();
    *this->mpOutStream << phase << " ";
}
Exemple #23
0
MeshPtr MeshTools::timeSliceMesh(MeshPtr spaceTimeMesh, double t,
                                 map<GlobalIndexType, GlobalIndexType> &sliceCellIDToSpaceTimeCellID, int H1OrderForSlice)
{
  MeshTopology* meshTopo = dynamic_cast<MeshTopology*>(spaceTimeMesh->getTopology().get());
  TEUCHOS_TEST_FOR_EXCEPTION(!meshTopo, std::invalid_argument, "timeSliceMesh() called with spaceTimeMesh that appears to be pure MeshTopologyView.  This is not supported.");
  set<IndexType> cellIDsToCheck = meshTopo->getRootCellIndices();
  set<IndexType> activeCellIDsForTime;

  set<IndexType> allActiveCellIDs = meshTopo->getActiveCellIndices();

  int spaceDim = meshTopo->getDimension() - 1;  // # of true spatial dimensions

  MeshTopologyPtr sliceTopo = Teuchos::rcp( new MeshTopology(spaceDim) );
  set<IndexType> rootCellIDs = meshTopo->getRootCellIndices();
  for (set<IndexType>::iterator rootCellIt = rootCellIDs.begin(); rootCellIt != rootCellIDs.end(); rootCellIt++)
  {
    IndexType rootCellID = *rootCellIt;
    FieldContainer<double> physicalNodes = spaceTimeMesh->physicalCellNodesForCell(rootCellID);
    if (cellMatches(physicalNodes, t))   // cell and some subset of its descendents should be included in slice mesh
    {
      vector< vector< double > > sliceNodes = timeSliceForCell(physicalNodes, t);
      CellTopoPtr cellTopo = getBottomTopology(meshTopo, rootCellID);
      GlobalIndexType newCellID = sliceTopo->cellCount();
      CellPtr sliceCell = sliceTopo->addCell(newCellID, cellTopo, sliceNodes); // for consistency, this is only valid if run on every MPI rank.
      sliceCellIDToSpaceTimeCellID[sliceCell->cellIndex()] = rootCellID;
    }
  }

  MeshPtr sliceMesh = Teuchos::rcp( new Mesh(sliceTopo, spaceTimeMesh->bilinearForm(), H1OrderForSlice, spaceDim) );

  // process refinements.  For now, we assume isotropic refinements, which means that each refinement in spacetime induces a refinement in the spatial slice
  set<IndexType> sliceCellIDsToCheckForRefinement = sliceTopo->getActiveCellIndices();
  while (sliceCellIDsToCheckForRefinement.size() > 0)
  {
    set<IndexType>::iterator cellIt = sliceCellIDsToCheckForRefinement.begin();
    IndexType sliceCellID = *cellIt;
    sliceCellIDsToCheckForRefinement.erase(cellIt);

    CellPtr sliceCell = sliceTopo->getCell(sliceCellID);
    CellPtr spaceTimeCell = meshTopo->getCell(sliceCellIDToSpaceTimeCellID[sliceCellID]);
    if (spaceTimeCell->isParent(spaceTimeMesh->getTopology()))
    {
      set<GlobalIndexType> cellsToRefine;
      cellsToRefine.insert(sliceCellID);
      sliceMesh->hRefine(cellsToRefine, RefinementPattern::regularRefinementPattern(sliceCell->topology()));
      vector<IndexType> spaceTimeChildren = spaceTimeCell->getChildIndices(spaceTimeMesh->getTopology());
      for (int childOrdinal=0; childOrdinal<spaceTimeChildren.size(); childOrdinal++)
      {
        IndexType childID = spaceTimeChildren[childOrdinal];
        FieldContainer<double> childNodes = meshTopo->physicalCellNodesForCell(childID);
        if (cellMatches(childNodes, t))
        {
          vector< vector<double> > childSlice = timeSliceForCell(childNodes, t);
          CellPtr childSliceCell = sliceTopo->findCellWithVertices(childSlice);
          sliceCellIDToSpaceTimeCellID[childSliceCell->cellIndex()] = childID;
          sliceCellIDsToCheckForRefinement.insert(childSliceCell->cellIndex());
        }
      }
    }
  }

  MeshPartitionPolicyPtr partitionPolicy = MeshPartitionPolicy::inducedPartitionPolicy(sliceMesh, spaceTimeMesh, sliceCellIDToSpaceTimeCellID);

  sliceMesh->setPartitionPolicy(partitionPolicy);

  return sliceMesh;
}
double CellProliferativePhasesWriter<ELEMENT_DIM, SPACE_DIM>::GetCellDataForVtkOutput(CellPtr pCell, AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>* pCellPopulation)
{
    double phase = pCell->GetCellCycleModel()->GetCurrentCellCyclePhase();
    return phase;
}
bool FullSpiralStc::go_from(CellPtr current, bool need_to_pass, CellPtr next) {
  VectorPtr direction = (next->get_center() - current->get_center()) / (2 * tool_size);
  PartiallyOccupiableCellPtr c = boost::static_pointer_cast<PartiallyOccupiableCell>(current);
  PartiallyOccupiableCellPtr n = boost::static_pointer_cast<PartiallyOccupiableCell>(next);
  Quadrant quadrant = c->get_current_quadrant();
  Quadrant q;
  Quadrant q1;
  Quadrant q2;
  Quadrant q3;
  Quadrant q4;
  if (~direction == AT_RIGHT_SIDE)
    q = IV;
  else if (~direction == IN_FRONT)
    q = I;
  else if (~direction == AT_LEFT_SIDE)
    q = II;
  else if (~direction == IN_BACK)
    q = III;
  q1 = q;
  q2 = ++q;
  q3 = ++q;
  q4 = ++q;
  if (quadrant == q1 || quadrant == q2) {
    if (!see_obstacle(direction, tool_size)) {
      if (need_to_pass == DONT_PASS)
        return true;
      bool successful = visit(next, quadrant == q1 ? q4 : q3);
      std::cout << "\n";
      return successful;
    } else {
      n->set_quadrants_state(q1 ? q4 : q3, OBSTACLE);
      if (!see_obstacle(quadrant == q1 ? ++direction : --direction, tool_size)) {
        visit(current, quadrant == q1 ? q2 : q1);
        if (!see_obstacle(quadrant == q1 ? --direction : ++direction, tool_size)) {
          if (need_to_pass == DONT_PASS)
            return true;
          bool successful = visit(next, quadrant == q1 ? q3 : q4);
          std::cout << "\n";
          return successful;
        } else {
          n->set_quadrants_state(q1 ? q3 : q4, OBSTACLE);
          return false;
        }
      } else {
        c->set_quadrants_state(q1 ? q2 : q1, OBSTACLE);
        return false;
      }
    }
  } else if (quadrant == q4 || quadrant == q3) {
    if (!see_obstacle(direction, tool_size)) {
      visit(c, quadrant == q4 ? q1 : q2);
      return go_from(c, need_to_pass, next);
    } else {
      c->set_quadrants_state(quadrant == q4 ? q1 : q2, OBSTACLE);
      if (!see_obstacle(quadrant == q4 ? ++direction : --direction, tool_size)) {
        visit(c, quadrant == q4 ? q3 : q4);
        if (!see_obstacle(quadrant == q4 ? --direction : ++direction, tool_size)) {
          visit(c, quadrant == q4 ? q2 : q1);
          return go_from(c, need_to_pass, next);
        } else {
          c->set_quadrants_state(quadrant == q4 ? q2 : q1, OBSTACLE);
          return false;
        }
      } else {
        c->set_quadrants_state(quadrant == q4 ? q3 : q4, OBSTACLE);
        return false;
      }
    }
  } else
    return false;
}
double GetDistanceFromDTC(CellPtr pCell){
    return pCell->GetCellData()->GetItem("DistanceAwayFromDTC");
};
void CellCycleModelProteinConcentrationsWriter<ELEMENT_DIM, SPACE_DIM>::VisitCell(CellPtr pCell, AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>* pCellPopulation)
{
    AbstractOdeBasedCellCycleModel* p_model = dynamic_cast<AbstractOdeBasedCellCycleModel*>(pCell->GetCellCycleModel());
    if (p_model)
    {
        // Write location index corresponding to cell
        *this->mpOutStream << pCellPopulation->GetLocationIndexUsingCell(pCell) << " ";

        // Write cell variables
        std::vector<double> proteins = p_model->GetProteinConcentrations();
        for (unsigned i=0; i<proteins.size(); i++)
        {
            *this->mpOutStream << proteins[i] << " ";
        }
    }
    else
    {
        EXCEPTION("CellCycleModelProteinConcentrationsWriter cannot be used with a cell-cycle model that does not inherit from AbstractOdeBasedCellCycleModel");
    }
}
double CellIdWriter<ELEMENT_DIM, SPACE_DIM>::GetCellDataForVtkOutput(CellPtr pCell, AbstractCellPopulation<ELEMENT_DIM, SPACE_DIM>* pCellPopulation)
{
    double cell_id = pCell->GetCellId();
    return cell_id;
}
MeshPartitionPolicyPtr MeshPartitionPolicy::inducedPartitionPolicyFromRefinedMesh(MeshTopologyViewPtr inducedMeshTopo, MeshPtr inducingRefinedMesh)
{
    // generate using the inducing mesh
    vector<GlobalIndexTypeToCast> myEntries;

    auto myCellIDs = &inducingRefinedMesh->cellIDsInPartition();
    bool rotateChildOrdinalThatOwns = false; // the 6-27-16 modification -- I don't think this actually helps with load balance, the way things are presently implemented, and it may introduce additional communication costs
    if (rotateChildOrdinalThatOwns)
    {
        /*
         Modification 6-27-16: instead of assigning parent to owner of first child,
         assign parent to owner of child with ordinal equal to the level of the
         parent, modulo the number of children.  This should result in better load
         balancing for multigrid.
         */
        for (GlobalIndexType myCellID : *myCellIDs)
        {
            IndexType ancestralCellIndex = myCellID;
            bool hasMatchingChild = true;
            while (inducingRefinedMesh->getTopology()->isValidCellIndex(ancestralCellIndex)
                    && !inducedMeshTopo->isValidCellIndex(ancestralCellIndex))
            {
                CellPtr myCell = inducingRefinedMesh->getTopology()->getCell(ancestralCellIndex);
                CellPtr parent = myCell->getParent();
                TEUCHOS_TEST_FOR_EXCEPTION(parent == Teuchos::null, std::invalid_argument, "ancestor not found in inducedMeshTopo");
                int childOrdinal = parent->findChildOrdinal(myCell->cellIndex());
                int numChildren = parent->numChildren();
                hasMatchingChild = ((parent->level() % numChildren) == childOrdinal);
                ancestralCellIndex = parent->cellIndex();
            }
            if (hasMatchingChild)
            {
                myEntries.push_back(ancestralCellIndex);
                myEntries.push_back(myCellID);
            }
        }
    }
    else
    {
        // first child is always owner
        for (GlobalIndexType myCellID : *myCellIDs)
        {
            IndexType ancestralCellIndex = myCellID;
            bool isFirstChild = true;
            while (isFirstChild && !inducedMeshTopo->isValidCellIndex(ancestralCellIndex))
            {
                CellPtr myCell = inducingRefinedMesh->getTopology()->getCell(ancestralCellIndex);
                CellPtr parent = myCell->getParent();
                TEUCHOS_TEST_FOR_EXCEPTION(parent == Teuchos::null, std::invalid_argument, "ancestor not found in inducedMeshTopo");
                int childOrdinal = parent->findChildOrdinal(myCell->cellIndex());
                isFirstChild = (childOrdinal == 0);
                ancestralCellIndex = parent->cellIndex();
            }
            if (isFirstChild)
            {
                myEntries.push_back(ancestralCellIndex);
                myEntries.push_back(myCellID);
            }
        }
    }
    // all-gather the entries
    vector<GlobalIndexTypeToCast> allEntries;
    vector<int> offsets;
    MPIWrapper::allGatherVariable(*inducingRefinedMesh->Comm(), allEntries, myEntries, offsets);

    map<GlobalIndexType,GlobalIndexType> cellIDMap;
    for (int i=0; i<allEntries.size()/2; i++)
    {
        GlobalIndexType ancestralCellIndex = allEntries[2*i+0];
        GlobalIndexType inducingMeshCellID = allEntries[2*i+1];
        cellIDMap[ancestralCellIndex] = inducingMeshCellID;
    }

    return Teuchos::rcp( new InducedMeshPartitionPolicy(inducingRefinedMesh, cellIDMap) );
}
void MstcOnline::scan(CellPtr current) {
  std::string status;
  communicator->set_current_cell(current);
  // FIXME
  status = communicator->create_status_message(boost::static_pointer_cast<IdentifiableCell>(current));
  communicator->write_status_message(status);
  communicator->read_message_then_update_old_cells();
  std::cout << "\033[1;34mcurrent-\033[0m\033[1;32mBEGIN:\033[0m " << current->get_center()->x << ","
            << current->get_center()->y << "\n";
  VectorPtr direction = (current->get_parent()->get_center() - current->get_center()) / 2 / tool_size;
  VectorPtr initial_direction = direction++;
  // While current cell has a new obstacle-free neighboring cell
  bool is_starting_cell = current == starting_cell;
  do {
    // Scan for new neighbor of current cell in counterclockwise order
    IdentifiableCellPtr neighbor = IdentifiableCellPtr(new IdentifiableCell(
        current->get_center() + direction * 2 * tool_size, 2 * tool_size, communicator->get_robot_name()));
    std::cout << "  \033[1;33mneighbor:\033[0m " << neighbor->get_center()->x << "," << neighbor->get_center()->y;
    communicator->read_message_then_update_old_cells();
    if (state_of(neighbor) == OLD) { // Check neighbor with current old cells
      // Go to next sub-cell
      if (communicator->ask_other_robot_still_alive(communicator->find_robot_name(neighbor))) {
        // Still alive
        communicator->set_current_cell(current);
        go_with(++direction, tool_size);
        continue;
      } else {
        // Dead
        if (state_of(neighbor) == OLD) { // Check again neighbor with new old cells
          communicator->set_current_cell(current);
          go_with(++direction, tool_size);
          continue;
        } else {
          std::cout << "\n";
          neighbor->set_parent(current);
          communicator->read_message_then_update_old_cells();
          communicator->insert_old_cell(neighbor);
          std::string message = communicator->create_old_cells_message();
          communicator->write_old_cells_message(message);
          communicator->set_current_cell(current);
          go_with(direction++, tool_size);
          scan(neighbor);
          continue;
        }
      }
    }
    if (see_obstacle(direction, tool_size / 2)) { // Obstacle
      // Go to next sub-cell
      communicator->set_current_cell(current);
      go_with(++direction, tool_size);
    } else { // New free neighbor
      std::cout << "\n";
      // Construct a spanning-tree edge
      neighbor->set_parent(current);
      communicator->read_message_then_update_old_cells();
      communicator->insert_old_cell(neighbor);
      std::string message = communicator->create_old_cells_message();
      communicator->write_old_cells_message(message);
      communicator->set_current_cell(current);
      go_with(direction++, tool_size);
      scan(neighbor);
    }
  } while (direction % initial_direction != (is_starting_cell ? AT_LEFT_SIDE : IN_FRONT));
  // Back to sub-cell of parent
  if (!is_starting_cell) {
    communicator->set_current_cell(current);
    go_with(direction, tool_size);
  }
  std::cout << "\033[1;34mcurrent-\033[0m\033[1;31mEND:\033[0m " << current->get_center()->x << ","
            << current->get_center()->y << "\n";
}