Salome HOME
PAL11398. Generalize access to interfaces wrapped by python class
authoreap <eap@opencascade.com>
Wed, 19 Apr 2006 13:43:50 +0000 (13:43 +0000)
committereap <eap@opencascade.com>
Wed, 19 Apr 2006 13:43:50 +0000 (13:43 +0000)
src/SMESH_I/SMESH_2smeshpy.cxx
src/SMESH_I/SMESH_2smeshpy.hxx

index 714ae7a4c466b2f83ff26b1efe42bb1b91a00ad0..35dd6c43d74cded378f36dad52118ebd55e5dc85 100644 (file)
@@ -140,6 +140,7 @@ _pyGen::_pyGen(Resource_DataMapOfAsciiStringAsciiString& theEntry2AccessorMethod
     myID2AccessorMethod( theEntry2AccessorMethod )
 {
   myNbCommands = 0;
+  myHasPattern = false;
   // make that GetID() to return TPythonDump::SMESHGenName()
   GetCreationCmd()->GetString() += "=";
 }
@@ -148,7 +149,6 @@ _pyGen::_pyGen(Resource_DataMapOfAsciiStringAsciiString& theEntry2AccessorMethod
 /*!
  * \brief Convert a command using a specific converter
   * \param theCommand - the command to convert
-  * \retval bool - convertion result
  */
 //================================================================================
 
@@ -178,19 +178,25 @@ void _pyGen::AddCommand( const TCollection_AsciiString& theCommand)
     id_mesh->second->Process( aCommand );
     return;
   }
-  // SMESH_Hypothesis method
+  // SMESH_Hypothesis method?
   list< Handle(_pyHypothesis) >::iterator hyp = myHypos.begin();
   for ( ; hyp != myHypos.end(); ++hyp )
-    if ( !(*hyp)->IsAlgo() && objID == (*hyp)->GetID() )
+    if ( !(*hyp)->IsAlgo() && objID == (*hyp)->GetID() ) {
       (*hyp)->Process( aCommand );
+      return;
+    }
+
+  // Add access to a wrapped mesh
+  for ( id_mesh = myMeshes.begin(); id_mesh != myMeshes.end(); ++id_mesh ) {
+    if ( aCommand->AddAccessorMethod( id_mesh->first, id_mesh->second->AccessorMethod() ))
+      break;
+  }
 
-  // Mesh provides SMESH_IDSource interface used in SMESH_MeshEditor.
-  // Add access to wrapped mesh
-  if ( objID.Location( TPythonDump::MeshEditorName(), 1, objID.Length() )) {
-    // in all SMESH_MeshEditor's commands, a SMESH_IDSource is the first arg
-    id_mesh = myMeshes.find( aCommand->GetArg( 1 ));
-    if ( id_mesh != myMeshes.end() )
-      aCommand->SetArg( 1 , aCommand->GetArg( 1 ) + ".GetMesh()" );
+  // Add access to a wrapped algorithm
+  for ( hyp = myHypos.begin(); hyp != myHypos.end(); ++hyp ) {
+    if ( (*hyp)->IsAlgo() &&
+         aCommand->AddAccessorMethod( (*hyp)->GetID(), (*hyp)->AccessorMethod() ))
+      break;
   }
 }
 
@@ -235,6 +241,15 @@ void _pyGen::Process( const Handle(_pyCommand)& theCommand )
     }
   }
 
+  // leave only one smeshgen.GetPattern() in the script
+  if ( theCommand->GetMethod() == "GetPattern" ) {
+    if ( myHasPattern ) {
+      theCommand->Clear();
+      return;
+    }
+    myHasPattern = true;
+  }
+
   // smeshgen.Method() --> smesh.smesh.Method()
   theCommand->SetObject( SMESH_2smeshpy::GenName() );
 }
@@ -1348,3 +1363,55 @@ bool _pyCommand::SetDependentCmdsAfter() const
   }
   return orderChanged;
 }
+//================================================================================
+/*!
+ * \brief Insert accessor method after theObjectID
+  * \param theObjectID - id of the accessed object
+  * \param theAcsMethod - name of the method giving access to the object
+  * \retval bool - false if theObjectID is not found in the command string
+ */
+//================================================================================
+
+bool _pyCommand::AddAccessorMethod( _pyID theObjectID, const char* theAcsMethod )
+{
+  if ( !theAcsMethod )
+    return false;
+  // start object search from the object, i.e. ignore result
+  GetObject();
+  int beg = GetBegPos( OBJECT_IND );
+  if ( beg < 1 || beg > Length() )
+    return false;
+  while (( beg = myString.Location( theObjectID, beg, Length() )))
+  {
+    // check that theObjectID is not just a part of a longer ID
+    int afterEnd = beg + theObjectID.Length();
+    Standard_Character c = myString.Value( afterEnd );
+    if ( !isalnum( c ) && c != ':' ) {
+      // insertion
+      int oldLen = Length();
+      myString.Insert( afterEnd, (char*) theAcsMethod );
+      myString.Insert( afterEnd, "." );
+      // update starting positions of the parts following the modified one
+      int posDelta = Length() - oldLen;
+      for ( int i = 1; i <= myBegPos.Length(); ++i ) {
+        if ( myBegPos( i ) > afterEnd )
+          myBegPos( i ) += posDelta;
+      }
+      return true;
+    }
+    beg = afterEnd; // is a part - next search
+  }
+  return false;
+}
+
+//================================================================================
+/*!
+ * \brief Return method name giving access to an interaface object wrapped by python class
+  * \retval const char* - method name
+ */
+//================================================================================
+
+const char* _pyObject::AccessorMethod() const
+{
+  return 0;
+}
index 0a8a590306abe7987c0ced7e79903765b100a436..4ad7eade15b04eed5b21bff364f7e9e61c02fa1a 100644 (file)
@@ -73,24 +73,31 @@ DEFINE_STANDARD_HANDLE (_pyMesh      ,_pyObject);
 DEFINE_STANDARD_HANDLE (_pyHypothesis,_pyObject);
 DEFINE_STANDARD_HANDLE (_pyAlgorithm ,_pyHypothesis);
 
