]> Creatis software - cpPlugins.git/blob - appli/ImageMPR/ImageMPR.cxx
...
[cpPlugins.git] / appli / ImageMPR / ImageMPR.cxx
1 #include "ImageMPR.h"
2 #include "ui_ImageMPR.h"
3
4 #include <vtkProperty.h>
5 #include <vtkRenderWindow.h>
6
7 #include <QFileDialog>
8 #include <QMessageBox>
9
10 #ifdef _WIN32
11 #  define PLUGIN_PREFIX ""
12 #  define PLUGIN_EXT "dll"
13 #  define PLUGIN_REGEX "Plugins file (*.dll);;All files (*)"
14 #else
15 #  define PLUGIN_PREFIX "lib"
16 #  define PLUGIN_EXT "so"
17 #  define PLUGIN_REGEX "Plugins file (*.so);;All files (*)"
18 #endif // _WIN32
19
20 // -------------------------------------------------------------------------
21 ImageMPR::ImageMPR( QWidget* parent )
22   : QMainWindow( parent ),
23     m_UI( new Ui::ImageMPR ),
24     m_ImageReaderClass( "" ),
25     m_ImageWriterClass( "" ),
26     m_InputImage( NULL )
27 {
28   this->m_UI->setupUi( this );
29
30   // Create and associate renderers
31   this->m_MPRObjects = vtkSmartPointer< TMPRObjects >::New( );
32   this->m_MPRObjects->SetRenderWindows(
33     this->m_UI->m_XPlaneVTK->GetRenderWindow( ),
34     this->m_UI->m_YPlaneVTK->GetRenderWindow( ),
35     this->m_UI->m_ZPlaneVTK->GetRenderWindow( ),
36     this->m_UI->m_3DVTK->GetRenderWindow( )
37     );
38
39   // signals <-> slots
40   QObject::connect(
41     this->m_UI->actionOpenPlugins, SIGNAL( triggered( ) ),
42     this, SLOT( _triggered_actionOpenPlugins( ) )
43     );
44   QObject::connect(
45     this->m_UI->actionOpenInputImage, SIGNAL( triggered( ) ),
46     this, SLOT( _triggered_actionOpenInputImage( ) )
47     );
48   QObject::connect(
49     this->m_UI->actionOpenSegmentation, SIGNAL( triggered( ) ),
50     this, SLOT( _triggered_actionOpenSegmentation( ) )
51     );
52   QObject::connect(
53     this->m_UI->actionOpenInputPolyData, SIGNAL( triggered( ) ),
54     this, SLOT( _triggered_actionOpenInputPolyData( ) )
55     );
56
57   // Start: load all disponible plugins
58   this->_LoadPlugins(
59     std::string( PLUGIN_PREFIX ) +
60     std::string( "cpPluginsIO." ) +
61     std::string( PLUGIN_EXT )
62     );
63 }
64
65 // -------------------------------------------------------------------------
66 ImageMPR::
67 ~ImageMPR( )
68 {
69   // Close all connections
70   this->m_Plugins.UnloadAll( );
71
72   // Delete objects
73   delete this->m_UI;
74 }
75
76 // -------------------------------------------------------------------------
77 bool ImageMPR::
78 _LoadPlugins( const std::string& filename )
79 {
80   QApplication::setOverrideCursor( Qt::WaitCursor );
81   this->setEnabled( false );
82
83   this->m_ImageReaderClass = "";
84   this->m_ImageWriterClass = "";
85   this->m_MeshReaderClass = "";
86   this->m_MeshWriterClass = "";
87   this->m_UI->MenuImageToImage->clear( );
88   this->m_UI->MenuImageToMesh->clear( );
89
90   if( !( this->m_Plugins.Load( filename ) ) )
91     return( false );
92
93   typedef TPluginsInterface::TClasses _TClasses;
94   _TClasses::const_iterator cIt = this->m_Plugins.GetClasses( ).begin( );
95   for( ; cIt != this->m_Plugins.GetClasses( ).end( ); ++cIt )
96   {
97     TPluginFilter::Pointer o =
98       this->m_Plugins.CreateProcessObject( cIt->first );
99     std::string name = o->GetClassName( );
100     std::string category = o->GetClassCategory( );
101     if( category == "ImageReader" )
102       this->m_ImageReaderClass = name;
103     else if( category == "ImageWriter" )
104       this->m_ImageWriterClass = name;
105     else if( category == "MeshReader" )
106       this->m_MeshReaderClass = name;
107     else if( category == "MeshWriter" )
108       this->m_MeshWriterClass = name;
109     else if( category == "ImageToImageFilter" )
110     {
111       QAction* action =
112         this->m_UI->MenuImageToImage->addAction( QString( name.c_str( ) ) );
113       QObject::connect(
114         action, SIGNAL( triggered( ) ),
115         this, SLOT( _triggered_actionImageToImage( ) )
116         );
117     }
118     else if( category == "ImageToMeshFilter" )
119     {
120       QAction* action =
121         this->m_UI->MenuImageToMesh->addAction( QString( name.c_str( ) ) );
122       QObject::connect(
123         action, SIGNAL( triggered( ) ),
124         this, SLOT( _triggered_actionImageToMesh( ) )
125         );
126
127     } // fi
128
129   } // rof
130   QApplication::restoreOverrideCursor( );
131   this->setEnabled( true );
132
133   return( true );
134 }
135
136 // -------------------------------------------------------------------------
137 std::string ImageMPR::
138 _LoadImage( TPluginImage::Pointer& image, const QStringList& names )
139 {
140   // Block application
141   QApplication::setOverrideCursor( Qt::WaitCursor );
142   this->setEnabled( false );
143
144   std::string ret = "";
145   image = NULL;
146
147   // Get a reader from loaded plugins
148   TPluginFilter::Pointer reader =
149     this->m_Plugins.CreateProcessObject( this->m_ImageReaderClass );
150   if( reader.IsNotNull( ) )
151   {
152     // Configure reader
153     TParameters params = reader->GetDefaultParameters( );
154     QStringList::const_iterator qIt = names.begin( );
155     for( ; qIt != names.end( ); ++qIt )
156       params.AddValueToStringList( "FileNames", qIt->toStdString( ) );
157     params.SetValueAsBool( "VectorType", false );
158     reader->SetParameters( params );
159
160     // Execute and get error message, if any
161     ret = reader->Update( );
162
163     // Assign fresh image, if any
164     if( ret == "" )
165     {
166       image = reader->GetOutput< TPluginImage >( 0 );
167       reader->DisconnectOutputs( );
168
169     } // fi
170   }
171   else
172     ret = "No suitable reader object found in loaded plugins.";
173   
174   // Finish reading
175   QApplication::restoreOverrideCursor( );
176   this->setEnabled( true );
177   return( ret );
178 }
179
180 // -------------------------------------------------------------------------
181 void ImageMPR::
182 _triggered_actionOpenPlugins( )
183 {
184   // Show dialog and check if it was accepted
185   QFileDialog dialog( this );
186   dialog.setFileMode( QFileDialog::ExistingFile );
187   dialog.setDirectory( "." );
188   dialog.setNameFilter( tr( PLUGIN_REGEX ) );
189   dialog.setDefaultSuffix( tr( PLUGIN_EXT ) );
190   if( !( dialog.exec( ) ) )
191     return;
192   
193   std::string fname = dialog.selectedFiles( ).at( 0 ).toStdString( );
194   if( !( _LoadPlugins( fname ) ) )
195     QMessageBox::critical(
196       this,
197       tr( "Ignoring plugin" ),
198       tr( fname.c_str( ) )
199       );
200 }
201
202 // -------------------------------------------------------------------------
203 void ImageMPR::
204 _triggered_actionOpenInputImage( )
205 {
206   // Show dialog and check if it was accepted
207   QFileDialog dialog( this );
208   dialog.setFileMode( QFileDialog::ExistingFiles );
209   dialog.setDirectory( tr( "." ) );
210   dialog.setNameFilter(
211     tr( "Medical image files (*.mhd *.bin *.dcm);;All files (*)" )
212     );
213   dialog.setDefaultSuffix( tr( "mhd" ) );
214   if( !( dialog.exec( ) ) )
215     return;
216   
217   // Read image
218   std::string err =
219     this->_LoadImage( this->m_InputImage, dialog.selectedFiles( ) );
220   if( err == "" )
221   {
222     vtkImageData* vtk_id = this->m_InputImage->GetVTKImageData( );
223     if( vtk_id != NULL )
224     {
225       this->m_MPRObjects->SetImage( vtk_id );
226       this->m_MPRObjects->ActivateInteractors( );
227       this->m_MPRObjects->ResetCameras( );
228       this->m_MPRObjects->RenderAll( );
229     }
230     else
231       QMessageBox::critical(
232         this,
233         tr( "Error message" ),
234         tr( "Read image does not have a valid VTK converter." )
235         );
236   }
237   else
238     QMessageBox::critical(
239       this,
240       tr( "Error reading single image" ),
241       tr( err.c_str( ) )
242       );
243 }
244
245 // -------------------------------------------------------------------------
246 void ImageMPR::
247 _triggered_actionOpenSegmentation( )
248 {
249   if( this->m_InputImage.IsNull( ) )
250   {
251     QMessageBox::critical(
252       this,
253       tr( "Error message" ),
254       tr( "Before reading a segmentation, first load a raw image." )
255       );
256     return;
257
258   } // fi
259
260   // Show dialog and check if it was accepted
261   QFileDialog dialog( this );
262   dialog.setFileMode( QFileDialog::ExistingFiles );
263   dialog.setDirectory( tr( "." ) );
264   dialog.setNameFilter(
265     tr( "Medical image files (*.mhd *.bin *.dcm);;All files (*)" )
266     );
267   dialog.setDefaultSuffix( tr( "mhd" ) );
268   if( !( dialog.exec( ) ) )
269     return;
270   
271   // Read image
272   std::string err =
273     this->_LoadImage( this->m_InputSegmentation, dialog.selectedFiles( ) );
274   if( err == "" )
275   {
276     vtkImageData* vtk_id = this->m_InputSegmentation->GetVTKImageData( );
277     if( vtk_id != NULL )
278     {
279       this->m_MPRObjects->AddAuxiliaryImage( vtk_id );
280       this->m_MPRObjects->RenderAll( );
281     }
282     else
283       QMessageBox::critical(
284         this,
285         tr( "Error message" ),
286         tr( "Read image does not have a valid VTK converter." )
287         );
288   }
289   else
290     QMessageBox::critical(
291       this,
292       tr( "Error reading single image" ),
293       tr( err.c_str( ) )
294       );
295 }
296
297 // -------------------------------------------------------------------------
298 void ImageMPR::
299 _triggered_actionOpenInputPolyData( )
300 {
301   /*
302   // Show dialog and check if it was accepted
303   QFileDialog dialog( this );
304   dialog.setFileMode( QFileDialog::ExistingFile );
305   dialog.setDirectory( tr( "." ) );
306   dialog.setNameFilter(
307     tr( "Mesh files (*.vtk *.obj);;All files (*)" )
308     );
309   dialog.setDefaultSuffix( tr( "vtk" ) );
310   if( !( dialog.exec( ) ) )
311     return;
312   
313   this->m_InputMesh = NULL;
314
315   // Get a reader from plugins
316   TPluginFilter::Pointer reader =
317     this->m_Plugins.CreateProcessObject( this->m_MeshReaderClass );
318
319   // Configure reader
320   TParameters reader_params = reader->GetDefaultParameters( );
321   QStringList q_fnames = dialog.selectedFiles( );
322   QStringList::const_iterator qIt = q_fnames.begin( );
323   for( ; qIt != q_fnames.end( ); ++qIt )
324     reader_params.SetValueAsString( "FileName", qIt->toStdString( ) );
325   reader->SetParameters( reader_params );
326
327   // Execute and get error message, if any
328   QApplication::setOverrideCursor( Qt::WaitCursor );
329   this->setEnabled( false );
330   std::string err = reader->Update( );
331   QApplication::restoreOverrideCursor( );
332   this->setEnabled( true );
333
334
335   // Assign fresh image, if any
336   if( err == "" )
337   {
338     this->m_InputMesh = reader->GetOutput< TPluginMesh >( 0 );
339     reader->DisconnectOutputs( );
340     if( this->m_InputMesh.IsNotNull( ) )
341     {
342       vtkActor* vtk_actor = this->m_InputMesh->GetVTKActor( );
343       if( vtk_actor != NULL )
344       {
345         this->m_MPRObjects->Get3DRenderer( )->AddActor( vtk_actor );
346         this->m_MPRObjects->Render( 4 );
347       }
348       else
349         QMessageBox::critical(
350           this,
351           tr( "Error message" ),
352           tr( "Read mesh does not have a valid vtkActor." )
353           );
354
355     } // fi
356   }
357   else
358     QMessageBox::critical(
359       this,
360       tr( "Error reading mesh" ),
361       tr( err.c_str( ) )
362       );
363   */
364 }
365
366 // -------------------------------------------------------------------------
367 void ImageMPR::
368 _triggered_actionImageToImage( )
369 {
370   /*
371   if( this->m_InputImage.IsNull( ) )
372     return;
373
374   // Get filter name
375   QAction* action = dynamic_cast< QAction* >( this->sender( ) );
376   if( action == NULL )
377     return;
378   std::string name = action->text( ).toStdString( );
379
380   // Configure filter
381   TPluginFilter::Pointer filter =
382     this->m_Plugins.CreateProcessObject( name );
383   bool dlg_ok = filter->ExecConfigurationDialog( NULL );
384   if( !dlg_ok )
385     return;
386
387   // Execute filter
388   QApplication::setOverrideCursor( Qt::WaitCursor );
389   this->setEnabled( false );
390   filter->SetInput( 0, this->m_InputImage );
391   std::string err = filter->Update( );
392   QApplication::restoreOverrideCursor( );
393   this->setEnabled( true );
394
395   // Update image
396   if( err == "" )
397   {
398     TPluginImage* result = filter->GetOutput< TPluginImage >( 0 );
399     result->DisconnectPipeline( );
400     this->m_InputImage = result;
401     if( this->m_InputImage.IsNotNull( ) )
402       this->m_MPRObjects->SetImage( this->m_InputImage->GetVTKImageData( ) );
403   }
404   else
405     QMessageBox::critical(
406       this,
407       tr( "Error executing filter" ),
408       tr( err.c_str( ) )
409       );
410   */
411 }
412
413 // -------------------------------------------------------------------------
414 void ImageMPR::
415 _triggered_actionImageToMesh( )
416 {
417   /*
418   if( this->m_InputImage.IsNull( ) )
419     return;
420
421   // Get filter name
422   QAction* action = dynamic_cast< QAction* >( this->sender( ) );
423   if( action == NULL )
424     return;
425   std::string name = action->text( ).toStdString( );
426
427   // Configure filter
428   TPluginFilter::Pointer filter =
429     this->m_Plugins.CreateProcessObject( name );
430   bool dlg_ok = filter->ExecConfigurationDialog( NULL );
431   if( !dlg_ok )
432     return;
433
434   // Execute filter
435   QApplication::setOverrideCursor( Qt::WaitCursor );
436   this->setEnabled( false );
437   filter->SetInput( 0, this->m_InputImage );
438   std::string err = filter->Update( );
439   QApplication::restoreOverrideCursor( );
440   this->setEnabled( true );
441
442   // Update image
443   if( err == "" )
444   {
445     TPluginMesh* result = filter->GetOutput< TPluginMesh >( 0 );
446     result->DisconnectPipeline( );
447     this->m_InputMesh = result;
448     if( this->m_InputMesh.IsNotNull( ) )
449       this->m_MPRObjects->Get3DRenderer( )->AddActor(
450         this->m_InputMesh->GetVTKActor( )
451         );
452   }
453   else
454     QMessageBox::critical(
455       this,
456       tr( "Error executing filter" ),
457       tr( err.c_str( ) )
458       );
459       */
460 }
461
462 // eof - $RCSfile$