]> SALOME platform Git repositories - modules/gui.git/commitdiff
Salome HOME
Selection improvement
authorenk <enk@opencascade.com>
Wed, 31 Oct 2007 13:38:21 +0000 (13:38 +0000)
committerenk <enk@opencascade.com>
Wed, 31 Oct 2007 13:38:21 +0000 (13:38 +0000)
Added changes from current version of SALOME

14 files changed:
src/SVTK/SVTK_Event.h
src/SVTK/SVTK_InteractorStyle.cxx
src/SVTK/SVTK_InteractorStyle.h
src/SVTK/SVTK_Renderer.cxx
src/SVTK/SVTK_Renderer.h
src/SVTK/SVTK_Selector.cxx
src/SVTK/SVTK_Selector.h
src/SVTK/SVTK_SelectorDef.h
src/SVTK/SVTK_View.cxx
src/SVTK/SVTK_View.h
src/SVTK/SVTK_ViewWindow.cxx
src/SVTK/SVTK_ViewWindow.h
src/VTKViewer/VTKViewer_Utilities.cxx
src/VTKViewer/VTKViewer_Utilities.h

index fa415ab831145c7a1df22ba3ca8ca9f8564ea92f..8b2d1bdb04dcaf6cc7d8c1c799aca83c5f541ab1 100644 (file)
@@ -61,6 +61,14 @@ namespace SVTK
     StartGlobalPan,
     StartFitArea,
 
+    SetRotateGravity,
+    StartPointSelection,
+    SetRotateSelected,
+    
+    BBCenterChanged,
+    RotationPointChanged,
+    ChangeRotationPoint,
+
     LastEvent
   };
 }
index 4f8dfaa60858dfd927dca36eefc5b98c17b6b831..7ba576467f3d96d3679d1553a68d70dd352f6a35 100644 (file)
@@ -36,6 +36,7 @@
 #include "SVTK_Event.h" 
 #include "SVTK_Selector.h"
 #include "SVTK_Functor.h"
+#include "SVTK_Actor.h"
 
 #include "VTKViewer_Algorithm.h"
 #include "SVTK_Functor.h"
 #include <vtkCommand.h>
 #include <vtkCamera.h>
 #include <vtkRenderer.h>
-#include <vtkPicker.h>
+#include <vtkPointPicker.h>
 #include <vtkRenderWindow.h>
 #include <vtkRenderWindowInteractor.h>
 #include <vtkCallbackCommand.h>
 #include <vtkRendererCollection.h>
+#include <vtkDataSet.h>
+#include <vtkPerspectiveTransform.h> 
+#include <vtkMatrix4x4.h>
 
 #include <qapplication.h>
 #include <qpixmap.h>
@@ -62,6 +66,8 @@
 //VRV: porting on Qt 3.0.5
 #include <algorithm>
 
+//#include <iostream.h>
+
 using namespace std;
 
 namespace
@@ -100,19 +106,23 @@ namespace
 
 vtkStandardNewMacro(SVTK_InteractorStyle);
 
+
 /*!
   Constructor
 */
 SVTK_InteractorStyle
 ::SVTK_InteractorStyle():
   mySelectionEvent(new SVTK_SelectionEvent()),
-  myPicker(vtkPicker::New()),
+  myPointPicker(vtkPointPicker::New()),
   myLastHighlitedActor(NULL),
   myLastPreHighlitedActor(NULL),
   myControllerIncrement(SVTK_ControllerIncrement::New()),
-  myControllerOnKeyDown(SVTK_ControllerOnKeyDown::New())
+  myControllerOnKeyDown(SVTK_ControllerOnKeyDown::New()),
+  myHighlightRotationPointActor(SVTK_Actor::New())
 {
-  myPicker->Delete();
+  myPointPicker->Delete();
+
+  myPointPicker->SetTolerance(0.025);
 
   this->MotionFactor = 10.0;
   this->State = VTK_INTERACTOR_STYLE_CAMERA_NONE;
@@ -131,6 +141,20 @@ SVTK_InteractorStyle
   //
   myControllerIncrement->Delete();
   myControllerOnKeyDown->Delete();
+
+  myCurrRotationPointType = SVTK::SetRotateGravity;
+  myPrevRotationPointType = myCurrRotationPointType;
+
+  myHighlightRotationPointActor->Delete();
+  myHighlightRotationPointActor->Initialize();
+  myHighlightRotationPointActor->PickableOff();
+  myHighlightRotationPointActor->SetVisibility( false );
+  
+  myHighlightRotationPointActor->GetProperty()->SetPointSize(SALOME_POINT_SIZE+2);
+  myHighlightRotationPointActor->GetProperty()->SetLineWidth(SALOME_LINE_WIDTH+2);
+  myHighlightRotationPointActor->GetProperty()->SetRepresentationToPoints();
+
+  myBBFirstCheck = true;
 }
 
 /*!
@@ -205,7 +229,7 @@ void
 SVTK_InteractorStyle
 ::RotateXY(int dx, int dy)
 {
-  if(GetCurrentRenderer() == NULL)
+  /*   if(GetCurrentRenderer() == NULL)
     return;
   
   int *size = GetCurrentRenderer()->GetRenderWindow()->GetSize();
@@ -222,6 +246,61 @@ SVTK_InteractorStyle
 
   GetCurrentRenderer()->ResetCameraClippingRange(); 
 
+  this->Render();*/
+
+  if(GetCurrentRenderer() == NULL)
+    return;
+  
+  vtkCamera *cam = GetCurrentRenderer()->GetActiveCamera();
+
+  double viewFP[3], viewPos[3];
+  cam->GetFocalPoint(viewFP);
+  cam->GetPosition(viewPos);
+
+  if ( myCurrRotationPointType == SVTK::SetRotateGravity )
+  {
+    vtkFloatingPointType aCenter[3];
+    if ( ComputeBBCenter(GetCurrentRenderer(),aCenter) ) 
+    {
+      myRotationPointX = aCenter[0];
+      myRotationPointY = aCenter[1];
+      myRotationPointZ = aCenter[2];
+    }
+  }
+
+  // Calculate corresponding transformation
+  vtkPerspectiveTransform* aTransform = vtkPerspectiveTransform::New();
+  aTransform->Identity();
+  aTransform->Translate(+myRotationPointX, +myRotationPointY, +myRotationPointZ);
+
+  // Azimuth transformation
+  int *size = GetCurrentRenderer()->GetRenderWindow()->GetSize();
+  double aDeltaAzimuth = -20.0 / size[0];
+  
+  double rxf = double(dx) * aDeltaAzimuth * this->MotionFactor;
+  aTransform->RotateWXYZ(rxf, cam->GetViewUp());
+
+  // Elevation transformation
+  double aDeltaElevation = -20.0 / size[1];
+
+  double ryf = double(dy) * aDeltaElevation * this->MotionFactor;
+  vtkMatrix4x4* aMatrix = cam->GetViewTransformMatrix();
+  const double anAxis[3] = {-aMatrix->GetElement(0,0), // mkr : 27.11.2006 : PAL14011 - Strange behaviour in rotation in VTK Viewer.
+                           -aMatrix->GetElement(0,1), 
+                           -aMatrix->GetElement(0,2)};
+  
+  aTransform->RotateWXYZ(ryf, anAxis);
+            
+  aTransform->Translate(-myRotationPointX, -myRotationPointY, -myRotationPointZ);
+
+  // To apply the transformation
+  cam->SetPosition(aTransform->TransformPoint(viewPos));
+  cam->SetFocalPoint(aTransform->TransformPoint(viewFP));
+
+  cam->OrthogonalizeViewUp();
+
+  GetCurrentRenderer()->ResetCameraClippingRange(); 
+
   this->Render();
 }
 
@@ -431,9 +510,53 @@ SVTK_InteractorStyle
   } else {
     if (ctrl)
       startOperation(VTK_INTERACTOR_STYLE_CAMERA_ZOOM);
+    else if ( myCurrRotationPointType == SVTK::StartPointSelection )
+    {
+      SVTK_SelectionEvent* aSelectionEvent = GetSelectionEventFlipY();
+
+      SALOME_Actor* anActor = GetSelector()->Pick(aSelectionEvent, GetCurrentRenderer());
+      
+      if ( anActor )
+      {
+       myPointPicker->Pick( aSelectionEvent->myX,
+                            aSelectionEvent->myY, 
+                            0.0, 
+                            GetCurrentRenderer() );
+       int aVtkId = myPointPicker->GetPointId();
+       if ( aVtkId >= 0 )
+       {
+         int anObjId = anActor->GetNodeObjId( aVtkId );
+         vtkFloatingPointType* aCoords = anActor->GetNodeCoord(anObjId);
+         
+         myCurrRotationPointType = SVTK::SetRotateSelected;
+         
+         // invoke event for update coordinates in SVTK_SetRotationPointDlg
+         InvokeEvent(SVTK::RotationPointChanged,(void*)aCoords);
+       }
+       else
+       {
+         // invoke event with no data (for SVTK_SetRotationPointDlg)
+         InvokeEvent(SVTK::RotationPointChanged,0);
+         myCurrRotationPointType = myPrevRotationPointType;
+       }
+      }
+      else
+      {
+       // invoke event with no data (for SVTK_SetRotationPointDlg)
+       InvokeEvent(SVTK::RotationPointChanged,0);
+       myCurrRotationPointType = myPrevRotationPointType;
+      }
+    
+      myHighlightRotationPointActor->SetVisibility( false );
+      if(GetCurrentRenderer() != NULL)
+       GetCurrentRenderer()->RemoveActor( myHighlightRotationPointActor.GetPointer() );
+
+      GetRenderWidget()->setCursor(myDefCursor); 
+    }
     else
       startOperation(VTK_INTERACTOR_STYLE_CAMERA_SELECT);
   }
+  
   return;
 }
 
@@ -696,6 +819,26 @@ SVTK_InteractorStyle
   ForcedState = VTK_INTERACTOR_STYLE_CAMERA_ROTATE;
 }
 
