]> SALOME platform Git repositories - modules/smesh.git/blob - src/OBJECT/SMESH_DeviceActor.cxx
Salome HOME
Bug IPAL19360 - Qt4 porting. Activation of functionality ?Modification/Mesh pass...
[modules/smesh.git] / src / OBJECT / SMESH_DeviceActor.cxx
1 //  SMESH OBJECT : interactive object for SMESH visualization
2 //
3 //  Copyright (C) 2003  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 //  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS 
5 // 
6 //  This library is free software; you can redistribute it and/or 
7 //  modify it under the terms of the GNU Lesser General Public 
8 //  License as published by the Free Software Foundation; either 
9 //  version 2.1 of the License. 
10 // 
11 //  This library is distributed in the hope that it will be useful, 
12 //  but WITHOUT ANY WARRANTY; without even the implied warranty of 
13 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU 
14 //  Lesser General Public License for more details. 
15 // 
16 //  You should have received a copy of the GNU Lesser General Public 
17 //  License along with this library; if not, write to the Free Software 
18 //  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA 
19 // 
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22 //
23 //
24 //  File   : SMESH_DeviceActor.cxx
25 //  Author : 
26 //  Module : SMESH
27 //  $Header$
28
29
30 #include "SMESH_DeviceActor.h"
31 #include "SMESH_ExtractGeometry.h"
32 #include "SMESH_ControlsDef.hxx"
33 #include "SMESH_ActorUtils.h"
34 #include "VTKViewer_CellLocationsArray.h"
35
36 #include <VTKViewer_Transform.h>
37 #include <VTKViewer_TransformFilter.h>
38 #include <VTKViewer_ExtractUnstructuredGrid.h>
39
40 // VTK Includes
41 #include <vtkObjectFactory.h>
42 #include <vtkShrinkFilter.h>
43 #include <vtkShrinkPolyData.h>
44
45 #include <vtkProperty.h>
46 #include <vtkPolyData.h>
47 #include <vtkMergeFilter.h>
48 #include <vtkPolyDataMapper.h>
49 #include <vtkUnstructuredGrid.h>
50
51 #include <vtkScalarBarActor.h>
52 #include <vtkLookupTable.h>
53 #include <vtkDoubleArray.h>
54 #include <vtkCellData.h>
55
56 #include <vtkCell.h>
57 #include <vtkIdList.h>
58 #include <vtkCellArray.h>
59 #include <vtkUnsignedCharArray.h>
60
61 #include <vtkImplicitBoolean.h>
62 #include <vtkPassThroughFilter.h>
63
64 #include "utilities.h"
65
66 #ifdef _DEBUG_
67 static int MYDEBUG = 0;
68 #else
69 static int MYDEBUG = 0;
70 #endif
71
72 using namespace std;
73
74
75 vtkStandardNewMacro(SMESH_DeviceActor);
76
77
78 SMESH_DeviceActor
79 ::SMESH_DeviceActor()
80 {
81   if(MYDEBUG) MESSAGE("SMESH_DeviceActor - "<<this);
82
83   myIsShrunk = false;
84   myIsShrinkable = false;
85   myRepresentation = eSurface;
86
87   myProperty = vtkProperty::New();
88   myMapper = vtkPolyDataMapper::New();
89
90   vtkMapper::GetResolveCoincidentTopologyPolygonOffsetParameters(myPolygonOffsetFactor,
91                                                                  myPolygonOffsetUnits);
92
93   myMapper->UseLookupTableScalarRangeOn();
94   myMapper->SetColorModeToMapScalars();
95
96   myShrinkFilter = vtkShrinkFilter::New();
97
98   myStoreClippingMapping = false;
99
100   myExtractGeometry = SMESH_ExtractGeometry::New();
101   myExtractGeometry->SetReleaseDataFlag(true);
102   myIsImplicitFunctionUsed = false;
103
104   myExtractUnstructuredGrid = VTKViewer_ExtractUnstructuredGrid::New();
105     
106   myMergeFilter = vtkMergeFilter::New();
107
108   myGeomFilter = VTKViewer_GeometryFilter::New();
109
110   myTransformFilter = VTKViewer_TransformFilter::New();
111
112   for(int i = 0; i < 6; i++)
113     myPassFilter.push_back(vtkPassThroughFilter::New());
114 }
115
116
117 SMESH_DeviceActor
118 ::~SMESH_DeviceActor()
119 {
120   if(MYDEBUG) MESSAGE("~SMESH_DeviceActor - "<<this);
121
122   myProperty->Delete();
123
124   myMapper->Delete();
125
126   myShrinkFilter->Delete();
127
128   myExtractUnstructuredGrid->Delete();
129
130   myMergeFilter->Delete();
131
132   myGeomFilter->Delete();
133
134   myExtractGeometry->Delete();
135
136   myTransformFilter->Delete();
137
138   for(int i = 0, iEnd = myPassFilter.size(); i < iEnd; i++){
139     myPassFilter[i]->Delete();
140   }
141 }
142
143
144 void
145 SMESH_DeviceActor
146 ::SetStoreGemetryMapping(bool theStoreMapping)
147 {
148   myGeomFilter->SetStoreMapping(theStoreMapping);
149   SetStoreClippingMapping(theStoreMapping);
150 }
151
152
153 void
154 SMESH_DeviceActor
155 ::SetStoreClippingMapping(bool theStoreMapping)
156 {
157   myStoreClippingMapping = theStoreMapping;
158   myExtractGeometry->SetStoreMapping(theStoreMapping && myIsImplicitFunctionUsed);
159   SetStoreIDMapping(theStoreMapping);
160 }
161
162
163 void
164 SMESH_DeviceActor
165 ::SetStoreIDMapping(bool theStoreMapping)
166 {
167   myExtractUnstructuredGrid->SetStoreMapping(theStoreMapping);
168 }
169
170
171 void 
172 SMESH_DeviceActor
173 ::Init(TVisualObjPtr theVisualObj, 
174        vtkImplicitBoolean* theImplicitBoolean)
175 {
176   myVisualObj = theVisualObj;
177   myExtractGeometry->SetImplicitFunction(theImplicitBoolean);
178   SetUnstructuredGrid(myVisualObj->GetUnstructuredGrid());
179 }
180
181
182 void
183 SMESH_DeviceActor
184 ::SetImplicitFunctionUsed(bool theIsImplicitFunctionUsed)
185 {
186   int anId = 0;
187   if(theIsImplicitFunctionUsed)
188     myPassFilter[ anId ]->SetInput( myExtractGeometry->GetOutput() );
189   else
190     myPassFilter[ anId ]->SetInput( myMergeFilter->GetOutput() );
191     
192   myIsImplicitFunctionUsed = theIsImplicitFunctionUsed;
193   SetStoreClippingMapping(myStoreClippingMapping);
194 }
195
196
197 void
198 SMESH_DeviceActor
199 ::SetUnstructuredGrid(vtkUnstructuredGrid* theGrid)
200 {
201   if(theGrid){
202     //myIsShrinkable = theGrid->GetNumberOfCells() > 10;
203     myIsShrinkable = true;
204
205     myExtractUnstructuredGrid->SetInput(theGrid);
206
207     myMergeFilter->SetGeometry(myExtractUnstructuredGrid->GetOutput());
208
209     myExtractGeometry->SetInput(myMergeFilter->GetOutput());
210
211     int anId = 0;
212     SetImplicitFunctionUsed(myIsImplicitFunctionUsed);
213     myPassFilter[ anId + 1]->SetInput( myPassFilter[ anId ]->GetOutput() );
214     
215     anId++; // 1
216     myGeomFilter->SetInput( myPassFilter[ anId ]->GetOutput() );
217
218     anId++; // 2
219     myPassFilter[ anId ]->SetInput( myGeomFilter->GetOutput() ); 
220     myPassFilter[ anId + 1 ]->SetInput( myPassFilter[ anId ]->GetOutput() );
221
222     anId++; // 3
223     myTransformFilter->SetInput( myPassFilter[ anId ]->GetPolyDataOutput() );
224     myTransformFilter->SetInput( myPassFilter[ anId ]->GetPolyDataOutput() );
225
226     anId++; // 4
227     myPassFilter[ anId ]->SetInput( myTransformFilter->GetOutput() );
228     myPassFilter[ anId + 1 ]->SetInput( myPassFilter[ anId ]->GetOutput() );
229     myPassFilter[ anId ]->SetInput( myTransformFilter->GetOutput() );
230     myPassFilter[ anId + 1 ]->SetInput( myPassFilter[ anId ]->GetOutput() );
231
232     anId++; // 5
233     myMapper->SetInput( myPassFilter[ anId ]->GetPolyDataOutput() );
234     myMapper->SetInput( myPassFilter[ anId ]->GetPolyDataOutput() );
235
236     vtkLODActor::SetMapper( myMapper );
237     Modified();
238   }
239 }
240
241
242 VTKViewer_ExtractUnstructuredGrid* 
243 SMESH_DeviceActor
244 ::GetExtractUnstructuredGrid()
245 {
246   return myExtractUnstructuredGrid;
247 }
248
249
250 vtkUnstructuredGrid* 
251 SMESH_DeviceActor
252 ::GetUnstructuredGrid()
253 {
254   myExtractUnstructuredGrid->Update();
255   return myExtractUnstructuredGrid->GetOutput();
256 }
257
258
259 void
260 SMESH_DeviceActor
261 ::SetControlMode(SMESH::Controls::FunctorPtr theFunctor,
262                  vtkScalarBarActor* theScalarBarActor,
263                  vtkLookupTable* theLookupTable)
264 {
265   bool anIsInitialized = theFunctor;
266   if(anIsInitialized){
267     vtkUnstructuredGrid* aDataSet = vtkUnstructuredGrid::New();
268
269     SetStoreIDMapping(true);
270     myExtractUnstructuredGrid->Update();
271     vtkUnstructuredGrid* aGrid = myExtractUnstructuredGrid->GetOutput();
272
273     aDataSet->ShallowCopy(aGrid);
274     
275     vtkDoubleArray *aScalars = vtkDoubleArray::New();
276     vtkIdType aNbCells = aGrid->GetNumberOfCells();
277     aScalars->SetNumberOfComponents(1);
278     aScalars->SetNumberOfTuples(aNbCells);
279     
280     myVisualObj->UpdateFunctor(theFunctor);
281
282     using namespace SMESH::Controls;
283     if(NumericalFunctor* aNumericalFunctor = dynamic_cast<NumericalFunctor*>(theFunctor.get())){
284       for(vtkIdType i = 0; i < aNbCells; i++){
285         vtkIdType anId = myExtractUnstructuredGrid->GetInputId(i);
286         vtkIdType anObjId = myVisualObj->GetElemObjId(anId);
287         double aValue = aNumericalFunctor->GetValue(anObjId);
288         aScalars->SetValue(i,aValue);
289       }
290     }else if(Predicate* aPredicate = dynamic_cast<Predicate*>(theFunctor.get())){
291       for(vtkIdType i = 0; i < aNbCells; i++){
292         vtkIdType anId = myExtractUnstructuredGrid->GetInputId(i);
293         vtkIdType anObjId = myVisualObj->GetElemObjId(anId);
294         bool aValue = aPredicate->IsSatisfy(anObjId);
295         aScalars->SetValue(i,aValue);
296       }
297     }
298
299     aDataSet->GetCellData()->SetScalars(aScalars);
300     aScalars->Delete();
301         
302     theLookupTable->SetRange(aScalars->GetRange());
303     theLookupTable->SetNumberOfTableValues(theScalarBarActor->GetMaximumNumberOfColors());
304     theLookupTable->Build();
305     
306     myMergeFilter->SetScalars(aDataSet);
307     aDataSet->Delete();
308   }
309   GetMapper()->SetScalarVisibility(anIsInitialized);
310   theScalarBarActor->SetVisibility(anIsInitialized);
311 }
312
313 void
314 SMESH_DeviceActor
315 ::SetExtControlMode(SMESH::Controls::FunctorPtr theFunctor,
316                     vtkScalarBarActor* theScalarBarActor,
317                     vtkLookupTable* theLookupTable)
318 {
319   bool anIsInitialized = theFunctor;
320   myExtractUnstructuredGrid->ClearRegisteredCells();
321   myExtractUnstructuredGrid->ClearRegisteredCellsWithType();
322   myExtractUnstructuredGrid->SetModeOfChanging(VTKViewer_ExtractUnstructuredGrid::ePassAll);
323   myVisualObj->UpdateFunctor(theFunctor);
324
325   using namespace SMESH::Controls;
326   if (anIsInitialized){
327     if (Length2D* aLength2D = dynamic_cast<Length2D*>(theFunctor.get())){
328       SMESH::Controls::Length2D::TValues aValues;
329
330       aLength2D->GetValues(aValues);
331       vtkUnstructuredGrid* aDataSet = vtkUnstructuredGrid::New();
332       vtkUnstructuredGrid* aGrid = myVisualObj->GetUnstructuredGrid();
333
334       aDataSet->SetPoints(aGrid->GetPoints());
335       
336       vtkIdType aNbCells = aValues.size();
337       
338       vtkDoubleArray *aScalars = vtkDoubleArray::New();
339       aScalars->SetNumberOfComponents(1);
340       aScalars->SetNumberOfTuples(aNbCells);
341
342       vtkIdType aCellsSize = 3*aNbCells;
343       vtkCellArray* aConnectivity = vtkCellArray::New();
344       aConnectivity->Allocate( aCellsSize, 0 );
345       
346       vtkUnsignedCharArray* aCellTypesArray = vtkUnsignedCharArray::New();
347       aCellTypesArray->SetNumberOfComponents( 1 );
348       aCellTypesArray->Allocate( aNbCells * aCellTypesArray->GetNumberOfComponents() );
349       
350       vtkIdList *anIdList = vtkIdList::New();
351       anIdList->SetNumberOfIds(2);
352       
353       Length2D::TValues::const_iterator anIter = aValues.begin();
354       for(vtkIdType aVtkId = 0; anIter != aValues.end(); anIter++,aVtkId++){
355         const Length2D::Value& aValue = *anIter;
356         int aNode[2] = {
357           myVisualObj->GetNodeVTKId(aValue.myPntId[0]),
358           myVisualObj->GetNodeVTKId(aValue.myPntId[1])
359         };
360         if(aNode[0] >= 0 && aNode[1] >= 0){
361           anIdList->SetId( 0, aNode[0] );
362           anIdList->SetId( 1, aNode[1] );
363           aConnectivity->InsertNextCell( anIdList );
364           aCellTypesArray->InsertNextValue( VTK_LINE );
365           aScalars->SetValue(aVtkId,aValue.myLength);
366         }
367       }
368       
369       VTKViewer_CellLocationsArray* aCellLocationsArray = VTKViewer_CellLocationsArray::New();
370       aCellLocationsArray->SetNumberOfComponents( 1 );
371       aCellLocationsArray->SetNumberOfTuples( aNbCells );
372       
373       aConnectivity->InitTraversal();
374       for( vtkIdType idType = 0, *pts, npts; aConnectivity->GetNextCell( npts, pts ); idType++ )
375         aCellLocationsArray->SetValue( idType, aConnectivity->GetTraversalLocation( npts ) );
376       
377       aDataSet->SetCells( aCellTypesArray, aCellLocationsArray,aConnectivity );
378       SetUnstructuredGrid(aDataSet);
379
380       aDataSet->GetCellData()->SetScalars(aScalars);
381       aScalars->Delete();
382       
383       theLookupTable->SetRange(aScalars->GetRange());
384       theLookupTable->Build();
385       
386       myMergeFilter->SetScalars(aDataSet);
387       aDataSet->Delete();
388     }
389     else if (MultiConnection2D* aMultiConnection2D = dynamic_cast<MultiConnection2D*>(theFunctor.get())){
390       SMESH::Controls::MultiConnection2D::MValues aValues;
391
392       aMultiConnection2D->GetValues(aValues);
393       vtkUnstructuredGrid* aDataSet = vtkUnstructuredGrid::New();
394       vtkUnstructuredGrid* aGrid = myVisualObj->GetUnstructuredGrid();
395       aDataSet->SetPoints(aGrid->GetPoints());
396       
397       vtkIdType aNbCells = aValues.size();
398       vtkDoubleArray *aScalars = vtkDoubleArray::New();
399       aScalars->SetNumberOfComponents(1);
400       aScalars->SetNumberOfTuples(aNbCells);
401
402       vtkIdType aCellsSize = 3*aNbCells;
403       vtkCellArray* aConnectivity = vtkCellArray::New();
404       aConnectivity->Allocate( aCellsSize, 0 );
405       
406       vtkUnsignedCharArray* aCellTypesArray = vtkUnsignedCharArray::New();
407       aCellTypesArray->SetNumberOfComponents( 1 );
408       aCellTypesArray->Allocate( aNbCells * aCellTypesArray->GetNumberOfComponents() );
409       
410       vtkIdList *anIdList = vtkIdList::New();
411       anIdList->SetNumberOfIds(2);
412       
413       MultiConnection2D::MValues::const_iterator anIter = aValues.begin();
414       for(vtkIdType aVtkId = 0; anIter != aValues.end(); anIter++,aVtkId++){
415         const MultiConnection2D::Value& aValue = (*anIter).first;
416         int aNode[2] = {
417           myVisualObj->GetNodeVTKId(aValue.myPntId[0]),
418           myVisualObj->GetNodeVTKId(aValue.myPntId[1])
419         };
420         if(aNode[0] >= 0 && aNode[1] >= 0){
421           anIdList->SetId( 0, aNode[0] );
422           anIdList->SetId( 1, aNode[1] );
423           aConnectivity->InsertNextCell( anIdList );
424           aCellTypesArray->InsertNextValue( VTK_LINE );
425           aScalars->SetValue(aVtkId,(*anIter).second);
426         }
427       }
428       
429       VTKViewer_CellLocationsArray* aCellLocationsArray = VTKViewer_CellLocationsArray::New();
430       aCellLocationsArray->SetNumberOfComponents( 1 );
431       aCellLocationsArray->SetNumberOfTuples( aNbCells );
432       
433       aConnectivity->InitTraversal();
434       for( vtkIdType idType = 0, *pts, npts; aConnectivity->GetNextCell( npts, pts ); idType++ )
435         aCellLocationsArray->SetValue( idType, aConnectivity->GetTraversalLocation( npts ) );
436       
437       aDataSet->SetCells( aCellTypesArray, aCellLocationsArray,aConnectivity );
438       SetUnstructuredGrid(aDataSet);
439
440       aDataSet->GetCellData()->SetScalars(aScalars);
441       aScalars->Delete();
442       
443       theLookupTable->SetRange(aScalars->GetRange());
444       theLookupTable->Build();
445       
446       myMergeFilter->SetScalars(aDataSet);
447       aDataSet->Delete();
448     }
449   }
450   GetMapper()->SetScalarVisibility(anIsInitialized);
451   theScalarBarActor->SetVisibility(anIsInitialized);
452 }
453
454 void
455 SMESH_DeviceActor
456 ::SetExtControlMode(SMESH::Controls::FunctorPtr theFunctor)
457 {
458   myExtractUnstructuredGrid->ClearRegisteredCells();
459   myExtractUnstructuredGrid->ClearRegisteredCellsWithType();
460   myExtractUnstructuredGrid->SetModeOfChanging(VTKViewer_ExtractUnstructuredGrid::ePassAll);
461   myVisualObj->UpdateFunctor(theFunctor);
462
463   using namespace SMESH::Controls;
464   if(FreeBorders* aFreeBorders = dynamic_cast<FreeBorders*>(theFunctor.get())){
465     myExtractUnstructuredGrid->SetModeOfChanging(VTKViewer_ExtractUnstructuredGrid::eAdding);
466     vtkUnstructuredGrid* aGrid = myVisualObj->GetUnstructuredGrid();
467     vtkIdType aNbCells = aGrid->GetNumberOfCells();
468     for( vtkIdType i = 0; i < aNbCells; i++ ){
469       vtkIdType anObjId = myVisualObj->GetElemObjId(i);
470       if(aFreeBorders->IsSatisfy(anObjId))
471         myExtractUnstructuredGrid->RegisterCell(i);
472     }
473     if(!myExtractUnstructuredGrid->IsCellsRegistered())
474       myExtractUnstructuredGrid->RegisterCell(-1);
475     SetUnstructuredGrid(myVisualObj->GetUnstructuredGrid());
476   }else if(FreeEdges* aFreeEdges = dynamic_cast<FreeEdges*>(theFunctor.get())){
477     SMESH::Controls::FreeEdges::TBorders aBorders;
478     aFreeEdges->GetBoreders(aBorders);
479     vtkUnstructuredGrid* aDataSet = vtkUnstructuredGrid::New();
480     vtkUnstructuredGrid* aGrid = myVisualObj->GetUnstructuredGrid();
481     aDataSet->SetPoints(aGrid->GetPoints());
482
483     vtkIdType aNbCells = aBorders.size();
484     vtkIdType aCellsSize = 3*aNbCells;
485     vtkCellArray* aConnectivity = vtkCellArray::New();
486     aConnectivity->Allocate( aCellsSize, 0 );
487     
488     vtkUnsignedCharArray* aCellTypesArray = vtkUnsignedCharArray::New();
489     aCellTypesArray->SetNumberOfComponents( 1 );
490     aCellTypesArray->Allocate( aNbCells * aCellTypesArray->GetNumberOfComponents() );
491     
492     vtkIdList *anIdList = vtkIdList::New();
493     anIdList->SetNumberOfIds(2);
494     
495     FreeEdges::TBorders::const_iterator anIter = aBorders.begin();
496     for(; anIter != aBorders.end(); anIter++){
497       const FreeEdges::Border& aBorder = *anIter;
498       int aNode[2] = {
499         myVisualObj->GetNodeVTKId(aBorder.myPntId[0]),
500         myVisualObj->GetNodeVTKId(aBorder.myPntId[1])
501       };
502       //cout<<"aNode = "<<aBorder.myPntId[0]<<"; "<<aBorder.myPntId[1]<<endl;
503       if(aNode[0] >= 0 && aNode[1] >= 0){
504         anIdList->SetId( 0, aNode[0] );
505         anIdList->SetId( 1, aNode[1] );
506         aConnectivity->InsertNextCell( anIdList );
507         aCellTypesArray->InsertNextValue( VTK_LINE );
508       }
509     }
510     
511     VTKViewer_CellLocationsArray* aCellLocationsArray = VTKViewer_CellLocationsArray::New();
512     aCellLocationsArray->SetNumberOfComponents( 1 );
513     aCellLocationsArray->SetNumberOfTuples( aNbCells );
514     
515     aConnectivity->InitTraversal();
516     for( vtkIdType idType = 0, *pts, npts; aConnectivity->GetNextCell( npts, pts ); idType++ )
517       aCellLocationsArray->SetValue( idType, aConnectivity->GetTraversalLocation( npts ) );
518     
519     aDataSet->SetCells( aCellTypesArray, aCellLocationsArray,aConnectivity );
520
521     SetUnstructuredGrid(aDataSet);
522     aDataSet->Delete();
523   }
524 }
525
526
527
528
529 unsigned long int 
530 SMESH_DeviceActor
531 ::GetMTime()
532 {
533   unsigned long mTime = this->Superclass::GetMTime();
534   mTime = max(mTime,myExtractGeometry->GetMTime());
535   mTime = max(mTime,myExtractUnstructuredGrid->GetMTime());
536   mTime = max(mTime,myMergeFilter->GetMTime());
537   mTime = max(mTime,myGeomFilter->GetMTime());
538   mTime = max(mTime,myTransformFilter->GetMTime());
539   return mTime;
540 }
541
542
543 void
544 SMESH_DeviceActor
545 ::SetTransform(VTKViewer_Transform* theTransform)
546 {
547   myTransformFilter->SetTransform(theTransform);
548 }
549
550
551 void
552 SMESH_DeviceActor
553 ::SetShrink() 
554 {
555   if ( !myIsShrinkable ) return;
556   if ( vtkDataSet* aDataSet = myPassFilter[ 0 ]->GetOutput() )
557   {
558     myShrinkFilter->SetInput( aDataSet );
559     myPassFilter[ 1 ]->SetInput( myShrinkFilter->GetOutput() );
560     myIsShrunk = true;
561   }
562 }
563
564 void
565 SMESH_DeviceActor
566 ::UnShrink() 
567 {
568   if ( !myIsShrunk ) return;
569   if ( vtkDataSet* aDataSet = myPassFilter[ 0 ]->GetOutput() )
570   {    
571     myPassFilter[ 1 ]->SetInput( aDataSet );
572     myPassFilter[ 1 ]->Modified();
573     myIsShrunk = false;
574     Modified();
575   }
576 }
577
578
579 void
580 SMESH_DeviceActor
581 ::SetRepresentation(EReperesent theMode)
582 {
583   switch(theMode){
584   case ePoint:
585     myGeomFilter->SetInside(true);
586     myGeomFilter->SetWireframeMode(false);
587     GetProperty()->SetRepresentation(0);
588     break;
589   case eWireframe:
590     myGeomFilter->SetInside(false);
591     myGeomFilter->SetWireframeMode(true);
592     GetProperty()->SetRepresentation(theMode);
593     break;
594   case eInsideframe:
595     myGeomFilter->SetInside(true);
596     myGeomFilter->SetWireframeMode(true);
597     GetProperty()->SetRepresentation(1);
598     break;
599   case eSurface:
600     myGeomFilter->SetInside(false);
601     myGeomFilter->SetWireframeMode(false);
602     GetProperty()->SetRepresentation(theMode);
603   }
604   myRepresentation = theMode;
605   GetProperty()->Modified();
606   myMapper->Modified();
607   Modified();
608 }
609
610
611 void
612 SMESH_DeviceActor
613 ::SetVisibility(int theMode)
614 {
615   if(!myExtractUnstructuredGrid->GetInput() || 
616      GetUnstructuredGrid()->GetNumberOfCells())
617   {
618     vtkLODActor::SetVisibility(theMode);
619   }else{
620     vtkLODActor::SetVisibility(false);
621   }
622 }
623
624
625 int
626 SMESH_DeviceActor
627 ::GetVisibility()
628 {
629   if(!GetUnstructuredGrid()->GetNumberOfCells()){
630     vtkLODActor::SetVisibility(false);
631   }
632   return vtkLODActor::GetVisibility();
633 }
634
635
636 int
637 SMESH_DeviceActor
638 ::GetNodeObjId(int theVtkID)
639 {
640   vtkIdType anID = theVtkID;
641
642   if(IsImplicitFunctionUsed())
643     anID = myExtractGeometry->GetNodeObjId(theVtkID);
644
645   vtkIdType aRetID = myVisualObj->GetNodeObjId(anID);
646   if(MYDEBUG) MESSAGE("GetNodeObjId - theVtkID = "<<theVtkID<<"; anID = "<<anID<<"; aRetID = "<<aRetID);
647   return aRetID;
648 }
649
650 vtkFloatingPointType* 
651 SMESH_DeviceActor
652 ::GetNodeCoord(int theObjID)
653 {
654   vtkDataSet* aDataSet = myMergeFilter->GetOutput();
655   vtkIdType anID = myVisualObj->GetNodeVTKId(theObjID);
656   vtkFloatingPointType* aCoord = aDataSet->GetPoint(anID);
657   if(MYDEBUG) MESSAGE("GetNodeCoord - theObjID = "<<theObjID<<"; anID = "<<anID);
658   return aCoord;
659 }
660
661
662 int
663 SMESH_DeviceActor
664 ::GetElemObjId(int theVtkID)
665 {
666   vtkIdType anId = myGeomFilter->GetElemObjId(theVtkID);
667   if(anId < 0) 
668     return -1;
669
670   vtkIdType anId2 = anId;
671   if(IsImplicitFunctionUsed())
672     anId2 = myExtractGeometry->GetElemObjId(anId);
673   if(anId2 < 0) 
674     return -1;
675
676   vtkIdType anId3 = myExtractUnstructuredGrid->GetInputId(anId2);
677   if(anId3 < 0) 
678     return -1;
679
680   vtkIdType aRetID = myVisualObj->GetElemObjId(anId3);
681   if(MYDEBUG) 
682      MESSAGE("GetElemObjId - theVtkID = "<<theVtkID<<"; anId2 = "<<anId2<<"; anId3 = "<<anId3<<"; aRetID = "<<aRetID);
683   return aRetID;
684 }
685
686 vtkCell* 
687 SMESH_DeviceActor
688 ::GetElemCell(int theObjID)
689 {
690   vtkDataSet* aDataSet = myVisualObj->GetUnstructuredGrid();
691   vtkIdType aGridID = myVisualObj->GetElemVTKId(theObjID);
692   vtkCell* aCell = aDataSet->GetCell(aGridID);
693   if(MYDEBUG) 
694     MESSAGE("GetElemCell - theObjID = "<<theObjID<<"; aGridID = "<<aGridID);
695   return aCell;
696 }
697
698
699 vtkFloatingPointType 
700 SMESH_DeviceActor
701 ::GetShrinkFactor()
702 {
703   return myShrinkFilter->GetShrinkFactor();
704 }
705
706 void
707 SMESH_DeviceActor
708 ::SetShrinkFactor(vtkFloatingPointType theValue)
709 {
710   theValue = theValue > 0.1? theValue: 0.8;
711   myShrinkFilter->SetShrinkFactor(theValue);
712   Modified();
713 }
714
715
716 void
717 SMESH_DeviceActor
718 ::SetHighlited(bool theIsHighlited)
719 {
720   if ( myIsHighlited == theIsHighlited )
721     return;
722   myIsHighlited = theIsHighlited;
723   Modified();
724 }
725
726 void
727 SMESH_DeviceActor
728 ::Render(vtkRenderer *ren, vtkMapper* m)
729 {
730   int aResolveCoincidentTopology = vtkMapper::GetResolveCoincidentTopology();
731   vtkFloatingPointType aStoredFactor, aStoredUnit; 
732   vtkMapper::GetResolveCoincidentTopologyPolygonOffsetParameters(aStoredFactor,aStoredUnit);
733
734   vtkMapper::SetResolveCoincidentTopologyToPolygonOffset();
735   vtkFloatingPointType aFactor = myPolygonOffsetFactor, aUnits = myPolygonOffsetUnits;
736   if(myIsHighlited){
737     static vtkFloatingPointType EPS = .01;
738     aUnits *= (1.0-EPS);
739   }
740   vtkMapper::SetResolveCoincidentTopologyPolygonOffsetParameters(aFactor,aUnits);
741   vtkLODActor::Render(ren,m);
742
743   vtkMapper::SetResolveCoincidentTopologyPolygonOffsetParameters(aStoredFactor,aStoredUnit);
744   vtkMapper::SetResolveCoincidentTopology(aResolveCoincidentTopology);
745 }
746
747
748 void
749 SMESH_DeviceActor
750 ::SetPolygonOffsetParameters(vtkFloatingPointType factor, 
751                              vtkFloatingPointType units)
752 {
753   myPolygonOffsetFactor = factor;
754   myPolygonOffsetUnits = units;
755 }
756