Ejemplo n.º 1
0
bool cloth::processSimplex(std::vector<Simplex> &simplex, glm::vec3 &direction)
{
	Simplex A,B,C,D;
	glm::vec3 AB,AC,AD,AO;

	switch(simplex.size())
	{
	case 2:

		A = simplex.at(1);
		B = simplex.at(0);

		AB = B.minkowskiDifference - A.minkowskiDifference;
		AO = -A.minkowskiDifference;


		if(isSameDirection(AO,AB))
		{
			direction = glm::cross(glm::cross(AB, AO), AB);
		}
		else
		{
			direction = AO;
		}

		return false;
	case 3:

		return checkTriangle(simplex, direction);
	}
}
Ejemplo n.º 2
0
void EarClipper::CheckForEarAndUpdateVertexType(VertexList::iterator vertexIterator)
{
   if (vertexIterator->type != VertexType::Reflex)
   {
      const FVector2 *firstPoint, *secondPoint, *thirdPoint;
      GetPointsStraddlingVertex(vertexIterator, firstPoint, secondPoint, thirdPoint);

      Triangle2D_t checkTriangle(*firstPoint, *secondPoint, *thirdPoint);

      for (VertexList::iterator checkVertexIterator = vertices.begin(), end = vertices.end(); checkVertexIterator != end; ++checkVertexIterator)
      {
         if ( (checkVertexIterator->point != firstPoint) && (checkVertexIterator->point != secondPoint) && (checkVertexIterator->point != thirdPoint) )
         {
            if (checkVertexIterator->type == VertexType::Reflex)
            {
               if (checkTriangle.PointIsOnPolygon(*(checkVertexIterator->point), EXPERIMENTAL_TOLERANCE))
               {
                  vertexIterator->type = VertexType::Convex;

                  return;
               }
            } 
         }
      }

      vertexIterator->type = VertexType::Ear;
   }
}
Ejemplo n.º 3
0
/// 最近接交点の探索.
///
///  @param[in] center 計算基準点座標
///  @param[in] range  6方向毎の計算基準線分の長さ
///  @param[out] pos6  交点座標値配列
///  @param[out] bid6  境界ID配列
///  @param[out] tri6  交点ポリゴンポインタ配列
///
///  @note pos6には計算基準線分長で規格化する前の値を格納
///
void CutSearch::search(const double center[], const double range[],
                       double pos6[], BidType bid6[],
                       Triangle* tri6[]) const
{
  Vec3r min(center[X]-range[X_M], center[Y]-range[Y_M], center[Z]-range[Z_M]);
  Vec3r max(center[X]+range[X_P], center[Y]+range[Y_P], center[Z]+range[Z_P]);

  clearCutInfo(range, pos6, bid6, tri6);

  std::vector<std::string>::const_iterator pg;
  for (pg = pgList->begin(); pg != pgList->end(); ++pg) {

#ifdef CUTLIB_TIMING
    Timer::Start(SEARCH_POLYGON);
#endif

    std::vector<Triangle*>* tList = pl->search_polygons(*pg, min, max, false);

#ifdef CUTLIB_TIMING
    Timer::Stop(SEARCH_POLYGON);
#endif

    std::vector<Triangle*>::const_iterator t;
    for (t = tList->begin(); t != tList->end(); ++t) {
      int exid = (*t)->get_exid();
      if (0 < exid && exid < 256) {
        BidType bid = exid;
        checkTriangle(*t, bid, center, range, pos6, bid6, tri6);
      }
    } 

    delete tList;
  }
}
Ejemplo n.º 4
0
void AngleSkewMetric::calculateQuality ()
{
	const std::vector<MeshLib::Element*>& elements(_mesh.getElements());
	const std::size_t nElements (_mesh.getNElements());

	for (std::size_t k(0); k < nElements; k++)
	{
		Element const& elem (*elements[k]);
		switch (elem.getGeomType())
		{
		case MeshElemType::LINE:
			_element_quality_metric[k] = -1.0;
			break;
		case MeshElemType::TRIANGLE:
			_element_quality_metric[k] = checkTriangle (elem);
			break;
		case MeshElemType::QUAD:
			_element_quality_metric[k] = checkQuad (elem);
			break;
		case MeshElemType::TETRAHEDRON:
			_element_quality_metric[k] = checkTetrahedron (elem);
			break;
		case MeshElemType::HEXAHEDRON:
			_element_quality_metric[k] = checkHexahedron (elem);
			break;
		case MeshElemType::PRISM:
			_element_quality_metric[k] = checkPrism (elem);
			break;
		default:
			break;
		}
	}
}
Ejemplo n.º 5
0
void triangulate(){
   bool pit;
   pit = true;//points in triangle, assume there are points in the given tri
   unsigned int i = 0;
   vector<V3> vec;
   vector<V3> temp(Points);
   vector<double> temp1(pointsType);
   if(Points.size()>0){
      while(Points.size() > 2 && i < Points.size()){
         pit = true;
         if(Points.size() == 3){
            vec.push_back(Points.at(0)); vec.push_back(Points.at(1)); vec.push_back(Points.at(2));
            Tris.push_back(vec);
            vec.clear();
            break;
         }
         if(getPointType(i) == CONVEX){
            cout<<"CONVEX\n";
            if(i == 0)
               pit = checkTriangle(i, i + 1, Points.size() - 1, Points);
            else
               pit = checkTriangle(i, i + 1, i - 1, Points);

            if(pit){
               if(i == 0){
                  vec.push_back(Points.at(i)); vec.push_back(Points.at(i + 1)); vec.push_back(Points.at(Points.size() - 1));
                  Tris.push_back(vec);
                  vec.clear();
               }else{
                  vec.push_back(Points.at(i)); vec.push_back(Points.at(i + 1));vec.push_back(Points.at(i - 1));
                  Tris.push_back(vec);
                  vec.clear();
               }
               Points.erase (Points.begin() + i);
               pointsType.erase (pointsType.begin() + i);
            }else{
               i++;
            }
         }else{
            i++;
         }
      }
   }
   pointsType = temp1;
   Points = temp;
}
Ejemplo n.º 6
0
void EdgeRatioMetric::calculateQuality()
{
    // get all elements of mesh
    const std::vector<MeshLib::Element*>& elements(_mesh.getElements());
    const std::size_t nElements (_mesh.getNumberOfElements());
    for (std::size_t k(0); k < nElements; k++)
    {
        Element const& elem (*elements[k]);
        switch (elem.getGeomType())
        {
        case MeshElemType::LINE:
            _element_quality_metric[k] = 1.0;
            break;
        case MeshElemType::TRIANGLE: {
            _element_quality_metric[k] = checkTriangle(*elem.getNode(0), *elem.getNode(1), *elem.getNode(2));
            break;
        }
        case MeshElemType::QUAD: {
            _element_quality_metric[k] = checkQuad(*elem.getNode(0), *elem.getNode(1), *elem.getNode(2), *elem.getNode(3));
            break;
        }
        case MeshElemType::TETRAHEDRON: {
            _element_quality_metric[k] = checkTetrahedron(*elem.getNode(0), *elem.getNode(1), *elem.getNode(2), *elem.getNode(3));
            break;
        }
        case MeshElemType::PRISM: {
            std::vector<const MathLib::Point3d*> pnts;
            for (std::size_t j(0); j < 6; j++)
                pnts.push_back(elem.getNode(j));
            _element_quality_metric[k] = checkPrism(pnts);
            break;
        }
        case MeshElemType::PYRAMID: {
            std::vector<const MathLib::Point3d*> pnts;
            for (std::size_t j(0); j < 5; j++)
                pnts.push_back(elem.getNode(j));
            _element_quality_metric[k] = checkPyramid(pnts);
            break;
        }
        case MeshElemType::HEXAHEDRON: {
            std::vector<const MathLib::Point3d*> pnts;
            for (std::size_t j(0); j < 8; j++)
                pnts.push_back(elem.getNode(j));
            _element_quality_metric[k] = checkHexahedron(pnts);
            break;
        }
        default:
            ERR ("MeshQualityShortestLongestRatio::check () check for element type %s not implemented.",
                 MeshElemType2String(elem.getGeomType()).c_str());
        }
    }
}
Ejemplo n.º 7
0
int checkTriangleInequality(struct edge *sortedEdgeList,struct edgeHashTable *edgeHash)
{
	int i,v1,v2,wt,j;
	int a,b,c;
	struct edge *temp=(struct edge*)malloc(sizeof(struct edge));
	struct edge *found;
	if(numEdges==0)
	{
		return 2;
	}
	for(i=numEdges-1;i>=0;i--)
	{
		v1=sortedEdgeList[i].vertexId1;
		v2=sortedEdgeList[i].vertexId2;
		wt=sortedEdgeList[i].weight;
		for(j=1;j<=numVertices;j++)
		{
			if(j!=v1&&j!=v2)
			{
				temp->vertexId1=j;
				temp->vertexId2=v1;
				temp->weight=0;
				if((found=edgeHashSearch(edgeHash,temp))==NULL)
				{
					a=typeBWeight;			
				}
				else
					a=found->weight;
			
				temp->vertexId1=v2;
				temp->vertexId2=j;
				temp->weight=0;
				if((found=edgeHashSearch(edgeHash,temp))==NULL)
				{
					b=typeBWeight;
				}
				else
					b=found->weight;
			
				c=wt;
				if(checkTriangle(a,b,c)==1)
				{
					printf("\n%s %s %s does not form a triangle",vertices[v1],vertices[v2],vertices[j]);
					return 1;
				}
			}
		}
	}
	return 0;
		
}
Ejemplo n.º 8
0
void MeshQualityShortestLongestRatio::check()
{
	// get all elements of mesh
	const std::vector<MeshLib::Element*>& elements(_mesh->getElements());
	const size_t nElements (_mesh->getNElements());
	for (size_t k(0); k < nElements; k++)
	{
		const Element* elem (elements[k]);
		switch (elem->getType())
		{
		case MshElemType::EDGE:
			_mesh_quality_measure[k] = 1.0;
			break;
		case MshElemType::TRIANGLE: {
			_mesh_quality_measure[k] = checkTriangle(elem->getNode(0), elem->getNode(1), elem->getNode(2));
			break;
		}
		case MshElemType::QUAD: {
			_mesh_quality_measure[k] = checkQuad(elem->getNode(0), elem->getNode(1), elem->getNode(2), elem->getNode(3));
			break;
		}
		case MshElemType::TETRAHEDRON: {
			_mesh_quality_measure[k] = checkTetrahedron(elem->getNode(0), elem->getNode(1), elem->getNode(2), elem->getNode(3));
			break;
		}
		case MshElemType::PRISM: {
			std::vector<const GeoLib::Point*> pnts;
			for (size_t j(0); j < 6; j++)
				pnts.push_back(elem->getNode(j));
			_mesh_quality_measure[k] = checkPrism(pnts);
			break;
		}
		case MshElemType::HEXAHEDRON: {
			std::vector<const GeoLib::Point*> pnts;
			for (size_t j(0); j < 8; j++)
				pnts.push_back(elem->getNode(j));
			_mesh_quality_measure[k] = checkHexahedron(pnts);
			break;
		}
		default:
			std::cout << "MeshQualityShortestLongestRatio::check () check for element type "
			          << MshElemType2String(elem->getType())
			          << " not implemented" << std::endl;
		}
	}
}
Ejemplo n.º 9
0
extern "C" void
driver(void)
{
  int ignored;
  int i, count;  
  int myChunk=FEM_My_partition();
  
  /*Add a refinement object to FEM array*/
  CkPrintf("[%d] begin init\n",myChunk);
  FEM_REFINE2D_Init();
  CkPrintf("[%d] end init\n",myChunk);
  
  myGlobals g;
  FEM_Register(&g,(FEM_PupFn)pup_myGlobals);
  init_myGlobal(&g);
  
  g.nnodes = FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_NODE);
  int maxNodes = g.nnodes;
  g.maxnodes=2*maxNodes;
  g.m_i_fid=FEM_Create_field(FEM_DOUBLE,1,0,sizeof(double));
  resize_nodes((void *)&g,&g.nnodes,&maxNodes);
  int nghost=0;
  g.nelems=FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_ELEM);
  g.maxelems=g.nelems;
  resize_elems((void *)&g,&g.nelems,&g.maxelems);

  FEM_REFINE2D_Newmesh(FEM_Mesh_default_read(),FEM_NODE,FEM_ELEM);
  
  //Initialize associated data
  for (i=0;i<g.maxnodes;i++) {
    g.R_net[i]=g.d[i]=g.v[i]=g.a[i]=vector2d(0.0);
  }
  
  //Apply a small initial perturbation to positions
  for (i=0;i<g.nnodes;i++) {
    const double max=1.0e-15/15.0; //Tiny perturbation
    g.d[i].x+=max*(i&15);
    g.d[i].y+=max*((i+5)&15);
  }
  
  int fid=FEM_Create_field(FEM_DOUBLE,2,0,sizeof(vector2d));
  
  for (i=0;i<g.nelems;i++){
    checkTriangle(g,i);
  }	
  sleep(5);
  //Timeloop
  if (CkMyPe()==0){
    CkPrintf("Entering timeloop\n");
  }	
  //  int tSteps=0x70FF00FF;
  int tSteps=4;
  int z=13;
  calcMasses(g);
  double startTime=CkWallTimer();
  double curArea=2.5e-5/1024;
  int t = 0;

  // THIS IS THE INITIAL MESH SENT TO NetFEM
  if (1) { //Publish data to the net
    publishMeshToNetFEM(g,myChunk,t);
  }
  double desiredArea;
  /* 
  //should not be necessary as it would have been set in the init
  for (i=0; i<g.nnodes; i++) {
    g.validNode[i] = 1;
  }
  for (i=0; i<g.nelems; i++) {
    g.validElem[i] = 1;
  }*/
  double avgArea = 0.0;
  for (i=0;i<g.nelems;i++) {
    avgArea += calcArea(g, i);
  }
  avgArea /= g.nelems;
  for (t=1;t<=tSteps;t++) {
    /*    if (1) { //Structural mechanics
    //Compute forces on nodes exerted by elements
    CST_NL(g.coord,g.conn,g.R_net,g.d,matConst,g.nnodes,g.nelems,g.S11,g.S22,g.S12);
    //Communicate net force on shared nodes
    FEM_Update_field(fid,g.R_net);
    //Advance node positions
    advanceNodes(dt,g.nnodes,g.coord,g.R_net,g.a,g.v,g.d,g.m_i,(t%4)==0);
    }*/
    
    //Debugging/perf. output
    double curTime=CkWallTimer();
    double total=curTime-startTime;
    startTime=curTime;
    vector2d *loc;
    double *areas;
	
    // prepare to coarsen
    loc=new vector2d[2*g.nnodes];
    for (i=0;i<g.nnodes;i++) {
      loc[i]=g.coord[i];//+g.d[i];
    }
    areas=new double[g.nelems];
    for (i=0;i<g.nelems;i++) {
      areas[i] = avgArea;
    }
    //coarsen one element at a time
    //int coarseIdx = (23  + 4*t)%g.nnodes;
    //areas[coarseIdx] = calcArea(g,coarseIdx)*2.5;
    
    CkPrintf("[%d] Starting coarsening step: %d nodes, %d elements\n", myChunk,countValidEntities(g.validNode,g.nnodes),countValidEntities(g.validElem,g.nelems));
    FEM_REFINE2D_Coarsen(FEM_Mesh_default_read(),FEM_NODE,(double *)g.coord,FEM_ELEM,areas,FEM_SPARSE);
    repeat_after_split((void *)&g);
    g.nelems = FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_ELEM);
    g.nnodes = FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_NODE);
    CkPrintf("[%d] Done with coarsening step: %d nodes, %d elements\n",
	     myChunk,countValidEntities(g.validNode,g.nnodes),countValidEntities(g.validElem,g.nelems));
    delete [] loc;
    delete[] areas;
    // THIS IS THE COARSENED MESH SENT TO NetFEM
    if (1) { //Publish data to the net
      publishMeshToNetFEM(g,myChunk,2*t-1);
    }

    //prepare to refine
    loc=new vector2d[2*g.nnodes];
    for (i=0;i<g.nnodes;i++) {
      loc[i]=g.coord[i];//+g.d[i];
    }
    
    areas=new double[g.nelems];
    for (i=0;i<g.nelems;i++) {
      areas[i] = avgArea;
    }
    //refine one element at a time
    //int refIdx = (13  + 3*t)%g.nnodes;
    //areas[refIdx] = calcArea(g,refIdx)/1.5;
    
    CkPrintf("[%d] Starting refinement step: %d nodes, %d elements\n", myChunk,countValidEntities(g.validNode,g.nnodes),countValidEntities(g.validElem,g.nelems));
    FEM_REFINE2D_Split(FEM_Mesh_default_read(),FEM_NODE,(double *)loc,FEM_ELEM,areas,FEM_SPARSE);
    repeat_after_split((void *)&g);
    
    g.nelems = FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_ELEM);
    g.nnodes = FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_NODE);
    CkPrintf("[%d] Done with refinement step: %d nodes, %d elements\n",
	     myChunk,countValidEntities(g.validNode,g.nnodes),countValidEntities(g.validElem,g.nelems));
    delete [] loc;
    delete[] areas;
    // THIS IS THE REFINED MESH SENT TO NetFEM
    if (1) { //Publish data to the net
      publishMeshToNetFEM(g,myChunk,2*t);
    }
  }
  if (CkMyPe()==0)
    CkPrintf("Driver finished\n");
}
Ejemplo n.º 10
0
EarClipper::VertexList::iterator EarClipper::DetermineMutuallyVisibleVertexFromRayCastResult(const FVector2& maxInteriorPoint, const FVector2& intersectionPointOnEdge, VertexList::iterator pointOnEdgeWithMaximumXIter)
{
   VertexList::iterator verticesEnd = vertices.end();

   VertexList::iterator mutuallyVisibleVertexIter = verticesEnd;

   // Form a triangle with P (see explanation of a) above) (P1), the intersection point on
   // the edge (P2) and the point on the edge with maximum X (P3).
   //
   // If no points on the outer polygon fall on this triangle, then P3 is the visible vertex.
   //
   // Otherwise, the reflex vertex of the outer polygon that falls into this triangle and
   // minimizes the angle to the ray (i.e. x axis) is the mutually visible vertex

   Triangle2D_t checkTriangle(maxInteriorPoint, intersectionPointOnEdge, *(pointOnEdgeWithMaximumXIter->point));

   VertexListIteratorList reflexVerticesOnTriangle;
   bool hasAnyReflexVerticesOnTriangle = false;

   for (VertexList::iterator vertexIterator = vertices.begin(); vertexIterator != verticesEnd; ++vertexIterator)
   {
      if (checkTriangle.PointIsOnPolygon(*(vertexIterator->point), EXPERIMENTAL_TOLERANCE))
      {
         if (GetConvexOrReflexVertexType(vertexIterator) == VertexType::Reflex)
         {
            reflexVerticesOnTriangle.push_front(vertexIterator);
            hasAnyReflexVerticesOnTriangle = true;
         }
      }
   }

   if (hasAnyReflexVerticesOnTriangle)
   {
      mutuallyVisibleVertexIter = reflexVerticesOnTriangle.front();
      reflexVerticesOnTriangle.pop_front();

      float minDistance = DistanceBetween(*(mutuallyVisibleVertexIter->point), maxInteriorPoint);
      float minAngle = AngleBetweenRadians(*(mutuallyVisibleVertexIter->point) - maxInteriorPoint, Vec2D::XAxis() );

      for (const VertexList::iterator& reflexVertexIter : reflexVerticesOnTriangle)
      {
         float angle = AngleBetweenRadians(*(reflexVertexIter->point) - maxInteriorPoint, Vec2D::XAxis() );
         float distance = DistanceBetween(*(reflexVertexIter->point), maxInteriorPoint);

         if (angle < minAngle)
         {
            minAngle = angle;
            mutuallyVisibleVertexIter = reflexVertexIter;

            minDistance = distance;
         }
         else if (angle == minAngle)
         {
            if (distance < minDistance)
            {
               minAngle = angle;
               mutuallyVisibleVertexIter = reflexVertexIter;

               minDistance = distance;
            }
         }
      }
   }
   else
   {
      mutuallyVisibleVertexIter = pointOnEdgeWithMaximumXIter;
   }

   return mutuallyVisibleVertexIter;
}
Ejemplo n.º 11
0
// uses ear-clipping method, so won't work on polygons with holes, and is relatively slow at O(n^2)
// assumes size of _shape is at least 3
std::vector<std::vector<Util::Vector>> SteerLib::GJK_EPA::decompose(std::vector<Util::Vector> _shape)
{
	// list of triangles that _shape decomposed into
	std::vector<std::vector<Util::Vector>> triangleList;

	// temporary shape that can be modified
	std::vector<Util::Vector> tempShape = _shape;

	int count = crossProductCount(_shape);
	
	// if absolute value of count is same as size of shape, then shape is convex
	if (std::abs(count) == _shape.size()) {
		triangleList.push_back(_shape);
		return triangleList;
	}

	bool isCCW;

	// if count > 0, shape is ordered ccw
	if (count > 0) {
		isCCW = true;
	}
	// if count < 0, shape is ordered cw
	else if (count < 0) {
		isCCW = false;
	}

	// start the search at any point
	int shapePos = 0;

	// loop until there are only 3 points left in tempShape
	// the loop will find ears in tempShape, and remove the ear, so the number of points in tempShape slowly decreases
	while (tempShape.size() > 0) {
		
		// if shapePos reaches the end, loop back to the beginning
		if (shapePos == tempShape.size()) {
			shapePos = 0;
		}

		// get the first point, and the two points adjacent to it
		Util::Vector point = tempShape.at(shapePos);

		// get the predecessor, if shapePos is 0, get the back of tempShape
		Util::Vector predecessor;
		if (shapePos == 0) {
			predecessor = tempShape.back();
		}
		else {
			predecessor = tempShape.at(shapePos - 1);
		}

		// get the predecessor, if shapePos is the end, get the front of tempShape
		Util::Vector successor;
		if (shapePos == tempShape.size()-1) {
			successor = tempShape.front();
		}
		else {
			successor = tempShape.at(shapePos + 1);
		}

		// find the angle of the first point
		Util::Vector line1 = predecessor - point;
		Util::Vector line2 = successor - point;
		float angle = findAngle(line1, line2);
		
		bool angleBool;
		// if shape is ccw, angles less than pi are positive
		if (isCCW) {
			angleBool = angle < M_PI && angle > 0;
		}
		// if shape is cw, angles less than pi are negative
		else {
			angleBool = angle > -M_PI && angle < 0;
		}

		// if the angle is less than pi, it is possible for an ear to exist
		if (angleBool) {
			// make another temporary shape that does not include the point and it's adjacent points
			std::vector<Util::Vector> triangleShape = tempShape;

			int remove = indexOf(triangleShape, predecessor);
			triangleShape.erase(triangleShape.begin() + remove);
			remove = indexOf(triangleShape, point);
			triangleShape.erase(triangleShape.begin() + remove);
			remove = indexOf(triangleShape, successor);
			triangleShape.erase(triangleShape.begin() + remove);

			// check if any points in tempShape are in the triangle formed by the point and it's adjacent points
			// if no points are in the triangle, then the point and it's adjacent points form an ear
			if (!checkTriangle(triangleShape, predecessor, point, successor)) {
				// construct the ear
				std::vector<Util::Vector> ear;
				ear.push_back(predecessor);
				ear.push_back(point);
				ear.push_back(successor);

				// add the ear to the list of decomposed triangles
				triangleList.push_back(ear);

				// remove the point from tempShape since no other triangles in the decomposition can use it
				remove = indexOf(tempShape, point);
				tempShape.erase(tempShape.begin() + remove);
			}
			// there is another point inside the triangle, so it's not an ear
			// move on to the next position
			else {
				shapePos++;
			}

		}
		// if the angle is pi, then the point and it's adjacent points forms a line
		// the point can be removed from tempShape
		else if (angle == M_PI || angle == -M_PI) {
			int remove = indexOf(tempShape, point);
			tempShape.erase(tempShape.begin() + remove);
		}
		// if the angle is greater than pi, it can't be an ear
		// move on to the next position
		else {
			shapePos++;
		}

		if (tempShape.size() == 3) {
			// since there are only 3 points left in tempShape, it must form a triangle in the decomposition
			triangleList.push_back(tempShape);
			tempShape.clear();
		}

	}
	

	
	for (int i = 0; i < triangleList.size(); i++) {
		std::cout << "triangle " << i << "\n";
		for (int j = 0; j < triangleList.at(i).size(); j++) {
			std::cout << "point " << triangleList.at(i).at(j) << "\n";
		}
	}
	

	return triangleList;
}
Ejemplo n.º 12
0
extern "C" void
driver(void)
{
  int ignored;
  int i;  
  int myChunk=FEM_My_partition();

/*Add a refinement object to FEM array*/
CkPrintf("[%d] begin init\n",myChunk);
  FEM_REFINE2D_Init();
CkPrintf("[%d] end init\n",myChunk);

  myGlobals g;
  FEM_Register(&g,(FEM_PupFn)pup_myGlobals);

	init_myGlobal(&g);
  
 	g.nnodes = FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_NODE);
	int maxNodes = g.nnodes;
  g.maxnodes=2*maxNodes;
  
	g.m_i_fid=FEM_Create_field(FEM_DOUBLE,1,0,sizeof(double));

	
	resize_nodes((void *)&g,&g.nnodes,&maxNodes);
  
	
	int nghost=0;
  
	g.nelems=FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_ELEM);
  g.maxelems=g.nelems;

	resize_elems((void *)&g,&g.nelems,&g.maxelems);
	
	g.nedges = FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_SPARSE);
	g.maxedges = g.nedges;
	resize_edges((void *)&g,&g.nedges,&g.maxedges);

	FEM_REFINE2D_Newmesh(FEM_Mesh_default_read(),FEM_NODE,FEM_ELEM);
  
  
  //Initialize associated data
  for (i=0;i<g.maxnodes;i++){
    g.R_net[i]=g.d[i]=g.v[i]=g.a[i]=vector2d(0.0);
	}

//Apply a small initial perturbation to positions
  for (i=0;i<g.nnodes;i++) {
	  const double max=1.0e-15/15.0; //Tiny perturbation
	  g.d[i].x+=max*(i&15);
	  g.d[i].y+=max*((i+5)&15);
  }

  int fid=FEM_Create_field(FEM_DOUBLE,2,0,sizeof(vector2d));
  
  for (i=0;i<g.nelems;i++){
    checkTriangle(g,i);
	}	

  //Timeloop
  if (CkMyPe()==0){
    CkPrintf("Entering timeloop\n");
	}	
  int tSteps=0x70FF00FF;
  calcMasses(g);
  double startTime=CkWallTimer();
  double curArea=2.0e-5;
  for (int t=0;t<tSteps;t++) {
    if (1) { //Structural mechanics
    	//Compute forces on nodes exerted by elements
			CST_NL(g.coord,g.conn,g.R_net,g.d,matConst,g.nnodes,g.nelems,g.S11,g.S22,g.S12);
	
	    //Communicate net force on shared nodes
			FEM_Update_field(fid,g.R_net);

	    //Advance node positions
			advanceNodes(dt,g.nnodes,g.coord,g.R_net,g.a,g.v,g.d,g.m_i,(t%4)==0);
    
    }

    //Debugging/perf. output
    double curTime=CkWallTimer();
    double total=curTime-startTime;
    startTime=curTime;
    if (CkMyPe()==0 && (t%64==0))
	    CkPrintf("%d %.6f sec for loop %d \n",CkNumPes(),total,t);
 /*   if (0 && t%16==0) {
	    CkPrintf("    Triangle 0:\n");
	    for (int j=0;j<3;j++) {
		    int n=g.conn[0][j];
		    CkPrintf("    Node %d: coord=(%.4f,%.4f)  d=(%.4g,%.4g)\n",
			     n,g.coord[n].x,g.coord[n].y,g.d[n].x,g.d[n].y);
	    }
    }*/
//    if (t%512==0)
//      FEM_Migrate();

    if (t%128==0) { //Refinement:
      vector2d *loc=new vector2d[2*g.nnodes];
      for (i=0;i<g.nnodes;i++) {
				loc[i]=g.coord[i];//+g.d[i];
      }
      double *areas=new double[g.nelems];
      curArea=curArea*0.98;
      for (i=0;i<g.nelems;i++) {
      #if 0
        double origArea=8e-8; //Typical triangle size
	if (fabs(g.S12[i])>1.0e8)
		areas[i]=origArea*0.9; //Refine stuff that's stressed
	else
		areas[i]=origArea; //Leave everything else big
      #endif
        areas[i]=curArea;
      }
      
      CkPrintf("[%d] Starting refinement step: %d nodes, %d elements to %.3g\n",
	       myChunk,g.nnodes,g.nelems,curArea);
			
			FEM_REFINE2D_Split(FEM_Mesh_default_read(),FEM_NODE,(double *)loc,FEM_ELEM,areas,FEM_SPARSE);
			repeat_after_split((void *)&g);

			
      g.nelems = FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_ELEM);
			g.nnodes = FEM_Mesh_get_length(FEM_Mesh_default_read(),FEM_NODE);
             
      CkPrintf("[%d] Done with refinement step: %d nodes, %d elements\n",
	       myChunk,g.nnodes,g.nelems);
      
    }
    
    if (1) { //Publish data to the net
	    NetFEM n=NetFEM_Begin(myChunk,t,2,NetFEM_POINTAT);
	    
	    NetFEM_Nodes(n,g.nnodes,(double *)g.coord,"Position (m)");
	    NetFEM_Vector(n,(double *)g.d,"Displacement (m)");
	    NetFEM_Vector(n,(double *)g.v,"Velocity (m/s)");
	    
	    NetFEM_Elements(n,g.nelems,3,(int *)g.conn,"Triangles");
		NetFEM_Scalar(n,g.S11,1,"X Stress (pure)");
		NetFEM_Scalar(n,g.S22,1,"Y Stress (pure)");
		NetFEM_Scalar(n,g.S12,1,"Shear Stress (pure)");
	    
	    NetFEM_End(n);
    }
  }

  if (CkMyPe()==0)
    CkPrintf("Driver finished\n");
}