+/*!
+  Set rotation point selected by user
+*/
+void 
+SVTK_InteractorStyle
+::startPointSelection()
+{
+  myCurrRotationPointType = SVTK::StartPointSelection;
+
+  if(GetCurrentRenderer() != NULL) {
+    GetCurrentRenderer()->AddActor( myHighlightRotationPointActor.GetPointer() );
+    vtkFloatingPointType aColor[3];
+    GetCurrentRenderer()->GetBackground( aColor );
+    myHighlightRotationPointActor->GetProperty()->SetColor(1. - aColor[0],
+                                                          1. - aColor[1],
+                                                          1. - aColor[2]);
+  }
+
+  setCursor(VTK_INTERACTOR_STYLE_CAMERA_NONE);
+}
 
 /*! 
   Starts Spin operation (e.g. through menu command)
@@ -863,7 +1006,10 @@ SVTK_InteractorStyle
       break;
     case VTK_INTERACTOR_STYLE_CAMERA_NONE:
     default:
-      GetRenderWidget()->setCursor(myDefCursor); 
+      if ( myCurrRotationPointType == SVTK::StartPointSelection )
+       GetRenderWidget()->setCursor(myHandCursor);
+      else
+       GetRenderWidget()->setCursor(myDefCursor); 
       myCursorState = false;
       break;
   }
@@ -947,12 +1093,8 @@ SVTK_InteractorStyle
           this->FindPokedRenderer(aSelectionEvent->myX, aSelectionEvent->myY);
          Interactor->StartPickCallback();
 
-          myPicker->Pick(aSelectionEvent->myX, 
-                        aSelectionEvent->myY, 
-                        0.0, 
-                        GetCurrentRenderer());
-         //
-         SALOME_Actor* anActor = GetFirstSALOMEActor(myPicker.GetPointer());
+         SALOME_Actor* anActor = GetSelector()->Pick(aSelectionEvent, GetCurrentRenderer());
+         
          aSelectionEvent->myIsRectangle = false;
 
          if(!myShiftState)
@@ -961,8 +1103,9 @@ SVTK_InteractorStyle
          if(anActor){
            anActor->Highlight( this, aSelectionEvent, true );
          }else{
-           if(myLastHighlitedActor.GetPointer() && myLastHighlitedActor.GetPointer() != anActor)
+           if(myLastHighlitedActor.GetPointer() && myLastHighlitedActor.GetPointer() != anActor) {
              myLastHighlitedActor->Highlight( this, aSelectionEvent, false );
+           }
          }
          myLastHighlitedActor = anActor;
        } 
@@ -1083,19 +1226,44 @@ SVTK_InteractorStyle
 
   bool anIsChanged = false;
 
-  myPicker->Pick(aSelectionEvent->myX, 
-                aSelectionEvent->myY, 
-                0.0, 
-                GetCurrentRenderer());
+  SALOME_Actor *anActor = GetSelector()->Pick(aSelectionEvent, GetCurrentRenderer());
   
-  SALOME_Actor *anActor = GetFirstSALOMEActor(myPicker.GetPointer());
-  if (anActor){
-    anIsChanged |= anActor->PreHighlight( this, aSelectionEvent, true );
+  if ( myCurrRotationPointType == SVTK::StartPointSelection )
+  {
+    myHighlightRotationPointActor->SetVisibility( false );
+
+    SALOME_Actor *anCurrActor;
+    if ( anActor ) anCurrActor = anActor;
+    else if ( myLastPreHighlitedActor.GetPointer() 
+             && 
+             myLastPreHighlitedActor.GetPointer() != anActor )
+      anCurrActor = myLastPreHighlitedActor.GetPointer();
+    if ( anCurrActor )
+    {
+      myPointPicker->Pick( aSelectionEvent->myX, aSelectionEvent->myY, 0.0, GetCurrentRenderer() );
+      int aVtkId = myPointPicker->GetPointId();
+      if ( aVtkId >= 0 ) {
+       int anObjId = anActor->GetNodeObjId( aVtkId );
+
+       TColStd_IndexedMapOfInteger aMapIndex;
+       aMapIndex.Add( anObjId );
+       myHighlightRotationPointActor->MapPoints( anActor, aMapIndex );
+
+       myHighlightRotationPointActor->SetVisibility( true );
+       anIsChanged = true;
+      }
+    }
   }
+  else {
+    if (anActor){
+      anIsChanged |= anActor->PreHighlight( this, aSelectionEvent, true );
+    }
 
-  if(myLastPreHighlitedActor.GetPointer() && myLastPreHighlitedActor.GetPointer() != anActor)
-    anIsChanged |= myLastPreHighlitedActor->PreHighlight( this, aSelectionEvent, false );   
+    if(myLastPreHighlitedActor.GetPointer() && myLastPreHighlitedActor.GetPointer() != anActor)
+      anIsChanged |= myLastPreHighlitedActor->PreHighlight( this, aSelectionEvent, false );   
 
+  }
+  
   myLastPreHighlitedActor = anActor;
 
   if(anIsChanged)
@@ -1225,6 +1393,11 @@ SVTK_InteractorStyle
     theInteractor->AddObserver( SVTK::StartRotate, EventCallbackCommand, Priority );
     theInteractor->AddObserver( SVTK::StartGlobalPan, EventCallbackCommand, Priority );
     theInteractor->AddObserver( SVTK::StartFitArea, EventCallbackCommand, Priority );
+
+    theInteractor->AddObserver( SVTK::SetRotateGravity, EventCallbackCommand, Priority );
+    theInteractor->AddObserver( SVTK::StartPointSelection, EventCallbackCommand, Priority );
+
+    theInteractor->AddObserver( SVTK::ChangeRotationPoint, EventCallbackCommand, Priority );
   }
 }
 
@@ -1237,6 +1410,30 @@ SVTK_InteractorStyle
 {
   //vtkInteractorStyle::OnTimer();
   this->Interactor->Render();
+  // check if bounding box was changed
+  if ( GetCurrentRenderer() )
+  {
+    vtkFloatingPointType aCurrBBCenter[3];
+    if ( ComputeBBCenter(GetCurrentRenderer(),aCurrBBCenter) )
+    {
+      if ( !myBBFirstCheck )
+      {
+       if ( fabs(aCurrBBCenter[0]-myBBCenter[0]) > 1e-38 ||
+            fabs(aCurrBBCenter[1]-myBBCenter[1]) > 1e-38 ||
+            fabs(aCurrBBCenter[2]-myBBCenter[2]) > 1e-38 ) {
+         // bounding box was changed => send SVTK::RotationPointChanged event
+         // invoke event for update coordinates in SVTK_SetRotationPointDlg
+         InvokeEvent(SVTK::BBCenterChanged,(void*)aCurrBBCenter);
+         for ( int i =0; i < 3; i++) myBBCenter[i] = aCurrBBCenter[i];
+       }
+      }
+      else 
+      {
+       for ( int i =0; i < 3; i++) myBBCenter[i] = aCurrBBCenter[i];
+       myBBFirstCheck = false;
+      }
+    }
+  }
 }
 
 /*!
@@ -1299,6 +1496,8 @@ SVTK_InteractorStyle
     vtkObject* anObject = reinterpret_cast<vtkObject*>( clientData );
     SVTK_InteractorStyle* self = dynamic_cast<SVTK_InteractorStyle*>( anObject );
     int aSpeedIncrement=self->ControllerIncrement()->Current();
+    vtkFloatingPointType aCenter[3];
+    vtkFloatingPointType* aSelectedPoint;
     if ( self ) {
       switch ( event ) {
       case SVTK::SpaceMouseMoveEvent : 
@@ -1372,6 +1571,40 @@ SVTK_InteractorStyle
       case SVTK::StartFitArea:
        self->startFitArea();
        return;
+
+      case SVTK::SetRotateGravity:
+       if ( self->myCurrRotationPointType == SVTK::StartPointSelection )
+       {
+         self->myHighlightRotationPointActor->SetVisibility( false );
+         if( self->GetCurrentRenderer() != NULL )
+           self->GetCurrentRenderer()->RemoveActor( self->myHighlightRotationPointActor.GetPointer() );
+         self->GetRenderWidget()->setCursor(self->myDefCursor); 
+       }
+       self->myPrevRotationPointType = self->myCurrRotationPointType;
+       self->myCurrRotationPointType = SVTK::SetRotateGravity;
+       if ( ComputeBBCenter(self->GetCurrentRenderer(),aCenter) ) 
+         // invoke event for update coordinates in SVTK_SetRotationPointDlg
+         self->InvokeEvent(SVTK::BBCenterChanged,(void*)aCenter);
+       return;
+      case SVTK::StartPointSelection:
+       self->startPointSelection();
+       return;
+
+      case SVTK::ChangeRotationPoint:
+       if ( self->myCurrRotationPointType == SVTK::StartPointSelection )
+       {
+         self->myHighlightRotationPointActor->SetVisibility( false );
+         if( self->GetCurrentRenderer() != NULL )
+           self->GetCurrentRenderer()->RemoveActor( self->myHighlightRotationPointActor.GetPointer() );
+         self->GetRenderWidget()->setCursor(self->myDefCursor); 
+       }
+       self->myPrevRotationPointType = self->myCurrRotationPointType;
+       self->myCurrRotationPointType = SVTK::SetRotateSelected;
+       aSelectedPoint = (vtkFloatingPointType*)callData;
+       self->myRotationPointX = aSelectedPoint[0];
+       self->myRotationPointY = aSelectedPoint[1];
+       self->myRotationPointZ = aSelectedPoint[2];
+       return;
       }
     }
   }
index 90057f5a84fab0b4e12dd8fdd1204382f3953ee5..712f5c3fd206bc552208cc634562f62f59bd8929 100644 (file)
@@ -104,12 +104,13 @@ class SVTK_EXPORT SVTK_ControllerOnKeyDown : public vtkObject{
 };
 
 class vtkCell;
-class vtkPicker;
+class vtkPointPicker;
 
 class SALOME_Actor;
 
 class SVTK_Selector;
 class SVTK_GenericRenderWindowInteractor;
+class SVTK_Actor;
 
 #define VTK_INTERACTOR_STYLE_CAMERA_NONE    0
 #define VTK_INTERACTOR_STYLE_CAMERA_ROTATE  1
@@ -119,6 +120,7 @@ class SVTK_GenericRenderWindowInteractor;
 #define VTK_INTERACTOR_STYLE_CAMERA_FIT        5
 #define VTK_INTERACTOR_STYLE_CAMERA_SELECT     6
 #define VTK_INTERACTOR_STYLE_CAMERA_GLOBAL_PAN 7
+#define VTK_INTERACTOR_STYLE_CAMERA_SELECT_ROTATION_POINT 8
 
 //! Introduce SALOME way of user interaction
 /*!
@@ -278,6 +280,8 @@ class SVTK_EXPORT SVTK_InteractorStyle: public vtkInteractorStyle
   void startFitArea();
   void startSpin();
 
+  void startPointSelection();
+
  protected:
   void loadCursors();
   void startOperation(int operation);
@@ -324,7 +328,18 @@ class SVTK_EXPORT SVTK_InteractorStyle: public vtkInteractorStyle
 
   PSelectionEvent mySelectionEvent;
 
-  vtkSmartPointer<vtkPicker> myPicker;
+  unsigned long                   myCurrRotationPointType;
+  unsigned long                   myPrevRotationPointType;
+
+  double                          myRotationPointX;
+  double                          myRotationPointY;
+  double                          myRotationPointZ;
+
+  vtkSmartPointer<SVTK_Actor>     myHighlightRotationPointActor;
+  vtkSmartPointer<vtkPointPicker> myPointPicker;
+  
+  vtkFloatingPointType            myBBCenter[3];
+  bool                            myBBFirstCheck;
 };
 
 #ifdef WIN32
index d3020f1c1a03657e55164e121ef585ca51c91b3b..155e419ca4688c2df6c6d5090967f7ae5196da10 100644 (file)
@@ -81,8 +81,6 @@ SVTK_Renderer
   myDevice->Delete();
   myTransform->Delete();
 
-  SetSelectionTolerance();
-
   myPointPicker->Delete();
   myCellPicker->Delete();
 
@@ -225,6 +223,7 @@ SVTK_Renderer
 {
   myInteractor = theInteractor;
   mySelector = theSelector;
+  SetSelectionTolerance();
 }
 
 /*!
@@ -348,13 +347,16 @@ SVTK_Renderer
 void
 SVTK_Renderer
 ::SetSelectionTolerance(const double& theTolNodes, 
-                       const double& theTolCell)
+                       const double& theTolCell,
+                       const double& theTolObjects)
 {
   myPointPicker->SetTolerance( theTolNodes );
   myCellPicker->SetTolerance( theTolCell );
 
   myPointRectPicker->SetTolerance( theTolNodes );
   myCellRectPicker->SetTolerance( theTolCell );
+
+  mySelector->SetTolerance( theTolObjects );
 }
 
 
index 3e44d5fe4d5f779fec6b3b8d6a2da2c5e0c84188..5c24cefa13b315a4a25202a2deaa174d9bd751c5 100644 (file)
@@ -122,7 +122,8 @@ class SVTK_EXPORT SVTK_Renderer : public vtkObject
   //! Setup requested tolerance for the picking
   void
   SetSelectionTolerance(const double& theTolNodes = 0.025, 
-                       const double& theTolCell = 0.001);
+                       const double& theTolCell = 0.001,
+                       const double& theTolObjects = 0.025);
 
   //----------------------------------------------------------------------------
   //! Adjust all intenal actors (trihedron and graduated rules) to the scene
index d93bd4b448f7e24a1786cf20dd21bc01bdb6338f..ead47cbbcaacdd7246b4afe743e169fddd4d1875 100644 (file)
 #include <TColStd_IndexedMapOfInteger.hxx>
 
 #include <vtkCallbackCommand.h>
+#include <vtkActorCollection.h>
+#include <vtkCellPicker.h>
+
+
+/*!
+  Find first SALOME_Actor from the end of actors collection
+*/
+inline
+SALOME_Actor* 
+GetLastSALOMEActor(vtkActorCollection* theCollection)
+{
+  if (theCollection) {
+    for (int i = theCollection->GetNumberOfItems() - 1; i >= 0; i--) {
+      if (SALOME_Actor* anActor = dynamic_cast<SALOME_Actor*>(theCollection->GetItemAsObject(i)))
+       if (anActor->hasIO())
+         return anActor;
+    }
+  }
+  return NULL;
+}
+
 
 /*!
   \return new SVTK_Selector
@@ -50,9 +71,14 @@ SVTK_Selector
   Default constructor
 */
 SVTK_SelectorDef
