]> Creatis software - cpPlugins.git/blob - lib/cpExtensions/Visualization/ImageInteractorStyle.cxx
Merge ssh://git.creatis.insa-lyon.fr/cpPlugins
[cpPlugins.git] / lib / cpExtensions / Visualization / ImageInteractorStyle.cxx
1 #include <cpExtensions/Visualization/ImageInteractorStyle.h>
2
3 #include <vtkImageActor.h>
4 #include <vtkRenderWindowInteractor.h>
5
6 // -------------------------------------------------------------------------
7 cpExtensions::Visualization::ImageInteractorStyle::
8 Self* cpExtensions::Visualization::ImageInteractorStyle::
9 New( )
10 {
11   return( new Self );
12 }
13
14 // -------------------------------------------------------------------------
15 void cpExtensions::Visualization::ImageInteractorStyle::
16 AssociateView( void* data )
17 {
18   this->Data = data;
19 }
20
21 // -------------------------------------------------------------------------
22 void cpExtensions::Visualization::ImageInteractorStyle::
23 AssociateImageActor( vtkImageActor* actor )
24 {
25   this->PropPicker->AddPickList( actor );
26   this->Modified( );
27 }
28
29 // -------------------------------------------------------------------------
30 void cpExtensions::Visualization::ImageInteractorStyle::
31 OnMouseMove( )
32 {
33   // Get current position on the associated actors
34   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
35   if( rwi == NULL || this->MouseMoveCommand == NULL )
36     return;
37   double pos[ 3 ];
38   if( !( this->_PickPosition( pos ) ) )
39     return;
40
41   // Get modifiers
42   bool alt = ( rwi->GetAltKey( ) == 1 );
43   bool ctr = ( rwi->GetControlKey( ) == 1 );
44   bool sft = ( rwi->GetShiftKey( ) == 1 );
45   ButtonID button = this->GetButtonID( );
46
47   // Invoke possible events
48   this->MouseMoveCommand( this->Data, button, pos, alt, ctr, sft );
49   rwi->Render( );
50 }
51
52 // -------------------------------------------------------------------------
53 void cpExtensions::Visualization::ImageInteractorStyle::
54 OnMouseWheelForward( )
55 {
56   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
57   if( rwi == NULL || this->MouseWheelCommand == NULL )
58     return;
59
60   // Get modifiers
61   bool alt = ( rwi->GetAltKey( ) == 1 );
62   bool ctr = ( rwi->GetControlKey( ) == 1 );
63   bool sft = ( rwi->GetShiftKey( ) == 1 );
64
65   // Invoke possible events
66   this->MouseWheelCommand( this->Data, 1, alt, ctr, sft );
67 }
68
69 // -------------------------------------------------------------------------
70 void cpExtensions::Visualization::ImageInteractorStyle::
71 OnMouseWheelBackward( )
72 {
73   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
74   if( rwi == NULL || this->MouseWheelCommand == NULL )
75     return;
76
77   // Get modifiers
78   bool alt = ( rwi->GetAltKey( ) == 1 );
79   bool ctr = ( rwi->GetControlKey( ) == 1 );
80   bool sft = ( rwi->GetShiftKey( ) == 1 );
81
82   // Invoke possible events
83   this->MouseWheelCommand( this->Data, -1, alt, ctr, sft );
84 }
85
86 // -------------------------------------------------------------------------
87 void cpExtensions::Visualization::ImageInteractorStyle::
88 OnLeftClick( )
89 {
90   // Get current position on the associated actors
91   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
92   if( rwi == NULL || this->MouseClickCommand == NULL )
93     return;
94   double pos[ 3 ];
95   if( !( this->_PickPosition( pos ) ) )
96     return;
97
98   // Get modifiers
99   bool alt = ( rwi->GetAltKey( ) == 1 );
100   bool ctr = ( rwi->GetControlKey( ) == 1 );
101   bool sft = ( rwi->GetShiftKey( ) == 1 );
102
103   // Invoke possible events
104   this->MouseClickCommand( this->Data, Self::ButtonID_Left, pos, alt, ctr, sft );
105 }
106
107 // -------------------------------------------------------------------------
108 void cpExtensions::Visualization::ImageInteractorStyle::
109 OnLeftDoubleClick( )
110 {
111   // Get current position on the associated actors
112   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
113   if( rwi == NULL || this->MouseDoubleClickCommand == NULL )
114     return;
115   double pos[ 3 ];
116   if( !( this->_PickPosition( pos ) ) )
117     return;
118
119   // Get modifiers
120   bool alt = ( rwi->GetAltKey( ) == 1 );
121   bool ctr = ( rwi->GetControlKey( ) == 1 );
122   bool sft = ( rwi->GetShiftKey( ) == 1 );
123
124   // Invoke possible events
125   this->MouseDoubleClickCommand( this->Data, Self::ButtonID_Left, pos, alt, ctr, sft );
126 }
127
128 // -------------------------------------------------------------------------
129 void cpExtensions::Visualization::ImageInteractorStyle::
130 OnMiddleClick( )
131 {
132   // Get current position on the associated actors
133   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
134   if( rwi == NULL || this->MouseClickCommand == NULL )
135     return;
136   double pos[ 3 ];
137   if( !( this->_PickPosition( pos ) ) )
138     return;
139
140   // Get modifiers
141   bool alt = ( rwi->GetAltKey( ) == 1 );
142   bool ctr = ( rwi->GetControlKey( ) == 1 );
143   bool sft = ( rwi->GetShiftKey( ) == 1 );
144
145   // Invoke possible events
146   this->MouseClickCommand( this->Data, Self::ButtonID_Middle, pos, alt, ctr, sft );
147 }
148
149 // -------------------------------------------------------------------------
150 void cpExtensions::Visualization::ImageInteractorStyle::
151 OnMiddleDoubleClick( )
152 {
153   // Get current position on the associated actors
154   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
155   if( rwi == NULL || this->MouseDoubleClickCommand == NULL )
156     return;
157   double pos[ 3 ];
158   if( !( this->_PickPosition( pos ) ) )
159     return;
160
161   // Get modifiers
162   bool alt = ( rwi->GetAltKey( ) == 1 );
163   bool ctr = ( rwi->GetControlKey( ) == 1 );
164   bool sft = ( rwi->GetShiftKey( ) == 1 );
165
166   // Invoke possible events
167   this->MouseDoubleClickCommand( this->Data, Self::ButtonID_Middle, pos, alt, ctr, sft );
168 }
169
170 // -------------------------------------------------------------------------
171 void cpExtensions::Visualization::ImageInteractorStyle::
172 OnRightClick( )
173 {
174   // Get current position on the associated actors
175   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
176   if( rwi == NULL || this->MouseClickCommand == NULL )
177     return;
178   double pos[ 3 ];
179   if( !( this->_PickPosition( pos ) ) )
180     return;
181
182   // Get modifiers
183   bool alt = ( rwi->GetAltKey( ) == 1 );
184   bool ctr = ( rwi->GetControlKey( ) == 1 );
185   bool sft = ( rwi->GetShiftKey( ) == 1 );
186
187   // Invoke possible events
188   this->MouseClickCommand( this->Data, Self::ButtonID_Right, pos, alt, ctr, sft );
189 }
190
191 // -------------------------------------------------------------------------
192 void cpExtensions::Visualization::ImageInteractorStyle::
193 OnRightDoubleClick( )
194 {
195   // Get current position on the associated actors
196   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
197   if( rwi == NULL || this->MouseDoubleClickCommand == NULL )
198     return;
199   double pos[ 3 ];
200   if( !( this->_PickPosition( pos ) ) )
201     return;
202
203   // Get modifiers
204   bool alt = ( rwi->GetAltKey( ) == 1 );
205   bool ctr = ( rwi->GetControlKey( ) == 1 );
206   bool sft = ( rwi->GetShiftKey( ) == 1 );
207
208   // Invoke possible events
209   this->MouseDoubleClickCommand( this->Data, Self::ButtonID_Right, pos, alt, ctr, sft );
210 }
211
212 // -------------------------------------------------------------------------
213 void cpExtensions::Visualization::ImageInteractorStyle::
214 OnChar( )
215 {
216   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
217   if( rwi == NULL || this->KeyCommand == NULL )
218     return;
219   this->KeyCommand( this->Data, rwi->GetKeyCode( ) );
220 }
221
222 // -------------------------------------------------------------------------
223 void cpExtensions::Visualization::ImageInteractorStyle::
224 OnExpose( )
225 {
226   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
227   if( rwi == NULL )
228     return;
229 }
230
231 // -------------------------------------------------------------------------
232 void cpExtensions::Visualization::ImageInteractorStyle::
233 OnConfigure( )
234 {
235   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
236   if( rwi == NULL )
237     return;
238 }
239
240 // -------------------------------------------------------------------------
241 void cpExtensions::Visualization::ImageInteractorStyle::
242 OnEnter( )
243 {
244   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
245   if( rwi == NULL )
246     return;
247 }
248
249 // -------------------------------------------------------------------------
250 void cpExtensions::Visualization::ImageInteractorStyle::
251 OnLeave( )
252 {
253   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
254   if( rwi == NULL )
255     return;
256 }
257
258 // -------------------------------------------------------------------------
259 cpExtensions::Visualization::ImageInteractorStyle::
260 ImageInteractorStyle( )
261   : Superclass( ),
262     Data( NULL ),
263     MouseMoveCommand( NULL ),
264     MouseClickCommand( NULL ),
265     MouseDoubleClickCommand( NULL ),
266     MouseWheelCommand( NULL ),
267     KeyCommand( NULL )
268 {
269   this->PropPicker = vtkSmartPointer< vtkPropPicker >::New( );
270   this->PropPicker->PickFromListOn( );
271 }
272
273 // -------------------------------------------------------------------------
274 cpExtensions::Visualization::ImageInteractorStyle::
275 ~ImageInteractorStyle( )
276 {
277 }
278
279 // -------------------------------------------------------------------------
280 bool cpExtensions::Visualization::ImageInteractorStyle::
281 _PickPosition( double pos[ 3 ] )
282 {
283   vtkRenderWindowInteractor* rwi = this->GetInteractor( );
284   if( rwi == NULL )
285     return( false );
286
287   // Find the renderer where the event has been raised
288   double x = double( rwi->GetEventPosition( )[ 0 ] );
289   double y = double( rwi->GetEventPosition( )[ 1 ] );
290   this->FindPokedRenderer( x, y );
291
292   // Pick a 3D position
293   int r = this->PropPicker->Pick( x, y, double( 0 ), this->CurrentRenderer );
294   if( r == 0 )
295     return( false );
296   this->PropPicker->GetPickPosition( pos );
297
298   return( true );
299 }
300
301 /*
302 #include <cmath>
303 #include <ctime>
304
305 #include <vtkAnnotatedCubeActor.h>
306 #include <vtkAxesActor.h>
307 #include <vtkCallbackCommand.h>
308 #include <vtkCamera.h>
309 #include <vtkCellArray.h>
310 #include <vtkCommand.h>
311 #include <vtkMatrix4x4.h>
312 #include <vtkPropAssembly.h>
313 #include <vtkProperty.h>
314 #include <vtkRendererCollection.h>
315 #include <vtkRenderWindow.h>
316 #include <vtkRenderWindowInteractor.h>
317
318 #include <cpExtensions/Visualization/ImageSliceActors.h>
319 #include <cpExtensions/Visualization/MPRActors.h>
320
321 // -------------------------------------------------------------------------
322 const int cpExtensions::Visualization::
323 ImageInteractorStyle::CursorEvent = vtkCommand::UserEvent + 1;
324 const int cpExtensions::Visualization::
325 ImageInteractorStyle::RadiusEvent = vtkCommand::UserEvent + 2;
326 const int cpExtensions::Visualization::
327 ImageInteractorStyle::DoubleClickEvent = vtkCommand::UserEvent + 3;
328
329 // -------------------------------------------------------------------------
330 cpExtensions::Visualization::ImageInteractorStyle::
331 Self* cpExtensions::Visualization::ImageInteractorStyle::
332 New( )
333 {
334   return( new Self( ) );
335 }
336
337 // -------------------------------------------------------------------------
338 void cpExtensions::Visualization::ImageInteractorStyle::
339 Configure( ImageSliceActors* slice_actors, MPRActors* mpr_actors )
340 {
341   this->m_SliceActors = slice_actors;
342   this->m_MPRActors = mpr_actors;
343   this->SetModeToNavigation( );
344   this->PropPicker->AddPickList( slice_actors->GetImageActor( 0 ) );
345   this->Modified( );
346 }
347
348 // -------------------------------------------------------------------------
349 void cpExtensions::Visualization::ImageInteractorStyle::
350 AssociateInteractor( vtkRenderWindowInteractor* interactor )
351 {
352   if( interactor != NULL )
353   {
354     this->AssociatedInteractors.push_back( interactor );
355     this->Modified( );
356
357   } // fi
358 }
359
360 // -------------------------------------------------------------------------
361 void cpExtensions::Visualization::ImageInteractorStyle::
362 SetModeToNavigation( )
363 {
364   this->Mode = Self::NavigationMode;
365 }
366
367 // -------------------------------------------------------------------------
368 void cpExtensions::Visualization::ImageInteractorStyle::
369 SetModeToDeformation( )
370 {
371   this->Mode = Self::DeformationMode;
372 }
373
374 // -------------------------------------------------------------------------
375 void cpExtensions::Visualization::ImageInteractorStyle::
376 SetInteractor( vtkRenderWindowInteractor* interactor, const int& axis )
377 {
378   this->Superclass::SetInteractor( interactor );
379   this->OrientationWidget->SetInteractor( interactor );
380   interactor->SetInteractorStyle( this );
381   if( interactor == NULL )
382     return;
383
384   // Get camera, avoiding segfaults
385   vtkRenderer* ren =
386     interactor->GetRenderWindow( )->GetRenderers( )->GetFirstRenderer( );
387   if( ren == NULL )
388     return;
389   vtkCamera* cam = ren->GetActiveCamera( );
390   if( cam == NULL )
391     return;
392
393   // Parallel projections are better when displaying 2D images
394   cam->ParallelProjectionOn( );
395   cam->SetFocalPoint( double( 0 ), double( 0 ), double( 0 ) );
396   if( axis == 0 )
397   {
398     cam->SetPosition( double( 1 ), double( 0 ), double( 0 ) );
399     cam->SetViewUp  ( double( 0 ), double( 1 ), double( 0 ) );
400   }
401   else if( axis == 1 )
402   {
403     cam->SetPosition( double( 0 ), double( 1 ), double(  0 ) );
404     cam->SetViewUp  ( double( 0 ), double( 0 ), double( -1 ) );
405   }
406   else // if( axis == 2 )
407   {
408     cam->SetPosition( double( 0 ), double( 0 ), double( 1 ) );
409     cam->SetViewUp  ( double( 0 ), double( 1 ), double( 0 ) );
410
411   } // fi
412   ren->ResetCamera( );
413
414   // Enable 2D orientation widget
415   this->OrientationWidget->SetEnabled( 1 );
416   this->OrientationWidget->InteractiveOff( );
417 }
418
419 // -------------------------------------------------------------------------
420 void cpExtensions::Visualization::ImageInteractorStyle::
421 OnMouseMove( )
422 {
423   if( this->m_MPRActors == NULL )
424     return;
425
426   if( this->CursorMoving )
427   {
428     bool picked = this->_PickPosition( this->Cursor );
429     if( picked )
430     {
431       for( int i = 0; i < 3; ++i )
432         if( this->m_SliceActors->GetAxis( ) != i )
433           this->m_MPRActors->SetSlice( i, this->Cursor[ i ] );
434       this->InvokeEvent( Self::CursorEvent, this->Cursor );
435       this->Interactor->Render( );
436       this->_RenderAssociateInteractors( );
437
438     } // fi
439   }
440   else if( this->RadiusMoving )
441   {
442     bool picked = this->_PickPosition( this->Radius );
443     if( picked )
444     {
445       this->InvokeEvent( Self::RadiusEvent, this->Radius );
446       this->_UpdateRadius( );
447
448     } // fi
449   }
450   else
451   {
452     switch( this->State )
453     {
454     case VTKIS_WINDOW_LEVEL:
455       this->WindowLevel( );
456       break;
457     case VTKIS_DOLLY:
458       this->Dolly( );
459       break;
460     case VTKIS_PAN:
461       this->Pan( );
462       break;
463     } // hctiws
464
465   } // fi
466 }
467
468 // -------------------------------------------------------------------------
469 void cpExtensions::Visualization::ImageInteractorStyle::
470 OnLeftButtonDown( )
471 {
472   static double pnt[ 3 ];
473   static int pos[ 2 ];
474   this->Interactor->GetEventPosition( pos );
475   this->FindPokedRenderer( pos[ 0 ], pos[ 1 ] );
476   if( this->CurrentRenderer == NULL )
477     return;
478   this->GrabFocus( this->EventCallbackCommand );
479
480   // TODO: check this code
481   // Manage double-click
482   static const long epsilon_time = 800;
483   static long last_click_time = -( epsilon_time << 1 );
484   long click_time = static_cast< long >( std::clock( ) );
485   if( ( click_time - last_click_time ) < epsilon_time )
486   {
487     last_click_time = -( epsilon_time << 1 );
488     if( this->_PickPosition( pnt ) )
489       this->InvokeEvent( Self::DoubleClickEvent, pnt );
490   }
491   else
492   {
493     last_click_time = click_time;
494     if( this->Interactor->GetControlKey( ) )
495       this->StartCursorMoving( );
496
497   } // fi
498 }
499
500 // -------------------------------------------------------------------------
501 void cpExtensions::Visualization::ImageInteractorStyle::
502 OnLeftButtonUp( )
503 {
504   if( this->CursorMoving )
505   {
506     this->EndCursorMoving( );
507     if( this->Interactor )
508       this->ReleaseFocus( );
509
510   } // fi
511 }
512
513 // -------------------------------------------------------------------------
514 void cpExtensions::Visualization::ImageInteractorStyle::
515 OnMiddleButtonDown( )
516 {
517   int x = this->Interactor->GetEventPosition( )[ 0 ];
518   int y = this->Interactor->GetEventPosition( )[ 1 ];
519
520   this->FindPokedRenderer( x, y );
521   if( this->CurrentRenderer == NULL )
522     return;
523   this->GrabFocus( this->EventCallbackCommand );
524
525   if( this->Interactor->GetAltKey( ) )
526   {
527   }
528   else if( this->Interactor->GetControlKey( ) )
529   {
530     this->StartRadiusMoving( );
531   }
532   else if( this->Interactor->GetShiftKey( ) )
533   {
534   }
535   else
536     this->StartPan( );
537 }
538
539 // -------------------------------------------------------------------------
540 void cpExtensions::Visualization::ImageInteractorStyle::
541 OnMiddleButtonUp( )
542 {
543   if( this->RadiusMoving )
544   {
545     this->EndRadiusMoving( );
546     if( this->Interactor )
547       this->ReleaseFocus( );
548   }
549   else
550   {
551     switch( this->State )
552     {
553     case VTKIS_PAN:
554       this->EndPan( );
555       break;
556     } // hctiws
557
558   } // fi
559 }
560
561 // -------------------------------------------------------------------------
562 void cpExtensions::Visualization::ImageInteractorStyle::
563 OnRightButtonDown( )
564 {
565   int x = this->Interactor->GetEventPosition( )[ 0 ];
566   int y = this->Interactor->GetEventPosition( )[ 1 ];
567
568   this->FindPokedRenderer( x, y );
569   if( this->CurrentRenderer == NULL )
570     return;
571   this->GrabFocus( this->EventCallbackCommand );
572
573   if( this->Interactor->GetControlKey( ) )
574   {
575     this->WindowLevelStartPosition[ 0 ] = x;
576     this->WindowLevelStartPosition[ 1 ] = y;
577     this->StartWindowLevel( );
578   }
579   else
580   {
581     this->StartDolly( );
582
583   } // fi
584 }
585
586 // -------------------------------------------------------------------------
587 void cpExtensions::Visualization::ImageInteractorStyle::
588 OnRightButtonUp( )
589 {
590   switch( this->State )
591   {
592   case VTKIS_WINDOW_LEVEL:
593   {
594     this->EndWindowLevel( );
595     if( this->Interactor )
596       this->ReleaseFocus( );
597   }
598   break;
599   case VTKIS_DOLLY:
600     this->EndDolly( );
601     break;
602   } // hctiws
603 }
604
605 // -------------------------------------------------------------------------
606 void cpExtensions::Visualization::ImageInteractorStyle::
607 OnMouseWheelForward( )
608 {
609   if( this->m_SliceActors == NULL || this->Interactor == NULL )
610     return;
611   int off = 1;
612   if( this->Interactor->GetShiftKey( ) == 1 )
613     off *= 10;
614   int s = this->m_SliceActors->GetSliceNumber( ) + off;
615   int maxs = this->m_SliceActors->GetSliceNumberMaxValue( );
616   this->m_SliceActors->SetSliceNumber( ( s < maxs )? s: maxs );
617   this->m_MPRActors->SetSlice(
618     this->m_SliceActors->GetAxis( ),
619     this->m_SliceActors->GetSliceNumber( )
620     );
621   this->Interactor->Render( );
622   this->_RenderAssociateInteractors( );
623 }
624
625 // -------------------------------------------------------------------------
626 void cpExtensions::Visualization::ImageInteractorStyle::
627 OnMouseWheelBackward( )
628 {
629   if( this->m_SliceActors == NULL || this->Interactor == NULL )
630     return;
631   int off = 1;
632   if( this->Interactor->GetShiftKey( ) == 1 )
633     off *= 10;
634   int s = this->m_SliceActors->GetSliceNumber( ) - off;
635   int mins = this->m_SliceActors->GetSliceNumberMinValue( );
636   this->m_SliceActors->SetSliceNumber( ( mins < s )? s: mins );
637   this->m_MPRActors->SetSlice(
638     this->m_SliceActors->GetAxis( ),
639     this->m_SliceActors->GetSliceNumber( )
640     );
641   this->Interactor->Render( );
642   this->_RenderAssociateInteractors( );
643 }
644
645 // -------------------------------------------------------------------------
646 void cpExtensions::Visualization::ImageInteractorStyle::
647 OnChar( )
648 {
649   switch( this->Interactor->GetKeyCode( ) )
650   {
651   case 'r': case 'R':
652   {
653     vtkRenderer* ren =
654       this->Interactor->GetRenderWindow( )->
655       GetRenderers( )->GetFirstRenderer( );
656     if( ren != NULL )
657       ren->ResetCamera( );
658     this->Interactor->Render( );
659   }
660   break;
661   case 'w': case 'W': case 'l': case 'L':
662   {
663     if( this->m_MPRActors != NULL )
664     {
665       this->m_MPRActors->ResetWindowLevel( 0 );
666       this->Interactor->Render( );
667       this->_RenderAssociateInteractors( );
668
669     } // fi
670   }
671   break;
672   } // hctiws
673 }
674
675 // -------------------------------------------------------------------------
676 void cpExtensions::Visualization::ImageInteractorStyle::
677 WindowLevel( )
678 {
679   if( this->Mode == Self::NavigationMode )
680   {
681     if( this->Interactor == NULL )
682       return;
683     vtkRenderer* ren =
684       this->Interactor->GetRenderWindow( )->
685       GetRenderers( )->GetFirstRenderer( );
686     if( ren == NULL )
687       return;
688
689     // Compute scales
690     this->WindowLevelCurrentPosition[ 0 ] =
691       this->Interactor->GetEventPosition( )[ 0 ];
692     this->WindowLevelCurrentPosition[ 1 ] =
693       this->Interactor->GetEventPosition( )[ 1 ];
694     int* size = ren->GetSize( );
695     double sw = double(
696       this->WindowLevelCurrentPosition[ 0 ] -
697       this->WindowLevelStartPosition[ 0 ]
698       ) / double( size[ 0 ] );
699     double sl = (
700       this->WindowLevelStartPosition[ 1 ] -
701       this->WindowLevelCurrentPosition[ 1 ]
702       ) / double( size[ 1 ] );
703
704     double w = this->WindowLevelInitial[ 0 ] + ( sw * 1000.0 );
705     double l = this->WindowLevelInitial[ 1 ] + ( sl * 1000.0 );
706     double minw = this->m_MPRActors->GetMinWindow( 0 );
707     double maxw = this->m_MPRActors->GetMaxWindow( 0 );
708     double minl = this->m_MPRActors->GetMinLevel( 0 );
709     double maxl = this->m_MPRActors->GetMaxLevel( 0 );
710
711     if( w < minw ) w = minw;
712     if( maxw < w ) w = maxw;
713     if( l < minl ) l = minl;
714     if( maxl < l ) l = maxl;
715
716     this->m_MPRActors->SetWindowLevel( 0, w, l );
717     this->Interactor->Render( );
718     this->_RenderAssociateInteractors( );
719   }
720   else if( this->Mode == Self::DeformationMode )
721   {
722     // TODO
723
724   } // fi
725 }
726
727 // -------------------------------------------------------------------------
728 void cpExtensions::Visualization::ImageInteractorStyle::
729 StartWindowLevel( )
730 {
731   if( this->State != VTKIS_NONE )
732     return;
733   if( this->Mode == Self::NavigationMode )
734   {
735     this->StartState( VTKIS_WINDOW_LEVEL );
736
737     this->WindowLevelInitial[ 0 ] = this->m_MPRActors->GetWindow( 0 );
738     this->WindowLevelInitial[ 1 ] = this->m_MPRActors->GetLevel( 0 );
739   }
740   else if( this->Mode == Self::DeformationMode )
741   {
742     // TODO
743
744   } // fi
745 }
746
747 // -------------------------------------------------------------------------
748 void cpExtensions::Visualization::ImageInteractorStyle::
749 EndWindowLevel( )
750 {
751   if( this->Mode == Self::NavigationMode )
752   {
753     if( this->State != VTKIS_WINDOW_LEVEL )
754       return;
755     this->StopState( );
756   }
757   else
758   {
759     // TODO
760
761   } // fi
762 }
763
764 // -------------------------------------------------------------------------
765 void cpExtensions::Visualization::ImageInteractorStyle::
766 StartCursorMoving( )
767 {
768   if( this->CursorMoving )
769     return;
770   this->_PickPosition( this->Cursor );
771   this->CursorMoving = true;
772 }
773
774 // -------------------------------------------------------------------------
775 void cpExtensions::Visualization::ImageInteractorStyle::
776 EndCursorMoving( )
777 {
778   if( !( this->CursorMoving ) )
779     return;
780   this->CursorMoving = false;
781 }
782
783 // -------------------------------------------------------------------------
784 void cpExtensions::Visualization::ImageInteractorStyle::
785 StartRadiusMoving( )
786 {
787   if( this->RadiusMoving )
788     return;
789   this->_PickPosition( this->Radius );
790   this->RadiusMoving = true;
791   this->_UpdateRadius( );
792 }
793
794 // -------------------------------------------------------------------------
795 void cpExtensions::Visualization::ImageInteractorStyle::
796 EndRadiusMoving( )
797 {
798   if( !( this->RadiusMoving ) )
799     return;
800   this->RadiusMoving = false;
801   this->_UpdateRadius( );
802   this->InvokeEvent( Self::RadiusEvent, NULL );
803 }
804
805 // -------------------------------------------------------------------------
806 cpExtensions::Visualization::ImageInteractorStyle::
807 ImageInteractorStyle( )
808   : Superclass( ),
809     Mode( Self::NavigationMode ),
810     m_SliceActors( NULL ),
811     m_MPRActors( NULL ),
812     CursorMoving( false ),
813     RadiusMoving( false )
814 {
815   // Orientation marks
816   vtkSmartPointer< vtkAnnotatedCubeActor > cube =
817     vtkSmartPointer< vtkAnnotatedCubeActor >::New( );
818   cube->GetCubeProperty( )->SetColor( 0.9, 0.7, 0.2 );
819   cube->GetTextEdgesProperty( )->SetLineWidth( 1 );
820   cube->GetTextEdgesProperty( )->SetDiffuse( 0 );
821   cube->GetTextEdgesProperty( )->SetAmbient( 1 );
822   cube->GetTextEdgesProperty( )->SetColor( 0.18, 0.28, 0.23 );
823   cube->GetXPlusFaceProperty( )->SetColor( 1, 0, 0 );
824   cube->GetXPlusFaceProperty( )->SetInterpolationToFlat( );
825   cube->GetXMinusFaceProperty( )->SetColor( 1, 0, 0 );
826   cube->GetXMinusFaceProperty( )->SetInterpolationToFlat( );
827   cube->GetYPlusFaceProperty( )->SetColor( 0, 1, 0 );
828   cube->GetYPlusFaceProperty( )->SetInterpolationToFlat( );
829   cube->GetYMinusFaceProperty( )->SetColor( 0, 1, 0 );
830   cube->GetYMinusFaceProperty( )->SetInterpolationToFlat( );
831   cube->GetZPlusFaceProperty( )->SetColor( 0, 0, 1 );
832   cube->GetZPlusFaceProperty( )->SetInterpolationToFlat( );
833   cube->GetZMinusFaceProperty( )->SetColor( 0, 0, 1 );
834   cube->GetZMinusFaceProperty( )->SetInterpolationToFlat( );
835
836   vtkSmartPointer< vtkAxesActor > axes =
837     vtkSmartPointer< vtkAxesActor >::New( );
838   axes->AxisLabelsOff( );
839   axes->SetShaftTypeToCylinder( );
840   axes->SetTotalLength( 2, 2, 2 );
841
842   vtkSmartPointer< vtkPropAssembly > actors =
843     vtkSmartPointer< vtkPropAssembly >::New( );
844   actors->AddPart( cube );
845   actors->AddPart( axes );
846
847   this->OrientationWidget =
848     vtkSmartPointer< vtkOrientationMarkerWidget >::New( );
849   this->OrientationWidget->SetOutlineColor( 0.93, 0.57, 0.13 );
850   this->OrientationWidget->SetOrientationMarker( actors );
851   this->OrientationWidget->SetViewport( 0.0, 0.0, 0.2, 0.2 );
852
853   // Circle
854   unsigned long circle_samples = 1000;
855   this->Circle = vtkSmartPointer< vtkPolyData >::New( );
856
857   vtkSmartPointer< vtkPoints > circle_points =
858     vtkSmartPointer< vtkPoints >::New( );
859   vtkSmartPointer< vtkCellArray > circle_lines =
860     vtkSmartPointer< vtkCellArray >::New( );
861   for( unsigned long s = 0; s < circle_samples; ++s )
862   {
863     double t = double( 6.2832 ) * double( s ) / double( circle_samples );
864     circle_points->InsertNextPoint(
865       std::cos( t ), std::sin( t ), double( 0 )
866       );
867
868     circle_lines->InsertNextCell( 2 );
869     circle_lines->InsertCellPoint( s );
870     circle_lines->InsertCellPoint( ( s + 1 ) % circle_samples );
871
872   } // rof
873   this->Circle->SetPoints( circle_points );
874   this->Circle->SetLines( circle_lines );
875
876   this->CircleMapper = vtkSmartPointer< vtkPolyDataMapper >::New( );
877   this->CircleMapper->SetInputData( this->Circle );
878   this->CircleActor = vtkSmartPointer< vtkActor >::New( );
879   this->CircleActor->SetMapper( this->CircleMapper );
880   this->CircleActor->GetProperty( )->SetColor( 1, 0, 1 );
881   this->CircleActor->GetProperty( )->SetLineWidth( 2 );
882
883   this->PropPicker = vtkSmartPointer< vtkPropPicker >::New( );
884   this->PropPicker->PickFromListOn( );
885 }
886
887 // -------------------------------------------------------------------------
888 cpExtensions::Visualization::ImageInteractorStyle::
889 ~ImageInteractorStyle( )
890 {
891 }
892
893 // -------------------------------------------------------------------------
894 void cpExtensions::Visualization::ImageInteractorStyle::
895 _RenderAssociateInteractors( )
896 {
897   std::vector< vtkRenderWindowInteractor* >::iterator rIt =
898     this->AssociatedInteractors.begin( );
899   for( ; rIt != this->AssociatedInteractors.end( ); ++rIt )
900     ( *rIt )->Render( );
901 }
902
903 // -------------------------------------------------------------------------
904 bool cpExtensions::Visualization::ImageInteractorStyle::
905 _PickPosition( double pos[ 3 ] )
906 {
907   if( this->m_SliceActors == NULL )
908     return( false );
909
910   double x = double( this->Interactor->GetEventPosition( )[ 0 ] );
911   double y = double( this->Interactor->GetEventPosition( )[ 1 ] );
912   this->FindPokedRenderer( x, y );
913   int success =
914     this->PropPicker->Pick( x, y, double( 0 ), this->CurrentRenderer );
915   if( success == 0 )
916     return( false );
917   this->PropPicker->GetPickPosition( pos );
918
919   int axis = this->m_SliceActors->GetAxis( );
920   double* bounds = this->m_SliceActors->GetDisplayBounds( );
921   pos[ axis ] = bounds[ axis << 1 ];
922
923   return( true );
924 }
925
926 // -------------------------------------------------------------------------
927 void cpExtensions::Visualization::ImageInteractorStyle::
928 _UpdateCursor( )
929 {
930   std::cout << "upcur" << std::endl;
931 }
932
933 // -------------------------------------------------------------------------
934 void cpExtensions::Visualization::ImageInteractorStyle::
935 _UpdateRadius( )
936 {
937   vtkRenderer* ren =
938     this->Interactor->GetRenderWindow( )->
939     GetRenderers( )->GetFirstRenderer( );
940   if( ren == NULL )
941     return;
942   vtkCamera* cam = ren->GetActiveCamera( );
943   if( cam == NULL )
944     return;
945
946   if( this->RadiusMoving )
947   {
948     double x = this->Cursor[ 0 ] - this->Radius[ 0 ];
949     double y = this->Cursor[ 1 ] - this->Radius[ 1 ];
950     double z = this->Cursor[ 2 ] - this->Radius[ 2 ];
951     double r = std::sqrt( ( x * x ) + ( y * y ) + ( z * z ) );
952
953     vtkMatrix4x4* cam_matrix = cam->GetModelViewTransformMatrix( );
954     vtkSmartPointer< vtkMatrix4x4 > circle_matrix =
955       this->CircleActor->GetUserMatrix( );
956     if( circle_matrix.GetPointer( ) == NULL )
957     {
958       circle_matrix = vtkSmartPointer< vtkMatrix4x4 >::New( );
959       this->CircleActor->SetUserMatrix( circle_matrix );
960
961     } // fi
962     for( int i = 0; i < 4; ++i )
963     {
964       for( int j = 0; j < 4; ++j )
965       {
966         double v = cam_matrix->GetElement( i, j );
967         if( i < 3 && j == 3 )
968           v = this->Cursor[ i ];
969         if( i < 3 && j < 3 )
970           v *= r;
971         circle_matrix->SetElement( i, j, v );
972
973       } // rof
974
975     } // rof
976     this->CircleActor->Modified( );
977     ren->AddActor( this->CircleActor );
978   }
979   else
980     ren->RemoveActor( this->CircleActor );
981
982   this->Interactor->Render( );
983 }
984 */
985
986 // eof - $RCSfile$