Back to index

salome-med  6.5.0
MEDMEM_GMesh.cxx
Go to the documentation of this file.
00001 // Copyright (C) 2007-2012  CEA/DEN, EDF R&D, OPEN CASCADE
00002 //
00003 // Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
00004 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
00005 //
00006 // This library is free software; you can redistribute it and/or
00007 // modify it under the terms of the GNU Lesser General Public
00008 // License as published by the Free Software Foundation; either
00009 // version 2.1 of the License.
00010 //
00011 // This library is distributed in the hope that it will be useful,
00012 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00013 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00014 // Lesser General Public License for more details.
00015 //
00016 // You should have received a copy of the GNU Lesser General Public
00017 // License along with this library; if not, write to the Free Software
00018 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
00019 //
00020 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
00021 //
00022 // File      : MEDMEM_GMesh.cxx
00023 // Created   : Fri Jul 23 12:32:18 2010
00024 // Author    : Edward AGAPOV (eap)
00025 //
00026 
00027 #include "MEDMEM_GMesh.hxx"
00028 
00029 #include "MEDMEM_Family.hxx"
00030 #include "MEDMEM_Group.hxx"
00031 #include "MEDMEM_DriverFactory.hxx"
00032 
00033 using namespace MEDMEM;
00034 using namespace MED_EN;
00035 using namespace std;
00036 
00052 //================================================================================
00054 //================================================================================
00055 
00056 GMESH::GMESH()
00057 {
00058   init();
00059 }
00060 
00061 //================================================================================
00065 //================================================================================
00066 
00067 GMESH::GMESH(GMESH &m)
00068 {
00069   _name = m._name;
00070   _description = m._description;
00071   _spaceDimension = m._spaceDimension;
00072 
00073   _familyNode = m._familyNode;
00074   for (int i=0; i<(int)m._familyNode.size(); i++)
00075   {
00076     _familyNode[i] = new FAMILY(* m._familyNode[i]);
00077     _familyNode[i]->setMesh(this);
00078     removeReference();
00079   }
00080 
00081   _familyCell = m._familyCell;
00082   for (int i=0; i<(int)m._familyCell.size(); i++)
00083   {
00084     _familyCell[i] = new FAMILY(* m._familyCell[i]);
00085     _familyCell[i]->setMesh(this);
00086     removeReference();
00087   }
00088 
00089   _familyFace = m._familyFace;
00090   for (int i=0; i<(int)m._familyFace.size(); i++)
00091   {
00092     _familyFace[i] = new FAMILY(* m._familyFace[i]);
00093     _familyFace[i]->setMesh(this);
00094     removeReference();
00095   }
00096 
00097   _familyEdge = m._familyEdge;
00098   for (int i=0; i<(int)m._familyEdge.size(); i++)
00099   {
00100     _familyEdge[i] = new FAMILY(* m._familyEdge[i]);
00101     _familyEdge[i]->setMesh(this);
00102     removeReference();
00103   }
00104 
00105   _groupNode = m._groupNode;
00106   for (int i=0; i<(int)m._groupNode.size(); i++)
00107   {
00108     _groupNode[i] = new GROUP(* m._groupNode[i]);
00109     _groupNode[i]->setMesh(this);
00110     removeReference();
00111   }
00112 
00113   _groupCell = m._groupCell;
00114   for (int i=0; i<(int)m._groupCell.size(); i++)
00115   {
00116     _groupCell[i] = new GROUP(* m._groupCell[i]);
00117     _groupCell[i]->setMesh(this);
00118     removeReference();
00119   }
00120 
00121   _groupFace = m._groupFace;
00122   for (int i=0; i<(int)m._groupFace.size(); i++)
00123   {
00124     _groupFace[i] = new GROUP(* m._groupFace[i]);
00125     _groupFace[i]->setMesh(this);
00126     removeReference();
00127   }
00128 
00129   _groupEdge = m._groupEdge;
00130   for (int i=0; i<(int)m._groupEdge.size(); i++)
00131   {
00132     _groupEdge[i] = new GROUP(* m._groupEdge[i]);
00133     _groupEdge[i]->setMesh(this);
00134     removeReference();
00135   }
00136 
00137   //_drivers = m._drivers;  //Recopie des drivers?
00138 }
00139 
00140 //================================================================================
00144 //================================================================================
00145 
00146 GMESH::~GMESH()
00147 {
00148   // if this is an automatic variable, be sure that destructor will be no more called
00149   // due to cyclic dependencies with child reference counters (groups and families)
00150   clearRefCouner();
00151 
00152   for (unsigned i=0;i<_familyNode.size();i++)
00153   {
00154     // if another object refers to a family and it survive now,
00155     // it sould not refer to a dead mesh
00156     _familyNode[i]->setMesh(0);
00157     _familyNode[i]->setMeshName( getName() );
00158     _familyNode[i]->removeReference();
00159   }
00160   _familyNode.clear();
00161   for (unsigned i=0;i<_familyCell.size();i++)
00162   {
00163     _familyCell[i]->setMesh(0);
00164     _familyCell[i]->setMeshName( getName() );
00165     _familyCell[i]->removeReference();
00166   }
00167   _familyCell.clear();
00168   for (unsigned i=0;i<_familyFace.size();i++)
00169   {
00170     _familyFace[i]->setMesh(0);
00171     _familyFace[i]->setMeshName( getName() );
00172     _familyFace[i]->removeReference();
00173   }
00174   _familyFace.clear();
00175   for (unsigned i=0;i<_familyEdge.size();i++)
00176   {
00177     _familyEdge[i]->setMesh(0);
00178     _familyEdge[i]->setMeshName( getName() );
00179     _familyEdge[i]->removeReference();
00180   }
00181   _familyEdge.clear();
00182   for (unsigned i=0;i<_groupNode.size();i++)
00183   {
00184     _groupNode[i]->setMesh(0);
00185     _groupNode[i]->setMeshName( getName() );
00186     _groupNode[i]->removeReference();
00187   }
00188   _groupNode.clear();
00189   for (unsigned i=0;i<_groupCell.size();i++)
00190   {
00191     _groupCell[i]->setMesh(0);
00192     _groupCell[i]->setMeshName( getName() );
00193     _groupCell[i]->removeReference();
00194   }
00195   _groupCell.clear();
00196   for (unsigned i=0;i<_groupFace.size();i++)
00197   {
00198     _groupFace[i]->setMesh(0);
00199     _groupFace[i]->setMeshName( getName() );
00200     _groupFace[i]->removeReference();
00201   }
00202   _groupFace.clear();
00203   for (unsigned i=0;i<_groupEdge.size();i++)
00204   {
00205     _groupEdge[i]->setMesh(0);
00206     _groupEdge[i]->setMeshName( getName() );
00207     _groupEdge[i]->removeReference();
00208   }
00209   _groupEdge.clear();
00210 
00211   map<medEntityMesh,SUPPORT*>::iterator it = _entitySupport.begin();
00212   for(;it!=_entitySupport.end();it++)
00213     if((*it).second != NULL)
00214     {
00215       (*it).second->setMesh(0);
00216       (*it).second->setMeshName( getName() );
00217       (*it).second->removeReference();
00218     }
00219   _entitySupport.clear();
00220 
00221   for (unsigned int index=0; index < _drivers.size(); index++ )
00222     if ( _drivers[index] ) delete _drivers[index];
00223   _drivers.clear();
00224 }
00225 
00226 //================================================================================
00230 //================================================================================
00231 
00232 void GMESH::init()
00233 {
00234   const char* LOC = "GMESH::init(): ";
00235   BEGIN_OF_MED(LOC);
00236 
00237   _name          ="NOT DEFINED";
00238   _spaceDimension=MED_INVALID;
00239   
00240   END_OF_MED(LOC);
00241 }
00242 
00243 //================================================================================
00247 //================================================================================
00248 
00249 GMESH & GMESH::operator=(const GMESH &m)
00250 {
00251   const char* LOC = "GMESH & GMESH::operator=(const GMESH &m) : ";
00252   BEGIN_OF_MED(LOC);
00253   MESSAGE_MED("Not yet implemented");
00254   END_OF_MED(LOC);
00255 
00256   return *this;
00257 }
00258 
00259 //================================================================================
00263 //================================================================================
00264 
00265 bool GMESH::operator==(const GMESH& other) const
00266 {
00267   return this==&other;
00268 }
00269 
00270 //================================================================================
00274 //================================================================================
00275 
00276 ostream & MEDMEM::operator<<(ostream &os, const GMESH &myMesh)
00277 {
00278   myMesh.printMySelf(os);
00279   return os;
00280 }
00281 
00287 //================================================================================
00293 //================================================================================
00294 
00295 int  GMESH::addDriver(driverTypes            driverType,
00296                       const std::string &    fileName,
00297                       const std::string &    driverName,
00298                       MED_EN::med_mode_acces access)
00299 {
00300   const char* LOC = "GMESH::addDriver(driverTypes driverType, const string & fileName=\"Default File Name.med\",const string & driverName=\"Default Mesh Name\",MED_EN::med_mode_acces access) : ";
00301   BEGIN_OF_MED(LOC);
00302 
00303   GENDRIVER * driver;
00304 
00305   SCRUTE_MED(driverType);
00306 
00307   driver = DRIVERFACTORY::buildDriverForMesh(driverType,fileName,this,driverName,access) ;
00308 
00309   _drivers.push_back(driver);
00310 
00311   int current = _drivers.size()-1;
00312 
00313   _drivers[current]->setMeshName(driverName);
00314 
00315   END_OF_MED(LOC);
00316 
00317   return current;
00318 }
00319 
00320 //================================================================================
00322 //================================================================================
00323 
00324 int GMESH::addDriver(GENDRIVER & driver)
00325 {
00326   const char* LOC = "GMESH::addDriver(GENDRIVER &) : ";
00327   BEGIN_OF_MED(LOC);
00328 
00329   // For the case where driver does not know about me since it has been created through
00330   // constructor witout parameters: create newDriver knowing me and get missing data
00331   // from driver using merge()
00332   //GENDRIVER * newDriver = driver.copy() ;
00333   GENDRIVER* newDriver = DRIVERFACTORY::buildDriverForMesh(driver.getDriverType(),
00334                                                            driver.getFileName(), this,
00335                                                            driver.getMeshName(),
00336                                                            driver.getAccessMode());
00337   _drivers.push_back(newDriver);
00338 
00339   int current = _drivers.size()-1;
00340   driver.setId(current);
00341 
00342   newDriver->merge( driver );
00343   newDriver->setId( current );
00344 
00345   return current;
00346 
00347   END_OF_MED(LOC);
00348 }
00349 
00350 //================================================================================
00352 //================================================================================
00353 
00354 void GMESH::rmDriver (int index/*=0*/)
00355 {
00356   const char * LOC = "GMESH::rmDriver (int index=0): ";
00357   BEGIN_OF_MED(LOC);
00358 
00359   if (index >= 0 && index < (int)_drivers.size() && _drivers[index])
00360   {
00361     delete _drivers[index];
00362     _drivers[index] = 0;
00363   }
00364   else
00365     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC)
00366                                      << "The index given is invalid, index must be between  0 and  |"
00367                                      << _drivers.size()
00368                                      ));
00369   END_OF_MED(LOC);
00370 }
00371 
00372 //================================================================================
00377 //================================================================================
00378 
00379 void GMESH::read(int index)
00380 {
00381   const char * LOC = "GMESH::read(int index=0) : ";
00382   BEGIN_OF_MED(LOC);
00383 
00384   if (index >= 0 && index < (int)_drivers.size() && _drivers[index])
00385   {
00386     _drivers[index]->open();
00387     try
00388     {
00389       _drivers[index]->read();
00390     }
00391     catch ( const MEDEXCEPTION& ex )
00392     {
00393       _drivers[index]->close();
00394       throw ex;
00395     }
00396     _drivers[index]->close();
00397   }
00398   else
00399     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC)
00400                                      << "The index given is invalid, index must be between  0 and |"
00401                                      << _drivers.size()
00402                                      ));
00403   END_OF_MED(LOC);
00404 }
00405 
00406 //================================================================================
00410 //================================================================================
00411 
00412 void GMESH::read(const GENDRIVER & driver)
00413 {
00414   // For the case where driver does not know about me since it has been created through
00415   // constructor witout parameters: create newDriver knowing me and get missing data
00416   // from driver using merge()
00417   auto_ptr<GENDRIVER> newDriver( DRIVERFACTORY::buildDriverForMesh(driver.getDriverType(),
00418                                                                    driver.getFileName(),
00419                                                                    this,
00420                                                                    driver.getMeshName(),
00421                                                                    driver.getAccessMode()));
00422   newDriver->merge( driver );
00423 
00424   newDriver->open();
00425   try
00426   {
00427     newDriver->read();
00428   }
00429   catch ( const MEDEXCEPTION& ex )
00430   {
00431     newDriver->close();
00432     throw ex;
00433   }
00434   newDriver->close();
00435 }
00436 
00437 //================================================================================
00444 //================================================================================
00445 
00446 void GMESH::read(driverTypes        driverType,
00447                  const std::string& filename,
00448                  const std::string& meshname)
00449 {
00450   auto_ptr<GENDRIVER> newDriver( DRIVERFACTORY::buildDriverForMesh(driverType, filename,
00451                                                                    this, meshname, RDONLY));
00452   newDriver->open();
00453   try
00454   {
00455     newDriver->read();
00456   }
00457   catch ( const MEDEXCEPTION& ex )
00458   {
00459     newDriver->close();
00460     throw ex;
00461   }
00462   newDriver->close();
00463 }
00464 
00465 //================================================================================
00477 //================================================================================
00478 
00479 void GMESH::write(int index) const
00480 {
00481   const char * LOC = "GMESH::write(int index=0) : ";
00482   BEGIN_OF_MED(LOC);
00483 
00484   if ( index > -1 && index < (int)_drivers.size() && _drivers[index] )
00485   {
00486     _drivers[index]->open();
00487     try
00488     {
00489       _drivers[index]->write();
00490     }
00491     catch ( const MEDEXCEPTION& ex )
00492     {
00493       _drivers[index]->close();
00494       throw ex;
00495     }
00496     _drivers[index]->close();
00497   }
00498   else
00499     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC)
00500                                      << "The index given is invalid, index must be between  0 and |"
00501                                      << _drivers.size()
00502                                      ));
00503   END_OF_MED(LOC);
00504 }
00505 
00506 //================================================================================
00510 //================================================================================
00511 
00512 void GMESH::write(const GENDRIVER & driver, MED_EN::med_mode_acces medMode/*=MED_EN::WRONLY*/) const
00513 {
00514   // For the case where driver does not know about me since it has been created through
00515   // constructor witout parameters: create newDriver knowing me and get missing data
00516   // from driver using merge()
00517   auto_ptr<GENDRIVER> newDriver( DRIVERFACTORY::buildDriverForMesh(driver.getDriverType(),
00518                                                                    driver.getFileName(),
00519                                                                    const_cast<GMESH*>( this ),
00520                                                                    driver.getMeshName(),
00521                                                                    MED_EN::WRONLY));
00522   newDriver->merge( driver );
00523 //   if ( newDriver->getDriverType() == MED_DRIVER )
00524 //     newDriver->setAccessMode( MED_EN::med_mode_acces( getMedAccessMode( medMode )));
00525 
00526   newDriver->open();
00527   try
00528   {
00529     newDriver->write();
00530   }
00531   catch ( const MEDEXCEPTION& ex )
00532   {
00533     newDriver->close();
00534     throw ex;
00535   }
00536   newDriver->close();
00537 }
00538 
00539 //================================================================================
00547 //================================================================================
00548 
00549 void GMESH::write(driverTypes        driverType,
00550                   const std::string& filename,
00551                   const std::string& meshname,
00552                   MED_EN::med_mode_acces medMode/*=MED_EN::WRONLY*/) const
00553 {
00554   auto_ptr<GENDRIVER> newDriver
00555     ( DRIVERFACTORY::buildDriverForMesh(driverType, filename,
00556                                         const_cast<GMESH*> ( this ),
00557                                         meshname.empty() ? _name : meshname,
00558                                         MED_EN::WRONLY));
00559 
00560 //   if ( newDriver->getDriverType() == MED_DRIVER )
00561 //     newDriver->setAccessMode( MED_EN::med_mode_acces( getMedAccessMode( medMode ) ));
00562 
00563   newDriver->open();
00564   try
00565   {
00566     newDriver->write();
00567   }
00568   catch ( const MEDEXCEPTION& ex )
00569   {
00570     newDriver->close();
00571     throw ex;
00572   }
00573   newDriver->close();
00574 }
00583 //================================================================================
00588 //================================================================================
00589 
00590 void GMESH::setName(std::string name)
00591 {
00592   _name=name; //NOM interne à la classe
00593 }
00594 
00595 //================================================================================
00599 //================================================================================
00600 
00601 string GMESH::getName() const
00602 {
00603   return _name;
00604 }
00605 
00606 //================================================================================
00611 //================================================================================
00612 
00613 void GMESH::setDescription(std::string description)
00614 {
00615   _description = description; //NOM interne à la classe
00616 }
00617 
00618 //================================================================================
00622 //================================================================================
00623 
00624 string GMESH::getDescription() const
00625 {
00626   return _description;
00627 }
00628 
00629 //================================================================================
00633 //================================================================================
00634 
00635 int GMESH::getSpaceDimension() const
00636 {
00637   return _spaceDimension;
00638 }
00639 
00654 //================================================================================
00658 //================================================================================
00659 
00660 int GMESH::getNumberOfFamilies (MED_EN::medEntityMesh entity) const
00661 {
00662   switch (entity) {
00663   case MED_EN::MED_NODE : return _familyNode.size();
00664   case MED_EN::MED_CELL : return _familyCell.size();
00665   case MED_EN::MED_FACE : return _familyFace.size();
00666   case MED_EN::MED_EDGE : return _familyEdge.size();
00667   default :
00668     throw MEDEXCEPTION("MESH::getNumberOfFamilies : Unknown entity");
00669   }
00670 }
00671 //================================================================================
00673 //================================================================================
00674 
00675 const vector<MEDMEM::FAMILY*> GMESH::getFamilies(MED_EN::medEntityMesh entity) const
00676 {
00677   switch (entity) {
00678   case MED_EN::MED_NODE : return _familyNode;
00679   case MED_EN::MED_CELL : return _familyCell;
00680   case MED_EN::MED_FACE : return _familyFace;
00681   case MED_EN::MED_EDGE : return _familyEdge;
00682   default :
00683     throw MEDEXCEPTION("MESH::getFamilies : Unknown entity");
00684   }
00685 }
00686 
00687 //================================================================================
00694 //================================================================================
00695 
00696 const MEDMEM::FAMILY* GMESH::getFamily(MED_EN::medEntityMesh entity, int i) const
00697 {
00698   if (i<=0)
00699     throw MEDEXCEPTION("MESH::getFamily(i) : argument i must be > 0");
00700   const vector<FAMILY*>* Family;
00701   switch (entity) {
00702   case MED_EN::MED_NODE : Family = &_familyNode; break;
00703   case MED_EN::MED_CELL : Family = &_familyCell; break;
00704   case MED_EN::MED_FACE : Family = &_familyFace; break;
00705   case MED_EN::MED_EDGE : Family = &_familyEdge; break;
00706   default :
00707     throw MEDEXCEPTION("MESH::getFamilies : Unknown entity");
00708   }
00709   if (i>(int)Family->size())
00710     throw MEDEXCEPTION("MESH::getFamily(entity,i) : argument i must be <= _numberOfFamilies");
00711   return (*Family)[i-1];
00712 }
00713 
00714 
00715 //================================================================================
00717 //================================================================================
00718 
00719 int GMESH::getNumberOfGroups (MED_EN::medEntityMesh entity) const
00720 {
00721   switch (entity) {
00722   case MED_EN::MED_NODE : return _groupNode.size();
00723   case MED_EN::MED_CELL : return _groupCell.size();
00724   case MED_EN::MED_FACE : return _groupFace.size();
00725   case MED_EN::MED_EDGE : return _groupEdge.size();
00726   default :
00727     throw MEDEXCEPTION("MESH::getNumberOfGroups : Unknown entity");
00728   }
00729 }
00730 //================================================================================
00733 //================================================================================
00734 
00735 const vector<GROUP*> GMESH::getGroups(MED_EN::medEntityMesh entity) const
00736 {
00737   switch (entity) {
00738   case MED_EN::MED_NODE : return _groupNode;
00739   case MED_EN::MED_CELL : return _groupCell;
00740   case MED_EN::MED_FACE : return _groupFace;
00741   case MED_EN::MED_EDGE : return _groupEdge;
00742   default :
00743     throw MEDEXCEPTION("MESH::getGroups : Unknown entity");
00744   }
00745 }
00746 
00747 //================================================================================
00754 //================================================================================
00755 
00756 const GROUP* GMESH::getGroup(MED_EN::medEntityMesh entity, int i) const
00757 {
00758   const char * LOC = "GMESH::getGroup(medEntityMesh entity, int i) : ";
00759   if (i<=0)
00760     throw MEDEXCEPTION(LOCALIZED(STRING(LOC)<<"argument i must be > 0"));
00761   const vector<GROUP*>* Group = 0;
00762   switch (entity) {
00763   case MED_EN::MED_NODE : Group = &_groupNode; break;
00764   case MED_EN::MED_CELL : Group = &_groupCell; break;
00765   case MED_EN::MED_FACE : Group = &_groupFace; break;
00766   case MED_EN::MED_EDGE : Group = &_groupEdge; break;
00767   default :
00768     throw MEDEXCEPTION(LOCALIZED(STRING(LOC)<<"Unknown entity"));
00769   }
00770   if (i>(int)Group->size())
00771     throw MEDEXCEPTION(LOCALIZED(STRING(LOC)<<"argument i="<<i<<" must be <= _numberOfGroups="<<Group->size()));
00772   return (*Group)[i-1];
00773 }
00774 
00775 //================================================================================
00782 //================================================================================
00783 
00784 const GROUP* GMESH::getGroup(const string& name) const  throw (MEDEXCEPTION)
00785 {
00786   const vector<GROUP*>* group_vectors [4]={&_groupNode, &_groupEdge,&_groupFace,&_groupCell};
00787   for (int ientity=0;ientity<4;ientity++)
00788     for (unsigned igroup=0; igroup< group_vectors[ientity]->size();igroup++)
00789     {
00790       const vector<GROUP*>& group_vect = *group_vectors[ientity];
00791       GROUP* group=group_vect[igroup];
00792       if (group->getName()==name)
00793         return group;
00794     }
00795   cerr << "MESH::getGroup("<<name<<") : group "<<name <<" was not found"<<endl;
00796   throw MEDEXCEPTION("MESH::getGroup(name) : name not found");
00797 }
00798 
00799 //================================================================================
00803 //================================================================================
00804 
00805 const SUPPORT * GMESH::getSupportOnAll(medEntityMesh entity) const throw(MEDEXCEPTION)
00806 {
00807   const char * LOC = "GMESH::getSupportOnAll : " ;
00808   BEGIN_OF_MED(LOC) ;
00809   if(entity == MED_ALL_ENTITIES)
00810     throw MEDEXCEPTION(LOCALIZED(STRING(LOC)<<"Support not defined on entity MED_ALL_ENTITIES !"));
00811 
00812   map<medEntityMesh,SUPPORT*>::const_iterator it =  _entitySupport.find(entity);
00813 
00814   // find support and return is if exists
00815   if(it != _entitySupport.end())
00816     return (*it).second;
00817   else
00818     {
00819       //build, store and return support
00820       GMESH* thisMesh = const_cast< GMESH* >( this );
00821       SUPPORT * aSupport = new SUPPORT;
00822       string aSuppName = "SupportOnAll_"+entNames[entity];
00823       aSupport->setName( aSuppName );
00824       aSupport->setMesh( thisMesh );
00825       aSupport->setEntity( entity );
00826       aSupport->setAll( true );
00827       aSupport->update();
00828 
00829       thisMesh->_entitySupport.insert(make_pair(entity,aSupport));
00830       thisMesh->removeReference();
00831 
00832       return aSupport;
00833     }
00834 }
00835 
00843 //================================================================================
00848 //================================================================================
00849 
00850 SUPPORT * GMESH::mergeSupports(const std::vector<SUPPORT *> Supports) throw (MEDEXCEPTION)
00851 {
00852   const char * LOC = "GMESH::mergeSupports(const vector<SUPPORT *> ) : " ;
00853   BEGIN_OF_MED(LOC) ;
00854 
00855   SUPPORT * returnedSupport;
00856   string returnedSupportName;
00857   string returnedSupportDescription;
00858   char * returnedSupportNameChar;
00859   char * returnedSupportDescriptionChar;
00860   int size = Supports.size();
00861 
00862   if (size == 0)
00863     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) <<
00864                                      " mergeSupports() does't accept zero size vector"));
00865 
00866   if (size == 1)
00867   {
00868     MESSAGE_MED(LOC <<" there is only one SUPPORT in the argument list, the method return a copy of this object !");
00869     SUPPORT * obj = const_cast <SUPPORT *> (Supports[0]);
00870 
00871     returnedSupport = new SUPPORT(*obj);
00872 
00873     int lenName = strlen((Supports[0]->getName()).c_str()) + 8 + 1;
00874     int lenDescription = strlen((Supports[0]->getDescription()).c_str()) + 8 + 1;
00875 
00876     returnedSupportNameChar = new char[lenName];
00877     returnedSupportDescriptionChar = new char[lenDescription];
00878 
00879     returnedSupportNameChar = strcpy(returnedSupportNameChar,"Copy of ");
00880     returnedSupportNameChar = strcat(returnedSupportNameChar,(Supports[0]->getName()).c_str());
00881     returnedSupportDescriptionChar = strcpy(returnedSupportDescriptionChar,"Copy of ");
00882     returnedSupportDescriptionChar = strcat(returnedSupportDescriptionChar,
00883                                             (Supports[0]->getDescription()).c_str());
00884 
00885     returnedSupportName = string(returnedSupportNameChar);
00886     returnedSupportDescription = string(returnedSupportDescriptionChar);
00887 
00888     returnedSupport->setName(returnedSupportName);
00889     returnedSupport->setDescription(returnedSupportDescription);
00890 
00891     delete [] returnedSupportNameChar;
00892     delete [] returnedSupportDescriptionChar;
00893   }
00894   else
00895   {
00896     SUPPORT * obj = const_cast <SUPPORT *> (Supports[0]);
00897     returnedSupport = new SUPPORT(*obj);
00898 
00899     int lenName = strlen((Supports[0]->getName()).c_str()) + 9 + 1;
00900     int lenDescription = strlen((Supports[0]->getDescription()).c_str()) + 9 + 1;
00901 
00902     for(int i = 1;i<size;i++)
00903     {
00904       obj = const_cast <SUPPORT *> (Supports[i]);
00905       returnedSupport->blending(obj);
00906 
00907       if (i == (size-1))
00908       {
00909         lenName = lenName + 5 + strlen((Supports[i]->getName()).c_str());
00910         lenDescription = lenDescription + 5 +
00911           strlen((Supports[i]->getDescription()).c_str());
00912       }
00913       else
00914       {
00915         lenName = lenName + 2 + strlen((Supports[i]->getName()).c_str());
00916         lenDescription = lenDescription + 2 +
00917           strlen((Supports[i]->getDescription()).c_str());
00918       }
00919     }
00920 
00921     returnedSupportNameChar = new char[lenName];
00922     returnedSupportDescriptionChar = new char[lenDescription];
00923 
00924     returnedSupportNameChar = strcpy(returnedSupportNameChar,"Merge of ");
00925     returnedSupportDescriptionChar = strcpy(returnedSupportDescriptionChar,"Merge of ");
00926 
00927     returnedSupportNameChar = strcat(returnedSupportNameChar,(Supports[0]->getName()).c_str());
00928     returnedSupportDescriptionChar = strcat(returnedSupportDescriptionChar,
00929                                             (Supports[0]->getDescription()).c_str());
00930 
00931     for(int i = 1;i<size;i++)
00932     {
00933       if (i == (size-1))
00934       {
00935         returnedSupportNameChar = strcat(returnedSupportNameChar," and ");
00936         returnedSupportDescriptionChar = strcat(returnedSupportDescriptionChar," and ");
00937 
00938         returnedSupportNameChar = strcat(returnedSupportNameChar,
00939                                          (Supports[i]->getName()).c_str());
00940         returnedSupportDescriptionChar = strcat(returnedSupportDescriptionChar,
00941                                                 (Supports[i]->getDescription()).c_str());
00942       }
00943       else
00944       {
00945         returnedSupportNameChar = strcat(returnedSupportNameChar,", ");
00946         returnedSupportNameChar = strcat(returnedSupportNameChar,
00947                                          (Supports[i]->getName()).c_str());
00948 
00949         returnedSupportDescriptionChar = strcat(returnedSupportDescriptionChar,", ");
00950         returnedSupportDescriptionChar = strcat(returnedSupportDescriptionChar,
00951                                                 (Supports[i]->getDescription()).c_str());
00952       }
00953     }
00954 
00955     returnedSupportName = string(returnedSupportNameChar);
00956     returnedSupport->setName(returnedSupportName);
00957 
00958     returnedSupportDescription = string(returnedSupportDescriptionChar);
00959     returnedSupport->setDescription(returnedSupportDescription);
00960 
00961     delete [] returnedSupportNameChar;
00962     delete [] returnedSupportDescriptionChar;
00963   }
00964 
00965   END_OF_MED(LOC);
00966   return returnedSupport;
00967 }
00968 
00969 //================================================================================
00975 //================================================================================
00976 
00977 SUPPORT * GMESH::intersectSupports(const std::vector<SUPPORT *> Supports) throw (MEDEXCEPTION)
00978 {
00979   const char* LOC = "MESH:::intersectSupports(const vector<SUPPORT *> ) : ";
00980   BEGIN_OF_MED(LOC);
00981 
00982   SUPPORT * returnedSupport;
00983   string returnedSupportName;
00984   string returnedSupportDescription;
00985   char * returnedSupportNameChar;
00986   char * returnedSupportDescriptionChar;
00987   int size = Supports.size();
00988 
00989   if (size == 1)
00990   {
00991     MESSAGE_MED(PREFIX_MED <<" there is only one SUPPORT in the argument list, the method return a copy of this object !");
00992     SUPPORT * obj = const_cast <SUPPORT *> (Supports[0]);
00993 
00994     returnedSupport = new SUPPORT(*obj);
00995 
00996     int lenName = strlen((Supports[0]->getName()).c_str()) + 8 + 1;
00997     int lenDescription = strlen((Supports[0]->getDescription()).c_str()) + 8 + 1;
00998 
00999     returnedSupportNameChar = new char[lenName];
01000     returnedSupportDescriptionChar = new char[lenDescription];
01001 
01002     returnedSupportNameChar = strcpy(returnedSupportNameChar,"Copy of ");
01003     returnedSupportNameChar = strcat(returnedSupportNameChar,(Supports[0]->getName()).c_str());
01004     returnedSupportDescriptionChar = strcpy(returnedSupportDescriptionChar,"Copy of ");
01005     returnedSupportDescriptionChar = strcat(returnedSupportDescriptionChar,
01006                                             (Supports[0]->getDescription()).c_str());
01007 
01008     returnedSupportName = string(returnedSupportNameChar);
01009     returnedSupportDescription = string(returnedSupportDescriptionChar);
01010 
01011     returnedSupport->setName(returnedSupportName);
01012     returnedSupport->setDescription(returnedSupportDescription);
01013 
01014     delete [] returnedSupportNameChar;
01015     delete [] returnedSupportDescriptionChar;
01016   }
01017   else
01018   {
01019     SUPPORT * obj = const_cast <SUPPORT *> (Supports[0]);
01020     returnedSupport = new SUPPORT(*obj);
01021 
01022     int lenName = strlen((Supports[0]->getName()).c_str()) + 16 + 1;
01023     int lenDescription = strlen((Supports[0]->getDescription()).c_str()) + 16 + 1;
01024 
01025     for(int i = 1;i<size;i++)
01026     {
01027       obj = const_cast <SUPPORT *> (Supports[i]);
01028       returnedSupport->intersecting(obj);
01029 
01030       if (i == (size-1))
01031       {
01032         lenName = lenName + 5 + strlen((Supports[i]->getName()).c_str());
01033         lenDescription = lenDescription + 5 +
01034           strlen((Supports[i]->getDescription()).c_str());
01035       }
01036       else
01037       {
01038         lenName = lenName + 2 + strlen((Supports[i]->getName()).c_str());
01039         lenDescription = lenDescription + 2 +
01040           strlen((Supports[i]->getDescription()).c_str());
01041       }
01042     }
01043     if(returnedSupport != (SUPPORT *) NULL)
01044     {
01045       returnedSupportNameChar = new char[lenName];
01046       returnedSupportDescriptionChar = new char[lenDescription];
01047 
01048       returnedSupportNameChar = strcpy(returnedSupportNameChar,
01049                                        "Intersection of ");
01050       returnedSupportDescriptionChar =
01051         strcpy(returnedSupportDescriptionChar,"Intersection of ");
01052 
01053       returnedSupportNameChar = strcat(returnedSupportNameChar,
01054                                        (Supports[0]->getName()).c_str());
01055       returnedSupportDescriptionChar =
01056         strcat(returnedSupportDescriptionChar,
01057                (Supports[0]->getDescription()).c_str());
01058 
01059       for(int i = 1;i<size;i++)
01060       {
01061         if (i == (size-1))
01062         {
01063           returnedSupportNameChar = strcat(returnedSupportNameChar,
01064                                            " and ");
01065           returnedSupportDescriptionChar =
01066             strcat(returnedSupportDescriptionChar," and ");
01067 
01068           returnedSupportNameChar =
01069             strcat(returnedSupportNameChar,
01070                    (Supports[i]->getName()).c_str());
01071           returnedSupportDescriptionChar =
01072             strcat(returnedSupportDescriptionChar,
01073                    (Supports[i]->getDescription()).c_str());
01074         }
01075         else
01076         {
01077           returnedSupportNameChar = strcat(returnedSupportNameChar,
01078                                            ", ");
01079           returnedSupportNameChar =
01080             strcat(returnedSupportNameChar,
01081                    (Supports[i]->getName()).c_str());
01082 
01083           returnedSupportDescriptionChar =
01084             strcat(returnedSupportDescriptionChar,", ");
01085           returnedSupportDescriptionChar =
01086             strcat(returnedSupportDescriptionChar,
01087                    (Supports[i]->getDescription()).c_str());
01088         }
01089       }
01090 
01091       returnedSupportName = string(returnedSupportNameChar);
01092       returnedSupport->setName(returnedSupportName);
01093 
01094       returnedSupportDescription = string(returnedSupportDescriptionChar);
01095       returnedSupport->setDescription(returnedSupportDescription);
01096 
01097       delete [] returnedSupportNameChar;
01098       delete [] returnedSupportDescriptionChar;
01099     }
01100   }
01101 
01102   END_OF_MED(LOC);
01103   return returnedSupport;
01104 }
01105 
01114 SUPPORT * GMESH::buildSupportOnElementsFromElementList(const list<int>& listOfElt, MED_EN::medEntityMesh entity) const throw (MEDEXCEPTION)
01115 {
01116   const char* LOC = "GMESH::buildSupportOnElementsFromElementList : ";
01117   BEGIN_OF_MED(LOC);
01118   SUPPORT * mySupport = new SUPPORT();
01119   mySupport->setMesh((MESH *)this);
01120   mySupport->setName("Boundary");
01121   mySupport->setEntity( entity );
01122   mySupport->fillFromElementList(listOfElt);
01123   END_OF_MED(LOC);
01124   return mySupport ;
01125 }
01126 
01127 // internal helper type
01128 struct _cell
01129 {
01130   std::vector<int> groups;
01131   MED_EN::medGeometryElement geometricType;
01132   // to have geometricType good for nodal groups when MESH::getNumberOfTypes(MED_NODE)==0
01133   _cell():geometricType(MED_POINT1) {}
01134 };
01135 
01136 //================================================================================
01144 //================================================================================
01145 
01146 void GMESH::createFamilies()
01147 {
01148   int idFamNode = 0; // identifier for node families
01149   int idFamElement = 0; // identifier for cell, face or edge families
01150 
01151   // Main loop on mesh's entities
01152   for (medEntityMesh entity=MED_CELL; entity!=MED_ALL_ENTITIES; ++entity)
01153   {
01154     int numberofgroups = getNumberOfGroups(entity);
01155     if(!numberofgroups)
01156       continue; // no groups for this entity
01157 
01158     vector< vector<FAMILY*> > whichFamilyInGroup(numberofgroups); // this container is used to update groups at the end
01159 
01160     // make myFamilies points to the member corresponding to entity
01161     vector<FAMILY*>* myFamilies;
01162     switch ( entity )
01163     {
01164     case MED_CELL : myFamilies = & _familyCell; break;
01165     case MED_FACE : myFamilies = & _familyFace; break;
01166     case MED_EDGE : myFamilies = & _familyEdge; break;
01167     case MED_NODE : myFamilies = & _familyNode; break;
01168     }
01169 
01170     vector<GROUP*> myGroups=getGroups(entity); // get a copy of the groups ptr for the entity
01171     // get a copy of the (old) family ptrs before clearing
01172     vector<FAMILY*> myOldFamilies=getFamilies(entity);
01173     myFamilies->clear();
01174 
01175 
01176     // 1 - Create a vector containing for each cell (of the entity) an information structure
01177     //     giving geometric type and the groups it belong to
01178 
01179     med_int numberOfTypes=0;
01180     const medGeometryElement* geometricTypes = 0;
01181     if ( entity != MED_NODE)
01182     {
01183       numberOfTypes = getNumberOfTypes(entity);
01184       geometricTypes = getTypes(entity);
01185     }
01186     med_int numberOfCells=getNumberOfElements(entity, MED_ALL_ELEMENTS);  // total number of cells for that entity
01187     SCRUTE_MED(numberOfTypes);
01188     SCRUTE_MED(numberOfCells);
01189     vector< _cell > tab_cell(numberOfCells);
01190     vector< _cell >::iterator cell = tab_cell.begin();
01191     for(med_int t=0; t!=numberOfTypes; ++t)
01192     {
01193       int nbCellsOfType = getNumberOfElements(entity,geometricTypes[t]);
01194       for(int n=0; n!=nbCellsOfType; ++n, ++cell)
01195         cell->geometricType=geometricTypes[t];
01196     }
01197 
01198     // 2 - Scan cells in groups and update in tab_cell the container of groups a cell belong to
01199 
01200     for (unsigned g=0; g!=myGroups.size(); ++g)
01201     {
01202       // scan cells that belongs to the group
01203       const int* groupCells=myGroups[g]->getnumber()->getValue();
01204       int nbCells=myGroups[g]->getnumber()->getLength();
01205       for(int c=0; c!=nbCells; ++c)
01206         tab_cell[groupCells[c]-1].groups.push_back(g);
01207     }
01208 
01209 
01210     // 3 - Scan the cells vector, genarate family name, and create a map associating the family names
01211     //     whith the vector of contained cells
01212 
01213     map< string,vector<int> > tab_families;
01214     map< string,vector<int> >::iterator fam;
01215     for(int n=0; n!=numberOfCells; ++n)
01216     {
01217       ostringstream key; // to generate the name of the family
01218       key << "FAM";
01219       if(tab_cell[n].groups.empty()) // this cell don't belong to any group
01220         key << "_NONE" << entity;
01221 
01222       for(vector<int>::const_iterator it=tab_cell[n].groups.begin(); it!=tab_cell[n].groups.end(); ++it)
01223       {
01224         string groupName=myGroups[*it]->getName();
01225         if(groupName.empty())
01226           key << "_G" << *it;
01227         else
01228           key << "_" << groupName;
01229       }
01230 
01231       tab_families[key.str()].push_back(n+1); // fill the vector of contained cells associated whith the family
01232     }
01233 
01234 
01235     // 4 - Scan the family map, create MED Families, check if it already exist.
01236 
01237     for( fam=tab_families.begin(); fam!=tab_families.end(); ++fam)
01238     {
01239       vector<medGeometryElement> tab_types_geometriques;
01240       medGeometryElement geometrictype=MED_NONE;
01241       vector<int> tab_index_types_geometriques;
01242       vector<int> tab_nombres_elements;
01243       if ( fam->second.empty() )
01244         continue; // it is just a truncated long family name
01245 
01246       // scan family cells and fill the tab that are needed by the create a MED FAMILY
01247       for( unsigned i=0; i!=fam->second.size(); ++i)
01248       {
01249         int ncell=fam->second[i]-1;
01250         if(tab_cell[ncell].geometricType != geometrictype)
01251         {
01252           // new geometric type -> we store it and complete index tabs
01253           if(!tab_index_types_geometriques.empty())
01254             tab_nombres_elements.push_back(i+1-tab_index_types_geometriques.back());
01255           tab_types_geometriques.push_back( (geometrictype=tab_cell[ncell].geometricType));
01256           tab_index_types_geometriques.push_back(i+1);
01257         }
01258       }
01259       // store and complete index tabs for the last geometric type
01260       tab_nombres_elements.push_back(fam->second.size()+1-tab_index_types_geometriques.back());
01261       tab_index_types_geometriques.push_back(fam->second.size()+1);
01262 
01263       // family name sould not be longer than MED_TAILLE_NOM
01264       string famName = fam->first;
01265       if ( famName.size() > MED_NAME_SIZE ) {
01266         // try to cut off "FAM_" from the head
01267         if ( famName.size() - 4 <= MED_NAME_SIZE ) {
01268           famName = famName.substr(4);
01269         }
01270         else { // try to make a unique name by cutting off char by char from the tail
01271           famName = famName.substr(0, MED_NAME_SIZE);
01272           map< string,vector<int> >::iterator foundName = tab_families.find( famName );
01273           while ( !famName.empty() &&
01274                   ( foundName != tab_families.end() || famName[ famName.size()-1 ] == ' ' ))
01275           {
01276             famName = famName.substr( 0, famName.size() - 1 );
01277             foundName = tab_families.find( famName );
01278           }
01279         }
01280         tab_families[ famName ]; // add a new name in the table to assure uniqueness
01281       }
01282 
01283       // create a MED FAMILY and fill it with the tabs we constructed
01284       FAMILY* newFam = new FAMILY();
01285       newFam->setName(famName);
01286       newFam->setMesh(this);
01287       removeReference();
01288       newFam->setNumberOfGeometricType(tab_types_geometriques.size());
01289       newFam->setGeometricType(&tab_types_geometriques[0]); // we know the tab is not empy
01290       newFam->setNumberOfElements(&tab_nombres_elements[0]);
01291       newFam->setNumber(&tab_index_types_geometriques[0],&fam->second[0]);
01292       newFam->setEntity(entity);
01293       newFam->setAll( getNumberOfElements( entity, MED_ALL_ELEMENTS ) == fam->second.size() );
01294 
01295       int idFam = 0;
01296 
01297       switch ( entity )
01298       {
01299       case MED_NODE :
01300         ++idFamNode;
01301         idFam = idFamNode;
01302         break;
01303       case MED_CELL :
01304       case MED_FACE :
01305       case MED_EDGE :
01306         ++idFamElement;
01307         idFam = -idFamElement;
01308         break;
01309       }
01310 
01311       newFam->setIdentifier(idFam);
01312 
01313       // Update links between families and groups
01314 
01315       int ncell1=fam->second[0]-1;  // number of first cell in family
01316       int numberOfGroups=tab_cell[ncell1].groups.size(); // number of groups in the family
01317       if(numberOfGroups)
01318       {
01319         newFam->setNumberOfGroups(numberOfGroups);
01320         string * groupNames=new string[numberOfGroups];
01321 
01322         // iterate on the groups the family belongs to
01323         vector<int>::const_iterator it=tab_cell[ncell1].groups.begin();
01324         for(int ng=0 ; it!=tab_cell[ncell1].groups.end(); ++it, ++ng)
01325         {
01326           whichFamilyInGroup[*it].push_back(newFam);
01327           groupNames[ng]=myGroups[*it]->getName();
01328         }
01329         newFam->setGroupsNames(groupNames);
01330         delete [] groupNames;
01331       }
01332 
01333       MESSAGE_MED("  MESH::createFamilies() entity " << entity <<
01334                   " size " << myFamilies->size());
01335 
01336       myFamilies->push_back(newFam);
01337     }
01338 
01339     // delete old families
01340     for (unsigned int i=0;i<myOldFamilies.size();i++)
01341       myOldFamilies[i]->removeReference();
01342 
01343     // update references in groups
01344     for (unsigned int i=0;i<myGroups.size();i++)
01345     {
01346       myGroups[i]->setNumberOfFamilies(whichFamilyInGroup[i].size());
01347       myGroups[i]->setFamilies(whichFamilyInGroup[i]);
01348     }
01349 
01350     // re-scan the cells vector, and fill the family vector with cells.
01351     // creation of support, check if it already exist.
01352   }
01353 }
01354 
01355 //================================================================================
01363 //================================================================================
01364 
01365 void GMESH::createGroups()
01366 {
01367   for (medEntityMesh entity=MED_CELL; entity!=MED_ALL_ENTITIES; ++entity)
01368   {
01369     // make myFamilies points to the member corresponding to entity
01370     vector<FAMILY*>* myFamilies;
01371     vector<GROUP*>* myGroups;
01372     switch ( entity )
01373     {
01374     case MED_CELL :
01375       myFamilies = & _familyCell;
01376       myGroups = & _groupCell;
01377       break;
01378     case MED_FACE :
01379       myFamilies = & _familyFace;
01380       myGroups = & _groupFace;
01381       break;
01382     case MED_EDGE :
01383       myFamilies = & _familyEdge;
01384       myGroups = & _groupEdge;
01385       break;
01386     case MED_NODE :
01387       myFamilies = & _familyNode;
01388       myGroups = & _groupNode;
01389       break;
01390     }
01391 
01392 
01393     for (unsigned i=0; i< myFamilies->size(); i++)
01394     {
01395       list <FAMILY*> fam_list;
01396       fam_list.push_back((*myFamilies)[i]);
01397       //creates a group with the family name and only one family
01398       GROUP* group=new GROUP((*myFamilies)[i]->getName(),fam_list);
01399       (*myGroups).push_back(group);
01400       removeReference();
01401     }
01402   }
01403 }