-::SVTK_SelectorDef()
+::SVTK_SelectorDef():
+  myPicker(vtkPicker::New()),
+  myCellPicker(vtkCellPicker::New())
 {
   mySelectionMode = ActorSelection;
+
+  myPicker->Delete();
+  myCellPicker->Delete();
 }
 
 /*!
@@ -280,13 +306,16 @@ SVTK_SelectorDef
   TMapIOSubIndex::const_iterator anIter = myMapIOSubIndex.find(theIO);
   if(anIter != myMapIOSubIndex.end()){
     const TColStd_IndexedMapOfInteger& aMapIndex = anIter->second.myMap;
-    return aMapIndex.Contains( theIndex ) == Standard_True;
+    return aMapIndex.Contains(theIndex);
   }
 
   return false;
 }
 
-static bool removeIndex(TColStd_IndexedMapOfInteger& theMapIndex, const int theIndex)
+static 
+bool
+removeIndex(TColStd_IndexedMapOfInteger& theMapIndex,
+           const int theIndex)
 {
   int anId = theMapIndex.FindIndex(theIndex); // i==0 if Index is not in the MapIndex
   if(anId){
@@ -305,7 +334,7 @@ static bool removeIndex(TColStd_IndexedMapOfInteger& theMapIndex, const int theI
       theMapIndex = aNewMap;
     }
   }
-  return anId != 0;
+  return anId;
 }
 
 /*!
@@ -399,18 +428,18 @@ SVTK_SelectorDef
   }
   TColStd_IndexedMapOfInteger& aMapIndex = anIter->second.myMap;
 
-  bool anIsConatains = aMapIndex.Contains( theIndex ) == Standard_True;
-  if ( anIsConatains )
-    removeIndex( aMapIndex, theIndex );
+  bool anIsConatains = aMapIndex.Contains(theIndex);
+  if(anIsConatains)
+    removeIndex(aMapIndex,theIndex);
   
-  if ( !theIsModeShift )
+  if(!theIsModeShift)
     aMapIndex.Clear();
   
-  if ( !anIsConatains )
+  if(!anIsConatains)
     aMapIndex.Add( theIndex );
 
-  if ( aMapIndex.IsEmpty() )
-    myMapIOSubIndex.erase( theIO );
+  if( aMapIndex.IsEmpty())
+    myMapIOSubIndex.erase(theIO);
 
   return false;
 }
@@ -515,3 +544,34 @@ SVTK_SelectorDef
   return Handle(VTKViewer_Filter)();
 }
 
+SALOME_Actor*
+SVTK_SelectorDef
+::Pick(const SVTK_SelectionEvent* theEvent, vtkRenderer* theRenderer) const
+{
+  myCellPicker->Pick(theEvent->myX,
+                    theEvent->myY, 
+                    0.0,
+                    theRenderer);
+  
+  vtkActorCollection* aListActors = myCellPicker->GetActors();
+  SALOME_Actor* anActor = GetLastSALOMEActor(aListActors);
+  
+  if (! anActor) {
+    myPicker->Pick(theEvent->myX,
+                  theEvent->myY, 
+                  0.0,
+                  theRenderer);
+    aListActors = myPicker->GetActors();
+    anActor = GetLastSALOMEActor(aListActors);
+  }
+  
+  return anActor;
+}
+
+void
+SVTK_SelectorDef
+::SetTolerance(const double& theTolerance) 
+{
+  myPicker->SetTolerance(theTolerance);        
+  myCellPicker->SetTolerance(theTolerance);
+}
index 380e28b31ef2e37ccc9a0265d2be8c0499480c6b..ae11f7710957bbdea5de2dfe728677d5daad52e3 100644 (file)
@@ -29,7 +29,6 @@
 #ifndef SVTK_SELECTOR_H
 #define SVTK_SELECTOR_H
 
-#include "SVTK.h"
 #include "SVTK_Selection.h"
 #include "SALOME_ListIO.hxx"
 #include "VTKViewer_Filter.h"
 
 class SALOME_Actor;
 
+struct SVTK_SelectionEvent;
+
+class vtkRenderer;
+
+
 //! Define an abstract interface for selection in SVTK package
 /*!
   The class implements selection functionality through storing corresponding
@@ -50,7 +54,7 @@ class SALOME_Actor;
   \note
   Also, for each #SALOME_InteractiveObject it tries to keep corresponding refenrence to #SALOME_Actor
  */
