1 // VISU OBJECT : interactive object for VISU entities implementation
3 // Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
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.
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.
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
20 // See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
29 #include "VISU_Actor.h"
30 #include "VISU_PipeLine.hxx"
31 #include "VTKViewer_ShrinkFilter.h"
32 #include "VTKViewer_GeometryFilter.h"
33 #include "VTKViewer_PassThroughFilter.h"
39 #include <vtkProperty.h>
40 #include <vtkSmartPointer.h>
41 #include <vtkTextMapper.h>
42 #include <vtkTextActor.h>
43 #include <vtkProperty2D.h>
44 #include <vtkRenderer.h>
45 #include <vtkCellPicker.h>
47 #include <vtkPointPicker.h>
48 #include <vtkPoints.h>
49 #include <vtkInteractorStyle.h>
50 #include <vtkDataSet.h>
51 #include <vtkPolyData.h>
52 #include <vtkUnstructuredGrid.h>
54 #include <vtkShrinkFilter.h>
55 #include <vtkShrinkPolyData.h>
57 #include <vtkDataSetMapper.h>
58 #include <vtkGeometryFilter.h>
59 #include <vtkObjectFactory.h>
61 #include <boost/bind.hpp>
63 #include "utilities.h"
67 static int MYVTKDEBUG = 0;
70 static int MYDEBUG = 1;
72 static int MYDEBUG = 0;
75 //#define ENABLE_ANNOTATION
77 //----------------------------------------------------------------------------
78 vtkStandardNewMacro(VISU_Actor);
80 //----------------------------------------------------------------------------
83 myIsVTKMapping(false),
86 myMapper(vtkDataSetMapper::New()),
88 myIsShrinkable(false),
89 myShrinkFilter(VTKViewer_ShrinkFilter::New()),
90 myAnnotationMapper(vtkTextMapper::New()),
91 myAnnotationActor(vtkTextActor::New())
93 if(MYDEBUG) MESSAGE("VISU_Actor::VISU_Actor - this = "<<this);
96 myShrinkFilter->Delete();
98 myStoreMapping = true;
100 myShrinkFilter->SetStoreMapping(true);
102 myAnnotationMapper->Delete();
103 myAnnotationActor->SetMapper(myAnnotationMapper.GetPointer());
105 myAnnotationActor->Delete();
106 myAnnotationActor->SetVisibility(0);
109 //----------------------------------------------------------------------------
112 ::ShallowCopy(vtkProp *prop)
114 VISU_Actor *anActor = VISU_Actor::SafeDownCast(prop);
116 setName(anActor->getName());
117 if(anActor->hasIO()) setIO(anActor->getIO());
119 Superclass::ShallowCopy(prop);
124 ::ShallowCopyPL(VISU_PipeLine* thePipeLine)
126 myPipeLine->ShallowCopy(thePipeLine);
128 vtkDataSet* aDatsSet = myMapper->GetInput();
129 GetMapper()->ShallowCopy(thePipeLine->GetMapper());
131 // To restore mapper input from pipeline
132 myMapper->SetInput(aDatsSet);
135 //----------------------------------------------------------------------------
139 if(MYDEBUG) MESSAGE("~VISU_Actor() - this = "<<this);
140 Superclass::SetProperty(NULL);
141 SetDebug(MYVTKDEBUG);
144 //----------------------------------------------------------------------------
147 ::setIO(const Handle(SALOME_InteractiveObject)& theIO)
149 Superclass::setIO(theIO);
150 myName = theIO->getName();
153 //----------------------------------------------------------------------------
156 ::SetPrs3d(VISU::Prs3d_i* thePrs3d)
168 //----------------------------------------------------------------------------
173 return myActorFactory;
178 ::SetFactory(VISU::TActorFactory* theActorFactory)
180 using namespace VISU;
182 if(myActorFactory == theActorFactory)
186 myDestroySignal.connect(boost::bind(&TActorFactory::RemoveActor,
190 myActorFactory = theActorFactory;
193 //----------------------------------------------------------------------------
196 ::UpdateFromFactory()
198 myActorFactory->UpdateActor(this);
206 RemoveFromRender(GetRenderer());
209 //----------------------------------------------------------------------------
212 ::SetMapperInput(vtkDataSet* theDataSet)
214 myMapper->SetInput(theDataSet);
215 SetMapper(myMapper.GetPointer());
220 ::SetPipeLine(VISU_PipeLine* thePipeLine)
222 myPipeLine = thePipeLine;
224 if(vtkMapper *aMapper = myPipeLine->GetMapper()){
225 if(vtkDataSet *aDataSet = aMapper->GetInput()){
226 SetShrinkable(thePipeLine->IsShrinkable());
228 SetMapperInput(aDataSet);
239 return myPipeLine.GetPointer();
246 return GetPipeLine();
250 //----------------------------------------------------------------------------
253 ::SetRepresentation(int theMode)
255 Superclass::SetRepresentation(theMode);
256 if(myRepresentation == VTK_POINTS)
261 //----------------------------------------------------------------------------
268 if(vtkDataSet* aDataSet = myPassFilter[0]->GetOutput()){
269 myShrinkFilter->SetInput(aDataSet);
270 myPassFilter[1]->SetInput(myShrinkFilter->GetOutput());
281 if(vtkDataSet* aDataSet = myPassFilter[0]->GetOutput()){
282 myPassFilter[1]->SetInput(aDataSet);
283 myPassFilter[1]->Modified();
298 ::SetShrinkable(bool theIsShrinkable)
300 myIsShrinkable = theIsShrinkable;
307 return myIsShrinkable;
312 ::SetShrinkFactor(float theValue)
314 myShrinkFilter->SetShrinkFactor(theValue);
322 return myShrinkFilter->GetShrinkFactor();
326 //----------------------------------------------------------------------------
329 ::SetOpacity(float theValue)
331 GetProperty()->SetOpacity(theValue);
338 return GetProperty()->GetOpacity();
343 ::SetLineWidth(float theLineWidth)
345 GetProperty()->SetLineWidth(theLineWidth);
352 return GetProperty()->GetLineWidth();
355 //==================================================================
356 // function: AddToRender
358 //==================================================================
361 ::AddToRender(vtkRenderer* theRenderer)
363 Superclass::AddToRender(theRenderer);
364 theRenderer->AddActor(myAnnotationActor.GetPointer());
367 //==================================================================
368 // function: RemoveFromRender
370 //==================================================================
373 ::RemoveFromRender(vtkRenderer* theRenderer)
375 theRenderer->RemoveActor(myAnnotationActor.GetPointer());
376 Superclass::RemoveFromRender(theRenderer);
377 myDestroySignal(this);
380 //----------------------------------------------------------------------------
383 ::SetVTKMapping(bool theIsVTKMapping)
385 myIsVTKMapping = theIsVTKMapping;
390 ::IsVTKMapping() const
392 return myIsVTKMapping;
395 //----------------------------------------------------------------------------
401 return Superclass::GetInput();
403 return GetCurrentPL()->GetOutput();
406 //----------------------------------------------------------------------------
409 ::GetNodeObjId(vtkIdType theID)
412 return Superclass::GetNodeObjId(theID);
414 vtkIdType anID = myGeomFilter->GetNodeObjId(theID);
417 anID = myShrinkFilter->GetNodeObjId(anID);
419 return GetCurrentPL()->GetNodeObjID(anID);
424 ::GetNodeVTKID(vtkIdType theID)
429 return GetCurrentPL()->GetNodeVTKID(theID);
434 ::GetNodeCoord(int theObjID)
437 return Superclass::GetNodeCoord(theObjID);
439 return GetCurrentPL()->GetNodeCoord(theObjID);
443 //----------------------------------------------------------------------------
446 ::GetElemObjId(vtkIdType theID)
449 return Superclass::GetElemObjId(theID);
451 vtkIdType anID = myGeomFilter->GetElemObjId(theID);
454 anID = myShrinkFilter->GetElemObjId(anID);
456 return GetCurrentPL()->GetElemObjID(anID);
461 ::GetElemVTKID(vtkIdType theID)
466 return GetCurrentPL()->GetElemVTKID(theID);
471 ::GetElemCell(vtkIdType theObjID)
474 return Superclass::GetElemCell(theObjID);
476 return GetCurrentPL()->GetElemCell(theObjID);
480 //----------------------------------------------------------------------------
483 ::PreHighlight(vtkInteractorStyle* theInteractorStyle,
484 SVTK_SelectionEvent* theSelectionEvent,
487 bool aRet = Superclass::PreHighlight(theInteractorStyle,
490 #ifndef ENABLE_ANNOTATION
494 myAnnotationActor->SetVisibility(0);
496 switch(mySelectionMode){
498 vtkRenderer* aRenderer = theInteractorStyle->GetCurrentRenderer();
499 myCellPicker->Pick(theSelectionEvent->myX,
500 theSelectionEvent->myY,
504 if(myCellPicker->GetActor() != this)
507 vtkIdType aVTKId = myCellPicker->GetCellId();
508 if(aVTKId >= 0 && mySelector->IsValid(this,aVTKId,true) && hasIO()){
509 vtkIdType anObjId = GetElemObjId(aVTKId);
510 if(vtkCell* aCell = GetElemCell(anObjId)){
511 vtkPoints* aPts = aCell->GetPoints();
512 if(int aNbPts = aCell->GetNumberOfPoints()){
513 float aCoord[3] = {0.0, 0.0, 0.0};
514 for(int i = 0; i < aNbPts; i++){
515 float *aPntCoord = aPts->GetPoint(i);
516 aCoord[0] += aPntCoord[0];
517 aCoord[1] += aPntCoord[1];
518 aCoord[2] += aPntCoord[2];
520 // Display coordinates
521 float aWorldCoord[4] = {aCoord[0]/aNbPts, aCoord[1]/aNbPts, aCoord[2]/aNbPts, 1.0};
522 aRenderer->SetWorldPoint(aWorldCoord);
523 aRenderer->WorldToDisplay();
524 float aSelectionPoint[3];
525 aRenderer->GetDisplayPoint(aSelectionPoint);
526 myAnnotationActor->SetPosition(aSelectionPoint);
528 // To prepare the annotation text
529 std::ostringstream aStr;
530 aStr<<"Cell ID: "<< anObjId;
531 std::string aString = aStr.str();
532 myAnnotationMapper->SetInput(aString.c_str());
534 myAnnotationActor->SetVisibility(1);
542 vtkRenderer* aRenderer = theInteractorStyle->GetCurrentRenderer();
543 myPointPicker->Pick(theSelectionEvent->myX,
544 theSelectionEvent->myY,
548 if(myPointPicker->GetActor() != this)
551 vtkIdType aVtkId = myPointPicker->GetPointId();
552 if(aVtkId >= 0 && mySelector->IsValid(this,aVtkId,true) && hasIO()){
553 vtkIdType anObjId = GetNodeObjId( aVtkId );
554 if(float* aCoord = GetNodeCoord(anObjId)){
555 // Display coordinates
556 float aWorldCoord[4] = {aCoord[0], aCoord[1], aCoord[2], 1.0};
557 aRenderer->SetWorldPoint(aWorldCoord);
558 aRenderer->WorldToDisplay();
559 float aSelectionPoint[3];
560 aRenderer->GetDisplayPoint(aSelectionPoint);
561 myAnnotationActor->SetPosition(aSelectionPoint);
563 // To prepare the annotation text
564 std::ostringstream aStr;
565 aStr<<"Node ID: "<< anObjId;
566 std::string aString = aStr.str();
567 myAnnotationMapper->SetInput(aString.c_str());
569 myAnnotationActor->SetVisibility(1);
575 case EdgeOfCellSelection: