1 // Created on: 2012-05-28
3 // Copyright (c) 2011-2014 OPEN CASCADE SAS
5 // This file is part of Open CASCADE Technology software library.
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.
13 // Alternatively, this file may be used under the terms of Open CASCADE
14 // commercial license or contractual agreement.
16 // prevent disabling some MSVC warning messages by VTK headers
21 #include <vtkWin32RenderWindowInteractor.h>
22 #include <vtkWin32OpenGLRenderWindow.h>
25 #include <vtkXRenderWindowInteractor.h>
26 #include <vtkXOpenGLRenderWindow.h>
29 #include <vtkActorCollection.h>
30 #include <vtkCommand.h>
31 #include <vtkObjectFactory.h>
32 #include <vtkSmartPointer.h>
34 #include <IVtkDraw_Interactor.hxx>
40 #include <IVtkTools_ShapePicker.hxx>
41 #include <IVtkTools_SubPolyDataFilter.hxx>
42 #include <IVtkTools_DisplayModeFilter.hxx>
43 #include <IVtkTools_ShapeObject.hxx>
44 #include <IVtkTools_ShapeDataSource.hxx>
46 #include <Message.hxx>
47 #include <Message_Messenger.hxx>
49 //===========================================================
50 // Function : ClearHighlightAndSelection
52 //===========================================================
53 static void ClearHighlightAndSelection (const Handle(ShapePipelineMap)& theMap,
54 const Standard_Boolean doHighlighting,
55 const Standard_Boolean doSelection)
57 if (!doHighlighting && !doSelection)
62 for (ShapePipelineMap::Iterator anIt (*theMap); anIt.More(); anIt.Next())
64 const Handle(IVtkDraw_HighlightAndSelectionPipeline)& aPL = anIt.Value();
68 aPL->ClearHighlightFilters();
73 aPL->ClearSelectionFilters();
78 vtkStandardNewMacro(IVtkDraw_Interactor)
80 //===========================================================
81 // Function : Constructor
83 //===========================================================
84 IVtkDraw_Interactor::IVtkDraw_Interactor()
90 myIsLeftButtonPressed (Standard_False)
94 //===========================================================
95 // Function : Destructor
97 //===========================================================
98 IVtkDraw_Interactor::~IVtkDraw_Interactor()
102 //===========================================================
103 // Function : SetShapePicker
105 //===========================================================
106 void IVtkDraw_Interactor::SetShapePicker (const PSelector& theSelector)
108 mySelector = theSelector;
111 //===========================================================
112 // Function : SetPipelines
114 //===========================================================
115 void IVtkDraw_Interactor::SetPipelines (const Handle(ShapePipelineMap)& thePipelines)
117 myPipelines = thePipelines;
120 //===========================================================
121 // Function : SetOCCWindow
123 //===========================================================
124 void IVtkDraw_Interactor::SetOCCWindow (const Handle(Aspect_Window)& theWindow)
126 myWindow = theWindow;
129 //===========================================================
130 // Function : GetOCCWindow
132 //===========================================================
133 const Handle(Aspect_Window)& IVtkDraw_Interactor::GetOCCWindow() const
138 //===========================================================
139 // Function : IsEnabled
141 //===========================================================
142 Standard_Boolean IVtkDraw_Interactor::IsEnabled() const
144 return (Enabled != 0);
147 //===========================================================
148 // Function : Initialize
150 //===========================================================
151 void IVtkDraw_Interactor::Initialize()
153 // Make sure we have a RenderWindow and camera
154 if (!this->RenderWindow)
156 vtkErrorMacro(<<"No renderer defined!");
160 if (this->Initialized)
165 this->Initialized = 1;
167 // Get the info we need from the RenderingWindow
168 Standard_Integer *aSize;
170 vtkWin32OpenGLRenderWindow *aRenWin;
171 aRenWin = (vtkWin32OpenGLRenderWindow *)(this->RenderWindow);
173 aSize = aRenWin->GetSize();
174 aRenWin->GetPosition();
175 this->myWindowId = aRenWin->GetWindowId();
177 vtkXOpenGLRenderWindow *aRenWin;
178 aRenWin = static_cast<vtkXOpenGLRenderWindow *>(this->RenderWindow);
179 this->myDisplayId = aRenWin->GetDisplayId();
180 this->myWindowId = aRenWin->GetWindowId();
181 aSize = aRenWin->GetSize();
186 this->Size[0] = aSize[0];
187 this->Size[1] = aSize[1];
191 LRESULT CALLBACK WndProc(HWND theHWnd, UINT theUMsg, WPARAM theWParam, LPARAM theLParam);
194 //===========================================================
197 //===========================================================
198 void IVtkDraw_Interactor::Enable()
205 // Add event handlers
207 SetWindowLongPtr(this->myWindowId, GWLP_USERDATA, (LONG_PTR)this);
208 SetWindowLongPtr(this->myWindowId, GWLP_WNDPROC, (LONG_PTR)WndProc);
210 #if TCL_MAJOR_VERSION < 8
211 Tk_CreateFileHandler((void*)ConnectionNumber(this->myDisplayId),
212 TK_READABLE, ProcessEvents, (ClientData) this);
214 Tk_CreateFileHandler(ConnectionNumber(this->myDisplayId),
215 TK_READABLE, ProcessEvents, (ClientData) this);
223 //===========================================================
226 //===========================================================
227 void IVtkDraw_Interactor::MoveTo (Standard_Integer theX, Standard_Integer theY)
229 // Processing highlighting
230 mySelector->Pick (theX, theY, 0.0);
231 vtkSmartPointer<vtkActorCollection> anActorCollection = mySelector->GetPickedActors();
233 if (anActorCollection)
235 // Highlight picked subshapes
236 ClearHighlightAndSelection (myPipelines, Standard_True, Standard_False);
237 anActorCollection->InitTraversal();
238 while (vtkActor* anActor = anActorCollection->GetNextActor())
240 IVtkTools_ShapeDataSource* aDataSource = IVtkTools_ShapeObject::GetShapeSource (anActor);
246 IVtkOCC_Shape::Handle anOccShape = aDataSource->GetShape();
247 if (anOccShape.IsNull())
252 IVtk_IdType aShapeID = anOccShape->GetId();
253 Handle(Message_Messenger) anOutput = Message::DefaultMessenger();
254 if (!myPipelines->IsBound(aShapeID))
256 anOutput->SendWarning() << "Warning: there is no VTK pipeline registered for highlighted shape" << std::endl;
260 const Handle(IVtkDraw_HighlightAndSelectionPipeline)& aPL = myPipelines->Find (aShapeID);
262 // Add a subpolydata filter to the highlight pipeline for the shape data source.
263 IVtkTools_SubPolyDataFilter* aFilter = aPL->GetHighlightFilter();
265 // Set the selected sub-shapes ids to subpolydata filter.
266 IVtk_ShapeIdList aSubShapeIds = mySelector->GetPickedSubShapesIds(aShapeID);
268 // Get ids of cells for picked subshapes.
269 IVtk_ShapeIdList aSubIds;
270 IVtk_ShapeIdList::Iterator aMetaIds (aSubShapeIds);
271 for (; aMetaIds.More(); aMetaIds.Next())
273 IVtk_ShapeIdList aSubSubIds = anOccShape->GetSubIds (aMetaIds.Value());
274 aSubIds.Append (aSubSubIds);
277 aFilter->SetDoFiltering (!aSubIds.IsEmpty());
278 aFilter->SetData (aSubIds);
279 if (!aFilter->GetInput())
281 aFilter->SetInputConnection (aDataSource->GetOutputPort());
289 //===========================================================
290 // Function : OnSelection
292 //===========================================================
293 void IVtkDraw_Interactor::OnSelection()
295 // Processing selection
296 vtkSmartPointer<vtkActorCollection> anActorCollection = mySelector->GetPickedActors();
298 if (anActorCollection)
300 // Highlight picked subshapes.
301 ClearHighlightAndSelection (myPipelines, Standard_False, Standard_True);
302 anActorCollection->InitTraversal();
303 while (vtkActor* anActor = anActorCollection->GetNextActor())
305 IVtkTools_ShapeDataSource* aDataSource = IVtkTools_ShapeObject::GetShapeSource (anActor);
311 IVtkOCC_Shape::Handle anOccShape = aDataSource->GetShape();
312 if (anOccShape.IsNull())
317 IVtk_IdType aShapeID = anOccShape->GetId();
318 Handle(Message_Messenger) anOutput = Message::DefaultMessenger();
319 if (!myPipelines->IsBound (aShapeID))
321 anOutput->SendWarning() << "Warning: there is no VTK pipeline registered for picked shape" << std::endl;
325 const Handle(IVtkDraw_HighlightAndSelectionPipeline)& aPL = myPipelines->Find (aShapeID);
327 // Add a subpolydata filter to the selection pipeline for the shape data source.
328 IVtkTools_SubPolyDataFilter* aFilter = aPL->GetSelectionFilter();
330 // Set the selected sub-shapes ids to subpolydata filter.
331 IVtk_ShapeIdList aSubShapeIds = mySelector->GetPickedSubShapesIds(aShapeID);
333 // Get ids of cells for picked subshapes.
334 IVtk_ShapeIdList aSubIds;
335 IVtk_ShapeIdList::Iterator aMetaIds (aSubShapeIds);
336 for (; aMetaIds.More(); aMetaIds.Next())
338 IVtk_ShapeIdList aSubSubIds = anOccShape->GetSubIds (aMetaIds.Value());
339 aSubIds.Append (aSubSubIds);
342 aFilter->SetDoFiltering (!aSubIds.IsEmpty());
343 aFilter->SetData (aSubIds);
344 if (!aFilter->GetInput())
346 aFilter->SetInputConnection (aDataSource->GetOutputPort());
356 //===========================================================
357 // Function : OnMouseMove
359 //===========================================================
360 void IVtkDraw_Interactor::OnMouseMove (HWND theHWnd, UINT theNFlags,
361 Standard_Integer theX,
362 Standard_Integer theY)
369 this->SetEventInformationFlipY (theX,
371 theNFlags & MK_CONTROL,
372 theNFlags & MK_SHIFT);
373 this->SetAltKey(GetKeyState(VK_MENU) & (~1));
374 if (!this->myMouseInWindow &&
375 (theX >= 0 && theX < this->Size[0] && theY >= 0 && theY < this->Size[1]))
377 this->InvokeEvent (vtkCommand::EnterEvent, NULL);
378 this->myMouseInWindow = 1;
379 // request WM_MOUSELEAVE generation
380 TRACKMOUSEEVENT aTme;
381 aTme.cbSize = sizeof (TRACKMOUSEEVENT);
382 aTme.dwFlags = TME_LEAVE;
383 aTme.hwndTrack = theHWnd;
384 TrackMouseEvent (&aTme);
387 if (!(theNFlags & MK_LBUTTON))
388 this->MoveTo (theX, this->Size[1] - theY - 1);
390 this->InvokeEvent (vtkCommand::MouseMoveEvent, NULL);
393 //===========================================================
394 // Function : OnMouseWheelForward
396 //===========================================================
397 void IVtkDraw_Interactor::OnMouseWheelForward (HWND, UINT theNFlags,
398 Standard_Integer theX,
399 Standard_Integer theY)
406 this->SetEventInformationFlipY (theX,
408 theNFlags & MK_CONTROL,
409 theNFlags & MK_SHIFT);
411 this->SetAltKey (GetKeyState(VK_MENU) & (~1));
412 this->InvokeEvent (vtkCommand::MouseWheelForwardEvent, NULL);
415 //===========================================================
416 // Function : OnMouseWheelBackward
418 //===========================================================
419 void IVtkDraw_Interactor::OnMouseWheelBackward (HWND, UINT theNFlags,
420 Standard_Integer theX,
421 Standard_Integer theY)
428 this->SetEventInformationFlipY (theX,
430 theNFlags & MK_CONTROL,
431 theNFlags & MK_SHIFT);
433 this->SetAltKey (GetKeyState(VK_MENU) & (~1));
434 this->InvokeEvent (vtkCommand::MouseWheelBackwardEvent, NULL);
437 //===========================================================
438 // Function : OnLButtonDown
440 //===========================================================
441 void IVtkDraw_Interactor::OnLButtonDown (HWND theHWnd, UINT theNFlags,
442 Standard_Integer theX,
443 Standard_Integer theY,
444 Standard_Integer theRepeat)
451 SetCapture (theHWnd);
452 this->SetEventInformationFlipY (theX,
454 theNFlags & MK_CONTROL,
455 theNFlags & MK_SHIFT,
457 this->SetAltKey (GetKeyState(VK_MENU) & (~1));
461 this->InvokeEvent (vtkCommand::LeftButtonPressEvent, NULL);
464 //===========================================================
465 // Function : OnLButtonUp
467 //===========================================================
468 void IVtkDraw_Interactor::OnLButtonUp (HWND, UINT theNFlags,
469 Standard_Integer theX,
470 Standard_Integer theY)
477 this->SetEventInformationFlipY (theX,
479 theNFlags & MK_CONTROL,
480 theNFlags & MK_SHIFT);
482 this->SetAltKey (GetKeyState(VK_MENU) & (~1));
483 this->InvokeEvent (vtkCommand::LeftButtonReleaseEvent, NULL);
487 //===========================================================
488 // Function : OnMButtonDown
490 //===========================================================
491 void IVtkDraw_Interactor::OnMButtonDown (HWND theHWnd, UINT theNFlags,
492 Standard_Integer theX,
493 Standard_Integer theY,
494 Standard_Integer theRepeat)
502 SetCapture (theHWnd);
503 this->SetEventInformationFlipY (theX,
505 theNFlags & MK_CONTROL,
506 theNFlags & MK_SHIFT,
508 this->SetAltKey (GetKeyState(VK_MENU) & (~1));
509 this->InvokeEvent (vtkCommand::MiddleButtonPressEvent, NULL);
512 //===========================================================
513 // Function : OnMButtonUp
515 //===========================================================
516 void IVtkDraw_Interactor::OnMButtonUp (HWND, UINT theNFlags,
517 Standard_Integer theX,
518 Standard_Integer theY)
524 this->SetEventInformationFlipY (theX,
526 theNFlags & MK_CONTROL,
527 theNFlags & MK_SHIFT);
529 this->SetAltKey (GetKeyState(VK_MENU) & (~1));
530 this->InvokeEvent (vtkCommand::MiddleButtonReleaseEvent, NULL);
534 //===========================================================
535 // Function : OnRButtonDown
537 //===========================================================
538 void IVtkDraw_Interactor::OnRButtonDown (HWND theHWnd, UINT theNFlags,
539 Standard_Integer theX,
540 Standard_Integer theY,
541 Standard_Integer theRepeat)
550 this->SetEventInformationFlipY (theX,
552 theNFlags & MK_CONTROL,
553 theNFlags & MK_SHIFT,
556 this->SetAltKey (GetKeyState(VK_MENU) & (~1));
557 this->InvokeEvent (vtkCommand::RightButtonPressEvent, NULL);
560 //===========================================================
561 // Function : OnRButtonUp
563 //===========================================================
564 void IVtkDraw_Interactor::OnRButtonUp (HWND, UINT theNFlags,
565 Standard_Integer theX,
566 Standard_Integer theY)
572 this->SetEventInformationFlipY (theX,
574 theNFlags & MK_CONTROL,
575 theNFlags & MK_SHIFT);
577 this->SetAltKey (GetKeyState(VK_MENU) & (~1));
578 this->InvokeEvent (vtkCommand::RightButtonReleaseEvent, NULL);
582 //===========================================================
585 //===========================================================
586 void IVtkDraw_Interactor::OnSize (HWND, UINT,
587 Standard_Integer theX,
588 Standard_Integer theY)
590 this->UpdateSize (theX, theY);
593 this->InvokeEvent (vtkCommand::ConfigureEvent, NULL);
597 //===========================================================
598 // Function : OnTimer
600 //===========================================================
601 void IVtkDraw_Interactor::OnTimer (HWND, UINT theTimerId)
608 Standard_Integer aTid = static_cast<Standard_Integer>(theTimerId);
609 this->InvokeEvent (vtkCommand::TimerEvent, (void*)&aTid);
611 // Here we deal with one-shot versus repeating timers
612 if (this->IsOneShotTimer(aTid))
614 KillTimer (this->myWindowId, aTid); //'cause windows timers are always repeating
618 //===========================================================
619 // Function : WndProc
621 //===========================================================
622 LRESULT CALLBACK WndProc (HWND theHWnd,UINT theUMsg,
627 IVtkDraw_Interactor *anInteractor = 0;
629 anInteractor = (IVtkDraw_Interactor *)GetWindowLongPtrW (theHWnd, GWLP_USERDATA);
631 if (anInteractor && anInteractor->GetReferenceCount() > 0)
633 anInteractor->Register (anInteractor);
634 aRes = ViewerWindowProc (theHWnd, theUMsg, theWParam, theLParam, anInteractor);
635 anInteractor->UnRegister (anInteractor);
641 //===========================================================
642 // Function : ViewerWindowProc
644 //===========================================================
645 LRESULT CALLBACK ViewerWindowProc (HWND theHWnd,
649 IVtkDraw_Interactor *theInteractor)
654 theInteractor->GetOCCWindow ()->Unmap ();
657 theInteractor->Render();
660 theInteractor->OnSize (theHWnd, (UINT)theWParam, LOWORD(theLParam), HIWORD(theLParam));
662 case WM_LBUTTONDBLCLK:
663 theInteractor->OnLButtonDown (theHWnd, (UINT)theWParam, MAKEPOINTS(theLParam).x, MAKEPOINTS(theLParam).y, 1);
666 theInteractor->OnLButtonDown (theHWnd, (UINT)theWParam, MAKEPOINTS(theLParam).x, MAKEPOINTS(theLParam).y, 0);
669 theInteractor->OnLButtonUp (theHWnd, (UINT)theWParam, MAKEPOINTS(theLParam).x, MAKEPOINTS(theLParam).y);
671 case WM_MBUTTONDBLCLK:
672 theInteractor->OnMButtonDown (theHWnd, (UINT)theWParam, MAKEPOINTS(theLParam).x, MAKEPOINTS(theLParam).y, 1);
675 theInteractor->OnMButtonDown (theHWnd, (UINT)theWParam, MAKEPOINTS(theLParam).x, MAKEPOINTS(theLParam).y, 0);
678 theInteractor->OnMButtonUp (theHWnd, (UINT)theWParam, MAKEPOINTS(theLParam).x, MAKEPOINTS(theLParam).y);
680 case WM_RBUTTONDBLCLK:
681 theInteractor->OnRButtonDown (theHWnd, (UINT)theWParam, MAKEPOINTS(theLParam).x, MAKEPOINTS(theLParam).y, 1);
684 theInteractor->OnRButtonDown (theHWnd, (UINT)theWParam, MAKEPOINTS(theLParam).x, MAKEPOINTS(theLParam).y, 0);
687 theInteractor->OnRButtonUp (theHWnd, (UINT)theWParam, MAKEPOINTS(theLParam).x, MAKEPOINTS(theLParam).y);
691 theInteractor->InvokeEvent (vtkCommand::LeaveEvent, NULL);
692 theInteractor->myMouseInWindow = 0;
696 theInteractor->OnMouseMove (theHWnd, (UINT)theWParam, MAKEPOINTS(theLParam).x, MAKEPOINTS(theLParam).y);
701 pt.x = MAKEPOINTS(theLParam).x;
702 pt.y = MAKEPOINTS(theLParam).y;
703 ::ScreenToClient(theHWnd, &pt);
704 if( GET_WHEEL_DELTA_WPARAM(theWParam) > 0)
706 theInteractor->OnMouseWheelForward (theHWnd, (UINT)theWParam, pt.x, pt.y);
710 theInteractor->OnMouseWheelBackward (theHWnd, (UINT)theWParam, pt.x, pt.y);
715 theInteractor->OnTimer (theHWnd, (UINT)theWParam);
718 return DefWindowProcW (theHWnd, theMsg, theWParam, theLParam);
723 //===========================================================
724 // Function : GetDisplayId
726 //===========================================================
727 Display* IVtkDraw_Interactor::GetDisplayId() const
732 //===========================================================
733 // Function : GetMousePosition
735 //===========================================================
736 void IVtkDraw_Interactor::GetMousePosition (Standard_Integer *theX,
737 Standard_Integer *theY)
739 Window aRoot, aChild;
740 Standard_Integer aRoot_x, aRoot_y;
743 XQueryPointer (this->myDisplayId, this->myWindowId,
744 &aRoot, &aChild, &aRoot_x, &aRoot_y, theX, theY, &aKeys);
748 //===========================================================
749 // Function : ViewerMainLoop
751 //===========================================================
752 Standard_Integer IVtkDraw_Interactor::ViewerMainLoop (Standard_Integer theArgNum, const char** /*theArgs*/)
754 Standard_Integer aXp, aYp;
755 Standard_Boolean aPick = theArgNum > 0;
757 static XEvent anEvent;
758 XNextEvent (myDisplayId, &anEvent);
760 switch (anEvent.type)
769 while (XCheckTypedWindowEvent (this->myDisplayId,
774 // just getting the expose configure event
778 this->SetEventSize (anEvent.xexpose.width, anEvent.xexpose.height);
781 aXp = anEvent.xexpose.x;
782 aYp = this->Size[1] - anEvent.xexpose.y - 1;
783 this->SetEventPosition (aXp, aYp);
785 // only render if we are currently accepting events
788 this->InvokeEvent(vtkCommand::ExposeEvent,NULL);
796 // only render if we are currently accepting events
797 if (this->Enabled && this->GetRenderWindow()->GetNeverRendered())
804 case ConfigureNotify:
807 while (XCheckTypedWindowEvent(this->myDisplayId,
812 // just getting the last configure event
815 Standard_Integer aWidth = anEvent.xconfigure.width;
816 Standard_Integer aHeight = anEvent.xconfigure.height;
817 if (aWidth != this->Size[0] || aHeight != this->Size[1])
819 Standard_Boolean toResizeSmaller = aWidth <= this->Size[0] && aHeight <= this->Size[1];
820 this->UpdateSize (aWidth, aHeight);
821 aXp = anEvent.xbutton.x;
822 aYp = anEvent.xbutton.y;
824 SetEventPosition (aXp, this->Size[1] - aYp - 1);
826 // only render if we are currently accepting events
829 this->InvokeEvent(vtkCommand::ConfigureEvent,NULL);
832 // Don't call Render when the window is resized to be larger:
834 // - if the window is resized to be larger, an Expose event will
835 // be trigged by the X server which will trigger a call to
837 // - if the window is resized to be smaller, no Expose event will
838 // be trigged by the X server, as no new area become visible.
839 // only in this case, we need to explicitly call Render()
840 // in ConfigureNotify.
855 Standard_Integer aCtrl = anEvent.xbutton.state & ControlMask ? 1 : 0;
856 Standard_Integer aShift = anEvent.xbutton.state & ShiftMask ? 1 : 0;
857 Standard_Integer anAlt = anEvent.xbutton.state & Mod1Mask ? 1 : 0;
858 aXp = anEvent.xbutton.x;
859 aYp = anEvent.xbutton.y;
861 // check for double click
862 static Standard_Integer aMousePressTime = 0;
863 Standard_Integer aRepeat = 0;
864 // 400 ms threshold by default is probably good to start
865 Standard_Integer anEventTime = static_cast<int>(anEvent.xbutton.time);
866 if ((anEventTime - aMousePressTime) < 400)
868 aMousePressTime -= 2000; // no double click next time
873 aMousePressTime = anEventTime;
876 this->SetEventInformationFlipY (aXp, aYp, aCtrl, aShift, 0, aRepeat);
877 this->SetAltKey (anAlt);
879 switch (anEvent.xbutton.button)
882 this->OnSelection ();
883 this->myIsLeftButtonPressed = 1;
884 this->InvokeEvent (vtkCommand::LeftButtonPressEvent,NULL);
887 this->InvokeEvent (vtkCommand::MiddleButtonPressEvent,NULL);
890 this->InvokeEvent (vtkCommand::RightButtonPressEvent,NULL);
893 this->InvokeEvent (vtkCommand::MouseWheelForwardEvent,NULL);
896 this->InvokeEvent (vtkCommand::MouseWheelBackwardEvent,NULL);
909 Standard_Integer aCtrl = anEvent.xbutton.state & ControlMask ? 1 : 0;
910 Standard_Integer aShift = anEvent.xbutton.state & ShiftMask ? 1 : 0;
911 Standard_Integer anAlt = anEvent.xbutton.state & Mod1Mask ? 1 : 0;
912 aXp = anEvent.xbutton.x;
913 aYp = anEvent.xbutton.y;
915 this->SetEventInformationFlipY (aXp, aYp, aCtrl, aShift);
916 this->SetAltKey (anAlt);
917 switch (anEvent.xbutton.button)
920 this->InvokeEvent (vtkCommand::LeftButtonReleaseEvent,NULL);
921 this->myIsLeftButtonPressed = False;
924 this->InvokeEvent (vtkCommand::MiddleButtonReleaseEvent,NULL);
927 this->InvokeEvent (vtkCommand::RightButtonReleaseEvent,NULL);
938 XEnterWindowEvent *anEnterEvent = reinterpret_cast<XEnterWindowEvent *>(&anEvent);
939 this->SetEventInformationFlipY (anEnterEvent->x,
941 (anEnterEvent->state & ControlMask) != 0,
942 (anEnterEvent->state & ShiftMask) != 0);
944 this->SetAltKey (anEvent.xbutton.state & Mod1Mask ? 1 : 0);
945 this->InvokeEvent (vtkCommand::EnterEvent, NULL);
955 XLeaveWindowEvent *aLeaveEvent = reinterpret_cast<XLeaveWindowEvent *>(&anEvent);
956 this->SetEventInformationFlipY (aLeaveEvent->x,
958 (aLeaveEvent->state & ControlMask) != 0,
959 (aLeaveEvent->state & ShiftMask) != 0);
961 this->SetAltKey (anEvent.xbutton.state & Mod1Mask ? 1 : 0);
962 this->InvokeEvent(vtkCommand::LeaveEvent, NULL);
975 Standard_Integer aCtrl = anEvent.xbutton.state & ControlMask ? 1 : 0;
976 Standard_Integer aShift = anEvent.xbutton.state & ShiftMask ? 1 : 0;
977 Standard_Integer anAlt = anEvent.xbutton.state & Mod1Mask ? 1 : 0;
979 // Note that even though the (x,y) location of the pointer is event structure,
980 // we must call XQueryPointer for the hints (motion event compression) to
982 this->GetMousePosition (&aXp, &aYp);
983 this->SetEventInformationFlipY (aXp, aYp, aCtrl, aShift);
984 this->SetAltKey (anAlt);
985 if (!myIsLeftButtonPressed)
986 MoveTo (aXp, this->Size[1]- aYp - 1);
987 this->InvokeEvent (vtkCommand::MouseMoveEvent, NULL);
995 //===========================================================
996 // Function : ProcessEvents
998 //===========================================================
999 void IVtkDraw_Interactor::ProcessEvents (ClientData theData, int)
1001 IVtkDraw_Interactor *anInteractor = (IVtkDraw_Interactor *)theData;
1003 while (XPending(anInteractor->GetDisplayId()))
1005 anInteractor->ViewerMainLoop (0, NULL);