예제 #1
0
int Tetgen::correctPolyTetraAdd(vector<int>&tet_id_buff,
                                vector<Adpt>&adpt_buff,Node* cr_nd)
{
	int i,j;
	Tetra* crtet,* nbtet;
	Node* nd0,* nd1,* nd2;
	Adpt tmp_adpt;
	const int ij0[4] = {1,2,3,0};
	const int ij1[4] = {3,3,1,1};
	const int ij2[4] = {2,0,0,2};

	//pick up surface triangle(=adpt_buff) of poly tetrahedra(polygon)(=tet_id_buff)
	i = 0;
	int n = (int)tet_id_buff.size();
	while (i < n)
	{
		crtet = getTetra(tet_id_buff[i] - 1);
		for (j = 0; j < 4; j++)
		{
			nbtet = crtet->getNeighborElement(j);
			nd0 = crtet->getNode(ij0[j]);
			nd1 = crtet->getNode(ij1[j]);
			nd2 = crtet->getNode(ij2[j]);
			if (!nbtet)
			{
				tmp_adpt.face[0] = nd0;
				tmp_adpt.face[1] = nd1;
				tmp_adpt.face[2] = nd2;
				tmp_adpt.neib = NULL;
				tmp_adpt.num = 0;
				tmp_adpt.vol = getTetraVolume(nd0,nd1,nd2,cr_nd);
				adpt_buff.push_back(tmp_adpt);
			} //if !nbtet
			else if (nbtet->getState() != 1)
			{
				tmp_adpt.face[0] = nd0;
				tmp_adpt.face[1] = nd1;
				tmp_adpt.face[2] = nd2;
				tmp_adpt.neib = nbtet;
				tmp_adpt.num = nbtet->getConection(crtet);
				tmp_adpt.vol = getTetraVolume(nd0,nd1,nd2,cr_nd);
				adpt_buff.push_back(tmp_adpt);
				if (tmp_adpt.vol < LIMIT)
				{
					tet_id_buff.push_back(nbtet->getId());
					nbtet->setState(1);
					adpt_buff.clear();
					i = -1;
					n = (int)tet_id_buff.size();
					break;
				}
			} //else if nbtet->getState() != 1
		} //for j
		i++;
	} //while i < tet_id_buff.size()

	return (int)tet_id_buff.size();
}
예제 #2
0
float FEMTetrahedronMesh::volume() const
{
    float r = 0.f;
    for(unsigned i = 0; i < m_totalTetrahedrons; i++)
        r += getTetraVolume(m_tetrahedron[i]);

    return r;
}
예제 #3
0
int Tetgen::isPossibleMerge(Node* po_nd,Node* ne_nd,deque<Tetra*>&pohang,
                            deque<Tetra*>&nehang)
{
	double vol,pre_vol,pst_vol;
	Tetra* ptet;
	Node* nd1,* nd2,* nd3;
	int edge;
	double mindens,minvolm;
	const int ij0[4] = {1,2,3,0};
	const int ij1[4] = {3,3,1,1};
	const int ij2[4] = {2,0,0,2};

	mindens = cr_crowd->getCurrentMinDensity();
	minvolm = mindens * mindens * mindens * rate_minvolm * 0.5;

	pre_vol = pst_vol = 0.;
	int n = (int)pohang.size();
	for(int i = 0; i < n; i++)
	{
		ptet = pohang[i];
		pre_vol += ptet->getVolume();
		edge = ptet->getNodeNumber(ne_nd);
		nd1 = ptet->getNode(ij0[edge]);
		nd2 = ptet->getNode(ij1[edge]);
		nd3 = ptet->getNode(ij2[edge]);
		vol = getTetraVolume(nd1,nd2,nd3,po_nd);

		printf("pr %20.15f\n",pre_vol);
		printf("%5d%5d%5d%5d\n",po_nd->getId(),nd1->getId(),nd2->getId(),
		       nd3->getId());
		printf("%20.15f\n",vol);
		//check area
		//if new area is too small( area < minvolm ), do not merge
		//but it possible to merge, if you want to do

		////if(vol < minvolm) return 0;
		if(vol < LIMIT_10)
			return 0;
		pst_vol += vol;
	}
	n = (int)nehang.size();
	for(int i = 0; i < n; i++)
	{
		ptet = nehang[i];
		pre_vol += ptet->getVolume();
	}

	printf("pre %20.15f\n",pre_vol);
	printf("pst %20.15f\n",pst_vol);
	getch();

	//if pst_vol > pre_vol(or pst_vol < pre_vol ), cannot merge
	if(fabs(pre_vol - pst_vol) > LIMIT)
		return 0;

	return 1;
}
예제 #4
0
float FEMTetrahedronMesh::getTetraVolume(Tetrahedron & tet) const
{
    Vector3F x0 = m_X[tet.indices[0]];
    Vector3F x1 = m_X[tet.indices[1]];
    Vector3F x2 = m_X[tet.indices[2]];
    Vector3F x3 = m_X[tet.indices[3]];
    Vector3F e10 = x1-x0;
	Vector3F e20 = x2-x0;
	Vector3F e30 = x3-x0;
	return getTetraVolume(e10,e20,e30);
}
예제 #5
0
int Tetgen::correctPolyTetraCut(vector<int>&tet_id_buff,
                                vector<Adpt>&adpt_buff,Node* cr_nd)
{
	int i,j;
	Tetra* crtet,* nbtet;
	Adpt tmp_adpt;
	const int ij0[4] = {1,2,3,0};
	const int ij1[4] = {3,3,1,1};
	const int ij2[4] = {2,0,0,2};
	///adpt.reserve(tet_id_buff.size()*2);

	//pick up surface triangle(=adpt_buff) of poly tetrahedra(polygon)(=tet_id_buff)
	//this part is diffarent from function Poly (other parts are almost same)
	i = 0;
	int n = (int)tet_id_buff.size();
	while (i < n)
	{
		crtet = getTetra(tet_id_buff[i] - 1);
		for (j = 0; j < 4; j++)
		{
			nbtet = crtet->getNeighborElement(j);
			if (!nbtet)
			{
				tmp_adpt.face[0] = crtet->getNode(ij0[j]);
				tmp_adpt.face[1] = crtet->getNode(ij1[j]);
				tmp_adpt.face[2] = crtet->getNode(ij2[j]);
				tmp_adpt.neib = NULL;
				tmp_adpt.num = 0;
				tmp_adpt.vol = getTetraVolume(tmp_adpt.face[0],
				                              tmp_adpt.face[1],
				                              tmp_adpt.face[2],
				                              cr_nd);
				adpt_buff.push_back(tmp_adpt);
				if(tmp_adpt.vol < LIMIT)
				{
					crtet->setState(-1);
					tet_id_buff[i] = tet_id_buff[tet_id_buff.size() - 1];
					tet_id_buff.pop_back();
					adpt_buff.clear();
					i = -1;
					n = (int)tet_id_buff.size();
					break;
				}
			} //if !nbtet
			else if (nbtet->getState() != 1)
			{
				tmp_adpt.face[0] = crtet->getNode(ij0[j]);
				tmp_adpt.face[1] = crtet->getNode(ij1[j]);
				tmp_adpt.face[2] = crtet->getNode(ij2[j]);
				tmp_adpt.neib = nbtet;
				tmp_adpt.num = nbtet->getConection(crtet);
				tmp_adpt.vol = getTetraVolume(tmp_adpt.face[0],
				                              tmp_adpt.face[1],
				                              tmp_adpt.face[2],
				                              cr_nd);
				adpt_buff.push_back(tmp_adpt);
				if (tmp_adpt.vol < LIMIT)
				{
					crtet->setState(-1);
					tet_id_buff[i] = tet_id_buff[tet_id_buff.size() - 1];
					tet_id_buff.pop_back();
					adpt_buff.clear();
					n = (int)tet_id_buff.size();
					i = -1;
					break;
				}
			} //else if nbtet->getState() != 1
		} //for j
		i++;
	} //while i < tet_id_buff.size()

	return (int)tet_id_buff.size();
}