Biomedical Image Analysis Library
The Biomedical Image Analysis Library is a poweful tool for developers, physicians, researchers, engineers, and so on.
mainwindow.cpp
Go to the documentation of this file.
1 #include "Color.hpp"
2 #include "controller.h"
3 #include "defaulttool.h"
4 #include "dicomdir.h"
5 #include "imagewidget.h"
6 #include "mainwindow.h"
7 #include "ui_mainwindow.h"
8 
9 #include "segmentationtool.h"
10 #include <QFileDialog>
11 #include <QFileInfoList>
12 #include <QGraphicsPixmapItem>
13 #include <QMessageBox>
14 #include <QProgressDialog>
15 #include <QSettings>
16 
17 MainWindow::MainWindow( QWidget *parent ) : QMainWindow( parent ), ui( new Ui::MainWindow ),
18  controller( new Controller( 4, this ) ) {
19 
20  ui->setupUi( this );
21 
22  controller->setThumbsWidget( ui->thumbsWidget );
23 
24  ui->controlsWidget->setController( controller );
25  ui->controlsDock->hide( );
26  ui->dockWidgetSegmentation->hide( );
27  ui->imageViewer->setController( controller );
28  ui->actionPrint->setEnabled( false );
29  /*
30  * ui->dockWidgetFunctional->hide( );
31  * ui->widgetDragDrop->hide( );
32  */
33 
34  setupLogoview( );
35  createConnections( );
36  currentImageChanged( );
37  readSettings( );
38  createActions( );
39  loadQss( );
40  containerUpdated( );
41 
42  ui->toolBar->setVisible( true );
43 
44  QActionGroup *group = new QActionGroup( this );
45  actionDefaultTool = group->addAction( "Default Tool" );
46  actionSegmentationTool = group->addAction( "Segmentation Tool" );
47  actionDefaultTool->setCheckable( true );
48  actionDefaultTool->setChecked( true );
49  actionSegmentationTool->setCheckable( true );
50  actionSegmentationTool->setChecked( false );
51 
52  connect( actionDefaultTool, &QAction::triggered, this, &MainWindow::on_actionDefaultTool_triggered );
53  connect( actionSegmentationTool, &QAction::triggered, this, &MainWindow::on_actionSegmentationTool_triggered );
54 
55  ui->toolBar->addActions( group->actions( ) );
56 
57 #ifndef LIBGDCM
58  ui->actionOpen_DicomDir->setVisible( false );
59 #endif
60 }
61 
62 void MainWindow::createConnections( ) {
63  /* Show/Hide docks. */
64  connect( ui->actionShow_controls_dock, &QAction::toggled, ui->controlsDock, &QDockWidget::setVisible );
65  connect( ui->actionHistogram_dock, &QAction::toggled, ui->dockWidgetHistogram, &QDockWidget::setVisible );
66  connect( ui->actionShow_images_dock, &QAction::toggled, ui->thumbsDock, &QDockWidget::setVisible );
67  connect( ui->actionSegmentation_dock, &QAction::toggled, ui->dockWidgetSegmentation, &QDockWidget::setVisible );
68  connect( ui->controlsDock, &QDockWidget::visibilityChanged, ui->actionShow_controls_dock, &QAction::setChecked );
69  connect( ui->thumbsDock, &QDockWidget::visibilityChanged, ui->actionShow_images_dock, &QAction::setChecked );
70  connect( ui->dockWidgetHistogram, &QDockWidget::visibilityChanged, ui->actionHistogram_dock, &QAction::setChecked );
71  connect( ui->dockWidgetSegmentation, &QDockWidget::visibilityChanged, ui->actionSegmentation_dock,
72  &QAction::setChecked );
73 
74  /* Controller. */
75  connect( controller, &Controller::currentImageChanged, this, &MainWindow::currentImageChanged );
76  connect( controller, &Controller::imageUpdated, this, &MainWindow::imageUpdated );
77  connect( controller, &Controller::containerUpdated, this, &MainWindow::containerUpdated );
78  connect( controller, &Controller::recentFilesUpdated, this, &MainWindow::updateRecentFileActions );
79 
80  /* ImageViewer */
81  connect( ui->imageViewer, &ImageViewer::mouseClicked, this, &MainWindow::updateIntensity );
82  connect( ui->imageViewer, &ImageViewer::mouseReleased, this, &MainWindow::updateIntensity );
83  connect( ui->imageViewer, &ImageViewer::mouseDragged, this, &MainWindow::updateIntensity );
84 
85  connect( ui->logoView, &GraphicsView::dropImage, this, &MainWindow::loadFile );
86  connect( ui->logoView, &GraphicsView::dropFolder, this, &MainWindow::loadFolder );
87  /*
88  * connect( ui->imageViewer, &ImageViewer::dropImage, this, &MainWindow::loadFile );
89  * connect( ui->imageViewer, &ImageViewer::dropFolder, this, &MainWindow::loadFolder );
90  */
91 }
92 
93 void MainWindow::setupLogoview( ) {
94  QGraphicsScene *scn = new QGraphicsScene( this );
95  QGraphicsPixmapItem *pixmapItem = new QGraphicsPixmapItem( QPixmap( ":/icons/logo_shadow.png" ) );
96  scn->addItem( pixmapItem );
97  scn->setSceneRect( 0, 0, pixmapItem->pixmap( ).width( ), pixmapItem->pixmap( ).height( ) );
98  ui->logoView->setScene( scn );
99 }
100 
102  delete ui;
103 }
104 
105 void MainWindow::on_actionRed_background_triggered( ) {
106  ui->imageViewer->setViewBgColor( Qt::red );
107 }
108 
109 void MainWindow::on_actionGreen_background_triggered( ) {
110  ui->imageViewer->setViewBgColor( Qt::green );
111 }
112 
113 void MainWindow::on_actionBlue_background_triggered( ) {
114  ui->imageViewer->setViewBgColor( Qt::blue );
115 }
116 
117 void MainWindow::on_actionBlack_background_triggered( ) {
118  ui->imageViewer->setViewBgColor( Qt::black );
119 }
120 
121 void MainWindow::on_actionWhite_background_triggered( ) {
122  ui->imageViewer->setViewBgColor( Qt::white );
123 }
124 
125 void MainWindow::currentImageChanged( ) {
126  if( controller->currentImage( ) ) {
127  DisplayFormat *format = controller->currentFormat( );
128  actionDefaultTool->setVisible( DefaultTool::supportedFormats & ( int ) format->modality( ) );
129  actionSegmentationTool->setVisible( SegmentationTool::supportedFormats & ( int ) format->modality( ) );
130 
131  ui->menuLayout->setEnabled( format->modality( ) != Modality::BW2D );
132  ui->menuOverlay->setEnabled( format->hasOverlay( ) );
133 
134  ui->actionGrid->setVisible( format->showOrientation( ) );
135  ui->actionHorizontal->setVisible( format->showOrientation( ) );
136  ui->actionVertical->setVisible( format->showOrientation( ) );
137 
138  ui->actionAxial->setVisible( format->modality( ) == Modality::BW3D );
139  ui->actionCoronal->setVisible( format->modality( ) == Modality::BW3D );
140  ui->actionSagittal->setVisible( format->modality( ) == Modality::BW3D );
141 
142  ui->actionRed_channel->setVisible( format->modality( ) == Modality::RGB2D );
143  ui->actionGreen_channel->setVisible( format->modality( ) == Modality::RGB2D );
144  ui->actionBlue_channel->setVisible( format->modality( ) == Modality::RGB2D );
145  ui->actionAll_channels->setVisible( format->modality( ) == Modality::RGB2D );
146 
147  ui->action3_Views->setVisible( format->has3Views( ) );
148  ui->action4_Views->setVisible( format->has4Views( ) );
149  if( controller->currentImage( )->tools.empty( ) ) {
150  actionDefaultTool->setChecked( true );
151  }
152  else if( controller->currentImage( )->currentTool( )->type( ) == DefaultTool::Type ) {
153  actionDefaultTool->setChecked( true );
154  }
155  else if( controller->currentImage( )->currentTool( )->type( ) == SegmentationTool::Type ) {
156  actionSegmentationTool->setChecked( true );
157  }
158  ui->segmentationWidget->setTool( controller->currentImage( )->currentTool( ) );
159  }
160 }
161 
162 void MainWindow::imageUpdated( ) {
163  const Bial::Signal &hist = controller->currentImage( )->getHistogram( );
164  QCustomPlot *plot = ui->histogramWidget;
165  QVector< double > x( hist.size( ) ), y( hist.size( ) );
166  for( size_t bin = 0; bin < hist.size( ); ++bin ) {
167  x[ bin ] = hist.Data( bin );
168  y[ bin ] = hist[ bin ];
169  }
170  plot->addGraph( );
171  plot->setInteraction( QCP::iRangeDrag, true );
172  plot->setInteraction( QCP::iRangeZoom, true );
173  plot->graph( 0 )->clearData( );
174  plot->graph( 0 )->setData( x, y );
175  plot->axisRect( 0 )->setRangeDrag( Qt::Vertical );
176  plot->axisRect( 0 )->setRangeZoom( Qt::Vertical );
177  plot->axisRect( 0 )->setRangeZoomAxes( plot->xAxis, plot->yAxis );
178  plot->graph( 0 )->setLineStyle( QCPGraph::lsImpulse );
179  plot->xAxis->setLabel( "Intensity" );
180  plot->yAxis->setLabel( "Frequency" );
181  plot->rescaleAxes( true );
182  plot->replot( );
183  if( controller->currentImage( ) ) {
184  ui->segmentationWidget->setTool( controller->currentImage( )->currentTool( ) );
185  }
186 }
187 
188 void MainWindow::containerUpdated( ) {
189  COMMENT( "MainWindow::containerUpdated( )", 0 );
190  if( controller->size( ) <= 1 ) {
191  ui->thumbsDock->hide( );
192  }
193  else {
194  ui->thumbsDock->show( );
195  }
196  bool hasImage = ( controller->currentImage( ) != nullptr );
197  ui->toolBar->setVisible( hasImage );
198  COMMENT( "Has Image = " << hasImage, 0 );
199  ui->menuWindow->setEnabled( hasImage );
200  ui->controlsDock->setVisible( hasImage );
201  ui->logoView->setVisible( !hasImage );
202  ui->imageViewer->setVisible( hasImage );
203  ui->menuLayout->setEnabled( hasImage );
204  ui->menuOverlay->setEnabled( hasImage );
205  ui->actionRemove_current_image->setEnabled( hasImage );
206  ui->actionAddLabel->setEnabled( hasImage );
207  if( !hasImage ) {
208  ui->actionRemove_current_label->setEnabled( false );
209  ui->dockWidgetHistogram->hide( );
210  }
211  ui->actionShow_controls_dock->setEnabled( hasImage );
212  ui->actionShow_images_dock->setEnabled( hasImage );
213  currentImageChanged( );
214 }
215 
216 void MainWindow::on_actionOpen_image_triggered( ) {
217  QString fileName = getFileDialog( );
218  if( fileName.isEmpty( ) ) {
219  return;
220  }
221  if( !loadFile( fileName ) ) {
222  QMessageBox::warning( this, "Warning", tr( "Could not open file!" ) );
223  return;
224  }
225 }
226 
227 QString MainWindow::getFileDialog( ) {
228  return( QFileDialog::getOpenFileName(
229  this, tr( "Open" ), defaultFolder,
230  tr( "All images (*.pbm *.pbm.gz *.pgm *.pgm.gz *.ppm *.ppm.gz *.dcm "
231  "*.dcm.gz *.nii *.nii.gz *.scn *.scn.gz);; PBM images (*.pbm *.pbm.gz);; PGM images "
232  "(*.pgm *.pgm.gz);; PPM images (*.ppm *.ppm.gz);; DICOM images "
233  "(*.dcm *.dcm.gz);; NIfTI images (*.nii *.nii.gz);; SCN Files (*.scn *.scn.gz);; All files (*)" ) ) );
234 }
235 
236 bool MainWindow::loadFile( QString filename ) {
237  COMMENT( "Loading file: " << filename.toStdString( ), 0 );
238  controller->clear( );
239  return( controller->addImage( filename ) );
240 }
241 
242 bool MainWindow::loadFolder( QString dirname ) {
243  QDir folder( dirname );
244  COMMENT( "Reding folder: " << folder.absolutePath( ).toStdString( ) << ".", 1 );
245  QFileInfoList list = folder.entryInfoList( QDir::NoDotAndDotDot | QDir::Files, QDir::DirsFirst | QDir::Name );
246  bool value = false;
247  /* qDebug() << "list size: " << list.size(); */
248  CursorChanger c( Qt::WaitCursor );
249 
250  QProgressDialog progress( "Reading files...", "Abort", 0, list.size( ), this );
251  progress.setWindowModality( Qt::WindowModal );
252  int size = list.size( );
253  for( int i = 0; i < size; ++i ) {
254  progress.setValue( i );
255  if( progress.wasCanceled( ) ) {
256  break;
257  }
258  QFileInfo fileInfo = list.at( i );
259  if( fileInfo.isFile( ) and checkExtension( fileInfo.completeSuffix( ).toLower( ) ) ) {
260  QString fileName = fileInfo.absoluteFilePath( );
261  if( controller->addImage( fileName ) ) {
262  value = true;
263  }
264  else {
265  BIAL_WARNING( std::string( "Could not open file!" ) );
266  statusBar( )->showMessage( tr( "Could not open file!" ), 2000 );
267  continue;
268  }
269  }
270  }
271  progress.setValue( list.size( ) );
272 
273  return( value );
274 }
275 
276 bool MainWindow::checkExtension( const QString &suffix ) { /* receive to lower */
277  if( suffix == "scn" or suffix == "scn.gz" or suffix == "img" or suffix == "img.gz" or suffix == "hdr" or
278  suffix == "hdr.gz" or suffix == "nii" or suffix == "nii.gz" or suffix == "pnm" or suffix == "pnm.gz" or
279  suffix == "pgm" or suffix == "pgm.gz" or suffix == "pbm" or suffix == "pbm.gz" or suffix == "dcm" or
280  suffix == "dcm.gz" ) {
281  return( true );
282  }
283  else {
284  return( false );
285  }
286 }
287 
288 void MainWindow::readSettings( ) {
289  COMMENT( "Reading QSettings", 1 );
290  QSettings settings;
291 
292  settings.beginGroup( "MainWindow" );
293  defaultFolder = settings.value( "defaultFolder" ).toString( );
294  if( defaultFolder.isEmpty( ) ) {
295  defaultFolder = QDir::homePath( );
296  }
297 }
298 
299 void MainWindow::commandLineOpen( int argc, char *argv[] ) {
300  COMMENT( "Command Line Open with " << argc << " arguments:", 0 );
301  if( ( argc == 3 ) && ( QString( argv[ 1 ] ) == "-d" ) ) {
302  loadDicomdir( QString( argv[ 2 ] ) );
303  }
304  else {
305  QFileInfo file;
306  for( int img = 1; img < argc; ++img ) {
307  QString fileName( argv[ img ] );
308  file.setFile( fileName );
309  COMMENT( "\tArgument[" << img << "] = " << fileName.toStdString( ), 0 );
310  if( file.exists( ) ) {
311  if( file.isFile( ) ) {
312  controller->addImage( file.absoluteFilePath( ) );
313  }
314  else if( file.isDir( ) ) {
315  loadFolder( file.absoluteFilePath( ) );
316  }
317  }
318  else {
319  BIAL_WARNING( "FILE DOES NOT EXISTS! : " << file.absolutePath( ).toStdString( ) );
320  }
321  }
322  }
323 }
324 
325 void MainWindow::on_actionQuit_triggered( ) {
326  close( );
327 }
328 
329 void MainWindow::openRecentFile( ) {
330  QAction *action = qobject_cast< QAction* >( sender( ) );
331  if( action ) {
332  QString fileName = action->data( ).toString( );
333  loadFile( fileName );
334  }
335 }
336 
337 void MainWindow::updateRecentFileActions( ) {
338  QSettings settings;
339  QStringList files = settings.value( "recentFileList" ).toStringList( );
340 
341  int numRecentFiles = qMin( files.size( ), ( int ) Controller::MaxRecentFiles );
342  if( numRecentFiles > 0 ) {
343  ui->menuRecent_files->setEnabled( true );
344  }
345  for( int i = 0; i < numRecentFiles; ++i ) {
346  QString text = QString( "&%1 %2" ).arg( i + 1 ).arg( QFileInfo( files[ i ] ).fileName( ) );
347  recentFileActs[ i ]->setText( text );
348  recentFileActs[ i ]->setData( files[ i ] );
349  recentFileActs[ i ]->setVisible( true );
350  }
351  for( int i = numRecentFiles; i < Controller::MaxRecentFiles; ++i ) {
352  recentFileActs[ i ]->setVisible( false );
353  }
354 }
355 
356 void MainWindow::createActions( ) {
357  for( int i = 0; i < Controller::MaxRecentFiles; ++i ) {
358  recentFileActs[ i ] = new QAction( this );
359  recentFileActs[ i ]->setVisible( false );
360  connect( recentFileActs[ i ], &QAction::triggered, this, &MainWindow::openRecentFile );
361  ui->menuRecent_files->addAction( recentFileActs[ i ] );
362  }
363  updateRecentFileActions( );
364  for( int i = 0; i < Controller::MaxRecentFiles; ++i ) {
365  ui->menuRecent_files->addAction( recentFileActs[ i ] );
366  }
367 }
368 
369 void MainWindow::loadQss( ) {
370  QFile file( ":/qss/stylesheet.qss" );
371  file.open( QFile::ReadOnly );
372  QString StyleSheet = QLatin1String( file.readAll( ) );
373  setStyleSheet( StyleSheet );
374 }
375 
376 bool MainWindow::loadDicomdir( QString dicomFName ) {
377  COMMENT( "Loading DicomDir file", 1 );
378  CursorChanger c( Qt::WaitCursor );
379  DicomDir dicomdir;
380  if( !dicomdir.open( dicomFName ) ) {
381  statusBar( )->showMessage( tr( "Could not open dicomdir" ), 2000 );
382  return( false );
383  }
384  const QStringList files = dicomdir.getImages( );
385  if( files.size( ) > 0 ) {
386  controller->clear( );
387  QProgressDialog progress( tr( "Reading dicomdir files..." ), tr( "Abort" ), 0, files.size( ), this );
388  progress.setWindowModality( Qt::WindowModal );
389  for( int i = 0, size = files.size( ); i < size; ++i ) {
390  progress.setValue( i );
391  if( progress.wasCanceled( ) ) {
392  break;
393  }
394  controller->addImage( files[ i ].trimmed( ) );
395  }
396  progress.setValue( files.size( ) );
397  if( controller->size( ) < 1 ) {
398  statusBar( )->showMessage( tr( "Could not load any dicomdir images" ), 2000 );
399  return( false );
400  }
401  return( true );
402  }
403  statusBar( )->showMessage( tr( "Empty dicomdir!" ), 2000 );
404  BIAL_WARNING( "Empty dicomdir!" );
405 
406  return( false );
407 }
408 
409 void MainWindow::on_actionAddLabel_triggered( ) {
410  controller->addLabel( getFileDialog( ) );
411 }
412 
413 void MainWindow::on_actionOpen_folder_triggered( ) {
414  QString folderString = QFileDialog::getExistingDirectory( this, tr( "Open folder" ), defaultFolder );
415  COMMENT( "Opening folder: \"" << folderString.toStdString( ) << "\"", 1 )
416  if( !folderString.isEmpty( ) ) {
417  controller->clear( );
418  if( !loadFolder( folderString ) ) {
419  BIAL_WARNING( "Could not read folder!" )
420  QMessageBox::warning( this, "Warning", tr( "Could not read folder!" ) );
421  }
422  }
423 }
424 
425 void MainWindow::on_actionOpen_DicomDir_triggered( ) {
426  QString fileName = QFileDialog::getOpenFileName( this, tr( "Open" ), defaultFolder, tr( "*" ) );
427  loadDicomdir( fileName );
428 }
429 
430 void MainWindow::on_actionAdd_image_triggered( ) {
431  controller->addImage( getFileDialog( ) );
432 }
433 
434 void MainWindow::on_actionRemove_current_image_triggered( ) {
435  controller->removeCurrentImage( );
436 }
437 
438 void MainWindow::on_actionSelect_default_folder_triggered( ) {
439  QString temp = QFileDialog::getExistingDirectory( this, tr( "Select default folder" ), QDir::homePath( ) );
440  if( !temp.isEmpty( ) ) {
441  defaultFolder = temp;
442  QSettings settings;
443  settings.beginGroup( "MainWindow" );
444  settings.setValue( "defaultFolder", defaultFolder );
445  settings.endGroup( );
446  }
447 }
448 
449 void MainWindow::on_actionRemove_current_label_triggered( ) {
450  controller->removeCurrentLabel( );
451 }
452 
453 void MainWindow::updateIntensity( QPointF scnPos, Qt::MouseButtons buttons, size_t axis ) {
454  Q_UNUSED( buttons )
455  GuiImage * img = controller->currentImage( );
456  if( img != nullptr ) {
457  Bial::Point3D pt = img->getPosition( scnPos, axis );
458  QString msg;
459  size_t dims = img->getDims( );
460  switch( img->getImageType( ) ) {
462  int max = img->max( );
463  const Bial::Image< int > &bial_img( img->getIntImage( ) );
464  if( dims == 3 ) {
465  if( bial_img.ValidCoordinate( pt.x, pt.y, pt.z ) ) {
466  int color = bial_img( pt.x, pt.y, pt.z );
467  msg = QString( "Axis %1 : (%2, %3, %4) = %5/%6" )
468  .arg( axis )
469  .arg( ( int ) pt.x )
470  .arg( ( int ) pt.y )
471  .arg( ( int ) pt.z )
472  .arg( color )
473  .arg( max );
474  }
475  }
476  else {
477  if( bial_img.ValidCoordinate( pt.x, pt.y ) ) {
478  int color = bial_img( pt.x, pt.y );
479  msg = QString( "(%1, %2) = %3/%4" ).arg( ( int ) pt.x ).arg( ( int ) pt.y ).arg( color ).arg( max );
480  }
481  }
482  break;
483  }
485  float max = img->fmax( );
486  const Bial::Image< float > &bial_img( img->getFltImage( ) );
487  if( dims == 3 ) {
488  if( bial_img.ValidCoordinate( pt.x, pt.y, pt.z ) ) {
489  int color = static_cast< int >( bial_img( pt.x, pt.y, pt.z ) );
490  msg = QString( "Axis %1 : (%2, %3, %4) = %5/%6" )
491  .arg( axis )
492  .arg( ( int ) pt.x )
493  .arg( ( int ) pt.y )
494  .arg( ( int ) pt.z )
495  .arg( color )
496  .arg( max );
497  }
498  }
499  else {
500  if( bial_img.ValidCoordinate( pt.x, pt.y ) ) {
501  int color = static_cast< int >( bial_img( pt.x, pt.y ) );
502  msg = QString( "(%1, %2) = %3/%4" ).arg( ( int ) pt.x ).arg( ( int ) pt.y ).arg( color ).arg( max );
503  }
504  }
505  break;
506  }
508  int max = img->max( );
509  const Bial::Image< Bial::Color > &bial_img( img->getClrImage( ) );
510  if( dims == 3 ) {
511  if( bial_img.ValidCoordinate( pt.x, pt.y, pt.z ) ) {
512  int r = static_cast< int >( bial_img( pt.x, pt.y, pt.z )[ 0 ] );
513  int g = static_cast< int >( bial_img( pt.x, pt.y, pt.z )[ 1 ] );
514  int b = static_cast< int >( bial_img( pt.x, pt.y, pt.z )[ 2 ] );
515  msg = QString( "Axis %1 : (%2, %3, %4) = %5/%6" )
516  .arg( axis )
517  .arg( ( int ) pt.x )
518  .arg( ( int ) pt.y )
519  .arg( ( int ) pt.z )
520  .arg( r )
521  .arg( g )
522  .arg( b )
523  .arg( max );
524  }
525  }
526  else {
527  if( bial_img.ValidCoordinate( pt.x, pt.y ) ) {
528  int r = static_cast< int >( bial_img( pt.x, pt.y )[ 0 ] );
529  int g = static_cast< int >( bial_img( pt.x, pt.y )[ 1 ] );
530  int b = static_cast< int >( bial_img( pt.x, pt.y )[ 2 ] );
531  msg = QString( "(%1, %2) = (%3, %4, %5)/%6" ).arg( ( int ) pt.x ).arg( ( int ) pt.y ).arg( r ).arg( g ).arg(
532  b ).arg( max );
533  }
534  }
535  break;
536  }
538  int max = img->fmax( );
539  const Bial::Image< Bial::RealColor > &bial_img( img->getRclImage( ) );
540  if( dims == 3 ) {
541  if( bial_img.ValidCoordinate( pt.x, pt.y, pt.z ) ) {
542  int r = static_cast< int >( bial_img( pt.x, pt.y, pt.z )[ 0 ] );
543  int g = static_cast< int >( bial_img( pt.x, pt.y, pt.z )[ 1 ] );
544  int b = static_cast< int >( bial_img( pt.x, pt.y, pt.z )[ 2 ] );
545  msg = QString( "Axis %1 : (%2, %3, %4) = %5/%6" )
546  .arg( axis )
547  .arg( ( int ) pt.x )
548  .arg( ( int ) pt.y )
549  .arg( ( int ) pt.z )
550  .arg( r )
551  .arg( g )
552  .arg( b )
553  .arg( max );
554  }
555  }
556  else {
557  if( bial_img.ValidCoordinate( pt.x, pt.y ) ) {
558  int r = static_cast< int >( bial_img( pt.x, pt.y )[ 0 ] );
559  int g = static_cast< int >( bial_img( pt.x, pt.y )[ 1 ] );
560  int b = static_cast< int >( bial_img( pt.x, pt.y )[ 2 ] );
561  msg = QString( "(%1, %2) = (%3, %4, %5)/%6" ).arg( ( int ) pt.x ).arg( ( int ) pt.y ).arg( r ).arg( g ).arg(
562  b ).arg( max );
563  }
564  }
565  }
566  default:
567  std::string msg( BIAL_ERROR( "Accessing non-initialized multi-image." ) );
568  throw( std::runtime_error( msg ) );
569  }
570  ui->statusBar->showMessage( msg, 10000 );
571  }
572 }
573 
574 void MainWindow::on_actionAxial_triggered( ) {
575  controller->currentFormat( )->setNumberOfViews( 1 );
576  controller->currentFormat( )->setCurrentViews( Views::SHOW0 );
577 }
578 
579 void MainWindow::on_actionCoronal_triggered( ) {
580  controller->currentFormat( )->setNumberOfViews( 1 );
581  controller->currentFormat( )->setCurrentViews( Views::SHOW1 );
582 }
583 
584 void MainWindow::on_actionSagittal_triggered( ) {
585  controller->currentFormat( )->setNumberOfViews( 1 );
586  controller->currentFormat( )->setCurrentViews( Views::SHOW2 );
587 }
588 
589 void MainWindow::on_action3_Views_triggered( ) {
590  controller->currentFormat( )->setNumberOfViews( 3 );
591 }
592 
593 void MainWindow::on_action4_Views_triggered( ) {
594  controller->currentFormat( )->setNumberOfViews( 4 );
595 }
596 
597 void MainWindow::on_actionVertical_triggered( ) {
599 }
600 
601 void MainWindow::on_actionHorizontal_triggered( ) {
603 }
604 
605 void MainWindow::on_actionGrid_triggered( ) {
606  controller->currentFormat( )->setCurrentLayout( Layout::GRID );
607 }
608 
609 void MainWindow::on_actionWhitePen_triggered( ) {
610  controller->currentFormat( )->setOverlayColor( Qt::white );
611 }
612 
613 void MainWindow::on_actionRedPen_triggered( ) {
614  controller->currentFormat( )->setOverlayColor( Qt::red );
615 }
616 
617 void MainWindow::on_actionBluePen_triggered( ) {
618  controller->currentFormat( )->setOverlayColor( Qt::blue );
619 }
620 
621 void MainWindow::on_actionGreenPen_triggered( ) {
622  controller->currentFormat( )->setOverlayColor( Qt::green );
623 }
624 
625 void MainWindow::on_actionBlackPen_triggered( ) {
626  controller->currentFormat( )->setOverlayColor( Qt::black );
627 }
628 
629 void MainWindow::on_actionToggle_overlay_triggered( ) {
630  if( controller->currentFormat( ) ) {
631  controller->currentFormat( )->toggleOverlay( );
632  }
633 }
634 
635 void MainWindow::on_actionDefaultTool_triggered( ) {
636  GuiImage *img = controller->currentImage( );
637  if( img ) {
638  bool found = false;
639  for( int tool = 0; tool < img->tools.size( ); ++tool ) {
640  if( img->tools[ tool ]->type( ) == DefaultTool::Type ) {
641  found = true;
642  img->setCurrentToolPos( tool );
643  break;
644  }
645  }
646  if( !found ) {
647  img->tools.push_back( new DefaultTool( img, ui->imageViewer ) );
648  img->setCurrentToolPos( img->tools.size( ) - 1 );
649  }
650  ui->segmentationWidget->setTool( img->currentTool( ) );
651  emit img->imageUpdated( );
652  }
653 }
654 
655 void MainWindow::on_actionSegmentationTool_triggered( ) {
656  GuiImage *img = controller->currentImage( );
657  if( img ) {
658  bool found = false;
659  for( int tool = 0; tool < img->tools.size( ); ++tool ) {
660  if( img->tools[ tool ]->type( ) == SegmentationTool::Type ) {
661  found = true;
662  img->setCurrentToolPos( tool );
663  }
664  }
665  if( !found ) {
666  img->tools.push_back( new SegmentationTool( img, ui->imageViewer ) );
667  img->setCurrentToolPos( img->tools.size( ) - 1 );
668  }
669  ui->segmentationWidget->setTool( img->currentTool( ) );
670  ui->dockWidgetSegmentation->show( );
671  emit img->imageUpdated( );
672  }
673 }
674 
675 void MainWindow::on_actionEnglish_triggered( ) {
676  QTranslator translator;
677  if( not translator.load( ":/translations/bial_en.qm" ) ) {
678  QMessageBox::critical( this, "Erro", "Erro carregando tradução!" );
679  return;
680  }
681  qApp->installTranslator( &translator );
682  ui->retranslateUi( this );
683 }
684 
685 void MainWindow::on_actionPortuguese_triggered( ) {
686  QTranslator translator;
687  if( not translator.load( ":/translations/bial_br.qm" ) ) {
688  QMessageBox::critical( this, "Erro", "Erro carregando tradução!" );
689  return;
690  }
691  qApp->installTranslator( &translator );
692  ui->retranslateUi( this );
693 }
694 
695 void MainWindow::on_actionFunctional_Tool_triggered( ) {
696  /* ui->dockWidgetFunctional->show(); */
697 /* ui->widgetDragDrop->show( ); */
698  ui->logoView->hide( );
699 }
700 
701 /*
702  * TODO: para a funcao drag and drop colocar uma arvore de navegacao de pasta a esquerda para facilitar, nao precisar
703  * abrir uma janela do sistema para isso
704  * TODO: arrumar itens na scene nao sendo carregadas no tamanho correto as vezes (precisa clicar novamente ou clicar em
705  * redimensionar)
706  */
707 
708 void MainWindow::on_actionChange_default_parameters_triggered( ) {
709  /* TODO: abrir janela para mostrar parametros */
710 }
void mouseClicked(QPointF pt, Qt::MouseButtons buttons, size_t axis)
QCPGraph * addGraph(QCPAxis *keyAxis=0, QCPAxis *valueAxis=0)
double z
Point position in z.
Definition: Geometrics.hpp:227
bool open(const QString &filename)
Definition: dicomdir.cpp:180
int max()
max is the maximum integer intensity of the input image. Used for int and Color images.
Definition: guiimage.cpp:439
void mouseReleased(QPointF pt, Qt::MouseButtons buttons, size_t axis)
virtual void setCurrentViews(const Views &currentViews)
Tool * currentTool()
currentTool returns the current Tool.
Definition: guiimage.cpp:150
void recentFilesUpdated()
recentFilesUpdated
each data point is represented by a line parallel to the value axis, which reaches from the data poin...
Definition: qcustomplot.h:2515
Modality modality() const
0x001 Axis ranges are draggable (see QCPAxisRect::setRangeDrag, QCPAxisRect::setRangeDragAxes) ...
Definition: qcustomplot.h:155
const Bial::Signal & getHistogram() const
getHistogram returns the image histogram.
Definition: guiimage.cpp:463
#define BIAL_ERROR(exp)
Use BIAL_ERROR to compose runtime error messages. Note that ERROR generates a string, instead of a stream, because it is better to throw an exception, rather than exiting the program. This way, the exception may be threated by a higher level program, like an user IDE.
Definition: Common.hpp:161
void commandLineOpen(int argc, char *argv[])
Definition: mainwindow.cpp:299
void setRangeZoom(Qt::Orientations orientations)
Signal handeling declaration.
Definition: Signal.hpp:20
DisplayFormat * currentFormat()
currentFormat returns the modality of current image.
Definition: controller.cpp:230
void setRangeZoomAxes(QCPAxis *horizontal, QCPAxis *vertical)
Bial::MultiImageType getImageType() const
getImageType returns image type among int, float, Color and RealColor.
Definition: guiimage.cpp:354
The GuiImage class is a bridge to the Bial::Image data structure to the QImage data structure...
Definition: guiimage.h:20
QCPAxis * xAxis
Definition: qcustomplot.h:1819
void setOverlayColor(const QColor &overlayColor)
void setInteraction(const QCP::Interaction &interaction, bool enabled=true)
virtual void setNumberOfViews(int numberOfViews)=0
The Point3D class is a Geometric representation of a point in 3D space. A point is a zero­dimension...
Definition: Geometrics.hpp:218
Bial::Point3D getPosition(QPointF pos, size_t view)
getPosition transforms the scene position to the input image coordinates.
Definition: guiimage.cpp:344
void dropImage(const QString &filePath)
void setRangeDrag(Qt::Orientations orientations)
static size_t size
Definition: enough.c:173
Q_SLOT void replot(QCustomPlot::RefreshPriority refreshPriority=QCustomPlot::rpHint)
virtual void clearData()
bool hasOverlay() const
size_t size() const
Returns the number of bins.
The central class of the library. This is the QWidget which displays the plot and interacts with the ...
Definition: qcustomplot.h:1680
void mouseDragged(QPointF pt, Qt::MouseButtons buttons, size_t axis)
bool removeCurrentLabel()
removeCurrentLabel removes the current label from current image.
Definition: controller.cpp:84
void setCurrentToolPos(const size_t &currentToolPos)
Definition: guiimage.cpp:529
void setLineStyle(LineStyle ls)
Q_SLOT void rescaleAxes(bool onlyVisiblePlottables=false)
bool showOrientation() const
void removeCurrentImage()
removeCurrentImage removes the current image from vector.
Definition: controller.cpp:89
double y
Point position in y.
Definition: Geometrics.hpp:225
The Controller class is one of the most important classes of the User Interface, and is responsible t...
Definition: controller.h:17
float fmax()
fmax is the maximum float intensity of the input image. Used for float and RealColor images...
Definition: guiimage.cpp:443
Definition: gzjoin.c:78
unsigned char suffix[65536]
Definition: gun.c:164
int size()
size
Definition: controller.cpp:114
virtual int type()=0
QCPAxisRect * axisRect(int index=0) const
MainWindow(QWidget *parent=0)
Definition: mainwindow.cpp:17
static int max
Definition: enough.c:170
void imageUpdated()
imageUpdated is called each time a internal property is updated, after that the image views are updat...
Bial::Image< int > & getIntImage() const
get*Image
Definition: guiimage.cpp:358
void clear()
clear Clears the image vector, and resets thumbnails.
Definition: controller.cpp:105
0x002 Axis ranges are zoomable with the mouse wheel (see QCPAxisRect::setRangeZoom, QCPAxisRect::setRangeZoomAxes)
Definition: qcustomplot.h:156
GuiImage * currentImage()
currentImage
Definition: controller.cpp:24
void currentImageChanged()
This signal is emmited every time the current image changes.
QCPGraph * graph(int index) const
bool has3Views() const
static const int supportedFormats
Definition: defaulttool.h:11
bool addLabel(QString label)
addLabel Adds a label to the current image.
Definition: controller.cpp:78
void setThumbsWidget(ThumbsWidget *thumbsWidget)
setThumbsWidget setThumbsWidget sets the pointer to the thumbnails dock.
Definition: controller.cpp:225
void setData(QCPDataMap *data, bool copy=false)
QStringList getImages()
Definition: dicomdir.cpp:329
QVector< Tool * > tools
tools is a vector containing the image tools.
Definition: guiimage.h:98
Bial::Image< Bial::Color > & getClrImage() const
Definition: guiimage.cpp:366
Definition: gzappend.c:170
static const int supportedFormats
QCPAxis * yAxis
Definition: qcustomplot.h:1819
const double * Data() const
Returns signal data.
#define BIAL_WARNING(exp)
Use BIAL_WARNING to print a message to the output stream warn the user that something bad may have ha...
Definition: Common.hpp:158
void setLabel(const QString &str)
void containerUpdated()
This signal is emmited avery time the m_images vector is updated.
Bial::Image< float > & getFltImage() const
Definition: guiimage.cpp:362
Bial::Image< Bial::RealColor > & getRclImage() const
Definition: guiimage.cpp:370
void imageUpdated()
This signal is emmited every time the current image is updated.
bool has4Views() const
size_t getDims() const
getDims
Definition: guiimage.cpp:374
virtual void setCurrentLayout(const Layout &currentLayout)
void dropFolder(const QString &folderPath)
bool addImage(QString fname)
addImage Adds an image to vector m_images.
Definition: controller.cpp:39