00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include <MeshOfHexahedra.hpp>
00021 #include <ConnectivityBuilder.hpp>
00022 #include <set>
00023 #include <queue>
00024
00025 #include <ConformTransformation.hpp>
00026 #include <FacesBuilder.hpp>
00027
00028 void MeshOfHexahedra::
00029 buildEdges()
00030 {
00031 EdgesBuilder<MeshOfHexahedra> edgesBuilder(*this);
00032 __edgesSet = edgesBuilder.edgesSet();
00033 }
00034
00035 void MeshOfHexahedra::
00036 buildFaces()
00037 {
00038 FacesBuilder<MeshOfHexahedra> facesBuilder(*this);
00039 __facesSet = facesBuilder.facesSet();
00040 }
00041
00042
00043 void MeshOfHexahedra::
00044 buildLocalizationTools()
00045 {
00046 if (this->numberOfVertices()==0) {
00047 throw ErrorHandler(__FILE__,__LINE__,
00048 "the mesh contains no vertices\n",
00049 ErrorHandler::normal);
00050 }
00051
00052 {
00053
00054
00055 ConnectivityBuilder<MeshOfHexahedra> builder(*this);
00056 builder.generates(Connectivity<MeshOfHexahedra>::CellToCells);
00057 }
00058
00059 if (__borderMesh != 0) {
00060 ConnectivityBuilder<MeshOfHexahedra> builder(*this);
00061 builder.borderMesh(__borderMesh);
00062 __borderMesh->setBackgroundMesh(this);
00063 }
00064
00065
00066 __a = (this->vertex(0));
00067 __b = __a;
00068 for (size_t i=1; i<this->numberOfVertices(); ++i) {
00069 Vertex& x = this->vertex(i);
00070 for (size_t k=0; k<3; ++k) {
00071 __a[k] = std::min(__a[k],x[k]);
00072 __b[k] = std::max(__b[k],x[k]);
00073 }
00074 }
00075 ffout(3) << "- Bounding box is " << __a << ',' << __b << '\n';
00076
00077 __a -= TinyVector<3,real_t>(1,1,1);
00078 __b += TinyVector<3,real_t>(1,1,1);
00079
00080 ffout(3) << "- Building the octree\n";
00081 __octree = new Octree<size_t, 3>(__a,__b);
00082
00083 for (size_t i = 0; i < this->numberOfCells(); ++i) {
00084
00085 ConformTransformationQ1Hexahedron T(this->cell(i));
00086
00087 for (size_t k=0; k<QuadratureFormulaQ1Hexahedron::numberOfQuadraturePoints; ++k) {
00088 TinyVector<3,real_t> X;
00089 T.value(QuadratureFormulaQ1Hexahedron::instance()[k], X);
00090 __octree->add(i,X);
00091 }
00092 }
00093 }
00094
00095
00096 MeshOfHexahedra::const_iterator
00097 MeshOfHexahedra::find(const double& x,
00098 const double& y,
00099 const double& z) const
00100 {
00101 TinyVector<3,real_t> X(x,y,z);
00102
00103 Octree<size_t, 3>::iterator i = (*__octree).fuzzySearch(X);
00104
00105 size_t cellNumber = (*i).value();
00106
00107 MeshOfHexahedra::const_iterator h0(*this, cellNumber);
00108
00109 bool found=false;
00110
00111 std::set<MeshOfHexahedra::const_iterator> visited;
00112 std::set<MeshOfHexahedra::const_iterator> toVisitSet;
00113 std::queue<MeshOfHexahedra::const_iterator> toVisitQueue;
00114
00115 toVisitSet.insert(h0);
00116 toVisitQueue.push(h0);
00117 MeshOfHexahedra::const_iterator h(*this);
00118
00119 TinyVector<3, real_t> Xhat;
00120 size_t cpt = 0;
00121 do {
00122 if (cpt > 125) {
00123 break;
00124 }
00125
00126 h = toVisitQueue.front();
00127
00128 toVisitSet.erase(h);
00129 toVisitQueue.pop();
00130 visited.insert(h);
00131
00132 const Hexahedron& H = *h;
00133
00134 ConformTransformationQ1Hexahedron T(H);
00135 found = T.invertT(x,y,z, Xhat);
00136
00137 if (not found) {
00138 for (size_t k=0; k<6; ++k) {
00139 MeshOfHexahedra::const_iterator icell(*this,const_iterator::End);
00140 icell = __connectivity.cells(*h)[k];
00141 if (not(icell.end())) {
00142 if (visited.find(icell) == visited.end()) {
00143 if (toVisitSet.find(icell) == toVisitSet.end()) {
00144 toVisitSet.insert(icell);
00145 toVisitQueue.push(icell);
00146 }
00147 }
00148 }
00149 }
00150 }
00151 cpt++;
00152 } while (not(found) and not(toVisitQueue.empty()));
00153
00154 if (not found) {
00155 return MeshOfHexahedra::const_iterator(*this,const_iterator::End);
00156 }
00157 return h;
00158 }