Salome HOME
fe877f791556c7ede77273f58b7482b28a1ffa4a
[modules/geom.git] / src / GEOM_I / GEOM_Gen_i.cc
1 // Copyright (C) 2007-2012  CEA/DEN, EDF R&D, OPEN CASCADE
2 //
3 // Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
5 //
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License.
10 //
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 // Lesser General Public License for more details.
15 //
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
19 //
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22
23 #ifdef WNT
24 #pragma warning( disable:4786 )
25 #endif
26
27 #include <Standard_Stream.hxx>
28
29 #include "GEOM_Gen_i.hh"
30 #include "GEOM_Object_i.hh"
31
32 #include <set>
33 #include <sstream>
34
35 #include "Utils_CorbaException.hxx"
36 #include "OpUtil.hxx"
37 #include "Utils_ExceptHandlers.hxx"
38 #include "utilities.h"
39
40 #include "GEOM_Object_i.hh"
41 #include "GEOM_Object.hxx"
42 #include "GEOM_Function.hxx"
43 #include "GEOM_ISubShape.hxx"
44 #include <GEOM_PythonDump.hxx>
45 #include "GEOMImpl_Types.hxx"
46 #include "GEOMImpl_CopyDriver.hxx"
47
48 // Cascade headers
49 #include <BRep_Builder.hxx>
50 #include <BRepTools.hxx>
51 #include <TDF_Label.hxx>
52 #include <TDF_Tool.hxx>
53 #include <TDF_ChildIDIterator.hxx>
54 #include <TNaming_NamedShape.hxx>
55 #include <TDataStd_Name.hxx>
56 #include <TCollection_AsciiString.hxx>
57 #include <TColStd_HArray1OfInteger.hxx>
58 #include <TopAbs_ShapeEnum.hxx>
59 //#include <TopTools_IndexedMapOfShape.hxx>
60 #include <TopExp.hxx>
61 #include <OSD.hxx>
62
63 #include "SALOMEDS_Tool.hxx"
64
65 //============================================================================
66 // function : GEOM_Gen_i()
67 // purpose  : constructor to be called for servant creation.
68 //============================================================================
69 GEOM_Gen_i::GEOM_Gen_i(CORBA::ORB_ptr            orb,
70                        PortableServer::POA_ptr   poa,
71                        PortableServer::ObjectId* contId,
72                        const char*               instanceName,
73                        const char*               interfaceName) :
74   Engines_Component_i(orb, poa, contId, instanceName, interfaceName)
75 {
76   _thisObj = this;
77   _id = _poa->activate_object(_thisObj);
78   name_service = new SALOME_NamingService(_orb);
79
80   _impl = new ::GEOMImpl_Gen;
81
82   //PAL10867: disable signals catching with "noexcepthandler" option
83   char* envNoCatchSignals = getenv("NOT_INTERCEPT_SIGNALS");
84   if (!envNoCatchSignals || !atoi(envNoCatchSignals))
85   {
86     //work around PAL12004, PAL12628
87     //OSD::SetSignal( true );
88     bool raiseFPE;
89 #ifdef _DEBUG_
90     raiseFPE = true;
91     char* envDisableFPE = getenv("DISABLE_FPE");
92     if (envDisableFPE && atoi(envDisableFPE))
93       raiseFPE = false;
94 #else
95     raiseFPE = false;
96 #endif
97     OSD::SetSignal( raiseFPE );
98   }
99 }
100
101 //============================================================================
102 // function : ~GEOM_Gen_i()
103 // purpose  : destructor
104 //============================================================================
105 GEOM_Gen_i::~GEOM_Gen_i() {
106   delete name_service;
107   delete _impl;
108 }
109
110
111 //============================================================================
112 // function : IORToLocalPersistentID()
113 // purpose  :
114 //============================================================================
115 char* GEOM_Gen_i::IORToLocalPersistentID(SALOMEDS::SObject_ptr theSObject,
116                                          const char* IORString,
117                                          CORBA::Boolean isMultiFile,
118                                          CORBA::Boolean isASCII)
119 {
120   GEOM::GEOM_Object_var anObject = GEOM::GEOM_Object::_narrow(_orb->string_to_object(IORString));
121   if (!CORBA::is_nil(anObject)) {
122     return CORBA::string_dup(anObject->GetEntry());
123   }
124   return 0;
125 }
126
127
128 //============================================================================
129 // function : LocalPersistentIDToIOR()
130 // purpose  : Create/Load CORBA object from a persistent ref (an entry)
131 //          : Used when a study is loaded
132 //          : The IOR (IORName) of object created is returned
133 //============================================================================
134 char* GEOM_Gen_i::LocalPersistentIDToIOR(SALOMEDS::SObject_ptr theSObject,
135                                          const char* aLocalPersistentID,
136                                          CORBA::Boolean isMultiFile,
137                                          CORBA::Boolean isASCII)
138 {
139   SALOMEDS::Study_var aStudy = theSObject->GetStudy();
140
141   Handle(GEOM_Object) anObject = _impl->GetObject(aStudy->StudyId(), const_cast<char*>(aLocalPersistentID));
142   TCollection_AsciiString anEntry;
143   TDF_Tool::Entry(anObject->GetEntry(), anEntry);
144   GEOM::GEOM_Object_var obj = GetObject(anObject->GetDocID(), anEntry.ToCString());
145
146   CORBA::String_var aPersRefString = _orb->object_to_string(obj);
147   return CORBA::string_dup(aPersRefString);
148 }
149
150 //============================================================================
151 // function : CanPublishInStudy
152 // purpose  :
153 //============================================================================
154 bool GEOM_Gen_i::CanPublishInStudy(CORBA::Object_ptr theIOR)
155 {
156   GEOM::GEOM_Object_var anObject = GEOM::GEOM_Object::_narrow(theIOR);
157   return !(anObject->_is_nil());
158 }
159
160
161 //============================================================================
162 // function : PublishInStudy
163 // purpose  :
164 //============================================================================
165 SALOMEDS::SObject_ptr GEOM_Gen_i::PublishInStudy(SALOMEDS::Study_ptr theStudy,
166                                                  SALOMEDS::SObject_ptr theSObject,
167                                                  CORBA::Object_ptr theObject,
168                                                  const char* theName) throw (SALOME::SALOME_Exception)
169 {
170   Unexpect aCatch(SALOME_SalomeException);
171   SALOMEDS::SObject_var aResultSO;
172   if(CORBA::is_nil(theObject) || theStudy->_is_nil()) return aResultSO;
173   GEOM::GEOM_Object_var aShape = GEOM::GEOM_Object::_narrow(theObject);
174   if(aShape->_is_nil()) return aResultSO;
175
176   SALOMEDS::GenericAttribute_var anAttr;
177   SALOMEDS::StudyBuilder_var     aStudyBuilder = theStudy->NewBuilder();
178
179   SALOMEDS::SComponent_var       aFather = theStudy->FindComponent("GEOM");
180   if (aFather->_is_nil()) {
181     aFather = aStudyBuilder->NewComponent("GEOM");
182     anAttr = aStudyBuilder->FindOrCreateAttribute(aFather, "AttributeName");
183     SALOMEDS::AttributeName_var aName = SALOMEDS::AttributeName::_narrow(anAttr);
184     aName->SetValue("Geometry");
185     aName->UnRegister();
186     anAttr = aStudyBuilder->FindOrCreateAttribute(aFather, "AttributePixMap");
187     SALOMEDS::AttributePixMap_var aPixMap=SALOMEDS::AttributePixMap::_narrow(anAttr);
188     aPixMap->SetPixMap("ICON_OBJBROWSER_Geometry");
189     aPixMap->UnRegister();
190     aStudyBuilder->DefineComponentInstance(aFather, (GEOM::GEOM_Gen_var)GEOM_Gen::_this());
191   }
192   if (aFather->_is_nil()) return aResultSO;
193
194   if (CORBA::is_nil(theSObject)) {
195     aResultSO = aStudyBuilder->NewObject(aFather);
196   } else {
197     if (!theSObject->ReferencedObject(aResultSO))
198       aResultSO = SALOMEDS::SObject::_duplicate(theSObject); //SRN: Added Aug 24,2004 : for  the method AddInStudy with theFather argumenet != NULL
199       //THROW_SALOME_CORBA_EXCEPTION("Publish in study supervision graph error",SALOME::BAD_PARAM);
200   }
201   CORBA::String_var aGeomObjIOR = _orb->object_to_string(theObject);
202   aResultSO->SetAttrString("AttributeIOR",aGeomObjIOR);
203
204   TCollection_AsciiString aShapeName("Shape_");
205
206   CORBA::Long mytype=aShape->GetType();
207   if ( mytype == GEOM_GROUP ) {
208     GEOM::GEOM_IGroupOperations_var anOp = GetIGroupOperations( theStudy->StudyId() );
209     switch ( (TopAbs_ShapeEnum)anOp->GetType( aShape ) ) {
210     case TopAbs_VERTEX:
211       aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_GROUP_PNT" );
212       aShapeName = "Group_Of_Vertices_";
213       break;
214     case TopAbs_EDGE:
215       aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_GROUP_EDGE");
216       aShapeName = "Group_Of_Edges_";
217       break;
218     case TopAbs_FACE:
219       aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_GROUP_FACE");
220       aShapeName = "Group_Of_Faces_";
221       break;
222     case TopAbs_SOLID:
223       aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_GROUP_SOLID");
224       aShapeName = "Group_Of_Solids_";
225       break;
226     }
227   } else if ( mytype == GEOM_MARKER ) {
228     aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_LCS");
229     aShapeName = "LocalCS_";
230   } else if ( mytype > ADVANCED_BASE ) {
231     char buf[20];
232     sprintf( buf, "%d", aShape->GetType() );
233     std::string advId = "ICON_OBJBROWSER_ADVANCED_"; advId += buf;
234     aResultSO->SetAttrString("AttributePixMap",advId.c_str());
235     aShapeName = "Advanced_";
236   } else {
237     GEOM::shape_type myshapetype=aShape->GetShapeType();
238     if ( myshapetype == GEOM::COMPOUND ) {
239     aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_COMPOUND" );
240     aShapeName = "Compound_";
241   } else if ( myshapetype == GEOM::COMPSOLID ) {
242     aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_COMPSOLID");
243     aShapeName = "Compsolid_";
244   } else if ( myshapetype == GEOM::SOLID ) {
245     aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_SOLID");
246     aShapeName = "Solid_";
247   } else if ( myshapetype == GEOM::SHELL ) {
248     aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_SHELL");
249     aShapeName = "Shell_";
250   } else if ( myshapetype == GEOM::FACE ) {
251     aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_FACE");
252     aShapeName = "Face_";
253   } else if ( myshapetype == GEOM::WIRE ) {
254     aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_WIRE");
255     aShapeName = "Wire_";
256   } else if ( myshapetype == GEOM::EDGE ) {
257     aResultSO->SetAttrString("AttributePixMap", "ICON_OBJBROWSER_EDGE");
258     aShapeName = "Edge_";
259   } else if ( myshapetype == GEOM::VERTEX ) {
260     aResultSO->SetAttrString("AttributePixMap","ICON_OBJBROWSER_VERTEX" );
261     aShapeName = "Vertex_";
262   }
263   }
264   //if (strlen(theName) == 0) aShapeName += TCollection_AsciiString(aResultSO->Tag());
265   //else aShapeName = TCollection_AsciiString(CORBA::string_dup(theName));
266
267   // BEGIN: try to find existed name for current shape
268   bool HasName = false;
269   // recieve current TopoDS shape
270   CORBA::String_var entry = aShape->GetEntry();
271   Handle(GEOM_Object) aGShape = _impl->GetObject(aShape->GetStudyID(), entry);
272   TopoDS_Shape TopoSh = aGShape->GetValue();
273   // find label of main shape
274   GEOM::GEOM_Object_var aMainSh = aShape;
275   while( !aMainSh->IsMainShape() ) {
276     aMainSh = aMainSh->GetMainShape();
277   }
278   entry = aMainSh->GetEntry();
279   Handle(GEOM_Object) anObj = _impl->GetObject(aMainSh->GetStudyID(), entry);
280   TDF_Label aMainLbl = anObj->GetFunction(1)->GetNamingEntry();
281
282   // check all named shapes using iterator
283   TDF_ChildIDIterator anIt (aMainLbl, TNaming_NamedShape::GetID(), Standard_True);
284
285   for (; anIt.More() && !HasName; anIt.Next()) {
286     Handle(TNaming_NamedShape) anAttr =
287       Handle(TNaming_NamedShape)::DownCast(anIt.Value());
288     if (anAttr.IsNull()) continue;
289     TopoDS_Shape S = anAttr->Get();
290     if (S.IsEqual(TopoSh)) {
291       TDF_Label L = anAttr->Label();
292       Handle(TDataStd_Name) aName;
293       if (L.FindAttribute(TDataStd_Name::GetID(), aName)) {
294         aShapeName = aName->Get();
295         HasName = true;
296       }
297     }
298   }
299   // END: try to find existed name for current shape
300
301   if (!HasName) {
302     // asv : 11.11.04 Introducing a more sofisticated method of name creation, just as
303     //       it is done in GUI in GEOMBase::GetDefaultName() - not just add a Tag() == number
304     //       of objects in the study, but compute a number of objects with the same prefix
305     //       and build a new name as Prefix_N+1
306     if ( strlen( theName ) == 0 ) { // MOST PROBABLY CALLED FROM BATCHMODE OR SUPERVISOR
307       int i = 0;                    // (WITH EMPTY NEW NAME)
308       SALOMEDS::SObject_var obj;
309       TCollection_AsciiString aNewShapeName;
310       do {
311         aNewShapeName = aShapeName + TCollection_AsciiString(++i);
312         obj = theStudy->FindObject( aNewShapeName.ToCString() );
313       }
314       while ( !obj->_is_nil() );
315       aShapeName = aNewShapeName;
316     }
317     else // MOST PROBABLY CALLED FROM GEOM GUI (ALREADY WITH VALID NAME)
318       aShapeName = TCollection_AsciiString((char*)theName);
319   }
320
321   //Set the study entry as a name of  the published GEOM_Object
322   CORBA::String_var anID =aResultSO->GetID();
323   aShape->SetStudyEntry(anID.in());
324
325   //Set a name of the added shape
326   aResultSO->SetAttrString("AttributeName",aShapeName.ToCString());
327
328   //Set NoteBook variables used in the object creation
329   TCollection_AsciiString aVars;
330   CORBA::String_var aString=aShape->GetParameters();
331   SALOMEDS::ListOfListOfStrings_var aSections = theStudy->ParseVariables(aString);
332   for(int i = 0, n = aSections->length(); i < n; i++) {
333     SALOMEDS::ListOfStrings aListOfVars = aSections[i];
334     for(int j = 0, m = aListOfVars.length(); j < m; j++) {
335       if(theStudy->IsVariable(aListOfVars[j].in()))
336         aVars += TCollection_AsciiString(aListOfVars[j].in());
337       if(j != m-1)
338         aVars += ":";
339     }
340     if(i != n-1)
341       aVars += "|";
342   }
343   aResultSO->SetAttrString("AttributeString",aVars.ToCString());
344
345   aFather->UnRegister();
346
347   //Set a name of the GEOM object
348   aShape->SetName(aShapeName.ToCString());
349
350   return aResultSO._retn();
351 }
352
353
354 //============================================================================
355 // function : CreateAndPublishGroup
356 // purpose  : auxilary for PublishNamedShapesInStudy
357 //============================================================================
358 void GEOM_Gen_i::CreateAndPublishGroup(SALOMEDS::Study_ptr theStudy,
359                                        GEOM::GEOM_Object_var theMainShape,
360                                        const TopTools_IndexedMapOfShape& anIndices,
361                                        const TopTools_SequenceOfShape& SeqS,
362                                        const TColStd_SequenceOfAsciiString& SeqN,
363                                        const Standard_CString& GrName,
364                                        GEOM::ListOfGO_var aResList)
365 {
366   CORBA::String_var entry = theMainShape->GetEntry();
367   Handle(GEOM_Object) aMainShape = _impl->GetObject(theMainShape->GetStudyID(), entry);
368   Handle(TColStd_HArray1OfInteger) anArray;
369   if(SeqS.Length()>0) {
370     // create a group
371     GEOM::GEOM_IGroupOperations_var GOp = GetIGroupOperations(theStudy->StudyId());
372     GEOM::GEOM_Object_ptr GrObj =
373       GOp->CreateGroup( theMainShape, SeqS.Value(1).ShapeType() );
374     AddInStudy(theStudy, GrObj, GrName, theMainShape._retn());
375     CORBA::String_var GrEntry = GrObj->GetEntry();
376     Handle(GEOM_Object) HGrObj = _impl->GetObject(GrObj->GetStudyID(), GrEntry);
377     // add named objects
378     //Handle(GEOM_Object) anObj;
379     for(int i=1; i<=SeqS.Length(); i++) {
380       TopoDS_Shape aValue = SeqS.Value(i);
381       //anArray = new TColStd_HArray1OfInteger(1,1);
382       Standard_Integer anIndex = anIndices.FindIndex(aValue);
383       //anArray->SetValue(1, anIndex);
384       GOp->AddObject(GrObj,anIndex);
385       //anObj = GEOM_Engine::GetEngine()->AddObject(aMainShape->GetDocID(), GEOM_SUBSHAPE);
386       //if (anObj.IsNull()) continue;
387       //Handle(GEOM_Function) aFunction = anObj->AddFunction(GEOM_Object::GetSubShapeID(), 1);
388       //if (aFunction.IsNull()) continue;
389       //GEOM_ISubShape aSSI(aFunction);
390       //aSSI.SetMainShape(aMainShape->GetLastFunction());
391       //aSSI.SetIndices(anArray);
392       //aFunction->SetValue(aValue);
393       //GOp->UnionIDs(GrObj, anIndex);
394       //SALOMEDS::SObject_var aResultSO;
395       //TCollection_AsciiString anEntry;
396       //TDF_Tool::Entry(anObj->GetEntry(),anEntry);
397       //GEOM::GEOM_Object_var aGObj = GetObject(anObj->GetDocID(), anEntry.ToCString());
398       //AddInStudy(theStudy, aGObj._retn(), SeqN.Value(i).ToCString(), GrObj);
399     }
400   }
401 }
402
403
404 //============================================================================
405 // function : PublishNamedShapesInStudy
406 // purpose  :
407 //============================================================================
408 GEOM::ListOfGO* GEOM_Gen_i::
409             PublishNamedShapesInStudy(SALOMEDS::Study_ptr theStudy,
410                                       //SALOMEDS::SObject_ptr theSObject,
411                                       CORBA::Object_ptr theObject)
412 {
413   //Unexpect aCatch(SALOME_SalomeException);
414   GEOM::ListOfGO_var aResList = new GEOM::ListOfGO;
415
416   //CORBA::Object_var theObject = theSObject->GetObject();
417   GEOM::GEOM_Object_var theMainShape = GEOM::GEOM_Object::_narrow(theObject);
418   if(theMainShape->_is_nil()) return aResList._retn();
419
420   CORBA::String_var entry = theMainShape->GetEntry();
421   Handle(GEOM_Object) aMainShape = _impl->GetObject(theMainShape->GetStudyID(), entry);
422   if (aMainShape.IsNull()) return aResList._retn();
423   TopoDS_Shape MainSh = aMainShape->GetValue();
424
425   TDF_Label aMainLbl = aMainShape->GetEntry();
426   TopTools_SequenceOfShape SolidSeqS, FaceSeqS, EdgeSeqS, VertSeqS;
427   TColStd_SequenceOfAsciiString SolidSeqN, FaceSeqN, EdgeSeqN, VertSeqN;
428   TDF_ChildIDIterator anIt(aMainLbl, TNaming_NamedShape::GetID(), Standard_True);
429   for(; anIt.More(); anIt.Next()) {
430     Handle(TNaming_NamedShape) anAttr =
431       Handle(TNaming_NamedShape)::DownCast(anIt.Value());
432     if(anAttr.IsNull()) continue;
433     TopoDS_Shape S = anAttr->Get();
434     TDF_Label L = anAttr->Label();
435     //if(S.IsEqual(MainSh)) continue;
436     Handle(TDataStd_Name) aName;
437     if(L.FindAttribute(TDataStd_Name::GetID(),aName)) {
438       TCollection_ExtendedString EName = aName->Get();
439       if(S.ShapeType()==TopAbs_SOLID) {
440         SolidSeqS.Append(S);
441         SolidSeqN.Append(aName->Get());
442       }
443       else if(S.ShapeType()==TopAbs_FACE) {
444         FaceSeqS.Append(S);
445         FaceSeqN.Append(aName->Get());
446       }
447       else if(S.ShapeType()==TopAbs_EDGE) {
448         EdgeSeqS.Append(S);
449         EdgeSeqN.Append(aName->Get());
450       }
451       else if(S.ShapeType()==TopAbs_VERTEX) {
452         VertSeqS.Append(S);
453         VertSeqN.Append(aName->Get());
454       }
455     }
456   }
457
458   TopTools_IndexedMapOfShape anIndices;
459   TopExp::MapShapes(MainSh, anIndices);
460
461   CreateAndPublishGroup(theStudy, theMainShape, anIndices, SolidSeqS, SolidSeqN,
462                         "Group_Of_Named_Solids", aResList);
463
464   CreateAndPublishGroup(theStudy, theMainShape, anIndices, FaceSeqS, FaceSeqN,
465                         "Group_Of_Named_Faces", aResList);
466
467   CreateAndPublishGroup(theStudy, theMainShape, anIndices, EdgeSeqS, EdgeSeqN,
468                         "Group_Of_Named_Edges", aResList);
469
470   CreateAndPublishGroup(theStudy, theMainShape, anIndices, VertSeqS, VertSeqN,
471                         "Group_Of_Named_Vertices", aResList);
472
473   return aResList._retn();
474 }
475
476
477 //============================================================================
478 // function : Save()
479 // purpose  : save OCAF/Geom document
480 //============================================================================
481 SALOMEDS::TMPFile* GEOM_Gen_i::Save(SALOMEDS::SComponent_ptr theComponent,
482                                     const char* theURL,
483                                     bool isMultiFile) {
484   SALOMEDS::TMPFile_var aStreamFile;
485   // Get a temporary directory to store a file
486   std::string aTmpDir = (isMultiFile)?theURL:SALOMEDS_Tool::GetTmpDir();
487
488   // OCCT BUG: cannot save a document (in current folder)
489   // if directory name is empty
490   if (aTmpDir.size() == 0) {
491 #ifdef WNT
492     aTmpDir = ".\\";
493 #else
494     aTmpDir = "./";
495 #endif
496   }
497
498   // Create a list to store names of created files
499   SALOMEDS::ListOfFileNames_var aSeq = new SALOMEDS::ListOfFileNames;
500   aSeq->length(1);
501   // Prepare a file name to open
502   TCollection_AsciiString aNameWithExt("");
503   if (isMultiFile)
504     aNameWithExt = TCollection_AsciiString((char*)(SALOMEDS_Tool::GetNameFromPath
505                                                    (theComponent->GetStudy()->URL())).c_str());
506   aNameWithExt += TCollection_AsciiString("_GEOM.sgd");
507   aSeq[0] = CORBA::string_dup(aNameWithExt.ToCString());
508   // Build a full file name of temporary file
509   TCollection_AsciiString aFullName = TCollection_AsciiString((char*)aTmpDir.c_str()) + aNameWithExt;
510   // Save GEOM component in this file
511   _impl->Save(theComponent->GetStudy()->StudyId(),(char*) aFullName.ToCString());
512   // Conver a file to the byte stream
513   aStreamFile = SALOMEDS_Tool::PutFilesToStream(aTmpDir.c_str(), aSeq.in(), isMultiFile);
514   // Remove the created file and tmp directory
515   if (!isMultiFile) SALOMEDS_Tool::RemoveTemporaryFiles(aTmpDir.c_str(), aSeq.in(), true);
516
517   // Return the created byte stream
518   return aStreamFile._retn();
519 }
520
521
522 //============================================================================
523 // function : SaveASCII()
524 // purpose  :
525 //============================================================================
526 SALOMEDS::TMPFile* GEOM_Gen_i::SaveASCII(SALOMEDS::SComponent_ptr theComponent,
527                                          const char* theURL,
528                                          bool isMultiFile) {
529   SALOMEDS::TMPFile_var aStreamFile = Save(theComponent, theURL, isMultiFile);
530   return aStreamFile._retn();
531 }
532
533
534 //============================================================================
535 // function : Load()
536 // purpose  :
537 //============================================================================
538 CORBA::Boolean GEOM_Gen_i::Load(SALOMEDS::SComponent_ptr theComponent,
539                                 const SALOMEDS::TMPFile& theStream,
540                                 const char* theURL,
541                                 bool isMultiFile) {
542
543   if (theStream.length() <= 9) {
544     MESSAGE("The TMPFile is too short : " << theStream.length() << " bytes ");
545     return false;
546   }
547
548   // Get a temporary directory for a file
549   std::string aTmpDir = isMultiFile?theURL:SALOMEDS_Tool::GetTmpDir();
550
551   // OCCT BUG: cannot load a document (from current folder)
552   // if directory name is empty
553   if (aTmpDir.size() == 0) {
554 #ifdef WNT
555     aTmpDir = ".\\";
556 #else
557     aTmpDir = "./";
558 #endif
559   }
560
561   // Conver the byte stream theStream to a file and place it in tmp directory
562   SALOMEDS::ListOfFileNames_var aSeq =
563     SALOMEDS_Tool::PutStreamToFiles(theStream, aTmpDir.c_str(), isMultiFile);
564
565   // Prepare a file name to open
566   TCollection_AsciiString aNameWithExt("");
567   if (isMultiFile)
568     aNameWithExt = TCollection_AsciiString((char*)(SALOMEDS_Tool::GetNameFromPath
569                                                    (theComponent->GetStudy()->URL())).c_str());
570   aNameWithExt += TCollection_AsciiString("_GEOM.sgd");
571   TCollection_AsciiString aFullName = (TCollection_AsciiString((char*)aTmpDir.c_str()) + aNameWithExt);
572
573   // Open document
574   if (!_impl->Load(theComponent->GetStudy()->StudyId(),(char*) aFullName.ToCString())) return false;
575
576   // Remove the created file and tmp directory
577   if (!isMultiFile) SALOMEDS_Tool::RemoveTemporaryFiles(aTmpDir.c_str(), aSeq.in(), true);
578
579   SALOMEDS::Study_var Study = theComponent->GetStudy();
580   TCollection_AsciiString name (Study->Name());
581
582   return true;
583 }
584
585
586 //============================================================================
587 // function : LoadASCII()
588 // purpose  :
589 //============================================================================
590 CORBA::Boolean GEOM_Gen_i::LoadASCII(SALOMEDS::SComponent_ptr theComponent,
591                                      const SALOMEDS::TMPFile& theStream,
592                                      const char* theURL,
593                                      bool isMultiFile) {
594   return Load(theComponent, theStream, theURL, isMultiFile);
595 }
596
597
598 //============================================================================
599 // function : Close()
600 // purpose  :
601 //============================================================================
602 void GEOM_Gen_i::Close(SALOMEDS::SComponent_ptr theComponent)
603 {
604   SALOMEDS::Study_var aStudy= theComponent->GetStudy();
605   _impl->Close(aStudy->StudyId());
606 }
607
608 //============================================================================
609 // function : CanCopy()
610 // purpose  :
611 //============================================================================
612 CORBA::Boolean GEOM_Gen_i::CanCopy(SALOMEDS::SObject_ptr theObject) {
613   // Try to retrieve known by Geometry component GEOM_Object by given IOR
614   SALOMEDS::GenericAttribute_var anAttr;
615   if (!theObject->FindAttribute(anAttr, "AttributeIOR")) return false;
616
617   SALOMEDS::AttributeIOR_var anIOR = SALOMEDS::AttributeIOR::_narrow(anAttr);
618
619   CORBA::String_var aString=anIOR->Value();
620   anIOR->UnRegister();
621   CORBA::Object_var anObj = _orb->string_to_object(aString);
622   GEOM::GEOM_Object_var anObject = GEOM::GEOM_Object::_narrow(anObj);
623   // If the object is null one it can't be copied: return false
624   if (anObject->_is_nil()) return false;
625   return true;
626 }
627
628 //============================================================================
629 // function : CopyFrom()
630 // purpose  :
631 //============================================================================
632 SALOMEDS::TMPFile* GEOM_Gen_i::CopyFrom(SALOMEDS::SObject_ptr theObject, CORBA::Long& theObjectID)
633 {
634   // Declare a sequence of the byte to store the copied object
635   SALOMEDS::TMPFile_var aStreamFile = new SALOMEDS::TMPFile;
636
637   // Try to get GEOM_Object object by given SObject
638   SALOMEDS::GenericAttribute_var anAttr;
639   if (!theObject->FindAttribute(anAttr, "AttributeIOR")) return aStreamFile._retn();
640   GEOM::GEOM_Object_var anObject = GEOM::GEOM_Object::_narrow
641     (_orb->string_to_object(SALOMEDS::AttributeIOR::_narrow(anAttr)->Value()));
642   if (anObject->_is_nil()) return aStreamFile._retn();
643
644   aStreamFile = anObject->GetShapeStream();
645
646   // Assign an ID  the type of  GEOM_Object
647   theObjectID = anObject->GetType();
648
649   // Return created TMPFile
650   return aStreamFile._retn();
651 }
652
653 //============================================================================
654 // function : CanPaste()
655 // purpose  :
656 //============================================================================
657 CORBA::Boolean GEOM_Gen_i::CanPaste(const char* theComponentName, CORBA::Long theObjectID) {
658   // The Geometry component can paste only objects copied by Geometry component
659   // and with the object type = 1
660   if (strcmp(theComponentName, ComponentDataType()) != 0) return false;
661   return true;
662 }
663
664 //============================================================================
665 // function : PasteInto()
666 // purpose  :
667 //============================================================================
668 SALOMEDS::SObject_ptr GEOM_Gen_i::PasteInto(const SALOMEDS::TMPFile& theStream,
669                                             CORBA::Long theObjectID,
670                                             SALOMEDS::SObject_ptr theObject) {
671   // Find the current Study and StudyBuilder
672   SALOMEDS::Study_var aStudy = theObject->GetStudy();
673   SALOMEDS::StudyBuilder_var aStudyBuilder = aStudy->NewBuilder();
674
675   // Retrieve a TopoDS_Shape from byte stream
676   TopoDS_Shape aTopology;
677   std::istringstream aStreamedBrep((char*) &theStream[0]);
678   BRep_Builder aBuilder;
679   try {
680     BRepTools::Read(aTopology, aStreamedBrep, aBuilder);
681   } catch (Standard_Failure) {
682     return false;
683   }
684
685   // SObject of the created shape is theObject or new Child of Component if theObject == geom component
686   SALOMEDS::SObject_var aNewSO;
687   if (strcmp(theObject->GetFatherComponent()->GetID(),theObject->GetID()) == 0) {
688     aNewSO = aStudyBuilder->NewObject(theObject);
689   } else aNewSO = SALOMEDS::SObject::_duplicate(theObject);
690
691
692   //Create a new GEOM_Object
693   Handle(GEOM_Object) anObj = _impl->AddObject(aNewSO->GetStudy()->StudyId(), theObjectID);
694   Handle(GEOM_Function) aFunction = anObj->AddFunction(GEOMImpl_CopyDriver::GetID(), COPY_WITHOUT_REF);
695   aFunction->SetValue(aTopology);
696
697   TCollection_AsciiString anEntry;
698   TDF_Tool::Entry(anObj->GetEntry(), anEntry);
699   GEOM::GEOM_Object_var obj = GetObject(anObj->GetDocID(), anEntry.ToCString());
700
701   //Set the study entry of the published GEOM_Object
702   obj->SetStudyEntry(aNewSO->GetID());
703
704   // Add IORAttribute to the Study and set IOR of the created GEOM_Object to it
705   SALOMEDS::GenericAttribute_var anAttr = aStudyBuilder->FindOrCreateAttribute(aNewSO, "AttributeIOR");
706   SALOMEDS::AttributeIOR_var anIOR = SALOMEDS::AttributeIOR::_narrow(anAttr);
707   CORBA::String_var objStr = _orb->object_to_string(obj);
708   anIOR->SetValue(objStr.in());
709   anIOR->UnRegister();
710
711   // Return the created in the Study SObject
712   return aNewSO._retn();
713 }
714
715 //============================================================================
716 // function : ComponentDataType()
717 // purpose  :
718 //============================================================================
719 char* GEOM_Gen_i::ComponentDataType()
720 {
721   return CORBA::string_dup("GEOM");
722 }
723
724 //============================================================================
725 // function : AddInStudy
726 // purpose  :
727 //============================================================================
728 SALOMEDS::SObject_ptr GEOM_Gen_i::AddInStudy (SALOMEDS::Study_ptr theStudy,
729                                               GEOM::GEOM_Object_ptr theObject,
730                                               const char* theName,
731                                               GEOM::GEOM_Object_ptr theFather)
732 {
733   SALOMEDS::SObject_var aResultSO;
734   if(theObject->_is_nil() || theStudy->_is_nil()) return aResultSO;
735
736   SALOMEDS::StudyBuilder_var aStudyBuilder = theStudy->NewBuilder();
737   CORBA::String_var IOR;
738
739   if(!theFather->_is_nil()) {
740     IOR = _orb->object_to_string(theFather);
741     SALOMEDS::SObject_var aFatherSO = theStudy->FindObjectIOR(IOR.in());
742     if(aFatherSO->_is_nil()) return aResultSO._retn();
743     aResultSO = aStudyBuilder->NewObject(aFatherSO);
744     aFatherSO->UnRegister();
745     //aStudyBuilder->Addreference(aResultSO, aResultSO);
746   }
747
748   aResultSO = PublishInStudy(theStudy, aResultSO, theObject, theName);
749   if(aResultSO->_is_nil()) return aResultSO._retn();
750
751   GEOM::ListOfGO_var aList = theObject->GetDependency();
752   Standard_Integer aLength = aList->length();
753   if(aLength < 1) return aResultSO._retn();
754
755   //Publish the arguments
756   TCollection_AsciiString aPrevID; // to avoid multiple references to same object
757   for(Standard_Integer i = 0; i< aLength; i++) {
758     GEOM::GEOM_Object_var anObject = aList[i];
759     if(anObject->_is_nil()) continue;
760     IOR = _orb->object_to_string(anObject);
761     SALOMEDS::SObject_var aSO =  theStudy->FindObjectIOR(IOR.in());
762     if(aSO->_is_nil()) continue;
763     CORBA::String_var anID = aSO->GetID();
764     if ( aPrevID == anID.in() ) continue;
765     aPrevID = anID.in();
766     SALOMEDS::SObject_var aSubSO = aStudyBuilder->NewObject(aResultSO);
767     aStudyBuilder->Addreference(aSubSO, aSO);
768     aSO->UnRegister();
769     aSubSO->UnRegister();
770   }
771
772   return aResultSO._retn();
773 }
774
775 //============================================================================
776 // function : RestoreSubShapesO
777 // purpose  : Publish sub-shapes, standing for arguments and sub-shapes of arguments.
778 //            To be used from python scripts out of geompy.addToStudy (non-default usage)
779 //============================================================================
780 GEOM::ListOfGO* GEOM_Gen_i::RestoreSubShapesO (SALOMEDS::Study_ptr     theStudy,
781                                                GEOM::GEOM_Object_ptr   theObject,
782                                                const GEOM::ListOfGO&   theArgs,
783                                                GEOM::find_shape_method theFindMethod,
784                                                CORBA::Boolean          theInheritFirstArg,
785                                                CORBA::Boolean          theAddPrefix)
786 {
787   GEOM::ListOfGO_var aParts = new GEOM::ListOfGO;
788   if (CORBA::is_nil(theStudy) || CORBA::is_nil(theObject))
789     return aParts._retn();
790
791   // find SObject in the study if it is already published
792   CORBA::String_var anIORo = _orb->object_to_string(theObject);
793   SALOMEDS::SObject_var aSO = theStudy->FindObjectIOR(anIORo.in());
794   //PTv, IMP 0020001, The salome object <aSO>
795   // is not obligatory in case of invokation from script
796   // if (CORBA::is_nil(aSO))
797   //  return aParts._retn();
798
799   aParts = RestoreSubShapes(theStudy, theObject, aSO, theArgs,
800                             theFindMethod, theInheritFirstArg, theAddPrefix);
801   if (!CORBA::is_nil(aSO)) aSO->UnRegister();
802   return aParts._retn();
803 }
804
805 //============================================================================
806 // function : RestoreGivenSubShapesO
807 // purpose  : Publish sub-shapes, standing for arguments and sub-shapes of arguments.
808 //            To be used from python scripts, generated by Dump Python.
809 //============================================================================
810 GEOM::ListOfGO* GEOM_Gen_i::RestoreGivenSubShapesO (SALOMEDS::Study_ptr     theStudy,
811                                                     GEOM::GEOM_Object_ptr   theObject,
812                                                     const GEOM::ListOfGO&   theArgs,
813                                                     GEOM::find_shape_method theFindMethod,
814                                                     CORBA::Boolean          theInheritFirstArg,
815                                                     CORBA::Boolean          theAddPrefix)
816 {
817   GEOM::ListOfGO_var aParts = new GEOM::ListOfGO;
818   if (CORBA::is_nil(theStudy) || CORBA::is_nil(theObject))
819     return aParts._retn();
820
821   // find SObject in the study if it is already published
822   CORBA::String_var anIORo = _orb->object_to_string(theObject);
823   SALOMEDS::SObject_var aSO = theStudy->FindObjectIOR(anIORo.in());
824   //PTv, IMP 0020001, The salome object <aSO>
825   // is not obligatory in case of invokation from script
826   // if (CORBA::is_nil(aSO))
827   //  return aParts._retn();
828
829   aParts = RestoreGivenSubShapes(theStudy, theObject, aSO, theArgs,
830                                  theFindMethod, theInheritFirstArg, theAddPrefix);
831   if (!CORBA::is_nil(aSO)) aSO->UnRegister();
832   return aParts._retn();
833 }
834
835 //============================================================================
836 // function : RestoreSubShapesSO
837 // purpose  : Publish sub-shapes, standing for arguments and sub-shapes of arguments.
838 //            To be used from GUI and from geompy.addToStudy
839 //============================================================================
840 GEOM::ListOfGO* GEOM_Gen_i::RestoreSubShapesSO (SALOMEDS::Study_ptr     theStudy,
841                                                 SALOMEDS::SObject_ptr   theSObject,
842                                                 const GEOM::ListOfGO&   theArgs,
843                                                 GEOM::find_shape_method theFindMethod,
844                                                 CORBA::Boolean          theInheritFirstArg,
845                                                 CORBA::Boolean          theAddPrefix)
846 {
847   GEOM::ListOfGO_var aParts = new GEOM::ListOfGO;
848   if (CORBA::is_nil(theStudy) || CORBA::is_nil(theSObject))
849     return aParts._retn();
850
851   SALOMEDS::GenericAttribute_var anAttr;
852   if (!theSObject->FindAttribute(anAttr, "AttributeIOR"))
853     return aParts._retn();
854
855   SALOMEDS::AttributeIOR_var anAttrIOR = SALOMEDS::AttributeIOR::_narrow(anAttr);
856   CORBA::String_var anIORso = anAttrIOR->Value();
857
858   // get Object from SObject
859   GEOM::GEOM_Object_var anO = GEOM::GEOM_Object::_narrow(_orb->string_to_object(anIORso));
860   if (CORBA::is_nil(anO))
861     return aParts._retn();
862
863   aParts = RestoreSubShapes(theStudy, anO, theSObject, theArgs,
864                             theFindMethod, theInheritFirstArg, theAddPrefix);
865   return aParts._retn();
866 }
867
868 //============================================================================
869 // function : addToListOfGO
870 // purpose  : static local function
871 //============================================================================
872 static void addToListOfGO( GEOM::GEOM_Object_ptr theObject,
873                            GEOM::ListOfGO& theList )
874 {
875   const int oldLen = theList.length();
876   theList.length(oldLen + 1);
877   theList[ oldLen ] = GEOM::GEOM_Object::_duplicate( theObject );
878 }
879
880 //============================================================================
881 // function : addToListOfGO
882 // purpose  : static local function
883 //============================================================================
884 static void addToListOfGO( const GEOM::ListOfGO& theSrcList,
885                            GEOM::ListOfGO& theTrgList )
886 {
887   const int oldLen = theTrgList.length();
888   const int srcLen = theSrcList.length();
889   theTrgList.length(oldLen + srcLen);
890   for( int i = 0; i < srcLen; i++ )
891     theTrgList[ oldLen + i ] = GEOM::GEOM_Object::_duplicate( theSrcList[ i ] );
892 }
893
894 //============================================================================
895 // function : RestoreSubShapes
896 // purpose  : Private method. Works only if both theObject and theSObject
897 //            are defined, and does not check, if they correspond to each other.
898 //============================================================================
899 GEOM::ListOfGO* GEOM_Gen_i::RestoreSubShapes(SALOMEDS::Study_ptr     theStudy,
900                                              GEOM::GEOM_Object_ptr   theObject,
901                                              SALOMEDS::SObject_ptr   theSObject,
902                                              const GEOM::ListOfGO&   theArgs,
903                                              GEOM::find_shape_method theFindMethod,
904                                              CORBA::Boolean          theInheritFirstArg,
905                                              CORBA::Boolean          theAddPrefix)
906 {
907   GEOM::ListOfGO_var aParts = new GEOM::ListOfGO;
908   //PTv, IMP 0020001, The salome object <theSObject>
909   //     is not obligatory in case of invokation from script
910   if (CORBA::is_nil(theStudy) || CORBA::is_nil(theObject) /*|| CORBA::is_nil(theSObject)*/)
911     return aParts._retn();
912
913   // For Dump Python (mantis issue 0020768)
914   GEOM::ListOfGO_var anOutArgs = new GEOM::ListOfGO;
915
916   // Arguments to be published
917   GEOM::ListOfGO_var aList;
918
919   // If theArgs list is empty, we try to publish all arguments,
920   // otherwise publish only passed args
921   Standard_Integer nbArgsActual = -1; // -1 means unknown
922   Standard_Integer aLength = theArgs.length();
923   if (aLength > 0) {
924     aList = new GEOM::ListOfGO;
925     aList->length(aLength);
926     for (int i = 0; i < aLength; i++) {
927       aList[i] = GEOM::GEOM_Object::_duplicate( theArgs[i] );
928     }
929   }
930   else {
931     // Get all arguments
932     aList = theObject->GetDependency();
933     aLength = aList->length();
934     nbArgsActual = aLength;
935   }
936
937   if (aLength < 1)
938     return aParts._retn();
939
940   if (theInheritFirstArg || (nbArgsActual == 1)) {
941     // Do not publish argument's reflection,
942     // but only reconstruct its published sub-shapes
943
944     CORBA::String_var anIOR = _orb->object_to_string(aList[0]);
945     SALOMEDS::SObject_var anArgSO = theStudy->FindObjectIOR(anIOR.in());
946
947     // remember restored objects for Python Dump
948     addToListOfGO(aList[0], anOutArgs);
949
950     aParts = RestoreSubShapesOneLevel(theStudy, anArgSO, theSObject, theObject,
951                                       anOutArgs, theFindMethod, theAddPrefix);
952
953     // set the color of the transformed shape to the color of initial shape
954     theObject->SetColor(aList[0]->GetColor());
955     // set the texture
956     if (theObject->GetShapeType() == GEOM::VERTEX) {
957       theObject->SetMarkerStd(aList[0]->GetMarkerType(), aList[0]->GetMarkerSize());
958       if (aList[0]->GetMarkerType() == GEOM::MT_USER)
959         theObject->SetMarkerTexture(aList[0]->GetMarkerTexture());
960     }
961
962     anArgSO->UnRegister();
963   }
964   else {
965     // Get interface, containing method, which we will use to reconstruct sub-shapes
966     GEOM::GEOM_IShapesOperations_var  aShapesOp = GetIShapesOperations(theStudy->StudyId());
967     GEOM::GEOM_IGroupOperations_var    aGroupOp = GetIGroupOperations(theStudy->StudyId());
968     GEOM::GEOM_ITransformOperations_var aTrsfOp = GetITransformOperations(theStudy->StudyId());
969
970     // Reconstruct arguments and tree of sub-shapes of the arguments
971     CORBA::String_var anIOR;
972     SALOMEDS::StudyBuilder_var aStudyBuilder = theStudy->NewBuilder();
973     for (Standard_Integer i = 0; i < aLength; i++)
974     {
975       GEOM::GEOM_Object_var anArgO = aList[i];
976       if (!CORBA::is_nil(anArgO)) {
977         anIOR = _orb->object_to_string(anArgO);
978         SALOMEDS::SObject_var anArgSO = theStudy->FindObjectIOR(anIOR.in());
979         TCollection_AsciiString anArgName;
980         if (CORBA::is_nil(anArgSO)) {
981           anArgName = "arg_";
982           anArgName += TCollection_AsciiString(i);
983         }
984         else {
985           anArgName = anArgSO->GetName();
986         }
987
988         // Find a sub-shape of theObject in place of the argument
989         GEOM::GEOM_Object_var aSubO;
990         switch (theFindMethod) {
991         case GEOM::FSM_GetInPlace:
992           {
993             // Use GetInPlace
994             aSubO = aShapesOp->GetInPlace(theObject, anArgO);
995           }
996           break;
997         case GEOM::FSM_MultiTransformed:
998           {
999             // Only for Multi-transformations
1000             GEOM::GEOM_Object_var anArgOTrsf = aTrsfOp->TransformLikeOtherCopy(anArgO, theObject);
1001             if (!CORBA::is_nil(anArgOTrsf)) {
1002               CORBA::String_var anArgOTrsfEntry = anArgOTrsf->GetEntry();
1003               Handle(GEOM_Object) anArgOTrsfImpl = _impl->GetObject(anArgOTrsf->GetStudyID(), anArgOTrsfEntry);
1004               Handle(GEOM_Function) anArgOTrsfFun = anArgOTrsfImpl->GetLastFunction();
1005               anArgOTrsfFun->SetDescription("");
1006               aSubO = aShapesOp->GetInPlace(theObject, anArgOTrsf);
1007             }
1008             /*
1009             Handle(GEOM_Function) anOFun = theObject->GetLastFunction();
1010             if (!anOFun.IsNull()) {
1011               CORBA::String_var entryArg = anArgO->GetEntry();
1012               Handle(GEOM_Object) anArgOImpl = _impl->GetObject(anArgO->GetStudyID(), entryArg);
1013               if (!anArgOImpl.IsNull()) {
1014                 TopoDS_Shape anArgOShape = anArgOImpl->GetValue();
1015                 TopoDS_Shape aMultiArgShape;
1016                 //GEOM::GEOM_Object_var anArgOMulti; // ???
1017                 switch (anOFun->GetType()) {
1018                 case TRANSLATE_1D:
1019                   {
1020                     GEOMImpl_ITranslate aTI (anOFun);
1021                     aMultiArgShape = GEOMImpl_ITransformOperations::TranslateShape1D(anArgOShape, &aTI);
1022                     //anArgOMulti = aTrsfOp->Translate1D(anArgO, , , );
1023                   }
1024                   break;
1025                 case TRANSLATE_2D:
1026                   {
1027                     GEOMImpl_ITranslate aTI (anOFun);
1028                     aMultiArgShape = GEOMImpl_ITransformOperations::TranslateShape2D(anArgOShape, &aTI);
1029                   }
1030                   break;
1031                 case ROTATE_1D:
1032                   {
1033                     GEOMImpl_IRotate aTI (anOFun);
1034                     //aMultiArgShape = GEOMImpl_ITransformOperations::TranslateShape2D(anArgOShape, &aTI);
1035                   }
1036                   break;
1037                 case ROTATE_2D:
1038                   {
1039                     GEOMImpl_IRotate aTI (anOFun);
1040                     //aMultiArgShape = GEOMImpl_ITransformOperations::TranslateShape2D(anArgOShape, &aTI);
1041                   }
1042                   break;
1043                 default:
1044                   {}
1045                 }
1046                 GEOM::GEOM_Object_var anArgOMulti = (aMultiArgShape); // TODO
1047                 Handle(GEOM_Function) anArgOMultiFun = anArgOMulti->GetLastFunction();
1048                 anArgOMultiFun->SetDescription("");
1049                 aSubO = aShapesOp->GetInPlace(theObject, anArgOMulti);
1050               }
1051             }
1052             */
1053           }
1054           break;
1055         case GEOM::FSM_Transformed:
1056           {
1057             // transformation, cannot use GetInPlace, operate with indices
1058             GEOM::ListOfLong_var anIDs = anArgO->GetSubShapeIndices();
1059             if (anIDs->length() > 1) {
1060               // group
1061               aSubO = aGroupOp->CreateGroup(theObject, aGroupOp->GetType(anArgO));
1062               if (!CORBA::is_nil(aSubO))
1063                 aGroupOp->UnionIDs(aSubO, anIDs);
1064             }
1065             else if (anIDs->length() > 0) {
1066               // single sub-shape
1067               aSubO = aShapesOp->GetSubShape(theObject, anIDs[0]);
1068             }
1069           }
1070           break;
1071         case GEOM::FSM_GetSame:
1072           {
1073             // Use GetSame
1074             aSubO = aShapesOp->GetSame(theObject, anArgO);
1075           }
1076           break;
1077         case GEOM::FSM_GetShapesOnShape:
1078           {
1079             // Use GetShapesOnShape. Can work only on solids, so it has sense to search only solids
1080             aSubO = aShapesOp->GetShapesOnShapeAsCompound(anArgO, theObject,
1081               (short)GEOM::SOLID, GEOM::ST_ONIN);
1082           }
1083           break;
1084         case GEOM::FSM_GetInPlaceByHistory:
1085           {
1086             // Use GetInPlaceByHistory
1087             aSubO = aShapesOp->GetInPlaceByHistory(theObject, anArgO);
1088           }
1089           break;
1090         default:
1091           {}
1092         }
1093
1094         if (!CORBA::is_nil(aSubO)) {
1095           // remember restored objects for Python Dump
1096           addToListOfGO(anArgO, anOutArgs);
1097
1098           // add to parts list
1099           addToListOfGO( aSubO, aParts );
1100
1101           // Publish the sub-shape
1102           SALOMEDS::SObject_var aSubSO;
1103           if (!CORBA::is_nil(theSObject)) {
1104             TCollection_AsciiString aSubName;
1105             if (theAddPrefix) {
1106               aSubName = "from_";
1107             }
1108             aSubName += anArgName;
1109             aSubSO = aStudyBuilder->NewObject(theSObject);
1110             aSubSO = PublishInStudy(theStudy, aSubSO, aSubO, aSubName.ToCString());
1111             // Restore color
1112             aSubO->SetColor(anArgO->GetColor());
1113             // set the texture
1114             if (aSubO->GetShapeType() == GEOM::VERTEX) {
1115               aSubO->SetMarkerStd(anArgO->GetMarkerType(), anArgO->GetMarkerSize());
1116               if (anArgO->GetMarkerType() == GEOM::MT_USER)
1117                 aSubO->SetMarkerTexture(anArgO->GetMarkerTexture());
1118             }
1119           }
1120
1121           if (!CORBA::is_nil(anArgSO)) {
1122             // Restore published sub-shapes of the argument
1123             GEOM::ListOfGO_var aSubParts;
1124             if (theFindMethod == GEOM::FSM_GetInPlaceByHistory)
1125               // pass theObject, because only it has the history
1126               aSubParts = RestoreSubShapesOneLevel(theStudy, anArgSO, aSubSO,
1127                                                    theObject, anOutArgs, theFindMethod, theAddPrefix);
1128             else
1129               aSubParts = RestoreSubShapesOneLevel(theStudy, anArgSO, aSubSO,
1130                                                    aSubO, anOutArgs, theFindMethod, theAddPrefix);
1131             // add to parts list
1132             addToListOfGO( aSubParts, aParts );
1133           }
1134         }
1135         else { // GetInPlace failed, try to build from published parts
1136           if (!CORBA::is_nil(anArgSO)) {
1137             SALOMEDS::SObject_var aSubSO;
1138             if (!CORBA::is_nil(theSObject))
1139               aSubSO = aStudyBuilder->NewObject(theSObject);
1140
1141             // Restore published sub-shapes of the argument
1142             GEOM::ListOfGO_var aSubParts =
1143               RestoreSubShapesOneLevel(theStudy, anArgSO, aSubSO,
1144                                        theObject, anOutArgs, theFindMethod, theAddPrefix);
1145
1146             // add to parts list
1147             addToListOfGO( aSubParts, aParts );
1148
1149             if (aSubParts->length() > 0) {
1150               // remember restored objects for Python Dump
1151               addToListOfGO(anArgO, anOutArgs);
1152
1153               // try to build an argument from a set of its sub-shapes,
1154               // that published and will be reconstructed
1155               if (aSubParts->length() > 1) {
1156                 aSubO = aShapesOp->MakeCompound(aSubParts);
1157                 // add to parts list
1158                 addToListOfGO( aSubO, aParts );
1159               }
1160               else {
1161                 aSubO = aSubParts[0];
1162               }
1163               if (!CORBA::is_nil(aSubO) && !CORBA::is_nil(aSubSO)) {
1164                 // Publish the sub-shape
1165                 TCollection_AsciiString aSubName;
1166                 if (theAddPrefix) {
1167                   aSubName = "from_parts_of_";
1168                 }
1169                 aSubName += anArgName;
1170                 aSubSO = PublishInStudy(theStudy, aSubSO, aSubO, aSubName.ToCString());
1171                 // Restore color
1172                 aSubO->SetColor(anArgO->GetColor());
1173                 // set the texture
1174                 if (aSubO->GetShapeType() == GEOM::VERTEX) {
1175                   aSubO->SetMarkerStd(anArgO->GetMarkerType(), anArgO->GetMarkerSize());
1176                   if (anArgO->GetMarkerType() == GEOM::MT_USER)
1177                     aSubO->SetMarkerTexture(anArgO->GetMarkerTexture());
1178                 }
1179               }
1180             }
1181             else if (!CORBA::is_nil(aSubSO)) {
1182               // remove created aSubSO, because no parts have been found
1183               aStudyBuilder->RemoveObject(aSubSO);
1184             }
1185           }
1186         } // try to build from published parts
1187         anArgSO->UnRegister();
1188       }
1189     } // process arguments
1190   }
1191   std::set<std::string> anObjEntryMap;
1192   GEOM::ListOfGO_var aResParts = new GEOM::ListOfGO;
1193   int nbRes = 0;
1194   int nb = aParts->length();
1195   aResParts->length(nb);
1196   if (nb > 0)
1197   {
1198     Handle(GEOM_Object) aMainObj = _impl->GetObject(theObject->GetStudyID(), theObject->GetEntry());
1199     Handle(GEOM_Function) aFunction = aMainObj->GetLastFunction();
1200     GEOM::TPythonDump pd (aFunction, true);
1201     pd <<"[";
1202     int i = 0, j = 0;
1203     for ( ; i < nb; i++ )
1204     {
1205       GEOM::GEOM_Object_var anObj = GEOM::GEOM_Object::_duplicate( aParts[ i ] );
1206       if (CORBA::is_nil(anObj))
1207         continue;
1208       char* anEntry = anObj->GetEntry();
1209       if (anObjEntryMap.count(anEntry))
1210         continue; // already treated
1211       anObjEntryMap.insert(anEntry);
1212       aResParts[nbRes++] = anObj;
1213       // clear python dump of object
1214       Handle(GEOM_Object) aGeomObj = _impl->GetObject(anObj->GetStudyID(), anEntry);
1215       Handle(GEOM_Function) anObjFun = aGeomObj->GetLastFunction();
1216       if ( !anObjFun.IsNull() )
1217         anObjFun->SetDescription( "" );
1218       if ( j > 0 )
1219         pd << ", ";
1220       pd << aGeomObj;
1221       j++;
1222     }
1223     pd <<"]" << " = geompy.RestoreGivenSubShapes(" << aMainObj << ", " << "[";
1224     //i = 0; nb = theArgs.length(); j = 0;
1225     i = 0; nb = anOutArgs->length(); j = 0;
1226     for ( ; i < nb; i++ )
1227     {
1228       //GEOM::GEOM_Object_var anObj = theArgs[ i ];
1229       GEOM::GEOM_Object_var anObj = anOutArgs[ i ];
1230       if (CORBA::is_nil(anObj))
1231         continue;
1232       Handle(GEOM_Object) aGeomObj = _impl->GetObject(anObj->GetStudyID(), anObj->GetEntry());
1233       if ( j > 0 )
1234         pd << ", ";
1235       pd << aGeomObj;
1236       j++;
1237     }
1238     pd <<"]" << ", " <<"geompy.GEOM.";
1239     switch (theFindMethod) {
1240     case GEOM::FSM_GetInPlace:
1241       pd << "FSM_GetInPlace"; break;
1242     case GEOM::FSM_MultiTransformed:
1243       pd << "FSM_MultiTransformed"; break;
1244     case GEOM::FSM_Transformed:
1245       pd << "FSM_Transformed"; break;
1246     case GEOM::FSM_GetSame:
1247       pd << "FSM_GetSame"; break;
1248     case GEOM::FSM_GetShapesOnShape:
1249       pd << "FSM_GetShapesOnShape"; break;
1250     case GEOM::FSM_GetInPlaceByHistory:
1251     default:
1252       pd << "FSM_GetInPlaceByHistory"; break;
1253     }
1254     pd << ", " << theInheritFirstArg << ", " << theAddPrefix << ")";
1255   }
1256   aResParts->length(nbRes);
1257   return aResParts._retn();
1258 }
1259
1260 //============================================================================
1261 // function : RestoreSubShapesOneLevel
1262 // purpose  : Private method
1263 //============================================================================
1264 GEOM::ListOfGO* GEOM_Gen_i::RestoreSubShapesOneLevel (SALOMEDS::Study_ptr     theStudy,
1265                                                       SALOMEDS::SObject_ptr   theOldSO,
1266                                                       SALOMEDS::SObject_ptr   theNewSO,
1267                                                       GEOM::GEOM_Object_ptr   theNewO,
1268                                                       GEOM::ListOfGO&         theOutArgs,
1269                                                       GEOM::find_shape_method theFindMethod,
1270                                                       CORBA::Boolean          theAddPrefix)
1271 {
1272   int i = 0;
1273   GEOM::ListOfGO_var aParts = new GEOM::ListOfGO;
1274   GEOM::ListOfGO_var aNewParts = new GEOM::ListOfGO;
1275   if (CORBA::is_nil(theStudy) || CORBA::is_nil(theOldSO) ||
1276       CORBA::is_nil(theNewO) /*|| CORBA::is_nil(theNewSO)*/)
1277     return aParts._retn();
1278
1279   SALOMEDS::StudyBuilder_var aStudyBuilder = theStudy->NewBuilder();
1280
1281   // Get interface, containing method, which we will use to reconstruct sub-shapes
1282   GEOM::GEOM_IShapesOperations_var  aShapesOp = GetIShapesOperations(theStudy->StudyId());
1283   GEOM::GEOM_IGroupOperations_var    aGroupOp = GetIGroupOperations(theStudy->StudyId());
1284   GEOM::GEOM_ITransformOperations_var aTrsfOp = GetITransformOperations(theStudy->StudyId());
1285
1286   // Reconstruct published sub-shapes
1287   SALOMEDS::ChildIterator_var it = theStudy->NewChildIterator(theOldSO);
1288
1289   int aLen = 0;
1290   for (it->Init(); it->More(); it->Next()) {
1291     aLen++;
1292   }
1293   aParts->length(aLen);
1294
1295   for (it->Init(); it->More(); it->Next()) {
1296     SALOMEDS::SObject_var anOldSubSO = it->Value();
1297
1298     TCollection_AsciiString anArgName = anOldSubSO->GetName();
1299
1300     SALOMEDS::GenericAttribute_var anAttr;
1301     if (anOldSubSO->FindAttribute(anAttr, "AttributeIOR")) {
1302       SALOMEDS::AttributeIOR_var anAttrIOR = SALOMEDS::AttributeIOR::_narrow(anAttr);
1303       GEOM::GEOM_Object_var anOldSubO =
1304         GEOM::GEOM_Object::_narrow(_orb->string_to_object(anAttrIOR->Value()));
1305       if (!CORBA::is_nil(anOldSubO)) {
1306         // Find a sub-shape of theNewO in place of anOldSubO
1307         GEOM::GEOM_Object_var aNewSubO;
1308         switch (theFindMethod) {
1309         case GEOM::FSM_GetInPlace:
1310           {
1311             // Use GetInPlace
1312             aNewSubO = aShapesOp->GetInPlace(theNewO, anOldSubO);
1313           }
1314           break;
1315         case GEOM::FSM_MultiTransformed:
1316           {
1317             // Only for Multi-transformations
1318             GEOM::GEOM_Object_var anArgOTrsf = aTrsfOp->TransformLikeOtherCopy(anOldSubO, theNewO);
1319             if (!CORBA::is_nil(anArgOTrsf)) {
1320               CORBA::String_var anArgOTrsfEntry = anArgOTrsf->GetEntry();
1321               Handle(GEOM_Object) anArgOTrsfImpl = _impl->GetObject(anArgOTrsf->GetStudyID(), anArgOTrsfEntry);
1322               Handle(GEOM_Function) anArgOTrsfFun = anArgOTrsfImpl->GetLastFunction();
1323               anArgOTrsfFun->SetDescription("");
1324               aNewSubO = aShapesOp->GetInPlace(theNewO, anArgOTrsf);
1325             }
1326           }
1327           break;
1328         case GEOM::FSM_Transformed:
1329           {
1330             // transformation, cannot use GetInPlace, operate with indices
1331             GEOM::ListOfLong_var anIDs = anOldSubO->GetSubShapeIndices();
1332             if (anIDs->length() > 1) {
1333               // group
1334               aNewSubO = aGroupOp->CreateGroup(theNewO, aGroupOp->GetType(anOldSubO));
1335               if (!CORBA::is_nil(aNewSubO))
1336                 aGroupOp->UnionIDs(aNewSubO, anIDs);
1337             }
1338             else {
1339               // single sub-shape
1340               aNewSubO = aShapesOp->GetSubShape(theNewO, anIDs[0]);
1341             }
1342           }
1343           break;
1344         case GEOM::FSM_GetSame:
1345           {
1346             // Use GetSame
1347             aNewSubO = aShapesOp->GetSame(theNewO, anOldSubO);
1348           }
1349           break;
1350         case GEOM::FSM_GetShapesOnShape:
1351           {
1352             // Use GetShapesOnShape. Can work only on solids, so it has sense to search only solids
1353             aNewSubO = aShapesOp->GetShapesOnShapeAsCompound(anOldSubO, theNewO,
1354                                                              (short)GEOM::SOLID, GEOM::ST_ONIN);
1355           }
1356           break;
1357         case GEOM::FSM_GetInPlaceByHistory:
1358           {
1359             // Use GetInPlaceByHistory
1360             aNewSubO = aShapesOp->GetInPlaceByHistory(theNewO, anOldSubO);
1361           }
1362           break;
1363         default:
1364           {}
1365         }
1366
1367         if (!CORBA::is_nil(aNewSubO)) {
1368           // remember restored objects for Python Dump
1369           addToListOfGO(anOldSubO, theOutArgs);
1370
1371           // add the part to the list
1372           aParts[i] = aNewSubO;
1373           i++;
1374           // add to parts list
1375           addToListOfGO( aNewSubO, aNewParts );
1376
1377           SALOMEDS::SObject_var aNewSubSO;
1378           if (!CORBA::is_nil(theNewSO)) {
1379               // Publish the sub-shape
1380             TCollection_AsciiString aSubName;
1381             if (theAddPrefix) {
1382               aSubName = "from_";
1383             }
1384             aSubName += anArgName;
1385             aNewSubSO = aStudyBuilder->NewObject(theNewSO);
1386             aNewSubSO = PublishInStudy(theStudy, aNewSubSO, aNewSubO, aSubName.ToCString());
1387             // Restore color
1388             aNewSubO->SetColor(anOldSubO->GetColor());
1389             // set the texture
1390             if (aNewSubO->GetShapeType() == GEOM::VERTEX) {
1391               aNewSubO->SetMarkerStd(anOldSubO->GetMarkerType(), anOldSubO->GetMarkerSize());
1392               if (anOldSubO->GetMarkerType() == GEOM::MT_USER)
1393                 aNewSubO->SetMarkerTexture(anOldSubO->GetMarkerTexture());
1394             }
1395           }
1396           // Restore published sub-shapes of the argument
1397           GEOM::ListOfGO_var aSubParts;
1398           if (theFindMethod == GEOM::FSM_GetInPlaceByHistory)
1399             // pass the main shape as Object, because only it has the history
1400             aSubParts = RestoreSubShapesOneLevel(theStudy, anOldSubSO, aNewSubSO,
1401                                                  theNewO, theOutArgs, theFindMethod, theAddPrefix);
1402           else
1403             aSubParts = RestoreSubShapesOneLevel(theStudy, anOldSubSO, aNewSubSO,
1404                                                  aNewSubO, theOutArgs, theFindMethod, theAddPrefix);
1405           // add to parts list
1406           addToListOfGO( aSubParts, aNewParts );
1407         }
1408         else { // GetInPlace failed, try to build from published parts
1409           SALOMEDS::SObject_var aNewSubSO;
1410           if (!CORBA::is_nil(theNewSO))
1411             aNewSubSO = aStudyBuilder->NewObject(theNewSO);
1412
1413           // Restore published sub-shapes of the argument
1414           GEOM::ListOfGO_var aSubParts =
1415             RestoreSubShapesOneLevel(theStudy, anOldSubSO, aNewSubSO,
1416                                      theNewO, theOutArgs, theFindMethod, theAddPrefix);
1417           // add to parts list
1418           addToListOfGO( aSubParts, aNewParts );
1419
1420           if (aSubParts->length() > 0) {
1421             // remember restored objects for Python Dump
1422             addToListOfGO(anOldSubO, theOutArgs);
1423
1424             // try to build an object from a set of its sub-shapes,
1425             // that published and will be reconstructed
1426             if (aSubParts->length() > 1) {
1427               aNewSubO = aShapesOp->MakeCompound(aSubParts);
1428               // add to parts list
1429               addToListOfGO( aNewSubO, aNewParts );
1430             }
1431             else {
1432               aNewSubO = aSubParts[0];
1433             }
1434
1435             if (!CORBA::is_nil(aNewSubO)) {
1436               // add the part to the list
1437               aSubParts[i] = aNewSubO;
1438               i++;
1439
1440               // Publish the sub-shape
1441               if (!CORBA::is_nil(aNewSubSO)) {
1442                 TCollection_AsciiString aSubName;
1443                 if (theAddPrefix) {
1444                   aSubName = "from_parts_of_";
1445                 }
1446                 aSubName += anArgName;
1447                 aNewSubSO = PublishInStudy(theStudy, aNewSubSO, aNewSubO, aSubName.ToCString());
1448                 // Restore color
1449                 aNewSubO->SetColor(anOldSubO->GetColor());
1450                 // set the texture
1451                 if (aNewSubO->GetShapeType() == GEOM::VERTEX) {
1452                   aNewSubO->SetMarkerStd(anOldSubO->GetMarkerType(), anOldSubO->GetMarkerSize());
1453                   if (anOldSubO->GetMarkerType() == GEOM::MT_USER)
1454                     aNewSubO->SetMarkerTexture(anOldSubO->GetMarkerTexture());
1455                 }
1456               }
1457             }
1458           }
1459           else if (!CORBA::is_nil(aNewSubSO)) {
1460             // remove created aSubSO, because no parts have been found
1461             aStudyBuilder->RemoveObject(aNewSubSO);
1462           }
1463         } // try to build from published parts
1464       }
1465     }
1466   } // iterate on published sub-shapes
1467
1468   aParts->length(i);
1469   // add to parts list
1470   addToListOfGO( aNewParts, aParts );
1471   return aParts._retn();
1472 }
1473
1474 //============================================================================
1475 // function : RestoreGivenSubShapes
1476 // purpose  : Private method. Works only if both theObject and theSObject
1477 //            are defined, and does not check, if they correspond to each other.
1478 //            List theArgs in this case contains not only operation arguments,
1479 //            but also all subshapes, which must be published.
1480 //============================================================================
1481 GEOM::ListOfGO* GEOM_Gen_i::RestoreGivenSubShapes(SALOMEDS::Study_ptr     theStudy,
1482                                                   GEOM::GEOM_Object_ptr   theObject,
1483                                                   SALOMEDS::SObject_ptr   theSObject,
1484                                                   const GEOM::ListOfGO&   theArgs,
1485                                                   GEOM::find_shape_method theFindMethod,
1486                                                   CORBA::Boolean          theInheritFirstArg,
1487                                                   CORBA::Boolean          theAddPrefix)
1488 {
1489   GEOM::ListOfGO_var aParts = new GEOM::ListOfGO;
1490   //PTv, IMP 0020001, The salome object <theSObject>
1491   //     is not obligatory in case of invokation from script
1492   if (CORBA::is_nil(theStudy) || CORBA::is_nil(theObject) /*|| CORBA::is_nil(theSObject)*/)
1493     return aParts._retn();
1494
1495   // If theArgs list is empty, nothing to do
1496   Standard_Integer aLength = theArgs.length();
1497   if (aLength == 0)
1498     return aParts._retn();
1499
1500   // Get all arguments
1501   GEOM::ListOfGO_var anOpArgsList = theObject->GetDependency();
1502   Standard_Integer nbArgsActual = anOpArgsList->length();
1503
1504   // If anOpArgsList list is empty, nothing to do
1505   if (nbArgsActual == 0)
1506     return aParts._retn();
1507
1508   // Entries of arguments and subshapes
1509   std::set<std::string> anArgs;
1510   for (int i = 0; i < aLength; i++) {
1511     CORBA::String_var anEntry = theArgs[i]->GetEntry();
1512     anArgs.insert(anEntry.in());
1513   }
1514
1515   // Arguments to be published
1516   // We try to publish all arguments, that are in theArgs list
1517   GEOM::ListOfGO_var aList = new GEOM::ListOfGO;
1518   aList->length(nbArgsActual);
1519
1520   int k = 0;
1521   for (int j = 0; j < nbArgsActual; j++) {
1522     CORBA::String_var anEntry = anOpArgsList[j]->GetEntry();
1523     if (anArgs.count(anEntry.in())) {
1524       aList[k] = GEOM::GEOM_Object::_duplicate(anOpArgsList[j]);
1525       k++;
1526     }
1527   }
1528   nbArgsActual = k;
1529   //aList->length(nbArgsActual);
1530
1531   if (nbArgsActual < 1)
1532     return aParts._retn();
1533
1534   if (theInheritFirstArg || (nbArgsActual == 1)) {
1535     // Do not publish argument's reflection,
1536     // but only reconstruct its published sub-shapes
1537
1538     CORBA::String_var anIOR = _orb->object_to_string(aList[0]);
1539     SALOMEDS::SObject_var anArgSO = theStudy->FindObjectIOR(anIOR.in());
1540
1541     aParts = RestoreGivenSubShapesOneLevel(theStudy, anArgSO, theSObject, theObject,
1542                                            anArgs, theFindMethod, theAddPrefix);
1543
1544     // set the color of the transformed shape to the color of initial shape
1545     theObject->SetColor(aList[0]->GetColor());
1546     // set the texture
1547     if (theObject->GetShapeType() == GEOM::VERTEX) {
1548       theObject->SetMarkerStd(aList[0]->GetMarkerType(), aList[0]->GetMarkerSize());
1549       if (aList[0]->GetMarkerType() == GEOM::MT_USER)
1550         theObject->SetMarkerTexture(aList[0]->GetMarkerTexture());
1551     }
1552
1553     anArgSO->UnRegister();
1554   }
1555   else {
1556     // Get interface, containing method, which we will use to reconstruct sub-shapes
1557     GEOM::GEOM_IShapesOperations_var  aShapesOp = GetIShapesOperations(theStudy->StudyId());
1558     GEOM::GEOM_IGroupOperations_var    aGroupOp = GetIGroupOperations(theStudy->StudyId());
1559     GEOM::GEOM_ITransformOperations_var aTrsfOp = GetITransformOperations(theStudy->StudyId());
1560
1561     // Reconstruct arguments and tree of sub-shapes of the arguments
1562     CORBA::String_var anIOR;
1563     SALOMEDS::StudyBuilder_var aStudyBuilder = theStudy->NewBuilder();
1564     for (Standard_Integer i = 0; i < nbArgsActual; i++)
1565     {
1566       GEOM::GEOM_Object_var anArgO = aList[i];
1567       if (!CORBA::is_nil(anArgO)) {
1568         anIOR = _orb->object_to_string(anArgO);
1569         SALOMEDS::SObject_var anArgSO = theStudy->FindObjectIOR(anIOR.in());
1570         TCollection_AsciiString anArgName;
1571         if (CORBA::is_nil(anArgSO)) {
1572           anArgName = "arg_";
1573           anArgName += TCollection_AsciiString(i);
1574         }
1575         else {
1576           anArgName = anArgSO->GetName();
1577         }
1578
1579         // Find a sub-shape of theObject in place of the argument
1580         GEOM::GEOM_Object_var aSubO;
1581         switch (theFindMethod) {
1582         case GEOM::FSM_GetInPlace:
1583           {
1584             // Use GetInPlace
1585             aSubO = aShapesOp->GetInPlace(theObject, anArgO);
1586           }
1587           break;
1588         case GEOM::FSM_MultiTransformed:
1589           {
1590             // Only for Multi-transformations
1591             GEOM::GEOM_Object_var anArgOTrsf = aTrsfOp->TransformLikeOtherCopy(anArgO, theObject);
1592             if (!CORBA::is_nil(anArgOTrsf)) {
1593               CORBA::String_var anArgOTrsfEntry = anArgOTrsf->GetEntry();
1594               Handle(GEOM_Object) anArgOTrsfImpl = _impl->GetObject(anArgOTrsf->GetStudyID(), anArgOTrsfEntry);
1595               Handle(GEOM_Function) anArgOTrsfFun = anArgOTrsfImpl->GetLastFunction();
1596               anArgOTrsfFun->SetDescription("");
1597               aSubO = aShapesOp->GetInPlace(theObject, anArgOTrsf);
1598             }
1599           }
1600           break;
1601         case GEOM::FSM_Transformed:
1602           {
1603             // transformation, cannot use GetInPlace, operate with indices
1604             GEOM::ListOfLong_var anIDs = anArgO->GetSubShapeIndices();
1605             if (anIDs->length() > 1) {
1606               // group
1607               aSubO = aGroupOp->CreateGroup(theObject, aGroupOp->GetType(anArgO));
1608               if (!CORBA::is_nil(aSubO))
1609                 aGroupOp->UnionIDs(aSubO, anIDs);
1610             }
1611             else if (anIDs->length() > 0) {
1612               // single sub-shape
1613               aSubO = aShapesOp->GetSubShape(theObject, anIDs[0]);
1614             }
1615           }
1616           break;
1617         case GEOM::FSM_GetSame:
1618           {
1619             // Use GetSame
1620             aSubO = aShapesOp->GetSame(theObject, anArgO);
1621           }
1622           break;
1623         case GEOM::FSM_GetShapesOnShape:
1624           {
1625             // Use GetShapesOnShape. Can work only on solids, so it has sense to search only solids
1626             aSubO = aShapesOp->GetShapesOnShapeAsCompound(anArgO, theObject,
1627               (short)GEOM::SOLID, GEOM::ST_ONIN);
1628           }
1629           break;
1630         case GEOM::FSM_GetInPlaceByHistory:
1631           {
1632             // Use GetInPlaceByHistory
1633             aSubO = aShapesOp->GetInPlaceByHistory(theObject, anArgO);
1634           }
1635           break;
1636         default:
1637           {}
1638         }
1639
1640         if (!CORBA::is_nil(aSubO)) {
1641           // add to parts list
1642           addToListOfGO( aSubO, aParts );
1643
1644           // Publish the sub-shape
1645           SALOMEDS::SObject_var aSubSO;
1646           if (!CORBA::is_nil(theSObject)) {
1647             TCollection_AsciiString aSubName;
1648             if (theAddPrefix) {
1649               aSubName = "from_";
1650             }
1651             aSubName += anArgName;
1652             aSubSO = aStudyBuilder->NewObject(theSObject);
1653             aSubSO = PublishInStudy(theStudy, aSubSO, aSubO, aSubName.ToCString());
1654             // Restore color
1655             aSubO->SetColor(anArgO->GetColor());
1656             // set the texture
1657             if (aSubO->GetShapeType() == GEOM::VERTEX) {
1658               aSubO->SetMarkerStd(anArgO->GetMarkerType(), anArgO->GetMarkerSize());
1659               if (anArgO->GetMarkerType() == GEOM::MT_USER)
1660                 aSubO->SetMarkerTexture(anArgO->GetMarkerTexture());
1661             }
1662           }
1663
1664           if (!CORBA::is_nil(anArgSO)) {
1665             // Restore published sub-shapes of the argument
1666             GEOM::ListOfGO_var aSubParts;
1667             if (theFindMethod == GEOM::FSM_GetInPlaceByHistory)
1668               // pass theObject, because only it has the history
1669               aSubParts = RestoreGivenSubShapesOneLevel(theStudy, anArgSO, aSubSO,
1670                                                         theObject, anArgs, theFindMethod, theAddPrefix);
1671             else
1672               aSubParts = RestoreGivenSubShapesOneLevel(theStudy, anArgSO, aSubSO,
1673                                                         aSubO, anArgs, theFindMethod, theAddPrefix);
1674             // add to parts list
1675             addToListOfGO( aSubParts, aParts );
1676           }
1677         }
1678         else { // GetInPlace failed, try to build from published parts
1679           if (!CORBA::is_nil(anArgSO)) {
1680             SALOMEDS::SObject_var aSubSO;
1681             if (!CORBA::is_nil(theSObject))
1682               aSubSO = aStudyBuilder->NewObject(theSObject);
1683
1684             // Restore published sub-shapes of the argument
1685             GEOM::ListOfGO_var aSubParts =
1686               RestoreGivenSubShapesOneLevel(theStudy, anArgSO, aSubSO,
1687                                             theObject, anArgs, theFindMethod, theAddPrefix);
1688
1689             // add to parts list
1690             addToListOfGO( aSubParts, aParts );
1691
1692             if (aSubParts->length() > 0) {
1693               // try to build an argument from a set of its sub-shapes,
1694               // that published and will be reconstructed
1695               if (aSubParts->length() > 1) {
1696                 aSubO = aShapesOp->MakeCompound(aSubParts);
1697                 // add to parts list
1698                 addToListOfGO( aSubO, aParts );
1699               }
1700               else {
1701                 aSubO = aSubParts[0];
1702               }
1703               if (!CORBA::is_nil(aSubO) && !CORBA::is_nil(aSubSO)) {
1704                 // Publish the sub-shape
1705                 TCollection_AsciiString aSubName;
1706                 if (theAddPrefix) {
1707                   aSubName = "from_parts_of_";
1708                 }
1709                 aSubName += anArgName;
1710                 aSubSO = PublishInStudy(theStudy, aSubSO, aSubO, aSubName.ToCString());
1711                 // Restore color
1712                 aSubO->SetColor(anArgO->GetColor());
1713                 // set the texture
1714                 if (aSubO->GetShapeType() == GEOM::VERTEX) {
1715                   aSubO->SetMarkerStd(anArgO->GetMarkerType(), anArgO->GetMarkerSize());
1716                   if (anArgO->GetMarkerType() == GEOM::MT_USER)
1717                     aSubO->SetMarkerTexture(anArgO->GetMarkerTexture());
1718                 }
1719               }
1720             }
1721             else if (!CORBA::is_nil(aSubSO)) {
1722               // remove created aSubSO, because no parts have been found
1723               aStudyBuilder->RemoveObject(aSubSO);
1724             }
1725           }
1726         } // try to build from published parts
1727         anArgSO->UnRegister();
1728       }
1729     } // process arguments
1730   }
1731   std::set<std::string> anObjEntryMap;
1732   GEOM::ListOfGO_var aResParts = new GEOM::ListOfGO;
1733   int nbRes = 0;
1734   int nb = aParts->length();
1735   aResParts->length(nb);
1736   if (nb > 0)
1737   {
1738     Handle(GEOM_Object) aMainObj = _impl->GetObject(theObject->GetStudyID(), theObject->GetEntry());
1739     Handle(GEOM_Function) aFunction = aMainObj->GetLastFunction();
1740     GEOM::TPythonDump pd (aFunction, true);
1741     pd <<"[";
1742     int i = 0, j = 0;
1743     for ( ; i < nb; i++ )
1744     {
1745       GEOM::GEOM_Object_var anObj = GEOM::GEOM_Object::_duplicate( aParts[ i ] );
1746       if (CORBA::is_nil(anObj))
1747         continue;
1748       char* anEntry = anObj->GetEntry();
1749       if (anObjEntryMap.count(anEntry))
1750         continue; // already treated
1751       anObjEntryMap.insert(anEntry);
1752       aResParts[nbRes++] = anObj;
1753       // clear python dump of object
1754       Handle(GEOM_Object) aGeomObj = _impl->GetObject(anObj->GetStudyID(), anEntry);
1755       Handle(GEOM_Function) anObjFun = aGeomObj->GetLastFunction();
1756       if ( !anObjFun.IsNull() )
1757         anObjFun->SetDescription( "" );
1758       if ( j > 0 )
1759         pd << ", ";
1760       pd << aGeomObj;
1761       j++;
1762     }
1763     pd <<"]" << " = geompy.RestoreGivenSubShapes(" << aMainObj << ", " << "[";
1764     i = 0; nb = theArgs.length(); j = 0;
1765     for ( ; i < nb; i++ )
1766     {
1767       GEOM::GEOM_Object_var anObj = theArgs[ i ];
1768       if (CORBA::is_nil(anObj))
1769         continue;
1770       Handle(GEOM_Object) aGeomObj = _impl->GetObject(anObj->GetStudyID(), anObj->GetEntry());
1771       if ( j > 0 )
1772         pd << ", ";
1773       pd << aGeomObj;
1774       j++;
1775     }
1776     pd <<"]" << ", " <<"geompy.GEOM.";
1777     switch (theFindMethod) {
1778     case GEOM::FSM_GetInPlace:
1779       pd << "FSM_GetInPlace"; break;
1780     case GEOM::FSM_MultiTransformed:
1781       pd << "FSM_MultiTransformed"; break;
1782     case GEOM::FSM_Transformed:
1783       pd << "FSM_Transformed"; break;
1784     case GEOM::FSM_GetSame:
1785       pd << "FSM_GetSame"; break;
1786     case GEOM::FSM_GetShapesOnShape:
1787       pd << "FSM_GetShapesOnShape"; break;
1788     case GEOM::FSM_GetInPlaceByHistory:
1789     default:
1790       pd << "FSM_GetInPlaceByHistory"; break;
1791     }
1792     pd << ", " << theInheritFirstArg << ", " << theAddPrefix << ")";
1793   }
1794   aResParts->length(nbRes);
1795   return aResParts._retn();
1796 }
1797
1798 //============================================================================
1799 // function : RestoreGivenSubShapesOneLevel
1800 // purpose  : Private method
1801 //============================================================================
1802 GEOM::ListOfGO* GEOM_Gen_i::RestoreGivenSubShapesOneLevel (SALOMEDS::Study_ptr     theStudy,
1803                                                            SALOMEDS::SObject_ptr   theOldSO,
1804                                                            SALOMEDS::SObject_ptr   theNewSO,
1805                                                            GEOM::GEOM_Object_ptr   theNewO,
1806                                                            std::set<std::string>   theArgs,
1807                                                            GEOM::find_shape_method theFindMethod,
1808                                                            CORBA::Boolean          theAddPrefix)
1809 {
1810   int i = 0;
1811   GEOM::ListOfGO_var aParts = new GEOM::ListOfGO;
1812   GEOM::ListOfGO_var aNewParts = new GEOM::ListOfGO;
1813   if (CORBA::is_nil(theStudy) || CORBA::is_nil(theOldSO) ||
1814       CORBA::is_nil(theNewO) /*|| CORBA::is_nil(theNewSO)*/)
1815     return aParts._retn();
1816
1817   SALOMEDS::StudyBuilder_var aStudyBuilder = theStudy->NewBuilder();
1818
1819   // Get interface, containing method, which we will use to reconstruct sub-shapes
1820   GEOM::GEOM_IShapesOperations_var  aShapesOp = GetIShapesOperations(theStudy->StudyId());
1821   GEOM::GEOM_IGroupOperations_var    aGroupOp = GetIGroupOperations(theStudy->StudyId());
1822   GEOM::GEOM_ITransformOperations_var aTrsfOp = GetITransformOperations(theStudy->StudyId());
1823
1824   // Reconstruct published sub-shapes
1825   SALOMEDS::ChildIterator_var it = theStudy->NewChildIterator(theOldSO);
1826
1827   int aLen = 0;
1828   for (it->Init(); it->More(); it->Next()) {
1829     aLen++;
1830   }
1831   aParts->length(aLen);
1832
1833   for (it->Init(); it->More(); it->Next()) {
1834     SALOMEDS::SObject_var anOldSubSO = it->Value();
1835
1836     TCollection_AsciiString anArgName = anOldSubSO->GetName();
1837
1838     SALOMEDS::GenericAttribute_var anAttr;
1839     if (anOldSubSO->FindAttribute(anAttr, "AttributeIOR")) {
1840       SALOMEDS::AttributeIOR_var anAttrIOR = SALOMEDS::AttributeIOR::_narrow(anAttr);
1841       GEOM::GEOM_Object_var anOldSubO =
1842         GEOM::GEOM_Object::_narrow(_orb->string_to_object(anAttrIOR->Value()));
1843
1844       bool okToContinue = false;
1845
1846       if (!CORBA::is_nil(anOldSubO)) {
1847         CORBA::String_var anEntry = anOldSubO->GetEntry();
1848         okToContinue = theArgs.count(anEntry.in());
1849       }
1850
1851       if (okToContinue) {
1852         // Find a sub-shape of theNewO in place of anOldSubO
1853         GEOM::GEOM_Object_var aNewSubO;
1854         switch (theFindMethod) {
1855         case GEOM::FSM_GetInPlace:
1856           {
1857             // Use GetInPlace
1858             aNewSubO = aShapesOp->GetInPlace(theNewO, anOldSubO);
1859           }
1860           break;
1861         case GEOM::FSM_MultiTransformed:
1862           {
1863             // Only for Multi-transformations
1864             GEOM::GEOM_Object_var anArgOTrsf = aTrsfOp->TransformLikeOtherCopy(anOldSubO, theNewO);
1865             if (!CORBA::is_nil(anArgOTrsf)) {
1866               CORBA::String_var anArgOTrsfEntry = anArgOTrsf->GetEntry();
1867               Handle(GEOM_Object) anArgOTrsfImpl = _impl->GetObject(anArgOTrsf->GetStudyID(), anArgOTrsfEntry);
1868               Handle(GEOM_Function) anArgOTrsfFun = anArgOTrsfImpl->GetLastFunction();
1869               anArgOTrsfFun->SetDescription("");
1870               aNewSubO = aShapesOp->GetInPlace(theNewO, anArgOTrsf);
1871             }
1872           }
1873           break;
1874         case GEOM::FSM_Transformed:
1875           {
1876             // transformation, cannot use GetInPlace, operate with indices
1877             GEOM::ListOfLong_var anIDs = anOldSubO->GetSubShapeIndices();
1878             if (anIDs->length() > 1) {
1879               // group
1880               aNewSubO = aGroupOp->CreateGroup(theNewO, aGroupOp->GetType(anOldSubO));
1881               if (!CORBA::is_nil(aNewSubO))
1882                 aGroupOp->UnionIDs(aNewSubO, anIDs);
1883             }
1884             else {
1885               // single sub-shape
1886               aNewSubO = aShapesOp->GetSubShape(theNewO, anIDs[0]);
1887             }
1888           }
1889           break;
1890         case GEOM::FSM_GetSame:
1891           {
1892             // Use GetSame
1893             aNewSubO = aShapesOp->GetSame(theNewO, anOldSubO);
1894           }
1895           break;
1896         case GEOM::FSM_GetShapesOnShape:
1897           {
1898             // Use GetShapesOnShape. Can work only on solids, so it has sense to search only solids
1899             aNewSubO = aShapesOp->GetShapesOnShapeAsCompound(anOldSubO, theNewO,
1900                                                              (short)GEOM::SOLID, GEOM::ST_ONIN);
1901           }
1902           break;
1903         case GEOM::FSM_GetInPlaceByHistory:
1904           {
1905             // Use GetInPlaceByHistory
1906             aNewSubO = aShapesOp->GetInPlaceByHistory(theNewO, anOldSubO);
1907           }
1908           break;
1909         default:
1910           {}
1911         }
1912
1913         if (!CORBA::is_nil(aNewSubO)) {
1914           // add the part to the list
1915           aParts[i] = aNewSubO;
1916           i++;
1917           // add to parts list
1918           addToListOfGO( aNewSubO, aNewParts );
1919
1920           SALOMEDS::SObject_var aNewSubSO;
1921           if (!CORBA::is_nil(theNewSO)) {
1922               // Publish the sub-shape
1923             TCollection_AsciiString aSubName;
1924             if (theAddPrefix) {
1925               aSubName = "from_";
1926             }
1927             aSubName += anArgName;
1928             aNewSubSO = aStudyBuilder->NewObject(theNewSO);
1929             aNewSubSO = PublishInStudy(theStudy, aNewSubSO, aNewSubO, aSubName.ToCString());
1930             // Restore color
1931             aNewSubO->SetColor(anOldSubO->GetColor());
1932             // set the texture
1933             if (aNewSubO->GetShapeType() == GEOM::VERTEX) {
1934               aNewSubO->SetMarkerStd(anOldSubO->GetMarkerType(), anOldSubO->GetMarkerSize());
1935               if (anOldSubO->GetMarkerType() == GEOM::MT_USER)
1936                 aNewSubO->SetMarkerTexture(anOldSubO->GetMarkerTexture());
1937             }
1938           }
1939           // Restore published sub-shapes of the argument
1940           GEOM::ListOfGO_var aSubParts;
1941           if (theFindMethod == GEOM::FSM_GetInPlaceByHistory)
1942             // pass the main shape as Object, because only it has the history
1943             aSubParts = RestoreGivenSubShapesOneLevel(theStudy, anOldSubSO, aNewSubSO,
1944                                                       theNewO, theArgs, theFindMethod, theAddPrefix);
1945           else
1946             aSubParts = RestoreGivenSubShapesOneLevel(theStudy, anOldSubSO, aNewSubSO,
1947                                                       aNewSubO, theArgs, theFindMethod, theAddPrefix);
1948           // add to parts list
1949           addToListOfGO( aSubParts, aNewParts );
1950         }
1951         else { // GetInPlace failed, try to build from published parts
1952           SALOMEDS::SObject_var aNewSubSO;
1953           if (!CORBA::is_nil(theNewSO))
1954             aNewSubSO = aStudyBuilder->NewObject(theNewSO);
1955
1956           // Restore published sub-shapes of the argument
1957           GEOM::ListOfGO_var aSubParts =
1958             RestoreGivenSubShapesOneLevel(theStudy, anOldSubSO, aNewSubSO,
1959                                           theNewO, theArgs, theFindMethod, theAddPrefix);
1960           // add to parts list
1961           addToListOfGO( aSubParts, aNewParts );
1962
1963           if (aSubParts->length() > 0) {
1964             // try to build an object from a set of its sub-shapes,
1965             // that published and will be reconstructed
1966             if (aSubParts->length() > 1) {
1967               aNewSubO = aShapesOp->MakeCompound(aSubParts);
1968               // add to parts list
1969               addToListOfGO( aNewSubO, aNewParts );
1970             }
1971             else {
1972               aNewSubO = aSubParts[0];
1973             }
1974
1975             if (!CORBA::is_nil(aNewSubO)) {
1976               // add the part to the list
1977               aSubParts[i] = aNewSubO;
1978               i++;
1979
1980               // Publish the sub-shape
1981               if (!CORBA::is_nil(aNewSubSO)) {
1982                 TCollection_AsciiString aSubName;
1983                 if (theAddPrefix) {
1984                   aSubName = "from_parts_of_";
1985                 }
1986                 aSubName += anArgName;
1987                 aNewSubSO = PublishInStudy(theStudy, aNewSubSO, aNewSubO, aSubName.ToCString());
1988                 // Restore color
1989                 aNewSubO->SetColor(anOldSubO->GetColor());
1990                 // set the texture
1991                 if (aNewSubO->GetShapeType() == GEOM::VERTEX) {
1992                   aNewSubO->SetMarkerStd(anOldSubO->GetMarkerType(), anOldSubO->GetMarkerSize());
1993                   if (anOldSubO->GetMarkerType() == GEOM::MT_USER)
1994                     aNewSubO->SetMarkerTexture(anOldSubO->GetMarkerTexture());
1995                 }
1996               }
1997             }
1998           }
1999           else if (!CORBA::is_nil(aNewSubSO)) {
2000             // remove created aSubSO, because no parts have been found
2001             aStudyBuilder->RemoveObject(aNewSubSO);
2002           }
2003         } // try to build from published parts
2004       }
2005     }
2006   } // iterate on published sub-shapes
2007
2008   aParts->length(i);
2009   // add to parts list
2010   addToListOfGO( aNewParts, aParts );
2011   return aParts._retn();
2012 }
2013
2014 //============================================================================
2015 // function : register()
2016 // purpose  : register 'name' in 'name_service'
2017 //============================================================================
2018 void GEOM_Gen_i::register_name(char * name)
2019 {
2020   GEOM::GEOM_Gen_var g = _this();
2021   name_service->Register(g, name);
2022 }
2023
2024 //============================================================================
2025 // function : Undo
2026 // purpose  :
2027 //============================================================================
2028 void GEOM_Gen_i::Undo(CORBA::Long theStudyID)
2029 {
2030   _impl->Undo(theStudyID);
2031 }
2032
2033 //============================================================================
2034 // function : Redo
2035 // purpose  :
2036 //============================================================================
2037 void GEOM_Gen_i::Redo(CORBA::Long theStudyID)
2038 {
2039   _impl->Redo(theStudyID);
2040 }
2041
2042 //============================================================================
2043 // function : GetIBasicOperations
2044 // purpose  :
2045 //============================================================================
2046 GEOM::GEOM_IBasicOperations_ptr GEOM_Gen_i::GetIBasicOperations(CORBA::Long theStudyID)
2047      throw ( SALOME::SALOME_Exception )
2048 {
2049   Unexpect aCatch(SALOME_SalomeException);
2050   MESSAGE( "GEOM_Gen_i::GetIBasicOperations" );
2051
2052   GEOM::GEOM_Gen_ptr engine = _this();
2053
2054   //transfer reference on engine
2055   GEOM_IBasicOperations_i* aServant =
2056     new GEOM_IBasicOperations_i(_poa, engine, _impl->GetIBasicOperations(theStudyID));
2057
2058   PortableServer::ObjectId_var id = _poa->activate_object(aServant);
2059   // activate the CORBA servant
2060   GEOM::GEOM_IBasicOperations_var operations = aServant->_this();
2061   return operations._retn();
2062 }
2063
2064 //============================================================================
2065 // function : GetITransformOperations
2066 // purpose  :
2067 //============================================================================
2068 GEOM::GEOM_ITransformOperations_ptr GEOM_Gen_i::GetITransformOperations(CORBA::Long theStudyID)
2069      throw ( SALOME::SALOME_Exception )
2070 {
2071   Unexpect aCatch(SALOME_SalomeException);
2072   MESSAGE( "GEOM_Gen_i::GetITransformOperations" );
2073
2074   GEOM::GEOM_Gen_ptr engine = _this();
2075
2076   GEOM_ITransformOperations_i* aServant =
2077     new GEOM_ITransformOperations_i(_poa, engine, _impl->GetITransformOperations(theStudyID));
2078
2079   // activate the CORBA servant
2080   GEOM::GEOM_ITransformOperations_var operations = aServant->_this();
2081   return operations._retn();
2082 }
2083
2084 //============================================================================
2085 // function : GetI3DPrimOperations
2086 // purpose  :
2087 //============================================================================
2088 GEOM::GEOM_I3DPrimOperations_ptr GEOM_Gen_i::GetI3DPrimOperations(CORBA::Long theStudyID)
2089      throw ( SALOME::SALOME_Exception )
2090 {
2091   Unexpect aCatch(SALOME_SalomeException);
2092   MESSAGE( "GEOM_Gen_i::GetI3DPrimOperations" );
2093
2094   GEOM::GEOM_Gen_ptr engine = _this();
2095
2096   GEOM_I3DPrimOperations_i* aServant =
2097     new GEOM_I3DPrimOperations_i(_poa, engine, _impl->GetI3DPrimOperations(theStudyID));
2098   PortableServer::ObjectId_var id = _poa->activate_object(aServant);
2099
2100   // activate the CORBA servant
2101   GEOM::GEOM_I3DPrimOperations_var operations = aServant->_this();
2102   return operations._retn();
2103 }
2104
2105 //============================================================================
2106 // function : GetIShapesOperations
2107 // purpose  :
2108 //============================================================================
2109 GEOM::GEOM_IShapesOperations_ptr GEOM_Gen_i::GetIShapesOperations(CORBA::Long theStudyID)
2110      throw ( SALOME::SALOME_Exception )
2111 {
2112   Unexpect aCatch(SALOME_SalomeException);
2113   MESSAGE( "GEOM_Gen_i::GetIShapesOperations" );
2114
2115   GEOM::GEOM_Gen_ptr engine = _this();
2116
2117   GEOM_IShapesOperations_i* aServant =
2118     new GEOM_IShapesOperations_i(_poa, engine, _impl->GetIShapesOperations(theStudyID));
2119
2120   // activate the CORBA servant
2121   GEOM::GEOM_IShapesOperations_var operations = aServant->_this();
2122   return operations._retn();
2123 }
2124
2125 //============================================================================
2126 // function : GetIBlocksOperations
2127 // purpose  :
2128 //============================================================================
2129 GEOM::GEOM_IBlocksOperations_ptr GEOM_Gen_i::GetIBlocksOperations(CORBA::Long theStudyID)
2130      throw ( SALOME::SALOME_Exception )
2131 {
2132   Unexpect aCatch(SALOME_SalomeException);
2133   MESSAGE( "GEOM_Gen_i::GetIBlocksOperations" );
2134
2135   GEOM::GEOM_Gen_ptr engine = _this();
2136
2137   GEOM_IBlocksOperations_i* aServant =
2138     new GEOM_IBlocksOperations_i(_poa, engine, _impl->GetIBlocksOperations(theStudyID));
2139
2140   // activate the CORBA servant
2141   GEOM::GEOM_IBlocksOperations_var operations = aServant->_this();
2142   return operations._retn();
2143 }
2144
2145 //============================================================================
2146 // function : GetIBooleanOperations
2147 // purpose  :
2148 //============================================================================
2149 GEOM::GEOM_IBooleanOperations_ptr GEOM_Gen_i::GetIBooleanOperations(CORBA::Long theStudyID)
2150      throw ( SALOME::SALOME_Exception )
2151 {
2152   Unexpect aCatch(SALOME_SalomeException);
2153   MESSAGE( "GEOM_Gen_i::GetIBooleanOperations" );
2154
2155   GEOM::GEOM_Gen_ptr engine = _this();
2156
2157   GEOM_IBooleanOperations_i* aServant =
2158     new GEOM_IBooleanOperations_i(_poa, engine, _impl->GetIBooleanOperations(theStudyID));
2159
2160   // activate the CORBA servant
2161   GEOM::GEOM_IBooleanOperations_var operations = aServant->_this();
2162   return operations._retn();
2163 }
2164
2165 //============================================================================
2166 // function : GetICurvesOperations
2167 // purpose  :
2168 //============================================================================
2169 GEOM::GEOM_ICurvesOperations_ptr GEOM_Gen_i::GetICurvesOperations(CORBA::Long theStudyID)
2170      throw ( SALOME::SALOME_Exception )
2171 {
2172   Unexpect aCatch(SALOME_SalomeException);
2173   MESSAGE( "GEOM_Gen_i::GetICurvesOperations" );
2174
2175   GEOM::GEOM_Gen_ptr engine = _this();
2176
2177   GEOM_ICurvesOperations_i* aServant =
2178     new GEOM_ICurvesOperations_i(_poa, engine, _impl->GetICurvesOperations(theStudyID));
2179
2180   // activate the CORBA servant
2181   GEOM::GEOM_ICurvesOperations_var operations = aServant->_this();
2182   return operations._retn();
2183 }
2184
2185 //============================================================================
2186 // function : GetILocalOperations
2187 // purpose  :
2188 //============================================================================
2189 GEOM::GEOM_ILocalOperations_ptr GEOM_Gen_i::GetILocalOperations(CORBA::Long theStudyID)
2190      throw ( SALOME::SALOME_Exception )
2191 {
2192   Unexpect aCatch(SALOME_SalomeException);
2193   MESSAGE( "GEOM_Gen_i::GetILocalOperations" );
2194
2195   GEOM::GEOM_Gen_ptr engine = _this();
2196
2197   GEOM_ILocalOperations_i* aServant =
2198     new GEOM_ILocalOperations_i(_poa, engine, _impl->GetILocalOperations(theStudyID));
2199
2200   // activate the CORBA servant
2201   GEOM::GEOM_ILocalOperations_var operations = aServant->_this();
2202   return operations._retn();
2203 }
2204
2205 //============================================================================
2206 // function : GetIHealingOperations
2207 // purpose  :
2208 //============================================================================
2209 GEOM::GEOM_IHealingOperations_ptr GEOM_Gen_i::GetIHealingOperations(CORBA::Long theStudyID)
2210      throw ( SALOME::SALOME_Exception )
2211 {
2212   Unexpect aCatch(SALOME_SalomeException);
2213   MESSAGE( "GEOM_Gen_i::IHealingOperations" );
2214
2215   GEOM::GEOM_Gen_ptr engine = _this();
2216
2217   GEOM_IHealingOperations_i* aServant =
2218     new GEOM_IHealingOperations_i(_poa, engine, _impl->GetIHealingOperations(theStudyID));
2219
2220   // activate the CORBA servant
2221   GEOM::GEOM_IHealingOperations_var operations = aServant->_this();
2222   return operations._retn();
2223 }
2224
2225 //============================================================================
2226 // function : GetIInsertOperations
2227 // purpose  :
2228 //============================================================================
2229 GEOM::GEOM_IInsertOperations_ptr GEOM_Gen_i::GetIInsertOperations(CORBA::Long theStudyID)
2230      throw ( SALOME::SALOME_Exception )
2231 {
2232   Unexpect aCatch(SALOME_SalomeException);
2233   MESSAGE( "GEOM_Gen_i::GetIInsertOperations" );
2234
2235   GEOM::GEOM_Gen_ptr engine = _this();
2236
2237   GEOM_IInsertOperations_i* aServant =
2238     new GEOM_IInsertOperations_i(_poa, engine, _impl->GetIInsertOperations(theStudyID));
2239
2240   // activate the CORBA servant
2241   GEOM::GEOM_IInsertOperations_var operations = aServant->_this();
2242   return operations._retn();
2243 }
2244
2245 //============================================================================
2246 // function : GetIMeasureOperations
2247 // purpose  :
2248 //============================================================================
2249 GEOM::GEOM_IMeasureOperations_ptr GEOM_Gen_i::GetIMeasureOperations(CORBA::Long theStudyID)
2250      throw ( SALOME::SALOME_Exception )
2251 {
2252   Unexpect aCatch(SALOME_SalomeException);
2253   MESSAGE( "GEOM_Gen_i::GetIMeasureOperations" );
2254
2255   GEOM::GEOM_Gen_ptr engine = _this();
2256
2257   GEOM_IMeasureOperations_i* aServant =
2258     new GEOM_IMeasureOperations_i(_poa, engine, _impl->GetIMeasureOperations(theStudyID));
2259
2260   // activate the CORBA servant
2261   GEOM::GEOM_IMeasureOperations_var operations = aServant->_this();
2262   return operations._retn();
2263 }
2264
2265 //============================================================================
2266 // function : GetIGroupOperations
2267 // purpose  :
2268 //============================================================================
2269 GEOM::GEOM_IGroupOperations_ptr GEOM_Gen_i::GetIGroupOperations(CORBA::Long theStudyID)
2270      throw ( SALOME::SALOME_Exception )
2271 {
2272   Unexpect aCatch(SALOME_SalomeException);
2273   MESSAGE( "GEOM_Gen_i::GetIGroupOperations" );
2274
2275   GEOM::GEOM_Gen_ptr engine = _this();
2276
2277   GEOM_IGroupOperations_i* aServant =
2278     new GEOM_IGroupOperations_i(_poa, engine, _impl->GetIGroupOperations(theStudyID));
2279
2280   // activate the CORBA servant
2281   GEOM::GEOM_IGroupOperations_var operations = aServant->_this();
2282   return operations._retn();
2283 }
2284
2285 //============================================================================
2286 // function : GetIAdvancedOperations
2287 // purpose  :
2288 //============================================================================
2289 GEOM::GEOM_IAdvancedOperations_ptr GEOM_Gen_i::GetIAdvancedOperations(CORBA::Long theStudyID)
2290      throw ( SALOME::SALOME_Exception )
2291 {
2292   Unexpect aCatch(SALOME_SalomeException);
2293   MESSAGE( "GEOM_Gen_i::GetIAdvancedOperations" );
2294
2295   GEOM::GEOM_Gen_ptr engine = _this();
2296
2297   GEOM_IAdvancedOperations_i* aServant =
2298     new GEOM_IAdvancedOperations_i(_poa, engine, _impl->GetIAdvancedOperations(theStudyID));
2299
2300   // activate the CORBA servant
2301   GEOM::GEOM_IAdvancedOperations_var operations = aServant->_this();
2302   return operations._retn();
2303 }
2304
2305 //=============================================================================
2306 /*!
2307  *  AddSubShape
2308  */
2309 //=============================================================================
2310 GEOM::GEOM_Object_ptr GEOM_Gen_i::AddSubShape (GEOM::GEOM_Object_ptr theMainShape,
2311                                                const GEOM::ListOfLong& theIndices)
2312 {
2313   if (CORBA::is_nil(theMainShape) || theIndices.length() < 1)
2314     return GEOM::GEOM_Object::_nil();
2315   CORBA::String_var entry = theMainShape->GetEntry();
2316   Handle(GEOM_Object) aMainShape = _impl->GetObject(theMainShape->GetStudyID(), entry);
2317   if (aMainShape.IsNull()) return GEOM::GEOM_Object::_nil();
2318
2319   Handle(TColStd_HArray1OfInteger) anArray = new TColStd_HArray1OfInteger(1, theIndices.length());
2320   for(Standard_Integer i = 0; i<theIndices.length(); i++) anArray->SetValue(i+1, theIndices[i]);
2321
2322   Handle(GEOM_Object) anObject = _impl->AddSubShape(aMainShape, anArray, true);
2323   if(anObject.IsNull()) return GEOM::GEOM_Object::_nil();
2324
2325   TCollection_AsciiString anEntry;
2326   TDF_Tool::Entry(anObject->GetEntry(), anEntry);
2327   return GetObject(anObject->GetDocID(), anEntry.ToCString());
2328 }
2329
2330 //=============================================================================
2331 /*!
2332  *  RemoveObject
2333  */
2334 //=============================================================================
2335 void GEOM_Gen_i::RemoveObject(GEOM::GEOM_Object_ptr theObject)
2336 {
2337   CORBA::String_var anEntry = theObject->GetEntry();
2338   Handle(GEOM_Object) anObject = _impl->GetObject(theObject->GetStudyID(), anEntry, false);
2339   if (anObject.IsNull()) return;
2340   _impl->RemoveObject(anObject);
2341   return;
2342 }
2343
2344
2345 //=================================================================================
2346 // function : GetStringFromIOR()
2347 // purpose  : returns a string that represents  a 'GEOM::GEOM_Object_var'
2348 //=================================================================================
2349 char* GEOM_Gen_i::GetStringFromIOR(GEOM::GEOM_Object_ptr theObject) {
2350   return _orb->object_to_string(theObject);
2351 }
2352
2353
2354 //=================================================================================
2355 // function : GetIORFromString()
2356 // purpose  : returns a 'GEOM::GEOM_Object_var' from a string representing it
2357 //=================================================================================
2358 GEOM::GEOM_Object_ptr GEOM_Gen_i::GetIORFromString(const char* stringIOR) {
2359   GEOM::GEOM_Object_var aGeomObject;
2360   if(strcmp(stringIOR,"") != 0){
2361     CORBA::Object_var anObject = _orb->string_to_object(stringIOR);
2362     if(!CORBA::is_nil(anObject))
2363       aGeomObject =  GEOM::GEOM_Object::_narrow(anObject.in());
2364   }
2365   return aGeomObject._retn();
2366 }
2367
2368 //=================================================================================
2369 // function : GetObject()
2370 // purpose  :
2371 //=================================================================================
2372 GEOM::GEOM_Object_ptr GEOM_Gen_i::GetObject (CORBA::Long theStudyID, const char* theEntry)
2373 {
2374   GEOM::GEOM_Object_var obj;
2375   Handle(GEOM_Object) handle_object = _impl->GetObject(theStudyID, (char*)theEntry);
2376   if (handle_object.IsNull()) return obj._retn();
2377
2378   TCollection_AsciiString stringIOR = handle_object->GetIOR();
2379   if (stringIOR.Length() > 1) {
2380     CORBA::Object_var corba_object = _orb->string_to_object(stringIOR.ToCString());
2381     if (!CORBA::is_nil(corba_object)) obj = GEOM::GEOM_Object::_narrow(corba_object);
2382     return obj._retn();
2383   }
2384
2385   GEOM::GEOM_Gen_ptr engine = _this();
2386   //transfer the reference to GEOM_Object_i
2387   GEOM_Object_i* servant = new GEOM_Object_i (_poa, engine, handle_object);
2388   PortableServer::ObjectId_var id = _poa->activate_object(servant);
2389
2390   obj = servant->_this();
2391   CORBA::String_var objStr = _orb->object_to_string(obj);
2392   TCollection_AsciiString anAscii( (char *)objStr.in() );
2393   handle_object->SetIOR( anAscii );
2394   return obj._retn();
2395 }
2396
2397 //=================================================================================
2398 // function : hasObjectInfo()
2399 // purpose  : shows if module provides information for its objects
2400 //=================================================================================
2401 bool GEOM_Gen_i::hasObjectInfo()
2402 {
2403   return true;
2404 }
2405
2406 //=================================================================================
2407 // function : getObjectInfo()
2408 // purpose  : returns an information for a given object by its entry
2409 //=================================================================================
2410 char* GEOM_Gen_i::getObjectInfo(CORBA::Long studyId, const char* entry)
2411 {
2412   GEOM::GEOM_Object_var aGeomObject;
2413
2414   CORBA::Object_var aSMObject = name_service->Resolve( "/myStudyManager" );
2415   SALOMEDS::StudyManager_var aStudyManager = SALOMEDS::StudyManager::_narrow( aSMObject );
2416   SALOMEDS::Study_var aStudy = aStudyManager->GetStudyByID( studyId );
2417   SALOMEDS::SObject_var aSObj = aStudy->FindObjectID( entry );
2418   SALOMEDS::SObject_var aResultSObj;
2419   if (aSObj->ReferencedObject(aResultSObj))
2420     aSObj = aResultSObj;
2421
2422   SALOMEDS::GenericAttribute_var anAttr;
2423   if (!aSObj->_is_nil() && aSObj->FindAttribute(anAttr, "AttributeIOR")) {
2424     SALOMEDS::AttributeIOR_var anIOR = SALOMEDS::AttributeIOR::_narrow(anAttr);
2425     CORBA::String_var aVal = anIOR->Value();
2426     anIOR->UnRegister();
2427     CORBA::Object_var anObject = aStudy->ConvertIORToObject(aVal);
2428     aGeomObject = GEOM::GEOM_Object::_narrow(anObject);
2429   }
2430   if (!aSObj->_is_nil() )
2431     aSObj->UnRegister();
2432
2433   const char* aTypeInfo = "Object";
2434   if ( !aGeomObject->_is_nil() ) {
2435     GEOM::GEOM_IKindOfShape::shape_kind aKind;
2436     GEOM::ListOfLong_var anInts;
2437     GEOM::ListOfDouble_var aDbls;
2438
2439     GEOM::GEOM_IMeasureOperations_var anOp = GetIMeasureOperations( studyId );
2440     aKind = anOp->KindOfShape( aGeomObject, anInts, aDbls );
2441
2442     if ( anOp->IsDone() ) {
2443       switch ( aKind ) {
2444       case GEOM::GEOM_IKindOfShape::COMPOUND:
2445         aTypeInfo = "Compound";
2446         break;
2447       case GEOM::GEOM_IKindOfShape::COMPSOLID:
2448         aTypeInfo = "CompSolid";
2449         break;
2450       case GEOM::GEOM_IKindOfShape::SHELL:
2451         aTypeInfo = "Shell";
2452         break;
2453       case GEOM::GEOM_IKindOfShape::WIRE:
2454         if ( anInts[0] == 1 )
2455           aTypeInfo = "Closed Wire";
2456         else if ( anInts[0] == 2 )
2457           aTypeInfo = "Opened Wire";
2458         else
2459           aTypeInfo = "Wire";
2460         break;
2461         // SOLIDs
2462       case GEOM::GEOM_IKindOfShape::SPHERE:
2463         aTypeInfo = "Sphere";
2464         break;
2465       case GEOM::GEOM_IKindOfShape::CYLINDER:
2466         aTypeInfo = "Cylinder";
2467         break;
2468       case GEOM::GEOM_IKindOfShape::BOX:
2469       case GEOM::GEOM_IKindOfShape::ROTATED_BOX:
2470         aTypeInfo = "Box";
2471         break;
2472       case GEOM::GEOM_IKindOfShape::TORUS:
2473         aTypeInfo = "Torus";
2474         break;
2475       case GEOM::GEOM_IKindOfShape::CONE:
2476         aTypeInfo = "Cone";
2477         break;
2478       case GEOM::GEOM_IKindOfShape::POLYHEDRON:
2479         aTypeInfo = "Polyhedron";
2480         break;
2481       case GEOM::GEOM_IKindOfShape::SOLID:
2482         aTypeInfo = "Solid";
2483         break;
2484         // FACEs
2485       case GEOM::GEOM_IKindOfShape::SPHERE2D:
2486         aTypeInfo = "Spherical Face";
2487         break;
2488       case GEOM::GEOM_IKindOfShape::CYLINDER2D:
2489         aTypeInfo = "Cylindrical Face";
2490         break;
2491       case GEOM::GEOM_IKindOfShape::TORUS2D:
2492         aTypeInfo = "Toroidal Face";
2493         break;
2494       case GEOM::GEOM_IKindOfShape::CONE2D:
2495         aTypeInfo = "Conical Face";
2496         break;
2497       case GEOM::GEOM_IKindOfShape::DISK_CIRCLE:
2498         aTypeInfo = "Disk";
2499         break;
2500       case GEOM::GEOM_IKindOfShape::DISK_ELLIPSE:
2501         aTypeInfo = "Elliptical Face";
2502         break;
2503       case GEOM::GEOM_IKindOfShape::POLYGON:
2504         aTypeInfo = "Polygon";
2505         break;
2506       case GEOM::GEOM_IKindOfShape::PLANE:
2507         aTypeInfo = "Plane";
2508         break;
2509       case GEOM::GEOM_IKindOfShape::PLANAR:
2510         aTypeInfo = "Planar Face";
2511         break;
2512       case GEOM::GEOM_IKindOfShape::FACE:
2513         aTypeInfo = "Face";
2514         break;
2515         // EDGEs
2516       case GEOM::GEOM_IKindOfShape::CIRCLE:
2517         aTypeInfo = "Circle";
2518         break;
2519       case GEOM::GEOM_IKindOfShape::ARC_CIRCLE:
2520         aTypeInfo = "Arc Circle";
2521         break;
2522       case GEOM::GEOM_IKindOfShape::ELLIPSE:
2523         aTypeInfo = "Ellipse";
2524         break;
2525       case GEOM::GEOM_IKindOfShape::ARC_ELLIPSE:
2526         aTypeInfo = "Arc Ellipse";
2527         break;
2528       case GEOM::GEOM_IKindOfShape::LINE:
2529         aTypeInfo = "Line";
2530         break;
2531       case GEOM::GEOM_IKindOfShape::SEGMENT:
2532         aTypeInfo = "Segment";
2533         break;
2534       case GEOM::GEOM_IKindOfShape::EDGE:
2535         aTypeInfo = "Edge";
2536         break;
2537       case GEOM::GEOM_IKindOfShape::VERTEX:
2538         aTypeInfo = "Vertex";
2539         break;
2540       default:
2541         break;
2542       }
2543     }
2544   }
2545
2546   char* anInfo = new char[strlen("Module ") + strlen(ComponentDataType()) + strlen(", ") + strlen(aTypeInfo) + 3];
2547   sprintf(anInfo, "Module %s, %s", ComponentDataType(), aTypeInfo);
2548
2549   char* ret = CORBA::string_dup(anInfo);
2550   delete [] anInfo;
2551   return ret;
2552 }
2553
2554 //=====================================================================================
2555 // EXPORTED METHODS
2556 //=====================================================================================
2557 extern "C"
2558 {
2559   /*
2560   GEOM_I_EXPORT
2561   PortableServer::ObjectId* GEOMEngine_factory(CORBA::ORB*, PortableServer::POA*, PortableServer::ObjectId*, const char*, const char*);
2562   */
2563
2564   GEOM_I_EXPORT
2565   PortableServer::ObjectId* GEOMEngine_factory(CORBA::ORB_ptr            orb,
2566                                                PortableServer::POA_ptr   poa,
2567                                                PortableServer::ObjectId* contId,
2568                                                const char*               instanceName,
2569                                                const char*               interfaceName)
2570   {
2571     GEOM_Gen_i* myGEOM_Gen_i = new GEOM_Gen_i(orb, poa, contId, instanceName, interfaceName);
2572     return myGEOM_Gen_i->getId();
2573   }
2574 }