1 #include <cpPlugins/Interface/Plugins.h>
5 #include <cpPlugins/Interface/Image.h>
6 #include <cpPlugins/Interface/Mesh.h>
8 #ifdef cpPlugins_Interface_QT4
10 #include <QApplication>
11 #include <QFileDialog>
12 #include <QMessageBox>
16 # define PLUGIN_PREFIX ""
17 # define PLUGIN_EXT "dll"
18 # define PLUGIN_REGEX "Plugins file (*.dll);;All files (*)"
20 # define PLUGIN_PREFIX "lib"
21 # define PLUGIN_EXT "so"
22 # define PLUGIN_REGEX "Plugins file (*.so);;All files (*)"
25 #endif // cpPlugins_Interface_QT4
27 // -------------------------------------------------------------------------
28 cpPlugins::Interface::Plugins::
31 m_Application( NULL ),
32 m_LastLoadedPlugin( "" ),
33 m_ActiveFilter( NULL )
37 // -------------------------------------------------------------------------
38 cpPlugins::Interface::Plugins::
43 // -------------------------------------------------------------------------
44 QWidget* cpPlugins::Interface::Plugins::
47 return( this->m_Widget );
50 // -------------------------------------------------------------------------
51 const QWidget* cpPlugins::Interface::Plugins::
54 return( this->m_Widget );
57 // -------------------------------------------------------------------------
58 void cpPlugins::Interface::Plugins::
59 SetWidget( QWidget* widget )
61 this->m_Widget = widget;
64 // -------------------------------------------------------------------------
65 void cpPlugins::Interface::Plugins::
68 #ifdef cpPlugins_Interface_QT4
69 if( this->m_Widget != NULL )
71 QApplication::setOverrideCursor( Qt::WaitCursor );
72 this->m_Widget->setEnabled( false );
75 #endif // cpPlugins_Interface_QT4
78 // -------------------------------------------------------------------------
79 void cpPlugins::Interface::Plugins::
82 #ifdef cpPlugins_Interface_QT4
83 if( this->m_Widget != NULL )
85 QApplication::restoreOverrideCursor( );
86 this->m_Widget->setEnabled( true );
89 #endif // cpPlugins_Interface_QT4
92 // -------------------------------------------------------------------------
93 void cpPlugins::Interface::Plugins::
96 #ifdef cpPlugins_Interface_QT4
97 if( this->m_Widget != NULL )
99 QFileDialog dialog( this->m_Widget );
100 dialog.setFileMode( QFileDialog::ExistingFile );
101 dialog.setDirectory( this->m_LastLoadedPlugin.c_str( ) );
102 dialog.setNameFilter( QFileDialog::tr( PLUGIN_REGEX ) );
103 dialog.setDefaultSuffix( QFileDialog::tr( PLUGIN_EXT ) );
104 if( !( dialog.exec( ) ) )
107 std::string fname = dialog.selectedFiles( ).at( 0 ).toStdString( );
108 if( !( this->LoadPlugins( fname ) ) )
109 QMessageBox::critical(
111 QMessageBox::tr( "Ignoring plugin" ),
112 QMessageBox::tr( fname.c_str( ) )
116 #endif // cpPlugins_Interface_QT4
119 // -------------------------------------------------------------------------
120 cpPlugins::Interface::
121 BaseApplication* cpPlugins::Interface::Plugins::
124 return( this->m_Application );
127 // -------------------------------------------------------------------------
128 const cpPlugins::Interface::
129 BaseApplication* cpPlugins::Interface::Plugins::
130 GetApplication( ) const
132 return( this->m_Application );
135 // -------------------------------------------------------------------------
136 void cpPlugins::Interface::Plugins::
137 SetApplication( BaseApplication* a )
139 this->m_Application = a;
142 // -------------------------------------------------------------------------
143 bool cpPlugins::Interface::Plugins::
144 LoadPluginsPath( const std::string& path, bool r )
146 this->BlockWidget( );
148 // Load all plugins from given folder
149 std::list< std::string > files =
150 this->m_Interface.LoadFromFolder( path, r );
152 // Update a simple track
154 if( files.size( ) > 0 )
156 for( auto fIt = files.begin( ); fIt != files.end( ); ++fIt )
158 this->m_LoadedPlugins.insert( *fIt );
159 this->m_LastLoadedPlugin = *fIt;
163 this->_UpdateLoadedPluginsInformation( );
167 this->UnblockWidget( );
171 // -------------------------------------------------------------------------
172 bool cpPlugins::Interface::Plugins::
173 LoadPlugins( const std::string& fname )
175 this->BlockWidget( );
177 // Is it already loaded?
179 if( this->m_LoadedPlugins.find( fname ) == this->m_LoadedPlugins.end( ) )
181 // Was it succesfully loaded?
182 ret = this->m_Interface.Load( fname );
184 // Update a simple track
187 this->m_LoadedPlugins.insert( fname );
188 this->m_LastLoadedPlugin = fname;
189 this->_UpdateLoadedPluginsInformation( );
195 this->UnblockWidget( );
199 // -------------------------------------------------------------------------
200 bool cpPlugins::Interface::Plugins::
201 LoadPluginsConfigurationFile( const std::string& fname )
203 // Load file into a char buffer
205 fname.c_str( ), std::ios::in | std::ios::binary | std::ios::ate
210 std::streampos size = in.tellg( );
211 char* buffer = new char[ size ];
212 in.seekg( 0, std::ios::beg );
213 in.read( buffer, size );
217 std::stringstream in_stream( buffer );
221 in_stream.getline( line, 4096 );
222 this->LoadPlugins( line );
230 // -------------------------------------------------------------------------
231 const cpPlugins::Interface::Plugins::
232 TStringContainer& cpPlugins::Interface::Plugins::
233 GetLoadedPlugins( ) const
235 return( this->m_LoadedPlugins );
238 // -------------------------------------------------------------------------
239 void cpPlugins::Interface::Plugins::
240 GetLoadedCategories( TStringContainer& categories ) const
243 auto fIt = this->m_LoadedFilters.begin( );
244 for( ; fIt != this->m_LoadedFilters.end( ); ++fIt )
245 categories.insert( fIt->first );
248 // -------------------------------------------------------------------------
249 void cpPlugins::Interface::Plugins::
250 GetLoadedFilters( TStringContainer& filters ) const
253 auto pIt = this->m_LoadedFilters.begin( );
254 for( ; pIt != this->m_LoadedFilters.end( ); ++pIt )
255 for( auto fIt = pIt->second.begin( ); fIt != pIt->second.end( ); ++fIt )
256 filters.insert( *fIt );
259 // -------------------------------------------------------------------------
260 const cpPlugins::Interface::Plugins::
261 TStringContainer& cpPlugins::Interface::Plugins::
262 GetLoadedFilters( const std::string& category ) const
264 static const TStringContainer EMPTY;
265 auto pIt = this->m_LoadedFilters.find( category );
266 if( pIt != this->m_LoadedFilters.end( ) )
267 return( pIt->second );
272 // -------------------------------------------------------------------------
273 void cpPlugins::Interface::Plugins::
274 AddInteractor( vtkRenderWindowInteractor* interactor )
276 this->m_Interactors.insert( interactor );
279 // -------------------------------------------------------------------------
280 void cpPlugins::Interface::Plugins::
281 RemoveInteractor( vtkRenderWindowInteractor* interactor )
283 this->m_Interactors.erase( interactor );
286 // -------------------------------------------------------------------------
287 void cpPlugins::Interface::Plugins::
290 this->m_Interactors.clear( );
293 // -------------------------------------------------------------------------
294 #define cpPlugins_Plugins_HasMacro( F ) \
295 bool cpPlugins::Interface::Plugins:: \
298 return( this->m_IOFilters.find( #F ) != this->m_IOFilters.end( ) ); \
301 cpPlugins_Plugins_HasMacro( ImageReader );
302 cpPlugins_Plugins_HasMacro( DicomSeriesReader );
303 cpPlugins_Plugins_HasMacro( MeshReader );
304 cpPlugins_Plugins_HasMacro( ImageWriter );
305 cpPlugins_Plugins_HasMacro( MeshWriter );
307 // -------------------------------------------------------------------------
308 std::string cpPlugins::Interface::Plugins::
309 ReadImage( const std::string& fname, const std::string& parent )
311 std::vector< std::string > fnames( 1, fname );
312 return( this->ReadImage( fnames, parent ) );
315 // -------------------------------------------------------------------------
316 std::string cpPlugins::Interface::Plugins::
318 const std::vector< std::string >& fnames, const std::string& parent
322 this->_ActivateIOFilter( "ImageReader" );
325 TParameters* params = this->GetActiveFilterParameters( );
326 params->ClearStringList( "FileNames" );
327 for( auto nIt = fnames.begin( ); nIt != fnames.end( ); ++nIt )
328 params->AddToStringList( "FileNames", *nIt );
331 return( this->_ReadData( parent ) );
334 // -------------------------------------------------------------------------
335 std::string cpPlugins::Interface::Plugins::
336 ReadImage( const std::string& parent )
339 this->_ActivateIOFilter( "ImageReader" );
341 // Try to configure source
342 if( this->ConfigureActiveFilter( ) == TProcessObject::DialogResult_Cancel )
344 this->DeactivateFilter( );
350 return( this->_ReadData( parent ) );
353 // -------------------------------------------------------------------------
354 std::string cpPlugins::Interface::Plugins::
355 ReadDicomSeries( const std::string& parent )
358 this->_ActivateIOFilter( "DicomSeriesReader" );
360 // Try to configure source
361 if( this->ConfigureActiveFilter( ) == TProcessObject::DialogResult_Cancel )
363 this->DeactivateFilter( );
369 return( this->_ReadData( parent ) );
372 // -------------------------------------------------------------------------
373 std::string cpPlugins::Interface::Plugins::
374 ReadMesh( const std::string& fname, const std::string& parent )
377 this->_ActivateIOFilter( "MeshReader" );
380 TParameters* params = this->GetActiveFilterParameters( );
381 params->SetString( "FileName", fname );
384 return( this->_ReadData( parent ) );
387 // -------------------------------------------------------------------------
388 std::string cpPlugins::Interface::Plugins::
389 ReadMesh( const std::string& parent )
392 this->_ActivateIOFilter( "MeshReader" );
394 // Try to configure source
395 if( this->ConfigureActiveFilter( ) == TProcessObject::DialogResult_Cancel )
397 this->DeactivateFilter( );
403 return( this->_ReadData( parent ) );
406 // -------------------------------------------------------------------------
407 bool cpPlugins::Interface::Plugins::
408 WriteDataObject( const std::string& fname, const std::string& name )
410 typedef cpPlugins::Interface::Image _TImage;
411 typedef cpPlugins::Interface::Mesh _TMesh;
414 TDataObject* obj = this->GetData< TDataObject >( name );
415 if( dynamic_cast< cpPlugins::Interface::Image* >( obj ) != NULL )
416 this->_ActivateIOFilter( "ImageWriter" );
417 else if( dynamic_cast< cpPlugins::Interface::Mesh* >( obj ) != NULL )
418 this->_ActivateIOFilter( "MeshWriter" );
421 this->DeactivateFilter( );
427 TParameters* params = this->GetActiveFilterParameters( );
428 params->SetString( "FileName", fname );
431 return( this->_WriteData( name ) );
434 // -------------------------------------------------------------------------
435 bool cpPlugins::Interface::Plugins::
436 WriteDataObject( const std::string& name )
438 typedef cpPlugins::Interface::Image _TImage;
439 typedef cpPlugins::Interface::Mesh _TMesh;
442 TDataObject* obj = this->GetData< TDataObject >( name );
443 if( dynamic_cast< cpPlugins::Interface::Image* >( obj ) != NULL )
444 this->_ActivateIOFilter( "ImageWriter" );
445 else if( dynamic_cast< cpPlugins::Interface::Mesh* >( obj ) != NULL )
446 this->_ActivateIOFilter( "MeshWriter" );
449 this->DeactivateFilter( );
454 // Try to configure source
455 if( this->ConfigureActiveFilter( ) == TProcessObject::DialogResult_Cancel )
457 this->DeactivateFilter( );
463 return( this->_WriteData( name ) );
466 // -------------------------------------------------------------------------
467 void cpPlugins::Interface::Plugins::
470 this->m_DataObjects.clear( );
473 // -------------------------------------------------------------------------
474 void cpPlugins::Interface::Plugins::
475 DeleteDataObject( const std::string& name )
477 // Find and delete object
478 auto oIt = this->m_DataObjects.find( name );
479 if( oIt == this->m_DataObjects.end( ) )
481 this->m_DataObjects.erase( oIt );
484 TStringContainer children;
485 this->GetChildren( children, name );
486 auto cIt = children.begin( );
487 for( ; cIt != children.end( ); ++cIt )
488 this->DeleteDataObject( *cIt );
491 // -------------------------------------------------------------------------
492 void cpPlugins::Interface::Plugins::
493 GetDataObjects( TStringContainer& names )
496 auto oIt = this->m_DataObjects.begin( );
497 for( ; oIt != this->m_DataObjects.end( ); ++oIt )
498 names.insert( oIt->first );
501 // -------------------------------------------------------------------------
502 std::string cpPlugins::Interface::Plugins::
503 GetParent( const std::string& name ) const
505 // Find and delete object
506 auto oIt = this->m_DataObjects.find( name );
507 if( oIt != this->m_DataObjects.end( ) )
508 return( oIt->second.first );
513 // -------------------------------------------------------------------------
514 void cpPlugins::Interface::Plugins::
515 GetChildren( TStringContainer& names, const std::string& name ) const
518 auto oIt = this->m_DataObjects.begin( );
519 for( ; oIt != this->m_DataObjects.end( ); ++oIt )
520 if( oIt->second.first == name )
521 names.insert( oIt->first );
524 // -------------------------------------------------------------------------
525 void cpPlugins::Interface::Plugins::
526 GetRoots( TStringContainer& names ) const
528 this->GetChildren( names, "" );
531 // -------------------------------------------------------------------------
532 bool cpPlugins::Interface::Plugins::
533 ActivateFilter( const std::string& name )
535 this->m_ActiveFilter = this->m_Interface.CreateObject( name );
536 if( this->m_ActiveFilter.IsNotNull( ) )
538 this->m_ActiveFilter->SetPlugins( this );
539 auto iIt = this->m_Interactors.begin( );
540 for( ; iIt != this->m_Interactors.end( ); ++iIt )
541 this->m_ActiveFilter->AddInteractor( *iIt );
548 // -------------------------------------------------------------------------
549 void cpPlugins::Interface::Plugins::
552 this->m_ActiveFilter = NULL;
555 // -------------------------------------------------------------------------
556 bool cpPlugins::Interface::Plugins::
557 HasActiveFilter( ) const
559 return( this->m_ActiveFilter.IsNotNull( ) );
562 // -------------------------------------------------------------------------
563 bool cpPlugins::Interface::Plugins::
564 IsActiveFilterInteractive( ) const
566 if( this->m_ActiveFilter.IsNotNull( ) )
567 return( this->m_ActiveFilter->GetInteractive( ) );
572 // -------------------------------------------------------------------------
573 void cpPlugins::Interface::Plugins::
574 GetActiveFilterInputsNames( TStringContainer& names ) const
576 if( this->m_ActiveFilter.IsNotNull( ) )
577 this->m_ActiveFilter->GetInputsNames( names );
580 // -------------------------------------------------------------------------
581 void cpPlugins::Interface::Plugins::
582 GetActiveFilterOutputsNames( TStringContainer& names ) const
584 if( this->m_ActiveFilter.IsNotNull( ) )
585 this->m_ActiveFilter->GetOutputsNames( names );
588 // -------------------------------------------------------------------------
589 bool cpPlugins::Interface::Plugins::
590 ConnectInputInActiveFilter(
591 const std::string& object_name, const std::string& input_name
594 if( this->m_ActiveFilter.IsNotNull( ) )
596 TDataObject* dobj = this->GetData< TDataObject >( object_name );
599 this->m_ActiveFilter->SetInput( input_name, dobj );
608 // -------------------------------------------------------------------------
609 bool cpPlugins::Interface::Plugins::
610 SetOutputNameInActiveFilter(
611 const std::string& new_object_name, const std::string& output_name
614 if( this->m_ActiveFilter.IsNotNull( ) )
616 this->m_ActiveFilter->SetOutputObjectName(
617 new_object_name, output_name
624 // -------------------------------------------------------------------------
625 cpPlugins::Interface::Plugins::
626 TParameters* cpPlugins::Interface::Plugins::
627 GetActiveFilterParameters( )
629 if( this->m_ActiveFilter.IsNotNull( ) )
630 return( this->m_ActiveFilter->GetParameters( ) );
635 // -------------------------------------------------------------------------
636 const cpPlugins::Interface::Plugins::
637 TParameters* cpPlugins::Interface::Plugins::
638 GetActiveFilterParameters( ) const
640 if( this->m_ActiveFilter.IsNotNull( ) )
641 return( this->m_ActiveFilter->GetParameters( ) );
646 // -------------------------------------------------------------------------
647 cpPlugins::Interface::Plugins::
648 TProcessObject::DialogResult cpPlugins::Interface::Plugins::
649 ConfigureActiveFilter( )
651 if( this->m_ActiveFilter.IsNotNull( ) )
652 return( this->m_ActiveFilter->ExecConfigurationDialog( this->m_Widget ) );
654 return( TProcessObject::DialogResult_Cancel );
657 // -------------------------------------------------------------------------
658 bool cpPlugins::Interface::Plugins::
659 UpdateActiveFilter( TStringContainer& outputs, const std::string& parent )
661 if( this->m_ActiveFilter.IsNull( ) )
665 this->BlockWidget( );
666 std::string err = this->m_ActiveFilter->Update( );
667 this->UnblockWidget( );
673 std::set< std::string > names;
674 this->m_ActiveFilter->GetOutputsNames( names );
675 for( auto oIt = names.begin( ); oIt != names.end( ); ++oIt )
678 this->m_ActiveFilter->GetOutput< TDataObject >( *oIt );
679 this->_InsertNewData( dobj, parent );
680 outputs.insert( dobj->GetName( ) );
683 this->m_ActiveFilter->DisconnectOutputs( );
688 #ifdef cpPlugins_Interface_QT4
689 if( this->m_Widget != NULL )
690 QMessageBox::critical(
692 QMessageBox::tr( "Error reading image." ),
693 QMessageBox::tr( err.c_str( ) )
696 throw std::runtime_error(
697 std::string( "Error reading image: " ) + err
699 #else // cpPlugins_Interface_QT4
700 throw std::runtime_error(
701 std::string( "Error reading image: " ) + err
703 #endif // cpPlugins_Interface_QT4
709 // -------------------------------------------------------------------------
710 void cpPlugins::Interface::Plugins::
711 _UpdateLoadedPluginsInformation( )
713 this->m_LoadedFilters.clear( );
714 const TInterface::TClasses& cls = this->m_Interface.GetClasses( );
715 for( auto i = cls.begin( ); i != cls.end( ); ++i )
717 TProcessObject::Pointer o = this->m_Interface.CreateObject( i->first );
718 std::string name = o->GetClassName( );
719 std::string category = o->GetClassCategory( );
722 category == "ImageReader" ||
723 category == "ImageWriter" ||
724 category == "MeshReader" ||
725 category == "MeshWriter" ||
726 category == "DicomSeriesReader"
728 this->m_IOFilters[ category ] = o;
730 this->m_LoadedFilters[ category ].insert( name );
735 // -------------------------------------------------------------------------
736 bool cpPlugins::Interface::Plugins::
737 _ActivateIOFilter( const std::string& filter )
740 auto fIt = this->m_IOFilters.find( filter );
741 if( fIt != this->m_IOFilters.end( ) )
743 this->m_ActiveFilter = fIt->second;
750 // -------------------------------------------------------------------------
751 std::string cpPlugins::Interface::Plugins::
752 _ReadData( const std::string& parent )
754 if( !( this->HasActiveFilter( ) ) )
757 TStringContainer outputs;
758 if( this->UpdateActiveFilter( outputs, parent ) )
759 return( *( outputs.begin( ) ) );
764 // ------------------------------------------------------------------------
765 bool cpPlugins::Interface::Plugins::
766 _WriteData( const std::string& name )
768 if( !( this->HasActiveFilter( ) ) )
771 TStringContainer inputs;
772 this->GetActiveFilterInputsNames( inputs );
774 for( auto iIt = inputs.begin( ); iIt != inputs.end( ); ++iIt )
775 r &= this->ConnectInputInActiveFilter( name, *iIt );
779 TStringContainer outputs;
780 return( this->UpdateActiveFilter( outputs, "" ) );
786 // -------------------------------------------------------------------------
787 bool cpPlugins::Interface::Plugins::
788 _InsertNewData( TDataObject* dobj, const std::string& parent )
792 auto oIt = this->m_DataObjects.find( parent );
793 if( oIt == this->m_DataObjects.end( ) )
797 this->m_DataObjects[ dobj->GetName( ) ] = _TTreeNode( parent, dobj );