Salome HOME
a012c220b7b1684696323245c100912c615adae8
[modules/geom.git] / src / GEOMGUI / GEOM_Displayer.cxx
1 // Copyright (C) 2007-2014  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, or (at your option) any later version.
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 // GEOM GEOMGUI : GUI for Geometry component
24 // File   : GEOM_Displayer.cxx
25 // Author : Vadim SANDLER, Open CASCADE S.A.S. (vadim.sandler@opencascade.com)
26
27 #include "GEOM_Displayer.h"
28 #include "GEOMGUI_DimensionProperty.h"
29 #include "GeometryGUI.h"
30
31 #include <GEOM_Constants.h>
32 #include <GEOM_TypeFilter.h>
33 #include <GEOM_EdgeFilter.h>
34 #include <GEOM_FaceFilter.h>
35 #include <GEOM_CompoundFilter.h>
36 #include <GEOM_PreviewFilter.h>
37 #include <GEOM_LogicalFilter.h>
38 #include <GEOM_OCCFilter.h>
39
40 #include <GEOM_Actor.h>
41 #include <GEOM_AISShape.hxx>
42 #include <GEOM_AISDimension.hxx>
43 #include <GEOM_TopWireframeShape.hxx>
44 #include <GEOM_AISVector.hxx>
45 #include <GEOM_AISTrihedron.hxx>
46 #include <GEOM_VTKTrihedron.hxx>
47 #include <GEOM_VTKPropertyMaterial.hxx>
48
49 #include <GEOMUtils.hxx>
50
51 #include <Material_Model.h>
52
53 #include <SUIT_Desktop.h>
54 #include <SUIT_ViewWindow.h>
55 #include <SUIT_Session.h>
56 #include <SUIT_ViewManager.h>
57 #include <SUIT_ResourceMgr.h>
58
59 #include <Basics_OCCTVersion.hxx>
60
61 #include <SalomeApp_Study.h>
62 #include <SalomeApp_Application.h>
63 #include <LightApp_SelectionMgr.h>
64 #include <LightApp_DataObject.h>
65 #include <SalomeApp_TypeFilter.h>
66 #include <SalomeApp_Tools.h>
67
68 #include <SALOME_ListIteratorOfListIO.hxx>
69 #include <SALOME_ListIO.hxx>
70 #include <SALOME_Prs.h>
71
72 #include <SOCC_Prs.h>
73 #include <SOCC_ViewModel.h>
74
75 #include <SVTK_Prs.h>
76 #include <SVTK_ViewModel.h>
77
78 #include <OCCViewer_ViewWindow.h>
79 #include <OCCViewer_ViewPort3d.h>
80
81 // OCCT Includes
82 #include <AIS_Drawer.hxx>
83 #include <AIS_Dimension.hxx>
84 #include <AIS_LengthDimension.hxx>
85 #include <AIS_DiameterDimension.hxx>
86 #include <AIS_AngleDimension.hxx>
87 #include <AIS_ListIteratorOfListOfInteractive.hxx>
88 #include <Aspect_PolygonOffsetMode.hxx>
89 #include <Aspect_ColorScale.hxx>
90 #include <Prs3d_IsoAspect.hxx>
91 #include <Prs3d_PointAspect.hxx>
92 #include <StdSelect_TypeOfEdge.hxx>
93 #include <StdSelect_TypeOfFace.hxx>
94 #include <StdSelect_DisplayMode.hxx>
95 #include <TopoDS_Face.hxx>
96 #include <BRep_Tool.hxx>
97 #include <Geom_Plane.hxx>
98 #include <Geom_Axis2Placement.hxx>
99 #include <Graphic3d_AspectFillArea3d.hxx>
100 #include <gp_Pln.hxx>
101 #include <TColStd_MapOfInteger.hxx>
102 #include <TColStd_MapIteratorOfMapOfInteger.hxx>
103 #include <TopoDS_Iterator.hxx>
104 #include <Graphic3d_AspectMarker3d.hxx>
105 #include <TopTools_MapOfShape.hxx>
106 #include <TopTools_ListOfShape.hxx>
107 #include <TopTools_ListIteratorOfListOfShape.hxx>
108 #include <TopoDS.hxx>
109 #include <NCollection_DataMap.hxx>
110 #include <NCollection_Map.hxx>
111
112 #include <Prs3d_ShadingAspect.hxx>
113
114 #include <BRepMesh_IncrementalMesh.hxx>
115
116 // VTK Includes
117 #include <vtkActorCollection.h>
118 #include <vtkProperty.h>
119
120 // CORBA Headers
121 #include CORBA_CLIENT_HEADER(SALOMEDS_Attributes)
122
123 #include <GEOMImpl_Types.hxx>
124
125 #if OCC_VERSION_LARGE > 0x06040000 // Porting to OCCT6.5.1
126 #include <TColStd_HArray1OfByte.hxx>
127 #else
128 #include <Graphic3d_HArray1OfBytes.hxx>
129 #endif
130
131 // If the next macro is defined, autocolor feature works for all sub-shapes;
132 // if it is undefined, autocolor feature works for groups only
133 #define GENERAL_AUTOCOLOR
134 // Below macro, when uncommented, switches on simplified (more performant) algorithm
135 // of auto-color picking up
136 #define SIMPLE_AUTOCOLOR
137
138 // Hard-coded value of shape deflection coefficient for VTK viewer
139 const double VTK_MIN_DEFLECTION = 0.001;
140
141 #if OCC_VERSION_LARGE > 0x06070000
142 // Pixmap caching support
143 namespace
144 {
145   typedef NCollection_Map<Handle(GEOM_AISShape)>                    SetOfAISShapes;
146   typedef NCollection_DataMap<Handle(Image_PixMap), SetOfAISShapes> PixmapUsageMap;
147   typedef QMap<QString, Handle(Image_PixMap)>                       PixmapCacheMap;
148
149   static inline PixmapUsageMap& getPixmapUsageMap()
150   {
151     static PixmapUsageMap aMap;
152     return aMap;
153   }
154
155   static inline PixmapCacheMap& getPixmapCacheMap()
156   {
157     static PixmapCacheMap aMap;
158     return aMap;
159   }
160
161   //===========================================================================
162   // Function : imageToPixmap
163   // Purpose  : Concert QImage to OCCT pixmap
164   //===========================================================================
165   static inline Handle(Image_PixMap) imageToPixmap( const QImage& anImage )
166   { 
167     Handle(Image_PixMap) aPixmap = new Image_PixMap();
168     if ( !anImage.isNull() ) {
169       aPixmap->InitTrash( Image_PixMap::ImgBGRA, anImage.width(), anImage.height() );
170       aPixmap->SetTopDown( Standard_True );
171       
172       const uchar* aImageBytes = anImage.bits();
173       
174       for ( int aLine = anImage.height() - 1; aLine >= 0; --aLine ) {
175 #if OCC_VERSION_LARGE > 0x06070100
176         // convert pixels from ARGB to renderer-compatible RGBA
177         for ( int aByte = 0; aByte < anImage.width(); ++aByte ) {
178           Image_ColorBGRA& aPixmapBytes = aPixmap->ChangeValue<Image_ColorBGRA>(aLine, aByte);
179         
180           aPixmapBytes.b() = (Standard_Byte) *aImageBytes++;
181           aPixmapBytes.g() = (Standard_Byte) *aImageBytes++;
182           aPixmapBytes.r() = (Standard_Byte) *aImageBytes++;
183           aPixmapBytes.a() = (Standard_Byte) *aImageBytes++;
184         }
185 #else
186         Image_ColorBGRA* aPixmapBytes = aPixmap->EditData<Image_ColorBGRA>().ChangeRow(aLine);
187         
188         // convert pixels from ARGB to renderer-compatible RGBA
189         for ( int aByte = 0; aByte < anImage.width(); ++aByte ) {
190           aPixmapBytes->b() = (Standard_Byte) *aImageBytes++;
191           aPixmapBytes->g() = (Standard_Byte) *aImageBytes++;
192           aPixmapBytes->r() = (Standard_Byte) *aImageBytes++;
193           aPixmapBytes->a() = (Standard_Byte) *aImageBytes++;
194           aPixmapBytes++;
195         }
196 #endif
197       }
198     }
199     return aPixmap;
200   }
201   
202   //===========================================================================
203   // Function : getDefaultTexture
204   // Purpose  : Get default texture
205   //===========================================================================
206   static inline Handle(Image_PixMap) getDefaultTexture()
207   {
208     static Handle(Image_PixMap) aPixmap;
209     if ( aPixmap.IsNull() ) {
210       QPixmap px(":images/default_texture.png");
211       if ( !px.isNull() )
212         aPixmap = imageToPixmap( px.toImage() );
213     }
214     return aPixmap;
215   }
216
217   //===========================================================================
218   // Function : cacheTextureFor
219   // Purpose  : Load and cache image for the specified presentation.
220   //===========================================================================
221   static inline Handle(Image_PixMap) cacheTextureFor( const QString& thePath,
222                                                       const Handle(GEOM_AISShape)& theShape )
223   {
224     if ( thePath.isEmpty() )
225       return NULL;
226
227     PixmapUsageMap& aPixmapUsersMap = getPixmapUsageMap();
228     PixmapCacheMap& aPixmapCacheMap = getPixmapCacheMap();
229
230     Handle(Image_PixMap) aPixmap = aPixmapCacheMap.value( thePath, NULL );
231     if ( !aPixmap.IsNull() ) {
232       // point that the texture is used by the presentation
233       if ( !aPixmapUsersMap.IsBound( aPixmap ) )
234         aPixmapUsersMap.Bind( aPixmap, SetOfAISShapes() );
235
236       aPixmapUsersMap.ChangeFind( aPixmap ).Add( theShape );
237
238       return aPixmap;
239     }
240
241     // convert texture to compatible image format
242     QImage anImage = QImage( thePath ).convertToFormat( QImage::Format_ARGB32 );
243     if ( anImage.isNull() )
244       return NULL;
245
246     aPixmap = imageToPixmap( anImage );
247
248     aPixmapCacheMap.insert( thePath, aPixmap );
249
250     if ( !aPixmapUsersMap.IsBound( aPixmap ) )
251       aPixmapUsersMap.Bind( aPixmap, SetOfAISShapes() );
252
253     aPixmapUsersMap.ChangeFind( aPixmap ).Add( theShape );
254
255     return aPixmap;
256   }
257
258   //===========================================================================
259   // Function : releaseTextures
260   // Purpose  : Releases cached textures found for the specified presentation.
261   //===========================================================================
262   static inline void releaseTextures( const SALOME_OCCPrs* thePrs )
263   {
264     const SOCC_Prs* anOccPrs = dynamic_cast<const SOCC_Prs*>( thePrs );
265
266     AIS_ListOfInteractive aListOfIO;
267
268     anOccPrs->GetObjects( aListOfIO );
269
270     AIS_ListIteratorOfListOfInteractive aIterateIO( aListOfIO );
271
272     PixmapUsageMap& aPixmapUsersMap = getPixmapUsageMap();
273     PixmapCacheMap& aPixmapCacheMap = getPixmapCacheMap();
274
275     for ( ; aIterateIO.More(); aIterateIO.Next() )
276     {
277       Handle(GEOM_AISShape) aAISShape =
278         Handle(GEOM_AISShape)::DownCast( aIterateIO.Value() );
279
280       if ( aAISShape.IsNull() )
281         continue;
282
283       const Handle(Image_PixMap)& aPixmap = aAISShape->TexturePixMap();
284       if ( aPixmap.IsNull() )
285         continue;
286
287       if ( !aPixmapUsersMap.IsBound( aPixmap ) )
288         continue;
289
290       SetOfAISShapes& aUsersShapes = aPixmapUsersMap.ChangeFind( aPixmap );
291
292       aUsersShapes.Remove( aAISShape );
293
294       if ( aUsersShapes.IsEmpty() ) {
295         aPixmapUsersMap.UnBind( aPixmap );
296         aPixmapCacheMap.remove( aPixmapCacheMap.key( aPixmap ) );
297       }
298     }
299   }
300 }
301 #endif
302
303 //================================================================
304 // Function : getActiveStudy
305 // Purpose  : Get active study, returns 0 if no open study frame
306 //================================================================
307 static inline SalomeApp_Study* getActiveStudy()
308 {
309   SUIT_Session* session = SUIT_Session::session();
310   SalomeApp_Application* app = dynamic_cast<SalomeApp_Application*>( session->activeApplication() );
311   if ( app )
312     return ( SalomeApp_Study* )app->activeStudy();
313   return 0;
314 }
315
316 static inline int getViewManagerId( SALOME_View* theViewFrame) {
317   SUIT_ViewModel* aModel = dynamic_cast<SUIT_ViewModel*>(theViewFrame);
318   SUIT_ViewManager* aViewMgr = 0;
319   if (aModel != 0)
320     aViewMgr = aModel->getViewManager();
321   return ((aViewMgr == 0) ? -1 :aViewMgr->getGlobalId());
322 }
323
324 //================================================================
325 // Function : getTopAbsMode
326 // Purpose  : Get TopAbs_ShapeEnum value corresponding to the
327 //            one from GEOMImpl_Types.h
328 //================================================================
329 static inline int getTopAbsMode( const int implType )
330 {
331   switch ( implType )
332   {
333     case GEOM_COMPOUND  : return TopAbs_COMPOUND;
334     case GEOM_SOLID     : return TopAbs_SOLID;
335     case GEOM_SHELL     : return TopAbs_SHELL;
336     case GEOM_FACE      : return TopAbs_FACE;
337     case GEOM_WIRE      : return TopAbs_WIRE;
338     case GEOM_EDGE      : return TopAbs_EDGE;
339     case GEOM_POINT     : return TopAbs_VERTEX;
340     default             : return -1;
341   }
342 }
343
344 int GEOM_Displayer::getMinMaxShapeType( const TopoDS_Shape& shape, bool ismin )
345 {
346   if ( shape.IsNull() )
347     return TopAbs_SHAPE;
348
349   int ret = shape.ShapeType();
350
351   if ( shape.ShapeType() == TopAbs_COMPOUND || shape.ShapeType() == TopAbs_COMPSOLID ) {
352     TopoDS_Iterator it(shape, Standard_True, Standard_False);
353     for (; it.More(); it.Next()) {
354       TopoDS_Shape sub_shape = it.Value();
355       if ( sub_shape.IsNull() ) continue;
356       int stype = getMinMaxShapeType( sub_shape, ismin );
357       if ( stype == TopAbs_SHAPE ) continue;
358       if ( ismin && stype > ret )
359         ret = stype;
360       else if ( !ismin && ( ret < TopAbs_SOLID || stype < ret ) )
361         ret = stype;
362     }
363   }
364
365   return ret;
366 }
367
368 bool GEOM_Displayer::isCompoundOfVertices( const TopoDS_Shape& theShape )
369 {
370   return theShape.ShapeType() == TopAbs_COMPOUND && getMinMaxShapeType( theShape, false ) == TopAbs_VERTEX;
371 }
372
373 //================================================================
374 // Function : getFilter
375 // Purpose  : Get filter corresponding to the type of object
376 //            from GEOMImpl_Types.h
377 //================================================================
378 SUIT_SelectionFilter* GEOM_Displayer::getFilter( const int theMode )
379 {
380   SUIT_SelectionFilter* aFilter;
381
382   int aTopAbsMode = getTopAbsMode( theMode );
383   if ( aTopAbsMode != -1 )
384     aFilter = new GEOM_TypeFilter( getStudy(), aTopAbsMode, true ); //@ aFilter = new GEOM_TypeFilter( ( TopAbs_ShapeEnum )aTopAbsMode );
385   else
386     switch ( theMode )
387       {
388       case GEOM_LINE      : aFilter = new GEOM_EdgeFilter( getStudy(), StdSelect_Line ); break;
389       case GEOM_CIRCLE    : aFilter = new GEOM_EdgeFilter( getStudy(), StdSelect_Circle ); break;
390
391       case GEOM_PLANE     : aFilter = new GEOM_FaceFilter( getStudy(), StdSelect_Plane ); break;
392       case GEOM_CYLINDER  : aFilter = new GEOM_FaceFilter( getStudy(), StdSelect_Cylinder ); break;
393       case GEOM_SPHERE    : aFilter = new GEOM_FaceFilter( getStudy(), StdSelect_Sphere ); break;
394       case GEOM_TORUS     : aFilter = new GEOM_FaceFilter( getStudy(), StdSelect_Torus ); break;
395       case GEOM_REVOLUTION: aFilter = new GEOM_FaceFilter( getStudy(), StdSelect_Revol ); break;
396       case GEOM_CONE      : aFilter = new GEOM_FaceFilter( getStudy(), StdSelect_Cone ); break;
397
398       case GEOM_PREVIEW   : aFilter = new GEOM_PreviewFilter( getStudy() ); break;
399
400       case GEOM_ALLSHAPES : aFilter = new GEOM_SelectionFilter(getStudy(), true ); break;
401       case GEOM_ALLGEOM   : aFilter = new SalomeApp_TypeFilter( getStudy(), "GEOM" ); break;
402
403       default             : aFilter = new GEOM_TypeFilter( getStudy(), theMode ); break;
404       }
405
406   return aFilter;
407 }
408
409 //================================================================
410 // Function : getComplexFilter
411 // Purpose  : Get compound filter corresponding to the type of
412 //            object from GEOMImpl_Types.h
413 //================================================================
414 SUIT_SelectionFilter* GEOM_Displayer::getComplexFilter( const QList<int>* aSubShapes)
415 {
416   GEOM_CompoundFilter* aFilter;
417
418   if(aSubShapes != NULL ) {
419     aFilter = new GEOM_CompoundFilter(getStudy());
420     QList<int> aTopAbsTypes;
421     QList<int>::const_iterator it;
422     for(it = aSubShapes->constBegin(); it != aSubShapes->constEnd(); ++it ) {
423       int topAbsMode = getTopAbsMode(*it);
424       if(topAbsMode != -1 )
425         aTopAbsTypes.append(topAbsMode);
426     }
427     aFilter->addSubTypes(aTopAbsTypes);
428   }
429
430   return aFilter;
431 }
432
433 //================================================================
434 // Function : getEntry
435 // Purpose  :
436 //================================================================
437 static std::string getEntry( GEOM::GEOM_BaseObject_ptr object )
438 {
439   SUIT_Session* session = SUIT_Session::session();
440   SalomeApp_Application* app = dynamic_cast<SalomeApp_Application*>( session->activeApplication() );
441   if ( app )
442   {
443     CORBA::String_var IOR = app->orb()->object_to_string( object );
444     if ( strcmp(IOR.in(), "") != 0 )
445     {
446       SalomeApp_Study* study = ( SalomeApp_Study* )app->activeStudy();
447       _PTR(SObject) SO ( study->studyDS()->FindObjectIOR( std::string(IOR) ) );
448       if ( SO )
449         return SO->GetID();
450     }
451   }
452   return "";
453 }
454
455 //================================================================
456 // Function : getName
457 // Purpose  :
458 //================================================================
459 static std::string getName( GEOM::GEOM_BaseObject_ptr object )
460 {
461   SUIT_Session* session = SUIT_Session::session();
462   SalomeApp_Application* app = dynamic_cast<SalomeApp_Application*>( session->activeApplication() );
463   if ( app )
464   {
465     CORBA::String_var IOR = app->orb()->object_to_string( object );
466     if ( strcmp(IOR.in(), "") != 0 )
467     {
468       SalomeApp_Study* study = ( SalomeApp_Study* )app->activeStudy();
469       _PTR(SObject) aSObj ( study->studyDS()->FindObjectIOR( std::string(IOR) ) );
470
471       _PTR(GenericAttribute) anAttr;
472
473       if ( aSObj && aSObj->FindAttribute( anAttr, "AttributeName") )
474       {
475         _PTR(AttributeName) aNameAttr( anAttr );
476         return aNameAttr->Value();
477       }
478     }
479   }
480
481   return "";
482 }
483
484 //=================================================================
485 /*!
486  *  GEOM_Displayer::GEOM_Displayer
487  *  Constructor
488  */
489 //=================================================================
490 GEOM_Displayer::GEOM_Displayer( SalomeApp_Study* st )
491 {
492   if( st )
493     myApp = dynamic_cast<SalomeApp_Application*>( st->application() );
494   else
495     myApp = 0;
496
497   /* Shading Color */
498   SUIT_Session* session = SUIT_Session::session();
499   SUIT_ResourceMgr* resMgr = session->resourceMgr();
500
501   QColor col = resMgr->colorValue( "Geometry", "shading_color", QColor( 255, 0, 0 ) );
502   myShadingColor = SalomeApp_Tools::color( col );
503
504   myDisplayMode = resMgr->integerValue("Geometry", "display_mode", 0);
505   myHasDisplayMode = false;
506
507   int aType = resMgr->integerValue("Geometry", "type_of_marker", (int)Aspect_TOM_PLUS);
508   myWidth = resMgr->integerValue("Geometry", "edge_width", -1);
509   myIsosWidth = resMgr->integerValue("Geometry", "isolines_width", -1);
510   
511   myTransparency = resMgr->integerValue("Geometry", "transparency", 0) / 100.;
512   myHasTransparency = false;
513
514   myTypeOfMarker = (Aspect_TypeOfMarker)(std::min((int)Aspect_TOM_RING3, std::max((int)Aspect_TOM_POINT, aType)));
515   myScaleOfMarker = (resMgr->integerValue("Geometry", "marker_scale", 1)-(int)GEOM::MS_10)*0.5 + 1.0;
516   myScaleOfMarker = std::min(7.0, std::max(1., myScaleOfMarker));
517
518   myColor = -1;
519   // This color is used for shape displaying. If it is equal -1 then
520   // default color is used.
521   myTexture = "";
522
523   myWidth = -1;
524   myType = -1;
525   myToActivate = true;
526   // This parameter is used for activisation/deactivisation of objects to be displayed
527
528   #if OCC_VERSION_LARGE > 0x06050100 // Functionnality available only in OCCT 6.5.2
529   // Activate parallel vizualisation only for testing purpose
530   // and if the corresponding env variable is set to 1
531   char* parallel_visu = getenv("PARALLEL_VISU");
532   if (parallel_visu && atoi(parallel_visu))
533   {
534     MESSAGE("Parallel visualisation on");
535     BRepMesh_IncrementalMesh::SetParallelDefault(Standard_True);
536   }
537   #endif
538
539   myViewFrame = 0;
540
541   myFieldDataType = GEOM::FDT_Double;
542   myFieldDimension = 0;
543   myFieldStepRangeMin = 0;
544   myFieldStepRangeMax = 0;
545 }
546
547 //=================================================================
548 /*!
549  *  GEOM_Displayer::~GEOM_Displayer
550  *  Destructor
551  */
552 //=================================================================
553 GEOM_Displayer::~GEOM_Displayer()
554 {
555 }
556
557 //=================================================================
558 /*!
559  *  GEOM_Displayer::Display
560  *  Display interactive object in the current viewer
561  */
562 //=================================================================
563 void GEOM_Displayer::Display( const Handle(SALOME_InteractiveObject)& theIO,
564                              const bool updateViewer,
565                              SALOME_View* theViewFrame )
566 {
567   SALOME_View* vf = theViewFrame ? theViewFrame : GetActiveView();
568   if ( vf )
569   {
570     SALOME_Prs* prs = buildPresentation( theIO->getEntry(), vf );
571
572     if ( prs )
573     {
574       vf->BeforeDisplay( this, prs );
575       vf->Display( prs );
576       vf->AfterDisplay( this, prs );
577
578       if ( updateViewer )
579         vf->Repaint();
580
581       int aMgrId = getViewManagerId(vf);
582       SalomeApp_Study* aStudy = getStudy();
583       aStudy->setObjectProperty(aMgrId, theIO->getEntry(), GEOM::propertyName( GEOM::Visibility ), 1 );
584
585       setVisibilityState(theIO->getEntry(), Qtx::ShownState);
586
587       delete prs;  // delete presentation because displayer is its owner
588     }
589   }
590 }
591
592 //=================================================================
593 /*!
594  *  GEOM_Displayer::Display
595  *  This overloaded Display() method can be useful for operations
596  *  not using dialog boxes.
597  */
598 //=================================================================
599 void GEOM_Displayer::Display( GEOM::GEOM_BaseObject_ptr theObj, const bool updateViewer )
600 {
601   if ( theObj->_is_nil() )
602     return;
603
604   std::string entry = getEntry( theObj );
605   if ( entry != "" ) {
606     Display(new SALOME_InteractiveObject(entry.c_str(), "GEOM", getName(theObj).c_str()),
607             updateViewer);
608   }
609 }
610
611 //=================================================================
612 /*!
613  *  GEOM_Displayer::Erase
614  *  Erase interactive object in the current viewer
615  */
616 //=================================================================
617 void GEOM_Displayer::Erase( const Handle(SALOME_InteractiveObject)& theIO,
618                             const bool forced,
619                             const bool updateViewer,
620                             SALOME_View* theViewFrame )
621 {
622   if ( theIO.IsNull() )
623     return;
624
625   SALOME_View* vf = theViewFrame ? theViewFrame : GetActiveView();
626
627   if ( vf ) {
628     SALOME_Prs* prs = vf->CreatePrs( theIO->getEntry() );
629     if ( prs ) {
630       vf->BeforeErase( this, prs );
631       vf->Erase( prs, forced );
632       vf->AfterErase( this, prs );
633       if ( updateViewer )
634         vf->Repaint();
635       delete prs;  // delete presentation because displayer is its owner
636
637       int aMgrId = getViewManagerId(vf);
638       SalomeApp_Study* aStudy = getStudy();
639       aStudy->setObjectProperty(aMgrId, theIO->getEntry(), GEOM::propertyName( GEOM::Visibility ), 0 );
640
641       setVisibilityState(theIO->getEntry(), Qtx::HiddenState);
642     }
643   }
644 }
645
646 //=================================================================
647 /*!
648  *  GEOM_Displayer::Erase
649  *  Erase geometry object in the current viewer
650  */
651 //=================================================================
652 void GEOM_Displayer::Erase( GEOM::GEOM_BaseObject_ptr theObj,
653                             const bool forced,
654                             const bool updateViewer,
655                             SALOME_View* theViewFrame)
656 {
657   std::string entry = getEntry( theObj );
658   if ( entry != "" )
659   {
660     Erase(new SALOME_InteractiveObject(entry.c_str(), "GEOM", getName(theObj).c_str()),
661           forced, updateViewer, theViewFrame);
662   }
663 }
664
665 //=================================================================
666 /*!
667  *  GEOM_Displayer::Redisplay
668  *  Redisplay (erase and then display again) interactive object
669  *  in the current viewer
670  */
671 //=================================================================
672 void GEOM_Displayer::Redisplay( const Handle(SALOME_InteractiveObject)& theIO,
673                                 const bool updateViewer,
674                                 const bool checkActiveViewer )
675 {
676   // Remove the object permanently (<forced> == true)
677   SUIT_Session* ses = SUIT_Session::session();
678   SUIT_Application* app = ses->activeApplication();
679   if ( app )
680   {
681     SUIT_Desktop* desk = app->desktop();
682     QList<SUIT_ViewWindow*> wnds = desk->windows();
683     SUIT_ViewWindow* wnd;
684     QListIterator<SUIT_ViewWindow*> it( wnds );
685     while ( it.hasNext() && (wnd = it.next()) )
686     {
687       SUIT_ViewManager* vman = wnd->getViewManager();
688       if ( vman )
689       {
690         SUIT_ViewModel* vmodel = vman->getViewModel();
691         if ( vmodel )
692         {
693           SALOME_View* view = dynamic_cast<SALOME_View*>(vmodel);
694           if ( view )
695           {
696             if ( view->isVisible( theIO ) || ( checkActiveViewer && view == GetActiveView() ) )
697             {
698               Redisplay( theIO, updateViewer, view );
699             }
700           }
701         }
702       }
703     }
704   }
705 }
706
707 //=================================================================
708 /*!
709  *  GEOM_Displayer::Redisplay
710  *  Redisplay (erase and then display again) interactive object
711  *  in the specified view
712  */
713 //=================================================================
714 void GEOM_Displayer::Redisplay( const Handle(SALOME_InteractiveObject)& theIO,
715                                 const bool theUpdateViewer,
716                                 SALOME_View* theViewFrame )
717 {
718   SALOME_View* vf = theViewFrame ? theViewFrame : GetActiveView();
719   if ( !vf )
720   {
721     return;
722   }
723
724   Erase( theIO, true, false, theViewFrame );
725   Display( theIO, theUpdateViewer, theViewFrame );
726 }
727
728 //=================================================================
729 /*!
730  *  GEOM_Displayer::Display
731  *  Calls Display() method for each object in the given list
732  */
733 //=================================================================
734 void GEOM_Displayer::Display( const SALOME_ListIO& theIOList, const bool updateViewer )
735 {
736   SALOME_ListIteratorOfListIO Iter( theIOList );
737   for ( ; Iter.More(); Iter.Next() ) {
738     Display( Iter.Value(), false );
739   }
740   if ( updateViewer )
741     UpdateViewer();
742 }
743
744 Quantity_Color GEOM_Displayer::qColorFromResources( const QString& property, const QColor& defColor )
745 {
746   // VSR: this method can be improved in future:
747   // to improve performance, the default values from resource manager should be cached in the displayer
748   return SalomeApp_Tools::color( SUIT_Session::session()->resourceMgr()->colorValue( "Geometry", property, defColor ) );
749 }
750
751 QColor GEOM_Displayer::colorFromResources( const QString& property, const QColor& defColor )
752 {
753   // VSR: this method can be improved in future:
754   // to improve performance, the default values from resource manager should be cached in the displayer
755   return SUIT_Session::session()->resourceMgr()->colorValue( "Geometry", property, defColor );
756 }
757
758 void GEOM_Displayer::updateShapeProperties( const Handle(GEOM_AISShape)& AISShape, bool create )
759 {
760   // check that shape is not null
761   if ( AISShape.IsNull() ) return;
762   
763   // check that study is active
764   SalomeApp_Study* study = getStudy();
765   if ( !study ) return;
766
767   if ( myShape.ShapeType() != TopAbs_VERTEX && // fix pb with not displayed points
768        !TopoDS_Iterator(myShape).More() )
769     return; // NPAL15983 (Bug when displaying empty groups)
770
771   // set interactive object
772
773   Handle( SALOME_InteractiveObject ) anIO;
774
775   if ( !myIO.IsNull() ) {
776     AISShape->setIO( myIO );
777     AISShape->SetOwner( myIO );
778     anIO = myIO;
779   }
780   else if ( !myName.empty() ) {
781     // workaround to allow selection of temporary objects
782     static int tempId = 0;
783     anIO = new SALOME_InteractiveObject( QString( "TEMP_%1" ).arg( tempId++ ).toLatin1().data(), "GEOM", myName.c_str() );
784     AISShape->setIO( anIO );
785     AISShape->SetOwner( anIO );
786   }
787
788   // flag:  only vertex or compound of vertices is processed (specific handling)
789   bool onlyVertex = myShape.ShapeType() == TopAbs_VERTEX || isCompoundOfVertices( myShape );
790   // presentation study entry (empty for temporary objects like preview)
791   QString entry = !anIO.IsNull() ? QString( anIO->getEntry() ) : QString();
792   // flag: temporary object
793   bool isTemporary = entry.isEmpty() || entry.startsWith( "TEMP_" );
794   // currently active view window's ID (-1 if no active view)
795   int aMgrId = !anIO.IsNull() ? getViewManagerId( myViewFrame ) : -1;
796
797   // get presentation properties
798   PropMap propMap = getObjectProperties( study, entry, myViewFrame );
799
800   // Temporary staff: vertex must be infinite for correct visualization
801   AISShape->SetInfiniteState( myShape.Infinite() ); // || myShape.ShapeType() == TopAbs_VERTEX // VSR: 05/04/2010: Fix 20668 (Fit All for points & lines)
802
803   // set material
804   Material_Model material;
805   // if predefined color isn't set in displayer(via GEOM_Displayer::SetColor() function)
806   if( !HasColor() )
807     material.fromProperties( propMap.value( GEOM::propertyName( GEOM::Material ) ).toString() );
808   // - set front material properties
809   AISShape->SetCurrentFacingModel( Aspect_TOFM_FRONT_SIDE );
810   AISShape->SetMaterial( material.getMaterialOCCAspect( true ) );
811   // - set back material properties
812   AISShape->SetCurrentFacingModel( Aspect_TOFM_BACK_SIDE );
813   AISShape->SetMaterial( material.getMaterialOCCAspect( false ) );
814   // - switch to default (both sides) facing mode
815   AISShape->SetCurrentFacingModel( Aspect_TOFM_BOTH_SIDE );
816
817   // set colors
818
819   // - shading color
820   if ( HasColor()  ) {
821     // predefined color, manually set to displayer via GEOM_Displayer::SetColor() function;
822     // we set it to the shape not taking into account material properties
823     AISShape->SetShadingColor( (Quantity_NameOfColor)GetColor() );
824   }
825   else if ( !material.isPhysical() ) {
826     // shading color from properties is used only for non-physical materials
827     AISShape->SetShadingColor( SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::ShadingColor ) ).value<QColor>() ) );
828   }
829
830   // - wireframe color
831   Handle(Prs3d_LineAspect) anAspect = AISShape->Attributes()->LineAspect();
832   anAspect->SetColor( HasColor() ? (Quantity_NameOfColor)GetColor() : 
833                       SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::WireframeColor ) ).value<QColor>() ) );
834   AISShape->Attributes()->SetLineAspect( anAspect );
835   
836   // - unfree boundaries color
837   anAspect = AISShape->Attributes()->UnFreeBoundaryAspect();
838   anAspect->SetColor( HasColor() ? (Quantity_NameOfColor)GetColor() : 
839                       SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::WireframeColor ) ).value<QColor>() ) );
840   AISShape->Attributes()->SetUnFreeBoundaryAspect( anAspect );
841   
842   // - free boundaries color
843   anAspect = AISShape->Attributes()->FreeBoundaryAspect();
844   anAspect->SetColor( HasColor() ? (Quantity_NameOfColor)GetColor() : 
845                       SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::FreeBndColor ) ).value<QColor>() ) );
846   AISShape->Attributes()->SetFreeBoundaryAspect( anAspect );
847   
848   // - standalone edges color
849   anAspect = AISShape->Attributes()->WireAspect();
850   anAspect->SetColor( HasColor() ? (Quantity_NameOfColor)GetColor() : 
851                       SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::LineColor ) ).value<QColor>() ) );
852   AISShape->Attributes()->SetWireAspect( anAspect );
853   
854   // - color for edges in shading+edges mode
855   AISShape->SetEdgesInShadingColor( SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::OutlineColor ) ).value<QColor>() ) );
856
857   // set display mode
858   AISShape->SetDisplayMode( HasDisplayMode() ? 
859                             // predefined display mode, manually set to displayer via GEOM_Displayer::SetDisplayMode() function 
860                             GetDisplayMode() :
861                             // display mode from properties
862                             propMap.value( GEOM::propertyName( GEOM::DisplayMode ) ).toInt() );
863
864   // - face boundaries color
865   if( AISShape->DisplayMode() == GEOM_AISShape::ShadingWithEdges )
866     AISShape->Attributes()->SetFaceBoundaryDraw( Standard_True );
867   anAspect = AISShape->Attributes()->FaceBoundaryAspect();
868   anAspect->SetColor( SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::OutlineColor ) ).value<QColor>() ) );
869   AISShape->Attributes()->SetFaceBoundaryAspect( anAspect );
870
871   // set display vectors flag
872   AISShape->SetDisplayVectors( propMap.value( GEOM::propertyName( GEOM::EdgesDirection ) ).toBool() );
873
874   // set display vertices flag
875   AISShape->SetDisplayVertices( propMap.value( GEOM::propertyName( GEOM::Vertices ) ).toBool() );
876
877   // set transparency
878   if( HasTransparency() ) {
879     AISShape->SetTransparency( GetTransparency() );
880   } else {
881     AISShape->SetTransparency( propMap.value( GEOM::propertyName( GEOM::Transparency ) ).toDouble() );
882   }
883
884   // set iso properties
885   int uIsos = propMap.value( GEOM::propertyName( GEOM::NbIsos ) ).toString().split( GEOM::subSectionSeparator() )[0].toInt();
886   int vIsos = propMap.value( GEOM::propertyName( GEOM::NbIsos ) ).toString().split( GEOM::subSectionSeparator() )[1].toInt();
887   Quantity_Color isosColor = SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::IsosColor ) ).value<QColor>() );
888   int isosWidth = propMap.value( GEOM::propertyName( GEOM::IsosWidth ) ).toInt();
889   Handle(Prs3d_IsoAspect) uIsoAspect = AISShape->Attributes()->UIsoAspect();
890   Handle(Prs3d_IsoAspect) vIsoAspect = AISShape->Attributes()->VIsoAspect();
891   uIsoAspect->SetColor( isosColor );
892   uIsoAspect->SetWidth( isosWidth );
893   uIsoAspect->SetNumber( uIsos );
894   vIsoAspect->SetColor( isosColor );
895   vIsoAspect->SetWidth( isosWidth );
896   vIsoAspect->SetNumber( vIsos );
897   AISShape->Attributes()->SetUIsoAspect( uIsoAspect );
898   AISShape->Attributes()->SetVIsoAspect( vIsoAspect );
899
900   // set deflection coefficient
901   // ... to avoid to small values of the coefficient, its lower value is limited 
902   AISShape->SetOwnDeviationCoefficient( qMax( propMap.value( GEOM::propertyName( GEOM::Deflection ) ).toDouble(), GEOM::minDeflection() ) );
903
904   // set texture
905   QString aImagePath;
906   if ( HasTexture() ) {
907     // predefined display texture, manually set to displayer via GEOM_Displayer::SetTexture() function 
908     aImagePath = GetTexture().c_str();
909     if ( ! entry.isEmpty() ) {
910       // check that study is active
911       SalomeApp_Study* study = getActiveStudy();
912       if ( study ) {
913         // Store the texture in object properties for next displays
914         study->setObjectProperty( aMgrId, entry, GEOM::propertyName( GEOM::Texture ), QString( GetTexture().c_str() ) );
915         study->setObjectProperty( aMgrId, entry, GEOM::propertyName( GEOM::DisplayMode ), 3 );
916         
917         // Update propeties map
918         propMap = getObjectProperties( study, entry, myViewFrame );
919       }
920     }
921   }
922   else {
923     aImagePath = propMap.value( GEOM::propertyName( GEOM::Texture ) ).toString();
924   }
925
926 #if OCC_VERSION_LARGE > 0x06070000
927   Handle(Image_PixMap) aPixmap;
928   if ( !aImagePath.isEmpty() )
929     aPixmap = cacheTextureFor( aImagePath, AISShape );
930   else
931     aPixmap = getDefaultTexture();
932
933   // apply image to shape
934   if ( !aPixmap.IsNull() ) {
935     AISShape->SetTexturePixMap( aPixmap );
936     AISShape->SetTextureMapOn();
937     AISShape->DisableTextureModulate();
938   }
939   else {
940     AISShape->SetTextureMapOff();
941   }
942 #else
943   if ( !aImagePath.isEmpty() ) {
944     AISShape->SetTextureFileName( TCollection_AsciiString( aImagePath.toUtf8().constData() ) );
945     AISShape->SetTextureMapOn();
946     AISShape->DisableTextureModulate();
947   }
948 #endif
949
950   // set line width
951   AISShape->SetWidth( HasWidth() ?
952                       // predefined line width, manually set to displayer via GEOM_Displayer::SetLineWidth() function 
953                       GetWidth() :
954                       // libe width from properties
955                       propMap.value( GEOM::propertyName( GEOM::LineWidth ) ).toInt() );
956
957   // set top-level flag
958   AISShape->setTopLevel( propMap.value( GEOM::propertyName( GEOM::TopLevel ) ).toBool() );
959
960   // set point marker (for vertex / compound of vertices only)
961   if ( onlyVertex ) {
962     QStringList aList = propMap.value( GEOM::propertyName( GEOM::PointMarker ) ).toString().split( GEOM::subSectionSeparator() );
963     if ( aList.size() == 2 ) {
964       // standard marker string contains "TypeOfMarker:ScaleOfMarker"
965       int aTypeOfMarker = aList[0].toInt();
966       double aScaleOfMarker = (aList[1].toInt() + 1) * 0.5;
967       Handle(Prs3d_PointAspect) anAspect = AISShape->Attributes()->PointAspect();
968       anAspect->SetScale( aScaleOfMarker );
969       anAspect->SetTypeOfMarker( (Aspect_TypeOfMarker)( aTypeOfMarker-1 ) );
970       anAspect->SetColor( HasColor() ? 
971                           // predefined color, manually set to displayer via GEOM_Displayer::SetColor() function
972                           (Quantity_NameOfColor)GetColor() : 
973                           // color from properties
974                           SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::PointColor ) ).value<QColor>() ) );
975       AISShape->Attributes()->SetPointAspect( anAspect );
976     }
977     else if ( aList.size() == 1 ) {
978       // custom marker string contains "IdOfTexture"
979       int textureId = aList[0].toInt();
980       Standard_Integer aWidth, aHeight;
981 #if OCC_VERSION_LARGE > 0x06040000 // Porting to OCCT6.5.1
982       Handle(TColStd_HArray1OfByte) aTexture =
983 #else
984         Handle(Graphic3d_HArray1OfBytes) aTexture =
985 #endif
986         GeometryGUI::getTexture( study, textureId, aWidth, aHeight );
987       if ( !aTexture.IsNull() ) {
988 #if OCC_VERSION_LARGE > 0x06060000 // Porting to OCCT higher 6.6.0 version
989         Handle(Prs3d_PointAspect) aTextureAspect =
990           new Prs3d_PointAspect( HasColor() ? 
991                                  // predefined color, manually set to displayer via GEOM_Displayer::SetColor() function
992                                  (Quantity_NameOfColor)GetColor() : 
993                                  // color from properties 
994                                  SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::PointColor ) ).value<QColor>() ),
995                                  aWidth, aHeight,
996                                  aTexture );
997 #else
998         int TextureId = 0;
999         Handle(Prs3d_PointAspect) aTextureAspect =
1000           new Prs3d_PointAspect( HasColor() ? 
1001                                  // predefined color, manually set to displayer via GEOM_Displayer::SetColor() function
1002                                  (Quantity_NameOfColor)GetColor() : 
1003                                  // color from properties 
1004                                  SalomeApp_Tools::color( propMap.value( GEOM::propertyName( GEOM::PointColor ) ).value<QColor>() ), 
1005                                  ++TextureId,
1006                                  aWidth, aHeight,
1007                                  aTexture );
1008 #endif
1009         AISShape->Attributes()->SetPointAspect( aTextureAspect );
1010       }
1011     }
1012   }
1013
1014   // set field step data
1015   AISShape->setFieldStepInfo( myFieldDataType,
1016                               myFieldDimension,
1017                               myFieldStepData,
1018                               myFieldStepName,
1019                               myFieldStepRangeMin,
1020                               myFieldStepRangeMax );
1021
1022   if ( create && !isTemporary && aMgrId != -1 ) {
1023     // set properties to the study
1024     study->setObjectPropMap( aMgrId, entry, propMap );
1025   }
1026
1027   // AISShape->SetName(???); ??? necessary to set name ???
1028 }
1029
1030 void GEOM_Displayer::updateActorProperties( GEOM_Actor* actor, bool create )
1031 {
1032   // check that actor is not null
1033   if ( !actor ) return;
1034   
1035   // check that study is active
1036   SalomeApp_Study* study = getStudy();
1037   if ( !study ) return;
1038
1039   // set interactive object
1040
1041   Handle( SALOME_InteractiveObject ) anIO;
1042
1043   if ( !myIO.IsNull() ) {
1044     actor->setIO( myIO );
1045     anIO = myIO;
1046   }
1047   else if ( !myName.empty() ) {
1048     // workaround to allow selection of temporary objects
1049     static int tempId = 0;
1050     anIO = new SALOME_InteractiveObject( QString( "TEMP_VTK_%1" ).arg( tempId++ ).toLatin1().data(), "GEOM", myName.c_str() );
1051     actor->setIO( anIO );
1052   }
1053
1054   // presentation study entry (empty for temporary objects like preview)
1055   QString entry = !anIO.IsNull() ? QString( anIO->getEntry() ) : QString();
1056   // flag: temporary object
1057   bool isTemporary = entry.isEmpty() || entry.startsWith( "TEMP_" );
1058   // currently active view window's ID (-1 if no active view)
1059   int aMgrId = !anIO.IsNull() ? getViewManagerId( myViewFrame ) : -1;
1060
1061   // get presentation properties
1062   PropMap propMap = getObjectProperties( study, entry, myViewFrame );
1063   QColor c;
1064
1065   /////////////////////////////////////////////////////////////////////////
1066   // VSR: for VTK viewer currently deflection coefficient is hardcoded
1067   //      due to performance problem
1068   // actor->SetShape(myShape,aDefPropMap.value(GEOM::propertyName( GEOM::Deflection )).toDouble(),myType == GEOM_VECTOR);
1069   /////////////////////////////////////////////////////////////////////////
1070   if ( !actor->getTopo().IsSame( myShape ) )
1071     actor->SetShape( myShape, VTK_MIN_DEFLECTION, myType == GEOM_VECTOR );
1072
1073   // set material
1074   Material_Model material;
1075   material.fromProperties( propMap.value( GEOM::propertyName( GEOM::Material ) ).toString() );
1076   std::vector<vtkProperty*> mprops;
1077   mprops.push_back( material.getMaterialVTKProperty( true ) );
1078   mprops.push_back( material.getMaterialVTKProperty( false) );
1079   actor->SetMaterial( mprops );
1080
1081   // set iso-lines properties
1082
1083   // - set number of iso-lines
1084   int nbIsos[2]= { 1, 1 };
1085   QStringList isos = propMap.value( GEOM::propertyName( GEOM::NbIsos ) ).toString().split( GEOM::subSectionSeparator() );
1086   nbIsos[0] = isos[0].toInt();
1087   nbIsos[1] = isos[1].toInt();
1088   actor->SetNbIsos( nbIsos );
1089
1090   // - set iso-lines width
1091   actor->SetIsosWidth( propMap.value( GEOM::propertyName( GEOM::IsosWidth ) ).toInt() );
1092
1093   // - set iso-lines color
1094   c = propMap.value( GEOM::propertyName( GEOM::IsosColor ) ).value<QColor>();
1095   actor->SetIsosColor( c.redF(), c.greenF(), c.blueF() );
1096
1097   // set colors
1098
1099   if ( HasColor()  ) {
1100     // - same color for all sub-actors
1101     Quantity_Color aColor( (Quantity_NameOfColor)GetColor() );
1102     actor->SetColor( aColor.Red(), aColor.Green(), aColor.Blue() );
1103   }
1104   else {
1105     // shading color (for non-physical materials)
1106     if ( !material.isPhysical() ) {
1107       c = propMap.value( GEOM::propertyName( GEOM::ShadingColor ) ).value<QColor>();
1108       actor->GetFrontMaterial()->SetColor( c.redF(), c.greenF(), c.blueF() );
1109       actor->GetBackMaterial()->SetColor( c.redF(), c.greenF(), c.blueF() );
1110     }
1111
1112     // - standalone edge color
1113     c = propMap.value( GEOM::propertyName( GEOM::LineColor ) ).value<QColor>();
1114     actor->SetIsolatedEdgeColor( c.redF(), c.greenF(), c.blueF() );
1115
1116     c = propMap.value( GEOM::propertyName( GEOM::WireframeColor ) ).value<QColor>();
1117     // - shared edges color ???
1118     actor->SetSharedEdgeColor( c.redF(), c.greenF(), c.blueF() );
1119
1120     c = propMap.value( GEOM::propertyName( GEOM::FreeBndColor ) ).value<QColor>();
1121     // - free edges color ???
1122     actor->SetFreeEdgeColor( c.redF(), c.greenF(), c.blueF() );
1123
1124     // - point color
1125     c = propMap.value( GEOM::propertyName( GEOM::PointColor ) ).value<QColor>();
1126     actor->SetPointColor( c.redF(), c.greenF(), c.blueF() );
1127   }
1128
1129   // - color for edges in shading+edges mode
1130   c = propMap.value( GEOM::propertyName( GEOM::OutlineColor ) ).value<QColor>();
1131   actor->SetEdgesInShadingColor( c.redF(), c.greenF(), c.blueF() );
1132
1133   // set opacity
1134   if( HasTransparency() ) {
1135     actor->SetOpacity( 1.0 - GetTransparency() );
1136   } else {
1137     actor->SetOpacity( 1.0 - propMap.value( GEOM::propertyName( GEOM::Transparency ) ).toDouble() );
1138   }
1139
1140   // set line width
1141   actor->SetWidth( HasWidth() ?
1142                    // predefined line width, manually set to displayer via GEOM_Displayer::SetLineWidth() function 
1143                    GetWidth() :
1144                    // libe width from properties
1145                    propMap.value( GEOM::propertyName( GEOM::LineWidth ) ).toInt() );
1146   
1147   // set display vectors flag
1148   actor->SetVectorMode( propMap.value( GEOM::propertyName( GEOM::EdgesDirection ) ).toBool() );
1149
1150   // set display vertices flag
1151   actor->SetVerticesMode( propMap.value( GEOM::propertyName( GEOM::Vertices ) ).toBool() );
1152
1153   // set display mode
1154   int displayMode = HasDisplayMode() ? 
1155     // predefined display mode, manually set to displayer via GEOM_Displayer::SetDisplayMode() function 
1156     GetDisplayMode() :
1157     // display mode from properties
1158     propMap.value( GEOM::propertyName( GEOM::DisplayMode ) ).toInt();
1159
1160   // specific processing of 'shading with edges' mode, as VTK provides only the following standard display modes:
1161   // Points - 0, Wireframe - 1, Surface - 2, Insideframe - 3, SurfaceWithEdges - 4
1162   // GEOM actor allows alternative display modes (see VTKViewer::Representation enum) and enum in GEOM_Actor:
1163   // eWireframe - 0, eShading - 1, eShadingWithEdges - 3
1164
1165   if ( displayMode == 2 )
1166       // this is 'Shading with edges' mode => we have to do the correct mapping to EDisplayMode
1167       // enum in GEOM_Actor (and further to VTKViewer::Representation enum)
1168     displayMode++;
1169   actor->setDisplayMode( displayMode );
1170
1171   if ( myToActivate )
1172     actor->PickableOn();
1173   else
1174     actor->PickableOff();
1175
1176   if ( create && !isTemporary && aMgrId != -1 ) {
1177     // set properties to the study
1178     study->setObjectPropMap( aMgrId, entry, propMap );
1179   }
1180 }
1181
1182 //=================================================================
1183 /*!
1184  *  GEOM_Displayer::updateDimensions
1185  *  Creates or renews dimension presentation for the IO.
1186  */
1187 //=================================================================
1188 void GEOM_Displayer::updateDimensions( const Handle(SALOME_InteractiveObject)& theIO,
1189                                        SALOME_OCCPrs* thePrs,
1190                                        const gp_Ax3& theShapeLCS )
1191 {
1192   SalomeApp_Study* aStudy = getStudy();
1193   if ( !aStudy )
1194   {
1195     return;
1196   }
1197
1198   if ( theIO.IsNull() )
1199   {
1200     return;
1201   }
1202
1203   SOCC_Prs* anOccPrs = dynamic_cast<SOCC_Prs*>( thePrs );
1204
1205   AIS_ListOfInteractive aListOfIO;
1206
1207   anOccPrs->GetObjects( aListOfIO );
1208
1209   AIS_ListIteratorOfListOfInteractive aIterateIO( aListOfIO );
1210
1211   // remove outdated presentations of dimensions
1212   for ( ; aIterateIO.More(); aIterateIO.Next() )
1213   {
1214     const Handle(AIS_InteractiveObject)& anIO = aIterateIO.Value();
1215     if ( !anIO->IsKind( STANDARD_TYPE( AIS_Dimension ) ) )
1216     {
1217       continue;
1218     }
1219
1220     aListOfIO.Remove( aIterateIO );
1221
1222     if ( !aIterateIO.More() )
1223     {
1224       break;
1225     }
1226   }
1227
1228   // prepare dimension styling
1229   SUIT_ResourceMgr* aResMgr = SUIT_Session::session()->resourceMgr();
1230
1231   QColor  aQColor       = aResMgr->colorValue  ( "Geometry", "dimensions_color", QColor( 0, 255, 0 ) );
1232   int     aLineWidth    = aResMgr->integerValue( "Geometry", "dimensions_line_width", 1 );
1233   double  aFontHeight   = aResMgr->doubleValue ( "Geometry", "dimensions_font_height", 10 );
1234   double  anArrowLength = aResMgr->doubleValue ( "Geometry", "dimensions_arrow_length", 5 );
1235   bool    isUnitsShown  = aResMgr->booleanValue( "Geometry", "dimensions_show_units", false );
1236   QString aUnitsLength  = aResMgr->stringValue ( "Geometry", "dimensions_length_units", "m" );
1237   QString aUnitsAngle   = aResMgr->stringValue ( "Geometry", "dimensions_angle_units", "deg" );
1238
1239   // restore dimension presentation from saved attribute or property data
1240   AIS_ListOfInteractive aRestoredDimensions;
1241
1242   QVariant aProperty = aStudy->getObjectProperty( GEOM::sharedPropertiesId(),
1243                                                   theIO->getEntry(),
1244                                                   GEOM::propertyName( GEOM::Dimensions ),
1245                                                   QVariant() );
1246
1247   GEOMGUI_DimensionProperty aRecords;
1248
1249   if ( aProperty.isValid() && aProperty.canConvert<GEOMGUI_DimensionProperty>() )
1250   {
1251     aRecords = aProperty.value<GEOMGUI_DimensionProperty>();
1252   }
1253   else
1254   {
1255     aRecords.LoadFromAttribute( getStudy(), theIO->getEntry() );
1256   }
1257   
1258   // create up-to-date dimension presentations
1259   for ( int aPrsIt = 0; aPrsIt < aRecords.GetNumber(); ++aPrsIt )
1260   {
1261     if ( !aRecords.IsVisible( aPrsIt ) )
1262     {
1263       continue;
1264     }
1265
1266     // init dimension by type
1267     Handle(AIS_Dimension) aPrs;
1268     switch( aRecords.GetType( aPrsIt ) )
1269     {
1270       case GEOMGUI_DimensionProperty::DimensionType_Length :
1271       {
1272         Handle(GEOM_AISLength) aLength = new GEOM_AISLength( aPrsIt );
1273         aRecords.GetRecord( aPrsIt )->AsLength()->Update( aLength, theShapeLCS );
1274         aPrs = aLength;
1275         break;
1276       }
1277
1278       case GEOMGUI_DimensionProperty::DimensionType_Diameter :
1279       {
1280         Handle(GEOM_AISDiameter) aDiam = new GEOM_AISDiameter( aPrsIt );
1281         aRecords.GetRecord( aPrsIt )->AsDiameter()->Update( aDiam, theShapeLCS );
1282         aPrs = aDiam;
1283         break;
1284       }
1285
1286       case GEOMGUI_DimensionProperty::DimensionType_Angle :
1287       {
1288         Handle(GEOM_AISAngle) anAng = new GEOM_AISAngle( aPrsIt );
1289         aRecords.GetRecord( aPrsIt )->AsAngle()->Update( anAng, theShapeLCS );
1290         aPrs = anAng;
1291         break;
1292       }
1293     }
1294
1295     aPrs->SetOwner( theIO );
1296
1297     Quantity_Color aColor( aQColor.redF(), aQColor.greenF(), aQColor.blueF(), Quantity_TOC_RGB );
1298
1299     Handle(Prs3d_DimensionAspect) aStyle = new Prs3d_DimensionAspect();
1300
1301     aStyle->SetCommonColor( aColor );
1302     aStyle->MakeUnitsDisplayed( (Standard_Boolean) isUnitsShown );
1303     aStyle->MakeText3d( Standard_True );
1304     aStyle->MakeTextShaded( Standard_True );
1305     aStyle->SetExtensionSize( aFontHeight * 0.5 );
1306     aStyle->TextAspect()->SetHeight( aFontHeight );
1307     aStyle->ArrowAspect()->SetLength( anArrowLength );
1308     aStyle->LineAspect()->SetWidth( aLineWidth );
1309     aStyle->SetTextHorizontalPosition( aPrs->DimensionAspect()->TextHorizontalPosition() );
1310     aStyle->SetTextVerticalPosition( aPrs->DimensionAspect()->TextVerticalPosition() );
1311     aStyle->SetArrowOrientation( aPrs->DimensionAspect()->ArrowOrientation() );
1312     aPrs->SetDimensionAspect( aStyle );
1313     aPrs->SetPolygonOffsets( Aspect_POM_Fill, -1.0, -1.0 );
1314     aPrs->Attributes()->SetDimLengthDisplayUnits( aUnitsLength.toLatin1().data() );
1315     aPrs->Attributes()->SetDimAngleDisplayUnits( aUnitsAngle.toLatin1().data() );
1316
1317     if ( aPrs->IsKind( STANDARD_TYPE(AIS_AngleDimension) ) )
1318     {
1319       // show degree symbol for dimension instead of label "deg"
1320       if ( aUnitsAngle == "deg" )
1321       {
1322         aPrs->SetSpecialSymbol(0xB0);
1323         aPrs->SetDisplaySpecialSymbol( isUnitsShown ? AIS_DSS_After : AIS_DSS_No );
1324         aStyle->MakeUnitsDisplayed(Standard_False);
1325       }
1326       else
1327       {
1328         aPrs->SetDisplaySpecialSymbol(AIS_DSS_No);
1329         aStyle->MakeUnitsDisplayed( (Standard_Boolean) isUnitsShown );
1330       }
1331     }
1332     else
1333     {
1334       aStyle->MakeUnitsDisplayed( (Standard_Boolean) isUnitsShown );
1335     }
1336
1337     aListOfIO.Append( aPrs );
1338   }
1339
1340   // update presentation
1341   anOccPrs->Clear();
1342
1343   for ( aIterateIO.Initialize( aListOfIO ); aIterateIO.More(); aIterateIO.Next() )
1344   {
1345     anOccPrs->AddObject( aIterateIO.Value() );
1346   }
1347 }
1348
1349 //=================================================================
1350 /*!
1351  *  GEOM_Displayer::Erase
1352  *  Calls Erase() method for each object in the given list
1353  */
1354 //=================================================================
1355 void GEOM_Displayer::Erase( const SALOME_ListIO& theIOList,
1356                             const bool forced,
1357                             const bool updateViewer )
1358 {
1359   SALOME_ListIteratorOfListIO Iter( theIOList );
1360   for ( ; Iter.More(); Iter.Next() )
1361     Erase( Iter.Value(), forced, false );
1362
1363   if ( updateViewer )
1364     UpdateViewer();
1365 }
1366
1367 //=================================================================
1368 /*!
1369  *  GEOM_Displayer::Redisplay
1370  *  Calls Redisplay() method for each object in the given list
1371  */
1372 //=================================================================
1373 void GEOM_Displayer::Redisplay( const SALOME_ListIO& theIOList,
1374                                 const bool updateViewer,
1375                                 const bool checkActiveViewer )
1376 {
1377   SALOME_ListIteratorOfListIO Iter( theIOList );
1378   for ( ; Iter.More(); Iter.Next() )
1379     Redisplay( Iter.Value(), false, checkActiveViewer );
1380
1381   if ( updateViewer )
1382     UpdateViewer();
1383 }
1384
1385 //=================================================================
1386 /*!
1387  *  GEOM_Displayer::Redisplay
1388  *  Calls Redisplay() method for each object in the given list
1389  */
1390 //=================================================================
1391 void GEOM_Displayer::Redisplay( const SALOME_ListIO& theIOList,
1392                                 const bool theUpdateViewer,
1393                                 SALOME_View* theViewFrame )
1394 {
1395   SALOME_ListIteratorOfListIO anIter( theIOList );
1396   for ( ; anIter.More(); anIter.Next() )
1397   {
1398     Redisplay( anIter.Value(), false, theViewFrame );
1399   }
1400
1401   if ( theUpdateViewer )
1402   {
1403     UpdateViewer();
1404   }
1405 }
1406
1407 //=================================================================
1408 /*!
1409  *  GEOM_Displayer::Update
1410  *  Update OCC presentaion
1411  *  [ Reimplemented from SALOME_Displayer ]
1412  */
1413 //=================================================================
1414 void GEOM_Displayer::Update( SALOME_OCCPrs* prs )
1415 {
1416   SOCC_Prs* occPrs = dynamic_cast<SOCC_Prs*>( prs );
1417   SalomeApp_Study* study = getStudy();
1418
1419   if ( !occPrs || myShape.IsNull() || !study )
1420     return;
1421
1422   if ( myType == GEOM_MARKER && myShape.ShapeType() == TopAbs_FACE )
1423   {
1424     // 
1425     // specific processing for local coordinate system presentation
1426     // 
1427
1428     TopoDS_Face aFace = TopoDS::Face( myShape );
1429     Handle(Geom_Plane) aPlane = Handle(Geom_Plane)::DownCast( BRep_Tool::Surface( aFace ) );
1430     if ( !aPlane.IsNull() )
1431     {
1432       gp_Ax3 aPos = aPlane->Pln().Position();
1433       Handle(Geom_Axis2Placement) aPlc = new Geom_Axis2Placement( aPos.Ax2() );
1434
1435       Handle(GEOM_AISTrihedron) aTrh;
1436
1437       if ( occPrs->IsNull() )
1438       {
1439         // new presentation is being created
1440         aTrh = new GEOM_AISTrihedron( aPlc );
1441         occPrs->AddObject( aTrh );
1442       }
1443       else
1444       {
1445         // presentation is being updated
1446         AIS_ListOfInteractive aList;
1447         occPrs->GetObjects( aList );
1448         AIS_ListIteratorOfListOfInteractive anIter( aList );
1449         for ( ; anIter.More() && aTrh.IsNull(); anIter.Next() ) {
1450           aTrh = Handle(GEOM_AISTrihedron)::DownCast( anIter.Value() );
1451         }
1452       }
1453         
1454       if ( !aTrh.IsNull() ) {
1455         // predefined color, manually set to displayer via GEOM_Displayer::SetColor() function
1456         if ( HasColor() )
1457           aTrh->SetColor( (Quantity_NameOfColor)GetColor() );
1458         // predefined line width, manually set to displayer via GEOM_Displayer::SetLineWidth() function 
1459         if ( HasWidth() )
1460           aTrh->SetWidth( GetWidth() );
1461         
1462         if ( !myIO.IsNull() )
1463         {
1464           aTrh->setIO( myIO );
1465           aTrh->SetOwner( myIO );
1466         }
1467         aTrh->SetComponent( aPlc );
1468         aTrh->SetToUpdate();
1469       }
1470       occPrs->SetToActivate( ToActivate() );
1471     }
1472   }
1473   else
1474   {
1475     // 
1476     // processing for usual geometry presentation
1477     // 
1478
1479     // if presentation is empty we try to create new one
1480     if ( occPrs->IsNull() )
1481     {
1482       // create presentation (specific for vectors)
1483       Handle(GEOM_AISShape) AISShape = ( myType == GEOM_VECTOR ) ? new GEOM_AISVector( myShape, "" )
1484                                                                  : new GEOM_AISShape ( myShape, "" );
1485
1486       if( myType == GEOM_FIELD_STEP )
1487         AISShape->SetHilightMode( GEOM_AISShape::CustomHighlight );
1488       // update shape properties
1489       updateShapeProperties( AISShape, true );
1490
1491       // add shape to the presentation
1492       occPrs->AddObject( AISShape );
1493
1494       // In accordance with ToActivate() value object will be activated/deactivated
1495       // when it will be displayed
1496       occPrs->SetToActivate( ToActivate() );
1497
1498       if ( AISShape->isTopLevel() && GEOM_AISShape::topLevelDisplayMode() == GEOM_AISShape::TopShowAdditionalWActor ) {
1499         // 21671: EDF 1829 GEOM : Bring to front selected objects (continuation):
1500
1501         // create additional wireframe shape
1502         Handle(GEOM_TopWireframeShape) aWirePrs = new GEOM_TopWireframeShape(myShape);
1503         aWirePrs->SetWidth(AISShape->Width());
1504         if ( !myIO.IsNull() ) {
1505           aWirePrs->setIO( myIO );
1506           aWirePrs->SetOwner( myIO );
1507         }
1508
1509         // add shape to the presentation
1510         occPrs->AddObject( aWirePrs );
1511       }
1512     }
1513     // if presentation is found -> set again shape for it
1514     else
1515     {
1516       AIS_ListOfInteractive IOList;
1517       occPrs->GetObjects( IOList );
1518       AIS_ListIteratorOfListOfInteractive Iter( IOList );
1519       for ( ; Iter.More(); Iter.Next() )
1520       {
1521         Handle(GEOM_AISShape) AISShape = Handle(GEOM_AISShape)::DownCast( Iter.Value() );
1522         if ( AISShape.IsNull() )
1523           continue;
1524
1525         // re-set shape (it might be changed)
1526         if ( AISShape->Shape() != myShape )
1527           AISShape->Set( myShape );
1528
1529         // update shape properties
1530         updateShapeProperties( AISShape, false );
1531
1532         // force updating
1533         AISShape->UpdateSelection();
1534         AISShape->SetToUpdate();
1535       }
1536     }
1537
1538     updateDimensions( myIO, occPrs, gp_Ax3().Transformed( myShape.Location().Transformation() ) );
1539   }
1540 }
1541
1542 //=================================================================
1543 /*!
1544  *  GEOM_Displayer::Update
1545  *  Update VTK presentaion
1546  *  [ Reimplemented from SALOME_Displayer ]
1547  */
1548 //=================================================================
1549 void GEOM_Displayer::Update( SALOME_VTKPrs* prs )
1550 {
1551   SVTK_Prs* vtkPrs = dynamic_cast<SVTK_Prs*>( prs );
1552   SalomeApp_Study* study = getStudy();
1553
1554   if ( !vtkPrs || myShape.IsNull() || !study )
1555     return;
1556
1557   if ( myType == GEOM_MARKER && myShape.ShapeType() == TopAbs_FACE )
1558   {
1559     // 
1560     // specific processing for local coordinate system presentation
1561     // 
1562
1563     TopoDS_Face aFace = TopoDS::Face( myShape );
1564     Handle(Geom_Plane) aPlane = Handle(Geom_Plane)::DownCast( BRep_Tool::Surface( aFace ) );
1565     if ( !aPlane.IsNull() ) {
1566       gp_Ax3 aPos = aPlane->Pln().Position();
1567       Handle(Geom_Axis2Placement) aPlc = new Geom_Axis2Placement( aPos.Ax2() );
1568
1569       GEOM_VTKTrihedron* aTrh = 0;
1570
1571       if ( vtkPrs->IsNull() ) {
1572         // new presentation is being created
1573         aTrh = GEOM_VTKTrihedron::New();
1574         vtkPrs->AddObject( aTrh );
1575       }
1576       else {
1577         // presentation is being updated
1578         vtkActorCollection* actors = vtkPrs->GetObjects();
1579         if ( actors ) {
1580           actors->InitTraversal();
1581           vtkActor* a = actors->GetNextActor();
1582           while ( a && !aTrh ) {
1583             aTrh = GEOM_VTKTrihedron::SafeDownCast( a );
1584             a = actors->GetNextActor();
1585           }
1586         }
1587       }
1588       
1589       if ( aTrh ) {
1590         // predefined color, manually set to displayer via GEOM_Displayer::SetColor() function
1591         if ( HasColor() ) {
1592           Quantity_Color aColor( (Quantity_NameOfColor)GetColor() );
1593           aTrh->SetColor( aColor.Red(), aColor.Green(), aColor.Blue() );
1594         }
1595 #ifdef VTK_TRIHEDRON_WIDTH
1596         // 
1597         // VSR: currently isn't supported
1598         //
1599         // predefined line width, manually set to displayer via GEOM_Displayer::SetLineWidth() function 
1600         if ( HasWidth() )
1601           aTrh->SetWidth( GetWidth() );
1602 #endif
1603
1604         if ( !myIO.IsNull() )
1605           aTrh->setIO( myIO );
1606
1607         aTrh->SetPlacement( aPlc );
1608       }
1609     }
1610   }
1611   else
1612   {
1613     // 
1614     // processing for usual geometry presentation
1615     // 
1616
1617     // if presentation is empty we try to create new one
1618     if ( vtkPrs->IsNull() )
1619     {
1620       // create an actor
1621       GEOM_Actor* actor = GEOM_Actor::New();
1622       // update actor properties
1623       updateActorProperties( actor, true );
1624       // add actor to the presentation
1625       vtkPrs->AddObject( actor );
1626     }
1627     else {
1628       // presentation is being updated
1629       vtkActorCollection* actors = vtkPrs->GetObjects();
1630       if ( actors ) {
1631         actors->InitTraversal();
1632         vtkActor* a = actors->GetNextActor();
1633         while ( a ) {
1634           GEOM_Actor* actor = GEOM_Actor::SafeDownCast( a );
1635           if ( actor ) {
1636             // update actor properties
1637             updateActorProperties( actor, false );
1638             a = actors->GetNextActor();
1639           }
1640         }
1641       }
1642     }
1643   }
1644 }
1645
1646 //=================================================================
1647 /*!
1648  *  GEOM_Displayer::BuildPrs
1649  *  Build presentation accordint to the current viewer type
1650  */
1651 //=================================================================
1652 SALOME_Prs* GEOM_Displayer::BuildPrs( GEOM::GEOM_Object_ptr theObj )
1653 {
1654   if ( theObj->_is_nil() )
1655     return 0;
1656
1657   myViewFrame = GetActiveView();
1658   if ( myViewFrame == 0 )
1659     return 0;
1660
1661   SALOME_Prs* aPrs = myViewFrame->CreatePrs();
1662   if ( aPrs == 0 )
1663     return 0;
1664
1665   internalReset();
1666   setShape( GEOM_Client::get_client().GetShape( GeometryGUI::GetGeomGen(), theObj ) );
1667   myType = theObj->GetType();
1668
1669   // Update presentation
1670   UpdatePrs( aPrs );
1671
1672   return aPrs;
1673 }
1674
1675 //=================================================================
1676 /*!
1677  *  GEOM_Displayer::BuildPrs
1678  *  Build presentation accordint to the current viewer type
1679  */
1680 //=================================================================
1681 SALOME_Prs* GEOM_Displayer::BuildPrs( const TopoDS_Shape& theShape )
1682 {
1683   myViewFrame = GetActiveView();
1684   if ( theShape.IsNull() || myViewFrame == 0 )
1685     return 0;
1686
1687   SALOME_Prs* aPrs = myViewFrame->CreatePrs();
1688   if ( aPrs == 0 )
1689     return 0;
1690
1691   internalReset();
1692   setShape( theShape );
1693   myType = -1;
1694
1695   UpdatePrs( aPrs );
1696
1697   return aPrs;
1698 }
1699
1700 //=================================================================
1701 /*!
1702  *  GEOM_Displayer::buildPresentation
1703  *  Builds/finds object's presentation for the current viewer
1704  *  Calls corresponding Update() method by means of double dispatch
1705  *  [ internal ]
1706  */
1707 //=================================================================
1708 SALOME_Prs* GEOM_Displayer::buildPresentation( const QString& entry,
1709                                                SALOME_View* theViewFrame )
1710 {
1711   SALOME_Prs* prs = 0;
1712   internalReset();
1713
1714   myViewFrame = theViewFrame ? theViewFrame : GetActiveView();
1715
1716   if ( myViewFrame )
1717   {
1718     prs = LightApp_Displayer::buildPresentation( entry, theViewFrame );
1719     if ( prs )
1720     {
1721       Handle( SALOME_InteractiveObject ) theIO = new SALOME_InteractiveObject();
1722       theIO->setEntry( entry.toLatin1().constData() );
1723       if ( !theIO.IsNull() )
1724       {
1725         // set interactive object
1726         setIO( theIO );
1727         //  Find SOBject (because shape should be published previously)
1728         SUIT_Session* session = SUIT_Session::session();
1729         SUIT_Application* app = session->activeApplication();
1730         if ( app )
1731         {
1732           SalomeApp_Study* study = dynamic_cast<SalomeApp_Study*>( app->activeStudy() );
1733           if ( study )
1734           {
1735             _PTR(SObject) SO ( study->studyDS()->FindObjectID( theIO->getEntry() ) );
1736             if ( SO )
1737             {
1738               // get CORBA reference to data object
1739               CORBA::Object_var object = GeometryGUI::ClientSObjectToObject(SO);
1740               if ( !CORBA::is_nil( object ) )
1741               {
1742                 // downcast to GEOM base object
1743                 GEOM::GEOM_BaseObject_var GeomBaseObject = GEOM::GEOM_BaseObject::_narrow( object );
1744                 if ( !GeomBaseObject->_is_nil() )
1745                 {
1746                   myType = GeomBaseObject->GetType();
1747
1748                   // downcast to GEOM object
1749                   GEOM::GEOM_Object_var GeomObject = GEOM::GEOM_Object::_narrow( GeomBaseObject );
1750                   if ( myType == GEOM_FIELD_STEP )
1751                   {
1752                     // get the GEOM object from the field's shape
1753                     GEOM::GEOM_FieldStep_var GeomFieldStep = GEOM::GEOM_FieldStep::_narrow( GeomBaseObject );
1754                     if ( !GeomFieldStep->_is_nil() )
1755                     {
1756                       GEOM::GEOM_Field_var GeomField = GeomFieldStep->GetField();
1757                       if ( !GeomField->_is_nil() )
1758                         GeomObject = GeomField->GetShape();
1759                     }
1760
1761                     // read the field step information
1762                     readFieldStepInfo( GeomFieldStep );
1763                   }
1764
1765                   if ( !GeomObject->_is_nil() )
1766                   {
1767                     // finally set shape
1768                     setShape( GEOM_Client::get_client().GetShape( GeometryGUI::GetGeomGen(), GeomObject ) );
1769                   }
1770                 }
1771               }
1772             }
1773           }
1774         }
1775       }
1776       UpdatePrs( prs );  // Update presentation by using of the double dispatch
1777     }
1778   }
1779   return prs;
1780 }
1781
1782 //=================================================================
1783 /*!
1784  *  GEOM_Displayer::buildSubshapePresentation
1785  *  Builds/finds object's presentation for the current viewer
1786  *  Calls corresponding Update() method by means of double dispatch
1787  *  For not published objects (for Mantis issue 0020435)
1788  */
1789 //=================================================================
1790 SALOME_Prs* GEOM_Displayer::buildSubshapePresentation(const TopoDS_Shape& aShape,
1791                                                       const QString& entry,
1792                                                       SALOME_View* theViewFrame)
1793 {
1794   SALOME_Prs* prs = 0;
1795   internalReset();
1796
1797   myViewFrame = theViewFrame ? theViewFrame : GetActiveView();
1798
1799   if (myViewFrame)
1800   {
1801     prs = LightApp_Displayer::buildPresentation(entry, theViewFrame);
1802     if (prs)
1803     {
1804       Handle(SALOME_InteractiveObject) theIO = new SALOME_InteractiveObject();
1805       theIO->setEntry(entry.toLatin1().constData());
1806       if (!theIO.IsNull())
1807       {
1808         // set interactive object
1809         setIO(theIO);
1810         // finally set shape
1811         setShape(aShape);
1812         myType = GEOM_SUBSHAPE;
1813       }
1814       UpdatePrs(prs);  // Update presentation by using of the double dispatch
1815     }
1816   }
1817   return prs;
1818 }
1819
1820 //=================================================================
1821 /*!
1822  *  GEOM_Displayer::internalReset
1823  *  Resets internal data
1824  *  [internal]
1825  */
1826 //=================================================================
1827 void GEOM_Displayer::internalReset()
1828 {
1829   myIO.Nullify();
1830   myShape.Nullify();
1831
1832   myFieldDataType = GEOM::FDT_Double;
1833   myFieldDimension = 0;
1834   myFieldStepData.clear();
1835   myFieldStepName.Clear();
1836   myFieldStepRangeMin = 0;
1837   myFieldStepRangeMax = 0;
1838 }
1839
1840 //=================================================================
1841 /*!
1842  *  GEOM_Displayer::LocalSelection
1843  *  Activate selection of CAD shapes with activisation of selection
1844  *  of their sub-shapes (with opened local context for OCC viewer)
1845  */
1846 //=================================================================
1847 void GEOM_Displayer::LocalSelection( const Handle(SALOME_InteractiveObject)& theIO, const int theMode )
1848 {
1849   SUIT_Session* session = SUIT_Session::session();
1850   SalomeApp_Application* app = dynamic_cast<SalomeApp_Application*>( session->activeApplication() );
1851   if ( !app )
1852     return;
1853
1854   LightApp_SelectionMgr* sm = app->selectionMgr();
1855
1856   // remove all filters from selection
1857   sm->clearFilters();
1858
1859   SALOME_View* vf = GetActiveView();
1860   if ( vf ) {
1861     if (!theIO.IsNull() && !vf->isVisible(theIO))
1862       Display(theIO);
1863     SALOME_Prs* prs = vf->CreatePrs( theIO.IsNull() ? 0 : theIO->getEntry() );
1864     vf->LocalSelection( prs, theMode );
1865     delete prs;  // delete presentation because displayer is its owner
1866   }
1867 }
1868
1869 //=================================================================
1870 /*!
1871  *  GEOM_Displayer::globalSelection
1872  *  Activate selection of CAD shapes without activisation of selection
1873  *  of their sub-shapes (without opened local context for OCC viewer)
1874  */
1875 //=================================================================
1876 void GEOM_Displayer::GlobalSelection( const int theMode, const bool update )
1877 {
1878   TColStd_MapOfInteger aModes;
1879   aModes.Add( theMode );
1880   GlobalSelection( aModes, update );
1881 }
1882
1883 //=================================================================
1884 /*!
1885  *  GEOM_Displayer::globalSelection
1886  *  Activate selection of CAD shapes without activisation of selection
1887  *  of their sub-shapes (without opened local context for OCC viewer)
1888  */
1889 //=================================================================
1890 void GEOM_Displayer::GlobalSelection( const TColStd_MapOfInteger& theModes,
1891                                       const bool update, const QList<int>* theSubShapes )
1892 {
1893   SUIT_Session* session = SUIT_Session::session();
1894   SalomeApp_Application* app = dynamic_cast<SalomeApp_Application*>( session->activeApplication() );
1895   if ( !app )
1896     return;
1897
1898   SALOME_View* vf = GetActiveView();
1899   if ( vf == 0 )
1900     return;
1901
1902   // Close local context
1903   vf->GlobalSelection( update );
1904
1905   // Set selection filters in accordance with current mode
1906   LightApp_SelectionMgr* sm = app->selectionMgr();
1907   if ( !sm )
1908     return;
1909
1910   // Remove from selection temporary objects if necessary
1911   if ( !theModes.Contains( GEOM_PREVIEW ) )
1912     clearTemporary( sm );
1913
1914   //@ aSel->ClearIndex();
1915
1916   sm->clearFilters();
1917
1918   // Remove filters from AIS_InteractiveContext
1919   Handle(AIS_InteractiveContext) ic;
1920   SOCC_Viewer* viewer = dynamic_cast<SOCC_Viewer*>( vf );
1921   if ( viewer )
1922     {
1923       ic = viewer->getAISContext();
1924       if ( !ic.IsNull() )
1925         ic->RemoveFilters();
1926     }
1927
1928   if ( theModes.Contains( GEOM_ALLOBJECTS ) )
1929     return;
1930
1931   SUIT_SelectionFilter* aFilter;
1932   if ( theModes.Extent() == 1 )
1933     {
1934       int aMode = TColStd_MapIteratorOfMapOfInteger( theModes ).Key();
1935
1936       if ( aMode == GEOM_COMPOUNDFILTER )
1937         aFilter = getComplexFilter( theSubShapes );
1938       else
1939         aFilter = getFilter( aMode );
1940     }
1941   else if ( theModes.Extent() > 1 )
1942     {
1943       TColStd_MapOfInteger aTopAbsModes;
1944       TColStd_MapIteratorOfMapOfInteger anIter( theModes );
1945       QList<SUIT_SelectionFilter*> aListOfFilters;
1946       for ( ; anIter.More(); anIter.Next() )
1947         {
1948           SUIT_SelectionFilter* aFilter;
1949           int aMode = anIter.Key();
1950           if ( aMode == GEOM_COMPOUNDFILTER )
1951             aFilter = getComplexFilter( theSubShapes );
1952           else
1953             aFilter = getFilter( aMode );
1954
1955           if ( aFilter )
1956             aListOfFilters.append( aFilter );
1957         }
1958
1959       aFilter = new GEOM_LogicalFilter( aListOfFilters, GEOM_LogicalFilter::LO_OR );
1960     }
1961   else
1962     return;
1963
1964   if ( aFilter )
1965     {
1966       sm->installFilter( aFilter );
1967       if ( !ic.IsNull() )
1968         {
1969           Handle(GEOM_OCCFilter) anOCCFilter = new GEOM_OCCFilter( sm );
1970           ic->AddFilter( anOCCFilter );
1971         }
1972     }
1973 }
1974
1975 //=================================================================
1976 /*!
1977  *  GEOM_Displayer::LocalSelection
1978  *  Activate selection of CAD shapes with activisation of selection
1979  *  of their sub-shapes (with opened local context for OCC viewer)
1980  */
1981 //=================================================================
1982 void GEOM_Displayer::LocalSelection( const SALOME_ListIO& theIOList, const int theMode )
1983 {
1984   SALOME_ListIteratorOfListIO Iter( theIOList );
1985   for ( ; Iter.More(); Iter.Next() )
1986     LocalSelection( Iter.Value(), theMode );
1987 }
1988
1989 //=================================================================
1990 /*!
1991  *  GEOM_Displayer::BeforeDisplay
1992  *  Called before displaying of pars. Close local context
1993  *  [ Reimplemented from SALOME_Displayer ]
1994  */
1995 //=================================================================
1996 void GEOM_Displayer::BeforeDisplay( SALOME_View* v, const SALOME_OCCPrs* )
1997 {
1998   SOCC_Viewer* vf = dynamic_cast<SOCC_Viewer*>( v );
1999   if ( vf )
2000   {
2001     Handle(AIS_InteractiveContext) ic = vf->getAISContext();
2002     if ( !ic.IsNull() )
2003     {
2004       if ( ic->HasOpenedContext() )
2005       ic->CloseAllContexts();
2006     }
2007   }
2008 }
2009
2010 void GEOM_Displayer::AfterDisplay( SALOME_View* v, const SALOME_OCCPrs* p )
2011 {
2012   UpdateColorScale(false,false);
2013 }
2014
2015 #if OCC_VERSION_LARGE > 0x06070000
2016 void GEOM_Displayer::BeforeErase( SALOME_View* v, const SALOME_OCCPrs* p )
2017 {
2018   LightApp_Displayer::BeforeErase( v, p );
2019   releaseTextures( p );
2020 }
2021 #endif
2022
2023 void GEOM_Displayer::AfterErase( SALOME_View* v, const SALOME_OCCPrs* p )
2024 {
2025   LightApp_Displayer::AfterErase( v, p );
2026   UpdateColorScale(false,false);
2027 }
2028
2029 //=================================================================
2030 /*!
2031  *  GEOM_Displayer::SetColor
2032  *  Set color for shape displaying. If it is equal -1 then default color is used.
2033  *  Available values are from Quantity_NameOfColor enumeration
2034  */
2035 //=================================================================
2036 void GEOM_Displayer::SetColor( const int color )
2037 {
2038   if ( color == -1 )
2039     UnsetColor();
2040   else
2041   {
2042     myColor = color;
2043     myShadingColor = Quantity_Color( (Quantity_NameOfColor)color );
2044   }
2045 }
2046
2047 int GEOM_Displayer::GetColor() const
2048 {
2049   return myColor;
2050 }
2051
2052 bool GEOM_Displayer::HasColor() const
2053 {
2054   return myColor != -1;
2055 }
2056
2057 void GEOM_Displayer::UnsetColor()
2058 {
2059   myColor = -1;
2060
2061   SUIT_ResourceMgr* resMgr = SUIT_Session::session()->resourceMgr();
2062   QColor col = resMgr->colorValue( "Geometry", "shading_color", QColor( 255, 0, 0 ) );
2063   myShadingColor = SalomeApp_Tools::color( col );
2064 }
2065
2066 //=================================================================
2067 /*!
2068  *  GEOM_Displayer::SetTransparency
2069  *  Set transparency for shape displaying.
2070  */
2071 //=================================================================
2072 double GEOM_Displayer::SetTransparency( const double transparency )
2073 {
2074   double aPrevTransparency = myTransparency;
2075   if ( transparency < 0 ) {
2076     UnsetTransparency();
2077   }
2078   else {
2079     myTransparency = transparency;
2080     myHasTransparency = true;
2081   }
2082   return aPrevTransparency;
2083 }
2084
2085 //=================================================================
2086 /*!
2087  *  GEOM_Displayer::GetTransparency
2088  *  Get transparency for shape displaying.
2089  */
2090 //=================================================================
2091 double GEOM_Displayer::GetTransparency() const
2092 {
2093   return myTransparency;
2094 }
2095
2096 //=================================================================
2097 /*!
2098  *  GEOM_Displayer::HasTransparency
2099  *  Check if transparency for shape displaying is set.
2100  */
2101 //=================================================================
2102 bool GEOM_Displayer::HasTransparency() const
2103 {
2104   return myHasTransparency;
2105 }
2106
2107 //=================================================================
2108 /*!
2109  *  GEOM_Displayer::UnsetTransparency
2110  *  Unset transparency for shape displaying.
2111  */
2112 //=================================================================
2113 double GEOM_Displayer::UnsetTransparency()
2114 {
2115   double aPrevTransparency = myTransparency;
2116   SUIT_ResourceMgr* resMgr = SUIT_Session::session()->resourceMgr();
2117   myTransparency = resMgr->integerValue("Geometry", "transparency", 0) / 100.;
2118   myHasTransparency = false;
2119   return aPrevTransparency;
2120 }
2121
2122
2123 //=================================================================
2124 /*!
2125  *  GEOM_Displayer::SetTexture
2126  *  Set color for shape displaying. If it is equal -1 then default color is used.
2127  *  Available values are from Quantity_NameOfColor enumeration
2128  */
2129 //=================================================================
2130 void GEOM_Displayer::SetTexture( const std::string& texureFileName )
2131 {
2132   if(texureFileName!="")
2133   {
2134     myTexture = texureFileName;
2135   }
2136 }
2137
2138 bool GEOM_Displayer::HasTexture() const
2139 {
2140   return myTexture != "";
2141 }
2142
2143 std::string GEOM_Displayer::GetTexture() const
2144 {
2145   return myTexture;
2146 }
2147
2148 //=================================================================
2149 /*!
2150  *  GEOM_Displayer::SetWidth
2151  *  Set width of shape displaying. If it is equal -1 then default width is used.
2152  */
2153 //=================================================================
2154 void GEOM_Displayer::SetWidth( const double width )
2155 {
2156   myWidth = width;
2157 }
2158
2159 double GEOM_Displayer::GetWidth() const
2160 {
2161   return myWidth;
2162 }
2163
2164 bool GEOM_Displayer::HasWidth() const
2165 {
2166   return myWidth != -1;
2167 }
2168
2169 void GEOM_Displayer::UnsetWidth()
2170 {
2171   myWidth = -1;
2172 }
2173
2174
2175 int GEOM_Displayer::GetIsosWidth() const
2176 {
2177   return myIsosWidth;
2178 }
2179
2180 void GEOM_Displayer::SetIsosWidth(const int width)
2181 {
2182   myIsosWidth = width;
2183 }
2184
2185 bool GEOM_Displayer::HasIsosWidth() const
2186 {
2187   return myIsosWidth != -1;
2188 }
2189
2190
2191 //=================================================================
2192 /*!
2193  *  GEOM_Displayer::SetToActivate
2194  *  This method is used for activisation/deactivisation of objects to be displayed
2195  */
2196 //=================================================================
2197 void GEOM_Displayer::SetToActivate( const bool toActivate )
2198 {
2199   myToActivate = toActivate;
2200 }
2201 bool GEOM_Displayer::ToActivate() const
2202 {
2203   return myToActivate;
2204 }
2205
2206 //=================================================================
2207 /*!
2208  *  GEOM_Displayer::clearTemporary
2209  *  Removes from selection temporary objects
2210  */
2211 //=================================================================
2212 void GEOM_Displayer::clearTemporary( LightApp_SelectionMgr* theSelMgr )
2213 {
2214   SALOME_ListIO selected, toSelect;
2215   theSelMgr->selectedObjects( selected );
2216
2217   for (  SALOME_ListIteratorOfListIO it( selected ) ; it.More(); it.Next() ) {
2218     Handle(SALOME_InteractiveObject) io = it.Value();
2219     if ( !io.IsNull() && io->hasEntry() && strncmp( io->getEntry(), "TEMP_", 5 ) != 0 )
2220       toSelect.Append( it.Value() );
2221   }
2222
2223   theSelMgr->setSelectedObjects( toSelect, true );
2224 }
2225
2226 void GEOM_Displayer::SetName( const char* theName )
2227 {
2228   myName = theName;
2229 }
2230
2231 void GEOM_Displayer::UnsetName()
2232 {
2233   myName = "";
2234 }
2235
2236 SalomeApp_Study* GEOM_Displayer::getStudy() const
2237 {
2238   return dynamic_cast<SalomeApp_Study*>( myApp->activeStudy() );
2239 }
2240
2241 void GEOM_Displayer::setIO( const Handle(SALOME_InteractiveObject)& theIO )
2242 {
2243   myIO = theIO;
2244 }
2245
2246 void GEOM_Displayer::setShape( const TopoDS_Shape& theShape )
2247 {
2248   myShape = theShape;
2249 }
2250
2251 void GEOM_Displayer::setFieldStepInfo( const GEOM::field_data_type theFieldDataType,
2252                                        const int theFieldDimension,
2253                                        const QList<QVariant>& theFieldStepData,
2254                                        const TCollection_AsciiString& theFieldStepName,
2255                                        const double theFieldStepRangeMin,
2256                                        const double theFieldStepRangeMax )
2257 {
2258   myFieldDataType = theFieldDataType;
2259   myFieldDimension = theFieldDimension;
2260   myFieldStepData = theFieldStepData;
2261   myFieldStepName = theFieldStepName;
2262   myFieldStepRangeMin = theFieldStepRangeMin;
2263   myFieldStepRangeMax = theFieldStepRangeMax;
2264 }
2265
2266 bool GEOM_Displayer::canBeDisplayed( const QString& entry, const QString& viewer_type ) const
2267 {
2268   _PTR(SObject) anObj = getStudy()->studyDS()->FindObjectID( (const char*)entry.toLatin1() );
2269   GEOM::GEOM_Object_var aGeomObj = GEOM::GEOM_Object::_narrow(GeometryGUI::ClientSObjectToObject(anObj)); // enable displaying of GEOM objects
2270   GEOM::GEOM_FieldStep_var aFieldStepObj = GEOM::GEOM_FieldStep::_narrow(GeometryGUI::ClientSObjectToObject(anObj)); // enable displaying of GEOM field steps
2271   GEOM::GEOM_Gen_var aCompObj = GEOM::GEOM_Gen::_narrow(GeometryGUI::ClientSObjectToObject(anObj)); // enable displaying of whole GEOM component
2272   return ( !CORBA::is_nil( aGeomObj ) || !CORBA::is_nil( aFieldStepObj ) || !CORBA::is_nil( aCompObj ) ) &&
2273          (viewer_type == SOCC_Viewer::Type() || viewer_type == SVTK_Viewer::Type());
2274 }
2275
2276 int GEOM_Displayer::SetDisplayMode( const int theMode )
2277 {
2278   int aPrevMode = myDisplayMode;
2279   if ( theMode != -1 ) {
2280     myDisplayMode = theMode;
2281     myHasDisplayMode = true;
2282   }
2283   else {
2284     UnsetDisplayMode();
2285   }
2286   return aPrevMode;
2287 }
2288
2289 int GEOM_Displayer::GetDisplayMode() const
2290 {
2291   return myDisplayMode;
2292 }
2293
2294 int GEOM_Displayer::UnsetDisplayMode()
2295 {
2296   int aPrevMode = myDisplayMode;
2297   SUIT_ResourceMgr* resMgr = SUIT_Session::session()->resourceMgr();
2298   myDisplayMode = resMgr->integerValue( "Geometry", "display_mode", 0 );
2299   myHasDisplayMode = false;
2300   return aPrevMode;
2301 }
2302
2303 bool GEOM_Displayer::HasDisplayMode() const
2304 {
2305   return myHasDisplayMode;
2306 }
2307
2308 SALOMEDS::Color GEOM_Displayer::getPredefinedUniqueColor()
2309 {
2310   static QList<QColor> colors;
2311
2312   if ( colors.isEmpty() ) {
2313
2314     for (int s = 0; s < 2 ; s++)
2315     {
2316       for (int v = 100; v >= 40; v = v - 20)
2317       {
2318         for (int h = 0; h < 359 ; h = h + 60)
2319         {
2320           colors.append(QColor::fromHsv(h, 255 - s * 127, v * 255 / 100));
2321         }
2322       }
2323     }
2324   }
2325
2326   static int currentColor = 0;
2327
2328   SALOMEDS::Color color;
2329   color.R = (double)colors[currentColor].red()   / 255.0;
2330   color.G = (double)colors[currentColor].green() / 255.0;
2331   color.B = (double)colors[currentColor].blue()  / 255.0;
2332
2333   currentColor = (currentColor+1) % colors.count();
2334
2335   return color;
2336 }
2337
2338 SALOMEDS::Color GEOM_Displayer::getUniqueColor( const QList<SALOMEDS::Color>& theReservedColors )
2339 {
2340   int aHue = -1;
2341   int aTolerance = 64;
2342   int anIterations = 0;
2343   int aPeriod = 5;
2344
2345   while( 1 )
2346   {
2347     anIterations++;
2348     if( anIterations % aPeriod == 0 )
2349     {
2350       aTolerance /= 2;
2351       if( aTolerance < 1 )
2352         break;
2353     }
2354     //std::cout << "Iteration N" << anIterations << " (tolerance=" << aTolerance << ")"<< std::endl;
2355
2356     aHue = (int)( 360.0 * rand() / RAND_MAX );
2357     //std::cout << "Hue = " << aHue << std::endl;
2358
2359     //std::cout << "Auto colors : ";
2360     bool ok = true;
2361     QList<SALOMEDS::Color>::const_iterator it = theReservedColors.constBegin();
2362     QList<SALOMEDS::Color>::const_iterator itEnd = theReservedColors.constEnd();
2363     for( ; it != itEnd; ++it )
2364     {
2365       SALOMEDS::Color anAutoColor = *it;
2366       QColor aQColor( (int)( anAutoColor.R * 255.0 ), (int)( anAutoColor.G * 255.0 ), (int)( anAutoColor.B * 255.0 ) );
2367
2368       int h, s, v;
2369       aQColor.getHsv( &h, &s, &v );
2370       //std::cout << h << " ";
2371       if( abs( h - aHue ) < aTolerance )
2372       {
2373         ok = false;
2374         //std::cout << "break (diff = " << abs( h - aHue ) << ")";
2375         break;
2376       }
2377     }
2378     //std::cout << std::endl;
2379
2380     if( ok )
2381       break;
2382   }
2383
2384   //std::cout << "Hue of the returned color = " << aHue << std::endl;
2385   QColor aColor;
2386   aColor.setHsv( aHue, 255, 255 );
2387
2388   SALOMEDS::Color aSColor;
2389   aSColor.R = (double)aColor.red() / 255.0;
2390   aSColor.G = (double)aColor.green() / 255.0;
2391   aSColor.B = (double)aColor.blue() / 255.0;
2392
2393   return aSColor;
2394 }
2395
2396 PropMap GEOM_Displayer::getObjectProperties( SalomeApp_Study* study,
2397                                              const QString& entry,
2398                                              SALOME_View* view )
2399 {
2400   // get default properties for the explicitly specified default view type
2401   PropMap propMap = GEOM_Displayer::getDefaultPropertyMap();
2402
2403   if ( study && view ) {
2404     SUIT_ViewModel* viewModel = dynamic_cast<SUIT_ViewModel*>( view );
2405     SUIT_ViewManager* viewMgr = ( viewModel != 0 ) ? viewModel->getViewManager() : 0;
2406     int viewId = ( viewMgr != 0 ) ? viewMgr->getGlobalId() : -1;
2407   
2408     if ( viewModel && viewId != -1 ) {
2409       // get properties from the study
2410       PropMap storedMap = study->getObjectPropMap( viewId, entry );
2411       // overwrite default properties from stored ones (that are specified)
2412       for ( int prop = GEOM::Visibility; prop <= GEOM::LastProperty; prop++ ) {
2413         if ( storedMap.contains( GEOM::propertyName( (GEOM::Property)prop ) ) )
2414           propMap.insert( GEOM::propertyName( (GEOM::Property)prop ), 
2415                           storedMap.value( GEOM::propertyName( (GEOM::Property)prop ) ) );
2416       }
2417       // ... specific processing for color
2418       // ... current implementation is to use same stored color for all aspects
2419       // ... (TODO) possible future improvements about free boundaries, standalone edges etc colors can be here
2420       if ( storedMap.contains( GEOM::propertyName( GEOM::Color ) ) ) {
2421         propMap.insert( GEOM::propertyName( GEOM::ShadingColor ),   storedMap.value( GEOM::propertyName( GEOM::Color ) ) );
2422         propMap.insert( GEOM::propertyName( GEOM::WireframeColor ), storedMap.value( GEOM::propertyName( GEOM::Color ) ) );
2423         propMap.insert( GEOM::propertyName( GEOM::LineColor ),      storedMap.value( GEOM::propertyName( GEOM::Color ) ) );
2424         propMap.insert( GEOM::propertyName( GEOM::FreeBndColor ),   storedMap.value( GEOM::propertyName( GEOM::Color ) ) );
2425         propMap.insert( GEOM::propertyName( GEOM::PointColor ),     storedMap.value( GEOM::propertyName( GEOM::Color ) ) );
2426       }
2427
2428       if ( !entry.isEmpty() ) {
2429         // get CORBA reference to geom object
2430         _PTR(SObject) SO( study->studyDS()->FindObjectID( entry.toStdString() ) );
2431         if ( SO ) {
2432           CORBA::Object_var object = GeometryGUI::ClientSObjectToObject( SO );
2433           if ( !CORBA::is_nil( object ) ) {
2434             GEOM::GEOM_Object_var geomObject = GEOM::GEOM_Object::_narrow( object );
2435             if ( !CORBA::is_nil( geomObject ) ) { // to check
2436               // check that geom object has color properly set
2437               bool hasColor = false;
2438               SALOMEDS::Color aSColor = getColor( geomObject, hasColor );
2439               // set color from geometry object (only once, if it is not yet set in GUI)
2440               // current implementation is to use same color for all aspects
2441               // (TODO) possible future improvements about free boundaries, standalone edges etc colors can be here
2442               if ( hasColor && !storedMap.contains( GEOM::propertyName( GEOM::Color ) ) ) {
2443                 QColor objColor = QColor::fromRgbF( aSColor.R, aSColor.G, aSColor.B );
2444                 propMap.insert( GEOM::propertyName( GEOM::ShadingColor ),   objColor );
2445                 propMap.insert( GEOM::propertyName( GEOM::WireframeColor ), objColor );
2446                 propMap.insert( GEOM::propertyName( GEOM::LineColor ),      objColor );
2447                 propMap.insert( GEOM::propertyName( GEOM::FreeBndColor ),   objColor );
2448                 propMap.insert( GEOM::propertyName( GEOM::PointColor ),     objColor );
2449               }
2450               // check that object has point marker properly set
2451               GEOM::marker_type mType = geomObject->GetMarkerType();
2452               GEOM::marker_size mSize = geomObject->GetMarkerSize();
2453               int mTextureId = geomObject->GetMarkerTexture();
2454               bool hasMarker = ( mType > GEOM::MT_NONE && mType < GEOM::MT_USER && mSize > GEOM::MS_NONE && mSize <= GEOM::MS_70 ) || 
2455                                ( mType == GEOM::MT_USER && mTextureId > 0 );
2456               // set point marker from geometry object (only once, if it is not yet set in GUI)
2457               if ( hasMarker && !storedMap.contains( GEOM::propertyName( GEOM::PointMarker ) ) ) {
2458                 if ( mType > GEOM::MT_NONE && mType < GEOM::MT_USER ) {
2459                   // standard type
2460                   propMap.insert( GEOM::propertyName( GEOM::PointMarker ),
2461                                   QString( "%1%2%3" ).arg( (int)mType ).arg( GEOM::subSectionSeparator() ).arg( (int)mSize ) );
2462                 }
2463                 else if ( mType == GEOM::MT_USER ) {
2464                   // custom texture
2465                   propMap.insert( GEOM::propertyName( GEOM::PointMarker ), QString::number( mTextureId ) );
2466                 }
2467               }
2468             }
2469           }
2470         }
2471       }
2472     }
2473   }
2474   return propMap;
2475 }
2476
2477 PropMap GEOM_Displayer::getDefaultPropertyMap()
2478 {
2479   PropMap propMap;
2480
2481   // get resource manager
2482   SUIT_ResourceMgr* resMgr = SUIT_Session::session()->resourceMgr();
2483
2484   // fill in the properties map with default values
2485
2486   // - visibility (false by default)
2487   propMap.insert( GEOM::propertyName( GEOM::Visibility ), false );
2488
2489   // - nb isos (take default value from preferences)
2490   propMap.insert( GEOM::propertyName( GEOM::NbIsos ),
2491                   QString( "%1%2%3" ).
2492                   arg( resMgr->integerValue( "Geometry", "iso_number_u", 1 ) ).
2493                   arg( GEOM::subSectionSeparator() ).
2494                   arg( resMgr->integerValue( "Geometry", "iso_number_v", 1 ) ) );
2495
2496   // - transparency (opacity = 1-transparency)
2497   propMap.insert( GEOM::propertyName( GEOM::Transparency ),
2498                   resMgr->integerValue( "Geometry", "transparency", 0 ) / 100. );
2499
2500   // - display mode (take default value from preferences)
2501   propMap.insert( GEOM::propertyName( GEOM::DisplayMode ),
2502                   resMgr->integerValue( "Geometry", "display_mode", 0 ) );
2503
2504   // - show edges direction flag (false by default)
2505   propMap.insert( GEOM::propertyName( GEOM::EdgesDirection ), false );
2506
2507   // - show vertices flag (false by default)
2508   propMap.insert( GEOM::propertyName( GEOM::Vertices ), false );
2509
2510   // - shading color (take default value from preferences)
2511   propMap.insert( GEOM::propertyName( GEOM::ShadingColor ),
2512                   colorFromResources( "shading_color", QColor( 255, 255, 0 ) ) );
2513
2514   // - wireframe color (take default value from preferences)
2515   propMap.insert( GEOM::propertyName( GEOM::WireframeColor ),
2516                   colorFromResources( "wireframe_color", QColor( 255, 255, 0 ) ) );
2517
2518   // - standalone edges color (take default value from preferences)
2519   propMap.insert( GEOM::propertyName( GEOM::LineColor ),
2520                   colorFromResources( "line_color", QColor( 255, 0, 0 ) ) );
2521
2522   // - free boundaries color (take default value from preferences)
2523   propMap.insert( GEOM::propertyName( GEOM::FreeBndColor ),
2524                   colorFromResources( "free_bound_color", QColor( 0, 255, 0 ) ) );
2525
2526   // - points color (take default value from preferences)
2527   propMap.insert( GEOM::propertyName( GEOM::PointColor ),
2528                   colorFromResources( "point_color", QColor( 255, 255, 0 ) ) );
2529
2530   // - isos color (take default value from preferences)
2531   propMap.insert( GEOM::propertyName( GEOM::IsosColor ),
2532                   colorFromResources( "isos_color", QColor( 200, 200, 200 ) ) );
2533
2534   // - outlines color (take default value from preferences)
2535   propMap.insert( GEOM::propertyName( GEOM::OutlineColor ),
2536                   colorFromResources( "edges_in_shading_color", QColor( 180, 180, 180 ) ) );
2537
2538   // - deflection coefficient (take default value from preferences)
2539   propMap.insert( GEOM::propertyName( GEOM::Deflection ),
2540                   resMgr->doubleValue( "Geometry", "deflection_coeff", 0.001 ) );
2541
2542   // - material (take default value from preferences)
2543   Material_Model material;
2544   material.fromResources( resMgr->stringValue( "Geometry", "material", "Plastic" ) );
2545   propMap.insert( GEOM::propertyName( GEOM::Material ), material.toProperties() );
2546
2547   // - edge width (take default value from preferences)
2548   propMap.insert( GEOM::propertyName( GEOM::LineWidth ),
2549                   resMgr->integerValue( "Geometry", "edge_width", 1 ) );
2550
2551   // - isos width (take default value from preferences)
2552   propMap.insert( GEOM::propertyName( GEOM::IsosWidth ),
2553                   resMgr->integerValue( "Geometry", "isolines_width", 1 ) );
2554
2555   // - point marker (take default value from preferences)
2556   propMap.insert( GEOM::propertyName( GEOM::PointMarker ),
2557                   QString( "%1%2%3" ).
2558                   arg( resMgr->integerValue( "Geometry", "type_of_marker", 1 ) + 1 ).
2559                   arg( GEOM::subSectionSeparator() ).
2560                   arg( resMgr->integerValue( "Geometry", "marker_scale", 1 ) ) );
2561
2562   // - top-level flag (false by default)
2563   propMap.insert( GEOM::propertyName( GEOM::TopLevel ), false );
2564
2565   return propMap;
2566 }
2567
2568 SALOMEDS::Color GEOM_Displayer::getColor(GEOM::GEOM_Object_var theGeomObject, bool& hasColor) {
2569   SALOMEDS::Color aSColor;
2570   hasColor = false;
2571
2572   SUIT_Session* session = SUIT_Session::session();
2573   SalomeApp_Application* app = dynamic_cast<SalomeApp_Application*>( session->activeApplication() );
2574
2575   if ( app && !theGeomObject->_is_nil()) {
2576     SalomeApp_Study* study = dynamic_cast<SalomeApp_Study*>( app->activeStudy() );
2577
2578     if ( study ) {
2579       _PTR(Study) aStudy = study->studyDS();
2580       aSColor = theGeomObject->GetColor();
2581       hasColor = aSColor.R >= 0 && aSColor.G >= 0 && aSColor.B >= 0;
2582       if ( !hasColor ) {
2583 #ifdef GENERAL_AUTOCOLOR // auto-color for all sub-shapes
2584         bool general_autocolor = true;
2585 #else                    // auto-color for groups only
2586         bool general_autocolor = false;
2587 #endif                   // GENERAL_AUTOCOLOR
2588         if ( general_autocolor || theGeomObject->GetType() == GEOM_GROUP ) {
2589           GEOM::GEOM_Object_var aMainObject = theGeomObject->GetMainShape();
2590           if ( !CORBA::is_nil( aMainObject ) && aMainObject->GetAutoColor() ) {
2591 #ifdef SIMPLE_AUTOCOLOR  // simplified algorithm for auto-colors
2592             aSColor = getPredefinedUniqueColor();
2593             hasColor = true;
2594 #else                    // old algorithm  for auto-colors
2595             QList<SALOMEDS::Color> aReservedColors;
2596             CORBA::String_var IOR = app->orb()->object_to_string( aMainObject );
2597             _PTR(SObject) aMainSObject( aStudy->FindObjectIOR( IOR.in() ) );
2598             if ( aMainSObject ) {
2599               _PTR(ChildIterator) it( aStudy->NewChildIterator( aMainSObject ) );
2600               for ( ; it->More(); it->Next() ) {
2601                 _PTR(SObject) aChildSObject( it->Value() );
2602                 GEOM::GEOM_Object_var aChildObject =
2603                   GEOM::GEOM_Object::_narrow(GeometryGUI::ClientSObjectToObject(aChildSObject));
2604                 if ( CORBA::is_nil( aChildObject ) )
2605                   continue;
2606
2607                 SALOMEDS::Color aReservedColor = aChildObject->GetColor();
2608                 if ( aReservedColor.R >= 0 && aReservedColor.G >= 0 && aReservedColor.B >= 0 )
2609                   aReservedColors.append( aReservedColor );
2610               }
2611             }
2612             aSColor = getUniqueColor( aReservedColors );
2613             hasColor = true;
2614 #endif                   // SIMPLE_AUTOCOLOR
2615           }
2616         }
2617       }
2618     }
2619   }
2620   return aSColor;
2621 }
2622
2623
2624 void GEOM_Displayer::EraseWithChildren(const Handle(SALOME_InteractiveObject)& theIO,
2625                                        const bool eraseOnlyChildren) {
2626   SalomeApp_Application* app = dynamic_cast< SalomeApp_Application* >( SUIT_Session::session()->activeApplication() );
2627   if ( !app )
2628     return;
2629
2630   SalomeApp_Study* appStudy = dynamic_cast<SalomeApp_Study*>( app->activeStudy() );
2631   if ( !appStudy )
2632     return;
2633
2634   LightApp_DataObject* parent = appStudy->findObjectByEntry(theIO->getEntry());
2635
2636   if( !parent)
2637     return;
2638
2639   // Erase from all views
2640   QList<SALOME_View*> views;
2641   SALOME_View* view;
2642   ViewManagerList vmans = app->viewManagers();
2643   SUIT_ViewManager* vman;
2644   foreach ( vman, vmans ) {
2645     SUIT_ViewModel* vmod = vman->getViewModel();
2646     view = dynamic_cast<SALOME_View*> ( vmod );
2647     if ( view )
2648       views.append( view );
2649   }
2650
2651   if( views.count() == 0 )
2652     return;
2653
2654   //Erase childrens w/o update views
2655   DataObjectList listObj = parent->children( true );
2656   SUIT_DataObject* obj;
2657   foreach( obj, listObj ) {
2658     LightApp_DataObject* l_obj = dynamic_cast<LightApp_DataObject*>(obj);
2659     if(l_obj)
2660       foreach ( view, views ) {
2661       Handle(SALOME_InteractiveObject) anIO =
2662         new SALOME_InteractiveObject(qPrintable(l_obj->entry()), "GEOM", "");
2663       Erase(anIO, false, false, view);
2664     }
2665   }
2666
2667   //Erase parent with view update or repaint views
2668   foreach ( view, views ) {
2669     if(!eraseOnlyChildren)
2670       Erase(theIO, false, true, view);
2671     else
2672       view->Repaint();
2673   }
2674 }
2675
2676 void GEOM_Displayer::readFieldStepInfo( GEOM::GEOM_FieldStep_var theGeomFieldStep )
2677 {
2678   if( theGeomFieldStep->_is_nil() )
2679     return;
2680
2681   GEOM::GEOM_Field_var aGeomField = theGeomFieldStep->GetField();
2682   if( aGeomField->_is_nil() )
2683     return;
2684
2685   GEOM::GEOM_Object_var aGeomFieldShape = aGeomField->GetShape();
2686   if( aGeomFieldShape->_is_nil() )
2687     return;
2688
2689   TCollection_AsciiString aFieldStepName( theGeomFieldStep->GetName() );
2690   TCollection_AsciiString aFieldName( aGeomField->GetName() );
2691   TCollection_AsciiString aShapeName( aGeomFieldShape->GetName() );
2692
2693   aFieldStepName = aShapeName + "\n" + aFieldName + "\n" + aFieldStepName;
2694
2695   GEOM::field_data_type aFieldDataType = aGeomField->GetDataType();
2696
2697   int aFieldDimension = aGeomField->GetDimension();
2698
2699   GEOM::string_array_var aFieldComponents = aGeomField->GetComponents();
2700   int aFieldNbComponents = aFieldComponents->length();
2701
2702   QList<QVariant> aFieldStepData;
2703   if( aFieldDataType == GEOM::FDT_Bool )
2704   {
2705     GEOM::GEOM_BoolFieldStep_var aGeomBoolFieldStep = GEOM::GEOM_BoolFieldStep::_narrow( theGeomFieldStep );
2706     if ( !aGeomBoolFieldStep->_is_nil() )
2707     {
2708       GEOM::short_array_var aValues = aGeomBoolFieldStep->GetValues();
2709       for( size_t i = 0, n = aValues->length(); i < n; i++ )
2710         aFieldStepData << (bool)aValues[i];
2711     }
2712   }
2713   else if( aFieldDataType == GEOM::FDT_Int )
2714   {
2715     GEOM::GEOM_IntFieldStep_var aGeomIntFieldStep = GEOM::GEOM_IntFieldStep::_narrow( theGeomFieldStep );
2716     if ( !aGeomIntFieldStep->_is_nil() )
2717     {
2718       GEOM::ListOfLong_var aValues = aGeomIntFieldStep->GetValues();
2719       for( size_t i = 0, n = aValues->length(); i < n; i++ )
2720         aFieldStepData << (qlonglong)aValues[i];
2721     }
2722   }
2723   else if( aFieldDataType == GEOM::FDT_Double )
2724   {
2725     GEOM::GEOM_DoubleFieldStep_var aGeomDoubleFieldStep = GEOM::GEOM_DoubleFieldStep::_narrow( theGeomFieldStep );
2726     if ( !aGeomDoubleFieldStep->_is_nil() )
2727     {
2728       GEOM::ListOfDouble_var aValues = aGeomDoubleFieldStep->GetValues();
2729       for( size_t i = 0, n = aValues->length(); i < n; i++ )
2730         aFieldStepData << (double)aValues[i];
2731     }
2732   }
2733   else if( aFieldDataType == GEOM::FDT_String )
2734   {
2735     GEOM::GEOM_StringFieldStep_var aGeomStringFieldStep = GEOM::GEOM_StringFieldStep::_narrow( theGeomFieldStep );
2736     if ( !aGeomStringFieldStep->_is_nil() )
2737     {
2738       GEOM::string_array_var aValues = aGeomStringFieldStep->GetValues();
2739       for( size_t i = 0, n = aValues->length(); i < n; i++ )
2740         aFieldStepData << QString( aValues[i] );
2741     }
2742   }
2743
2744   double aFieldStepRangeMin = 0, aFieldStepRangeMax = 0;
2745   aFieldStepData = groupFieldData( aFieldStepData,
2746                                    aFieldNbComponents,
2747                                    aFieldDataType == GEOM::FDT_String,
2748                                    aFieldStepRangeMin,
2749                                    aFieldStepRangeMax );
2750
2751   setFieldStepInfo( aFieldDataType,
2752                     aFieldDimension,
2753                     aFieldStepData,
2754                     aFieldStepName,
2755                     aFieldStepRangeMin,
2756                     aFieldStepRangeMax );
2757 }
2758
2759 QList<QVariant> GEOM_Displayer::groupFieldData( const QList<QVariant>& theFieldStepData,
2760                                                 const int theFieldNbComponents,
2761                                                 const bool theIsString,
2762                                                 double& theFieldStepRangeMin,
2763                                                 double& theFieldStepRangeMax )
2764 {
2765   QList<QVariant> aResultList;
2766   theFieldStepRangeMin = 0;
2767   theFieldStepRangeMax = 0;
2768
2769   if( theFieldStepData.isEmpty() || theFieldNbComponents < 1 )
2770     return aResultList;
2771
2772   int aNbSubShapes = theFieldStepData.count() / theFieldNbComponents;
2773
2774   QList<QVariant> aGroupedList;
2775
2776   bool anIsBoolean = false;
2777   for( int aSubShape = 0; aSubShape < aNbSubShapes; aSubShape++ )
2778   {
2779     double aNorm = 0;
2780     QStringList aStringList;
2781
2782     int aBaseIndex = aSubShape * theFieldNbComponents;
2783     for( int aComponent = 0; aComponent < theFieldNbComponents; aComponent++ )
2784     {
2785       int anIndex = aComponent + aBaseIndex;
2786
2787       const QVariant& aVariant = theFieldStepData[ anIndex ];
2788       if( theIsString )
2789       {
2790         if( aVariant.type() == QVariant::String )
2791           aStringList << aVariant.toString();
2792       }
2793       else
2794       {
2795         double aValue = 0;
2796         if( aVariant.type() == QVariant::Bool )
2797         {
2798           aValue = aVariant.toBool() ? 1.0 : 0.0;
2799           aNorm += aValue;
2800           anIsBoolean = true;
2801         }
2802         else
2803         {
2804           if( aVariant.type() == QVariant::LongLong )
2805             aValue = double( aVariant.toLongLong() );
2806           else if( aVariant.type() == QVariant::Double )
2807             aValue = aVariant.toDouble();
2808           aNorm += aValue * aValue;
2809         }
2810       }
2811     }
2812
2813     if( theIsString )
2814       aGroupedList << aStringList.join( "\n" );
2815     else
2816     {
2817       if( anIsBoolean )
2818         aNorm /= theFieldNbComponents;
2819       else
2820         aNorm = pow( aNorm, 0.5 );
2821
2822       if( aGroupedList.isEmpty() )
2823         theFieldStepRangeMin = theFieldStepRangeMax = aNorm;
2824       else
2825       {
2826         theFieldStepRangeMin = Min( theFieldStepRangeMin, aNorm );
2827         theFieldStepRangeMax = Max( theFieldStepRangeMax, aNorm );
2828       }
2829
2830       aGroupedList << aNorm;
2831     }
2832   }
2833
2834   if( anIsBoolean )
2835   {
2836     theFieldStepRangeMin = 0.0;
2837     theFieldStepRangeMax = 1.0;
2838   }
2839
2840   SUIT_Session* session = SUIT_Session::session();
2841   SUIT_ResourceMgr* resMgr = session->resourceMgr();
2842   Standard_Integer aNbIntervals = resMgr->integerValue( "Geometry", "scalar_bar_nb_intervals", 20 );
2843
2844   QListIterator<QVariant> anIter( aGroupedList );
2845   while( anIter.hasNext() )
2846   {
2847     const QVariant& aVariant = anIter.next();
2848     if( theIsString )
2849       aResultList << aVariant;
2850     else
2851     {
2852       QColor aQColor;
2853       Quantity_Color aColor;
2854       if( FindColor( aVariant.toDouble(), theFieldStepRangeMin, theFieldStepRangeMax, anIsBoolean ? 2 : aNbIntervals, aColor ) )
2855         aQColor = QColor::fromRgbF( aColor.Red(), aColor.Green(), aColor.Blue() );
2856       aResultList << aQColor;
2857     }
2858   }
2859   return aResultList;
2860 }
2861
2862 // Note: the method is copied from Aspect_ColorScale class
2863 Standard_Integer GEOM_Displayer::HueFromValue( const Standard_Integer aValue,
2864                                                const Standard_Integer aMin,
2865                                                const Standard_Integer aMax )
2866 {
2867   Standard_Integer minLimit( 0 ), maxLimit( 230 );
2868
2869   Standard_Integer aHue = maxLimit;
2870   if ( aMin != aMax )
2871     aHue = (Standard_Integer)( maxLimit - ( maxLimit - minLimit ) * ( aValue - aMin ) / ( aMax - aMin ) );
2872
2873   aHue = Min( Max( minLimit, aHue ), maxLimit );
2874
2875   return aHue;
2876 }
2877
2878 // Note: the method is copied from Aspect_ColorScale class
2879 Standard_Boolean GEOM_Displayer::FindColor( const Standard_Real aValue, 
2880                                             const Standard_Real aMin,
2881                                             const Standard_Real aMax,
2882                                             const Standard_Integer ColorsCount,
2883                                             Quantity_Color& aColor )
2884 {
2885   if( aValue<aMin || aValue>aMax || aMax<aMin )
2886     return Standard_False;
2887
2888   else
2889   {
2890     Standard_Real IntervNumber = 0;
2891     if( aValue<aMin )
2892       IntervNumber = 0;
2893     else if( aValue>aMax )
2894       IntervNumber = ColorsCount-1;
2895     else if( Abs( aMax-aMin ) > Precision::Approximation() )
2896       IntervNumber = Floor( Standard_Real( ColorsCount ) * ( aValue - aMin ) / ( aMax - aMin ) ); // 'Ceiling' replaced with 'Floor'
2897
2898     Standard_Integer Interv = Standard_Integer( IntervNumber );
2899
2900     aColor = Quantity_Color( HueFromValue( Interv, 0, ColorsCount - 1 ), 1.0, 1.0, Quantity_TOC_HLS );
2901
2902     return Standard_True;
2903   } 
2904 }
2905
2906 void GEOM_Displayer::UpdateColorScale( const bool theIsRedisplayFieldSteps, const bool updateViewer ) 
2907 {
2908   SalomeApp_Study* aStudy = dynamic_cast<SalomeApp_Study*>( myApp->activeStudy() );
2909   if( !aStudy )
2910     return;
2911
2912   SOCC_Viewer* aViewModel = dynamic_cast<SOCC_Viewer*>( GetActiveView() );
2913   if( !aViewModel )
2914     return;
2915
2916   Handle(V3d_Viewer) aViewer = aViewModel->getViewer3d();
2917   if( aViewer.IsNull() )
2918     return;
2919
2920   aViewer->InitActiveViews();
2921   if( !aViewer->MoreActiveViews() )
2922     return;
2923
2924   Handle(V3d_View) aView = aViewer->ActiveView();
2925   if( aView.IsNull() )
2926     return;
2927
2928   Standard_Boolean anIsDisplayColorScale = Standard_False;
2929   TCollection_AsciiString aColorScaleTitle;
2930   Standard_Real aColorScaleMin = 0, aColorScaleMax = 0;
2931   Standard_Boolean anIsBoolean = Standard_False;
2932
2933   SALOME_ListIO aSelectedObjects;
2934   myApp->selectionMgr()->selectedObjects( aSelectedObjects );
2935   if( aSelectedObjects.Extent() == 1 )
2936   {
2937     Handle(SALOME_InteractiveObject) anIO = aSelectedObjects.First();
2938     if( !anIO.IsNull() )
2939     {
2940       SOCC_Prs* aPrs = dynamic_cast<SOCC_Prs*>( aViewModel->CreatePrs( anIO->getEntry() ) );
2941       if( aPrs )
2942       {
2943         AIS_ListOfInteractive aList;
2944         aPrs->GetObjects( aList );
2945         AIS_ListIteratorOfListOfInteractive anIter( aList );
2946         for( ; anIter.More(); anIter.Next() )
2947         {
2948           Handle(GEOM_AISShape) aShape = Handle(GEOM_AISShape)::DownCast( anIter.Value() );
2949           if( !aShape.IsNull() )
2950           {
2951             GEOM::field_data_type aFieldDataType;
2952             int aFieldDimension;
2953             QList<QVariant> aFieldStepData;
2954             TCollection_AsciiString aFieldStepName;
2955             double aFieldStepRangeMin, aFieldStepRangeMax;
2956             aShape->getFieldStepInfo( aFieldDataType,
2957                                       aFieldDimension,
2958                                       aFieldStepData,
2959                                       aFieldStepName,
2960                                       aFieldStepRangeMin,
2961                                       aFieldStepRangeMax );
2962             if( !aFieldStepData.isEmpty() && aFieldDataType != GEOM::FDT_String )
2963             {
2964               anIsDisplayColorScale = Standard_True;
2965               aColorScaleTitle = aFieldStepName;
2966               aColorScaleMin = aFieldStepRangeMin;
2967               aColorScaleMax = aFieldStepRangeMax;
2968               anIsBoolean = aFieldDataType == GEOM::FDT_Bool;
2969             }
2970           }
2971         }
2972       }
2973     }
2974   }
2975
2976   if( anIsDisplayColorScale )
2977   {
2978     Handle(Aspect_ColorScale) aColorScale = aView->ColorScale();
2979     if( !aColorScale.IsNull() )
2980     {
2981       SUIT_Session* session = SUIT_Session::session();
2982       SUIT_ResourceMgr* resMgr = session->resourceMgr();
2983
2984       Standard_Real anXPos = resMgr->doubleValue( "Geometry", "scalar_bar_x_position", 0.05 );
2985       Standard_Real anYPos = resMgr->doubleValue( "Geometry", "scalar_bar_y_position", 0.1 );
2986       Standard_Real aWidth = resMgr->doubleValue( "Geometry", "scalar_bar_width", 0.2 );
2987       Standard_Real aHeight = resMgr->doubleValue( "Geometry", "scalar_bar_height", 0.5 );
2988       Standard_Integer aTextHeight = resMgr->integerValue( "Geometry", "scalar_bar_text_height", 14 );
2989       Standard_Integer aNbIntervals = resMgr->integerValue( "Geometry", "scalar_bar_nb_intervals", 20 );
2990  
2991       aColorScale->SetXPosition( anXPos );
2992       aColorScale->SetYPosition( anYPos );
2993       aColorScale->SetWidth( aWidth );
2994       aColorScale->SetHeight( aHeight );
2995
2996       aColorScale->SetTextHeight( aTextHeight );
2997       aColorScale->SetNumberOfIntervals( anIsBoolean ? 2 : aNbIntervals );
2998
2999       aColorScale->SetTitle( aColorScaleTitle );
3000       aColorScale->SetRange( aColorScaleMin, aColorScaleMax );
3001     }
3002     if( !aView->ColorScaleIsDisplayed() )
3003       aView->ColorScaleDisplay();
3004   }
3005   else
3006   {
3007     if( aView->ColorScaleIsDisplayed() )
3008       aView->ColorScaleErase();
3009   }
3010
3011   if( theIsRedisplayFieldSteps )
3012   {
3013     _PTR(Study) aStudyDS = aStudy->studyDS();
3014     QList<SUIT_ViewManager*> vmList;
3015     myApp->viewManagers( vmList );
3016     for( QList<SUIT_ViewManager*>::Iterator vmIt = vmList.begin(); vmIt != vmList.end(); vmIt++ )
3017     {
3018       if( SUIT_ViewManager* aViewManager = *vmIt )
3019       {
3020         const ObjMap anObjects = aStudy->getObjectMap( aViewManager->getGlobalId() );
3021         for( ObjMap::ConstIterator objIt = anObjects.begin(); objIt != anObjects.end(); objIt++ )
3022         {
3023           _PTR(SObject) aSObj( aStudyDS->FindObjectID( objIt.key().toLatin1().constData() ) );
3024           if( aSObj )
3025           {
3026             CORBA::Object_var anObject = GeometryGUI::ClientSObjectToObject( aSObj );
3027             if( !CORBA::is_nil( anObject ) )
3028             {
3029               GEOM::GEOM_FieldStep_var aFieldStep = GEOM::GEOM_FieldStep::_narrow( anObject );
3030               if( !aFieldStep->_is_nil() )
3031               {
3032                 CORBA::String_var aStepEntry = aFieldStep->GetStudyEntry();
3033                 Handle(SALOME_InteractiveObject) aStepIO =
3034                   new SALOME_InteractiveObject( aStepEntry.in(), "GEOM", "TEMP_IO" );
3035                 Redisplay( aStepIO, false, false );
3036               }
3037             }
3038           }
3039         }
3040       }
3041     }
3042   }
3043   if(updateViewer)
3044     UpdateViewer();
3045 }