-class SVTK_EXPORT SVTK_Selector: public vtkObject
+class SVTK_Selector: public vtkObject
 {
 public:
   static SVTK_Selector* New();
@@ -205,6 +209,15 @@ public:
   virtual
   void 
   EndPickCallback() = 0;
+
+  //----------------------------------------------------------------------------
+  virtual
+  SALOME_Actor*
+  Pick(const SVTK_SelectionEvent* theEvent, vtkRenderer* theRenderer) const =0;
+
+  virtual
+  void
+  SetTolerance(const double& theTolerance) = 0;
 };
 
 
index e20d764ec73c54b1b358f83c8dfd02b5b6a08e6d..634d7297bf2a62b4539877823a9c41317038b920 100644 (file)
@@ -43,6 +43,9 @@ class SALOME_Actor;
 class SVTK_Viewer;
 class SVTK_ViewWindow;
 
+class vtkPicker;
+class vtkCellPicker;
+
 class SVTK_SelectorDef: public SVTK_Selector
 {
 public:
@@ -165,6 +168,15 @@ public:
   void 
   EndPickCallback();
 
+  //----------------------------------------------------------------------------
+  virtual
+  SALOME_Actor*
+  Pick(const SVTK_SelectionEvent* theEvent, vtkRenderer* theRenderer) const;
+
+  virtual
+  void
+  SetTolerance(const double& theTolerance);
+
 private:
   int mySelectionMode;
 
@@ -206,6 +218,9 @@ private:
 
   typedef std::map<TFilterID,Handle(VTKViewer_Filter)> TFilters;
   TFilters myFilters;
+
+  vtkSmartPointer<vtkPicker> myPicker;
+  vtkSmartPointer<vtkCellPicker> myCellPicker;
 };
 
 #endif
