0026413: Visualization, SelectMgr_ViewerSelector - Pixel tolerance is overridden...
[occt.git] / src / IVtkOCC / IVtkOCC_ViewerSelector.cxx
1 // Created on: 2011-10-20 
2 // Created by: Roman KOZLOV
3 // Copyright (c) 2011-2014 OPEN CASCADE SAS 
4 // 
5 // This file is part of Open CASCADE Technology software library.
6 //
7 // This library is free software; you can redistribute it and/or modify it under
8 // the terms of the GNU Lesser General Public License version 2.1 as published
9 // by the Free Software Foundation, with special exception defined in the file
10 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
11 // distribution for complete text of the license and disclaimer of any warranty.
12 //
13 // Alternatively, this file may be used under the terms of Open CASCADE
14 // commercial license or contractual agreement.
15
16 #include <IVtkOCC_ViewerSelector.hxx>
17 #include <Select3D_SensitiveBox.hxx>
18 #include <TColgp_Array1OfPnt2d.hxx>
19 #include <gp_Quaternion.hxx>
20 #include <Graphic3d_Camera.hxx>
21
22
23 //============================================================================
24 // Method:  Constructor
25 // Purpose:
26 //============================================================================
27 IVtkOCC_ViewerSelector::IVtkOCC_ViewerSelector()
28 : SelectMgr_ViewerSelector(),
29 myPixTol(2),
30 myToUpdateTol(Standard_True) {}
31
32 //============================================================================
33 // Method:  Pick
34 // Purpose: Implements point picking
35 //============================================================================
36 void IVtkOCC_ViewerSelector::Pick (const Standard_Integer theXPix,
37                                    const Standard_Integer theYPix,
38                                    const IVtk_IView::Handle&    theView)
39 {
40   if (myToUpdateTol)
41   {
42     // Compute and set a sensitivity tolerance according to the renderer (viewport).
43     // TODO: Think if this works well in perspective view...'cause result depends
44     // on position on the screen, but we always use the point close to the
45     // screen's origin...
46     mySelectingVolumeMgr.SetPixelTolerance (myPixTol);
47
48     myToUpdateTol = Standard_False;
49   }
50
51   Standard_Integer aWidth = 0, aHeight = 0;
52   Graphic3d_Mat4d aProj, anOrient;
53   Standard_Boolean isOrthographic = Standard_False;
54   Standard_Real aX = RealLast(), aY = RealLast();
55   Standard_Real aVpWidth = RealLast(), aVpHeight = RealLast();
56
57   mySelectingVolumeMgr.SetActiveSelectionType (SelectMgr_SelectingVolumeManager::Point);
58   theView->GetCamera (aProj, anOrient, isOrthographic);
59   mySelectingVolumeMgr.SetCamera (aProj, anOrient, isOrthographic);
60
61   theView->GetWindowSize (aWidth, aHeight);
62   mySelectingVolumeMgr.SetWindowSize (aWidth, aHeight);
63
64   theView->GetViewport (aX, aY, aVpWidth, aVpHeight);
65   mySelectingVolumeMgr.SetViewport (aX, aY, aVpWidth, aVpHeight);
66
67   gp_Pnt2d aMousePos (static_cast<Standard_Real> (theXPix),
68                       static_cast<Standard_Real> (theYPix));
69   mySelectingVolumeMgr.BuildSelectingVolume (aMousePos);
70
71   TraverseSensitives();
72 }
73
74 //============================================================================
75 // Method:  Pick
76 // Purpose: Picking by rectangle
77 //============================================================================
78 void IVtkOCC_ViewerSelector::Pick (const Standard_Integer    theXMin,
79                                    const Standard_Integer    theYMin,
80                                    const Standard_Integer    theXMax,
81                                    const Standard_Integer    theYMax,
82                                    const IVtk_IView::Handle& theView)
83 {
84   if (myToUpdateTol)
85   {
86     // Compute and set a sensitivity tolerance according to the renderer (viewport).
87     // TODO: Think if this works well in perspective view...'cause result depends
88     // on position on the screen, but we always use the point close to the
89     // screen's origin...
90     mySelectingVolumeMgr.SetPixelTolerance (myPixTol);
91
92     myToUpdateTol = Standard_False;
93   }
94
95   Standard_Integer aWidth = 0, aHeight = 0;
96   Graphic3d_Mat4d aProj, anOrient;
97   Standard_Boolean isOrthographic = Standard_False;
98   Standard_Real aX = RealLast(), aY = RealLast();
99   Standard_Real aVpWidth = RealLast(), aVpHeight = RealLast();
100
101   mySelectingVolumeMgr.SetActiveSelectionType (SelectMgr_SelectingVolumeManager::Box);
102   theView->GetCamera (aProj, anOrient, isOrthographic);
103   mySelectingVolumeMgr.SetCamera (aProj, anOrient, isOrthographic);
104
105   theView->GetWindowSize (aWidth, aHeight);
106   mySelectingVolumeMgr.SetWindowSize (aWidth, aHeight);
107
108   theView->GetViewport (aX, aY, aVpWidth, aVpHeight);
109   mySelectingVolumeMgr.SetViewport (aX, aY, aVpWidth, aVpHeight);
110
111   gp_Pnt2d aMinMousePos (static_cast<Standard_Real> (theXMin),
112                          static_cast<Standard_Real> (theYMin));
113   gp_Pnt2d aMaxMousePos (static_cast<Standard_Real> (theXMax),
114                          static_cast<Standard_Real> (theYMax));
115
116   mySelectingVolumeMgr.BuildSelectingVolume (aMinMousePos,
117                                              aMaxMousePos);
118
119   TraverseSensitives();
120 }
121
122 //============================================================================
123 // Method:  Pick
124 // Purpose:
125 //============================================================================
126 void IVtkOCC_ViewerSelector::Pick (double**                  thePoly,
127                                    const int                 theNbPoints,
128                                    const IVtk_IView::Handle& theView)
129 {
130   TColgp_Array1OfPnt2d aPolyline (1, theNbPoints);
131
132   if (myToUpdateTol)
133   {
134     // Compute and set a sensitivity tolerance according to the renderer (viewport).
135     // TODO: Think if this works well in perspective view...'cause result depends
136     // on position on the screen, but we always use the point close to the
137     // screen's origin...
138     mySelectingVolumeMgr.SetPixelTolerance (myPixTol);
139
140     myToUpdateTol = Standard_False;
141   }
142
143   // Build TColgp_Array1OfPnt2d from input array of doubles
144   gp_XYZ aWorldPnt;
145
146   for (Standard_Integer anIt = 0; anIt < theNbPoints; anIt++)
147   {
148     gp_XY aDispPnt = thePoly[anIt][2] != 0 ? gp_XY (thePoly[anIt][0] / thePoly[anIt][2], thePoly[anIt][1] / thePoly[anIt][2])
149                                            : gp_XY (thePoly[anIt][0], thePoly[anIt][1]);
150     aPolyline.SetValue (anIt + 1, aDispPnt);
151   }
152
153   Standard_Integer aWidth = 0, aHeight = 0;
154   Graphic3d_Mat4d aProj, anOrient;
155   Standard_Boolean isOrthographic = Standard_False;
156   Standard_Real aX = RealLast(), aY = RealLast();
157   Standard_Real aVpWidth = RealLast(), aVpHeight = RealLast();
158
159   mySelectingVolumeMgr.SetActiveSelectionType (SelectMgr_SelectingVolumeManager::Polyline);
160   theView->GetCamera (aProj, anOrient, isOrthographic);
161   mySelectingVolumeMgr.SetCamera (aProj, anOrient, isOrthographic);
162
163   theView->GetWindowSize (aWidth, aHeight);
164   mySelectingVolumeMgr.SetWindowSize (aWidth, aHeight);
165
166   theView->GetViewport (aX, aY, aVpWidth, aVpHeight);
167   mySelectingVolumeMgr.SetViewport (aX, aY, aVpWidth, aVpHeight);
168
169   mySelectingVolumeMgr.BuildSelectingVolume (aPolyline);
170
171   TraverseSensitives();
172 }
173
174 //============================================================================
175 // Method:  Activate
176 // Purpose: Activates the given selection
177 //============================================================================
178 void IVtkOCC_ViewerSelector::Activate (const Handle(SelectMgr_Selection)& theSelection)
179 {
180   for (theSelection->Init(); theSelection->More(); theSelection->Next())
181   {
182     theSelection->Sensitive()->SetActiveForSelection();
183   }
184
185   theSelection->SetSelectionState (SelectMgr_SOS_Activated);
186
187   myTolerances.Add (theSelection->Sensitivity());
188   myToUpdateTolerance = Standard_True;
189 }
190
191 //============================================================================
192 // Method:  Deactivate
193 // Purpose: Deactivate the given selection
194 //============================================================================
195 void IVtkOCC_ViewerSelector::Deactivate (const Handle(SelectMgr_Selection)& theSelection)
196 {
197   for (theSelection->Init(); theSelection->More(); theSelection->Next())
198   {
199     theSelection->Sensitive()->ResetSelectionActiveStatus();
200   }
201
202   theSelection->SetSelectionState (SelectMgr_SOS_Deactivated);
203
204   myTolerances.Decrement (theSelection->Sensitivity());
205   myToUpdateTolerance = Standard_True;
206 }