void highOrderTools::computeStraightSidedPositions() { _clean(); // compute straigh sided positions that are actually X,Y,Z positions // that are NOT always on curves and surfaces // points classified on model vertices shall not move ! for(GModel::viter it = _gm->firstVertex(); it != _gm->lastVertex(); ++it){ if ((*it)->points.size()){ MPoint *p = (*it)->points[0]; MVertex *v = p->getVertex(0); _straightSidedLocation [v] = SVector3((*it)->x(),(*it)->y(),(*it)->z()); _targetLocation [v] = SVector3((*it)->x(),(*it)->y(),(*it)->z()); } } // printf("coucou2\n"); // compute stright sided positions of vertices that are classified on model edges for(GModel::eiter it = _gm->firstEdge(); it != _gm->lastEdge(); ++it){ for (unsigned int i=0;i<(*it)->lines.size();i++){ MLine *l = (*it)->lines[i]; int N = l->getNumVertices()-2; SVector3 p0((*it)->lines[i]->getVertex(0)->x(), (*it)->lines[i]->getVertex(0)->y(), (*it)->lines[i]->getVertex(0)->z()); SVector3 p1((*it)->lines[i]->getVertex(1)->x(), (*it)->lines[i]->getVertex(1)->y(), (*it)->lines[i]->getVertex(1)->z()); for (int j=1;j<=N;j++){ const double xi = (double)(j)/(N+1); // printf("xi = %g\n",xi); const SVector3 straightSidedPoint = p0 *(1.-xi) + p1*xi; MVertex *v = (*it)->lines[i]->getVertex(j+1); if (_straightSidedLocation.find(v) == _straightSidedLocation.end()){ _straightSidedLocation [v] = straightSidedPoint; _targetLocation[v] = SVector3(v->x(),v->y(),v->z()); } } } } // printf("coucou3\n"); // compute stright sided positions of vertices that are classified on model faces for(GModel::fiter it = _gm->firstFace(); it != _gm->lastFace(); ++it){ for (unsigned int i=0;i<(*it)->mesh_vertices.size();i++){ MVertex *v = (*it)->mesh_vertices[i]; _targetLocation[v] = SVector3(v->x(),v->y(),v->z()); } for (unsigned int i=0;i<(*it)->triangles.size();i++){ MTriangle *t = (*it)->triangles[i]; MFace face = t->getFace(0); const nodalBasis* fs = t->getFunctionSpace(); for (int j=0;j<t->getNumVertices();j++){ if (t->getVertex(j)->onWhat() == *it){ const double t1 = fs->points(j, 0); const double t2 = fs->points(j, 1); SPoint3 pc = face.interpolate(t1, t2); _straightSidedLocation [t->getVertex(j)] = SVector3(pc.x(),pc.y(),pc.z()); } } } for (unsigned int i=0;i<(*it)->quadrangles.size();i++){ // printf("coucou quad %d\n",i); MQuadrangle *q = (*it)->quadrangles[i]; MFace face = q->getFace(0); const nodalBasis* fs = q->getFunctionSpace(); for (int j=0;j<q->getNumVertices();j++){ if (q->getVertex(j)->onWhat() == *it){ const double t1 = fs->points(j, 0); const double t2 = fs->points(j, 1); SPoint3 pc = face.interpolate(t1, t2); _straightSidedLocation [q->getVertex(j)] = SVector3(pc.x(),pc.y(),pc.z()); } } } } for(GModel::riter it = _gm->firstRegion(); it != _gm->lastRegion(); ++it){ for (unsigned int i=0;i<(*it)->mesh_vertices.size();i++){ MVertex *v = (*it)->mesh_vertices[i]; _targetLocation[v] = SVector3(v->x(),v->y(),v->z()); } for (unsigned int i=0;i<(*it)->tetrahedra.size();i++){ _dim = 3; MTetrahedron *t = (*it)->tetrahedra[i]; MTetrahedron t_1 ((*it)->tetrahedra[i]->getVertex(0), (*it)->tetrahedra[i]->getVertex(1), (*it)->tetrahedra[i]->getVertex(2), (*it)->tetrahedra[i]->getVertex(3)); const nodalBasis* fs = t->getFunctionSpace(); for (int j=0;j<t->getNumVertices();j++){ if (t->getVertex(j)->onWhat() == *it){ double t1 = fs->points(j, 0); double t2 = fs->points(j, 1); double t3 = fs->points(j, 2); SPoint3 pc; t_1.pnt(t1, t2, t3,pc); _straightSidedLocation [t->getVertex(j)] = SVector3(pc.x(),pc.y(),pc.z()); } } } for (unsigned int i=0;i<(*it)->hexahedra.size();i++){ _dim = 3; MHexahedron *h = (*it)->hexahedra[i]; MHexahedron h_1 ((*it)->hexahedra[i]->getVertex(0), (*it)->hexahedra[i]->getVertex(1), (*it)->hexahedra[i]->getVertex(2), (*it)->hexahedra[i]->getVertex(3), (*it)->hexahedra[i]->getVertex(4), (*it)->hexahedra[i]->getVertex(5), (*it)->hexahedra[i]->getVertex(6), (*it)->hexahedra[i]->getVertex(7)); const nodalBasis* fs = h->getFunctionSpace(); for (int j=0;j<h->getNumVertices();j++){ if (h->getVertex(j)->onWhat() == *it){ double t1 = fs->points(j, 0); double t2 = fs->points(j, 1); double t3 = fs->points(j, 2); SPoint3 pc; h_1.pnt(t1, t2, t3,pc); _straightSidedLocation [h->getVertex(j)] = SVector3(pc.x(),pc.y(),pc.z()); } } } } Msg::Info("highOrderTools has been set up : %d nodes are considered", _straightSidedLocation.size()); }
static void Subdivide(GRegion *gr, bool splitIntoHexas, faceContainer &faceVertices) { if(!splitIntoHexas){ std::vector<MTetrahedron*> tetrahedra2; for(unsigned int i = 0; i < gr->tetrahedra.size(); i++){ MTetrahedron *t = gr->tetrahedra[i]; if(t->getNumVertices() == 10){ tetrahedra2.push_back (new MTetrahedron(t->getVertex(0), t->getVertex(4), t->getVertex(7), t->getVertex(6))); tetrahedra2.push_back (new MTetrahedron(t->getVertex(1), t->getVertex(4), t->getVertex(5), t->getVertex(9))); tetrahedra2.push_back (new MTetrahedron(t->getVertex(2), t->getVertex(5), t->getVertex(6), t->getVertex(8))); tetrahedra2.push_back (new MTetrahedron(t->getVertex(3), t->getVertex(7), t->getVertex(9), t->getVertex(8))); tetrahedra2.push_back (new MTetrahedron(t->getVertex(5), t->getVertex(8), t->getVertex(7), t->getVertex(9))); tetrahedra2.push_back (new MTetrahedron(t->getVertex(5), t->getVertex(7), t->getVertex(4), t->getVertex(9))); tetrahedra2.push_back (new MTetrahedron(t->getVertex(7), t->getVertex(8), t->getVertex(5), t->getVertex(6))); tetrahedra2.push_back (new MTetrahedron(t->getVertex(4), t->getVertex(7), t->getVertex(5), t->getVertex(6))); } delete t; } gr->tetrahedra = tetrahedra2; } std::vector<MHexahedron*> hexahedra2; for(unsigned int i = 0; i < gr->hexahedra.size(); i++){ MHexahedron *h = gr->hexahedra[i]; if(h->getNumVertices() == 27){ hexahedra2.push_back (new MHexahedron(h->getVertex(0), h->getVertex(8), h->getVertex(20), h->getVertex(9), h->getVertex(10), h->getVertex(21), h->getVertex(26), h->getVertex(22))); hexahedra2.push_back (new MHexahedron(h->getVertex(10), h->getVertex(21), h->getVertex(26), h->getVertex(22), h->getVertex(4), h->getVertex(16), h->getVertex(25), h->getVertex(17))); hexahedra2.push_back (new MHexahedron(h->getVertex(8), h->getVertex(1), h->getVertex(11), h->getVertex(20), h->getVertex(21), h->getVertex(12), h->getVertex(23), h->getVertex(26))); hexahedra2.push_back (new MHexahedron(h->getVertex(21), h->getVertex(12), h->getVertex(23), h->getVertex(26), h->getVertex(16), h->getVertex(5), h->getVertex(18), h->getVertex(25))); hexahedra2.push_back (new MHexahedron(h->getVertex(9), h->getVertex(20), h->getVertex(13), h->getVertex(3), h->getVertex(22), h->getVertex(26), h->getVertex(24), h->getVertex(15))); hexahedra2.push_back (new MHexahedron(h->getVertex(22), h->getVertex(26), h->getVertex(24), h->getVertex(15), h->getVertex(17), h->getVertex(25), h->getVertex(19), h->getVertex(7))); hexahedra2.push_back (new MHexahedron(h->getVertex(20), h->getVertex(11), h->getVertex(2), h->getVertex(13), h->getVertex(26), h->getVertex(23), h->getVertex(14), h->getVertex(24))); hexahedra2.push_back (new MHexahedron(h->getVertex(26), h->getVertex(23), h->getVertex(14), h->getVertex(24), h->getVertex(25), h->getVertex(18), h->getVertex(6), h->getVertex(19))); } delete h; } if(splitIntoHexas){ for(unsigned int i = 0; i < gr->tetrahedra.size(); i++){ MTetrahedron *t = gr->tetrahedra[i]; if(t->getNumVertices() == 10){ std::vector<MVertex*> newv; for(int j = 0; j < t->getNumFaces(); j++){ MFace face = t->getFace(j); faceContainer::iterator fIter = faceVertices.find(face); if (fIter != faceVertices.end()){ newv.push_back(fIter->second[0]); } else{ SPoint3 pc = face.barycenter(); newv.push_back(new MVertex(pc.x(), pc.y(), pc.z(), gr)); faceVertices[face].push_back(newv.back()); gr->mesh_vertices.push_back(newv.back()); } } SPoint3 pc = t->barycenter(); newv.push_back(new MVertex(pc.x(), pc.y(), pc.z(), gr)); gr->mesh_vertices.push_back(newv.back()); hexahedra2.push_back (new MHexahedron(t->getVertex(0), t->getVertex(4), newv[0], t->getVertex(6), t->getVertex(7), newv[1], newv[4], newv[2])); hexahedra2.push_back (new MHexahedron(t->getVertex(4), t->getVertex(1), t->getVertex(5), newv[0], newv[1], t->getVertex(9), newv[3], newv[4])); hexahedra2.push_back (new MHexahedron(t->getVertex(6), newv[0], t->getVertex(5), t->getVertex(2), newv[2], newv[4], newv[3], t->getVertex(8))); hexahedra2.push_back (new MHexahedron(t->getVertex(3), t->getVertex(9), newv[1], t->getVertex(7), t->getVertex(8), newv[3], newv[4], newv[2])); delete t; } } gr->tetrahedra.clear(); for(unsigned int i = 0; i < gr->prisms.size(); i++){ MPrism *p = gr->prisms[i]; if(p->getNumVertices() == 18){ std::vector<MVertex*> newv; for(int j = 0; j < 2; j++){ MFace face = p->getFace(j); faceContainer::iterator fIter = faceVertices.find(face); if (fIter != faceVertices.end()){ newv.push_back(fIter->second[0]); } else{ SPoint3 pc = face.barycenter(); newv.push_back(new MVertex(pc.x(), pc.y(), pc.z(), gr)); faceVertices[face].push_back(newv.back()); gr->mesh_vertices.push_back(newv.back()); } } SPoint3 pc = p->barycenter(); newv.push_back(new MVertex(pc.x(), pc.y(), pc.z(), gr)); gr->mesh_vertices.push_back(newv.back()); hexahedra2.push_back (new MHexahedron(p->getVertex(0), p->getVertex(6), newv[0], p->getVertex(7), p->getVertex(8), p->getVertex(15), newv[2], p->getVertex(16))); hexahedra2.push_back (new MHexahedron(p->getVertex(1), p->getVertex(9), newv[0], p->getVertex(6), p->getVertex(10), p->getVertex(17), newv[2], p->getVertex(15))); hexahedra2.push_back (new MHexahedron(p->getVertex(2), p->getVertex(7), newv[0], p->getVertex(9), p->getVertex(11), p->getVertex(16), newv[2], p->getVertex(17))); hexahedra2.push_back (new MHexahedron(p->getVertex(8), p->getVertex(15), newv[2], p->getVertex(16), p->getVertex(3), p->getVertex(12), newv[1], p->getVertex(13))); hexahedra2.push_back (new MHexahedron(p->getVertex(10), p->getVertex(17), newv[2], p->getVertex(15), p->getVertex(4), p->getVertex(14), newv[1], p->getVertex(12))); hexahedra2.push_back (new MHexahedron(p->getVertex(11), p->getVertex(16), newv[2], p->getVertex(17), p->getVertex(5), p->getVertex(13), newv[1], p->getVertex(14))); } } gr->prisms.clear(); } gr->hexahedra = hexahedra2; std::vector<MPrism*> prisms2; for(unsigned int i = 0; i < gr->prisms.size(); i++){ MPrism *p = gr->prisms[i]; if(p->getNumVertices() == 18){ prisms2.push_back (new MPrism(p->getVertex(0), p->getVertex(6), p->getVertex(7), p->getVertex(8), p->getVertex(15), p->getVertex(16))); prisms2.push_back (new MPrism(p->getVertex(8), p->getVertex(15), p->getVertex(16), p->getVertex(3), p->getVertex(12), p->getVertex(13))); prisms2.push_back (new MPrism(p->getVertex(6), p->getVertex(1), p->getVertex(9), p->getVertex(15), p->getVertex(10), p->getVertex(17))); prisms2.push_back (new MPrism(p->getVertex(15), p->getVertex(10), p->getVertex(17), p->getVertex(12), p->getVertex(4), p->getVertex(14))); prisms2.push_back (new MPrism(p->getVertex(7), p->getVertex(9), p->getVertex(2), p->getVertex(16), p->getVertex(17), p->getVertex(11))); prisms2.push_back (new MPrism(p->getVertex(16), p->getVertex(17), p->getVertex(11), p->getVertex(13), p->getVertex(14), p->getVertex(5))); prisms2.push_back (new MPrism(p->getVertex(9), p->getVertex(7), p->getVertex(6), p->getVertex(17), p->getVertex(16), p->getVertex(15))); prisms2.push_back (new MPrism(p->getVertex(17), p->getVertex(16), p->getVertex(15), p->getVertex(14), p->getVertex(13), p->getVertex(12))); } delete p; } gr->prisms = prisms2; std::vector<MPyramid*> pyramids2; for(unsigned int i = 0; i < gr->pyramids.size(); i++){ if(splitIntoHexas){ Msg::Error("Full hexahedron subdivision is not implemented for pyramids"); return; } MPyramid *p = gr->pyramids[i]; if(p->getNumVertices() == 14){ // Base pyramids2.push_back (new MPyramid(p->getVertex(0), p->getVertex(5), p->getVertex(13), p->getVertex(6), p->getVertex(7))); pyramids2.push_back (new MPyramid(p->getVertex(5), p->getVertex(1), p->getVertex(8), p->getVertex(13), p->getVertex(9))); pyramids2.push_back (new MPyramid(p->getVertex(13), p->getVertex(8), p->getVertex(2), p->getVertex(10), p->getVertex(11))); pyramids2.push_back (new MPyramid(p->getVertex(6), p->getVertex(13), p->getVertex(10), p->getVertex(3), p->getVertex(12))); // Split remaining into tets // Top gr->tetrahedra.push_back ((new MTetrahedron(p->getVertex(7), p->getVertex(9), p->getVertex(12), p->getVertex(4)))); gr->tetrahedra.push_back ((new MTetrahedron(p->getVertex(9), p->getVertex(11), p->getVertex(12), p->getVertex(4)))); // Upside down one gr->tetrahedra.push_back ((new MTetrahedron(p->getVertex(9), p->getVertex(12), p->getVertex(11), p->getVertex(13)))); gr->tetrahedra.push_back ((new MTetrahedron(p->getVertex(7), p->getVertex(12), p->getVertex(9), p->getVertex(13)))); // Four tets around bottom perimeter gr->tetrahedra.push_back ((new MTetrahedron(p->getVertex(7), p->getVertex(9), p->getVertex(5), p->getVertex(13)))); gr->tetrahedra.push_back ((new MTetrahedron(p->getVertex(9), p->getVertex(11), p->getVertex(8), p->getVertex(13)))); gr->tetrahedra.push_back ((new MTetrahedron(p->getVertex(12), p->getVertex(10), p->getVertex(11), p->getVertex(13)))); gr->tetrahedra.push_back ((new MTetrahedron(p->getVertex(7), p->getVertex(6), p->getVertex(12), p->getVertex(13)))); } delete p; } gr->pyramids = pyramids2; for(unsigned int i = 0; i < gr->mesh_vertices.size(); i++) gr->mesh_vertices[i]->setPolynomialOrder(1); gr->deleteVertexArrays(); }