index 882728b3ae045ff48e015db26c9a877847ad01cf..34ea473009411a804fdadbc7a1182fefdd093e58 100644 (file)
@@ -259,9 +259,10 @@ SVTK_View
 void
 SVTK_View
 ::SetSelectionTolerance(const double& theTolNodes, 
-                       const double& theTolCell)
+                       const double& theTolCell,
+                       const double& theTolObjects)
 {
-  GetRenderer()->SetSelectionTolerance(theTolNodes,theTolCell);
+  GetRenderer()->SetSelectionTolerance(theTolNodes,theTolCell, theTolObjects);
 }
 
 /*!
index 4c25de9bcead69118b2ec683f2c0e43b6774733a..c7cc984b9aa39ed24b0579882fe1c2ce24b5ef87 100644 (file)
@@ -251,7 +251,8 @@ public:
   //! Redirect the request to #SVTK_Renderer::SetPreselectionProp
   void
   SetSelectionTolerance(const double& theTolNodes = 0.025, 
-                       const double& theTolCell = 0.001);
+                       const double& theTolCell = 0.001,
+                       const double& theTolObjects = 0.025);
 
  protected:  
   int myDisplayMode;
index 667f406c3ab04473b12ad1fd5d5a5f285ef5e465..8fbb70053869eb8781f3500e165e467827ae6121 100755 (executable)
@@ -61,7 +61,6 @@
 #include "VTKViewer_Algorithm.h"
 #include "SVTK_Functor.h"
 
-
 namespace SVTK
 {
   int convertAction( const int accelAction )
@@ -82,10 +81,6 @@ namespace SVTK
   }
 }
 
-
-
-
-
 /*!
   Constructor
 */
