]> Creatis software - bbtk.git/blob - packages/wxvtk/src/wxVTKRenderWindowInteractor.cxx
*** empty log message ***
[bbtk.git] / packages / wxvtk / src / wxVTKRenderWindowInteractor.cxx
1 /*=========================================================================
2
3   Program:   Visualization Toolkit
4   Module:    $RCSfile: wxVTKRenderWindowInteractor.cxx,v $
5   Language:  C++
6   Date:      $Date: 2008/05/09 10:39:47 $
7   Version:   $Revision: 1.2 $
8
9   Copyright (c) 1993-2002 Ken Martin, Will Schroeder, Bill Lorensen 
10   All rights reserved.
11   See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
12
13      This software is distributed WITHOUT ANY WARRANTY; without even 
14      the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR 
15      PURPOSE.  See the above copyright notice for more information.
16
17 =========================================================================*/
18
19 #include "wxVTKRenderWindowInteractor.h"
20
21 //This is needed for vtk 3.1 :
22 #ifndef VTK_MAJOR_VERSION
23 #  include "vtkVersion.h"
24 #endif
25
26 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
27 #  include "vtkCommand.h"
28 #else
29 #  include "vtkInteractorStyle.h"
30 #endif
31
32 //=======================================================================
33 // LG : NAMESPACE IS NECESSARY TO AVOID CONFLICTING SYMBOLS IN DYN LIBS
34 namespace bbwxvtk
35 {
36
37   //Keep this for compatibilty reason, this was introduced in wxGTK 2.4.0
38 #if (!wxCHECK_VERSION(2, 4, 0))
39   wxWindow* wxGetTopLevelParent(wxWindow *win)
40   {
41     while ( win && !win->IsTopLevel() )
42       win = win->GetParent();
43     return win;
44   }
45 #endif
46 }
47 // LG : EO namespace bbwxvtk
48 //=======================================================================
49
50 // To access objc calls on cocoa
51 #ifdef __WXCOCOA__
52 #ifdef VTK_USE_COCOA
53 #import <Cocoa/Cocoa.h>
54 // This trick is no longer need in VTK CVS, should get rid of that:
55 #define id Id
56 #else
57 #error Build mismatch you need both wxWidgets and VTK to be configure against Cocoa to work
58 #endif //VTK_USE_COCOA
59 #endif //__WXCOCOA__
60
61 #ifdef __WXGTK__
62 #    include <gdk/gdkx.h> // GDK_WINDOW_XWINDOW is found here in wxWidgets 2.8.0
63 #    include "gdk/gdkprivate.h"
64 #ifdef __WXGTK20__
65 #include <wx/gtk/win_gtk.h>
66 #else
67 #include <wx/gtk1/win_gtk.h>
68 #endif
69 #define GetXWindow(wxwin) (wxwin)->m_wxwindow ? \
70                           GDK_WINDOW_XWINDOW(GTK_PIZZA((wxwin)->m_wxwindow)->bin_window) : \
71                           GDK_WINDOW_XWINDOW((wxwin)->m_widget->window)
72 #endif
73
74 #ifdef __WXX11__
75 #include "wx/x11/privx.h"
76 #define GetXWindow(wxwin)   ((Window)(wxwin)->GetHandle())
77 #endif
78
79
80 //For more info on this class please go to:
81 //http://wxvtk.sf.net
82 //This hack is for some buggy wxGTK version:
83 #if wxCHECK_VERSION(2, 3, 2) && !wxCHECK_VERSION(2, 4, 1) && defined(__WXGTK__)
84 #  define WX_USE_X_CAPTURE 0
85 #else
86 #  define WX_USE_X_CAPTURE 1
87 #endif
88
89 #define ID_wxVTKRenderWindowInteractor_TIMER 1001
90
91 //=======================================================================
92 // LG : NAMESPACE IS NECESSARY TO AVOID CONFLICTING SYMBOLS IN DYN LIBS
93 namespace bbwxvtk
94 {
95
96 #if defined(__WXGTK__) && defined(USE_WXGLCANVAS)
97 IMPLEMENT_DYNAMIC_CLASS(wxVTKRenderWindowInteractor, wxGLCanvas)
98 #else
99 IMPLEMENT_DYNAMIC_CLASS(wxVTKRenderWindowInteractor, wxWindow)
100 #endif  //__WXGTK__
101
102 //---------------------------------------------------------------------------
103 #if defined(__WXGTK__) && defined(USE_WXGLCANVAS)
104 BEGIN_EVENT_TABLE(wxVTKRenderWindowInteractor, wxGLCanvas)
105 #else
106 BEGIN_EVENT_TABLE(wxVTKRenderWindowInteractor, wxWindow)
107 #endif //__WXGTK__
108   //refresh window by doing a Render
109   EVT_PAINT       (wxVTKRenderWindowInteractor::OnPaint)
110   EVT_ERASE_BACKGROUND(wxVTKRenderWindowInteractor::OnEraseBackground)
111   EVT_MOTION      (wxVTKRenderWindowInteractor::OnMotion)
112
113   //Bind the events to the event converters
114   EVT_LEFT_DOWN   (wxVTKRenderWindowInteractor::OnButtonDown)
115   EVT_MIDDLE_DOWN (wxVTKRenderWindowInteractor::OnButtonDown)
116   EVT_RIGHT_DOWN  (wxVTKRenderWindowInteractor::OnButtonDown)
117   EVT_LEFT_UP     (wxVTKRenderWindowInteractor::OnButtonUp)
118   EVT_MIDDLE_UP   (wxVTKRenderWindowInteractor::OnButtonUp)
119   EVT_RIGHT_UP    (wxVTKRenderWindowInteractor::OnButtonUp)
120 #if !(VTK_MAJOR_VERSION == 3 && VTK_MINOR_VERSION == 1)
121   EVT_ENTER_WINDOW(wxVTKRenderWindowInteractor::OnEnter)
122   EVT_LEAVE_WINDOW(wxVTKRenderWindowInteractor::OnLeave)
123   EVT_MOUSEWHEEL  (wxVTKRenderWindowInteractor::OnMouseWheel)
124 // If we use EVT_KEY_DOWN instead of EVT_CHAR, capital versions
125 // of all characters are always returned.  EVT_CHAR also performs
126 // other necessary keyboard-dependent translations.
127   //EVT_KEY_DOWN    (wxVTKRenderWindowInteractor::OnKeyDown)
128   EVT_CHAR        (wxVTKRenderWindowInteractor::OnKeyDown)
129   EVT_KEY_UP      (wxVTKRenderWindowInteractor::OnKeyUp)
130 #endif
131   EVT_TIMER       (ID_wxVTKRenderWindowInteractor_TIMER, wxVTKRenderWindowInteractor::OnTimer)
132   EVT_SIZE        (wxVTKRenderWindowInteractor::OnSize)
133 END_EVENT_TABLE()
134
135 //---------------------------------------------------------------------------
136 #if defined(__WXGTK__) && defined(USE_WXGLCANVAS)
137 wxVTKRenderWindowInteractor::wxVTKRenderWindowInteractor() : vtkRenderWindowInteractor(), wxGLCanvas()
138 #else
139 wxVTKRenderWindowInteractor::wxVTKRenderWindowInteractor() : vtkRenderWindowInteractor(), wxWindow()
140 #endif //__WXGTK__
141       , timer(this, ID_wxVTKRenderWindowInteractor_TIMER)
142       , ActiveButton(wxEVT_NULL)
143       , RenderAllowed(0)
144       , Stereo(0)
145       , Handle(0)
146       , Created(true)
147       , RenderWhenDisabled(1)
148       , UseCaptureMouse(0)
149 {
150   
151   this->RenderWindow = NULL;
152   this->SetRenderWindow(vtkRenderWindow::New());
153   this->RenderWindow->Delete();
154   
155   //this->SetBackgroundColour( wxColour(255,0,255) );
156 }
157 //---------------------------------------------------------------------------
158 wxVTKRenderWindowInteractor::wxVTKRenderWindowInteractor(wxWindow *parent,
159                                                          wxWindowID id,
160                                                          const wxPoint &pos,
161                                                          const wxSize &size,
162                                                          long style,
163                                                          const wxString &name)
164 #if defined(__WXGTK__) && defined(USE_WXGLCANVAS)
165       : vtkRenderWindowInteractor(), wxGLCanvas(parent, id, pos, size, style, name)
166 #else
167       : vtkRenderWindowInteractor(), wxWindow(parent, id, pos, size, style, name)
168 #endif //__WXGTK__
169       , timer(this, ID_wxVTKRenderWindowInteractor_TIMER)
170       , ActiveButton(wxEVT_NULL)
171       , RenderAllowed(0)
172       , Stereo(0)
173       , Handle(0)
174       , Created(true)
175       , RenderWhenDisabled(1)
176       , UseCaptureMouse(0)
177 {
178   
179   this->RenderWindow = NULL;
180   this->SetRenderWindow(vtkRenderWindow::New());
181   this->RenderWindow->Delete();
182   
183   // this->SetBackgroundColour( wxColour(255,0,0) );
184 }
185 //---------------------------------------------------------------------------
186 wxVTKRenderWindowInteractor::~wxVTKRenderWindowInteractor()
187 {   
188   // LG : trompe la mort !
189   SetRenderWindow(NULL);
190   SetReferenceCount(0);
191 }
192 //---------------------------------------------------------------------------
193 wxVTKRenderWindowInteractor * wxVTKRenderWindowInteractor::New()
194 {
195   // we don't make use of the objectfactory, because we're not registered
196   return new wxVTKRenderWindowInteractor;
197 }
198 //---------------------------------------------------------------------------
199 void wxVTKRenderWindowInteractor::Initialize()
200 {
201   int *size = RenderWindow->GetSize();
202   // enable everything and start rendering
203   Enable();
204   //RenderWindow->Start();
205
206   // set the size in the render window interactor
207   Size[0] = size[0];
208   Size[1] = size[1];
209
210   // this is initialized
211   Initialized = 1;
212 }
213 //---------------------------------------------------------------------------
214 void wxVTKRenderWindowInteractor::Enable()
215 {
216   // if already enabled then done
217   if (Enabled)
218     return;
219
220   // that's it
221   Enabled = 1;
222 #if defined(__WXGTK__) && defined(USE_WXGLCANVAS)
223   SetCurrent();
224 #endif
225   Modified();
226 }
227 //---------------------------------------------------------------------------
228 bool wxVTKRenderWindowInteractor::Enable(bool enable)
229 {
230 #if defined(__WXGTK__) && defined(USE_WXGLCANVAS)
231   return wxGLCanvas::Enable(enable);
232 #else
233   return wxWindow::Enable(enable);
234 #endif
235 }
236 //---------------------------------------------------------------------------
237 void wxVTKRenderWindowInteractor::Disable()
238 {
239   // if already disabled then done
240   if (!Enabled)
241     return;
242
243   // that's it (we can't remove the event handler like it should be...)
244   Enabled = 0;
245   Modified();
246 }
247 //---------------------------------------------------------------------------
248 void wxVTKRenderWindowInteractor::Start()
249 {
250   // the interactor cannot control the event loop
251   vtkErrorMacro( << "wxVTKRenderWindowInteractor::Start() "
252     "interactor cannot control event loop.");
253 }
254 //---------------------------------------------------------------------------
255 void wxVTKRenderWindowInteractor::UpdateSize(int x, int y)
256 {
257   if( RenderWindow )
258   {
259     // if the size changed tell render window
260     if ( x != Size[0] || y != Size[1] )
261     {
262       // adjust our (vtkRenderWindowInteractor size)
263       Size[0] = x;
264       Size[1] = y;
265       // and our RenderWindow's size
266       RenderWindow->SetSize(x, y);
267     }
268   }
269 }
270 //---------------------------------------------------------------------------
271 int wxVTKRenderWindowInteractor::CreateTimer(int WXUNUSED(timertype))
272 {
273   // it's a one shot timer
274   if (!timer.Start(10, TRUE))
275     assert(false);
276
277   return 1;
278   
279 }
280 //---------------------------------------------------------------------------
281 int wxVTKRenderWindowInteractor::DestroyTimer()
282 {
283   // do nothing
284   return 1;
285 }
286 //---------------------------------------------------------------------------
287 void wxVTKRenderWindowInteractor::OnTimer(wxTimerEvent& WXUNUSED(event))
288 {
289   if (!Enabled)
290     return;
291     
292 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
293     // new style
294     InvokeEvent(vtkCommand::TimerEvent, NULL);
295 #else
296     // old style
297     InteractorStyle->OnTimer();
298 #endif
299 }
300
301 //---------------------------------------------------------------------------
302 // NOTE on implementation:
303 // Bad luck you ended up in the only tricky place of this code.
304 // A few note, wxWidgets still refuse to provide such convenient method
305 // so I have to maintain it myself, eventhough this is completely integrated
306 // in wxPython...
307 // Anyway if this happen to break for you then compare to a recent version of wxPython
308 // and look for the function long wxPyGetWinHandle(wxWindow* win)
309 // in wxPython/src/helpers.cpp
310 long wxVTKRenderWindowInteractor::GetHandleHack()
311 {
312   //helper function to hide the MSW vs GTK stuff
313   long handle_tmp = 0;
314
315 // __WXMSW__ is for Win32
316 //__WXMAX__ stands for using Carbon C-headers, using either the CarbonLib/CFM or the native Mach-O builds (which then also use the latest features available)
317 // __WXGTK__ is for both gtk 1.2.x and gtk 2.x
318 #if defined(__WXMSW__) || defined(__WXMAC__)
319     handle_tmp = (long)this->GetHandle();
320 #endif //__WXMSW__
321
322 //__WXCOCOA__ stands for using the objective-c Cocoa API
323 #ifdef __WXCOCOA__
324    // Here is how to find the NSWindow
325    wxTopLevelWindow* toplevel = dynamic_cast<wxTopLevelWindow*>(
326      wxGetTopLevelParent( this ) );
327    if (toplevel != NULL )    
328    {
329      handle_tmp = (long)toplevel->GetNSWindow();
330    }
331    // The NSView will be deducted from 
332    // [(NSWindow*)Handle contentView]
333    // if only I knew how to write that in c++
334 #endif //__WXCOCOA__
335
336     // Find and return the actual X-Window.
337 #if defined(__WXGTK__) || defined(__WXX11__)
338     return (long)GetXWindow(this);
339 #endif
340
341 //#ifdef __WXMOTIF__
342 //    handle_tmp = (long)this->GetXWindow();
343 //#endif
344
345   return handle_tmp;
346 }
347 //---------------------------------------------------------------------------
348 void wxVTKRenderWindowInteractor::OnPaint(wxPaintEvent& WXUNUSED(event))
349 {
350
351   //must always be here
352   wxPaintDC pDC(this);
353
354   //do it here rather than in the cstor: this is safer.
355   if(!Handle)
356   {
357     Handle = GetHandleHack();
358     RenderWindow->SetWindowId(reinterpret_cast<void *>(Handle));
359 #ifdef __WXMSW__
360     RenderWindow->SetParentId(reinterpret_cast<void *>(this->GetParent()->GetHWND()));
361 #endif //__WXMSW__
362   }
363   // get vtk to render to the wxWindows
364   //bbtkDebugMessage("Wx",9,"wxVTKRenderWindowInteractor::OnPaint"<<std::endl);
365   //std::cout << "wxVTKRenderWindowInteractor::OnPaint"<<std::endl;
366   Render();
367
368 #if defined(__WXGTK__) && defined(USE_WXGLCANVAS)
369   //  bbtkDebugMessage("Core",9,"wxVTKRenderWindowInteractor::OnPaint   public wxGLCanvas, virtual public vtkRenderWindowInteractor  \n");
370 #else
371   //  bbtkDebugMessage("Core",9,"wxVTKRenderWindowInteractor::OnPaint public wxWindow, virtual public vtkRenderWindowInteractor     \n");
372 #endif //__WXGTK__
373
374 }
375 //---------------------------------------------------------------------------
376 void wxVTKRenderWindowInteractor::OnEraseBackground(wxEraseEvent &event)
377 {
378   //printf("EED wxVTKRenderWindowInteractor::OnEraseBackground \n");
379   //turn off background erase to reduce flickering on MSW
380   event.Skip(false);
381 }
382 //---------------------------------------------------------------------------
383 void wxVTKRenderWindowInteractor::OnSize(wxSizeEvent& WXUNUSED(event))
384 {
385   int w, h;
386   GetClientSize(&w, &h);
387   UpdateSize(w, h);
388
389   if (!Enabled) 
390     {
391     return;
392     }
393
394 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
395   InvokeEvent(vtkCommand::ConfigureEvent, NULL);
396 #endif
397   //this will check for Handle
398   //Render();
399 }
400 //---------------------------------------------------------------------------
401 void wxVTKRenderWindowInteractor::OnMotion(wxMouseEvent &event)
402 {
403  if (!Enabled) 
404     {
405    return;
406     }
407
408 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
409   SetEventInformationFlipY(event.GetX(), event.GetY(), 
410     event.ControlDown(), event.ShiftDown(), '\0', 0, NULL);
411
412   InvokeEvent(vtkCommand::MouseMoveEvent, NULL);
413 #else
414   InteractorStyle->OnMouseMove(event.ControlDown(), event.ShiftDown(),
415     event.GetX(), Size[1] - event.GetY() - 1);
416 #endif
417 }
418 //---------------------------------------------------------------------------
419 #if !(VTK_MAJOR_VERSION == 3 && VTK_MINOR_VERSION == 1)
420 void wxVTKRenderWindowInteractor::OnEnter(wxMouseEvent &event)
421 {
422   if (!Enabled) 
423     {
424     return;
425     }
426
427 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
428     // new style
429   SetEventInformationFlipY(event.GetX(), event.GetY(), 
430       event.ControlDown(), event.ShiftDown(), '\0', 0, NULL);
431
432   InvokeEvent(vtkCommand::EnterEvent, NULL);
433 #else
434     // old style
435   InteractorStyle->OnEnter(event.ControlDown(), event.ShiftDown(),
436       event.GetX(), Size[1] - event.GetY() - 1);  
437 #endif
438 }
439 //---------------------------------------------------------------------------
440 void wxVTKRenderWindowInteractor::OnLeave(wxMouseEvent &event)
441 {
442   if (!Enabled) 
443     {
444     return;
445     }
446
447 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
448     // new style
449   SetEventInformationFlipY(event.GetX(), event.GetY(), 
450       event.ControlDown(), event.ShiftDown(), '\0', 0, NULL);
451
452   InvokeEvent(vtkCommand::LeaveEvent, NULL);
453 #else
454     // old style
455   InteractorStyle->OnLeave(event.ControlDown(), event.ShiftDown(),
456       event.GetX(), Size[1] - event.GetY() - 1);  
457 #endif
458 }
459 //---------------------------------------------------------------------------
460 void wxVTKRenderWindowInteractor::OnKeyDown(wxKeyEvent &event)
461 {
462   if (!Enabled) 
463     {
464     return;
465     }
466
467 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
468     // new style
469   int keycode = event.GetKeyCode();
470   char key = '\0';
471   if (keycode < 256)
472   {
473     // TODO: Unicode in non-Unicode mode ??
474     key = (char)keycode;
475   }
476
477   SetEventInformationFlipY(event.GetX(), event.GetY(), 
478     event.ControlDown(), event.ShiftDown(), key, 0, NULL);
479
480   InvokeEvent(vtkCommand::KeyPressEvent, NULL);
481   InvokeEvent(vtkCommand::CharEvent, NULL);
482 #else
483   InteractorStyle->OnKeyDown(event.ControlDown(), event.ShiftDown(), 
484     event.GetKeyCode(), 1);
485 #endif
486   event.Skip();
487 }
488 //---------------------------------------------------------------------------
489 void wxVTKRenderWindowInteractor::OnKeyUp(wxKeyEvent &event)
490 {
491   if (!Enabled) 
492     {
493     return;
494     }
495
496 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
497     // new style
498   int keycode = event.GetKeyCode();
499   char key = '\0';
500   if (keycode < 256)
501   {
502     // TODO: Unicode in non-Unicode mode ??
503     key = (char)keycode;
504   }
505
506   SetEventInformationFlipY(event.GetX(), event.GetY(), 
507     event.ControlDown(), event.ShiftDown(), key, 0, NULL);
508   InvokeEvent(vtkCommand::KeyReleaseEvent, NULL);
509 #else
510   InteractorStyle->OnKeyUp(event.ControlDown(), event.ShiftDown(), 
511     event.GetKeyCode(), 1);
512 #endif
513   event.Skip();
514 }
515 #endif //!(VTK_MAJOR_VERSION == 3 && VTK_MINOR_VERSION == 1)
516 //---------------------------------------------------------------------------
517 void wxVTKRenderWindowInteractor::OnButtonDown(wxMouseEvent &event)
518 {
519   if (!Enabled || (ActiveButton != wxEVT_NULL))
520     {
521     return;
522     }
523   ActiveButton = event.GetEventType();
524
525 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
526   SetEventInformationFlipY(event.GetX(), event.GetY(), 
527     event.ControlDown(), event.ShiftDown(), '\0', 0, NULL);
528 #endif
529
530   if(event.RightDown())
531   {
532 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
533     // new style
534     InvokeEvent(vtkCommand::RightButtonPressEvent, NULL);
535 #else            
536     // old style
537     InteractorStyle->OnRightButtonDown(event.ControlDown(), event.ShiftDown(),
538       event.GetX(), Size[1] - event.GetY() - 1);
539 #endif
540   }
541   else if(event.LeftDown())
542   {
543 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
544     // new style
545     InvokeEvent(vtkCommand::LeftButtonPressEvent, NULL);
546 #else            
547     // old style
548     InteractorStyle->OnLeftButtonDown(event.ControlDown(),  event.ShiftDown(),
549       event.GetX(), Size[1] - event.GetY() - 1);
550 #endif
551   }
552   else if(event.MiddleDown())
553   {
554 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
555     // new style
556     InvokeEvent(vtkCommand::MiddleButtonPressEvent, NULL);
557 #else            
558     // old style
559     InteractorStyle->OnMiddleButtonDown(event.ControlDown(), event.ShiftDown(),
560       event.GetX(), Size[1] - event.GetY() - 1);
561 #endif
562   }
563   //save the button and capture mouse until the button is released
564   //Only if :
565   //1. it is possible (WX_USE_X_CAPTURE)
566   //2. user decided to.
567   if ((ActiveButton != wxEVT_NULL) && WX_USE_X_CAPTURE && UseCaptureMouse)
568   {
569     CaptureMouse();
570   }
571 }
572 //---------------------------------------------------------------------------
573 void wxVTKRenderWindowInteractor::OnButtonUp(wxMouseEvent &event)
574 {
575   //EVT_xxx_DOWN == EVT_xxx_UP - 1
576   //This is only needed if two mouse buttons are pressed at the same time.
577   //In wxWindows 2.4 and later: better use of wxMOUSE_BTN_RIGHT or 
578   //wxEVT_COMMAND_RIGHT_CLICK
579   if (!Enabled || (ActiveButton != (event.GetEventType()-1))) 
580     {
581     return;
582     }
583
584 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
585   SetEventInformationFlipY(event.GetX(), event.GetY(), 
586     event.ControlDown(), event.ShiftDown(), '\0', 0, NULL);
587 #endif
588   
589   if(ActiveButton == wxEVT_RIGHT_DOWN)
590   {
591 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
592     // new style
593     InvokeEvent(vtkCommand::RightButtonReleaseEvent, NULL);
594 #else            
595     // old style
596     InteractorStyle->OnRightButtonUp(event.ControlDown(), event.ShiftDown(),
597       event.GetX(), Size[1] - event.GetY() - 1);
598 #endif
599   }
600   else if(ActiveButton == wxEVT_LEFT_DOWN)
601   {
602 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
603     // new style
604     InvokeEvent(vtkCommand::LeftButtonReleaseEvent, NULL);
605 #else            
606     // old style
607     InteractorStyle->OnLeftButtonUp(event.ControlDown(), event.ShiftDown(),
608       event.GetX(), Size[1] - event.GetY() - 1);
609 #endif
610   }
611   else if(ActiveButton == wxEVT_MIDDLE_DOWN)
612   {
613 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 0)
614     // new style
615     InvokeEvent(vtkCommand::MiddleButtonReleaseEvent, NULL);
616 #else            
617     // old style
618     InteractorStyle->OnMiddleButtonUp(event.ControlDown(), event.ShiftDown(),
619       event.GetX(), Size[1] - event.GetY() - 1);
620 #endif
621   }
622   //if the ActiveButton is realeased, then release mouse capture
623   if ((ActiveButton != wxEVT_NULL) && WX_USE_X_CAPTURE && UseCaptureMouse)
624   {
625     ReleaseMouse();
626   }
627   ActiveButton = wxEVT_NULL;
628 }
629 //---------------------------------------------------------------------------
630 void wxVTKRenderWindowInteractor::OnMouseWheel(wxMouseEvent& event)
631 {
632 // Mouse wheel was only added after VTK 4.4 (I think...)
633 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 2)
634   // new style
635   //Set vtk event information ... The numebr of wheel rotations is stored in
636   //the x varible.  y varible is zero
637   SetEventInformationFlipY(event.GetWheelRotation() / event.GetWheelDelta(), 0, 
638                            event.ControlDown(), event.ShiftDown(), '\0', 0, NULL);
639   if(event.GetWheelRotation() > 0)
640     {
641       //Send event to VTK
642 // EED
643 //      InvokeEvent(vtkCommand::MouseWheelForwardEvent, NULL);
644     }
645   else
646     {
647       //Send event to VTK
648 // EED
649 //      InvokeEvent(vtkCommand::MouseWheelBackwardEvent, NULL);
650     }
651 #endif
652     
653 }
654
655 //---------------------------------------------------------------------------
656 void wxVTKRenderWindowInteractor::Render()
657 {
658   RenderAllowed = 1;
659   if (!RenderWhenDisabled)
660     {
661     //the user doesn't want us to render when the toplevel frame
662     //is disabled - first find the top level parent
663     wxWindow *topParent = wxGetTopLevelParent(this);
664     if (topParent)
665       {
666       //if it exists, check whether it's enabled
667       //if it's not enabeld, RenderAllowed will be false
668       RenderAllowed = topParent->IsEnabled();
669       }
670     }
671
672   if (RenderAllowed)
673     {
674     if(Handle && (Handle == GetHandleHack()) )
675       {
676       RenderWindow->Render();
677       }
678 #if VTK_MAJOR_VERSION == 5 || (VTK_MAJOR_VERSION == 4 && VTK_MINOR_VERSION > 2)
679     else if(GetHandleHack())
680       {
681       //this means the user has reparented us; let's adapt to the
682       //new situation by doing the WindowRemap dance
683       //store the new situation
684       Handle = GetHandleHack();
685       RenderWindow->SetNextWindowId(reinterpret_cast<void *>(Handle));
686       RenderWindow->WindowRemap();
687       RenderWindow->Render();
688       }
689 #endif
690     }
691 }
692 //---------------------------------------------------------------------------
693 void wxVTKRenderWindowInteractor::SetRenderWhenDisabled(int newValue)
694 {
695   //Change value of __RenderWhenDisabled ivar.
696   //If __RenderWhenDisabled is false (the default), this widget will not
697   //call Render() on the RenderWindow if the top level frame (i.e. the
698   //containing frame) has been disabled.
699
700   //This prevents recursive rendering during wxSafeYield() calls.
701   //wxSafeYield() can be called during the ProgressMethod() callback of
702   //a VTK object to have progress bars and other GUI elements updated -
703   //it does this by disabling all windows (disallowing user-input to
704   //prevent re-entrancy of code) and then handling all outstanding
705   //GUI events.
706         
707   //However, this often triggers an OnPaint() method for wxVTKRWIs,
708   //resulting in a Render(), resulting in Update() being called whilst
709   //still in progress.
710
711   RenderWhenDisabled = (bool)newValue;
712 }
713 //---------------------------------------------------------------------------
714 //
715 // Set the variable that indicates that we want a stereo capable window
716 // be created. This method can only be called before a window is realized.
717 //
718 void wxVTKRenderWindowInteractor::SetStereo(int capable)
719 {
720   if (Stereo != capable)
721     {
722     Stereo = capable;
723     RenderWindow->StereoCapableWindowOn();
724     RenderWindow->SetStereoTypeToCrystalEyes();
725     Modified();
726     }
727 }
728
729 //---------------------------------------------------------------------------
730 //
731 //
732 void wxVTKRenderWindowInteractor::PrintSelf(ostream& os, vtkIndent indent)
733 {
734   this->Superclass::PrintSelf(os, indent);
735 }
736
737
738 #if defined(_WIN32)
739 const char * wxVTKRenderWindowInteractor::GetClassName() const
740 {
741   return "wxVTKRenderWindowInteractor";
742 }
743 #endif //_WIN32
744
745 }
746 // LG : EO namespace bbwxvtk
747 //=======================================================================
748