1 // Copyright (c) 2016-2019 OPEN CASCADE SAS 2 // 3 // This file is part of Open CASCADE Technology software library. 4 // 5 // This library is free software; you can redistribute it and/or modify it under 6 // the terms of the GNU Lesser General Public License version 2.1 as published 7 // by the Free Software Foundation, with special exception defined in the file 8 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT 9 // distribution for complete text of the license and disclaimer of any warranty. 10 // 11 // Alternatively, this file may be used under the terms of Open CASCADE 12 // commercial license or contractual agreement. 13 14 #ifndef _AIS_ViewController_HeaderFile 15 #define _AIS_ViewController_HeaderFile 16 17 #include <Aspect_VKeySet.hxx> 18 #include <Aspect_TouchMap.hxx> 19 #include <AIS_DragAction.hxx> 20 #include <AIS_MouseGesture.hxx> 21 #include <AIS_NavigationMode.hxx> 22 #include <AIS_ViewInputBuffer.hxx> 23 #include <AIS_RotationMode.hxx> 24 #include <AIS_WalkDelta.hxx> 25 26 #include <gp_Pnt.hxx> 27 #include <Graphic3d_Vec3.hxx> 28 #include <NCollection_Array1.hxx> 29 #include <OSD_Timer.hxx> 30 #include <Precision.hxx> 31 #include <Standard_Mutex.hxx> 32 33 class AIS_AnimationCamera; 34 class AIS_InteractiveObject; 35 class AIS_InteractiveContext; 36 class AIS_Point; 37 class AIS_RubberBand; 38 class V3d_View; 39 40 //! Auxiliary structure for handling viewer events between GUI and Rendering threads. 41 //! 42 //! Class implements the following features: 43 //! - Buffers storing the state of user input (mouse, touches and keyboard). 44 //! - Mapping mouse/multi-touch input to View camera manipulations (panning/rotating/zooming). 45 //! - Input events are not applied immediately but queued for separate processing from two working threads 46 //! UI thread receiving user input and Rendering thread for OCCT 3D Viewer drawing. 47 class AIS_ViewController 48 { 49 public: 50 51 //! Empty constructor. 52 Standard_EXPORT AIS_ViewController(); 53 54 //! Return input buffer. InputBuffer(AIS_ViewInputBufferType theType) const55 const AIS_ViewInputBuffer& InputBuffer (AIS_ViewInputBufferType theType) const { return theType == AIS_ViewInputBufferType_UI ? myUI : myGL; } 56 57 //! Return input buffer. ChangeInputBuffer(AIS_ViewInputBufferType theType)58 AIS_ViewInputBuffer& ChangeInputBuffer (AIS_ViewInputBufferType theType) { return theType == AIS_ViewInputBufferType_UI ? myUI : myGL; } 59 60 //! Return view animation; empty (but not NULL) animation by default. Handle(AIS_AnimationCamera)61 const Handle(AIS_AnimationCamera)& ViewAnimation() const { return myViewAnimation; } 62 63 //! Set view animation to be handled within handleViewRedraw(). SetViewAnimation(const Handle (AIS_AnimationCamera)& theAnimation)64 void SetViewAnimation (const Handle(AIS_AnimationCamera)& theAnimation) { myViewAnimation = theAnimation; } 65 66 //! Interrupt active view animation. 67 Standard_EXPORT void AbortViewAnimation(); 68 69 public: //! @name global parameters 70 71 //! Return camera rotation mode, AIS_RotationMode_BndBoxActive by default. RotationMode() const72 AIS_RotationMode RotationMode() const { return myRotationMode; } 73 74 //! Set camera rotation mode. SetRotationMode(AIS_RotationMode theMode)75 void SetRotationMode (AIS_RotationMode theMode) { myRotationMode = theMode; } 76 77 //! Return camera navigation mode; AIS_NavigationMode_Orbit by default. NavigationMode() const78 AIS_NavigationMode NavigationMode() const { return myNavigationMode; } 79 80 //! Set camera navigation mode. 81 Standard_EXPORT void SetNavigationMode (AIS_NavigationMode theMode); 82 83 //! Return mouse input acceleration ratio in First Person mode; 1.0 by default. MouseAcceleration() const84 float MouseAcceleration() const { return myMouseAccel; } 85 86 //! Set mouse input acceleration ratio. SetMouseAcceleration(float theRatio)87 void SetMouseAcceleration (float theRatio) { myMouseAccel = theRatio; } 88 89 //! Return orbit rotation acceleration ratio; 1.0 by default. OrbitAcceleration() const90 float OrbitAcceleration() const { return myOrbitAccel; } 91 92 //! Set orbit rotation acceleration ratio. SetOrbitAcceleration(float theRatio)93 void SetOrbitAcceleration (float theRatio) { myOrbitAccel = theRatio; } 94 95 //! Return TRUE if panning anchor point within perspective projection should be displayed in 3D Viewer; TRUE by default. ToShowPanAnchorPoint() const96 bool ToShowPanAnchorPoint() const { return myToShowPanAnchorPoint; } 97 98 //! Set if panning anchor point within perspective projection should be displayed in 3D Viewer. SetShowPanAnchorPoint(bool theToShow)99 void SetShowPanAnchorPoint (bool theToShow) { myToShowPanAnchorPoint = theToShow; } 100 101 //! Return TRUE if rotation point should be displayed in 3D Viewer; TRUE by default. ToShowRotateCenter() const102 bool ToShowRotateCenter() const { return myToShowRotateCenter; } 103 104 //! Set if rotation point should be displayed in 3D Viewer. SetShowRotateCenter(bool theToShow)105 void SetShowRotateCenter (bool theToShow) { myToShowRotateCenter = theToShow; } 106 107 //! Return TRUE if camera up orientation within AIS_NavigationMode_Orbit rotation mode should be forced Z up; FALSE by default. ToLockOrbitZUp() const108 bool ToLockOrbitZUp() const { return myToLockOrbitZUp; } 109 110 //! Set if camera up orientation within AIS_NavigationMode_Orbit rotation mode should be forced Z up. SetLockOrbitZUp(bool theToForceUp)111 void SetLockOrbitZUp (bool theToForceUp) { myToLockOrbitZUp = theToForceUp; } 112 113 //! Return TRUE if z-rotation via two-touches gesture is enabled; FALSE by default. ToAllowTouchZRotation() const114 bool ToAllowTouchZRotation() const { return myToAllowTouchZRotation; } 115 116 //! Set if z-rotation via two-touches gesture is enabled. SetAllowTouchZRotation(bool theToEnable)117 void SetAllowTouchZRotation (bool theToEnable) { myToAllowTouchZRotation = theToEnable; } 118 119 //! Return TRUE if camera rotation is allowed; TRUE by default. ToAllowRotation() const120 bool ToAllowRotation() const { return myToAllowRotation; } 121 122 //! Set if camera rotation is allowed. SetAllowRotation(bool theToEnable)123 void SetAllowRotation (bool theToEnable) { myToAllowRotation = theToEnable; } 124 125 //! Return TRUE if panning is allowed; TRUE by default. ToAllowPanning() const126 bool ToAllowPanning() const { return myToAllowPanning; } 127 128 //! Set if panning is allowed. SetAllowPanning(bool theToEnable)129 void SetAllowPanning (bool theToEnable) { myToAllowPanning = theToEnable; } 130 131 //! Return TRUE if zooming is allowed; TRUE by default. ToAllowZooming() const132 bool ToAllowZooming() const { return myToAllowZooming; } 133 134 //! Set if zooming is allowed. SetAllowZooming(bool theToEnable)135 void SetAllowZooming (bool theToEnable) { myToAllowZooming = theToEnable; } 136 137 //! Return TRUE if ZFocus change is allowed; TRUE by default. ToAllowZFocus() const138 bool ToAllowZFocus() const { return myToAllowZFocus; } 139 140 //! Set if ZFocus change is allowed. SetAllowZFocus(bool theToEnable)141 void SetAllowZFocus (bool theToEnable) { myToAllowZFocus = theToEnable; } 142 143 //! Return TRUE if dynamic highlight on mouse move is allowed; TRUE by default. ToAllowHighlight() const144 bool ToAllowHighlight() const { return myToAllowHighlight; } 145 146 //! Set if dragging object is allowed. SetAllowHighlight(bool theToEnable)147 void SetAllowHighlight (bool theToEnable) { myToAllowHighlight = theToEnable; } 148 149 //! Return TRUE if dragging object is allowed; TRUE by default. ToAllowDragging() const150 bool ToAllowDragging() const { return myToAllowDragging; } 151 152 //! Set if dynamic highlight on mouse move is allowed. SetAllowDragging(bool theToEnable)153 void SetAllowDragging (bool theToEnable) { myToAllowDragging = theToEnable; } 154 155 //! Return TRUE if picked point should be projected to picking ray on zooming at point; TRUE by default. ToStickToRayOnZoom() const156 bool ToStickToRayOnZoom() const { return myToStickToRayOnZoom; } 157 158 //! Set if picked point should be projected to picking ray on zooming at point. SetStickToRayOnZoom(bool theToEnable)159 void SetStickToRayOnZoom (bool theToEnable) { myToStickToRayOnZoom = theToEnable; } 160 161 //! Return TRUE if picked point should be projected to picking ray on rotating around point; TRUE by default. ToStickToRayOnRotation() const162 bool ToStickToRayOnRotation() const { return myToStickToRayOnRotation; } 163 164 //! Set if picked point should be projected to picking ray on rotating around point. SetStickToRayOnRotation(bool theToEnable)165 void SetStickToRayOnRotation (bool theToEnable) { myToStickToRayOnRotation = theToEnable; } 166 167 //! Return TRUE if pitch direction should be inverted while processing Aspect_VKey_NavLookUp/Aspect_VKey_NavLookDown; FALSE by default. ToInvertPitch() const168 bool ToInvertPitch() const { return myToInvertPitch; } 169 170 //! Set flag inverting pitch direction. SetInvertPitch(bool theToInvert)171 void SetInvertPitch (bool theToInvert) { myToInvertPitch = theToInvert; } 172 173 //! Return normal walking speed, in m/s; 1.5 by default. WalkSpeedAbsolute() const174 float WalkSpeedAbsolute() const { return myWalkSpeedAbsolute; } 175 176 //! Set normal walking speed, in m/s; 1.5 by default. SetWalkSpeedAbsolute(float theSpeed)177 void SetWalkSpeedAbsolute (float theSpeed) { myWalkSpeedAbsolute = theSpeed; } 178 179 //! Return walking speed relative to scene bounding box; 0.1 by default. WalkSpeedRelative() const180 float WalkSpeedRelative() const { return myWalkSpeedRelative; } 181 182 //! Set walking speed relative to scene bounding box. SetWalkSpeedRelative(float theFactor)183 void SetWalkSpeedRelative (float theFactor) { myWalkSpeedRelative = theFactor; } 184 185 //! Return active thrust value; 0.0f by default. ThrustSpeed() const186 float ThrustSpeed() const { return myThrustSpeed; } 187 188 //! Set active thrust value. SetThrustSpeed(float theSpeed)189 void SetThrustSpeed (float theSpeed) { myThrustSpeed = theSpeed; } 190 191 //! Return TRUE if previous position of MoveTo has been defined. HasPreviousMoveTo() const192 bool HasPreviousMoveTo() const { return myPrevMoveTo != Graphic3d_Vec2i (-1); } 193 194 //! Return previous position of MoveTo event in 3D viewer. PreviousMoveTo() const195 const Graphic3d_Vec2i& PreviousMoveTo() const { return myPrevMoveTo; } 196 197 //! Reset previous position of MoveTo. ResetPreviousMoveTo()198 void ResetPreviousMoveTo() { myPrevMoveTo = Graphic3d_Vec2i (-1); } 199 200 public: //! @name keyboard input 201 202 //! Return keyboard state. Keys() const203 const Aspect_VKeySet& Keys() const { return myKeys; } 204 205 //! Return keyboard state. ChangeKeys()206 Aspect_VKeySet& ChangeKeys() { return myKeys; } 207 208 //! Press key. 209 //! @param theKey key pressed 210 //! @param theTime event timestamp 211 Standard_EXPORT virtual void KeyDown (Aspect_VKey theKey, 212 double theTime, 213 double thePressure = 1.0); 214 215 //! Release key. 216 //! @param theKey key pressed 217 //! @param theTime event timestamp 218 Standard_EXPORT virtual void KeyUp (Aspect_VKey theKey, 219 double theTime); 220 221 //! Simulate key up/down events from axis value. 222 Standard_EXPORT virtual void KeyFromAxis (Aspect_VKey theNegative, 223 Aspect_VKey thePositive, 224 double theTime, 225 double thePressure); 226 227 //! Fetch active navigation actions. 228 Standard_EXPORT AIS_WalkDelta FetchNavigationKeys (Standard_Real theCrouchRatio, 229 Standard_Real theRunRatio); 230 231 public: //! @name mouse input 232 233 //! Return map defining mouse gestures. MouseGestureMap() const234 const AIS_MouseGestureMap& MouseGestureMap() const { return myMouseGestureMap; } 235 236 //! Return map defining mouse gestures. ChangeMouseGestureMap()237 AIS_MouseGestureMap& ChangeMouseGestureMap() { return myMouseGestureMap; } 238 239 //! Return double click interval in seconds; 0.4 by default. MouseDoubleClickInterval() const240 double MouseDoubleClickInterval() const { return myMouseDoubleClickInt; } 241 242 //! Set double click interval in seconds. SetMouseDoubleClickInterval(double theSeconds)243 void SetMouseDoubleClickInterval (double theSeconds) { myMouseDoubleClickInt = theSeconds; } 244 245 //! Perform selection in 3D viewer. 246 //! This method is expected to be called from UI thread. 247 //! @param thePnt picking point 248 //! @param theIsXOR XOR selection flag 249 Standard_EXPORT virtual void SelectInViewer (const Graphic3d_Vec2i& thePnt, 250 const bool theIsXOR = false); 251 252 //! Perform selection in 3D viewer. 253 //! This method is expected to be called from UI thread. 254 //! @param thePnts picking point 255 //! @param theIsXOR XOR selection flag 256 Standard_EXPORT virtual void SelectInViewer (const NCollection_Sequence<Graphic3d_Vec2i>& thePnts, 257 const bool theIsXOR = false); 258 259 //! Update rectangle selection tool. 260 //! This method is expected to be called from UI thread. 261 //! @param thePntFrom rectangle first corner 262 //! @param thePntTo rectangle another corner 263 //! @param theIsXOR XOR selection flag 264 Standard_EXPORT virtual void UpdateRubberBand (const Graphic3d_Vec2i& thePntFrom, 265 const Graphic3d_Vec2i& thePntTo, 266 const bool theIsXOR = false); 267 268 //! Update polygonal selection tool. 269 //! This method is expected to be called from UI thread. 270 //! @param thePnt new point to add to polygon 271 //! @param theToAppend append new point or update the last point 272 Standard_EXPORT virtual void UpdatePolySelection (const Graphic3d_Vec2i& thePnt, 273 bool theToAppend); 274 275 //! Update zoom event (e.g. from mouse scroll). 276 //! This method is expected to be called from UI thread. 277 //! @param theDelta mouse cursor position to zoom at and zoom delta 278 //! @return TRUE if new zoom event has been created or FALSE if existing one has been updated 279 Standard_EXPORT virtual bool UpdateZoom (const Aspect_ScrollDelta& theDelta); 280 281 //! Update Z rotation event. 282 //! @param theAngle rotation angle, in radians. 283 //! @return TRUE if new zoom event has been created or FALSE if existing one has been updated 284 Standard_EXPORT virtual bool UpdateZRotation (double theAngle); 285 286 //! Update mouse scroll event; redirects to UpdateZoom by default. 287 //! This method is expected to be called from UI thread. 288 //! @param theDelta mouse cursor position and delta 289 //! @return TRUE if new event has been created or FALSE if existing one has been updated 290 Standard_EXPORT virtual bool UpdateMouseScroll (const Aspect_ScrollDelta& theDelta); 291 292 //! Handle mouse button press/release event. 293 //! This method is expected to be called from UI thread. 294 //! @param thePoint mouse cursor position 295 //! @param theButtons pressed buttons 296 //! @param theModifiers key modifiers 297 //! @param theIsEmulated if TRUE then mouse event comes NOT from real mouse 298 //! but emulated from non-precise input like touch on screen 299 //! @return TRUE if View should be redrawn 300 Standard_EXPORT virtual bool UpdateMouseButtons (const Graphic3d_Vec2i& thePoint, 301 Aspect_VKeyMouse theButtons, 302 Aspect_VKeyFlags theModifiers, 303 bool theIsEmulated); 304 305 //! Handle mouse cursor movement event. 306 //! This method is expected to be called from UI thread. 307 //! @param thePoint mouse cursor position 308 //! @param theButtons pressed buttons 309 //! @param theModifiers key modifiers 310 //! @param theIsEmulated if TRUE then mouse event comes NOT from real mouse 311 //! but emulated from non-precise input like touch on screen 312 //! @return TRUE if View should be redrawn 313 Standard_EXPORT virtual bool UpdateMousePosition (const Graphic3d_Vec2i& thePoint, 314 Aspect_VKeyMouse theButtons, 315 Aspect_VKeyFlags theModifiers, 316 bool theIsEmulated); 317 318 //! Handle mouse button press event. 319 //! This method is expected to be called from UI thread. 320 //! @param thePoint mouse cursor position 321 //! @param theButton pressed button 322 //! @param theModifiers key modifiers 323 //! @param theIsEmulated if TRUE then mouse event comes NOT from real mouse 324 //! but emulated from non-precise input like touch on screen 325 //! @return TRUE if View should be redrawn PressMouseButton(const Graphic3d_Vec2i & thePoint,Aspect_VKeyMouse theButton,Aspect_VKeyFlags theModifiers,bool theIsEmulated)326 bool PressMouseButton (const Graphic3d_Vec2i& thePoint, 327 Aspect_VKeyMouse theButton, 328 Aspect_VKeyFlags theModifiers, 329 bool theIsEmulated) 330 { 331 return UpdateMouseButtons (thePoint, myMousePressed | theButton, theModifiers, theIsEmulated); 332 } 333 334 //! Handle mouse button release event. 335 //! This method is expected to be called from UI thread. 336 //! @param thePoint mouse cursor position 337 //! @param theButton released button 338 //! @param theModifiers key modifiers 339 //! @param theIsEmulated if TRUE then mouse event comes NOT from real mouse 340 //! but emulated from non-precise input like touch on screen 341 //! @return TRUE if View should be redrawn ReleaseMouseButton(const Graphic3d_Vec2i & thePoint,Aspect_VKeyMouse theButton,Aspect_VKeyFlags theModifiers,bool theIsEmulated)342 bool ReleaseMouseButton (const Graphic3d_Vec2i& thePoint, 343 Aspect_VKeyMouse theButton, 344 Aspect_VKeyFlags theModifiers, 345 bool theIsEmulated) 346 { 347 Aspect_VKeyMouse aButtons = myMousePressed & (~theButton); 348 return UpdateMouseButtons (thePoint, aButtons, theModifiers, theIsEmulated); 349 } 350 351 //! Handle mouse button click event (emulated by UpdateMouseButtons() while releasing single button). 352 //! Note that as this method is called by UpdateMouseButtons(), it should be executed from UI thread. 353 //! Default implementation redirects to SelectInViewer(). 354 //! This method is expected to be called from UI thread. 355 //! @param thePoint mouse cursor position 356 //! @param theButton clicked button 357 //! @param theModifiers key modifiers 358 //! @param theIsDoubleClick flag indicating double mouse click 359 //! @return TRUE if View should be redrawn 360 Standard_EXPORT virtual bool UpdateMouseClick (const Graphic3d_Vec2i& thePoint, 361 Aspect_VKeyMouse theButton, 362 Aspect_VKeyFlags theModifiers, 363 bool theIsDoubleClick); 364 365 //! Return currently pressed mouse buttons. PressedMouseButtons() const366 Aspect_VKeyMouse PressedMouseButtons() const { return myMousePressed; } 367 368 //! Return active key modifiers passed with last mouse event. LastMouseFlags() const369 Aspect_VKeyFlags LastMouseFlags() const { return myMouseModifiers; } 370 371 //! Return last mouse position. LastMousePosition() const372 const Graphic3d_Vec2i& LastMousePosition() const { return myMousePositionLast; } 373 374 public: //! @name multi-touch input 375 376 //! Return scale factor for adjusting tolerances for starting multi-touch gestures; 1.0 by default 377 //! This scale factor is expected to be computed from touch screen resolution. TouchToleranceScale() const378 float TouchToleranceScale() const { return myTouchToleranceScale; } 379 380 //! Set scale factor for adjusting tolerances for starting multi-touch gestures. SetTouchToleranceScale(float theTolerance)381 void SetTouchToleranceScale (float theTolerance) { myTouchToleranceScale = theTolerance; } 382 383 //! Return TRUE if touches map is not empty. HasTouchPoints() const384 bool HasTouchPoints() const { return !myTouchPoints.IsEmpty(); } 385 386 //! Add touch point with the given ID. 387 //! This method is expected to be called from UI thread. 388 //! @param theId touch unique identifier 389 //! @param thePnt touch coordinates 390 //! @param theClearBefore if TRUE previously registered touches will be removed 391 Standard_EXPORT virtual void AddTouchPoint (Standard_Size theId, 392 const Graphic3d_Vec2d& thePnt, 393 Standard_Boolean theClearBefore = false); 394 395 //! Remove touch point with the given ID. 396 //! This method is expected to be called from UI thread. 397 //! @param theId touch unique identifier 398 //! @param theClearSelectPnts if TRUE will initiate clearing of selection points 399 //! @return TRUE if point has been removed 400 Standard_EXPORT virtual bool RemoveTouchPoint (Standard_Size theId, 401 Standard_Boolean theClearSelectPnts = false); 402 403 //! Update touch point with the given ID. 404 //! If point with specified ID was not registered before, it will be added. 405 //! This method is expected to be called from UI thread. 406 //! @param theId touch unique identifier 407 //! @param thePnt touch coordinates 408 Standard_EXPORT virtual void UpdateTouchPoint (Standard_Size theId, 409 const Graphic3d_Vec2d& thePnt); 410 411 public: 412 413 //! Return event time (e.g. current time). EventTime() const414 double EventTime() const { return myEventTimer.ElapsedTime(); } 415 416 //! Reset input state (pressed keys, mouse buttons, etc.) e.g. on window focus loss. 417 //! This method is expected to be called from UI thread. 418 Standard_EXPORT virtual void ResetViewInput(); 419 420 //! Reset view orientation. 421 //! This method is expected to be called from UI thread. 422 Standard_EXPORT virtual void UpdateViewOrientation (V3d_TypeOfOrientation theOrientation, 423 bool theToFitAll); 424 425 //! Update buffer for rendering thread. 426 //! This method is expected to be called within synchronization barrier between GUI 427 //! and Rendering threads (e.g. GUI thread should be locked beforehand to avoid data races). 428 //! @param theCtx interactive context 429 //! @param theView active view 430 //! @param theToHandle if TRUE, the HandleViewEvents() will be called 431 Standard_EXPORT virtual void FlushViewEvents (const Handle(AIS_InteractiveContext)& theCtx, 432 const Handle(V3d_View)& theView, 433 Standard_Boolean theToHandle = Standard_False); 434 435 //! Process events within rendering thread. 436 Standard_EXPORT virtual void HandleViewEvents (const Handle(AIS_InteractiveContext)& theCtx, 437 const Handle(V3d_View)& theView); 438 439 public: 440 441 //! Callback called by handleMoveTo() on Selection in 3D Viewer. 442 //! This method is expected to be called from rendering thread. 443 Standard_EXPORT virtual void OnSelectionChanged (const Handle(AIS_InteractiveContext)& theCtx, 444 const Handle(V3d_View)& theView); 445 446 //! Callback called by handleMoveTo() on dragging object in 3D Viewer. 447 //! This method is expected to be called from rendering thread. 448 Standard_EXPORT virtual void OnObjectDragged (const Handle(AIS_InteractiveContext)& theCtx, 449 const Handle(V3d_View)& theView, 450 AIS_DragAction theAction); 451 452 //! Pick closest point under mouse cursor. 453 //! This method is expected to be called from rendering thread. 454 //! @param thePnt [out] result point 455 //! @param theCtx [in] interactive context 456 //! @param theView [in] active view 457 //! @param theCursor [in] mouse cursor 458 //! @param theToStickToPickRay [in] when TRUE, the result point will lie on picking ray 459 //! @return TRUE if result has been found 460 Standard_EXPORT virtual bool PickPoint (gp_Pnt& thePnt, 461 const Handle(AIS_InteractiveContext)& theCtx, 462 const Handle(V3d_View)& theView, 463 const Graphic3d_Vec2i& theCursor, 464 bool theToStickToPickRay); 465 466 //! Compute rotation gravity center point depending on rotation mode. 467 //! This method is expected to be called from rendering thread. 468 Standard_EXPORT virtual gp_Pnt GravityPoint (const Handle(AIS_InteractiveContext)& theCtx, 469 const Handle(V3d_View)& theView); 470 471 public: 472 473 //! Perform camera actions. 474 //! This method is expected to be called from rendering thread. 475 Standard_EXPORT virtual void handleCameraActions (const Handle(AIS_InteractiveContext)& theCtx, 476 const Handle(V3d_View)& theView, 477 const AIS_WalkDelta& theWalk); 478 479 //! Perform moveto/selection/dragging. 480 //! This method is expected to be called from rendering thread. 481 Standard_EXPORT virtual void handleMoveTo (const Handle(AIS_InteractiveContext)& theCtx, 482 const Handle(V3d_View)& theView); 483 484 //! Return TRUE if another frame should be drawn right after this one. toAskNextFrame() const485 bool toAskNextFrame() const { return myToAskNextFrame; } 486 487 //! Set if another frame should be drawn right after this one. setAskNextFrame(bool theToDraw=true)488 void setAskNextFrame (bool theToDraw = true) { myToAskNextFrame = theToDraw; } 489 490 //! Return if panning anchor point has been defined. hasPanningAnchorPoint() const491 bool hasPanningAnchorPoint() const { return !Precision::IsInfinite (myPanPnt3d.X()); } 492 493 //! Return active panning anchor point. panningAnchorPoint() const494 const gp_Pnt& panningAnchorPoint() const { return myPanPnt3d; } 495 496 //! Set active panning anchor point. setPanningAnchorPoint(const gp_Pnt & thePnt)497 void setPanningAnchorPoint (const gp_Pnt& thePnt) { myPanPnt3d = thePnt; } 498 499 //! Handle panning event myGL.Panning. 500 Standard_EXPORT virtual void handlePanning (const Handle(V3d_View)& theView); 501 502 //! Handle Z rotation event myGL.ZRotate. 503 Standard_EXPORT virtual void handleZRotate (const Handle(V3d_View)& theView); 504 505 //! Return minimal camera distance for zoom operation. MinZoomDistance() const506 double MinZoomDistance() const { return myMinCamDistance; } 507 508 //! Set minimal camera distance for zoom operation. SetMinZoomDistance(double theDist)509 void SetMinZoomDistance (double theDist) { myMinCamDistance = theDist; } 510 511 //! Handle zoom event myGL.ZoomActions. 512 //! This method is expected to be called from rendering thread. 513 Standard_EXPORT virtual void handleZoom (const Handle(V3d_View)& theView, 514 const Aspect_ScrollDelta& theParams, 515 const gp_Pnt* thePnt); 516 517 //! Handle ZScroll event myGL.ZoomActions. 518 //! This method is expected to be called from rendering thread. 519 Standard_EXPORT virtual void handleZFocusScroll (const Handle(V3d_View)& theView, 520 const Aspect_ScrollDelta& theParams); 521 522 //! Handle orbital rotation events myGL.OrbitRotation. 523 //! @param theView view to modify 524 //! @param thePnt 3D point to rotate around 525 //! @param theToLockZUp amend camera to exclude roll angle (put camera Up vector to plane containing global Z and view direction) 526 Standard_EXPORT virtual void handleOrbitRotation (const Handle(V3d_View)& theView, 527 const gp_Pnt& thePnt, 528 bool theToLockZUp); 529 530 //! Handle view direction rotation events myGL.ViewRotation. 531 //! This method is expected to be called from rendering thread. 532 //! @param theView camera to modify 533 //! @param theYawExtra extra yaw increment 534 //! @param thePitchExtra extra pitch increment 535 //! @param theRoll roll value 536 //! @param theToRestartOnIncrement flag indicating flight mode 537 Standard_EXPORT virtual void handleViewRotation (const Handle(V3d_View)& theView, 538 double theYawExtra, 539 double thePitchExtra, 540 double theRoll, 541 bool theToRestartOnIncrement); 542 543 //! Handle view redraw. 544 //! This method is expected to be called from rendering thread. 545 Standard_EXPORT virtual void handleViewRedraw (const Handle(AIS_InteractiveContext)& theCtx, 546 const Handle(V3d_View)& theView); 547 548 protected: 549 550 //! Flush buffers. 551 Standard_EXPORT virtual void flushBuffers (const Handle(AIS_InteractiveContext)& theCtx, 552 const Handle(V3d_View)& theView); 553 554 //! Flush touch gestures. 555 Standard_EXPORT virtual void flushGestures (const Handle(AIS_InteractiveContext)& theCtx, 556 const Handle(V3d_View)& theView); 557 558 //! Return current and previously fetched event times. 559 //! This callback is intended to compute delta between sequentially processed events. 560 //! @param thePrevTime [out] events time fetched previous time by this method 561 //! @param theCurrTime [out] actual events time updateEventsTime(double & thePrevTime,double & theCurrTime)562 void updateEventsTime (double& thePrevTime, 563 double& theCurrTime) 564 { 565 thePrevTime = myLastEventsTime; 566 myLastEventsTime = EventTime(); 567 theCurrTime = myLastEventsTime; 568 } 569 570 //! Perform selection via mouse click. 571 //! This method is expected to be called from rendering thread. 572 Standard_EXPORT virtual void handleSelectionPick (const Handle(AIS_InteractiveContext)& theCtx, 573 const Handle(V3d_View)& theView); 574 575 //! Perform dynamic highlight on mouse move. 576 //! This method is expected to be called from rendering thread. 577 Standard_EXPORT virtual void handleDynamicHighlight (const Handle(AIS_InteractiveContext)& theCtx, 578 const Handle(V3d_View)& theView); 579 580 //! Perform rubber-band selection. 581 //! This method is expected to be called from rendering thread. 582 Standard_EXPORT virtual void handleSelectionPoly (const Handle(AIS_InteractiveContext)& theCtx, 583 const Handle(V3d_View)& theView); 584 585 //! Lazy AIS_InteractiveContext::MoveTo() with myPrevMoveTo check. 586 Standard_EXPORT virtual void contextLazyMoveTo (const Handle(AIS_InteractiveContext)& theCtx, 587 const Handle(V3d_View)& theView, 588 const Graphic3d_Vec2i& thePnt); 589 590 protected: 591 592 AIS_ViewInputBuffer myUI; //!< buffer for UI thread 593 AIS_ViewInputBuffer myGL; //!< buffer for rendering thread 594 595 OSD_Timer myEventTimer; //!< timer for timestamping events 596 Standard_Real myLastEventsTime; //!< last fetched events timer value for computing delta/progress 597 Standard_Boolean myToAskNextFrame; //!< flag indicating that another frame should be drawn right after this one 598 599 Standard_Real myMinCamDistance; //!< minimal camera distance for zoom operation 600 AIS_RotationMode myRotationMode; //!< rotation mode 601 AIS_NavigationMode myNavigationMode; //!< navigation mode (orbit rotation / first person) 602 Standard_ShortReal myMouseAccel; //!< mouse input acceleration ratio in First Person mode 603 Standard_ShortReal myOrbitAccel; //!< Orbit rotation acceleration ratio 604 Standard_Boolean myToShowPanAnchorPoint; //!< option displaying panning anchor point 605 Standard_Boolean myToShowRotateCenter; //!< option displaying rotation center point 606 Standard_Boolean myToLockOrbitZUp; //!< force camera up orientation within AIS_NavigationMode_Orbit rotation mode 607 Standard_Boolean myToInvertPitch; //!< flag inverting pitch direction while processing Aspect_VKey_NavLookUp/Aspect_VKey_NavLookDown 608 Standard_Boolean myToAllowTouchZRotation; //!< enable z-rotation two-touches gesture; FALSE by default 609 Standard_Boolean myToAllowRotation; //!< enable rotation; TRUE by default 610 Standard_Boolean myToAllowPanning; //!< enable panning; TRUE by default 611 Standard_Boolean myToAllowZooming; //!< enable zooming; TRUE by default 612 Standard_Boolean myToAllowZFocus; //!< enable ZFocus change; TRUE by default 613 Standard_Boolean myToAllowHighlight; //!< enable dynamic highlight on mouse move; TRUE by default 614 Standard_Boolean myToAllowDragging; //!< enable dragging object; TRUE by default 615 Standard_Boolean myToStickToRayOnZoom; //!< project picked point to ray while zooming at point, TRUE by default 616 Standard_Boolean myToStickToRayOnRotation; //!< project picked point to ray while rotating around point; TRUE by default 617 618 Standard_ShortReal myWalkSpeedAbsolute; //!< normal walking speed, in m/s; 1.5 by default 619 Standard_ShortReal myWalkSpeedRelative; //!< walking speed relative to scene bounding box; 0.1 by default 620 Standard_ShortReal myThrustSpeed; //!< active thrust value 621 Standard_Boolean myHasThrust; //!< flag indicating active thrust 622 623 Handle(AIS_AnimationCamera) myViewAnimation; //!< view animation 624 Handle(AIS_RubberBand) myRubberBand; //!< Rubber-band presentation 625 Handle(AIS_InteractiveObject) myDragObject; //!< currently dragged object 626 Graphic3d_Vec2i myPrevMoveTo; //!< previous position of MoveTo event in 3D viewer 627 Standard_Boolean myHasHlrOnBeforeRotation; //!< flag for restoring Computed mode after rotation 628 629 protected: //! @name keyboard input variables 630 631 Aspect_VKeySet myKeys; //!< keyboard state 632 633 protected: //! @name mouse input variables 634 635 Standard_Real myMouseClickThreshold; //!< mouse click threshold in pixels; 3 by default 636 Standard_Real myMouseDoubleClickInt; //!< double click interval in seconds; 0.4 by default 637 Standard_ShortReal myScrollZoomRatio; //!< distance ratio for mapping mouse scroll event to zoom; 15.0 by default 638 639 AIS_MouseGestureMap myMouseGestureMap; //!< map defining mouse gestures 640 AIS_MouseGesture myMouseActiveGesture; //!< initiated mouse gesture (by pressing mouse button) 641 Standard_Boolean myMouseActiveIdleRotation; //!< flag indicating view idle rotation state 642 Graphic3d_Vec2i myMousePositionLast; //!< last mouse position 643 Graphic3d_Vec2i myMousePressPoint; //!< mouse position where active gesture was been initiated 644 Graphic3d_Vec2i myMouseProgressPoint; //!< gesture progress 645 OSD_Timer myMouseClickTimer; //!< timer for handling double-click event 646 Standard_Integer myMouseClickCounter; //!< counter for handling double-click event 647 Aspect_VKeyMouse myMousePressed; //!< active mouse buttons 648 Aspect_VKeyFlags myMouseModifiers; //!< active key modifiers passed with last mouse event 649 Standard_Integer myMouseSingleButton; //!< index of mouse button pressed alone (>0) 650 651 protected: //! @name multi-touch input variables 652 653 Standard_ShortReal myTouchToleranceScale; //!< tolerance scale factor; 1.0 by default 654 Standard_ShortReal myTouchRotationThresholdPx; //!< threshold for starting one-touch rotation gesture in pixels; 6 by default 655 Standard_ShortReal myTouchZRotationThreshold; //!< threshold for starting two-touch Z-rotation gesture in radians; 2 degrees by default 656 Standard_ShortReal myTouchPanThresholdPx; //!< threshold for starting two-touch panning gesture in pixels; 4 by default 657 Standard_ShortReal myTouchZoomThresholdPx; //!< threshold for starting two-touch zoom (pitch) gesture in pixels; 6 by default 658 Standard_ShortReal myTouchZoomRatio; //!< distance ratio for mapping two-touch zoom (pitch) gesture from pixels to zoom; 0.13 by default 659 660 Aspect_TouchMap myTouchPoints; //!< map of active touches 661 Graphic3d_Vec2d myStartPanCoord; //!< touch coordinates at the moment of starting panning gesture 662 Graphic3d_Vec2d myStartRotCoord; //!< touch coordinates at the moment of starting rotating gesture 663 Standard_Integer myNbTouchesLast; //!< number of touches within previous gesture flush to track gesture changes 664 Standard_Boolean myUpdateStartPointPan; //!< flag indicating that new anchor point should be picked for starting panning gesture 665 Standard_Boolean myUpdateStartPointRot; //!< flag indicating that new gravity point should be picked for starting rotation gesture 666 Standard_Boolean myUpdateStartPointZRot; //!< flag indicating that new gravity point should be picked for starting Z-rotation gesture 667 668 protected: //! @name rotation/panning transient state variables 669 670 Handle(AIS_Point) myAnchorPointPrs1; //!< anchor point presentation (Graphic3d_ZLayerId_Top) 671 Handle(AIS_Point) myAnchorPointPrs2; //!< anchor point presentation (Graphic3d_ZLayerId_Topmost) 672 gp_Pnt myPanPnt3d; //!< active panning anchor point 673 gp_Pnt myRotatePnt3d; //!< active rotation center of gravity 674 gp_Dir myCamStartOpUp; //!< camera Up direction at the beginning of rotation 675 gp_Dir myCamStartOpDir; //!< camera View direction at the beginning of rotation 676 gp_Pnt myCamStartOpEye; //!< camera Eye position at the beginning of rotation 677 gp_Pnt myCamStartOpCenter; //!< camera Center position at the beginning of rotation 678 gp_Vec myCamStartOpToCenter; //!< vector from rotation gravity point to camera Center at the beginning of rotation 679 gp_Vec myCamStartOpToEye; //!< vector from rotation gravity point to camera Eye at the beginning of rotation 680 Graphic3d_Vec3d myRotateStartYawPitchRoll; //!< camera yaw pitch roll at the beginning of rotation 681 682 }; 683 684 #endif // _AIS_ViewController_HeaderFile 685