]> Creatis software - cpPlugins.git/blob - lib/cpPlugins/ActorPropertiesQtDialog.cxx
...
[cpPlugins.git] / lib / cpPlugins / ActorPropertiesQtDialog.cxx
1 #include <cpPlugins/ActorPropertiesQtDialog.h>
2
3 #ifdef cpPlugins_QT4
4
5 #include <vtkActor.h>
6 #include <vtkAxesActor.h>
7 #include <vtkImageActor.h>
8 #include <vtkImageData.h>
9 #include <vtkImageProperty.h>
10 #include <vtkMapper.h>
11 #include <vtkProperty.h>
12
13 #include <QCheckBox>
14 #include <QColorDialog>
15 #include <QDoubleSpinBox>
16 #include <QPushButton>
17 #include <QSlider>
18
19 // -------------------------------------------------------------------------
20 cpPlugins::ActorPropertiesQtDialog::
21 ActorPropertiesQtDialog( QWidget* parent, Qt::WindowFlags f )
22   : QDialog( parent, f ),
23     m_WidgetsUpdated( false )
24 {
25   this->m_Title = new QLabel( this );
26   this->m_Title->setText( "Visualization properties" );
27   this->m_MainLayout = new QGridLayout( this );
28   this->m_ToolsLayout = new QVBoxLayout( );
29   this->m_ToolsLayout->addWidget( this->m_Title );
30   this->m_MainLayout->addLayout( this->m_ToolsLayout, 0, 0, 1, 1 );
31 }
32
33 // -------------------------------------------------------------------------
34 cpPlugins::ActorPropertiesQtDialog::
35 ~ActorPropertiesQtDialog( )
36 {
37   this->m_Actors.clear( );
38   this->m_Windows.clear( );
39   delete this->m_Title;
40   delete this->m_ToolsLayout;
41   delete this->m_MainLayout;
42 }
43
44 // -------------------------------------------------------------------------
45 bool cpPlugins::ActorPropertiesQtDialog::
46 addActor( vtkProp* obj )
47 {
48   if( obj == NULL )
49     return( false );
50
51   if( this->m_Actors.size( ) > 0 )
52   {
53     bool     s = this->_addActor< vtkAxesActor >( obj );
54     if( !s ) s = this->_addActor< vtkImageActor >( obj );
55     if( !s ) s = this->_addActor< vtkActor >( obj );
56     return( s );
57   }
58   else
59   {
60     this->m_Actors.insert( obj );
61     this->m_WidgetsUpdated = false;
62     return( true );
63
64   } // fi
65 }
66
67 // -------------------------------------------------------------------------
68 bool cpPlugins::ActorPropertiesQtDialog::
69 addRenderWindow( vtkRenderWindow* win )
70 {
71   if( win == NULL )
72     return( false );
73   this->m_Windows.insert( win );
74   this->m_WidgetsUpdated = false;
75   return( true );
76 }
77
78 // -------------------------------------------------------------------------
79 int cpPlugins::ActorPropertiesQtDialog::
80 exec( )
81 {
82   this->_updateWidgets( );
83   int ret = this->QDialog::exec( );
84   /* TODO
85      if( ret == 1 )
86      this->updateParameters( );
87      else
88      this->updateView( );
89   */
90   return( ret );
91 }
92
93 // -------------------------------------------------------------------------
94 void cpPlugins::ActorPropertiesQtDialog::
95 _addButtons( )
96 {
97   // Add buttons
98   this->m_Buttons = new QDialogButtonBox( QDialogButtonBox::Ok );
99   this->connect(
100     this->m_Buttons, SIGNAL( accepted( ) ), this, SLOT( accept( ) )
101     );
102   this->connect(
103     this->m_Buttons, SIGNAL( rejected( ) ), this, SLOT( reject( ) )
104     );
105   this->m_ToolsLayout->addWidget( this->m_Buttons );
106   this->m_WidgetsUpdated = true;
107 }
108
109 // -------------------------------------------------------------------------
110 void cpPlugins::ActorPropertiesQtDialog::
111 _updateWidgets( )
112 {
113   if( this->m_WidgetsUpdated || this->m_Actors.size( ) == 0 )
114     return;
115   bool     s = this->_configureForAxes( );
116   if( !s ) s = this->_configureForImage( );
117   if( !s ) s = this->_configureForMesh( );
118   this->_addButtons( );
119 }
120
121 // -------------------------------------------------------------------------
122 bool cpPlugins::ActorPropertiesQtDialog::
123 _configureForAxes( )
124 {
125   if( this->m_Actors.size( ) == 0 )
126     return( false );
127   auto actor =
128     dynamic_cast< vtkAxesActor* >( this->m_Actors.begin( )->GetPointer( ) );
129   if( actor == NULL )
130     return( false );
131
132   // Set dialog title
133   std::stringstream title;
134   title << "Parameters for an object of class \"Axes\"";
135   this->m_Title->setText( title.str( ).c_str( ) );
136
137   /*
138     vtkAxesActor axes
139     178   axes SetShaftTypeToCylinder
140     179   axes SetXAxisLabelText "x"
141     180   axes SetYAxisLabelText "y"
142     181   axes SetZAxisLabelText "z"
143     182   axes SetTotalLength 1.5 1.5 1.5
144     183   vtkTextProperty tprop
145     184   tprop ItalicOn
146     185   tprop ShadowOn
147     186   tprop SetFontFamilyToTimes
148     187   [ axes GetXAxisCaptionActor2D ] SetCaptionTextProperty tprop
149     188   vtkTextProperty tprop2
150     189   tprop2 ShallowCopy tprop
151     190   [ axes GetYAxisCaptionActor2D ] SetCaptionTextProperty tprop2
152     191   vtkTextProperty tprop3
153     192   tprop3 ShallowCopy tprop
154     193   [ axes GetZAxisCaptionActor2D ] SetCaptionTextProperty tprop3
155   */
156
157   return( true );
158 }
159
160 // -------------------------------------------------------------------------
161 bool cpPlugins::ActorPropertiesQtDialog::
162 _configureForImage( )
163 {
164   if( this->m_Actors.size( ) == 0 )
165     return( false );
166   auto actor =
167     dynamic_cast< vtkImageActor* >( this->m_Actors.begin( )->GetPointer( ) );
168   if( actor == NULL )
169     return( false );
170   auto image = actor->GetInput( );
171   if( image == NULL )
172     return( false );
173
174   // Get properties
175   auto prop = actor->GetProperty( );
176   double r[ 2 ];
177   image->GetScalarRange( r );
178   double w = actor->GetProperty( )->GetColorWindow( );
179   double l = actor->GetProperty( )->GetColorLevel( );
180   double sw = double( 1000 ) * w / ( r[ 1 ] - r[ 0 ] );
181   double sl = double( 1000 ) * ( l - r[ 0 ] ) / ( r[ 1 ] - r[ 0 ] );
182   double op = double( 10 ) * prop->GetOpacity( );
183
184   // Set dialog title
185   std::stringstream title;
186   title << "Parameters for an object of class \"Image\"";
187   this->m_Title->setText( title.str( ).c_str( ) );
188
189   // Create widgets
190   QDoubleSpinBox* win_box = new QDoubleSpinBox( this );
191   win_box->setObjectName( "win_box" );
192   win_box->setDecimals( 3 );
193   win_box->setMinimum( 0 );
194   win_box->setMaximum( r[ 1 ] - r[ 0 ] );
195   win_box->setValue( w );
196   win_box->connect(
197     win_box, SIGNAL( valueChanged( double ) ),
198     this, SLOT( _boxWindow( double ) )
199     );
200
201   QSlider* win_sld = new QSlider( Qt::Horizontal, this );
202   win_sld->setObjectName( "win_sld" );
203   win_sld->setRange( 0, 1000 );
204   win_sld->setValue( ( unsigned int )( sw ) );
205   win_sld->connect(
206     win_sld, SIGNAL( valueChanged( int ) ),
207     this, SLOT( _sldWindow( int ) )
208     );
209
210   QHBoxLayout* win_layout = new QHBoxLayout( );
211   QLabel* win_label = new QLabel( this );
212   win_label->setText( QString( "Window: " ) );
213   win_layout->addWidget( win_label );
214   win_layout->addWidget( win_box );
215   win_layout->addWidget( win_sld );
216   this->m_ToolsLayout->addLayout( win_layout );
217
218   QDoubleSpinBox* lev_box = new QDoubleSpinBox( this );
219   lev_box->setObjectName( "lev_box" );
220   lev_box->setDecimals( 3 );
221   lev_box->setMinimum( r[ 0 ] );
222   lev_box->setMaximum( r[ 1 ] );
223   lev_box->setValue( l );
224   lev_box->connect(
225     lev_box, SIGNAL( valueChanged( double ) ),
226     this, SLOT( _boxLevel( double ) )
227     );
228
229   QSlider* lev_sld = new QSlider( Qt::Horizontal, this );
230   lev_sld->setObjectName( "lev_sld" );
231   lev_sld->setRange( 0, 1000 );
232   lev_sld->setValue( ( unsigned int )( sl ) );
233   lev_sld->connect(
234     lev_sld, SIGNAL( valueChanged( int ) ),
235     this, SLOT( _sldLevel( int ) )
236     );
237
238   QHBoxLayout* lev_layout = new QHBoxLayout( );
239   QLabel* lev_label = new QLabel( this );
240   lev_label->setText( QString( "Level: " ) );
241   lev_layout->addWidget( lev_label );
242   lev_layout->addWidget( lev_box );
243   lev_layout->addWidget( lev_sld );
244   this->m_ToolsLayout->addLayout( lev_layout );
245
246   // Configure generic objects
247   QSlider* op_sld = new QSlider( Qt::Horizontal, this );
248   op_sld->setObjectName( "op_sld" );
249   op_sld->setRange( 0, 10 );
250   op_sld->setValue( ( unsigned int )( op ) );
251   op_sld->connect(
252     op_sld, SIGNAL( valueChanged( int ) ),
253     this, SLOT( _sldOpacity( int ) )
254     );
255
256   QHBoxLayout* op_layout = new QHBoxLayout( );
257   QLabel* op_label = new QLabel( this );
258   op_label->setText( QString( "Opacity: " ) );
259   op_layout->addWidget( op_label );
260   op_layout->addWidget( op_sld );
261   this->m_ToolsLayout->addLayout( op_layout );
262
263   return( true );
264 }
265
266 // -------------------------------------------------------------------------
267 bool cpPlugins::ActorPropertiesQtDialog::
268 _configureForMesh( )
269 {
270   if( this->m_Actors.size( ) == 0 )
271     return( false );
272   auto actor =
273     dynamic_cast< vtkActor* >( this->m_Actors.begin( )->GetPointer( ) );
274   if( actor == NULL )
275     return( false );
276   auto prop = actor->GetProperty( );
277
278   // Set dialog title
279   std::stringstream title;
280   title << "Parameters for an object of class \"Mesh\"";
281   this->m_Title->setText( title.str( ).c_str( ) );
282
283   // Input boxes
284   QSpinBox* ps_box = new QSpinBox( this );
285   ps_box->setObjectName( "ps_box" );
286   ps_box->setMinimum( 1 );
287   ps_box->setMaximum( 100 );
288   ps_box->setValue( prop->GetPointSize( ) );
289   ps_box->connect(
290     ps_box, SIGNAL( valueChanged( int ) ),
291     this, SLOT( _boxPointSize( int ) )
292     );
293
294   QHBoxLayout* ps_layout = new QHBoxLayout( );
295   QLabel* ps_label = new QLabel( this );
296   ps_label->setText( QString( "Point size: " ) );
297   ps_layout->addWidget( ps_label );
298   ps_layout->addWidget( ps_box );
299   this->m_ToolsLayout->addLayout( ps_layout );
300
301   QSpinBox* lw_box = new QSpinBox( this );
302   lw_box->setObjectName( "lw_box" );
303   lw_box->setMinimum( 1 );
304   lw_box->setMaximum( 100 );
305   lw_box->setValue( prop->GetLineWidth( ) );
306   lw_box->connect(
307     lw_box, SIGNAL( valueChanged( int ) ),
308     this, SLOT( _boxLineWidth( int ) )
309     );
310
311   QHBoxLayout* lw_layout = new QHBoxLayout( );
312   QLabel* lw_label = new QLabel( this );
313   lw_label->setText( QString( "Line width: " ) );
314   lw_layout->addWidget( lw_label );
315   lw_layout->addWidget( lw_box );
316   this->m_ToolsLayout->addLayout( lw_layout );
317
318   QCheckBox* sv_box = new QCheckBox( this );
319   sv_box->setObjectName( "sv_box" );
320   sv_box->setText( "Scalar visibility: " );
321   sv_box->setChecked( ( actor->GetMapper( )->GetScalarVisibility( ) == 1 ) );
322   sv_box->connect(
323     sv_box, SIGNAL( stateChanged( int ) ),
324     this, SLOT( _scalarVisibility( int ) )
325     );
326
327   QHBoxLayout* sv_layout = new QHBoxLayout( );
328   sv_layout->addWidget( sv_box );
329   this->m_ToolsLayout->addLayout( sv_layout );
330
331   double cr, cg, cb;
332   prop->GetColor( cr, cg, cb );
333   cr *= double( 255 );
334   cg *= double( 255 );
335   cb *= double( 255 );
336
337   QPushButton* color_button = new QPushButton( "Color", this );
338   color_button->setObjectName( "color_button" );
339   QPalette color_palette = color_button->palette( );
340   color_palette.setColor( QPalette::Button, QColor( cr, cg, cb ) );
341   color_button->setAutoFillBackground( true );
342   color_button->setPalette( color_palette );
343   color_button->update( );
344   color_button->connect(
345     color_button, SIGNAL( clicked( ) ),
346     this, SLOT( _color( ) )
347     );
348
349   QHBoxLayout* color_layout = new QHBoxLayout( );
350   color_layout->addWidget( color_button );
351   this->m_ToolsLayout->addLayout( color_layout );
352
353   // Configure generic objects
354   QSlider* op_sld = new QSlider( Qt::Horizontal, this );
355   op_sld->setObjectName( "op_sld" );
356   op_sld->setRange( 0, 10 );
357   op_sld->setValue(
358     ( unsigned int )( prop->GetOpacity( ) * double( 10 ) )
359     );
360   op_sld->connect(
361     op_sld, SIGNAL( valueChanged( int ) ),
362     this, SLOT( _sldOpacity( int ) )
363     );
364
365   QHBoxLayout* op_layout = new QHBoxLayout( );
366   QLabel* op_label = new QLabel( this );
367   op_label->setText( QString( "Opacity: " ) );
368   op_layout->addWidget( op_label );
369   op_layout->addWidget( op_sld );
370   this->m_ToolsLayout->addLayout( op_layout );
371
372   return( true );
373 }
374
375 // -------------------------------------------------------------------------
376 void cpPlugins::ActorPropertiesQtDialog::
377 _setWindow( double w )
378 {
379   if( this->m_Actors.size( ) == 0 )
380     return;
381   auto aIt = this->m_Actors.begin( );
382   for( ; aIt != this->m_Actors.end( ); ++aIt )
383   {
384     auto actor = dynamic_cast< vtkImageActor* >( aIt->GetPointer( ) );
385     if( actor != NULL )
386     {
387       actor->GetProperty( )->SetColorWindow( w );
388       actor->Modified( );
389
390     } // fi
391
392   } // rof
393   this->_render( );
394 }
395
396 // -------------------------------------------------------------------------
397 void cpPlugins::ActorPropertiesQtDialog::
398 _setLevel( double l )
399 {
400   if( this->m_Actors.size( ) == 0 )
401     return;
402   auto aIt = this->m_Actors.begin( );
403   for( ; aIt != this->m_Actors.end( ); ++aIt )
404   {
405     auto actor = dynamic_cast< vtkImageActor* >( aIt->GetPointer( ) );
406     if( actor != NULL )
407     {
408       actor->GetProperty( )->SetColorLevel( l );
409       actor->Modified( );
410
411     } // fi
412
413   } // rof
414   this->_render( );
415 }
416
417 // -------------------------------------------------------------------------
418 void cpPlugins::ActorPropertiesQtDialog::
419 _render( )
420 {
421   for( auto i = this->m_Windows.begin( ); i != this->m_Windows.end( ); ++i )
422     ( *i )->Render( );
423 }
424
425 // -------------------------------------------------------------------------
426 template< class _TActor >
427 bool cpPlugins::ActorPropertiesQtDialog::
428 _addActor( vtkProp* obj )
429 {
430   auto new_obj = dynamic_cast< _TActor* >( obj );
431   auto pre_obj =
432     dynamic_cast< _TActor* >( this->m_Actors.begin( )->GetPointer( ) );
433   if( new_obj != NULL && pre_obj != NULL )
434   {
435     this->m_Actors.insert( obj );
436     this->m_WidgetsUpdated = false;
437     return( true );
438   }
439   else
440     return( false );
441 }
442
443 // -------------------------------------------------------------------------
444 void cpPlugins::ActorPropertiesQtDialog::
445 _boxWindow( double v )
446 {
447   auto* box = this->findChild< QDoubleSpinBox* >( "win_box" );
448   auto* sld = this->findChild< QSlider* >( "win_sld" );
449   if( box == NULL || sld == NULL )
450     return;
451
452   double min = double( sld->minimum( ) );
453   double max = double( sld->maximum( ) );
454   double vmin = box->minimum( );
455   double vmax = box->maximum( );
456   double s = ( v - vmin ) / ( vmax - vmin );
457   s = ( ( max - min ) * s ) + min;
458
459   bool o = sld->blockSignals( true );
460   sld->setValue( ( unsigned int )( s ) );
461   sld->blockSignals( o );
462   this->_setWindow( v );
463 }
464
465 // -------------------------------------------------------------------------
466 void cpPlugins::ActorPropertiesQtDialog::
467 _sldWindow( int v )
468 {
469   auto* box = this->findChild< QDoubleSpinBox* >( "win_box" );
470   auto* sld = this->findChild< QSlider* >( "win_sld" );
471   if( box == NULL || sld == NULL )
472     return;
473
474   double min = double( sld->minimum( ) );
475   double max = double( sld->maximum( ) );
476   double vmin = box->minimum( );
477   double vmax = box->maximum( );
478   double s = ( double( v ) - min ) / ( max - min );
479   s = ( ( vmax - vmin ) * s ) + vmin;
480
481   bool o = box->blockSignals( true );
482   box->setValue( s );
483   box->blockSignals( o );
484   this->_setWindow( s );
485 }
486
487 // -------------------------------------------------------------------------
488 void cpPlugins::ActorPropertiesQtDialog::
489 _boxLevel( double v )
490 {
491   auto* box = this->findChild< QDoubleSpinBox* >( "lev_box" );
492   auto* sld = this->findChild< QSlider* >( "lev_sld" );
493   if( box == NULL || sld == NULL )
494     return;
495
496   double min = double( sld->minimum( ) );
497   double max = double( sld->maximum( ) );
498   double vmin = box->minimum( );
499   double vmax = box->maximum( );
500   double s = ( v - vmin ) / ( vmax - vmin );
501   s = ( ( max - min ) * s ) + min;
502
503   bool o = sld->blockSignals( true );
504   sld->setValue( ( unsigned int )( s ) );
505   sld->blockSignals( o );
506   this->_setLevel( v );
507 }
508
509 // -------------------------------------------------------------------------
510 void cpPlugins::ActorPropertiesQtDialog::
511 _sldLevel( int v )
512 {
513   auto* box = this->findChild< QDoubleSpinBox* >( "lev_box" );
514   auto* sld = this->findChild< QSlider* >( "lev_sld" );
515   if( box == NULL || sld == NULL )
516     return;
517
518   double min = double( sld->minimum( ) );
519   double max = double( sld->maximum( ) );
520   double vmin = box->minimum( );
521   double vmax = box->maximum( );
522   double s = ( double( v ) - min ) / ( max - min );
523   s = ( ( vmax - vmin ) * s ) + vmin;
524
525   bool o = box->blockSignals( true );
526   box->setValue( s );
527   box->blockSignals( o );
528   this->_setLevel( s );
529 }
530
531 // -------------------------------------------------------------------------
532 void cpPlugins::ActorPropertiesQtDialog::
533 _sldOpacity( int v )
534 {
535   if( this->m_Actors.size( ) == 0 )
536     return;
537   auto* sld = this->findChild< QSlider* >( "op_sld" );
538   if( sld == NULL )
539     return;
540
541   double min = double( sld->minimum( ) );
542   double max = double( sld->maximum( ) );
543   double s = ( double( v ) - min ) / ( max - min );
544
545   auto aIt = this->m_Actors.begin( );
546   for( ; aIt != this->m_Actors.end( ); ++aIt )
547   {
548     auto ia = dynamic_cast< vtkImageActor* >( aIt->GetPointer( ) );
549     auto ma = dynamic_cast< vtkActor* >( aIt->GetPointer( ) );
550     if( ia != NULL )
551     {
552       ia->GetProperty( )->SetOpacity( s );
553       ia->Modified( );
554     }
555     else if( ma != NULL )
556     {
557       ma->GetProperty( )->SetOpacity( s );
558       ma->Modified( );
559
560     } // fi
561
562   } // rof
563   this->_render( );
564 }
565
566 // -------------------------------------------------------------------------
567 void cpPlugins::ActorPropertiesQtDialog::
568 _boxPointSize( int v )
569 {
570   if( this->m_Actors.size( ) == 0 )
571     return;
572   auto aIt = this->m_Actors.begin( );
573   for( ; aIt != this->m_Actors.end( ); ++aIt )
574   {
575     auto ma = dynamic_cast< vtkActor* >( aIt->GetPointer( ) );
576     if( ma != NULL )
577     {
578       ma->GetProperty( )->SetPointSize( v );
579       ma->Modified( );
580
581     } // fi
582
583   } // rof
584   this->_render( );
585 }
586
587 // -------------------------------------------------------------------------
588 void cpPlugins::ActorPropertiesQtDialog::
589 _boxLineWidth( int v )
590 {
591   if( this->m_Actors.size( ) == 0 )
592     return;
593   auto aIt = this->m_Actors.begin( );
594   for( ; aIt != this->m_Actors.end( ); ++aIt )
595   {
596     auto ma = dynamic_cast< vtkActor* >( aIt->GetPointer( ) );
597     if( ma != NULL )
598     {
599       ma->GetProperty( )->SetLineWidth( v );
600       ma->Modified( );
601
602     } // fi
603
604   } // rof
605   this->_render( );
606 }
607
608 // -------------------------------------------------------------------------
609 void cpPlugins::ActorPropertiesQtDialog::
610 _scalarVisibility( int v )
611 {
612   if( this->m_Actors.size( ) == 0 )
613     return;
614   auto* btn = this->findChild< QPushButton* >( "color_button" );
615   auto* chk = this->findChild< QCheckBox* >( "sv_box" );
616   if( btn == NULL || chk == NULL )
617     return;
618   QPalette pal = btn->palette( );
619   QColor color = pal.color( QPalette::Button );
620   double rgb[ 3 ];
621   rgb[ 0 ] = double( color.red( ) ) / double( 255 );
622   rgb[ 1 ] = double( color.green( ) ) / double( 255 );
623   rgb[ 2 ] = double( color.blue( ) ) / double( 255 );
624
625   auto aIt = this->m_Actors.begin( );
626   for( ; aIt != this->m_Actors.end( ); ++aIt )
627   {
628     auto ma = dynamic_cast< vtkActor* >( aIt->GetPointer( ) );
629     if( ma != NULL )
630     {
631       if( !( chk->isChecked( ) ) )
632       {
633         ma->GetMapper( )->ScalarVisibilityOff( );
634         ma->GetProperty( )->SetColor( rgb );
635       }
636       else
637         ma->GetMapper( )->ScalarVisibilityOn( );
638       ma->Modified( );
639
640     } // fi
641
642   } // rof
643   this->_render( );
644 }
645
646 // -------------------------------------------------------------------------
647 void cpPlugins::ActorPropertiesQtDialog::
648 _color( )
649 {
650   if( this->m_Actors.size( ) == 0 )
651     return;
652   auto* btn = this->findChild< QPushButton* >( "color_button" );
653   auto* chk = this->findChild< QCheckBox* >( "sv_box" );
654   if( btn == NULL || chk == NULL )
655     return;
656
657   QPalette pal = btn->palette( );
658   QColor color =
659     QColorDialog::getColor(
660       pal.color( QPalette::Button ),
661       this,
662       "Select Color",
663       QColorDialog::DontUseNativeDialog
664       );
665   if( color.isValid( ) )
666   {
667     pal.setColor( QPalette::Button, color );
668     btn->setAutoFillBackground( true );
669     btn->setPalette( pal );
670     btn->update( );
671     this->_scalarVisibility( 0 );
672
673   } // fi
674 }
675
676 #endif // cpPlugins_QT4
677
678 // eof - $RCSfile$