MOAB: Mesh Oriented datABase
(version 5.2.1)
|
00001 /** 00002 * MOAB, a Mesh-Oriented datABase, is a software component for creating, 00003 * storing and accessing finite element mesh data. 00004 * 00005 * Copyright 2004 Sandia Corporation. Under the terms of Contract 00006 * DE-AC04-94AL85000 with Sandia Corporation, the U.S. Government 00007 * retains certain rights in this software. 00008 * 00009 * This library is free software; you can redistribute it and/or 00010 * modify it under the terms of the GNU Lesser General Public 00011 * License as published by the Free Software Foundation; either 00012 * version 2.1 of the License, or (at your option) any later version. 00013 * 00014 */ 00015 00016 #include "ExoIIUtil.hpp" 00017 #include "Internals.hpp" 00018 #include "moab/Interface.hpp" 00019 #include "moab/CN.hpp" 00020 #include <string.h> 00021 00022 namespace moab 00023 { 00024 00025 // 00026 // definitions of ExoII-related static arrays 00027 // 00028 00029 const EntityType ExoIIUtil::ExoIIElementMBEntity[] = { 00030 MBVERTEX, // SPHERE, 00031 MBEDGE, // SPRING, 00032 MBEDGE, // BAR = 0, 00033 MBEDGE, // BAR2, 00034 MBEDGE, // BAR3, 00035 MBEDGE, // BEAM, 00036 MBEDGE, // BEAM2, 00037 MBEDGE, // BEAM3, 00038 MBEDGE, // TRUSS, 00039 MBEDGE, // TRUSS2, 00040 MBEDGE, // TRUSS3, 00041 MBTRI, // TRI, 00042 MBTRI, // TRI3, 00043 MBTRI, // SHELL3, 00044 MBTRI, // TRI6, 00045 MBTRI, // TRI7, 00046 MBQUAD, // QUAD, 00047 MBQUAD, // QUAD4, 00048 MBQUAD, // QUAD5, 00049 MBQUAD, // QUAD8, 00050 MBQUAD, // QUAD9, 00051 MBQUAD, // SHELL, 00052 MBQUAD, // SHELL4, 00053 MBQUAD, // SHELL5, 00054 MBQUAD, // SHELL8, 00055 MBQUAD, // SHELL9, 00056 MBTET, // TETRA, 00057 MBTET, // TETRA4, 00058 MBTET, // TET4 00059 MBTET, // TETRA8, 00060 MBTET, // TETRA10, 00061 MBTET, // TETRA14, 00062 MBPYRAMID, // PYRAMID, 00063 MBPYRAMID, // PYRAMID5, 00064 MBPYRAMID, // PYRAMID10, 00065 MBPYRAMID, // PYRAMID13, 00066 MBPYRAMID, // PYRAMID18, 00067 MBPRISM, // WEDGE, 00068 MBKNIFE, // KNIFE, 00069 MBHEX, // HEX, 00070 MBHEX, // HEX8, 00071 MBHEX, // HEX9, 00072 MBHEX, // HEX20, 00073 MBHEX, // HEX27, 00074 MBHEX, // HEXSHELL, 00075 MBPOLYGON, // POLYGON 00076 MBPOLYHEDRON, // POLYHEDRON 00077 MBMAXTYPE // UNKNOWN 00078 }; 00079 00080 const char* ExoIIUtil::ElementTypeNames[] = { "SPHERE", // 0 00081 "SPRING", // 1 00082 "BAR", // 2 00083 "BAR2", // 3 00084 "BAR3", // 4 00085 "BEAM", // 5 00086 "BEAM2", // 6 00087 "BEAM3", // 7 00088 "TRUSS", // 8 00089 "TRUSS2", // 9 00090 "TRUSS3", // 10 00091 "TRI", // 11 00092 "TRI3", // 12 00093 "SHELL3", // 13 really the same as TRI3; for sure in 3d? 00094 "TRI6", "TRI7", "QUAD", "QUAD4", "QUAD5", "QUAD8", 00095 "QUAD9", "SHELL", "SHELL4", "SHELL5", "SHELL8", "SHELL9", 00096 "TETRA", "TETRA4", "TET4", "TETRA8", "TETRA10", "TETRA14", 00097 "PYRAMID", "PYRAMID5", "PYRAMID10", "PYRAMID13", "PYRAMID18", "WEDGE", 00098 "KNIFE", "HEX", "HEX8", "HEX9", "HEX20", "HEX27", 00099 "HEXSHELL", 00100 "nsided", // polygons, described differently 00101 "NFACED", // polyhedra, described in faconn%d attributes 00102 "UNKNOWN" }; 00103 00104 const int ExoIIUtil::VerticesPerElement[] = { 00105 1, // SPHERE 00106 1, // SPRING 00107 2, 2, 00108 3, // BAR 00109 2, 2, 00110 3, // BEAM 00111 2, 2, 00112 3, // TRUSS 00113 3, // TRI 00114 3, // TRI3 00115 3, // SHELL3 this is new 00116 6, 00117 7, // TRI 00118 4, 4, 5, 8, 00119 9, // QUAD 00120 4, 4, 5, 8, 00121 9, // SHELL 00122 4, 4, 00123 4, // TET4 00124 8, 10, 00125 14, // TETRA 00126 5, 5, 10, 13, 00127 18, // PYRAMID 00128 6, // WEDGE 00129 7, // KNIFE 00130 8, 8, 9, 20, 00131 27, // HEX 00132 12, // HEXSHELL 00133 0, // POLYGON 00134 0, // POLYHEDRON 00135 0 // UNKNOWN 00136 }; 00137 00138 const int ExoIIUtil::HasMidNodes[][4] = { 00139 { 0, 0, 0, 0 }, // SPHERE - no mid nodes 00140 { 0, 0, 0, 0 }, // SPRING - no mid nodes 00141 { 0, 0, 0, 0 }, // BAR - no mid nodes, same as BAR2 00142 { 0, 0, 0, 0 }, // BAR2 - no mid nodes 00143 { 0, 1, 0, 0 }, // BAR3 - mid nodes on edges 00144 { 0, 0, 0, 0 }, // BEAM - no mid nodes 00145 { 0, 0, 0, 0 }, // BEAM2 - no mid nodes 00146 { 0, 1, 0, 0 }, // BEAM3 - mid nodes on edges 00147 { 0, 0, 0, 0 }, // TRUSS - no mid nodes 00148 { 0, 0, 0, 0 }, // TRUSS2 - no mid nodes 00149 { 0, 1, 0, 0 }, // TRUSS3 - mid nodes on edges 00150 { 0, 0, 0, 0 }, // TRI - no mid nodes 00151 { 0, 0, 0, 0 }, // TRI3 - no mid nodes 00152 { 0, 0, 0, 0 }, // SHELL3 - no mid nodes 00153 { 0, 1, 0, 0 }, // TRI6 - mid nodes on edges 00154 { 0, 1, 1, 0 }, // TRI7 - mid nodes on edges and faces 00155 { 0, 0, 0, 0 }, // QUAD - no mid nodes 00156 { 0, 0, 0, 0 }, // QUAD4 - no mid nodes 00157 { 0, 0, 1, 0 }, // QUAD5 - mid node on faces 00158 { 0, 1, 0, 0 }, // QUAD8 - mid nodes on edges 00159 { 0, 1, 1, 0 }, // QUAD9 - mid nodes on edges and faces 00160 { 0, 0, 0, 0 }, // SHELL - no mid nodes 00161 { 0, 0, 0, 0 }, // SHELL4 - no mid nodes 00162 { 0, 0, 1, 0 }, // SHELL5 - mid node on faces 00163 { 0, 1, 0, 0 }, // SHELL8 - mid nodes on edges 00164 { 0, 1, 1, 0 }, // SHELL9 - mid nodes on edges and faces 00165 { 0, 0, 0, 0 }, // TETRA - no mid nodes 00166 { 0, 0, 0, 0 }, // TETRA4 - no mid nodes 00167 { 0, 0, 0, 0 }, // TET4 - no mid nodes 00168 { 0, 0, 1, 0 }, // TETRA8 - mid nodes on faces 00169 { 0, 1, 0, 0 }, // TETRA10 - mid nodes on edges 00170 { 0, 1, 1, 0 }, // TETRA14 - mid nodes on edges and faces 00171 { 0, 0, 0, 0 }, // PYRAMID - no mid nodes 00172 { 0, 0, 0, 0 }, // PYRAMID5 - no mid nodes 00173 { 0, 0, 1, 0 }, // PYRAMID10 - *** TODO - not sure if this is right... 00174 { 0, 1, 0, 0 }, // PYRAMID13 - *** TODO - not sure if this is right... 00175 { 0, 1, 1, 0 }, // PYRAMID18 - *** TODO - not sure if this is right... 00176 { 0, 0, 0, 0 }, // WEDGE - no mid nodes 00177 { 0, 0, 0, 0 }, // KNIFE - no mid nodes 00178 { 0, 0, 0, 0 }, // HEX - no mid nodes 00179 { 0, 0, 0, 0 }, // HEX8 - no mid nodes 00180 { 0, 0, 0, 1 }, // HEX9 - mid node on element 00181 { 0, 1, 0, 0 }, // HEX20 - mid nodes on edges 00182 { 0, 1, 1, 1 }, // HEX27 - mid node on edges, faces and element 00183 { 0, 0, 0, 0 }, // HEXSHELL - *** TODO - not sure if this is right... 00184 { 0, 0, 0, 0 }, // POLYGON 00185 { 0, 0, 0, 0 }, // POLYHEDRON 00186 { 0, 0, 0, 0 } // UNKNOWN - no mid nodes 00187 }; 00188 00189 const int ExoIIUtil::ElementGeometricDimension[] = { 00190 3, // SPHERE 00191 3, // SPRING 00192 2, 2, 00193 2, // BAR 00194 3, 3, 00195 3, // BEAM 00196 3, 3, 00197 3, // TRUSS 00198 3, 3, 3, 3, 00199 3, // TRI 00200 2, 2, 2, 2, 00201 2, // QUAD 00202 3, 3, 3, 3, 00203 3, // SHELL 00204 3, 3, 3, 3, 00205 3, // TETRA 00206 3, 3, 3, 3, 3, 00207 3, // PYRAMID 00208 3, // WEDGE 00209 3, // KNIFE 00210 3, 3, 3, 3, 00211 3, // HEX 00212 3, // HEXSHELL 00213 2, // POLYGON 00214 3, // POLYHEDRON 00215 0 // UNKNOWN 00216 }; 00217 00218 ExoIIElementType ExoIIUtil::static_element_name_to_type( const char* name ) 00219 { 00220 int i; 00221 for( i = 0; i < EXOII_MAX_ELEM_TYPE; i++ ) 00222 if( strcmp( ElementTypeNames[i], name ) == 0 ) return (ExoIIElementType)i; 00223 00224 return EXOII_MAX_ELEM_TYPE; 00225 } 00226 00227 ExoIIElementType ExoIIUtil::static_get_element_type( Interface* mdbImpl, const EntityHandle entity, 00228 const Tag mid_nodes_tag, const Tag geom_dimension_tag, 00229 const EntityType indiv_entity_type ) 00230 { 00231 // branch based on what kind of entity we're looking at 00232 EntityType handle_type = mdbImpl->type_from_handle( entity ); 00233 00234 if( handle_type == MBENTITYSET ) 00235 { 00236 00237 // it's a meshset - assume it's a block (check this?) and work off the midnodes tag 00238 00239 // get the element type of the block; first, get the hasMidNodes tag, then convert to an exo 00240 // element type 00241 int has_mid_nodes[4]; 00242 int dimension = -1; 00243 if( mdbImpl->tag_get_data( mid_nodes_tag, &entity, 1, has_mid_nodes ) != MB_SUCCESS ) 00244 { 00245 // no mid nodes tag - look for indiv entity type, and if it was input, output the 00246 // default number of vertices 00247 if( MBMAXTYPE != indiv_entity_type ) 00248 { 00249 // get dimension 00250 if( indiv_entity_type == MBQUAD || indiv_entity_type == MBTRI ) 00251 dimension = 3; // want to ouput shells by default 00252 else if( indiv_entity_type == MBEDGE ) 00253 dimension = 2; 00254 else 00255 dimension = CN::Dimension( indiv_entity_type ); 00256 00257 return get_element_type_from_num_verts( CN::VerticesPerEntity( indiv_entity_type ), indiv_entity_type, 00258 dimension ); 00259 } 00260 else 00261 return EXOII_MAX_ELEM_TYPE; 00262 } 00263 else 00264 { 00265 // block meshset had midnodes tag - look for geometric dimension one too 00266 mdbImpl->tag_get_data( geom_dimension_tag, &entity, 1, &dimension ); 00267 } 00268 00269 for( int i = 0; i < EXOII_MAX_ELEM_TYPE; i++ ) 00270 { 00271 if( ( indiv_entity_type == MBMAXTYPE || indiv_entity_type == ExoIIElementMBEntity[i] ) && 00272 has_mid_nodes[0] == HasMidNodes[i][0] && has_mid_nodes[1] == HasMidNodes[i][1] && 00273 has_mid_nodes[2] == HasMidNodes[i][2] && has_mid_nodes[3] == HasMidNodes[i][3] && 00274 ( -1 == dimension || ElementGeometricDimension[i] == dimension ) ) 00275 return (ExoIIElementType)i; 00276 } 00277 00278 return EXOII_MAX_ELEM_TYPE; 00279 } 00280 00281 else if( handle_type == MBVERTEX ) 00282 // only have one type of entity for vertices... 00283 return EXOII_SPHERE; 00284 00285 else 00286 { 00287 std::vector< EntityHandle > tmp( 31 ); 00288 00289 mdbImpl->get_connectivity( &entity, 1, tmp, true ); 00290 return get_element_type_from_num_verts( tmp.size(), indiv_entity_type ); 00291 // it's a regular entity - look for a connectivity tag 00292 } 00293 00294 // if we've gotten here, we failed 00295 // return EXOII_MAX_ELEM_TYPE; 00296 } 00297 00298 ExoIIElementType ExoIIUtil::get_element_type_from_num_verts( const int num_verts, const EntityType entity_type, 00299 const int dimension ) 00300 { 00301 if( MBPOLYGON == entity_type && 2 == dimension ) return EXOII_POLYGON; 00302 if( MBPOLYHEDRON == entity_type && 3 == dimension ) return EXOII_POLYHEDRON; 00303 for( int i = 0; i < EXOII_MAX_ELEM_TYPE; i++ ) 00304 { 00305 if( ( entity_type == MBMAXTYPE || entity_type == ExoIIElementMBEntity[i] ) && 00306 VerticesPerElement[i] == num_verts && ElementGeometricDimension[i] >= dimension ) 00307 return (ExoIIElementType)i; 00308 } 00309 00310 return EXOII_MAX_ELEM_TYPE; 00311 } 00312 00313 } // namespace moab