@@ -758,9 +753,10 @@ SVTK_ViewWindow
 void
 SVTK_ViewWindow
 ::SetSelectionTolerance(const double& theTolNodes, 
-                       const double& theTolItems)
+                       const double& theTolItems,
+                       const double& theTolObjects)
 {
-  myView->SetSelectionTolerance(theTolNodes,theTolItems);
+  myView->SetSelectionTolerance(theTolNodes,theTolItems, theTolObjects);
 }
 
 /*!
index 809168505d1be23beb2d4d12669bb44765f6629f..14b79945bd7afa26e1a8241fff25d856c8c20a3a 100755 (executable)
@@ -249,7 +249,8 @@ class SVTK_EXPORT SVTK_ViewWindow : public SUIT_ViewWindow
   virtual
   void
   SetSelectionTolerance(const double& theTolNodes = 0.025, 
-                       const double& theTolCell = 0.001);
+                       const double& theTolCell = 0.001,
+                       const double& theTolObjects = 0.025);
 
   //! Methods to save/restore visual parameters of a view (pan, zoom, etc.)
   virtual 
index 5f061a64bc52ef94caacb6cac3bc00f9f4a64045..51ae5356889047cbe5e5ef5d93e14b00d571b427 100755 (executable)
@@ -214,3 +214,106 @@ ComputeTrihedronSize( vtkRenderer* theRenderer,
   return fabs( theNewSize - theSize) > theSize * EPS_SIZE ||
          fabs( theNewSize-theSize ) > theNewSize * EPS_SIZE;
 }
+
+bool IsBBEmpty(vtkRenderer* theRenderer)
+{
+  if(!theRenderer)
+    return false;
+
+  vtkFloatingPointType aNewBndBox[6];
+  aNewBndBox[ 0 ] = aNewBndBox[ 2 ] = aNewBndBox[ 4 ] = VTK_LARGE_FLOAT;
+  aNewBndBox[ 1 ] = aNewBndBox[ 3 ] = aNewBndBox[ 5 ] = -VTK_LARGE_FLOAT;
+  
+  // iterate through displayed objects and set size if necessary
+  vtkActorCollection* anActors = theRenderer->GetActors();
+  anActors->InitTraversal();
+  bool isAny = false;
+  while(vtkActor* anAct = anActors->GetNextActor())
+    //if(SALOME_Actor* anActor = dynamic_cast<SALOME_Actor*>(anAct))
+    if(VTKViewer_Actor* anActor = VTKViewer_Actor::SafeDownCast(anAct))
+      if(anActor->GetVisibility() && !anActor->IsInfinitive())
+      {
+       vtkFloatingPointType *aBounds = anActor->GetBounds();
+       if(aBounds[0] > -VTK_LARGE_FLOAT && aBounds[1] < VTK_LARGE_FLOAT &&
+          aBounds[2] > -VTK_LARGE_FLOAT && aBounds[3] < VTK_LARGE_FLOAT &&
+          aBounds[4] > -VTK_LARGE_FLOAT && aBounds[5] < VTK_LARGE_FLOAT)
+         isAny = true;
+      }
+  
+  return !isAny;
+}
+
+bool ComputeBBCenter(vtkRenderer* theRenderer, vtkFloatingPointType theCenter[3])
+{  
+  theCenter[0] = theCenter[1] = theCenter[2] = 0.0;
+  
+  if(!theRenderer)
+    return false;
+
+  vtkFloatingPointType aNewBndBox[6];
+  aNewBndBox[ 0 ] = aNewBndBox[ 2 ] = aNewBndBox[ 4 ] = VTK_LARGE_FLOAT;
+  aNewBndBox[ 1 ] = aNewBndBox[ 3 ] = aNewBndBox[ 5 ] = -VTK_LARGE_FLOAT;
+
+  // iterate through displayed objects and set size if necessary
+  vtkActorCollection* anActors = theRenderer->GetActors();
+  anActors->InitTraversal();
+  bool isAny = false;
+  while(vtkActor* anAct = anActors->GetNextActor())
+  {
+    //if(SALOME_Actor* anActor = dynamic_cast<SALOME_Actor*>(anAct))
+    if(VTKViewer_Actor* anActor = VTKViewer_Actor::SafeDownCast(anAct))
+    {
+      if(anActor->GetVisibility() && !anActor->IsInfinitive())
+      {
+       vtkFloatingPointType *aBounds = anActor->GetBounds();
+       if(aBounds[0] > -VTK_LARGE_FLOAT && aBounds[1] < VTK_LARGE_FLOAT &&
+          aBounds[2] > -VTK_LARGE_FLOAT && aBounds[3] < VTK_LARGE_FLOAT &&
+          aBounds[4] > -VTK_LARGE_FLOAT && aBounds[5] < VTK_LARGE_FLOAT)
+       {
+         for(int i = 0; i < 5; i = i + 2){
+           if(aBounds[i] < aNewBndBox[i]) 
+             aNewBndBox[i] = aBounds[i];
+           if(aBounds[i+1] > aNewBndBox[i+1]) 
+             aNewBndBox[i+1] = aBounds[i+1];
+         }
+         isAny = true;
+       }
+      }
+    }
+  }
+  
+  if ( !isAny )
+  {
+    // null bounding box => the center is (0,0,0)
+    return true;
+  }
+
+  if(aNewBndBox[0] > -VTK_LARGE_FLOAT && aNewBndBox[1] < VTK_LARGE_FLOAT &&
+     aNewBndBox[2] > -VTK_LARGE_FLOAT && aNewBndBox[3] < VTK_LARGE_FLOAT &&
+     aNewBndBox[4] > -VTK_LARGE_FLOAT && aNewBndBox[5] < VTK_LARGE_FLOAT)
+  {
+    static vtkFloatingPointType MIN_DISTANCE = 1.0 / VTK_LARGE_FLOAT;
+    
+    vtkFloatingPointType aLength = aNewBndBox[1]-aNewBndBox[0];
+    aLength = max((aNewBndBox[3]-aNewBndBox[2]),aLength);
+    aLength = max((aNewBndBox[5]-aNewBndBox[4]),aLength);
+    
+    if(aLength < MIN_DISTANCE)
+      return false;
+
+    vtkFloatingPointType aWidth = 
+      sqrt((aNewBndBox[1]-aNewBndBox[0])*(aNewBndBox[1]-aNewBndBox[0]) +
+          (aNewBndBox[3]-aNewBndBox[2])*(aNewBndBox[3]-aNewBndBox[2]) +
+          (aNewBndBox[5]-aNewBndBox[4])*(aNewBndBox[5]-aNewBndBox[4]));
+    
+    if(aWidth < MIN_DISTANCE)
+      return false;
+
+    theCenter[0] = (aNewBndBox[0] + aNewBndBox[1])/2.0;
+    theCenter[1] = (aNewBndBox[2] + aNewBndBox[3])/2.0;
+    theCenter[2] = (aNewBndBox[4] + aNewBndBox[5])/2.0;
+    return true;
+  }
+
+  return false;
+}
\ No newline at end of file
index 7ef9cc550c63e20bf47310a7d1eda3b28fb76d4b..785d14fbde7fc223db2f5437163f220013c1fbf1 100755 (executable)
@@ -47,4 +47,12 @@ ComputeTrihedronSize(vtkRenderer* theRenderer,
                     const vtkFloatingPointType theSize, 
                     const vtkFloatingPointType theSizeInPercents);
 
+VTKVIEWER_EXPORT
+extern
+bool IsBBEmpty(vtkRenderer* theRenderer);
+VTKVIEWER_EXPORT
+extern
+bool ComputeBBCenter(vtkRenderer* theRenderer, 
+                    vtkFloatingPointType theCenter[3]);
+
 #endif