+typedef TCollection_AsciiString _pyID;
+
+// ===========================================================
 /*!
  * \brief Class operating on a command string looking like
  *        ResultValue = Object.Method( Arg1, Arg2,...)
  */
+// ===========================================================
+
 class _pyCommand: public Standard_Transient
 {
-  int myOrderNb; // position within the script
-  TCollection_AsciiString myString;
-  TCollection_AsciiString myRes, myObj, myMeth;
-  TColStd_SequenceOfAsciiString myArgs;
-  TColStd_SequenceOfInteger myBegPos; //!< where myRes, myObj, ... begin
-  std::list< Handle(_pyCommand) > myDependentCmds;
+  int                             myOrderNb;            //!< position within the script
+  TCollection_AsciiString         myString;             //!< command text
+  TCollection_AsciiString         myRes, myObj, myMeth; //!< found parts of command
+  TColStd_SequenceOfAsciiString   myArgs;               //!< found arguments
+  TColStd_SequenceOfInteger       myBegPos;             //!< where myRes, myObj, ... begin
+  std::list< Handle(_pyCommand) > myDependentCmds; //!< commands that sould follow me in the script
+
   enum { UNKNOWN=-1, EMPTY=0, RESULT_IND, OBJECT_IND, METHOD_IND, ARG1_IND };
   int GetBegPos( int thePartIndex );
   void SetBegPos( int thePartIndex, int thePosition );
   void SetPart( int thePartIndex, const TCollection_AsciiString& theNewPart,
                 TCollection_AsciiString& theOldPart);
   void FindAllArgs() { GetArg(1); }
+
 public:
   _pyCommand() {};
   _pyCommand( const TCollection_AsciiString& theString, int theNb )
@@ -123,13 +130,14 @@ public:
   { return myDependentCmds.push_back( cmd ); }
   bool SetDependentCmdsAfter() const;
 
+  bool AddAccessorMethod( _pyID theObjectID, const char* theAcsMethod );
+
   DEFINE_STANDARD_RTTI (_pyCommand)
 };
 
 /*!
  * \brief Root of all objects
  */
-typedef TCollection_AsciiString _pyID;
 
 class _pyObject: public Standard_Transient
 {
@@ -142,6 +150,7 @@ public:
   int GetCommandNb() { return myCreationCmd->GetOrderNb(); }
   virtual void Process(const Handle(_pyCommand) & theCommand) = 0;
   virtual void Flush() = 0;
+  virtual const char* AccessorMethod() const;
 
   DEFINE_STANDARD_RTTI (_pyObject)
 };
@@ -165,11 +174,13 @@ public:
   void SetCommandAfter( Handle(_pyCommand) theCmd, Handle(_pyCommand) theAfterCmd );
   std::list< Handle(_pyCommand) >& GetCommands() { return myCommands; }
   void SetAccessorMethod(const _pyID& theID, const char* theMethod );
+  const char* AccessorMethod() const { return SMESH_2smeshpy::GenName(); }
 private:
   std::map< _pyID, Handle(_pyMesh) > myMeshes;
   std::list< Handle(_pyHypothesis) > myHypos;
   std::list< Handle(_pyCommand) >    myCommands;
   int                                myNbCommands;
+  bool                               myHasPattern;
   Resource_DataMapOfAsciiStringAsciiString& myID2AccessorMethod;
 
   DEFINE_STANDARD_RTTI (_pyGen)
@@ -178,6 +189,7 @@ private:
 /*!
  * \brief Contains commands concerning mesh substructures
  */
+#define _pyMesh_ACCESS_METHOD "GetMesh()"
 class _pyMesh: public _pyObject
 {
   std::list< Handle(_pyHypothesis) > myHypos;
@@ -189,12 +201,14 @@ public:
   const _pyID& GetGeom() { return GetCreationCmd()->GetArg(1); }
   void Process( const Handle(_pyCommand)& theCommand);
   void Flush();
+  const char* AccessorMethod() const { return _pyMesh_ACCESS_METHOD; }
 private:
   static void AddMeshAccess( const Handle(_pyCommand)& theCommand )
-  { theCommand->SetObject( theCommand->GetObject() + ".GetMesh()" ); }
+  { theCommand->SetObject( theCommand->GetObject() + "." _pyMesh_ACCESS_METHOD ); }
 
   DEFINE_STANDARD_RTTI (_pyMesh)
 };
+#undef _pyMesh_ACCESS_METHOD 
 
 /*!
  * \brief Root class for hypothesis
@@ -283,6 +297,7 @@ public:
   _pyAlgorithm(const Handle(_pyCommand)& theCreationCmd);
   virtual bool Addition2Creation( const Handle(_pyCommand)& theAdditionCmd,
                                   const _pyID&              theMesh);
+  const char* AccessorMethod() const { return "GetAlgorithm()"; }
 
   DEFINE_STANDARD_RTTI (_pyAlgorithm)
 };