MOAB: Mesh Oriented datABase  (version 5.4.1)
QuadTriConv.cpp
Go to the documentation of this file.
00001 /** @example QuadTriConv.cpp \n
00002  * \brief Merge vertices in 2d cell, if they are repeated \n
00003  * <b>To run</b>: QuadTriConv  input_file output_file \n
00004  *
00005  * In this example, a mesh that has vertices repeated due to south or north pole, for
00006  *  example in an rll mesh, need to be converted to triangles, preserving GLOBAL_ID tag
00007  */
00008 
00009 #include <iostream>
00010 #include <vector>
00011 //#include <string>
00012 
00013 // Include header for MOAB instance and tag conventions for
00014 #include "moab/Core.hpp"
00015 #include "MBTagConventions.hpp"
00016 
00017 using namespace moab;
00018 using namespace std;
00019 
00020 int main( int argc, char** argv )
00021 {
00022     // Get MOAB instance
00023     Interface* mb = new( std::nothrow ) Core;
00024     if( NULL == mb ) return 1;
00025 
00026     std::string filename, outfile;
00027     outfile = string( "out.h5m" );
00028     if( argc == 1 ) return 0;
00029     if( argc > 1 ) filename = string( argv[1] );
00030     if( argc > 2 ) outfile = string( argv[2] );
00031 
00032     // This file is in the mesh files directory
00033     ErrorCode rval = mb->load_file( filename.c_str() );MB_CHK_SET_ERR( rval, "Failed to read" );
00034 
00035     // get all cells of dimension 2;
00036     Range cells;
00037     rval = mb->get_entities_by_dimension( 0, 2, cells );MB_CHK_SET_ERR( rval, "Failed to get cells" );
00038 
00039     cout << " number of cells : " << cells.size() << "\n";
00040 
00041     Tag gid;  // global id tag
00042     rval = mb->tag_get_handle( "GLOBAL_ID", gid );MB_CHK_SET_ERR( rval, "Failed to get Global ID tag" );
00043 
00044     Range modifiedCells;  // will be deleted at the end; keep the gid
00045 
00046     for( Range::iterator cit = cells.begin(); cit != cells.end(); cit++ )
00047     {
00048         EntityHandle cell          = *cit;
00049         const EntityHandle* connec = NULL;
00050         int num_verts              = 0;
00051         rval                       = mb->get_connectivity( cell, connec, num_verts );MB_CHK_SET_ERR( rval, "Failed to get connectivity" );
00052 
00053         vector< EntityHandle > newConnec;
00054         newConnec.push_back( connec[0] );  // at least one vertex
00055         int index    = 0;
00056         int new_size = 1;
00057         while( index < num_verts - 2 )
00058         {
00059             int next_index = ( index + 1 );
00060             if( connec[next_index] != newConnec[new_size - 1] )
00061             {
00062                 newConnec.push_back( connec[next_index] );
00063                 new_size++;
00064             }
00065             index++;
00066         }
00067         // add the last one only if different from previous and first node
00068         if( ( connec[num_verts - 1] != connec[num_verts - 2] ) && ( connec[num_verts - 1] != connec[0] ) )
00069         {
00070             newConnec.push_back( connec[num_verts - 1] );
00071             new_size++;
00072         }
00073         if( new_size < num_verts )
00074         {
00075             // cout << "new cell from " << cell << " has only " << new_size << " vertices \n";
00076             modifiedCells.insert( cell );
00077             // create a new cell with type triangle, quad or polygon
00078             EntityType type = MBTRI;
00079             if( new_size == 3 )
00080                 type = MBTRI;
00081             else if( new_size == 4 )
00082                 type = MBQUAD;
00083             else if( new_size > 4 )
00084                 type = MBPOLYGON;
00085 
00086             // create new cell
00087             EntityHandle newCell;
00088             rval = mb->create_element( type, &newConnec[0], new_size, newCell );MB_CHK_SET_ERR( rval, "Failed to create new cell" );
00089             // set the old id to the new element
00090             int id;
00091             rval = mb->tag_get_data( gid, &cell, 1, &id );MB_CHK_SET_ERR( rval, "Failed to get global id" );
00092             rval = mb->tag_set_data( gid, &newCell, 1, &id );MB_CHK_SET_ERR( rval, "Failed to set global id on new cell" );
00093         }
00094     }
00095 
00096     mb->delete_entities( modifiedCells );
00097     // in case global ids are not set for vertices, set them, in order;
00098     // they are needed for migrating later on
00099     //
00100     Range verts;
00101     rval = mb->get_entities_by_dimension( 0, 0, verts );MB_CHK_SET_ERR( rval, "Failed to get vertices" );
00102 
00103     vector< int > gids;
00104     gids.resize( verts.size() );
00105     rval = mb->tag_get_data( gid, verts, &gids[0] );MB_CHK_SET_ERR( rval, "Failed to get gids on vertices" );
00106     if( gids[0] <= 0 )
00107     {
00108         // gids were never set, assign them
00109         for( size_t i = 1; i <= verts.size(); i++ )
00110             gids[i - 1] = (int)i;
00111         rval = mb->tag_set_data( gid, verts, &gids[0] );MB_CHK_SET_ERR( rval, "Failed to set gids on vertices" );
00112     }
00113     rval = mb->write_file( outfile.c_str() );MB_CHK_SET_ERR( rval, "Failed to write new file" );
00114 
00115     cout << " wrote file " << outfile << " with " << modifiedCells.size() << " modified cells\n";
00116 
00117     delete mb;
00118     return 0;
00119 }
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines