Salome HOME
MEDReader again
[modules/med.git] / src / MEDLoader / MEDFileMesh.cxx
index 74a40b7f0443866c973a137b50c5211237253715..615abd7aaace8a0c9bd0483bbbe254288dcb0959 100644 (file)
@@ -20,6 +20,8 @@
 
 #include "MEDFileMesh.hxx"
 #include "MEDFileUtilities.hxx"
+#include "MEDFileFieldOverView.hxx"
+#include "MEDFileField.hxx"
 #include "MEDLoader.hxx"
 #include "MEDLoaderBase.hxx"
 
@@ -1960,7 +1962,7 @@ MEDFileMesh *MEDFileUMesh::deepCpy() const throw(INTERP_KERNEL::Exception)
   for(std::vector< MEDCouplingAutoRefCountObjectPtr<MEDFileUMeshSplitL1> >::const_iterator it=_ms.begin();it!=_ms.end();it++,i++)
     {
       if((const MEDFileUMeshSplitL1 *)(*it))
-        ret->_ms[i]=(*it)->deepCpy();
+        ret->_ms[i]=(*it)->deepCpy(ret->_coords);
     }
   return ret.retn();
 }
@@ -2616,6 +2618,40 @@ int MEDFileUMesh::getNumberOfNodes() const throw(INTERP_KERNEL::Exception)
   return coo->getNumberOfTuples();
 }
 
+void MEDFileUMesh::whichAreNodesFetched(const MEDFileField1TSStructItem& st, const MEDFileFieldGlobsReal *globs, std::vector<bool>& nodesFetched) const throw(INTERP_KERNEL::Exception)
+{
+  std::size_t sz(st.getNumberOfItems());
+  int mdim(getMeshDimension());
+  for(std::size_t i=0;i<sz;i++)
+    {
+      INTERP_KERNEL::NormalizedCellType curGt(st[i].getGeo());
+      const INTERP_KERNEL::CellModel& cm=INTERP_KERNEL::CellModel::GetCellModel(curGt);
+      int relDim((int)cm.getDimension()-mdim);
+      MEDCouplingAutoRefCountObjectPtr<MEDCouplingUMesh> um(getMeshAtLevel(relDim));
+      std::vector<int> d(um->getDistributionOfTypes());
+      std::size_t nbOfTypes(d.size()/3);
+      int offset=0,nbOfEltWT=-1;
+      for(std::size_t j=0;j<nbOfTypes;j++)
+        {
+          if(d[3*j]!=(int)curGt)
+            offset+=d[3*j+1];
+          else
+            { break; nbOfEltWT=d[3*j+1]; }
+        }
+      if(nbOfEltWT==-1)
+        throw INTERP_KERNEL::Exception("MEDFileUMesh::whichAreNodesFetched : asking for a geo type not present in this !");
+      um=dynamic_cast<MEDCouplingUMesh *>(um->buildPartOfMySelf2(offset,offset+nbOfEltWT,1,true));
+      if(st[i].getPflName().empty())
+        um->computeNodeIdsAlg(nodesFetched);
+      else
+        {
+          const DataArrayInt *arr(globs->getProfile(st[i].getPflName().c_str()));
+          um=dynamic_cast<MEDCouplingUMesh *>(um->buildPartOfMySelf(arr->begin(),arr->end(),true));
+          um->computeNodeIdsAlg(nodesFetched);
+        }
+    }
+}
+
 /*!
  * Returns the optional numbers of mesh entities of a given dimension transformed using
  * DataArrayInt::invertArrayN2O2O2N().
@@ -2819,7 +2855,7 @@ MEDCouplingUMesh *MEDFileUMesh::getMeshAtLevel(int meshDimRelToMaxExt, bool renu
           MEDCouplingAutoRefCountObjectPtr<DataArrayDouble> cc=_coords->deepCpy();
           umesh->setCoords(cc);
           MEDFileUMeshSplitL1::ClearNonDiscrAttributes(umesh);
-          umesh->setName(getName());
+          umesh->setName(getName().c_str());
           return umesh;
         }
     }
@@ -2898,6 +2934,29 @@ MEDCouplingUMesh *MEDFileUMesh::getLevelM3Mesh(bool renum) const throw(INTERP_KE
   return getMeshAtLevel(-3,renum);
 }
 
+/*!
+ * This method returns a vector of mesh parts containing each exactly one geometric type.
+ * This method will never launch an automatic computation of split by type (an INTERP_KERNEL::Exception will be then thrown).
+ * This method is only for memory aware users.
+ */
+std::vector<MEDCoupling1GTUMesh *> MEDFileUMesh::getDirectUndergroundSingleGeoTypeMeshes(int meshDimRelToMax) const throw(INTERP_KERNEL::Exception)
+{
+  const MEDFileUMeshSplitL1 *sp(getMeshAtLevSafe(meshDimRelToMax));
+  return sp->getDirectUndergroundSingleGeoTypeMeshes();
+}
+
+/*!
+ * This method returns the part of \a this having the geometric type \a gt.
+ * If such part is not existing an exception will be thrown.
+ */
+MEDCoupling1GTUMesh *MEDFileUMesh::getDirectUndergroundSingleGeoTypeMesh(INTERP_KERNEL::NormalizedCellType gt) const throw(INTERP_KERNEL::Exception)
+{
+  const INTERP_KERNEL::CellModel& cm=INTERP_KERNEL::CellModel::GetCellModel(gt);
+  int lev=(int)cm.getDimension()-getMeshDimension();
+  const MEDFileUMeshSplitL1 *sp(getMeshAtLevSafe(lev));
+  return sp->getDirectUndergroundSingleGeoTypeMesh(gt);
+}
+
 const MEDFileUMeshSplitL1 *MEDFileUMesh::getMeshAtLevSafe(int meshDimRelToMaxExt) const throw(INTERP_KERNEL::Exception)
 {
   if(meshDimRelToMaxExt==1)
@@ -2947,7 +3006,6 @@ void MEDFileUMesh::checkMeshDimCoherency(int meshDim, int meshDimRelToMax) const
  *  \param [in] coords - the new node coordinates array.
  *  \throw If \a coords == \c NULL.
  */
-
 void MEDFileUMesh::setCoords(DataArrayDouble *coords) throw(INTERP_KERNEL::Exception)
 {
   if(!coords)
@@ -2959,6 +3017,9 @@ void MEDFileUMesh::setCoords(DataArrayDouble *coords) throw(INTERP_KERNEL::Excep
   _fam_coords=DataArrayInt::New();
   _fam_coords->alloc(nbOfTuples,1);
   _fam_coords->fillWithZero();
+  for(std::vector< MEDCouplingAutoRefCountObjectPtr<MEDFileUMeshSplitL1> >::iterator it=_ms.begin();it!=_ms.end();it++)
+    if((MEDFileUMeshSplitL1 *)(*it))
+      (*it)->setCoords(coords);
 }
 
 /*!
@@ -3064,7 +3125,7 @@ void MEDFileUMesh::duplicateNodesOnM1Group(const char *grpNameM1, DataArrayInt *
   MEDCouplingAutoRefCountObjectPtr<DataArrayInt> szOfCellGrpOfSameType(tmp00);
   MEDCouplingAutoRefCountObjectPtr<DataArrayInt> idInMsOfCellGrpOfSameType(tmp11);
   //
-  newm1->setName(getName());
+  newm1->setName(getName().c_str());
   const DataArrayInt *fam=getFamilyFieldAtLevel(-1);
   if(!fam)
     throw INTERP_KERNEL::Exception("MEDFileUMesh::duplicateNodesOnM1Group : internal problem !");
@@ -3465,7 +3526,7 @@ void MEDFileUMesh::setMeshes(const std::vector<const MEDCouplingUMesh *>& ms, bo
   for(std::vector<const MEDCouplingUMesh *>::const_iterator it=ms.begin();it!=ms.end();it++)
     {
       int mdim=(*it)->getMeshDimension();
-      setName((*it)->getName());
+      setName((*it)->getName().c_str());
       setMeshAtLevel(mdim-zeDim,const_cast<MEDCouplingUMesh *>(*it),renum);
     }
   setName(name.c_str());
@@ -4311,6 +4372,34 @@ int MEDFileStructuredMesh::getNumberOfNodes() const throw(INTERP_KERNEL::Excepti
   return cmesh->getNumberOfNodes();
 }
 
+void MEDFileStructuredMesh::whichAreNodesFetched(const MEDFileField1TSStructItem& st, const MEDFileFieldGlobsReal *globs, std::vector<bool>& nodesFetched) const throw(INTERP_KERNEL::Exception)
+{
+  if(st.getNumberOfItems()!=1)
+    throw INTERP_KERNEL::Exception("MEDFileStructuredMesh::whichAreNodesFetched : The sturture of field is not lying on single geo type ! it is not managed yet for structured mesh !");
+  if(st[0].getGeo()!=MEDCouplingStructuredMesh::GetGeoTypeGivenMeshDimension(getMeshDimension()))
+    throw INTERP_KERNEL::Exception("MEDFileStructuredMesh::whichAreNodesFetched : The sturture of field is not lying on expected geo type !");
+  if(getNumberOfNodes()!=(int)nodesFetched.size())
+    throw INTERP_KERNEL::Exception("MEDFileStructuredMesh::whichAreNodesFetched : invalid size of array !");
+  if(st[0].getPflName().empty())
+    {
+      std::fill(nodesFetched.begin(),nodesFetched.end(),true);
+      return ;
+    }
+  const DataArrayInt *arr(globs->getProfile(st[0].getPflName().c_str()));
+  const MEDCouplingStructuredMesh *cmesh=getStructuredMesh();//cmesh not null because getNumberOfNodes called before
+  int sz(nodesFetched.size());
+  for(const int *work=arr->begin();work!=arr->end();work++)
+    {
+      std::vector<int> conn;
+      cmesh->getNodeIdsOfCell(*work,conn);
+      for(std::vector<int>::const_iterator it=conn.begin();it!=conn.end();it++)
+        if(*it>=0 && *it<sz)
+          nodesFetched[*it]=true;
+        else
+          throw INTERP_KERNEL::Exception("MEDFileStructuredMesh::whichAreNodesFetched : internal error !");
+    }
+}
+
 med_geometry_type MEDFileStructuredMesh::GetGeoTypeFromMeshDim(int meshDim) throw(INTERP_KERNEL::Exception)
 {
   med_geometry_type geoTypeReq=MED_NONE;
@@ -4961,7 +5050,7 @@ std::size_t MEDFileMeshMultiTS::getHeapMemorySize() const
   return ret;
 }
 
-const char *MEDFileMeshMultiTS::getName() const throw(INTERP_KERNEL::Exception)
+std::string MEDFileMeshMultiTS::getName() const throw(INTERP_KERNEL::Exception)
 {
   if(_mesh_one_ts.empty())
     throw INTERP_KERNEL::Exception("MEDFileMeshMultiTS::getName : no time steps set !");