Salome HOME
PAL10494 (SMESH python dump uses idl interface). Python dump converted to smesh...
[modules/smesh.git] / src / SMESH_I / SMESH_DumpPython.cxx
1 // Copyright (C) 2005  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
2 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
3 // 
4 // This library is free software; you can redistribute it and/or
5 // modify it under the terms of the GNU Lesser General Public
6 // License as published by the Free Software Foundation; either 
7 // version 2.1 of the License.
8 // 
9 // This library is distributed in the hope that it will be useful 
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of 
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU 
12 // Lesser General Public License for more details.
13 //
14 // You should have received a copy of the GNU Lesser General Public  
15 // License along with this library; if not, write to the Free Software 
16 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
17 //
18 // See http://www.salome-platform.org/
19 //
20 // File    : SMESH_Gen_i_DumpPython.cxx
21 // Created : Thu Mar 24 17:17:59 2005
22 // Author  : Julia DOROVSKIKH
23 // Module  : SMESH
24 // $Header : $
25
26 #include "SMESH_PythonDump.hxx"
27 #include "SMESH_Gen_i.hxx"
28 #include "SMESH_Filter_i.hxx"
29 #include "SMESH_2smeshpy.hxx"
30
31 #include <TColStd_HSequenceOfInteger.hxx>
32 #include <TCollection_AsciiString.hxx>
33
34
35 #ifdef _DEBUG_
36 static int MYDEBUG = 0;
37 #else
38 static int MYDEBUG = 0;
39 #endif
40
41 static TCollection_AsciiString NotPublishedObjectName()
42 {
43   return "__NOT__Published__Object__";
44 }
45
46 namespace SMESH
47 {
48
49   size_t TPythonDump::myCounter = 0;
50
51   TPythonDump::
52   TPythonDump()
53   {
54     ++myCounter;
55   }
56   TPythonDump::
57   ~TPythonDump()
58   {
59     if(--myCounter == 0){
60       SMESH_Gen_i* aSMESHGen = SMESH_Gen_i::GetSMESHGen();
61       SALOMEDS::Study_ptr aStudy = aSMESHGen->GetCurrentStudy();
62       if(!aStudy->_is_nil()){
63         std::string aString = myStream.str();
64         TCollection_AsciiString aCollection(Standard_CString(aString.c_str()));
65         aSMESHGen->AddToPythonScript(aStudy->StudyId(),aCollection);
66         if(MYDEBUG) MESSAGE(aString);
67       }
68     }
69   }
70
71   TPythonDump& 
72   TPythonDump::
73   operator<<(long int theArg){
74     myStream<<theArg;
75     return *this;
76   }
77
78   TPythonDump& 
79   TPythonDump::
80   operator<<(int theArg){
81     myStream<<theArg;
82     return *this;
83   }
84
85   TPythonDump& 
86   TPythonDump::
87   operator<<(double theArg){
88     myStream<<theArg;
89     return *this;
90   }
91
92   TPythonDump& 
93   TPythonDump::
94   operator<<(float theArg){
95     myStream<<theArg;
96     return *this;
97   }
98
99   TPythonDump& 
100   TPythonDump::
101   operator<<(const void* theArg){
102     myStream<<theArg;
103     return *this;
104   }
105
106   TPythonDump& 
107   TPythonDump::
108   operator<<(const char* theArg){
109     if ( theArg )
110       myStream<<theArg;
111     return *this;
112   }
113
114   TPythonDump& 
115   TPythonDump::
116   operator<<(const SMESH::ElementType& theArg)
117   {
118     myStream<<"SMESH.";
119     switch(theArg){
120     case ALL:   myStream<<"ALL";break;
121     case NODE:  myStream<<"NODE";break;
122     case EDGE:  myStream<<"EDGE";break;
123     case FACE:  myStream<<"FACE";break;
124     case VOLUME:myStream<<"VOLUME";break;
125     }
126     return *this;
127   }
128
129   template<class TArray>
130   void DumpArray(const TArray& theArray, std::ostringstream & theStream)
131   {
132     theStream << "[ ";
133     for (int i = 1; i <= theArray.length(); i++) {
134       theStream << theArray[i-1];
135       if ( i < theArray.length() )
136         theStream << ", ";
137     }
138     theStream << " ]";
139   }
140
141   TPythonDump& 
142   TPythonDump::operator<<(const SMESH::long_array& theArg)
143   {
144     DumpArray( theArg, myStream );
145     return *this;
146   }
147
148   TPythonDump& 
149   TPythonDump::operator<<(const SMESH::double_array& theArg)
150   {
151     DumpArray( theArg, myStream );
152     return *this;
153   }
154
155   TPythonDump& 
156   TPythonDump::
157   operator<<(SALOMEDS::SObject_ptr aSObject)
158   {
159     if ( !aSObject->_is_nil() )
160       myStream << aSObject->GetID();
161     else
162       myStream << NotPublishedObjectName();
163     return *this;
164   }
165
166   TPythonDump& 
167   TPythonDump::
168   operator<<(CORBA::Object_ptr theArg)
169   {
170     SMESH_Gen_i* aSMESHGen = SMESH_Gen_i::GetSMESHGen();
171     SALOMEDS::Study_ptr aStudy = aSMESHGen->GetCurrentStudy();
172     SALOMEDS::SObject_var aSObject = SMESH_Gen_i::ObjectToSObject(aStudy,theArg);
173     if(!aSObject->_is_nil()) {
174       myStream << aSObject->GetID();
175     } else if ( !CORBA::is_nil(theArg)) {
176       if ( aSMESHGen->CanPublishInStudy( theArg )) // not published SMESH object
177         myStream << "smeshObj_" << (int) theArg;
178       else
179         myStream << NotPublishedObjectName();
180     }
181     else
182       myStream << "None";
183     return *this;
184   }
185
186   TPythonDump& 
187   TPythonDump::
188   operator<<(SMESH::FilterLibrary_i* theArg)
189   {
190     myStream<<"aFilterLibrary"<<theArg;
191     return *this;
192   }
193
194   TPythonDump& 
195   TPythonDump::
196   operator<<(SMESH::FilterManager_i* theArg)
197   {
198     myStream<<"aFilterManager";
199     return *this;
200   }
201
202   TPythonDump& 
203   TPythonDump::
204   operator<<(SMESH::Filter_i* theArg)
205   {
206     myStream<<"aFilter"<<theArg;
207     return *this;
208   }
209
210   TPythonDump& 
211   TPythonDump::
212   operator<<(SMESH::Functor_i* theArg)
213   {
214     if ( theArg ) {
215       FunctorType aFunctorType = theArg->GetFunctorType();
216       switch(aFunctorType){
217       case FT_AspectRatio:      myStream<< "anAspectRatio";     break;
218       case FT_AspectRatio3D:    myStream<< "anAspectRatio3D";   break;
219       case FT_Warping:          myStream<< "aWarping";          break;
220       case FT_MinimumAngle:     myStream<< "aMinimumAngle";     break;
221       case FT_Taper:            myStream<< "aTaper";            break;
222       case FT_Skew:             myStream<< "aSkew";             break;
223       case FT_Area:             myStream<< "aArea";             break;
224       case FT_FreeBorders:      myStream<< "aFreeBorders";      break;
225       case FT_FreeEdges:        myStream<< "aFreeEdges";        break;
226       case FT_MultiConnection:  myStream<< "aMultiConnection";  break;
227       case FT_MultiConnection2D:myStream<< "aMultiConnection2D";break;
228       case FT_Length:           myStream<< "aLength";           break;
229       case FT_Length2D:         myStream<< "aLength";           break;
230       case FT_BelongToGeom:     myStream<< "aBelongToGeom";     break;
231       case FT_BelongToPlane:    myStream<< "aBelongToPlane";    break;
232       case FT_BelongToCylinder: myStream<< "aBelongToCylinder"; break;
233       case FT_LyingOnGeom:      myStream<< "aLyingOnGeom";      break;
234       case FT_RangeOfIds:       myStream<< "aRangeOfIds";       break;
235       case FT_BadOrientedVolume:myStream<< "aBadOrientedVolume";break;
236       case FT_LessThan:         myStream<< "aLessThan";         break;
237       case FT_MoreThan:         myStream<< "aMoreThan";         break;
238       case FT_EqualTo:          myStream<< "anEqualTo";         break;
239       case FT_LogicalNOT:       myStream<< "aLogicalNOT";       break;
240       case FT_LogicalAND:       myStream<< "aLogicalAND";       break;
241       case FT_LogicalOR:        myStream<< "aLogicalOR";        break;
242       case FT_Undefined:        myStream<< "anUndefined";       break;
243       }
244       myStream<<theArg;
245     }
246     return *this;
247   }
248
249   TPythonDump& TPythonDump:: operator<<(SMESH_Gen_i* theArg)
250   {
251     myStream << SMESHGenName(); return *this;
252   }
253
254   TPythonDump& TPythonDump::operator<<(SMESH_MeshEditor_i* theArg)
255   {
256     myStream << MeshEditorName(); return *this;
257   }
258
259   TPythonDump& TPythonDump::operator<<(const TCollection_AsciiString & theStr)
260   {
261     myStream << theStr; return *this;
262   }
263
264
265   TPythonDump& TPythonDump::operator<<(SMESH::MED_VERSION theVersion)
266   {
267     switch (theVersion) {
268     case SMESH::MED_V2_1: myStream << "SMESH.MED_V2_1"; break;
269     case SMESH::MED_V2_2: myStream << "SMESH.MED_V2_2"; break;
270     default: myStream << theVersion;
271     }
272     return *this;
273   }
274
275   TPythonDump& TPythonDump::operator<<(const SMESH::AxisStruct & theAxis)
276   {
277     myStream << "SMESH.AxisStruct( "
278              << theAxis.x  << ", "
279              << theAxis.y  << ", "
280              << theAxis.z  << ", "
281              << theAxis.vx << ", "
282              << theAxis.vy << ", "
283              << theAxis.vz << " )";
284     return *this;
285   }
286
287   TPythonDump& TPythonDump::operator<<(const SMESH::DirStruct & theDir)
288   {
289     const SMESH::PointStruct & P = theDir.PS;
290     myStream << "SMESH.DirStruct( SMESH.PointStruct ( "
291              << P.x  << ", "
292              << P.y  << ", "
293              << P.z  << " ))";
294     return *this;
295   }
296 }
297
298 //=======================================================================
299 //function : DumpPython
300 //purpose  : 
301 //=======================================================================
302 Engines::TMPFile* SMESH_Gen_i::DumpPython (CORBA::Object_ptr theStudy,
303                                            CORBA::Boolean isPublished,
304                                            CORBA::Boolean& isValidScript)
305 {
306   SALOMEDS::Study_var aStudy = SALOMEDS::Study::_narrow(theStudy);
307   if (CORBA::is_nil(aStudy))
308     return new Engines::TMPFile(0);
309
310   SALOMEDS::SObject_var aSO = aStudy->FindComponent(ComponentDataType());
311   if (CORBA::is_nil(aSO))
312     return new Engines::TMPFile(0);
313
314   // Map study entries to object names
315   Resource_DataMapOfAsciiStringAsciiString aMap;
316   Resource_DataMapOfAsciiStringAsciiString aMapNames;
317   //TCollection_AsciiString s ("qwertyuioplkjhgfdsazxcvbnmQWERTYUIOPLKJHGFDSAZXCVBNM0987654321_");
318
319   SALOMEDS::ChildIterator_var Itr = aStudy->NewChildIterator(aSO);
320   for (Itr->InitEx(true); Itr->More(); Itr->Next()) {
321     SALOMEDS::SObject_var aValue = Itr->Value();
322     CORBA::String_var anID = aValue->GetID();
323     CORBA::String_var aName = aValue->GetName();
324     TCollection_AsciiString aGUIName ( (char*) aName.in() );
325     TCollection_AsciiString anEnrty ( (char*) anID.in() );
326     if (aGUIName.Length() > 0) {
327       aMapNames.Bind( anEnrty, aGUIName );
328       aMap.Bind( anEnrty, aGUIName );
329     }
330   }
331
332   // Get trace of restored study
333   //SALOMEDS::SObject_var aSO = SMESH_Gen_i::ObjectToSObject(theStudy, _this());
334   SALOMEDS::StudyBuilder_var aStudyBuilder = aStudy->NewBuilder();
335   SALOMEDS::GenericAttribute_var anAttr =
336     aStudyBuilder->FindOrCreateAttribute(aSO, "AttributePythonObject");
337
338   char* oldValue = SALOMEDS::AttributePythonObject::_narrow(anAttr)->GetObject();
339   TCollection_AsciiString aSavedTrace (oldValue);
340
341   // Add trace of API methods calls and replace study entries by names
342   TCollection_AsciiString aScript =
343     "### This file is generated by SALOME automatically by dump python functionality of SMESH component\n\n";
344   aScript += DumpPython_impl(aStudy->StudyId(), aMap, aMapNames,
345                              isPublished, isValidScript, aSavedTrace);
346
347   int aLen = aScript.Length(); 
348   unsigned char* aBuffer = new unsigned char[aLen+1];
349   strcpy((char*)aBuffer, aScript.ToCString());
350
351   CORBA::Octet* anOctetBuf =  (CORBA::Octet*)aBuffer;
352   Engines::TMPFile_var aStreamFile = new Engines::TMPFile(aLen+1, aLen+1, anOctetBuf, 1); 
353
354   bool hasNotPublishedObjects = aScript.Location( NotPublishedObjectName(), 1, aLen);
355   isValidScript = isValidScript && !hasNotPublishedObjects;
356
357   return aStreamFile._retn(); 
358 }
359
360 //=============================================================================
361 /*!
362  *  AddToPythonScript
363  */
364 //=============================================================================
365 void SMESH_Gen_i::AddToPythonScript (int theStudyID, const TCollection_AsciiString& theString)
366 {
367   if (myPythonScripts.find(theStudyID) == myPythonScripts.end()) {
368     myPythonScripts[theStudyID] = new TColStd_HSequenceOfAsciiString;
369   }
370   myPythonScripts[theStudyID]->Append(theString);
371 }
372
373 //=============================================================================
374 /*!
375  *  RemoveLastFromPythonScript
376  */
377 //=============================================================================
378 void SMESH_Gen_i::RemoveLastFromPythonScript (int theStudyID)
379 {
380   if (myPythonScripts.find(theStudyID) != myPythonScripts.end()) {
381     int aLen = myPythonScripts[theStudyID]->Length();
382     myPythonScripts[theStudyID]->Remove(aLen);
383   }
384 }
385
386 //=======================================================================
387 //function : SavePython
388 //purpose  : 
389 //=======================================================================
390 void SMESH_Gen_i::SavePython (SALOMEDS::Study_ptr theStudy)
391 {
392   // Dump trace of API methods calls
393   TCollection_AsciiString aScript = GetNewPythonLines(theStudy->StudyId());
394
395   // Check contents of PythonObject attribute
396   SALOMEDS::SObject_var aSO = theStudy->FindComponent(ComponentDataType());
397   //SALOMEDS::SObject_var aSO = SMESH_Gen_i::ObjectToSObject(theStudy, _this());
398   SALOMEDS::StudyBuilder_var aStudyBuilder = theStudy->NewBuilder();
399   SALOMEDS::GenericAttribute_var anAttr =
400     aStudyBuilder->FindOrCreateAttribute(aSO, "AttributePythonObject");
401
402   char* oldValue = SALOMEDS::AttributePythonObject::_narrow(anAttr)->GetObject();
403   TCollection_AsciiString oldScript (oldValue);
404
405   if (oldScript.Length() > 0) {
406     oldScript += "\n";
407     oldScript += aScript;
408   } else {
409     oldScript = aScript;
410   }
411
412   // Store in PythonObject attribute
413   SALOMEDS::AttributePythonObject::_narrow(anAttr)->SetObject(oldScript.ToCString(), 1);
414
415   // Clean trace of API methods calls
416   CleanPythonTrace(theStudy->StudyId());
417 }
418
419
420 // impl
421
422
423 //=============================================================================
424 /*!
425  *  FindEntries: Returns a sequence of start/end positions of entries in the string
426  */
427 //=============================================================================
428 Handle(TColStd_HSequenceOfInteger) FindEntries (TCollection_AsciiString& theString)
429 {
430   Handle(TColStd_HSequenceOfInteger) aSeq = new TColStd_HSequenceOfInteger;
431   Standard_Integer aLen = theString.Length();
432   Standard_Boolean isFound = Standard_False;
433
434   char* arr = theString.ToCString();
435   Standard_Integer i = 0, j;
436
437   while(i < aLen) {
438     int c = (int)arr[i];
439     j = i+1;
440     if ( isdigit( c )) { //Is digit?
441  
442       isFound = Standard_False;
443       while((j < aLen) && ( isdigit(c) || c == ':' )) { //Check if it is an entry
444         c = (int)arr[j++];  
445         if(c == ':') isFound = Standard_True;
446       }
447
448       if (isFound) {
449         int prev = (i < 1) ? 0 : (int)arr[i - 1];
450         // to distinguish from a sketcher command:
451         // last char should be a digit, not ":",
452         // previous char should not be '"'.
453         if (arr[j-2] != ':' && prev != '"') {
454           aSeq->Append(i+1); // +1 because AsciiString starts from 1
455           aSeq->Append(j-1);
456         }
457       }
458     }
459
460     i = j;
461   }
462
463   return aSeq;
464 }
465
466 //=============================================================================
467 /*!
468  *  DumpPython
469  */
470 //=============================================================================
471 TCollection_AsciiString SMESH_Gen_i::DumpPython_impl
472                         (int theStudyID, 
473                          Resource_DataMapOfAsciiStringAsciiString& theObjectNames,
474                          Resource_DataMapOfAsciiStringAsciiString& theNames,
475                          bool isPublished, 
476                          bool& aValidScript,
477                          const TCollection_AsciiString& theSavedTrace)
478 {
479   TCollection_AsciiString helper; // to comfortably concatenate C strings
480   TCollection_AsciiString aSmeshpy( SMESH_2smeshpy::SmeshpyName() );
481   TCollection_AsciiString aSMESHGen( SMESH_2smeshpy::GenName() );
482   TCollection_AsciiString anOldGen( SMESH::TPythonDump::SMESHGenName() );
483
484   TCollection_AsciiString aScript;
485   aScript = "def RebuildData(theStudy):\n\t";
486   aScript += helper + "aFilterManager = " + aSMESHGen + ".CreateFilterManager()\n\t";
487   if ( isPublished )
488     aScript += aSMESHGen + ".SetCurrentStudy(theStudy)";
489   else
490     aScript += aSMESHGen + ".SetCurrentStudy(None)";
491
492   // Dump trace of restored study
493   if (theSavedTrace.Length() > 0) {
494     // For the convertion of IDL API calls -> smesh.py API, "smesh" standing for SMESH_Gen
495     // was replaces with "smeshgen" (==TPythonDump::SMESHGenName()).
496     // Change "smesh" -> "smeshgen" in the trace saved before passage to smesh.py API
497     bool isNewVersion =
498       theSavedTrace.Location( anOldGen + ".", 1, theSavedTrace.Length() );
499     if ( !isNewVersion ) {
500       TCollection_AsciiString aSavedTrace( theSavedTrace );
501       TCollection_AsciiString aSmeshCall ( "smesh." ), gen( "gen" );
502       int beg, end = aSavedTrace.Length(), from = 1;
503       while ( from < end && ( beg = aSavedTrace.Location( aSmeshCall, from, end ))) {
504         char charBefore = ( beg == 1 ) ? ' ' : aSavedTrace.Value( beg - 1 );
505         if ( isspace( charBefore ) || charBefore == '=' ) {
506           aSavedTrace.Insert( beg + aSmeshCall.Length() - 1, gen );
507           end += gen.Length();
508         }
509         from = beg + aSmeshCall.Length();
510       }
511       aScript += helper + "\n" + aSavedTrace;
512     }
513     else
514       // append a saved trace to the script
515       aScript += helper + "\n" + theSavedTrace;
516   }
517
518   // Dump trace of API methods calls
519   TCollection_AsciiString aNewLines = GetNewPythonLines(theStudyID);
520   if (aNewLines.Length() > 0) {
521     aScript += helper + "\n" + aNewLines;
522   }
523
524   // Convert IDL API calls into smesh.py API.
525   // Some objects are wrapped with python classes and
526   // Resource_DataMapOfAsciiStringAsciiString holds methods returning wrapped objects
527   Resource_DataMapOfAsciiStringAsciiString anEntry2AccessorMethod;
528   aScript = SMESH_2smeshpy::ConvertScript( aScript, anEntry2AccessorMethod );
529
530   // Find entries to be replaced by names
531   Handle(TColStd_HSequenceOfInteger) aSeq = FindEntries(aScript);
532   Standard_Integer aLen = aSeq->Length();
533
534   if (aLen == 0)
535     return aScript;
536
537   // Replace entries by the names
538   GEOM::GEOM_Gen_ptr geom = GetGeomEngine();
539   TColStd_SequenceOfAsciiString seqRemoved;
540   Resource_DataMapOfAsciiStringAsciiString mapRemoved;
541   Standard_Integer objectCounter = 0, aStart = 1, aScriptLength = aScript.Length();
542   TCollection_AsciiString anUpdatedScript, anEntry, aName, aBaseName("smeshObj_"),
543     allowedChars ("qwertyuioplkjhgfdsazxcvbnmQWERTYUIOPLKJHGFDSAZXCVBNM0987654321_");
544
545   // Collect names of GEOM objects to exclude same names for SMESH objects
546   GEOM::string_array_var aGeomNames = geom->GetAllDumpNames();
547   int ign = 0, nbgn = aGeomNames->length();
548   for (; ign < nbgn; ign++) {
549     aName = aGeomNames[ign];
550     theObjectNames.Bind(aName, "1");
551   }
552
553   bool importGeom = false;
554   for (Standard_Integer i = 1; i <= aLen; i += 2) {
555     anUpdatedScript += aScript.SubString(aStart, aSeq->Value(i) - 1);
556     anEntry = aScript.SubString(aSeq->Value(i), aSeq->Value(i + 1));
557     // is a GEOM object?
558     aName = geom->GetDumpName( anEntry.ToCString() );
559     if (aName.IsEmpty()) {
560       // is a SMESH object
561       if (theObjectNames.IsBound(anEntry)) {
562         // The Object is in Study
563         aName = theObjectNames.Find(anEntry);
564         // check validity of aName
565         bool isValidName = true;
566         int p=1; // replace not allowed chars with underscore
567         while (p <= aName.Length() &&
568                (p = aName.FirstLocationNotInSet(allowedChars, p, aName.Length())))
569         {
570           if ( p == 1 || p == aName.Length() || aName.Value(p-1) == '_')
571             aName.Remove( p, 1 ); // remove double _ and from the start and the end
572           else
573             aName.SetValue(p, '_');
574           isValidName = false;
575         }
576         if ( aName.IsIntegerValue() ) { // aName must not start with a digit
577           aName.Insert( 1, 'a' );
578           isValidName = false;
579         }
580         if (theObjectNames.IsBound(aName) && anEntry != theObjectNames(aName)) {
581           // diff objects have same name - make a new name by appending a digit
582           TCollection_AsciiString aName2;
583           Standard_Integer i = 0;
584           do {
585             aName2 = aName + "_" + ++i;
586           } while (theObjectNames.IsBound(aName2) && anEntry != theObjectNames(aName2));
587           aName = aName2;
588           isValidName = false;
589         }
590         if ( !isValidName )
591           theObjectNames(anEntry) = aName;
592
593       } else {
594         // Removed Object
595         do {
596           aName = aBaseName + (++objectCounter);
597         } while (theObjectNames.IsBound(aName));
598         seqRemoved.Append(aName);
599         mapRemoved.Bind(anEntry, "1");
600         theObjectNames.Bind(anEntry, aName);
601       }
602       theObjectNames.Bind(aName, anEntry); // to detect same name of diff objects
603     }
604     else
605     {
606       importGeom = true;
607     }
608     anUpdatedScript += aName;
609     aStart = aSeq->Value(i + 1) + 1;
610   }
611
612   // set initial part of aSript
613   TCollection_AsciiString initPart = "import salome, SMESH\n";
614   initPart += helper + "import " + aSmeshpy + "\n\n";
615   if ( importGeom )
616   {
617     initPart += ("## import GEOM dump file ## \n"
618                  "import string, os, sys, re\n"
619                  "sys.path.insert( 0, os.path.dirname(__file__) )\n"
620                  "exec(\"from \"+re.sub(\"SMESH$\",\"GEOM\",__name__)+\" import *\")\n\n");
621   }
622   anUpdatedScript.Insert ( 1, initPart );
623
624   // add final part of aScript
625   if (aSeq->Value(aLen) < aScriptLength)
626     anUpdatedScript += aScript.SubString(aSeq->Value(aLen) + 1, aScriptLength);
627
628   // Remove removed objects
629   if ( seqRemoved.Length() > 0 ) {
630     anUpdatedScript += "\n\t## some objects were removed";
631     anUpdatedScript += "\n\taStudyBuilder = theStudy.NewBuilder()";
632   }
633   for (int ir = 1; ir <= seqRemoved.Length(); ir++) {
634     anUpdatedScript += "\n\tSO = theStudy.FindObjectIOR(theStudy.ConvertObjectToIOR(";
635     anUpdatedScript += seqRemoved.Value(ir);
636     anUpdatedScript += "))\n\tif SO is not None: aStudyBuilder.RemoveObjectWithChildren(SO)";
637   }
638
639   // Set object names
640   anUpdatedScript += "\n\t## set object names";
641   anUpdatedScript += helper + "  \n\tisGUIMode = " + isPublished;
642   anUpdatedScript += "\n\tif isGUIMode and salome.sg.hasDesktop():";
643 //   anUpdatedScript += "\n\t\tsmeshgui = salome.ImportComponentGUI(\"SMESH\")";
644 //   anUpdatedScript += "\n\t\tsmeshgui.Init(theStudy._get_StudyId())";
645 //   anUpdatedScript += "\n";
646
647   TCollection_AsciiString aGUIName;
648   Resource_DataMapOfAsciiStringAsciiString mapEntries;
649   for (Standard_Integer i = 1; i <= aLen; i += 2)
650   {
651     anEntry = aScript.SubString(aSeq->Value(i), aSeq->Value(i + 1));
652     aName = geom->GetDumpName( anEntry.ToCString() );
653     if (aName.IsEmpty() && // Not a GEOM object
654         theNames.IsBound(anEntry) &&
655         !mapEntries.IsBound(anEntry) && // Not yet processed
656         !mapRemoved.IsBound(anEntry)) // Was not removed
657     {
658       aName = theObjectNames.Find(anEntry);
659       aGUIName = theNames.Find(anEntry);
660       mapEntries.Bind(anEntry, aName);
661       anUpdatedScript += helper + "\n\t\t" + aSmeshpy + ".SetName(" + aName;
662       if ( anEntry2AccessorMethod.IsBound( anEntry ) )
663         anUpdatedScript += helper + "." + anEntry2AccessorMethod( anEntry );
664       anUpdatedScript += helper + ", '" + aGUIName + "')";
665     }
666   }
667   anUpdatedScript += "\n\n\t\tsalome.sg.updateObjBrowser(0)";
668
669   anUpdatedScript += "\n\n\tpass\n";
670
671   aValidScript = true;
672
673   return anUpdatedScript;
674 }
675
676 //=============================================================================
677 /*!
678  *  GetNewPythonLines
679  */
680 //=============================================================================
681 TCollection_AsciiString SMESH_Gen_i::GetNewPythonLines (int theStudyID)
682 {
683   TCollection_AsciiString aScript;
684
685   // Dump trace of API methods calls
686   if (myPythonScripts.find(theStudyID) != myPythonScripts.end()) {
687     Handle(TColStd_HSequenceOfAsciiString) aPythonScript = myPythonScripts[theStudyID];
688     Standard_Integer istr, aLen = aPythonScript->Length();
689     for (istr = 1; istr <= aLen; istr++) {
690       aScript += "\n\t";
691       aScript += aPythonScript->Value(istr);
692     }
693     aScript += "\n";
694   }
695
696   return aScript;
697 }
698
699 //=============================================================================
700 /*!
701  *  CleanPythonTrace
702  */
703 //=============================================================================
704 void SMESH_Gen_i::CleanPythonTrace (int theStudyID)
705 {
706   TCollection_AsciiString aScript;
707
708   // Clean trace of API methods calls
709   if (myPythonScripts.find(theStudyID) != myPythonScripts.end()) {
710     myPythonScripts[theStudyID]->Clear();
711   }
712 }