Salome HOME
Fix of 0021175: EDF 1692 VISU: Scalar bar range is not good.
[modules/visu.git] / src / CONVERTOR / VISU_ConvertorUtils.cxx
index 60c0a962eaa5172b61971d28ec7ac855998960a6..75b6da65182382c386db2ab044a4d290bba60fe7 100644 (file)
-//  VISU OBJECT : interactive object for VISU entities implementation
+//  Copyright (C) 2007-2010  CEA/DEN, EDF R&D, OPEN CASCADE
+//
+//  Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+//  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+//  This library is free software; you can redistribute it and/or
+//  modify it under the terms of the GNU Lesser General Public
+//  License as published by the Free Software Foundation; either
+//  version 2.1 of the License.
 //
-//  Copyright (C) 2003  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
-//  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS 
-// 
-//  This library is free software; you can redistribute it and/or 
-//  modify it under the terms of the GNU Lesser General Public 
-//  License as published by the Free Software Foundation; either 
-//  version 2.1 of the License. 
-// 
-//  This library is distributed in the hope that it will be useful, 
-//  but WITHOUT ANY WARRANTY; without even the implied warranty of 
-//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU 
-//  Lesser General Public License for more details. 
-// 
-//  You should have received a copy of the GNU Lesser General Public 
-//  License along with this library; if not, write to the Free Software 
-//  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA 
-// 
-//  See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org 
+//  This library is distributed in the hope that it will be useful,
+//  but WITHOUT ANY WARRANTY; without even the implied warranty of
+//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+//  Lesser General Public License for more details.
 //
+//  You should have received a copy of the GNU Lesser General Public
+//  License along with this library; if not, write to the Free Software
+//  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
 //
+//  See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+//  VISU OBJECT : interactive object for VISU entities implementation
 //  File   : VISU_Convertor_impl.cxx
 //  Author : Alexey PETROV
 //  Module : VISU
-
-#include "VISU_Convertor.hxx"
+//
 #include "VISU_ConvertorUtils.hxx"
 
 #include <vtkCellType.h>
 
-using namespace std;
-
-#define MED2VTK(MEDTYPE,VTKTYPE,VTKNBNODES) \
- {MEDTYPE,#MEDTYPE,getNbMedNodes(MEDTYPE),VTKTYPE,#VTKTYPE,VTKNBNODES}
-Med2vtk med2vtk[MED_NBR_GEOMETRIE_MAILLE] = {
-  MED2VTK(MED_POINT1,VTK_VERTEX,1),
-  MED2VTK(MED_SEG2,VTK_LINE,2),
-  MED2VTK(MED_SEG3,VTK_LINE,2),
-  MED2VTK(MED_TRIA3,VTK_TRIANGLE,3),
-  MED2VTK(MED_TRIA6,VTK_TRIANGLE,3),
-  MED2VTK(MED_QUAD4,VTK_QUAD,4),
-  MED2VTK(MED_QUAD8,VTK_QUAD,4),
-  MED2VTK(MED_TETRA4,VTK_TETRA,4),
-  MED2VTK(MED_TETRA10,VTK_TETRA,4),
-  MED2VTK(MED_HEXA8,VTK_HEXAHEDRON,8),
-  MED2VTK(MED_HEXA20,VTK_HEXAHEDRON,8),
-  MED2VTK(MED_PENTA6,VTK_WEDGE,6),
-  MED2VTK(MED_PENTA15,VTK_WEDGE,6),
-  MED2VTK(MED_PYRA5,VTK_PYRAMID,5),
-  MED2VTK(MED_PYRA13,VTK_PYRAMID,5)
-};
-#undef MED2VTK
-
-extern "C" {
-  int getNbMedConnect(int theMedType, int theMedEntity, int theMeshDim){
-    int anElemDim = theMedType / 100, nsup = 0;
-    if(theMedEntity == VISU::CELL_ENTITY && anElemDim < theMeshDim) nsup = 1;
-    return nsup + theMedType % 100;
-  }
-
-  int getNbMedNodes(int geom){ 
-    return geom % 100;
-  } 
-
-  int getIdMedType(int medType){
-    for(int i = 0; i < MED_NBR_GEOMETRIE_MAILLE; i++)
-      if(med2vtk[i].medType == medType) return i;
+#include <vtkUnstructuredGridWriter.h>
+#include <vtkUnstructuredGrid.h>
+
+#include <vtkPolyDataWriter.h>
+#include <vtkPolyData.h>
+
+#include <vtkInformationVector.h>
+#include <vtkInformation.h>
+#include <vtkExecutive.h>
+
+#include <vtkTimerLog.h>
+#include <vtkPointData.h>
+#include <vtkCellData.h>
+#include <vtkDataSet.h>
+#include <vtkIdList.h>
+
+#include <vtkIntArray.h>
+#include <algorithm>
+
+#ifdef _DEBUG_
+static int MYDEBUG = 0;
+#else
+static int MYDEBUG = 0;
+#endif
+
+namespace VISU
+{
+  //---------------------------------------------------------------
+  vtkIdType
+  VISUGeom2NbNodes(EGeometry theGeom)
+  { 
+    switch(theGeom){
+#ifndef VISU_ENABLE_QUADRATIC
+    case VISU::eSEG3: 
+      return 2;
+    case VISU::eTRIA6: 
+      return 3;
+    case VISU::eQUAD8: 
+      return 4;
+    case VISU::eTETRA10: 
+      return 4;
+    case VISU::eHEXA20: 
+      return 8;
+    case VISU::ePENTA15: 
+      return 6;
+    case VISU::ePYRA13: 
+      return 5;
+#endif
+    case VISU::ePOLYGONE: 
+    case VISU::ePOLYEDRE: 
+      return -1;
+    default:
+      return theGeom % 100;
+    }
+  }
+
+
+  //---------------------------------------------------------------
+  vtkIdType
+  VISUGeom2VTK(EGeometry theGeom)
+  { 
+    switch(theGeom){
+    case VISU::ePOINT1: 
+      return VTK_VERTEX;
+    case VISU::eSEG2: 
+      return VTK_LINE;
+    case VISU::eTRIA3: 
+      return VTK_TRIANGLE;
+    case VISU::eQUAD4: 
+      return VTK_QUAD;
+    case VISU::eTETRA4: 
+      return VTK_TETRA;
+    case VISU::eHEXA8: 
+      return VTK_HEXAHEDRON;
+    case VISU::ePENTA6: 
+      return VTK_WEDGE;
+    case VISU::ePYRA5: 
+      return VTK_PYRAMID;
+
+    case VISU::ePOLYGONE: 
+      return VTK_POLYGON;
+    case VISU::ePOLYEDRE: 
+      return VTK_CONVEX_POINT_SET;
+
+#ifndef VISU_ENABLE_QUADRATIC
+    case VISU::eSEG3: 
+      return VTK_LINE;
+    case VISU::eTRIA6: 
+      return VTK_TRIANGLE;
+    case VISU::eQUAD8: 
+      return VTK_QUAD;
+    case VISU::eTETRA10: 
+      return VTK_TETRA;
+    case VISU::eHEXA20: 
+      return VTK_HEXAHEDRON;
+    case VISU::ePENTA15: 
+      return VTK_WEDGE;
+    case VISU::ePYRA13: 
+      return VTK_PYRAMID;
+
+#else
+
+    case VISU::eSEG3: 
+#if defined(VTK_QUADRATIC_EDGE) && defined(VISU_USE_VTK_QUADRATIC)
+      return VTK_QUADRATIC_EDGE;
+#else
+      return VTK_POLY_LINE;
+#endif
+
+    case VISU::eTRIA6: 
+#if defined(VTK_QUADRATIC_TRIANGLE) && defined(VISU_USE_VTK_QUADRATIC)
+      return VTK_QUADRATIC_TRIANGLE;
+#else
+      return VTK_POLYGON;
+#endif
+
+    case VISU::eQUAD8: 
+#if defined(VTK_QUADRATIC_QUAD) && defined(VISU_USE_VTK_QUADRATIC)
+      return VTK_QUADRATIC_QUAD;
+#else
+      return VTK_POLYGON;
+#endif
+
+    case VISU::eTETRA10: 
+#if defined(VTK_QUADRATIC_TETRA) && defined(VISU_USE_VTK_QUADRATIC)
+      return VTK_QUADRATIC_TETRA;
+#else
+      return VTK_CONVEX_POINT_SET;
+#endif
+
+    case VISU::eHEXA20: 
+#if defined(VTK_QUADRATIC_HEXAHEDRON) && defined(VISU_USE_VTK_QUADRATIC)
+      return VTK_QUADRATIC_HEXAHEDRON;
+#else
+      return VTK_CONVEX_POINT_SET;
+#endif
+
+    case VISU::ePENTA15: 
+#if defined(VTK_QUADRATIC_WEDGE) && defined(VISU_USE_VTK_QUADRATIC)
+      return VTK_QUADRATIC_WEDGE;
+#else
+      return VTK_CONVEX_POINT_SET;
+#endif
+
+    case VISU::ePYRA13: 
+#if defined(VTK_QUADRATIC_PYRAMID) && defined(VISU_USE_VTK_QUADRATIC)
+      return VTK_QUADRATIC_PYRAMID;
+#else
+      return VTK_CONVEX_POINT_SET;
+#endif
+
+#endif //VISU_ENABLE_QUADRATIC
+
+    default:
+      return -1;
+    }
+  }
+
+
+  //---------------------------------------------------------------
+  void 
+  WriteToFile(vtkUnstructuredGrid* theDataSet, 
+              const std::string& theFileName)
+  {
+    vtkUnstructuredGridWriter* aWriter = vtkUnstructuredGridWriter::New();
+    //aWriter->SetFileType(VTK_BINARY);
+    aWriter->SetFileName(theFileName.c_str());
+    aWriter->SetInput(theDataSet);
+    aWriter->Write();
+    aWriter->Delete();
+  }
+
+
+  //---------------------------------------------------------------
+  void 
+  WriteToFile(vtkPolyData* theDataSet, 
+              const std::string& theFileName)
+  {
+    vtkPolyDataWriter* aWriter = vtkPolyDataWriter::New();
+    //aWriter->SetFileType(VTK_BINARY);
+    aWriter->SetFileName(theFileName.c_str());
+    aWriter->SetInput(theDataSet);
+    aWriter->Write();
+    aWriter->Delete();
+  }
+
+
+  //---------------------------------------------------------------
+  bool 
+  IsDataOnPoints(vtkDataSet* theDataSet)
+  {
+    theDataSet->Update();
+    vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetPointData();
+    return aDataSetAttributes->GetArray("VISU_FIELD") != NULL;
+  }
+
+
+  //---------------------------------------------------------------
+  bool 
+  IsDataOnCells(vtkDataSet* theDataSet)
+  {
+    theDataSet->Update();
+    vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetCellData();
+    return aDataSetAttributes->GetArray("VISU_FIELD") != NULL;
+  }
+
+  //---------------------------------------------------------------
+  bool 
+  IsElnoData(vtkDataSet* theDataSet)
+  {
+    theDataSet->Update();
+
+    if ( vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetCellData() )
+      if ( aDataSetAttributes->GetArray( "ELNO_FIELD" )  != NULL )
+        return true;
+
+    if ( vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetPointData() )
+      if ( aDataSetAttributes->GetArray( "ELNO_POINT_COORDS" )  != NULL )
+        return true;
+
+    return false;
+  }
+
+
+  //---------------------------------------------------------------
+  vtkIdType
+  GetVTKID(vtkDataArray *theIDDataArray, vtkIdType theID, int theEntity)
+  {
+    if(vtkIntArray *anIntArray = dynamic_cast<vtkIntArray*>(theIDDataArray)){
+      int aNbTuples = anIntArray->GetNumberOfTuples();
+      int* aPointer = anIntArray->GetPointer(0);
+      for(int aTupleId = 0; aTupleId < aNbTuples; aTupleId++){
+        if(*aPointer == theID && *(aPointer + 1) == theEntity){
+          return aTupleId;
+        }
+        aPointer += 2;
+      }
+    }
+    return -1;
+  }
+
+
+  //---------------------------------------------------------------
+  vtkIdType
+  GetObjectID(vtkDataArray *theIDDataArray, vtkIdType theID)
+  {
+    if(vtkIntArray *anIntArray = dynamic_cast<vtkIntArray*>(theIDDataArray)){
+      int aNbComp = anIntArray->GetNumberOfComponents();
+      int* aPointer = anIntArray->GetPointer(theID*aNbComp);
+      return *aPointer;
+    }
+    return -1;
+  }
+
+
+  //---------------------------------------------------------------
+  vtkIdType
+  GetElemVTKID(vtkDataSet *theDataSet, vtkIdType theID, int theEntity)
+  {
+    theDataSet->Update();
+    vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetCellData();
+    if(vtkDataArray *aDataArray = aDataSetAttributes->GetArray("VISU_CELLS_MAPPER")){
+      if(theEntity < 0){
+        {
+          vtkIdType anID = GetVTKID(aDataArray, theID, VISU::CELL_ENTITY);
+          if(anID != -1)
+            return anID;
+        }
+        {
+          vtkIdType anID = GetVTKID(aDataArray, theID, VISU::FACE_ENTITY);
+          if(anID != -1)
+            return anID;
+        }
+        {
+          vtkIdType anID = GetVTKID(aDataArray, theID, VISU::EDGE_ENTITY);
+          if(anID != -1)
+            return anID;
+        }
+        {
+          vtkIdType anID = GetVTKID(aDataArray, theID, VISU::NODE_ENTITY);
+          if(anID != -1)
+            return anID;
+        }
+      }else
+        return GetVTKID(aDataArray, theID, theEntity);
+    }
+    return -1;
+  }
+
+
+  //---------------------------------------------------------------
+  vtkIdType
+  GetElemObjID(vtkDataSet *theDataSet, vtkIdType theID)
+  {
+    theDataSet->Update();
+    vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetCellData();
+    if(vtkDataArray *aDataArray = aDataSetAttributes->GetArray("VISU_CELLS_MAPPER"))
+      return GetObjectID(aDataArray, theID);
+
     return -1;
   }
 
-  int med2vtkCellType(int medType){
-    for(int i = 0; i < MED_NBR_GEOMETRIE_MAILLE; i++)
-      if(med2vtk[i].medType == medType) return med2vtk[i].vtkType;
+
+  //---------------------------------------------------------------
+  vtkCell* 
+  GetElemCell(vtkDataSet *theDataSet, vtkIdType  theObjID)
+  {
+    vtkIdType aVTKID = GetElemVTKID(theDataSet, theObjID);
+    return theDataSet->GetCell(aVTKID);
+  }
+
+
+  //---------------------------------------------------------------
+  vtkIdType
+  GetNodeVTKID(vtkDataSet *theDataSet, vtkIdType theID)
+  {
+    theDataSet->Update();
+    vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetPointData();
+    if(vtkDataArray *aDataArray = aDataSetAttributes->GetArray("VISU_POINTS_MAPPER"))
+      return GetVTKID(aDataArray, theID, VISU::NODE_ENTITY);
+
     return -1;
   }
-  
-  int vtk2medCellType(int vtkType){
-    for(int i = 0; i < MED_NBR_GEOMETRIE_MAILLE; i++)
-      if(med2vtk[i].vtkType == vtkType) return med2vtk[i].medType;
+
+
+  //---------------------------------------------------------------
+  vtkIdType
+  GetNodeObjID(vtkDataSet *theDataSet, vtkIdType theID)
+  {
+    theDataSet->Update();
+    vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetPointData();
+    if(vtkDataArray *aDataArray = aDataSetAttributes->GetArray("VISU_POINTS_MAPPER"))
+      return GetObjectID(aDataArray, theID);
+
     return -1;
   }
+
+
+  //---------------------------------------------------------------
+  vtkFloatingPointType* 
+  GetNodeCoord(vtkDataSet *theDataSet, vtkIdType theObjID)
+  {
+    vtkIdType aVTKID = GetNodeVTKID(theDataSet, theObjID);
+    if ( aVTKID >= 0 ) return theDataSet->GetPoint(aVTKID);
+    return 0;
+  }
+
+
+  //---------------------------------------------------------------
+  TGaussPointID
+  GetObjID(vtkDataSet *theDataSet, vtkIdType theID)
+  {
+    theDataSet->Update();
+    vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetCellData();
+    if(vtkDataArray *aDataArray = aDataSetAttributes->GetArray("VISU_CELLS_MAPPER")){
+      if(vtkIntArray *anIntArray = dynamic_cast<vtkIntArray*>(aDataArray)){
+        vtkIdType anID = 2 * theID;
+        TCellID aCellID = anIntArray->GetValue(anID);
+        TLocalPntID aLocalPntID = anIntArray->GetValue(anID + 1);
+        return TGaussPointID(aCellID, aLocalPntID);
+      }
+    }
+    return TGaussPointID();
+  }
+
+
+  //---------------------------------------------------------------
+  TInputCellID
+  GetInputCellID(vtkDataSet *theDataSet, vtkIdType theObjID)
+  {
+    theDataSet->Update();
+    vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetCellData();
+    if(vtkDataArray *aDataArray = aDataSetAttributes->GetArray("VISU_INPUTS_MAPPER")){
+      if(vtkIntArray *anIntArray = dynamic_cast<vtkIntArray*>(aDataArray)){
+        vtkIdType aVTKID = GetElemVTKID(theDataSet, theObjID);
+        vtkIdType aTupleID = 2 * aVTKID;
+        TCellID aCellID = anIntArray->GetValue(aTupleID);
+        TInputID anInputID = anIntArray->GetValue(aTupleID + 1);
+        return TInputCellID(anInputID, aCellID);
+      }
+    }
+    return TInputCellID();
+  }
+
+
+  //---------------------------------------------------------------
+  vtkDataSet*
+  GetInput(vtkInformationVector **theInputVector, 
+           vtkIdType theInputId)
+  {
+    if(vtkInformation* anInformation = theInputVector[0]->GetInformationObject(theInputId))
+      return vtkDataSet::SafeDownCast(anInformation->Get(vtkDataObject::DATA_OBJECT()));
+    return NULL;
+  }
+
+
+  //---------------------------------------------------------------
+  vtkDataSet*
+  GetOutput(vtkInformationVector *theOutputVector)
+  {
+    if(vtkInformation* anInformation = theOutputVector->GetInformationObject(0))
+      return vtkDataSet::SafeDownCast(anInformation->Get(vtkDataObject::DATA_OBJECT()));
+    return NULL;
+  }
+
+  //---------------------------------------------------------------
+  TElnoPoints
+  GetElnoPoints(vtkDataSet *theDataSet, vtkIdType theNodeObjID)
+  {
+    TElnoPoints aResult;
+    if(theDataSet && IsElnoData(theDataSet)) {
+      vtkDataSetAttributes *aDataSetAttributes = theDataSet->GetPointData();
+      vtkDataArray *aDataArray = aDataSetAttributes->GetArray("VISU_POINTS_MAPPER");
+      if(aDataArray){
+        if(vtkIntArray *anIntArray = dynamic_cast<vtkIntArray*>(aDataArray)){
+          int aNbTuples = anIntArray->GetNumberOfTuples();
+          int* aPointer = anIntArray->GetPointer(0);
+          for(int aTupleId = 0; aTupleId < aNbTuples; aTupleId++){
+            if( *aPointer == theNodeObjID ) {
+              vtkIdList *aCellIds = vtkIdList::New();
+              theDataSet->GetPointCells(aTupleId,aCellIds);
+              if(aCellIds->GetNumberOfIds() == 1){
+                aResult.push_back(TElnoPointID(aTupleId,aCellIds->GetId(0)));
+              }
+            }
+            aPointer += 2;
+          }
+        }
+      }
+    }
+    return aResult;
+  }
+
+  //---------------------------------------------------------------
+  TTimerLog
+  ::TTimerLog(int theIsDebug,
+              const std::string& theName):
+    myIsDebug(MYDEBUG + theIsDebug),
+    myTimerLog(vtkTimerLog::New()),
+    myPrefixPrinter(myIsDebug == 1),
+    myName(theName)
+  {
+    myCPUTime = myTimerLog->GetCPUTime();
+    BEGMSG(myIsDebug > 1,"{\n");
+  }
+
+  //---------------------------------------------------------------
+  TTimerLog
+  ::~TTimerLog()
+  {
+    myCPUTime = myTimerLog->GetCPUTime() - myCPUTime;
+
+    if(myIsDebug > 1){
+      BEGMSG(myIsDebug,"} = "<<myCPUTime<<" secs ("<<myName<<")\n");
+    }else{
+      BEGMSG(myIsDebug,myName<<" takes "<<myCPUTime<<" secs\n");
+    }
+    
+    myTimerLog->Delete();
+    myTimerLog = NULL;
+  }
+
+
+  //---------------------------------------------------------------
 }