diff --git a/Plugins/org.mitk.gui.qt.diffusionimaging/src/internal/Connectomics/QmitkNetworkHistogramCanvas.h b/Plugins/org.mitk.gui.qt.diffusionimaging/src/internal/Connectomics/QmitkNetworkHistogramCanvas.h index 0f13d49571..ebd96bd040 100644 --- a/Plugins/org.mitk.gui.qt.diffusionimaging/src/internal/Connectomics/QmitkNetworkHistogramCanvas.h +++ b/Plugins/org.mitk.gui.qt.diffusionimaging/src/internal/Connectomics/QmitkNetworkHistogramCanvas.h @@ -1,74 +1,73 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #ifndef QmitkNetworkHistogramCanvas_H_INCLUDED #define QmitkNetworkHistogramCanvas_H_INCLUDED #include #include #include "QmitkPlotWidget.h" -#include #include #include #include #include //##Documentation //## @brief A widget for displaying the data in a ConnectomicsHistogramBase class QmitkNetworkHistogramCanvas : public QmitkPlotWidget { Q_OBJECT public: QmitkNetworkHistogramCanvas( QWidget * parent=0, Qt::WindowFlags f = 0 ); ~QmitkNetworkHistogramCanvas(); /** @brief Returns the histogram the canvas is using */ mitk::ConnectomicsHistogramBase* GetHistogram() { return m_Histogram; } /** @brief Set the histogram the canvas is to use */ void SetHistogram(mitk::ConnectomicsHistogramBase *histogram) { m_Histogram = histogram; } /** @brief Draw the histogram */ void DrawProfiles(); /** @brief Return the plot */ QwtPlot* GetPlot() { return m_Plot; } protected: /** @brief The histogram to be plotted */ mitk::ConnectomicsHistogramBase *m_Histogram; }; #endif diff --git a/Plugins/org.mitk.gui.qt.diffusionimaging/src/internal/QmitkFiberExtractionView.cpp b/Plugins/org.mitk.gui.qt.diffusionimaging/src/internal/QmitkFiberExtractionView.cpp index 6f65fa6d06..5be77a4ac4 100644 --- a/Plugins/org.mitk.gui.qt.diffusionimaging/src/internal/QmitkFiberExtractionView.cpp +++ b/Plugins/org.mitk.gui.qt.diffusionimaging/src/internal/QmitkFiberExtractionView.cpp @@ -1,1445 +1,1445 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ // Blueberry #include #include // Qmitk #include "QmitkFiberExtractionView.h" #include // Qt #include // MITK #include #include #include #include #include #include #include #include #include #include #include #include #include "usModuleRegistry.h" // ITK #include #include #include #include #include #include #include #include const std::string QmitkFiberExtractionView::VIEW_ID = "org.mitk.views.fiberextraction"; const std::string id_DataManager = "org.mitk.views.datamanager"; using namespace mitk; QmitkFiberExtractionView::QmitkFiberExtractionView() : QmitkFunctionality() , m_Controls( 0 ) , m_MultiWidget( NULL ) , m_CircleCounter(0) , m_PolygonCounter(0) , m_UpsamplingFactor(1) { } // Destructor QmitkFiberExtractionView::~QmitkFiberExtractionView() { } void QmitkFiberExtractionView::CreateQtPartControl( QWidget *parent ) { // build up qt view, unless already done if ( !m_Controls ) { // create GUI widgets from the Qt Designer's .ui file m_Controls = new Ui::QmitkFiberExtractionViewControls; m_Controls->setupUi( parent ); m_Controls->doExtractFibersButton->setDisabled(true); m_Controls->PFCompoANDButton->setDisabled(true); m_Controls->PFCompoORButton->setDisabled(true); m_Controls->PFCompoNOTButton->setDisabled(true); m_Controls->m_PlanarFigureButtonsFrame->setEnabled(false); m_Controls->m_RectangleButton->setVisible(false); connect( m_Controls->m_CircleButton, SIGNAL( clicked() ), this, SLOT( OnDrawCircle() ) ); connect( m_Controls->m_PolygonButton, SIGNAL( clicked() ), this, SLOT( OnDrawPolygon() ) ); connect(m_Controls->PFCompoANDButton, SIGNAL(clicked()), this, SLOT(GenerateAndComposite()) ); connect(m_Controls->PFCompoORButton, SIGNAL(clicked()), this, SLOT(GenerateOrComposite()) ); connect(m_Controls->PFCompoNOTButton, SIGNAL(clicked()), this, SLOT(GenerateNotComposite()) ); connect(m_Controls->m_JoinBundles, SIGNAL(clicked()), this, SLOT(JoinBundles()) ); connect(m_Controls->m_SubstractBundles, SIGNAL(clicked()), this, SLOT(SubstractBundles()) ); connect(m_Controls->m_GenerateRoiImage, SIGNAL(clicked()), this, SLOT(GenerateRoiImage()) ); connect(m_Controls->m_Extract3dButton, SIGNAL(clicked()), this, SLOT(ExtractPassingMask())); connect( m_Controls->m_ExtractMask, SIGNAL(clicked()), this, SLOT(ExtractEndingInMask()) ); connect( m_Controls->doExtractFibersButton, SIGNAL(clicked()), this, SLOT(DoFiberExtraction()) ); connect( m_Controls->m_RemoveOutsideMaskButton, SIGNAL(clicked()), this, SLOT(DoRemoveOutsideMask())); connect( m_Controls->m_RemoveInsideMaskButton, SIGNAL(clicked()), this, SLOT(DoRemoveInsideMask())); } } void QmitkFiberExtractionView::DoRemoveInsideMask() { if (m_MaskImageNode.IsNull()) return; mitk::Image::Pointer mitkMask = dynamic_cast(m_MaskImageNode->GetData()); for (int i=0; i(m_SelectedFB.at(i)->GetData()); QString name(m_SelectedFB.at(i)->GetName().c_str()); itkUCharImageType::Pointer mask = itkUCharImageType::New(); mitk::CastToItkImage(mitkMask, mask); mitk::FiberBundleX::Pointer newFib = fib->RemoveFibersOutside(mask, true); if (newFib->GetNumFibers()<=0) { QMessageBox::information(NULL, "No output generated:", "The resulting fiber bundle contains no fibers."); continue; } DataNode::Pointer newNode = DataNode::New(); newNode->SetData(newFib); name += "_Cut"; newNode->SetName(name.toStdString()); GetDefaultDataStorage()->Add(newNode); m_SelectedFB.at(i)->SetVisibility(false); } } void QmitkFiberExtractionView::DoRemoveOutsideMask() { if (m_MaskImageNode.IsNull()) return; mitk::Image::Pointer mitkMask = dynamic_cast(m_MaskImageNode->GetData()); for (int i=0; i(m_SelectedFB.at(i)->GetData()); QString name(m_SelectedFB.at(i)->GetName().c_str()); itkUCharImageType::Pointer mask = itkUCharImageType::New(); mitk::CastToItkImage(mitkMask, mask); mitk::FiberBundleX::Pointer newFib = fib->RemoveFibersOutside(mask); if (newFib->GetNumFibers()<=0) { QMessageBox::information(NULL, "No output generated:", "The resulting fiber bundle contains no fibers."); continue; } DataNode::Pointer newNode = DataNode::New(); newNode->SetData(newFib); name += "_Cut"; newNode->SetName(name.toStdString()); GetDefaultDataStorage()->Add(newNode); m_SelectedFB.at(i)->SetVisibility(false); } } void QmitkFiberExtractionView::ExtractEndingInMask() { if (m_MaskImageNode.IsNull()) return; mitk::Image::Pointer mitkMask = dynamic_cast(m_MaskImageNode->GetData()); for (int i=0; i(m_SelectedFB.at(i)->GetData()); QString name(m_SelectedFB.at(i)->GetName().c_str()); itkUCharImageType::Pointer mask = itkUCharImageType::New(); mitk::CastToItkImage(mitkMask, mask); mitk::FiberBundleX::Pointer newFib = fib->ExtractFiberSubset(mask, false); if (newFib->GetNumFibers()<=0) { QMessageBox::information(NULL, "No output generated:", "The resulting fiber bundle contains no fibers."); continue; } DataNode::Pointer newNode = DataNode::New(); newNode->SetData(newFib); name += "_ending-in-mask"; newNode->SetName(name.toStdString()); GetDefaultDataStorage()->Add(newNode); m_SelectedFB.at(i)->SetVisibility(false); } } void QmitkFiberExtractionView::ExtractPassingMask() { if (m_MaskImageNode.IsNull()) return; mitk::Image::Pointer mitkMask = dynamic_cast(m_MaskImageNode->GetData()); for (int i=0; i(m_SelectedFB.at(i)->GetData()); QString name(m_SelectedFB.at(i)->GetName().c_str()); itkUCharImageType::Pointer mask = itkUCharImageType::New(); mitk::CastToItkImage(mitkMask, mask); mitk::FiberBundleX::Pointer newFib = fib->ExtractFiberSubset(mask, true); if (newFib->GetNumFibers()<=0) { QMessageBox::information(NULL, "No output generated:", "The resulting fiber bundle contains no fibers."); continue; } DataNode::Pointer newNode = DataNode::New(); newNode->SetData(newFib); name += "_passing-mask"; newNode->SetName(name.toStdString()); GetDefaultDataStorage()->Add(newNode); m_SelectedFB.at(i)->SetVisibility(false); } } void QmitkFiberExtractionView::GenerateRoiImage(){ if (m_SelectedPF.empty()) return; mitk::Geometry3D::Pointer geometry; if (!m_SelectedFB.empty()) { mitk::FiberBundleX::Pointer fib = dynamic_cast(m_SelectedFB.front()->GetData()); geometry = fib->GetGeometry(); } else if (m_SelectedImage) geometry = m_SelectedImage->GetGeometry(); else return; itk::Vector spacing = geometry->GetSpacing(); spacing /= m_UpsamplingFactor; mitk::Point3D newOrigin = geometry->GetOrigin(); mitk::Geometry3D::BoundsArrayType bounds = geometry->GetBounds(); newOrigin[0] += bounds.GetElement(0); newOrigin[1] += bounds.GetElement(2); newOrigin[2] += bounds.GetElement(4); itk::Matrix direction; itk::ImageRegion<3> imageRegion; for (int i=0; i<3; i++) for (int j=0; j<3; j++) direction[j][i] = geometry->GetMatrixColumn(i)[j]/spacing[j]; imageRegion.SetSize(0, geometry->GetExtent(0)*m_UpsamplingFactor); imageRegion.SetSize(1, geometry->GetExtent(1)*m_UpsamplingFactor); imageRegion.SetSize(2, geometry->GetExtent(2)*m_UpsamplingFactor); m_PlanarFigureImage = itkUCharImageType::New(); m_PlanarFigureImage->SetSpacing( spacing ); // Set the image spacing m_PlanarFigureImage->SetOrigin( newOrigin ); // Set the image origin m_PlanarFigureImage->SetDirection( direction ); // Set the image direction m_PlanarFigureImage->SetRegions( imageRegion ); m_PlanarFigureImage->Allocate(); m_PlanarFigureImage->FillBuffer( 0 ); Image::Pointer tmpImage = Image::New(); tmpImage->InitializeByItk(m_PlanarFigureImage.GetPointer()); tmpImage->SetVolume(m_PlanarFigureImage->GetBufferPointer()); for (int i=0; iInitializeByItk(m_PlanarFigureImage.GetPointer()); tmpImage->SetVolume(m_PlanarFigureImage->GetBufferPointer()); node->SetData(tmpImage); node->SetName("ROI Image"); this->GetDefaultDataStorage()->Add(node); } void QmitkFiberExtractionView::CompositeExtraction(mitk::DataNode::Pointer node, mitk::Image* image) { if (dynamic_cast(node.GetPointer()->GetData()) && !dynamic_cast(node.GetPointer()->GetData())) { m_PlanarFigure = dynamic_cast(node.GetPointer()->GetData()); AccessFixedDimensionByItk_2( image, InternalReorientImagePlane, 3, m_PlanarFigure->GetGeometry(), -1); AccessFixedDimensionByItk_2( m_InternalImage, InternalCalculateMaskFromPlanarFigure, 3, 2, node->GetName() ); } } template < typename TPixel, unsigned int VImageDimension > void QmitkFiberExtractionView::InternalReorientImagePlane( const itk::Image< TPixel, VImageDimension > *image, mitk::Geometry3D* planegeo3D, int additionalIndex ) { MITK_DEBUG << "InternalReorientImagePlane() start"; typedef itk::Image< TPixel, VImageDimension > ImageType; typedef itk::Image< float, VImageDimension > FloatImageType; typedef itk::ResampleImageFilter ResamplerType; typename ResamplerType::Pointer resampler = ResamplerType::New(); mitk::PlaneGeometry* planegeo = dynamic_cast(planegeo3D); float upsamp = m_UpsamplingFactor; float gausssigma = 0.5; // Spacing typename ResamplerType::SpacingType spacing = planegeo->GetSpacing(); spacing[0] = image->GetSpacing()[0] / upsamp; spacing[1] = image->GetSpacing()[1] / upsamp; spacing[2] = image->GetSpacing()[2]; resampler->SetOutputSpacing( spacing ); // Size typename ResamplerType::SizeType size; size[0] = planegeo->GetParametricExtentInMM(0) / spacing[0]; size[1] = planegeo->GetParametricExtentInMM(1) / spacing[1]; size[2] = 1; resampler->SetSize( size ); // Origin typename mitk::Point3D orig = planegeo->GetOrigin(); typename mitk::Point3D corrorig; planegeo3D->WorldToIndex(orig,corrorig); corrorig[0] += 0.5/upsamp; corrorig[1] += 0.5/upsamp; corrorig[2] += 0; planegeo3D->IndexToWorld(corrorig,corrorig); resampler->SetOutputOrigin(corrorig ); // Direction typename ResamplerType::DirectionType direction; typename mitk::AffineTransform3D::MatrixType matrix = planegeo->GetIndexToWorldTransform()->GetMatrix(); for(int c=0; cSetOutputDirection( direction ); // Gaussian interpolation if(gausssigma != 0) { double sigma[3]; for( unsigned int d = 0; d < 3; d++ ) { sigma[d] = gausssigma * image->GetSpacing()[d]; } double alpha = 2.0; typedef itk::GaussianInterpolateImageFunction GaussianInterpolatorType; typename GaussianInterpolatorType::Pointer interpolator = GaussianInterpolatorType::New(); interpolator->SetInputImage( image ); interpolator->SetParameters( sigma, alpha ); resampler->SetInterpolator( interpolator ); } else { // typedef typename itk::BSplineInterpolateImageFunction // InterpolatorType; typedef typename itk::LinearInterpolateImageFunction InterpolatorType; typename InterpolatorType::Pointer interpolator = InterpolatorType::New(); interpolator->SetInputImage( image ); resampler->SetInterpolator( interpolator ); } // Other resampling options resampler->SetInput( image ); resampler->SetDefaultPixelValue(0); MITK_DEBUG << "Resampling requested image plane ... "; resampler->Update(); MITK_DEBUG << " ... done"; if(additionalIndex < 0) { this->m_InternalImage = mitk::Image::New(); this->m_InternalImage->InitializeByItk( resampler->GetOutput() ); this->m_InternalImage->SetVolume( resampler->GetOutput()->GetBufferPointer() ); } } template < typename TPixel, unsigned int VImageDimension > void QmitkFiberExtractionView::InternalCalculateMaskFromPlanarFigure( itk::Image< TPixel, VImageDimension > *image, unsigned int axis, std::string nodeName ) { MITK_DEBUG << "InternalCalculateMaskFromPlanarFigure() start"; typedef itk::Image< TPixel, VImageDimension > ImageType; typedef itk::CastImageFilter< ImageType, itkUCharImageType > CastFilterType; // Generate mask image as new image with same header as input image and // initialize with "1". itkUCharImageType::Pointer newMaskImage = itkUCharImageType::New(); newMaskImage->SetSpacing( image->GetSpacing() ); // Set the image spacing newMaskImage->SetOrigin( image->GetOrigin() ); // Set the image origin newMaskImage->SetDirection( image->GetDirection() ); // Set the image direction newMaskImage->SetRegions( image->GetLargestPossibleRegion() ); newMaskImage->Allocate(); newMaskImage->FillBuffer( 1 ); // Generate VTK polygon from (closed) PlanarFigure polyline // (The polyline points are shifted by -0.5 in z-direction to make sure // that the extrusion filter, which afterwards elevates all points by +0.5 // in z-direction, creates a 3D object which is cut by the the plane z=0) const Geometry2D *planarFigureGeometry2D = m_PlanarFigure->GetGeometry2D(); const PlanarFigure::PolyLineType planarFigurePolyline = m_PlanarFigure->GetPolyLine( 0 ); const Geometry3D *imageGeometry3D = m_InternalImage->GetGeometry( 0 ); vtkPolyData *polyline = vtkPolyData::New(); polyline->Allocate( 1, 1 ); // Determine x- and y-dimensions depending on principal axis int i0, i1; switch ( axis ) { case 0: i0 = 1; i1 = 2; break; case 1: i0 = 0; i1 = 2; break; case 2: default: i0 = 0; i1 = 1; break; } // Create VTK polydata object of polyline contour vtkPoints *points = vtkPoints::New(); PlanarFigure::PolyLineType::const_iterator it; std::vector indices; unsigned int numberOfPoints = 0; for ( it = planarFigurePolyline.begin(); it != planarFigurePolyline.end(); ++it ) { Point3D point3D; // Convert 2D point back to the local index coordinates of the selected // image Point2D point2D = it->Point; planarFigureGeometry2D->WorldToIndex(point2D, point2D); point2D[0] -= 0.5/m_UpsamplingFactor; point2D[1] -= 0.5/m_UpsamplingFactor; planarFigureGeometry2D->IndexToWorld(point2D, point2D); planarFigureGeometry2D->Map( point2D, point3D ); // Polygons (partially) outside of the image bounds can not be processed // further due to a bug in vtkPolyDataToImageStencil if ( !imageGeometry3D->IsInside( point3D ) ) { float bounds[2] = {0,0}; bounds[0] = this->m_InternalImage->GetLargestPossibleRegion().GetSize().GetElement(i0); bounds[1] = this->m_InternalImage->GetLargestPossibleRegion().GetSize().GetElement(i1); imageGeometry3D->WorldToIndex( point3D, point3D ); // if (point3D[i0]<0) // point3D[i0] = 0.5; // else if (point3D[i0]>bounds[0]) // point3D[i0] = bounds[0]-0.5; // if (point3D[i1]<0) // point3D[i1] = 0.5; // else if (point3D[i1]>bounds[1]) // point3D[i1] = bounds[1]-0.5; if (point3D[i0]<0) point3D[i0] = 0.0; else if (point3D[i0]>bounds[0]) point3D[i0] = bounds[0]-0.001; if (point3D[i1]<0) point3D[i1] = 0.0; else if (point3D[i1]>bounds[1]) point3D[i1] = bounds[1]-0.001; points->InsertNextPoint( point3D[i0], point3D[i1], -0.5 ); numberOfPoints++; } else { imageGeometry3D->WorldToIndex( point3D, point3D ); // Add point to polyline array points->InsertNextPoint( point3D[i0], point3D[i1], -0.5 ); numberOfPoints++; } } polyline->SetPoints( points ); points->Delete(); vtkIdType *ptIds = new vtkIdType[numberOfPoints]; for ( vtkIdType i = 0; i < numberOfPoints; ++i ) { ptIds[i] = i; } polyline->InsertNextCell( VTK_POLY_LINE, numberOfPoints, ptIds ); // Extrude the generated contour polygon vtkLinearExtrusionFilter *extrudeFilter = vtkLinearExtrusionFilter::New(); - extrudeFilter->SetInput( polyline ); + extrudeFilter->SetInputData( polyline ); extrudeFilter->SetScaleFactor( 1 ); extrudeFilter->SetExtrusionTypeToNormalExtrusion(); extrudeFilter->SetVector( 0.0, 0.0, 1.0 ); // Make a stencil from the extruded polygon vtkPolyDataToImageStencil *polyDataToImageStencil = vtkPolyDataToImageStencil::New(); - polyDataToImageStencil->SetInput( extrudeFilter->GetOutput() ); + polyDataToImageStencil->SetInputConnection( extrudeFilter->GetOutputPort() ); // Export from ITK to VTK (to use a VTK filter) typedef itk::VTKImageImport< itkUCharImageType > ImageImportType; typedef itk::VTKImageExport< itkUCharImageType > ImageExportType; typename ImageExportType::Pointer itkExporter = ImageExportType::New(); itkExporter->SetInput( newMaskImage ); vtkImageImport *vtkImporter = vtkImageImport::New(); this->ConnectPipelines( itkExporter, vtkImporter ); vtkImporter->Update(); // Apply the generated image stencil to the input image vtkImageStencil *imageStencilFilter = vtkImageStencil::New(); imageStencilFilter->SetInputConnection( vtkImporter->GetOutputPort() ); - imageStencilFilter->SetStencil( polyDataToImageStencil->GetOutput() ); + imageStencilFilter->SetStencilConnection(polyDataToImageStencil->GetOutputPort() ); imageStencilFilter->ReverseStencilOff(); imageStencilFilter->SetBackgroundValue( 0 ); imageStencilFilter->Update(); // Export from VTK back to ITK vtkImageExport *vtkExporter = vtkImageExport::New(); vtkExporter->SetInputConnection( imageStencilFilter->GetOutputPort() ); vtkExporter->Update(); typename ImageImportType::Pointer itkImporter = ImageImportType::New(); this->ConnectPipelines( vtkExporter, itkImporter ); itkImporter->Update(); // calculate cropping bounding box m_InternalImageMask3D = itkImporter->GetOutput(); m_InternalImageMask3D->SetDirection(image->GetDirection()); itk::ImageRegionConstIterator itmask(m_InternalImageMask3D, m_InternalImageMask3D->GetLargestPossibleRegion()); itk::ImageRegionIterator itimage(image, image->GetLargestPossibleRegion()); itmask = itmask.Begin(); itimage = itimage.Begin(); typename ImageType::SizeType lowersize = {{9999999999,9999999999,9999999999}}; typename ImageType::SizeType uppersize = {{0,0,0}}; while( !itmask.IsAtEnd() ) { if(itmask.Get() == 0) { itimage.Set(0); } else { typename ImageType::IndexType index = itimage.GetIndex(); typename ImageType::SizeType signedindex; signedindex[0] = index[0]; signedindex[1] = index[1]; signedindex[2] = index[2]; lowersize[0] = signedindex[0] < lowersize[0] ? signedindex[0] : lowersize[0]; lowersize[1] = signedindex[1] < lowersize[1] ? signedindex[1] : lowersize[1]; lowersize[2] = signedindex[2] < lowersize[2] ? signedindex[2] : lowersize[2]; uppersize[0] = signedindex[0] > uppersize[0] ? signedindex[0] : uppersize[0]; uppersize[1] = signedindex[1] > uppersize[1] ? signedindex[1] : uppersize[1]; uppersize[2] = signedindex[2] > uppersize[2] ? signedindex[2] : uppersize[2]; } ++itmask; ++itimage; } typename ImageType::IndexType index; index[0] = lowersize[0]; index[1] = lowersize[1]; index[2] = lowersize[2]; typename ImageType::SizeType size; size[0] = uppersize[0] - lowersize[0] + 1; size[1] = uppersize[1] - lowersize[1] + 1; size[2] = uppersize[2] - lowersize[2] + 1; itk::ImageRegion<3> cropRegion = itk::ImageRegion<3>(index, size); // crop internal mask typedef itk::RegionOfInterestImageFilter< itkUCharImageType, itkUCharImageType > ROIMaskFilterType; typename ROIMaskFilterType::Pointer roi2 = ROIMaskFilterType::New(); roi2->SetRegionOfInterest(cropRegion); roi2->SetInput(m_InternalImageMask3D); roi2->Update(); m_InternalImageMask3D = roi2->GetOutput(); Image::Pointer tmpImage = Image::New(); tmpImage->InitializeByItk(m_InternalImageMask3D.GetPointer()); tmpImage->SetVolume(m_InternalImageMask3D->GetBufferPointer()); Image::Pointer tmpImage2 = Image::New(); tmpImage2->InitializeByItk(m_PlanarFigureImage.GetPointer()); const Geometry3D *pfImageGeometry3D = tmpImage2->GetGeometry( 0 ); const Geometry3D *intImageGeometry3D = tmpImage->GetGeometry( 0 ); typedef itk::ImageRegionIteratorWithIndex IteratorType; IteratorType imageIterator (m_InternalImageMask3D, m_InternalImageMask3D->GetRequestedRegion()); imageIterator.GoToBegin(); while ( !imageIterator.IsAtEnd() ) { unsigned char val = imageIterator.Value(); if (val>0) { itk::Index<3> index = imageIterator.GetIndex(); Point3D point; point[0] = index[0]; point[1] = index[1]; point[2] = index[2]; intImageGeometry3D->IndexToWorld(point, point); pfImageGeometry3D->WorldToIndex(point, point); point[i0] += 0.5; point[i1] += 0.5; index[0] = point[0]; index[1] = point[1]; index[2] = point[2]; if (pfImageGeometry3D->IsIndexInside(index)) m_PlanarFigureImage->SetPixel(index, 1); } ++imageIterator; } // Clean up VTK objects polyline->Delete(); extrudeFilter->Delete(); polyDataToImageStencil->Delete(); vtkImporter->Delete(); imageStencilFilter->Delete(); //vtkExporter->Delete(); // TODO: crashes when outcommented; memory leak?? delete[] ptIds; } void QmitkFiberExtractionView::StdMultiWidgetAvailable (QmitkStdMultiWidget &stdMultiWidget) { m_MultiWidget = &stdMultiWidget; } void QmitkFiberExtractionView::StdMultiWidgetNotAvailable() { m_MultiWidget = NULL; } /* OnSelectionChanged is registered to SelectionService, therefore no need to implement SelectionService Listener explicitly */ void QmitkFiberExtractionView::UpdateGui() { m_Controls->m_Extract3dButton->setEnabled(false); m_Controls->m_ExtractMask->setEnabled(false); m_Controls->m_RemoveOutsideMaskButton->setEnabled(false); m_Controls->m_RemoveInsideMaskButton->setEnabled(false); // are fiber bundles selected? if ( m_SelectedFB.empty() ) { m_Controls->m_InputData->setTitle("Please Select Input Data"); m_Controls->m_JoinBundles->setEnabled(false); m_Controls->m_SubstractBundles->setEnabled(false); m_Controls->doExtractFibersButton->setEnabled(false); m_Controls->m_PlanarFigureButtonsFrame->setEnabled(false); } else { m_Controls->m_InputData->setTitle("Input Data"); m_Controls->m_PlanarFigureButtonsFrame->setEnabled(true); // one bundle and one planar figure needed to extract fibers if (!m_SelectedPF.empty()) m_Controls->doExtractFibersButton->setEnabled(true); // more than two bundles needed to join/subtract if (m_SelectedFB.size() > 1) { m_Controls->m_JoinBundles->setEnabled(true); m_Controls->m_SubstractBundles->setEnabled(true); } else { m_Controls->m_JoinBundles->setEnabled(false); m_Controls->m_SubstractBundles->setEnabled(false); } if (m_MaskImageNode.IsNotNull()) { m_Controls->m_Extract3dButton->setEnabled(true); m_Controls->m_ExtractMask->setEnabled(true); m_Controls->m_RemoveOutsideMaskButton->setEnabled(true); m_Controls->m_RemoveInsideMaskButton->setEnabled(true); } } // are planar figures selected? if ( m_SelectedPF.empty() ) { m_Controls->doExtractFibersButton->setEnabled(false); m_Controls->PFCompoANDButton->setEnabled(false); m_Controls->PFCompoORButton->setEnabled(false); m_Controls->PFCompoNOTButton->setEnabled(false); m_Controls->m_GenerateRoiImage->setEnabled(false); } else { if ( !m_SelectedFB.empty() || m_SelectedImage.IsNotNull()) m_Controls->m_GenerateRoiImage->setEnabled(true); else m_Controls->m_GenerateRoiImage->setEnabled(false); if (m_SelectedPF.size() > 1) { m_Controls->PFCompoANDButton->setEnabled(true); m_Controls->PFCompoORButton->setEnabled(true); m_Controls->PFCompoNOTButton->setEnabled(false); } else { m_Controls->PFCompoANDButton->setEnabled(false); m_Controls->PFCompoORButton->setEnabled(false); m_Controls->PFCompoNOTButton->setEnabled(true); } } } void QmitkFiberExtractionView::OnSelectionChanged( std::vector nodes ) { //reset existing Vectors containing FiberBundles and PlanarFigures from a previous selection m_SelectedFB.clear(); m_SelectedPF.clear(); m_SelectedSurfaces.clear(); m_SelectedImage = NULL; m_MaskImageNode = NULL; m_Controls->m_FibLabel->setText("mandatory"); m_Controls->m_PfLabel->setText("needed for extraction"); for( std::vector::iterator it = nodes.begin(); it != nodes.end(); ++it ) { mitk::DataNode::Pointer node = *it; if ( dynamic_cast(node->GetData()) ) { m_Controls->m_FibLabel->setText(node->GetName().c_str()); m_SelectedFB.push_back(node); } else if (dynamic_cast(node->GetData())) { m_Controls->m_PfLabel->setText(node->GetName().c_str()); m_SelectedPF.push_back(node); } else if (dynamic_cast(node->GetData())) { m_SelectedImage = dynamic_cast(node->GetData()); bool isBinary = false; node->GetPropertyValue("binary", isBinary); if (isBinary) { m_MaskImageNode = node; m_Controls->m_PfLabel->setText(node->GetName().c_str()); } } else if (dynamic_cast(node->GetData())) { m_Controls->m_PfLabel->setText(node->GetName().c_str()); m_SelectedSurfaces.push_back(dynamic_cast(node->GetData())); } } UpdateGui(); GenerateStats(); } void QmitkFiberExtractionView::OnDrawPolygon() { // bool checked = m_Controls->m_PolygonButton->isChecked(); // if(!this->AssertDrawingIsPossible(checked)) // return; mitk::PlanarPolygon::Pointer figure = mitk::PlanarPolygon::New(); figure->ClosedOn(); this->AddFigureToDataStorage(figure, QString("Polygon%1").arg(++m_PolygonCounter)); MITK_DEBUG << "PlanarPolygon created ..."; mitk::DataStorage::SetOfObjects::ConstPointer _NodeSet = this->GetDefaultDataStorage()->GetAll(); mitk::DataNode* node = 0; mitk::PlanarFigureInteractor::Pointer figureInteractor = 0; mitk::PlanarFigure* figureP = 0; for(mitk::DataStorage::SetOfObjects::ConstIterator it=_NodeSet->Begin(); it!=_NodeSet->End() ; it++) { node = const_cast(it->Value().GetPointer()); figureP = dynamic_cast(node->GetData()); if(figureP) { figureInteractor = dynamic_cast(node->GetDataInteractor().GetPointer()); if(figureInteractor.IsNull()) { figureInteractor = mitk::PlanarFigureInteractor::New(); us::Module* planarFigureModule = us::ModuleRegistry::GetModule( "PlanarFigure" ); figureInteractor->LoadStateMachine("PlanarFigureInteraction.xml", planarFigureModule ); figureInteractor->SetEventConfig( "PlanarFigureConfig.xml", planarFigureModule ); figureInteractor->SetDataNode( node ); } } } } void QmitkFiberExtractionView::OnDrawCircle() { mitk::PlanarCircle::Pointer figure = mitk::PlanarCircle::New(); this->AddFigureToDataStorage(figure, QString("Circle%1").arg(++m_CircleCounter)); this->GetDataStorage()->Modified(); mitk::DataStorage::SetOfObjects::ConstPointer _NodeSet = this->GetDefaultDataStorage()->GetAll(); mitk::DataNode* node = 0; mitk::PlanarFigureInteractor::Pointer figureInteractor = 0; mitk::PlanarFigure* figureP = 0; for(mitk::DataStorage::SetOfObjects::ConstIterator it=_NodeSet->Begin(); it!=_NodeSet->End(); it++) { node = const_cast(it->Value().GetPointer()); figureP = dynamic_cast(node->GetData()); if(figureP) { figureInteractor = dynamic_cast(node->GetDataInteractor().GetPointer()); if(figureInteractor.IsNull()) { figureInteractor = mitk::PlanarFigureInteractor::New(); us::Module* planarFigureModule = us::ModuleRegistry::GetModule( "PlanarFigure" ); figureInteractor->LoadStateMachine("PlanarFigureInteraction.xml", planarFigureModule ); figureInteractor->SetEventConfig( "PlanarFigureConfig.xml", planarFigureModule ); figureInteractor->SetDataNode( node ); } } } } void QmitkFiberExtractionView::Activated() { } void QmitkFiberExtractionView::AddFigureToDataStorage(mitk::PlanarFigure* figure, const QString& name, const char *propertyKey, mitk::BaseProperty *property ) { // initialize figure's geometry with empty geometry mitk::PlaneGeometry::Pointer emptygeometry = mitk::PlaneGeometry::New(); figure->SetGeometry2D( emptygeometry ); //set desired data to DataNode where Planarfigure is stored mitk::DataNode::Pointer newNode = mitk::DataNode::New(); newNode->SetName(name.toStdString()); newNode->SetData(figure); newNode->AddProperty( "planarfigure.default.line.color", mitk::ColorProperty::New(1.0,0.0,0.0)); newNode->AddProperty( "planarfigure.line.width", mitk::FloatProperty::New(2.0)); newNode->AddProperty( "planarfigure.drawshadow", mitk::BoolProperty::New(true)); newNode->AddProperty( "selected", mitk::BoolProperty::New(true) ); newNode->AddProperty( "planarfigure.ishovering", mitk::BoolProperty::New(true) ); newNode->AddProperty( "planarfigure.drawoutline", mitk::BoolProperty::New(true) ); newNode->AddProperty( "planarfigure.drawquantities", mitk::BoolProperty::New(false) ); newNode->AddProperty( "planarfigure.drawshadow", mitk::BoolProperty::New(true) ); newNode->AddProperty( "planarfigure.line.width", mitk::FloatProperty::New(3.0) ); newNode->AddProperty( "planarfigure.shadow.widthmodifier", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.outline.width", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.helperline.width", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.default.line.color", mitk::ColorProperty::New(1.0,1.0,1.0) ); newNode->AddProperty( "planarfigure.default.line.opacity", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.default.outline.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.default.outline.opacity", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.default.helperline.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.default.helperline.opacity", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.default.markerline.color", mitk::ColorProperty::New(0.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.default.markerline.opacity", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.default.marker.color", mitk::ColorProperty::New(1.0,1.0,1.0) ); newNode->AddProperty( "planarfigure.default.marker.opacity",mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.hover.line.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.hover.line.opacity", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.hover.outline.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.hover.outline.opacity", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.hover.helperline.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.hover.helperline.opacity", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.hover.markerline.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.hover.markerline.opacity", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.hover.marker.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.hover.marker.opacity", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.selected.line.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.selected.line.opacity",mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.selected.outline.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.selected.outline.opacity", mitk::FloatProperty::New(2.0)); newNode->AddProperty( "planarfigure.selected.helperline.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.selected.helperline.opacity",mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.selected.markerline.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.selected.markerline.opacity", mitk::FloatProperty::New(2.0) ); newNode->AddProperty( "planarfigure.selected.marker.color", mitk::ColorProperty::New(1.0,0.0,0.0) ); newNode->AddProperty( "planarfigure.selected.marker.opacity",mitk::FloatProperty::New(2.0)); // figure drawn on the topmost layer / image newNode->SetColor(1.0,1.0,1.0); newNode->SetOpacity(0.8); GetDataStorage()->Add(newNode ); std::vector selectedNodes = GetDataManagerSelection(); for(unsigned int i = 0; i < selectedNodes.size(); i++) { selectedNodes[i]->SetSelected(false); } newNode->SetSelected(true); } void QmitkFiberExtractionView::DoFiberExtraction() { if ( m_SelectedFB.empty() ){ QMessageBox::information( NULL, "Warning", "No fibe bundle selected!"); MITK_WARN("QmitkFiberExtractionView") << "no fibe bundle selected"; return; } for (int i=0; i(m_SelectedFB.at(i)->GetData()); mitk::PlanarFigure::Pointer roi = dynamic_cast (m_SelectedPF.at(0)->GetData()); mitk::FiberBundleX::Pointer extFB = fib->ExtractFiberSubset(roi); if (extFB->GetNumFibers()<=0) { QMessageBox::information(NULL, "No output generated:", "The resulting fiber bundle contains no fibers."); continue; } mitk::DataNode::Pointer node; node = mitk::DataNode::New(); node->SetData(extFB); QString name(m_SelectedFB.at(i)->GetName().c_str()); name += "_"; name += m_SelectedPF.at(0)->GetName().c_str(); node->SetName(name.toStdString()); GetDataStorage()->Add(node); m_SelectedFB.at(i)->SetVisibility(false); } } void QmitkFiberExtractionView::GenerateAndComposite() { mitk::PlanarFigureComposite::Pointer PFCAnd = mitk::PlanarFigureComposite::New(); mitk::PlaneGeometry* currentGeometry2D = dynamic_cast( const_cast(GetActiveStdMultiWidget()->GetRenderWindow1()->GetRenderer()->GetCurrentWorldGeometry2D())); PFCAnd->SetGeometry2D(currentGeometry2D); PFCAnd->setOperationType(mitk::PFCOMPOSITION_AND_OPERATION); for( std::vector::iterator it = m_SelectedPF.begin(); it != m_SelectedPF.end(); ++it ) { mitk::DataNode::Pointer nodePF = *it; mitk::PlanarFigure::Pointer tmpPF = dynamic_cast( nodePF->GetData() ); PFCAnd->addPlanarFigure( tmpPF ); PFCAnd->addDataNode( nodePF ); PFCAnd->setDisplayName("AND_COMPO"); } AddCompositeToDatastorage(PFCAnd, NULL); } void QmitkFiberExtractionView::GenerateOrComposite() { mitk::PlanarFigureComposite::Pointer PFCOr = mitk::PlanarFigureComposite::New(); mitk::PlaneGeometry* currentGeometry2D = dynamic_cast( const_cast(GetActiveStdMultiWidget()->GetRenderWindow1()->GetRenderer()->GetCurrentWorldGeometry2D())); PFCOr->SetGeometry2D(currentGeometry2D); PFCOr->setOperationType(mitk::PFCOMPOSITION_OR_OPERATION); for( std::vector::iterator it = m_SelectedPF.begin(); it != m_SelectedPF.end(); ++it ) { mitk::DataNode::Pointer nodePF = *it; mitk::PlanarFigure::Pointer tmpPF = dynamic_cast( nodePF->GetData() ); PFCOr->addPlanarFigure( tmpPF ); PFCOr->addDataNode( nodePF ); PFCOr->setDisplayName("OR_COMPO"); } AddCompositeToDatastorage(PFCOr, NULL); } void QmitkFiberExtractionView::GenerateNotComposite() { mitk::PlanarFigureComposite::Pointer PFCNot = mitk::PlanarFigureComposite::New(); mitk::PlaneGeometry* currentGeometry2D = dynamic_cast( const_cast(GetActiveStdMultiWidget()->GetRenderWindow1()->GetRenderer()->GetCurrentWorldGeometry2D())); PFCNot->SetGeometry2D(currentGeometry2D); PFCNot->setOperationType(mitk::PFCOMPOSITION_NOT_OPERATION); for( std::vector::iterator it = m_SelectedPF.begin(); it != m_SelectedPF.end(); ++it ) { mitk::DataNode::Pointer nodePF = *it; mitk::PlanarFigure::Pointer tmpPF = dynamic_cast( nodePF->GetData() ); PFCNot->addPlanarFigure( tmpPF ); PFCNot->addDataNode( nodePF ); PFCNot->setDisplayName("NOT_COMPO"); } AddCompositeToDatastorage(PFCNot, NULL); } /* CLEANUP NEEDED */ void QmitkFiberExtractionView::AddCompositeToDatastorage(mitk::PlanarFigureComposite::Pointer pfcomp, mitk::DataNode::Pointer parentDataNode ) { mitk::DataNode::Pointer newPFCNode; newPFCNode = mitk::DataNode::New(); newPFCNode->SetName( pfcomp->getDisplayName() ); newPFCNode->SetData(pfcomp); newPFCNode->SetVisibility(true); switch (pfcomp->getOperationType()) { case 0: { if (!parentDataNode.IsNull()) { GetDataStorage()->Add(newPFCNode, parentDataNode); } else { GetDataStorage()->Add(newPFCNode); } //iterate through its childs for(int i=0; igetNumberOfChildren(); ++i) { mitk::PlanarFigure::Pointer tmpPFchild = pfcomp->getChildAt(i); mitk::DataNode::Pointer savedPFchildNode = pfcomp->getDataNodeAt(i); mitk::PlanarFigureComposite::Pointer pfcompcast= dynamic_cast(tmpPFchild.GetPointer()); if ( !pfcompcast.IsNull() ) { // child is of type planar Figure composite // make new node of the child, cuz later the child has to be removed of its old position in datamanager // feed new dataNode with information of the savedDataNode, which is gonna be removed soon mitk::DataNode::Pointer newChildPFCNode; newChildPFCNode = mitk::DataNode::New(); newChildPFCNode->SetData(tmpPFchild); newChildPFCNode->SetName( savedPFchildNode->GetName() ); pfcompcast->setDisplayName( savedPFchildNode->GetName() ); //name might be changed in DataManager by user //update inside vector the dataNodePointer pfcomp->replaceDataNodeAt(i, newChildPFCNode); AddCompositeToDatastorage(pfcompcast, newPFCNode); //the current PFCNode becomes the childs parent // remove savedNode here, cuz otherwise its children will change their position in the dataNodeManager // without having its parent anymore //GetDataStorage()->Remove(savedPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " exists in DS...trying to remove it"; }else{ MITK_DEBUG << "[ERROR] does NOT exist, but can I read its Name? " << savedPFchildNode->GetName(); } // remove old child position in dataStorage GetDataStorage()->Remove(savedPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " still exists"; } } else { // child is not of type PlanarFigureComposite, so its one of the planarFigures // create new dataNode containing the data of the old dataNode, but position in dataManager will be // modified cuz we re setting a (new) parent. mitk::DataNode::Pointer newPFchildNode = mitk::DataNode::New(); newPFchildNode->SetName(savedPFchildNode->GetName() ); newPFchildNode->SetData(tmpPFchild); newPFchildNode->SetVisibility(true); // replace the dataNode in PFComp DataNodeVector pfcomp->replaceDataNodeAt(i, newPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " exists in DS...trying to remove it"; } else { MITK_DEBUG << "[ERROR] does NOT exist, but can I read its Name? " << savedPFchildNode->GetName(); } // remove old child position in dataStorage GetDataStorage()->Remove(savedPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " still exists"; } MITK_DEBUG << "adding " << newPFchildNode->GetName() << " to " << newPFCNode->GetName(); //add new child to datamanager with its new position as child of newPFCNode parent GetDataStorage()->Add(newPFchildNode, newPFCNode); } } GetDataStorage()->Modified(); break; } case 1: { if (!parentDataNode.IsNull()) { MITK_DEBUG << "adding " << newPFCNode->GetName() << " to " << parentDataNode->GetName() ; GetDataStorage()->Add(newPFCNode, parentDataNode); } else { MITK_DEBUG << "adding " << newPFCNode->GetName(); GetDataStorage()->Add(newPFCNode); } for(int i=0; igetNumberOfChildren(); ++i) { mitk::PlanarFigure::Pointer tmpPFchild = pfcomp->getChildAt(i); mitk::DataNode::Pointer savedPFchildNode = pfcomp->getDataNodeAt(i); mitk::PlanarFigureComposite::Pointer pfcompcast= dynamic_cast(tmpPFchild.GetPointer()); if ( !pfcompcast.IsNull() ) { // child is of type planar Figure composite // make new node of the child, cuz later the child has to be removed of its old position in datamanager // feed new dataNode with information of the savedDataNode, which is gonna be removed soon mitk::DataNode::Pointer newChildPFCNode; newChildPFCNode = mitk::DataNode::New(); newChildPFCNode->SetData(tmpPFchild); newChildPFCNode->SetName( savedPFchildNode->GetName() ); pfcompcast->setDisplayName( savedPFchildNode->GetName() ); //name might be changed in DataManager by user //update inside vector the dataNodePointer pfcomp->replaceDataNodeAt(i, newChildPFCNode); AddCompositeToDatastorage(pfcompcast, newPFCNode); //the current PFCNode becomes the childs parent // remove savedNode here, cuz otherwise its children will change their position in the dataNodeManager // without having its parent anymore //GetDataStorage()->Remove(savedPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " exists in DS...trying to remove it"; }else{ MITK_DEBUG << "[ERROR] does NOT exist, but can I read its Name? " << savedPFchildNode->GetName(); } // remove old child position in dataStorage GetDataStorage()->Remove(savedPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " still exists"; } } else { // child is not of type PlanarFigureComposite, so its one of the planarFigures // create new dataNode containing the data of the old dataNode, but position in dataManager will be // modified cuz we re setting a (new) parent. mitk::DataNode::Pointer newPFchildNode = mitk::DataNode::New(); newPFchildNode->SetName(savedPFchildNode->GetName() ); newPFchildNode->SetData(tmpPFchild); newPFchildNode->SetVisibility(true); // replace the dataNode in PFComp DataNodeVector pfcomp->replaceDataNodeAt(i, newPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " exists in DS...trying to remove it"; }else{ MITK_DEBUG << "[ERROR] does NOT exist, but can I read its Name? " << savedPFchildNode->GetName(); } // remove old child position in dataStorage GetDataStorage()->Remove(savedPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " still exists"; } MITK_DEBUG << "adding " << newPFchildNode->GetName() << " to " << newPFCNode->GetName(); //add new child to datamanager with its new position as child of newPFCNode parent GetDataStorage()->Add(newPFchildNode, newPFCNode); } } GetDataStorage()->Modified(); break; } case 2: { if (!parentDataNode.IsNull()) { MITK_DEBUG << "adding " << newPFCNode->GetName() << " to " << parentDataNode->GetName() ; GetDataStorage()->Add(newPFCNode, parentDataNode); } else { MITK_DEBUG << "adding " << newPFCNode->GetName(); GetDataStorage()->Add(newPFCNode); } //iterate through its childs for(int i=0; igetNumberOfChildren(); ++i) { mitk::PlanarFigure::Pointer tmpPFchild = pfcomp->getChildAt(i); mitk::DataNode::Pointer savedPFchildNode = pfcomp->getDataNodeAt(i); mitk::PlanarFigureComposite::Pointer pfcompcast= dynamic_cast(tmpPFchild.GetPointer()); if ( !pfcompcast.IsNull() ) { // child is of type planar Figure composite // makeRemoveBundle new node of the child, cuz later the child has to be removed of its old position in datamanager // feed new dataNode with information of the savedDataNode, which is gonna be removed soon mitk::DataNode::Pointer newChildPFCNode; newChildPFCNode = mitk::DataNode::New(); newChildPFCNode->SetData(tmpPFchild); newChildPFCNode->SetName( savedPFchildNode->GetName() ); pfcompcast->setDisplayName( savedPFchildNode->GetName() ); //name might be changed in DataManager by user //update inside vector the dataNodePointer pfcomp->replaceDataNodeAt(i, newChildPFCNode); AddCompositeToDatastorage(pfcompcast, newPFCNode); //the current PFCNode becomes the childs parent // remove savedNode here, cuz otherwise its children will change their position in the dataNodeManager // without having its parent anymore //GetDataStorage()->Remove(savedPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " exists in DS...trying to remove it"; }else{ MITK_DEBUG << "[ERROR] does NOT exist, but can I read its Name? " << savedPFchildNode->GetName(); } // remove old child position in dataStorage GetDataStorage()->Remove(savedPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " still exists"; } } else { // child is not of type PlanarFigureComposite, so its one of the planarFigures // create new dataNode containing the data of the old dataNode, but position in dataManager will be // modified cuz we re setting a (new) parent. mitk::DataNode::Pointer newPFchildNode = mitk::DataNode::New(); newPFchildNode->SetName(savedPFchildNode->GetName() ); newPFchildNode->SetData(tmpPFchild); newPFchildNode->SetVisibility(true); // replace the dataNode in PFComp DataNodeVector pfcomp->replaceDataNodeAt(i, newPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " exists in DS...trying to remove it"; }else{ MITK_DEBUG << "[ERROR] does NOT exist, but can I read its Name? " << savedPFchildNode->GetName(); } // remove old child position in dataStorage GetDataStorage()->Remove(savedPFchildNode); if ( GetDataStorage()->Exists(savedPFchildNode)) { MITK_DEBUG << savedPFchildNode->GetName() << " still exists"; } MITK_DEBUG << "adding " << newPFchildNode->GetName() << " to " << newPFCNode->GetName(); //add new child to datamanager with its new position as child of newPFCNode parent GetDataStorage()->Add(newPFchildNode, newPFCNode); } } GetDataStorage()->Modified(); break; } default: MITK_DEBUG << "we have an UNDEFINED composition... ERROR" ; break; } } void QmitkFiberExtractionView::JoinBundles() { if ( m_SelectedFB.size()<2 ){ QMessageBox::information( NULL, "Warning", "Select at least two fiber bundles!"); MITK_WARN("QmitkFiberExtractionView") << "Select at least two fiber bundles!"; return; } mitk::FiberBundleX::Pointer newBundle = dynamic_cast(m_SelectedFB.at(0)->GetData()); m_SelectedFB.at(0)->SetVisibility(false); QString name(""); name += QString(m_SelectedFB.at(0)->GetName().c_str()); for (int i=1; iAddBundle(dynamic_cast(m_SelectedFB.at(i)->GetData())); name += "+"+QString(m_SelectedFB.at(i)->GetName().c_str()); m_SelectedFB.at(i)->SetVisibility(false); } mitk::DataNode::Pointer fbNode = mitk::DataNode::New(); fbNode->SetData(newBundle); fbNode->SetName(name.toStdString()); fbNode->SetVisibility(true); GetDataStorage()->Add(fbNode); } void QmitkFiberExtractionView::SubstractBundles() { if ( m_SelectedFB.size()<2 ){ QMessageBox::information( NULL, "Warning", "Select at least two fiber bundles!"); MITK_WARN("QmitkFiberExtractionView") << "Select at least two fiber bundles!"; return; } mitk::FiberBundleX::Pointer newBundle = dynamic_cast(m_SelectedFB.at(0)->GetData()); m_SelectedFB.at(0)->SetVisibility(false); QString name(""); name += QString(m_SelectedFB.at(0)->GetName().c_str()); for (int i=1; iSubtractBundle(dynamic_cast(m_SelectedFB.at(i)->GetData())); if (newBundle.IsNull()) break; name += "-"+QString(m_SelectedFB.at(i)->GetName().c_str()); m_SelectedFB.at(i)->SetVisibility(false); } if (newBundle.IsNull()) { QMessageBox::information(NULL, "No output generated:", "The resulting fiber bundle contains no fibers. Did you select the fiber bundles in the correct order? X-Y is not equal to Y-X!"); return; } mitk::DataNode::Pointer fbNode = mitk::DataNode::New(); fbNode->SetData(newBundle); fbNode->SetName(name.toStdString()); fbNode->SetVisibility(true); GetDataStorage()->Add(fbNode); } void QmitkFiberExtractionView::GenerateStats() { if ( m_SelectedFB.empty() ) return; QString stats(""); for( int i=0; i(node->GetData())) { if (i>0) stats += "\n-----------------------------\n"; stats += QString(node->GetName().c_str()) + "\n"; mitk::FiberBundleX::Pointer fib = dynamic_cast(node->GetData()); stats += "Number of fibers: "+ QString::number(fib->GetNumFibers()) + "\n"; stats += "Min. length: "+ QString::number(fib->GetMinFiberLength(),'f',1) + " mm\n"; stats += "Max. length: "+ QString::number(fib->GetMaxFiberLength(),'f',1) + " mm\n"; stats += "Mean length: "+ QString::number(fib->GetMeanFiberLength(),'f',1) + " mm\n"; stats += "Median length: "+ QString::number(fib->GetMedianFiberLength(),'f',1) + " mm\n"; stats += "Standard deviation: "+ QString::number(fib->GetLengthStDev(),'f',1) + " mm\n"; } } this->m_Controls->m_StatsTextEdit->setText(stats); } diff --git a/Plugins/org.mitk.gui.qt.examples/src/internal/simpleexample/QmitkSimpleExampleView.cpp b/Plugins/org.mitk.gui.qt.examples/src/internal/simpleexample/QmitkSimpleExampleView.cpp index 88f58189cb..7f768e68a7 100644 --- a/Plugins/org.mitk.gui.qt.examples/src/internal/simpleexample/QmitkSimpleExampleView.cpp +++ b/Plugins/org.mitk.gui.qt.examples/src/internal/simpleexample/QmitkSimpleExampleView.cpp @@ -1,305 +1,305 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "QmitkSimpleExampleView.h" #include "mitkNodePredicateDataType.h" #include "QmitkDataStorageComboBox.h" #include "QmitkStdMultiWidget.h" #include #include #include "mitkNodePredicateProperty.h" #include "mitkNodePredicateNot.h" #include "mitkProperties.h" #include #include #include #include #include #include "vtkImageWriter.h" #include "vtkPNGWriter.h" #include "vtkJPEGWriter.h" #include "vtkRenderLargeImage.h" const std::string QmitkSimpleExampleView::VIEW_ID = "org.mitk.views.simpleexample"; QmitkSimpleExampleView::QmitkSimpleExampleView() : QmitkFunctionality(), m_Controls(NULL), m_MultiWidget(NULL), m_NavigatorsInitialized(false) { } QmitkSimpleExampleView::QmitkSimpleExampleView(const QmitkSimpleExampleView& other) { Q_UNUSED(other) throw std::runtime_error("Copy constructor not implemented"); } QmitkSimpleExampleView::~QmitkSimpleExampleView() { } void QmitkSimpleExampleView::CreateQtPartControl(QWidget *parent) { if (!m_Controls) { // create GUI widgets m_Controls = new Ui::QmitkSimpleExampleViewControls; m_Controls->setupUi(parent); this->CreateConnections(); } } void QmitkSimpleExampleView::StdMultiWidgetAvailable (QmitkStdMultiWidget &stdMultiWidget) { m_MultiWidget = &stdMultiWidget; new QmitkStepperAdapter(m_Controls->sliceNavigatorAxial, m_MultiWidget->mitkWidget1->GetSliceNavigationController()->GetSlice(), "sliceNavigatorAxialFromSimpleExample"); new QmitkStepperAdapter(m_Controls->sliceNavigatorSagittal, m_MultiWidget->mitkWidget2->GetSliceNavigationController()->GetSlice(), "sliceNavigatorSagittalFromSimpleExample"); new QmitkStepperAdapter(m_Controls->sliceNavigatorFrontal, m_MultiWidget->mitkWidget3->GetSliceNavigationController()->GetSlice(), "sliceNavigatorFrontalFromSimpleExample"); new QmitkStepperAdapter(m_Controls->sliceNavigatorTime, m_MultiWidget->GetTimeNavigationController()->GetTime(), "sliceNavigatorTimeFromSimpleExample"); new QmitkStepperAdapter(m_Controls->movieNavigatorTime, m_MultiWidget->GetTimeNavigationController()->GetTime(), "movieNavigatorTimeFromSimpleExample"); } void QmitkSimpleExampleView::StdMultiWidgetNotAvailable() { m_MultiWidget = NULL; } void QmitkSimpleExampleView::CreateConnections() { if ( m_Controls ) { connect(m_Controls->stereoSelect, SIGNAL(activated(int)), this, SLOT(stereoSelectionChanged(int)) ); connect(m_Controls->reInitializeNavigatorsButton, SIGNAL(clicked()), this, SLOT(initNavigators()) ); connect(m_Controls->genMovieButton, SIGNAL(clicked()), this, SLOT(generateMovie()) ); connect(m_Controls->m_RenderWindow1Button, SIGNAL(clicked()), this, SLOT(OnRenderWindow1Clicked()) ); connect(m_Controls->m_RenderWindow2Button, SIGNAL(clicked()), this, SLOT(OnRenderWindow2Clicked()) ); connect(m_Controls->m_RenderWindow3Button, SIGNAL(clicked()), this, SLOT(OnRenderWindow3Clicked()) ); connect(m_Controls->m_RenderWindow4Button, SIGNAL(clicked()), this, SLOT(OnRenderWindow4Clicked()) ); connect(m_Controls->m_TakeScreenshotBtn, SIGNAL(clicked()), this, SLOT(OnTakeScreenshot()) ); connect(m_Controls->m_TakeHighResScreenShotBtn, SIGNAL(clicked()), this, SLOT(OnTakeHighResolutionScreenshot()) ); } } void QmitkSimpleExampleView::Activated() { QmitkFunctionality::Activated(); } void QmitkSimpleExampleView::Deactivated() { QmitkFunctionality::Deactivated(); } void QmitkSimpleExampleView::initNavigators() { /* get all nodes that have not set "includeInBoundingBox" to false */ mitk::NodePredicateNot::Pointer pred = mitk::NodePredicateNot::New(mitk::NodePredicateProperty::New("includeInBoundingBox", mitk::BoolProperty::New(false))); mitk::DataStorage::SetOfObjects::ConstPointer rs = this->GetDataStorage()->GetSubset(pred); /* calculate bounding geometry of these nodes */ mitk::TimeGeometry::Pointer bounds = this->GetDataStorage()->ComputeBoundingGeometry3D(rs); /* initialize the views to the bounding geometry */ m_NavigatorsInitialized = mitk::RenderingManager::GetInstance()->InitializeViews(bounds); //m_NavigatorsInitialized = mitk::RenderingManager::GetInstance()->InitializeViews(GetDefaultDataStorage()); } void QmitkSimpleExampleView::generateMovie() { QmitkRenderWindow* movieRenderWindow = GetMovieRenderWindow(); //mitk::Stepper::Pointer stepper = multiWidget->mitkWidget1->GetSliceNavigationController()->GetSlice(); mitk::Stepper::Pointer stepper = movieRenderWindow->GetSliceNavigationController()->GetSlice(); mitk::MovieGenerator::Pointer movieGenerator = mitk::MovieGenerator::New(); if (movieGenerator.IsNotNull()) { movieGenerator->SetStepper( stepper ); movieGenerator->SetRenderer( mitk::BaseRenderer::GetInstance(movieRenderWindow->GetRenderWindow()) ); QString movieFileName = QFileDialog::getSaveFileName(0, "Choose a file name", QString(), "Movie (*.avi)"); if (!movieFileName.isEmpty()) { movieGenerator->SetFileName( movieFileName.toStdString().c_str() ); movieGenerator->WriteMovie(); } } } void QmitkSimpleExampleView::stereoSelectionChanged( int id ) { /* From vtkRenderWindow.h tells us about stereo rendering: Set/Get what type of stereo rendering to use. CrystalEyes mode uses frame-sequential capabilities available in OpenGL to drive LCD shutter glasses and stereo projectors. RedBlue mode is a simple type of stereo for use with red-blue glasses. Anaglyph mode is a superset of RedBlue mode, but the color output channels can be configured using the AnaglyphColorMask and the color of the original image can be (somewhat maintained using AnaglyphColorSaturation; the default colors for Anaglyph mode is red-cyan. Interlaced stereo mode produces a composite image where horizontal lines alternate between left and right views. StereoLeft and StereoRight modes choose one or the other stereo view. Dresden mode is yet another stereoscopic interleaving. */ vtkRenderWindow * vtkrenderwindow = m_MultiWidget->mitkWidget4->GetRenderWindow(); // note: foreground vtkRenderers (at least the department logo renderer) produce errors in stereoscopic visualization. // Therefore, we disable the logo visualization during stereo rendering. switch(id) { case 0: vtkrenderwindow->StereoRenderOff(); break; case 1: vtkrenderwindow->SetStereoTypeToRedBlue(); vtkrenderwindow->StereoRenderOn(); m_MultiWidget->DisableDepartmentLogo(); break; case 2: vtkrenderwindow->SetStereoTypeToDresden(); vtkrenderwindow->StereoRenderOn(); m_MultiWidget->DisableDepartmentLogo(); break; } mitk::BaseRenderer::GetInstance(m_MultiWidget->mitkWidget4->GetRenderWindow())->SetMapperID(2); m_MultiWidget->RequestUpdate(); } QmitkRenderWindow* QmitkSimpleExampleView::GetMovieRenderWindow() { //check which RenderWindow should be used to generate the movie, e.g. which button is toggled if(m_Controls->m_RenderWindow1Button->isChecked()) { return m_MultiWidget->mitkWidget1; } else if(m_Controls->m_RenderWindow2Button->isChecked()) { return m_MultiWidget->mitkWidget2; } else if(m_Controls->m_RenderWindow3Button->isChecked()) { return m_MultiWidget->mitkWidget3; } else if(m_Controls->m_RenderWindow4Button->isChecked()) { return m_MultiWidget->mitkWidget4; } else //as default take widget1 { return m_MultiWidget->mitkWidget1; } } void QmitkSimpleExampleView::OnRenderWindow1Clicked() { m_Controls->m_RenderWindow2Button->setChecked(false); m_Controls->m_RenderWindow3Button->setChecked(false); m_Controls->m_RenderWindow4Button->setChecked(false); } void QmitkSimpleExampleView::OnRenderWindow2Clicked() { m_Controls->m_RenderWindow1Button->setChecked(false); m_Controls->m_RenderWindow3Button->setChecked(false); m_Controls->m_RenderWindow4Button->setChecked(false); } void QmitkSimpleExampleView::OnRenderWindow3Clicked() { m_Controls->m_RenderWindow2Button->setChecked(false); m_Controls->m_RenderWindow1Button->setChecked(false); m_Controls->m_RenderWindow4Button->setChecked(false); } void QmitkSimpleExampleView::OnRenderWindow4Clicked() { m_Controls->m_RenderWindow2Button->setChecked(false); m_Controls->m_RenderWindow3Button->setChecked(false); m_Controls->m_RenderWindow1Button->setChecked(false); } void QmitkSimpleExampleView::OnTakeHighResolutionScreenshot() { QString fileName = QFileDialog::getSaveFileName(NULL, "Save screenshot to...", QDir::currentPath(), "JPEG file (*.jpg);;PNG file (*.png)"); // only works correctly for 3D RenderWindow vtkRenderer* renderer = m_MultiWidget->mitkWidget4->GetRenderer()->GetVtkRenderer(); if (renderer == NULL) return; this->TakeScreenshot(renderer, 4, fileName); } void QmitkSimpleExampleView::OnTakeScreenshot() { QString fileName = QFileDialog::getSaveFileName(NULL, "Save screenshot to...", QDir::currentPath(), "JPEG file (*.jpg);;PNG file (*.png)"); QmitkRenderWindow* renWin = this->GetMovieRenderWindow(); if (renWin == NULL) return; vtkRenderer* renderer = renWin->GetRenderer()->GetVtkRenderer(); if (renderer == NULL) return; this->TakeScreenshot(renderer, 1, fileName); } void QmitkSimpleExampleView::TakeScreenshot(vtkRenderer* renderer, unsigned int magnificationFactor, QString fileName) { if ((renderer == NULL) ||(magnificationFactor < 1) || fileName.isEmpty()) return; bool doubleBuffering( renderer->GetRenderWindow()->GetDoubleBuffer() ); renderer->GetRenderWindow()->DoubleBufferOff(); vtkImageWriter* fileWriter; QFileInfo fi(fileName); QString suffix = fi.suffix(); if (suffix.compare("png", Qt::CaseInsensitive) == 0) { fileWriter = vtkPNGWriter::New(); } else // default is jpeg { vtkJPEGWriter* w = vtkJPEGWriter::New(); w->SetQuality(100); w->ProgressiveOff(); fileWriter = w; } vtkRenderLargeImage* magnifier = vtkRenderLargeImage::New(); magnifier->SetInput(renderer); magnifier->SetMagnification(magnificationFactor); //magnifier->Update(); - fileWriter->SetInput(magnifier->GetOutput()); + fileWriter->SetInputConnection(magnifier->GetOutputPort()); fileWriter->SetFileName(fileName.toLatin1()); // vtkRenderLargeImage has problems with different layers, therefore we have to // temporarily deactivate all other layers. // we set the background to white, because it is nicer than black... double oldBackground[3]; renderer->GetBackground(oldBackground); double white[] = {1.0, 1.0, 1.0}; renderer->SetBackground(white); m_MultiWidget->DisableColoredRectangles(); m_MultiWidget->DisableDepartmentLogo(); m_MultiWidget->DisableGradientBackground(); fileWriter->Write(); fileWriter->Delete(); m_MultiWidget->EnableColoredRectangles(); m_MultiWidget->EnableDepartmentLogo(); m_MultiWidget->EnableGradientBackground(); renderer->SetBackground(oldBackground); renderer->GetRenderWindow()->SetDoubleBuffer(doubleBuffering); } diff --git a/Plugins/org.mitk.gui.qt.examples/src/internal/surfaceutilities/mitkSurfaceToPointSetFilter.cpp b/Plugins/org.mitk.gui.qt.examples/src/internal/surfaceutilities/mitkSurfaceToPointSetFilter.cpp index f73b48c661..3ae0549887 100644 --- a/Plugins/org.mitk.gui.qt.examples/src/internal/surfaceutilities/mitkSurfaceToPointSetFilter.cpp +++ b/Plugins/org.mitk.gui.qt.examples/src/internal/surfaceutilities/mitkSurfaceToPointSetFilter.cpp @@ -1,86 +1,86 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "mitkSurfaceToPointSetFilter.h" //mitk headers #include "mitkPointSet.h" //itk headers #include "itkMatrix.h" #include "itkVector.h" //vtk headers #include #include mitk::SurfaceToPointSetFilter::SurfaceToPointSetFilter() { this->SetNumberOfOutputs(1); } mitk::SurfaceToPointSetFilter::~SurfaceToPointSetFilter() { } void mitk::SurfaceToPointSetFilter::GenerateData() { if (m_InputSurface.IsNull()) { this->SetNthOutput(0,NULL); m_ErrorMessage = "Error in SurfaceToPointSetFilter: Input is not set correctly."; return; } mitk::PointSet::Pointer result = mitk::PointSet::New(); vtkPolyData* points = this->m_InputSurface->GetVtkPolyData(); vtkCleanPolyData *cleaner = vtkCleanPolyData::New(); cleaner->PieceInvariantOff(); cleaner->ConvertLinesToPointsOff(); cleaner->ConvertPolysToLinesOff(); cleaner->ConvertStripsToPolysOff(); cleaner->PointMergingOn(); - cleaner->SetInput(points); + cleaner->SetInputData(points); cleaner->Update(); vtkPolyData* mergedPoints = cleaner->GetOutput(); //generate filter output for (int i=0; iGetNumberOfPoints(); i++) { mitk::Point3D currentPoint; currentPoint[0] = mergedPoints->GetPoint(i)[0]; currentPoint[1] = mergedPoints->GetPoint(i)[1]; currentPoint[2] = mergedPoints->GetPoint(i)[2]; result->InsertPoint(i,currentPoint); } this->SetNthOutput(0,result); //------------------------- cleaner->Delete(); } void mitk::SurfaceToPointSetFilter::SetInput(mitk::Surface::Pointer InputSurface) { m_InputSurface = InputSurface; this->Modified(); } std::string mitk::SurfaceToPointSetFilter::GetErrorMessage() { return this->m_ErrorMessage; } diff --git a/Plugins/org.mitk.gui.qt.measurementtoolbox/src/internal/QmitkImageStatisticsView.cpp b/Plugins/org.mitk.gui.qt.measurementtoolbox/src/internal/QmitkImageStatisticsView.cpp index c3cccbc3cd..e4b291080a 100644 --- a/Plugins/org.mitk.gui.qt.measurementtoolbox/src/internal/QmitkImageStatisticsView.cpp +++ b/Plugins/org.mitk.gui.qt.measurementtoolbox/src/internal/QmitkImageStatisticsView.cpp @@ -1,726 +1,726 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "QmitkImageStatisticsView.h" // Qt includes #include // berry includes #include // mitk includes #include "mitkNodePredicateDataType.h" #include "mitkPlanarFigureInteractor.h" // itk includes #include "itksys/SystemTools.hxx" #include #include const std::string QmitkImageStatisticsView::VIEW_ID = "org.mitk.views.imagestatistics"; QmitkImageStatisticsView::QmitkImageStatisticsView(QObject* /*parent*/, const char* /*name*/) : m_Controls( NULL ), m_TimeStepperAdapter( NULL ), m_SelectedImage( NULL ), m_SelectedImageMask( NULL ), m_SelectedPlanarFigure( NULL ), m_ImageObserverTag( -1 ), m_ImageMaskObserverTag( -1 ), m_PlanarFigureObserverTag( -1 ), m_CurrentStatisticsValid( false ), m_StatisticsUpdatePending( false ), m_DataNodeSelectionChanged ( false ), m_Visible(false) { this->m_CalculationThread = new QmitkImageStatisticsCalculationThread; } QmitkImageStatisticsView::~QmitkImageStatisticsView() { if ( m_SelectedImage != NULL ) m_SelectedImage->RemoveObserver( m_ImageObserverTag ); if ( m_SelectedImageMask != NULL ) m_SelectedImageMask->RemoveObserver( m_ImageMaskObserverTag ); if ( m_SelectedPlanarFigure != NULL ) m_SelectedPlanarFigure->RemoveObserver( m_PlanarFigureObserverTag ); while(this->m_CalculationThread->isRunning()) // wait until thread has finished { itksys::SystemTools::Delay(100); } delete this->m_CalculationThread; } void QmitkImageStatisticsView::CreateQtPartControl(QWidget *parent) { if (m_Controls == NULL) { m_Controls = new Ui::QmitkImageStatisticsViewControls; m_Controls->setupUi(parent); this->CreateConnections(); m_Controls->m_ErrorMessageLabel->hide(); m_Controls->m_StatisticsWidgetStack->setCurrentIndex( 0 ); - m_Controls->m_LineProfileWidget->SetPathModeToPlanarFigure(); +// m_Controls->m_LineProfileWidget->SetPathModeToPlanarFigure(); } } void QmitkImageStatisticsView::CreateConnections() { if ( m_Controls ) { connect( (QObject*)(this->m_Controls->m_ButtonCopyHistogramToClipboard), SIGNAL(clicked()),(QObject*) this, SLOT(OnClipboardHistogramButtonClicked()) ); connect( (QObject*)(this->m_Controls->m_ButtonCopyStatisticsToClipboard), SIGNAL(clicked()),(QObject*) this, SLOT(OnClipboardStatisticsButtonClicked()) ); connect( (QObject*)(this->m_Controls->m_IgnoreZerosCheckbox), SIGNAL(clicked()),(QObject*) this, SLOT(OnIgnoreZerosCheckboxClicked()) ); connect( (QObject*) this->m_CalculationThread, SIGNAL(finished()),this, SLOT( OnThreadedStatisticsCalculationEnds()),Qt::QueuedConnection); connect( (QObject*) this, SIGNAL(StatisticsUpdate()),this, SLOT( RequestStatisticsUpdate()), Qt::QueuedConnection); connect( (QObject*) this->m_Controls->m_StatisticsTable, SIGNAL(cellDoubleClicked(int,int)),this, SLOT( JumpToCoordinates(int,int)) ); connect( (QObject*) (this->m_Controls->m_barRadioButton), SIGNAL(clicked()), (QObject*) (this->m_Controls->m_JSHistogram), SLOT(OnBarRadioButtonSelected())); connect( (QObject*) (this->m_Controls->m_lineRadioButton), SIGNAL(clicked()), (QObject*) (this->m_Controls->m_JSHistogram), SLOT(OnLineRadioButtonSelected())); } } void QmitkImageStatisticsView::JumpToCoordinates(int row ,int col) { if(m_SelectedDataNodes.isEmpty()) { MITK_WARN("QmitkImageStatisticsView") << "No data node selected for statistics calculation." ; return; } mitk::Point3D world; if (row==4) world = m_WorldMin; else if (row==3) world = m_WorldMax; else return; mitk::IRenderWindowPart* part = this->GetRenderWindowPart(); if (part) { part->GetQmitkRenderWindow("axial")->GetSliceNavigationController()->SelectSliceByPoint(world); part->GetQmitkRenderWindow("sagittal")->GetSliceNavigationController()->SelectSliceByPoint(world); part->GetQmitkRenderWindow("coronal")->GetSliceNavigationController()->SelectSliceByPoint(world); } } void QmitkImageStatisticsView::OnIgnoreZerosCheckboxClicked() { emit StatisticsUpdate(); } void QmitkImageStatisticsView::OnClipboardHistogramButtonClicked() { if ( m_CurrentStatisticsValid ) { typedef mitk::ImageStatisticsCalculator::HistogramType HistogramType; const HistogramType *histogram = this->m_CalculationThread->GetTimeStepHistogram().GetPointer(); QString clipboard( "Measurement \t Frequency\n" ); for ( HistogramType::ConstIterator it = histogram->Begin(); it != histogram->End(); ++it ) { clipboard = clipboard.append( "%L1 \t %L2\n" ) .arg( it.GetMeasurementVector()[0], 0, 'f', 2 ) .arg( it.GetFrequency() ); } QApplication::clipboard()->setText( clipboard, QClipboard::Clipboard ); } else { QApplication::clipboard()->clear(); } } void QmitkImageStatisticsView::OnClipboardStatisticsButtonClicked() { if ( this->m_CurrentStatisticsValid ) { const mitk::ImageStatisticsCalculator::Statistics &statistics = this->m_CalculationThread->GetStatisticsData(); // Copy statistics to clipboard ("%Ln" will use the default locale for // number formatting) QString clipboard( "Mean \t StdDev \t RMS \t Max \t Min \t N \t V (mm³)\n" ); clipboard = clipboard.append( "%L1 \t %L2 \t %L3 \t %L4 \t %L5 \t %L6 \t %L7" ) .arg( statistics.Mean, 0, 'f', 10 ) .arg( statistics.Sigma, 0, 'f', 10 ) .arg( statistics.RMS, 0, 'f', 10 ) .arg( statistics.Max, 0, 'f', 10 ) .arg( statistics.Min, 0, 'f', 10 ) .arg( statistics.N ) .arg( m_Controls->m_StatisticsTable->item( 0, 6 )->text() ); QApplication::clipboard()->setText( clipboard, QClipboard::Clipboard ); } else { QApplication::clipboard()->clear(); } } void QmitkImageStatisticsView::OnSelectionChanged( berry::IWorkbenchPart::Pointer /*part*/, const QList &selectedNodes ) { if (this->m_Visible) { this->SelectionChanged( selectedNodes ); } else { this->m_DataNodeSelectionChanged = true; } } void QmitkImageStatisticsView::SelectionChanged(const QList &selectedNodes) { if( this->m_StatisticsUpdatePending ) { this->m_DataNodeSelectionChanged = true; return; // not ready for new data now! } if (selectedNodes.size() == this->m_SelectedDataNodes.size()) { int i = 0; for (; i < selectedNodes.size(); ++i) { if (selectedNodes.at(i) != this->m_SelectedDataNodes.at(i)) { break; } } // node selection did not change if (i == selectedNodes.size()) return; } this->ReinitData(); if (selectedNodes.isEmpty()) { m_Controls->m_JSHistogram->ClearHistogram(); m_Controls->m_lineRadioButton->setEnabled(true); m_Controls->m_barRadioButton->setEnabled(true); m_Controls->m_InfoLabel->setText(QString("")); // m_Controls->horizontalLayout_3->setEnabled(false); m_Controls->groupBox->setEnabled(false); m_Controls->groupBox_3->setEnabled(false); } else { // m_Controls->horizontalLayout_3->setEnabled(true); m_Controls->groupBox->setEnabled(true); m_Controls->groupBox_3->setEnabled(true); } if(selectedNodes.size() == 1 || selectedNodes.size() == 2) { bool isBinary = false; selectedNodes.value(0)->GetBoolProperty("binary",isBinary); if(isBinary) { m_Controls->m_JSHistogram->ClearHistogram(); m_Controls->m_lineRadioButton->setEnabled(true); m_Controls->m_barRadioButton->setEnabled(true); m_Controls->m_InfoLabel->setText(QString("")); } for (int i= 0; i< selectedNodes.size(); ++i) { this->m_SelectedDataNodes.push_back(selectedNodes.at(i)); } this->m_DataNodeSelectionChanged = false; this->m_Controls->m_ErrorMessageLabel->setText( "" ); this->m_Controls->m_ErrorMessageLabel->hide(); emit StatisticsUpdate(); } else { this->m_DataNodeSelectionChanged = false; } } void QmitkImageStatisticsView::ReinitData() { while( this->m_CalculationThread->isRunning()) // wait until thread has finished { itksys::SystemTools::Delay(100); } if(this->m_SelectedImage != NULL) { this->m_SelectedImage->RemoveObserver( this->m_ImageObserverTag); this->m_SelectedImage = NULL; } if(this->m_SelectedImageMask != NULL) { this->m_SelectedImageMask->RemoveObserver( this->m_ImageMaskObserverTag); this->m_SelectedImageMask = NULL; } if(this->m_SelectedPlanarFigure != NULL) { this->m_SelectedPlanarFigure->RemoveObserver( this->m_PlanarFigureObserverTag); this->m_SelectedPlanarFigure = NULL; } this->m_SelectedDataNodes.clear(); this->m_StatisticsUpdatePending = false; m_Controls->m_ErrorMessageLabel->setText( "" ); m_Controls->m_ErrorMessageLabel->hide(); this->InvalidateStatisticsTableView(); m_Controls->m_StatisticsWidgetStack->setCurrentIndex( 0 ); } void QmitkImageStatisticsView::OnThreadedStatisticsCalculationEnds() { std::stringstream message; message << ""; m_Controls->m_ErrorMessageLabel->setText( message.str().c_str() ); m_Controls->m_ErrorMessageLabel->hide(); this->WriteStatisticsToGUI(); } void QmitkImageStatisticsView::UpdateStatistics() { mitk::IRenderWindowPart* renderPart = this->GetRenderWindowPart(); if ( renderPart == NULL ) { this->m_StatisticsUpdatePending = false; return; } m_WorldMin.Fill(-1); m_WorldMax.Fill(-1); // classify selected nodes mitk::NodePredicateDataType::Pointer imagePredicate = mitk::NodePredicateDataType::New("Image"); std::string maskName = std::string(); std::string maskType = std::string(); unsigned int maskDimension = 0; // reset data from last run ITKCommandType::Pointer changeListener = ITKCommandType::New(); changeListener->SetCallbackFunction( this, &QmitkImageStatisticsView::SelectedDataModified ); mitk::DataNode::Pointer planarFigureNode; for( int i= 0 ; i < this->m_SelectedDataNodes.size(); ++i) { mitk::PlanarFigure::Pointer planarFig = dynamic_cast(this->m_SelectedDataNodes.at(i)->GetData()); if( imagePredicate->CheckNode(this->m_SelectedDataNodes.at(i)) ) { bool isMask = false; this->m_SelectedDataNodes.at(i)->GetPropertyValue("binary", isMask); if( this->m_SelectedImageMask == NULL && isMask) { this->m_SelectedImageMask = dynamic_cast(this->m_SelectedDataNodes.at(i)->GetData()); this->m_ImageMaskObserverTag = this->m_SelectedImageMask->AddObserver(itk::ModifiedEvent(), changeListener); maskName = this->m_SelectedDataNodes.at(i)->GetName(); maskType = m_SelectedImageMask->GetNameOfClass(); maskDimension = 3; } else if( !isMask ) { if(this->m_SelectedImage == NULL) { this->m_SelectedImage = static_cast(this->m_SelectedDataNodes.at(i)->GetData()); this->m_ImageObserverTag = this->m_SelectedImage->AddObserver(itk::ModifiedEvent(), changeListener); } } } else if (planarFig.IsNotNull()) { if(this->m_SelectedPlanarFigure == NULL) { this->m_SelectedPlanarFigure = planarFig; this->m_PlanarFigureObserverTag = this->m_SelectedPlanarFigure->AddObserver(mitk::EndInteractionPlanarFigureEvent(), changeListener); maskName = this->m_SelectedDataNodes.at(i)->GetName(); maskType = this->m_SelectedPlanarFigure->GetNameOfClass(); maskDimension = 2; planarFigureNode = m_SelectedDataNodes.at(i); } } else { std::stringstream message; message << "" << "Invalid data node type!" << ""; m_Controls->m_ErrorMessageLabel->setText( message.str().c_str() ); m_Controls->m_ErrorMessageLabel->show(); } } if(maskName == "") { maskName = "None"; maskType = ""; maskDimension = 0; } if (m_SelectedPlanarFigure != NULL && m_SelectedImage == NULL) { mitk::DataStorage::SetOfObjects::ConstPointer parentSet = this->GetDataStorage()->GetSources(planarFigureNode); for (int i=0; iSize(); i++) { mitk::DataNode::Pointer node = parentSet->ElementAt(i); if( imagePredicate->CheckNode(node) ) { bool isMask = false; node->GetPropertyValue("binary", isMask); if( !isMask ) { if(this->m_SelectedImage == NULL) { this->m_SelectedImage = static_cast(node->GetData()); this->m_ImageObserverTag = this->m_SelectedImage->AddObserver(itk::ModifiedEvent(), changeListener); } } } } } unsigned int timeStep = renderPart->GetTimeNavigationController()->GetTime()->GetPos(); if ( m_SelectedImage != NULL && m_SelectedImage->IsInitialized()) { // Check if a the selected image is a multi-channel image. If yes, statistics // cannot be calculated currently. if ( m_SelectedImage->GetPixelType().GetNumberOfComponents() > 1 ) { std::stringstream message; message << "Multi-component images not supported."; m_Controls->m_ErrorMessageLabel->setText( message.str().c_str() ); m_Controls->m_ErrorMessageLabel->show(); this->InvalidateStatisticsTableView(); m_Controls->m_StatisticsWidgetStack->setCurrentIndex( 0 ); m_Controls->m_JSHistogram->ClearHistogram(); m_CurrentStatisticsValid = false; this->m_StatisticsUpdatePending = false; m_Controls->m_lineRadioButton->setEnabled(true); m_Controls->m_barRadioButton->setEnabled(true); m_Controls->m_InfoLabel->setText(QString("")); return; } std::stringstream maskLabel; maskLabel << maskName; if ( maskDimension > 0 ) { maskLabel << " [" << maskDimension << "D " << maskType << "]"; } m_Controls->m_SelectedMaskLabel->setText( maskLabel.str().c_str() ); // check time step validity if(m_SelectedImage->GetDimension() <= 3 && timeStep > m_SelectedImage->GetDimension(3)-1) { timeStep = m_SelectedImage->GetDimension(3)-1; } //// initialize thread and trigger it this->m_CalculationThread->SetIgnoreZeroValueVoxel( m_Controls->m_IgnoreZerosCheckbox->isChecked() ); this->m_CalculationThread->Initialize( m_SelectedImage, m_SelectedImageMask, m_SelectedPlanarFigure ); this->m_CalculationThread->SetTimeStep( timeStep ); std::stringstream message; message << "Calculating statistics..."; m_Controls->m_ErrorMessageLabel->setText( message.str().c_str() ); m_Controls->m_ErrorMessageLabel->show(); try { // Compute statistics this->m_CalculationThread->start(); } catch ( const mitk::Exception& e) { std::stringstream message; message << "" << e.GetDescription() << ""; m_Controls->m_ErrorMessageLabel->setText( message.str().c_str() ); m_Controls->m_ErrorMessageLabel->show(); this->m_StatisticsUpdatePending = false; } catch ( const std::runtime_error &e ) { // In case of exception, print error message on GUI std::stringstream message; message << "" << e.what() << ""; m_Controls->m_ErrorMessageLabel->setText( message.str().c_str() ); m_Controls->m_ErrorMessageLabel->show(); this->m_StatisticsUpdatePending = false; } catch ( const std::exception &e ) { MITK_ERROR << "Caught exception: " << e.what(); // In case of exception, print error message on GUI std::stringstream message; message << "Error! Unequal Dimensions of Image and Segmentation. No recompute possible "; m_Controls->m_ErrorMessageLabel->setText( message.str().c_str() ); m_Controls->m_ErrorMessageLabel->show(); this->m_StatisticsUpdatePending = false; } } else { this->m_StatisticsUpdatePending = false; } } void QmitkImageStatisticsView::SelectedDataModified() { if( !m_StatisticsUpdatePending ) { emit StatisticsUpdate(); } } void QmitkImageStatisticsView::NodeRemoved(const mitk::DataNode *node) { while(this->m_CalculationThread->isRunning()) // wait until thread has finished { itksys::SystemTools::Delay(100); } if (node->GetData() == m_SelectedImage) { m_SelectedImage = NULL; } } void QmitkImageStatisticsView::RequestStatisticsUpdate() { if ( !m_StatisticsUpdatePending ) { if(this->m_DataNodeSelectionChanged) { this->SelectionChanged(this->GetCurrentSelection()); } else { this->m_StatisticsUpdatePending = true; this->UpdateStatistics(); } } if (this->GetRenderWindowPart()) this->GetRenderWindowPart()->RequestUpdate(); } void QmitkImageStatisticsView::WriteStatisticsToGUI() { m_Controls->m_lineRadioButton->setEnabled(true); m_Controls->m_barRadioButton->setEnabled(true); m_Controls->m_InfoLabel->setText(QString("")); if(m_DataNodeSelectionChanged) { this->m_StatisticsUpdatePending = false; this->RequestStatisticsUpdate(); return; // stop visualization of results and calculate statistics of new selection } if ( this->m_CalculationThread->GetStatisticsUpdateSuccessFlag()) { if ( this->m_CalculationThread->GetStatisticsChangedFlag() ) { // Do not show any error messages m_Controls->m_ErrorMessageLabel->hide(); m_CurrentStatisticsValid = true; } if (m_Controls->m_barRadioButton->isChecked()) { m_Controls->m_JSHistogram->OnBarRadioButtonSelected(); } m_Controls->m_StatisticsWidgetStack->setCurrentIndex( 0 ); m_Controls->m_JSHistogram->ComputeHistogram( this->m_CalculationThread->GetTimeStepHistogram().GetPointer() ); this->FillStatisticsTableView( this->m_CalculationThread->GetStatisticsData(), this->m_CalculationThread->GetStatisticsImage()); } else { m_Controls->m_SelectedMaskLabel->setText( "None" ); m_Controls->m_ErrorMessageLabel->setText( m_CalculationThread->GetLastErrorMessage().c_str() ); m_Controls->m_ErrorMessageLabel->show(); // Clear statistics and histogram this->InvalidateStatisticsTableView(); m_Controls->m_StatisticsWidgetStack->setCurrentIndex( 0 ); //m_Controls->m_JSHistogram->clearHistogram(); m_CurrentStatisticsValid = false; // If a (non-closed) PlanarFigure is selected, display a line profile widget if ( m_SelectedPlanarFigure != NULL ) { // Check if the (closed) planar figure is out of bounds and so no image mask could be calculated--> Intensity Profile can not be calculated bool outOfBounds = false; if ( m_SelectedPlanarFigure->IsClosed() && m_SelectedImageMask == NULL) { outOfBounds = true; std::stringstream message; message << "Planar figure is outside the images bounds."; m_Controls->m_InfoLabel->setText(message.str().c_str()); } // check whether PlanarFigure is initialized const mitk::Geometry2D *planarFigureGeometry2D = m_SelectedPlanarFigure->GetGeometry2D(); if ( planarFigureGeometry2D == NULL || outOfBounds) { // Clear statistics, histogram, and GUI this->InvalidateStatisticsTableView(); m_Controls->m_StatisticsWidgetStack->setCurrentIndex( 0 ); m_Controls->m_JSHistogram->ClearHistogram(); m_CurrentStatisticsValid = false; m_Controls->m_ErrorMessageLabel->hide(); m_Controls->m_SelectedMaskLabel->setText( "None" ); this->m_StatisticsUpdatePending = false; m_Controls->m_lineRadioButton->setEnabled(true); m_Controls->m_barRadioButton->setEnabled(true); if (!outOfBounds) m_Controls->m_InfoLabel->setText(QString("")); return; } unsigned int timeStep = this->GetRenderWindowPart()->GetTimeNavigationController()->GetTime()->GetPos(); m_Controls->m_JSHistogram->SetImage(this->m_CalculationThread->GetStatisticsImage()); m_Controls->m_JSHistogram->SetPlanarFigure(m_SelectedPlanarFigure); m_Controls->m_JSHistogram->ComputeIntensityProfile(timeStep); m_Controls->m_lineRadioButton->setEnabled(false); m_Controls->m_barRadioButton->setEnabled(false); std::stringstream message; message << "Only linegraph available for an intesityprofile!"; m_Controls->m_InfoLabel->setText(message.str().c_str()); } } this->m_StatisticsUpdatePending = false; } void QmitkImageStatisticsView::FillStatisticsTableView( const mitk::ImageStatisticsCalculator::Statistics &s, const mitk::Image *image ) { if (s.MaxIndex.size()==3) { mitk::Point3D index; index[0] = s.MaxIndex[0]; index[1] = s.MaxIndex[1]; index[2] = s.MaxIndex[2]; m_SelectedImage->GetGeometry()->IndexToWorld(index, m_WorldMax); index[0] = s.MinIndex[0]; index[1] = s.MinIndex[1]; index[2] = s.MinIndex[2]; m_SelectedImage->GetGeometry()->IndexToWorld(index, m_WorldMin); } int decimals = 2; mitk::PixelType doublePix = mitk::MakeScalarPixelType< double >(); mitk::PixelType floatPix = mitk::MakeScalarPixelType< float >(); if (image->GetPixelType()==doublePix || image->GetPixelType()==floatPix) decimals = 5; this->m_Controls->m_StatisticsTable->setItem( 0, 0, new QTableWidgetItem( QString("%1").arg(s.Mean, 0, 'f', decimals) ) ); this->m_Controls->m_StatisticsTable->setItem( 0, 1, new QTableWidgetItem( QString("%1").arg(s.Sigma, 0, 'f', decimals) ) ); this->m_Controls->m_StatisticsTable->setItem( 0, 2, new QTableWidgetItem( QString("%1").arg(s.RMS, 0, 'f', decimals) ) ); QString max; max.append(QString("%1").arg(s.Max, 0, 'f', decimals)); max += " ("; for (int i=0; im_Controls->m_StatisticsTable->setItem( 0, 3, new QTableWidgetItem( max ) ); QString min; min.append(QString("%1").arg(s.Min, 0, 'f', decimals)); min += " ("; for (int i=0; im_Controls->m_StatisticsTable->setItem( 0, 4, new QTableWidgetItem( min ) ); this->m_Controls->m_StatisticsTable->setItem( 0, 5, new QTableWidgetItem( QString("%1").arg(s.N) ) ); const mitk::Geometry3D *geometry = image->GetGeometry(); if ( geometry != NULL ) { const mitk::Vector3D &spacing = image->GetGeometry()->GetSpacing(); double volume = spacing[0] * spacing[1] * spacing[2] * (double) s.N; this->m_Controls->m_StatisticsTable->setItem( 0, 6, new QTableWidgetItem( QString("%1").arg(volume, 0, 'f', decimals) ) ); } else { this->m_Controls->m_StatisticsTable->setItem( 0, 6, new QTableWidgetItem( "NA" ) ); } } void QmitkImageStatisticsView::InvalidateStatisticsTableView() { for ( unsigned int i = 0; i < 7; ++i ) { this->m_Controls->m_StatisticsTable->setItem( 0, i, new QTableWidgetItem( "NA" ) ); } } void QmitkImageStatisticsView::Activated() { } void QmitkImageStatisticsView::Deactivated() { } void QmitkImageStatisticsView::Visible() { m_Visible = true; if (m_DataNodeSelectionChanged) { if (this->IsCurrentSelectionValid()) { this->SelectionChanged(this->GetCurrentSelection()); } else { this->SelectionChanged(this->GetDataManagerSelection()); } m_DataNodeSelectionChanged = false; } } void QmitkImageStatisticsView::Hidden() { m_Visible = false; } void QmitkImageStatisticsView::SetFocus() { } diff --git a/Plugins/org.mitk.gui.qt.measurementtoolbox/src/internal/QmitkImageStatisticsViewControls.ui b/Plugins/org.mitk.gui.qt.measurementtoolbox/src/internal/QmitkImageStatisticsViewControls.ui index a6f3672629..be1d88a8a6 100644 --- a/Plugins/org.mitk.gui.qt.measurementtoolbox/src/internal/QmitkImageStatisticsViewControls.ui +++ b/Plugins/org.mitk.gui.qt.measurementtoolbox/src/internal/QmitkImageStatisticsViewControls.ui @@ -1,483 +1,489 @@ QmitkImageStatisticsViewControls true 0 0 465 800 Form 0 0 Mask: None 2 Qt::Horizontal 40 20 color: rgb(255, 0, 0); Error Message Qt::AutoText Ignore zero-valued voxels false Statistics 9 9 9 0 0 100 175 16777215 170 Qt::ScrollBarAlwaysOff Qt::ScrollBarAsNeeded true true true Qt::DotLine false false false 80 true 80 false true - true + false false 25 25 false false Mean StdDev RMS Max Min N V (mm³) Component 1 0 - + + 0 + + + 0 + + + 0 + + 0 Copy to Clipboard Qt::Horizontal 40 20 false 150 160 Histogram false - 0 + 2 0 0 - + 0 0 - + 0 - + + 0 + + + 0 + + + 0 + + 0 Copy to Clipboard Qt::Horizontal 40 20 0 0 0 50 16777215 16777215 Plot 0 20 411 31 QLayout::SetDefaultConstraint Qt::Horizontal QSizePolicy::Preferred 10 0 0 0 Use barchart true 0 0 0 0 Use linegraph Qt::Horizontal 40 20 Qt::Vertical 20 40 - - QmitkVtkHistogramWidget - QWidget -
QmitkVtkHistogramWidget.h
- 1 -
- - QmitkVtkLineProfileWidget - QWidget -
QmitkVtkLineProfileWidget.h
- 1 -
QmitkHistogramJSWidget QWidget
QmitkHistogramJSWidget.h
1
diff --git a/Plugins/org.mitk.gui.qt.meshdecimation/src/internal/QmitkMeshDecimationView.cpp b/Plugins/org.mitk.gui.qt.meshdecimation/src/internal/QmitkMeshDecimationView.cpp index a352ad3fd4..55f4d216a7 100644 --- a/Plugins/org.mitk.gui.qt.meshdecimation/src/internal/QmitkMeshDecimationView.cpp +++ b/Plugins/org.mitk.gui.qt.meshdecimation/src/internal/QmitkMeshDecimationView.cpp @@ -1,231 +1,231 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ // Blueberry #include #include // Qmitk #include "QmitkMeshDecimationView.h" #include "QmitkStdMultiWidget.h" // Qt #include #include #include // mitk #include #include #include // VTK #include #include #include const std::string QmitkMeshDecimationView::VIEW_ID = "org.mitk.views.meshdecimation"; QmitkMeshDecimationView::QmitkMeshDecimationView() : QmitkAbstractView() , m_Controls( 0 ) , m_MessageBox( 0 ) , m_MessageBoxDisplayTime( 5 ) , m_MessageBoxTimer( new QTimer(this) ) { m_MessageBoxTimer->setInterval(1000); connect(m_MessageBoxTimer, SIGNAL(timeout()), this, SLOT(MessageBoxTimer())); } QmitkMeshDecimationView::~QmitkMeshDecimationView() { } void QmitkMeshDecimationView::CreateQtPartControl( QWidget *parent ) { // build up qt view, unless already done if ( !m_Controls ) { // create GUI widgets from the Qt Designer's .ui file m_Controls = new Ui::QmitkMeshDecimationView; m_Controls->setupUi( parent ); connect((QObject*)(m_Controls->Decimate), SIGNAL(clicked()), this, SLOT(Decimate())); } } void QmitkMeshDecimationView::OnSelectionChanged(berry::IWorkbenchPart::Pointer, const QList& nodes) { this->m_Node = 0; this->DisableGui(); for( int i=0; iGetData(); if( dynamic_cast( baseData ) != 0 ) { this->m_Node = nodes.at(i); this->m_Controls->NodeLabel->setEnabled( true ); this->m_Controls->TargetReduction->setEnabled( true ); this->m_Controls->Decimate->setEnabled( true ); this->m_Controls->DecimationType->setEnabled( true ); break; } } this->UpdateNodeLabel(); } void QmitkMeshDecimationView::SetFocus() { m_Controls->NodeLabel->setFocus(); } void QmitkMeshDecimationView::DisableGui() { this->m_Controls->NodeLabel->setEnabled( false ); this->m_Controls->TargetReduction->setEnabled( false ); this->m_Controls->Decimate->setEnabled( false ); this->m_Controls->DecimationType->setEnabled( false ); } void QmitkMeshDecimationView::UpdateNodeLabel() { QString nodeLabel = "none selected"; if (this->m_Node.IsNotNull()) { vtkPolyData* polyData = static_cast(this->m_Node->GetData())->GetVtkPolyData(); nodeLabel = QString::fromStdString( this->m_Node->GetName() ); nodeLabel.append(" ("); nodeLabel.append( QString("%1").arg( polyData->GetNumberOfCells() ) ); nodeLabel.append(" cells)"); } this->m_Controls->NodeLabel->setText( nodeLabel ); } void QmitkMeshDecimationView::Decimate() { if (this->m_Node.IsNotNull()) { this->WaitCursorOn(); QString error; try { vtkPolyData* polyData = static_cast(this->m_Node->GetData())->GetVtkPolyData(); int startingNumberOfCells = polyData->GetNumberOfCells(); if( startingNumberOfCells == 0 ) throw std::logic_error("Could not reduce Mesh since it is already empty."); double targetReduction = static_cast(this->m_Controls->TargetReduction->value()) / 100.0; vtkPolyData* newPolyData = 0; if( this->m_Controls->DecimationType->currentText() == "DecimatePro" ) { vtkSmartPointer decimator = vtkSmartPointer::New(); - decimator->SetInput( polyData ); + decimator->SetInputData( polyData ); decimator->SetTargetReduction( targetReduction ); decimator->SetPreserveTopology( 1 ); decimator->Update(); newPolyData = decimator->GetOutput(); } else { vtkSmartPointer decimator = vtkSmartPointer::New(); - decimator->SetInput( polyData ); + decimator->SetInputData( polyData ); decimator->SetTargetReduction( targetReduction ); decimator->Update(); newPolyData = decimator->GetOutput(); } if( newPolyData != 0 ) { static_cast(this->m_Node->GetData())->SetVtkPolyData(newPolyData); this->m_Node->Update(); this->UpdateNodeLabel(); mitk::RenderingManager::GetInstance()->RequestUpdateAll(); } int endingNumberOfCells = newPolyData->GetNumberOfCells(); int reducedCells = startingNumberOfCells - endingNumberOfCells; QString message; if( reducedCells == 0 ) message = "Decimation was not able to reduce any more cells from Mesh."; else message = QString("Decimation successful. %1 cells removed").arg(reducedCells); this->WaitCursorOff(); this->ShowAutoCloseMessageDialog(message); } catch(std::exception& e) { this->WaitCursorOff(); error = QString::fromStdString(e.what()); } catch(...) { this->WaitCursorOff(); error = "An unknown error occured. Please report error at bugs.mitk.org."; } if( !error.isEmpty() ) this->ShowAutoCloseErrorDialog(error); } else this->DisableGui(); } void QmitkMeshDecimationView::MessageBoxTimer() { m_MessageBoxDisplayTime--; QString text = m_MessageBoxText; text.append( QString(" (Will close in %1 seconds)").arg(m_MessageBoxDisplayTime) ); m_MessageBox->setText( text ); if( m_MessageBoxDisplayTime == 0 ) { m_MessageBox->accept(); } } void QmitkMeshDecimationView::ShowAutoCloseErrorDialog( const QString& error ) { m_MessageBox = new QMessageBox(QMessageBox::Warning, "Warning", error, QMessageBox::Ok ); m_MessageBoxDisplayTime = 5; m_MessageBoxText = error; this->MessageBoxTimer(); m_MessageBoxTimer->start(); m_MessageBox->exec(); m_MessageBoxTimer->stop(); delete m_MessageBox; m_MessageBox = 0; } void QmitkMeshDecimationView::ShowAutoCloseMessageDialog( const QString& message ) { m_MessageBox = new QMessageBox(QMessageBox::Information, "Information", message, QMessageBox::Ok ); m_MessageBoxDisplayTime = 5; m_MessageBoxText = message; this->MessageBoxTimer(); m_MessageBoxTimer->start(); m_MessageBox->exec(); m_MessageBoxTimer->stop(); delete m_MessageBox; m_MessageBox = 0; } diff --git a/Plugins/org.mitk.gui.qt.moviemaker/src/internal/QmitkMovieMaker.cpp b/Plugins/org.mitk.gui.qt.moviemaker/src/internal/QmitkMovieMaker.cpp index ffe8ee2ff4..0d78c15e3c 100644 --- a/Plugins/org.mitk.gui.qt.moviemaker/src/internal/QmitkMovieMaker.cpp +++ b/Plugins/org.mitk.gui.qt.moviemaker/src/internal/QmitkMovieMaker.cpp @@ -1,769 +1,769 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "QmitkMovieMaker.h" //#include "QmitkMovieMakerControls.h" #include "QmitkStepperAdapter.h" #include "QmitkStdMultiWidget.h" #include "QmitkMovieMaker.h" //#include "QmitkMovieMakerControls.h" #include "QmitkStepperAdapter.h" #include "QmitkStdMultiWidget.h" #include "mitkVtkPropRenderer.h" #include "mitkGlobalInteraction.h" #include #include #include #include #include #include #include #include #include #include "qapplication.h" #include "vtkImageWriter.h" #include "vtkJPEGWriter.h" #include "vtkPNGWriter.h" #include "vtkRenderLargeImage.h" #include "vtkRenderWindowInteractor.h" #include "vtkRenderer.h" #include "vtkTestUtilities.h" #include #include "vtkMitkRenderProp.h" #include #include #include "vtkRenderWindowInteractor.h" #include QmitkMovieMaker::QmitkMovieMaker(QObject *parent, const char * /*name*/) : QmitkFunctionality(), m_Controls(NULL), m_StepperAdapter(NULL), m_FocusManagerCallback(0), m_Looping(true), m_Direction(0), m_Aspect(0) { parentWidget = parent; m_Timer = new QTimer(this); m_Time = new QTime(); m_FocusManagerCallback = MemberCommand::New(); m_FocusManagerCallback->SetCallbackFunction(this, &QmitkMovieMaker::FocusChange); m_movieGenerator = mitk::MovieGenerator::New(); if (m_movieGenerator.IsNull()) { MITK_ERROR << "Either mitk::MovieGenerator is not implemented for your"; MITK_ERROR << " platform or an error occurred during"; MITK_ERROR << " mitk::MovieGenerator::New()" ; } } QmitkMovieMaker::~QmitkMovieMaker() { delete m_StepperAdapter; delete m_Timer; delete m_Time; //delete m_RecordingRenderer; } mitk::BaseController* QmitkMovieMaker::GetSpatialController() { mitk::BaseRenderer* focusedRenderer = mitk::GlobalInteraction::GetInstance()->GetFocus(); if (mitk::BaseRenderer::GetInstance(GetActiveStdMultiWidget()->mitkWidget1->GetRenderWindow()) == focusedRenderer) { return GetActiveStdMultiWidget()->mitkWidget1->GetController(); } else if (mitk::BaseRenderer::GetInstance( GetActiveStdMultiWidget()->mitkWidget2->GetRenderWindow()) == focusedRenderer) { return GetActiveStdMultiWidget()->mitkWidget2->GetController(); } else if (mitk::BaseRenderer::GetInstance( GetActiveStdMultiWidget()->mitkWidget3->GetRenderWindow()) == focusedRenderer) { return GetActiveStdMultiWidget()->mitkWidget3->GetController(); } else if (mitk::BaseRenderer::GetInstance( GetActiveStdMultiWidget()->mitkWidget4->GetRenderWindow()) == focusedRenderer) { return GetActiveStdMultiWidget()->mitkWidget4->GetController(); } return GetActiveStdMultiWidget()->mitkWidget4->GetController(); } mitk::BaseController* QmitkMovieMaker::GetTemporalController() { return GetActiveStdMultiWidget()->GetTimeNavigationController(); } void QmitkMovieMaker::CreateConnections() { if (m_Controls) { // start / pause / stop playing connect((QObject*) m_Controls->btnPlay, SIGNAL(clicked()), (QObject*) this, SLOT(StartPlaying())); connect((QObject*) m_Controls->btnPause, SIGNAL(clicked()), this, SLOT(PausePlaying())); connect((QObject*) m_Controls->btnStop, SIGNAL(clicked()), this, SLOT(StopPlaying())); connect((QObject*) m_Controls->rbtnForward, SIGNAL(clicked()), this, SLOT(RBTNForward())); connect((QObject*) m_Controls->rbtnBackward, SIGNAL(clicked()), this, SLOT(RBTNBackward())); connect((QObject*) m_Controls->rbtnPingPong, SIGNAL(clicked()), this, SLOT(RBTNPingPong())); // radio button group: forward, backward, ping-pong connect( this, SIGNAL(SwitchDirection(int)), this, SLOT(SetDirection(int)) ); // radio button group: spatial, temporal connect((QObject*) m_Controls->rbtnSpatial, SIGNAL(clicked()), this, SLOT(RBTNSpatial())); connect((QObject*) m_Controls->rbtnTemporal, SIGNAL(clicked()), this, SLOT(RBTNTemporal())); connect((QObject*) m_Controls->rbtnCombined, SIGNAL(clicked()), this, SLOT(RBTNCombined())); connect( this, SIGNAL(SwitchAspect(int)), this, SLOT(SetAspect(int)) ); // stepper window selection connect((QObject*) (m_Controls->cmbSelectedStepperWindow), SIGNAL ( activated ( int) ), (QObject*) this, SLOT ( SetStepperWindow (int) ) ); // recording window selection connect((QObject*) (m_Controls->cmbSelectedRecordingWindow), SIGNAL ( activated ( int) ), (QObject*) this, SLOT ( SetRecordingWindow (int) ) ); // advance the animation // every timer tick connect((QObject*) m_Timer, SIGNAL(timeout()), this, SLOT(AdvanceAnimation())); // movie generation // when the movie button is clicked connect((QObject*) m_Controls->btnMovie, SIGNAL(clicked()), this, SLOT(GenerateMovie())); connect((QObject*) m_Controls->btnScreenshot, SIGNAL(clicked()), this, SLOT( GenerateScreenshot())); connect((QObject*) m_Controls->m_HRScreenshot, SIGNAL(clicked()), this, SLOT( GenerateHR3DScreenshot())); // blocking of ui elements during movie generation connect((QObject*) this, SIGNAL(StartBlockControls()), (QObject*) this, SLOT(BlockControls())); connect((QObject*) this, SIGNAL(EndBlockControls()), (QObject*) this, SLOT(UnBlockControls())); connect((QObject*) this, SIGNAL(EndBlockControlsMovieDeactive()), (QObject*) this, SLOT( UnBlockControlsMovieDeactive())); // allow for change of spatialtime relation connect((QObject*) m_Controls->spatialTimeRelation, SIGNAL(valueChanged ( int ) ), this, SLOT( DeleteMStepper() ) ); m_Controls->btnScreenshot->setVisible(false); m_Controls->m_HRScreenshot->setVisible(false); } } void QmitkMovieMaker::Activated() { QmitkFunctionality::Activated(); // create a member command that will be executed from the observer itk::SimpleMemberCommand::Pointer stepperChangedCommand; stepperChangedCommand = itk::SimpleMemberCommand::New(); // set the callback function of the member command stepperChangedCommand->SetCallbackFunction(this, &QmitkMovieMaker::UpdateGUI); // add an observer to the data tree node pointer connected to the above member command MITK_INFO << "Add observer on insertion point node in NavigationPathController::AddObservers"; m_StepperObserverTag = this->GetTemporalController()->GetTime()->AddObserver( itk::ModifiedEvent(), stepperChangedCommand); m_FocusManagerObserverTag = mitk::GlobalInteraction::GetInstance()->GetFocusManager()->AddObserver(mitk::FocusEvent(), m_FocusManagerCallback); this->UpdateGUI(); // Initialize steppers etc. this->FocusChange(); } void QmitkMovieMaker::Deactivated() { QmitkFunctionality::Deactivated(); this->GetTemporalController()->GetTime()->RemoveObserver(m_StepperObserverTag); mitk::GlobalInteraction::GetInstance()->GetFocusManager()->RemoveObserver( m_FocusManagerObserverTag); // remove (if tag is invalid, nothing is removed) } void QmitkMovieMaker::FocusChange() { mitk::Stepper *stepper = this->GetAspectStepper(); m_StepperAdapter->SetStepper(stepper); // Make the stepper movement non-inverted stepper->InverseDirectionOff(); // Set stepping direction and aspect (spatial / temporal) for new stepper this->UpdateLooping(); this->UpdateDirection(); // Set newly focused window as active in "Selected Window" combo box const mitk::RenderingManager::RenderWindowVector rwv = mitk::RenderingManager::GetInstance()->GetAllRegisteredRenderWindows(); int i; mitk::RenderingManager::RenderWindowVector::const_iterator iter; for (iter = rwv.begin(), i = 0; iter != rwv.end(); ++iter, ++i) { mitk::BaseRenderer* focusedRenderer = mitk::GlobalInteraction::GetInstance()->GetFocusManager()->GetFocused(); if (focusedRenderer == mitk::BaseRenderer::GetInstance((*iter))) { m_Controls->cmbSelectedStepperWindow->setCurrentIndex(i); // this->cmbSelectedStepperWindow_activated(i); this->SetStepperWindow(i); m_Controls->cmbSelectedRecordingWindow->setCurrentIndex(i); // this->cmbSelectedRecordWindow_activated(i); this->SetRecordingWindow(i); break; } } } void QmitkMovieMaker::AdvanceAnimation() { // This method is called when a timer timeout occurs. It increases the // stepper value according to the elapsed time and the stepper interval. // Note that a screen refresh is not forced, but merely requested, and may // occur only after more calls to AdvanceAnimation(). mitk::Stepper* stepper = this->GetAspectStepper(); m_StepperAdapter->SetStepper(stepper); int elapsedTime = m_Time->elapsed(); m_Time->restart(); static double increment = 0.0; increment = increment - static_cast (increment); increment += elapsedTime * stepper->GetSteps() / (m_Controls->spnDuration->value() * 1000.0); int i, n = static_cast (increment); for (i = 0; i < n; ++i) { stepper->Next(); } } void QmitkMovieMaker::RenderSlot() { int *i = widget->GetRenderWindow()->GetSize(); m_PropRenderer->Resize(i[0], i[1]); widget->GetRenderWindow()->Render(); } void QmitkMovieMaker::PausePlaying() { m_Controls->slidAngle->setDisabled(false); m_Controls->btnMovie->setEnabled(true); m_Controls->btnPlay->setEnabled(true); m_Controls->btnScreenshot->setEnabled(true); m_Timer->stop(); m_Controls->btnPlay->setHidden(false); m_Controls->btnPause->setHidden(true); if (m_movieGenerator.IsNull()) m_Controls->btnMovie->setEnabled(false); } void QmitkMovieMaker::StopPlaying() { m_Controls->slidAngle->setDisabled(false); m_Controls->btnMovie->setEnabled(true); m_Controls->btnPlay->setEnabled(true); m_Controls->btnScreenshot->setEnabled(true); m_Controls->btnPlay->setHidden(false); m_Controls->btnPause->setHidden(true); m_Timer->stop(); switch (m_Direction) { case 0: case 2: this->GetAspectStepper()->First(); break; case 1: this->GetAspectStepper()->Last(); break; } // Reposition slider GUI element m_StepperAdapter->SetStepper(this->GetAspectStepper()); if (m_movieGenerator.IsNull()) m_Controls->btnMovie->setEnabled(false); } void QmitkMovieMaker::SetLooping(bool looping) { m_Looping = looping; this->UpdateLooping(); } void QmitkMovieMaker::SetDirection(int direction) { m_Direction = direction; this->UpdateDirection(); } void QmitkMovieMaker::SetAspect(int aspect) { m_Aspect = aspect; m_StepperAdapter->SetStepper(this->GetAspectStepper()); this->UpdateLooping(); this->UpdateDirection(); } void QmitkMovieMaker::SetStepperWindow(int window) { // Set newly selected window / renderer as focused const mitk::RenderingManager::RenderWindowVector rwv = mitk::RenderingManager::GetInstance()->GetAllRegisteredRenderWindows(); //Delete MultiStepper DeleteMStepper(); int i; mitk::RenderingManager::RenderWindowVector::const_iterator iter; for (iter = rwv.begin(), i = 0; iter != rwv.end(); ++iter, ++i) { if (i == window) { mitk::GlobalInteraction::GetInstance()->GetFocusManager() ->SetFocused( mitk::BaseRenderer::GetInstance((*iter))); break; } } } void QmitkMovieMaker::SetRecordingWindow(int window) { // Set newly selected window for recording const mitk::RenderingManager::RenderWindowVector rwv = mitk::RenderingManager::GetInstance()->GetAllRegisteredRenderWindows(); //Delete MultiStepper DeleteMStepper(); int i; mitk::RenderingManager::RenderWindowVector::const_iterator iter; for (iter = rwv.begin(), i = 0; iter != rwv.end(); ++iter, ++i) { if (i == window) { m_RecordingRenderer = mitk::BaseRenderer::GetInstance((*iter)); break; } } } void QmitkMovieMaker::UpdateLooping() { this->GetAspectStepper()->SetAutoRepeat(m_Looping); } void QmitkMovieMaker::UpdateDirection() { mitk::Stepper* stepper = this->GetAspectStepper(); switch (m_Direction) { case 0: stepper->InverseDirectionOff(); stepper->PingPongOff(); break; case 1: stepper->InverseDirectionOn(); stepper->PingPongOff(); break; case 2: stepper->PingPongOn(); break; } } mitk::Stepper* QmitkMovieMaker::GetAspectStepper() { if (m_Aspect == 0) { m_Stepper = NULL; return this->GetSpatialController()->GetSlice(); } else if (m_Aspect == 1) { m_Stepper = NULL; return this->GetTemporalController()->GetTime(); } else if (m_Aspect == 2) { if (m_Stepper.IsNull()) { int rel = m_Controls->spatialTimeRelation->value(); int timeRepeat = 1; int sliceRepeat = 1; if (rel < 0) { sliceRepeat = -rel; } else if (rel > 0) { timeRepeat = rel; } m_Stepper = mitk::MultiStepper::New(); m_Stepper->AddStepper(this->GetSpatialController()->GetSlice(), sliceRepeat); m_Stepper->AddStepper(this->GetTemporalController()->GetTime(), timeRepeat); } return m_Stepper.GetPointer(); } else { // should never get here return 0; } } void QmitkMovieMaker::GenerateMovie() { emit StartBlockControls(); // provide the movie generator with the stepper and rotate the camera each step if (m_movieGenerator.IsNotNull()) { m_movieGenerator->SetStepper(this->GetAspectStepper()); m_movieGenerator->SetRenderer(m_RecordingRenderer); m_movieGenerator->SetFrameRate(static_cast (360 / (m_Controls->spnDuration->value()))); // QString movieFileName = QFileDialog::getSaveFileName( QString::null, "Movie (*.avi)", 0, "movie file dialog", "Choose a file name" ); QString movieFileName = QFileDialog::getSaveFileName(0, "Choose a file name", QString::null, "Movie (*.avi)", 0, 0); if (movieFileName.isEmpty() == false) { mitk::RenderingManager::GetInstance()->RequestUpdateAll(); m_movieGenerator->SetFileName(movieFileName.toAscii()); m_movieGenerator->WriteMovie(); } emit EndBlockControls(); } else { MITK_ERROR << "Either mitk::MovieGenerator is not implemented for your"; MITK_ERROR << " platform or an error occurred during"; MITK_ERROR << " mitk::MovieGenerator::New()"; emit EndBlockControlsMovieDeactive(); } } void QmitkMovieMaker::GenerateScreenshot() { emit StartBlockControls(); QString fileName = QFileDialog::getSaveFileName(NULL, "Save screenshot to...", QDir::currentPath(), "JPEG file (*.jpg);;PNG file (*.png)"); vtkRenderer* renderer = mitk::GlobalInteraction::GetInstance()->GetFocus()->GetVtkRenderer(); if (renderer == NULL) return; this->TakeScreenshot(renderer, 1, fileName); if (m_movieGenerator.IsNotNull()) emit EndBlockControls(); else emit EndBlockControlsMovieDeactive(); } void QmitkMovieMaker::GenerateHR3DScreenshot() { emit StartBlockControls(); QString fileName = QFileDialog::getSaveFileName(NULL, "Save screenshot to...", QDir::currentPath(), "JPEG file (*.jpg);;PNG file (*.png)"); // only works correctly for 3D RenderWindow vtkRenderer* renderer = m_MultiWidget->mitkWidget4->GetRenderer()->GetVtkRenderer(); if (renderer == NULL) return; this->TakeScreenshot(renderer, 4, fileName); if (m_movieGenerator.IsNotNull()) emit EndBlockControls(); else emit EndBlockControlsMovieDeactive(); } void QmitkMovieMaker::UpdateGUI() { int bla = this->GetTemporalController()->GetTime()->GetSteps(); if (bla < 2) { m_Controls->rbtnTemporal->setEnabled(false); m_Controls->rbtnCombined->setEnabled(false); m_Controls->spatialTimeRelation->setEnabled(false); } else { m_Controls->rbtnTemporal->setEnabled(true); m_Controls->rbtnCombined->setEnabled(true); m_Controls->spatialTimeRelation->setEnabled(true); } } void QmitkMovieMaker::DataStorageChanged() { // UpdateGUI(); } void QmitkMovieMaker::CreateQtPartControl(QWidget *parent) { if (!m_Controls) { m_Controls = new Ui::QmitkMovieMakerControls; m_Controls->setupUi(parent); m_StepperAdapter = new QmitkStepperAdapter((QObject*) m_Controls->slidAngle, this->GetSpatialController()->GetSlice(), "AngleStepperToMovieMakerFunctionality"); // Initialize "Selected Window" combo box const mitk::RenderingManager::RenderWindowVector rwv = mitk::RenderingManager::GetInstance()->GetAllRegisteredRenderWindows(); mitk::RenderingManager::RenderWindowVector::const_iterator iter; unsigned int i = 0; for (iter = rwv.begin(); iter != rwv.end(); ++iter) { QString name(mitk::BaseRenderer::GetInstance((*iter))->GetName()); if (name=="stdmulti.widget1") { m_Controls->cmbSelectedStepperWindow->insertItem(i, "Axial"); m_Controls->cmbSelectedRecordingWindow->insertItem(i++, "Axial"); } else if (name=="stdmulti.widget2") { m_Controls->cmbSelectedStepperWindow->insertItem(i, "Sagittal"); m_Controls->cmbSelectedRecordingWindow->insertItem(i++, "Sagittal"); } else if (name=="stdmulti.widget3") { m_Controls->cmbSelectedStepperWindow->insertItem(i, "Coronal"); m_Controls->cmbSelectedRecordingWindow->insertItem(i++, "Coronal"); } else if (name=="stdmulti.widget4") { m_Controls->cmbSelectedStepperWindow->insertItem(i, "3D Window"); m_Controls->cmbSelectedRecordingWindow->insertItem(i++, "3D Window"); } else { m_Controls->cmbSelectedStepperWindow->insertItem(i, name); m_Controls->cmbSelectedRecordingWindow->insertItem(i++, name); } } m_Controls->btnPause->setHidden(true); if (m_movieGenerator.IsNull()) m_Controls->btnMovie->setEnabled(false); } this->CreateConnections(); } void QmitkMovieMaker::StartPlaying() { m_Controls->slidAngle->setDisabled(true); m_Controls->btnMovie->setEnabled(false); m_Controls->btnPlay->setEnabled(false); m_Controls->btnScreenshot->setEnabled(false); // Restart timer with 5 msec interval - this should be fine-grained enough // even for high display refresh frequencies m_Timer->start(5); m_Time->restart(); m_Controls->btnPlay->setHidden(true); m_Controls->btnPause->setHidden(false); if (m_movieGenerator.IsNull()) m_Controls->btnMovie->setEnabled(false); } void QmitkMovieMaker::RBTNForward() { emit SwitchDirection(0); } void QmitkMovieMaker::RBTNBackward() { emit SwitchDirection(1); } void QmitkMovieMaker::RBTNPingPong() { emit SwitchDirection(2); } void QmitkMovieMaker::RBTNSpatial() { emit SwitchAspect(0); } void QmitkMovieMaker::RBTNTemporal() { emit SwitchAspect(1); } void QmitkMovieMaker::RBTNCombined() { emit SwitchAspect(2); } void QmitkMovieMaker::BlockControls() { BlockControls(true); } void QmitkMovieMaker::UnBlockControls() { BlockControls(false); } void QmitkMovieMaker::UnBlockControlsMovieDeactive() { BlockControls(false); m_Controls->btnMovie->setEnabled(false); } void QmitkMovieMaker::BlockControls(bool blocked) { m_Controls->slidAngle->setDisabled(blocked); m_Controls->spnDuration->setEnabled(!blocked); m_Controls->btnPlay->setEnabled(!blocked); m_Controls->btnMovie->setEnabled(!blocked); m_Controls->btnScreenshot->setEnabled(!blocked); } void QmitkMovieMaker::StdMultiWidgetAvailable(QmitkStdMultiWidget& stdMultiWidget) { m_MultiWidget = &stdMultiWidget; m_Parent->setEnabled(true); } void QmitkMovieMaker::StdMultiWidgetNotAvailable() { m_MultiWidget = NULL; m_Parent->setEnabled(false); } void QmitkMovieMaker::TakeScreenshot(vtkRenderer* renderer, unsigned int magnificationFactor, QString fileName) { if ((renderer == NULL) ||(magnificationFactor < 1) || fileName.isEmpty()) return; bool doubleBuffering( renderer->GetRenderWindow()->GetDoubleBuffer() ); renderer->GetRenderWindow()->DoubleBufferOff(); vtkImageWriter* fileWriter; QFileInfo fi(fileName); QString suffix = fi.suffix(); if (suffix.compare("png", Qt::CaseInsensitive) == 0) { fileWriter = vtkPNGWriter::New(); } else // default is jpeg { vtkJPEGWriter* w = vtkJPEGWriter::New(); w->SetQuality(100); w->ProgressiveOff(); fileWriter = w; } vtkRenderLargeImage* magnifier = vtkRenderLargeImage::New(); magnifier->SetInput(renderer); magnifier->SetMagnification(magnificationFactor); //magnifier->Update(); - fileWriter->SetInput(magnifier->GetOutput()); + fileWriter->SetInputConnection(magnifier->GetOutputPort()); fileWriter->SetFileName(fileName.toLatin1()); // vtkRenderLargeImage has problems with different layers, therefore we have to // temporarily deactivate all other layers. // we set the background to white, because it is nicer than black... double oldBackground[3]; renderer->GetBackground(oldBackground); double white[] = {1.0, 1.0, 1.0}; renderer->SetBackground(white); m_MultiWidget->DisableColoredRectangles(); m_MultiWidget->DisableDepartmentLogo(); m_MultiWidget->DisableGradientBackground(); m_MultiWidget->mitkWidget1->ActivateMenuWidget( false ); m_MultiWidget->mitkWidget2->ActivateMenuWidget( false ); m_MultiWidget->mitkWidget3->ActivateMenuWidget( false ); m_MultiWidget->mitkWidget4->ActivateMenuWidget( false ); fileWriter->Write(); fileWriter->Delete(); m_MultiWidget->mitkWidget1->ActivateMenuWidget( true ); m_MultiWidget->mitkWidget2->ActivateMenuWidget( true ); m_MultiWidget->mitkWidget3->ActivateMenuWidget( true ); m_MultiWidget->mitkWidget4->ActivateMenuWidget( true ); m_MultiWidget->EnableColoredRectangles(); m_MultiWidget->EnableDepartmentLogo(); m_MultiWidget->EnableGradientBackground(); renderer->SetBackground(oldBackground); renderer->GetRenderWindow()->SetDoubleBuffer(doubleBuffering); } void QmitkMovieMaker::DeleteMStepper() { m_Stepper = NULL; UpdateLooping(); } diff --git a/Plugins/org.mitk.gui.qt.moviemaker/src/internal/QmitkScreenshotMaker.cpp b/Plugins/org.mitk.gui.qt.moviemaker/src/internal/QmitkScreenshotMaker.cpp index 3ce85e0448..b6c63fdfcf 100644 --- a/Plugins/org.mitk.gui.qt.moviemaker/src/internal/QmitkScreenshotMaker.cpp +++ b/Plugins/org.mitk.gui.qt.moviemaker/src/internal/QmitkScreenshotMaker.cpp @@ -1,443 +1,443 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "QmitkScreenshotMaker.h" //#include "QmitkMovieMakerControls.h" #include "QmitkStepperAdapter.h" #include "QmitkStdMultiWidget.h" #include "mitkVtkPropRenderer.h" #include "mitkGlobalInteraction.h" #include #include #include #include #include #include #include #include #include #include #include #include "qapplication.h" #include "vtkImageWriter.h" #include "vtkJPEGWriter.h" #include "vtkPNGWriter.h" #include "vtkRenderLargeImage.h" #include "vtkRenderWindowInteractor.h" #include "vtkRenderer.h" #include "vtkTestUtilities.h" #include #include "vtkMitkRenderProp.h" #include #include #include "vtkRenderWindowInteractor.h" #include #include "mitkSliceNavigationController.h" #include "mitkPlanarFigure.h" QmitkScreenshotMaker::QmitkScreenshotMaker(QObject *parent, const char * /*name*/) : QmitkFunctionality(), m_Controls(NULL), m_SelectedNode(0), m_BackgroundColor(QColor(0,0,0)) { parentWidget = parent; } QmitkScreenshotMaker::~QmitkScreenshotMaker() { } void QmitkScreenshotMaker::CreateConnections() { if (m_Controls) { connect((QObject*) m_Controls->m_AllViews, SIGNAL(clicked()), (QObject*) this, SLOT(GenerateMultiplanar3DHighresScreenshot())); connect((QObject*) m_Controls->m_View1, SIGNAL(clicked()), (QObject*) this, SLOT(View1())); connect((QObject*) m_Controls->m_View2, SIGNAL(clicked()), (QObject*) this, SLOT(View2())); connect((QObject*) m_Controls->m_View3, SIGNAL(clicked()), (QObject*) this, SLOT(View3())); connect((QObject*) m_Controls->m_Shot, SIGNAL(clicked()), (QObject*) this, SLOT(GenerateMultiplanarScreenshots())); connect((QObject*) m_Controls->m_BackgroundColor, SIGNAL(clicked()), (QObject*) this, SLOT(SelectBackgroundColor())); connect((QObject*) m_Controls->btnScreenshot, SIGNAL(clicked()), this, SLOT(GenerateScreenshot())); connect((QObject*) m_Controls->m_HRScreenshot, SIGNAL(clicked()), this, SLOT(Generate3DHighresScreenshot())); QString styleSheet = "background-color:rgb(0,0,0)"; m_Controls->m_BackgroundColor->setStyleSheet(styleSheet); } } void QmitkScreenshotMaker::Activated() { QmitkFunctionality::Activated(); } void QmitkScreenshotMaker::Deactivated() { QmitkFunctionality::Deactivated(); } void QmitkScreenshotMaker::GenerateScreenshot() { if (m_LastFile.size()==0) m_LastFile = QDir::currentPath()+"/screenshot.png"; QString fileName = QFileDialog::getSaveFileName(NULL, "Save screenshot to...", m_LastFile, "PNG file (*.png);;JPEG file (*.jpg)"); if (fileName.size()>0) m_LastFile = fileName; vtkRenderer* renderer = mitk::GlobalInteraction::GetInstance()->GetFocus()->GetVtkRenderer(); if (renderer == NULL) return; this->TakeScreenshot(renderer, 1, fileName); } void QmitkScreenshotMaker::GenerateMultiplanarScreenshots() { if (m_LastPath.size()==0) m_LastPath = QDir::currentPath(); QString filePath = QFileDialog::getExistingDirectory(NULL, "Save screenshots to...", m_LastPath); if (filePath.size()>0) m_LastPath = filePath; if( filePath.isEmpty() ) { return; } //emit StartBlockControls(); mitk::DataNode* n; n = this->m_MultiWidget->GetWidgetPlane1(); if(n) { n->SetProperty( "color", mitk::ColorProperty::New( 1,1,1 ) ); } n = this->m_MultiWidget->GetWidgetPlane2(); if(n) { n->SetProperty( "color", mitk::ColorProperty::New( 1,1,1 ) ); } n = this->m_MultiWidget->GetWidgetPlane3(); if(n) { n->SetProperty( "color", mitk::ColorProperty::New( 1,1,1 ) ); } QString fileName = "/axial.png"; int c = 1; while (QFile::exists(filePath+fileName)) { fileName = QString("/axial_"); fileName += QString::number(c); fileName += ".png"; c++; } vtkRenderer* renderer = m_MultiWidget->mitkWidget1->GetRenderer()->GetVtkRenderer(); if (renderer != NULL) this->TakeScreenshot(renderer, 1, filePath+fileName); fileName = "/sagittal.png"; c = 1; while (QFile::exists(filePath+fileName)) { fileName = QString("/sagittal_"); fileName += QString::number(c); fileName += ".png"; c++; } renderer = m_MultiWidget->mitkWidget2->GetRenderer()->GetVtkRenderer(); if (renderer != NULL) this->TakeScreenshot(renderer, 1, filePath+fileName); fileName = "/coronal.png"; c = 1; while (QFile::exists(filePath+fileName)) { fileName = QString("/coronal_"); fileName += QString::number(c); fileName += ".png"; c++; } renderer = m_MultiWidget->mitkWidget3->GetRenderer()->GetVtkRenderer(); if (renderer != NULL) this->TakeScreenshot(renderer, 1, filePath+fileName); n = this->m_MultiWidget->GetWidgetPlane1(); if(n) { n->SetProperty( "color", mitk::ColorProperty::New( 1,0,0 ) ); } n = this->m_MultiWidget->GetWidgetPlane2(); if(n) { n->SetProperty( "color", mitk::ColorProperty::New( 0,1,0 ) ); } n = this->m_MultiWidget->GetWidgetPlane3(); if(n) { n->SetProperty( "color", mitk::ColorProperty::New( 0,0,1 ) ); } } void QmitkScreenshotMaker::Generate3DHighresScreenshot() { if (m_LastFile.size()==0) m_LastFile = QDir::currentPath()+"/3D_screenshot.png"; QString fileName = QFileDialog::getSaveFileName(NULL, "Save screenshot to...", m_LastFile, "PNG file (*.png);;JPEG file (*.jpg)"); if (fileName.size()>0) m_LastFile = fileName; GenerateHR3DAtlasScreenshots(fileName); } void QmitkScreenshotMaker::GenerateMultiplanar3DHighresScreenshot() { if (m_LastPath.size()==0) m_LastPath = QDir::currentPath(); QString filePath = QFileDialog::getExistingDirectory( NULL, "Save screenshots to...", m_LastPath); if (filePath.size()>0) m_LastPath = filePath; if( filePath.isEmpty() ) { return; } QString fileName = "/3D_View1.png"; int c = 1; while (QFile::exists(filePath+fileName)) { fileName = QString("/3D_View1_"); fileName += QString::number(c); fileName += ".png"; c++; } GetCam()->Azimuth( -7.5 ); GetCam()->Roll(-4); GenerateHR3DAtlasScreenshots(filePath+fileName); GetCam()->Roll(4); fileName = "/3D_View2.png"; c = 1; while (QFile::exists(filePath+fileName)) { fileName = QString("/3D_View2_"); fileName += QString::number(c); fileName += ".png"; c++; } GetCam()->Azimuth( 90 ); GetCam()->Elevation( 4 ); GenerateHR3DAtlasScreenshots(filePath+fileName); fileName = "/3D_View3.png"; c = 1; while (QFile::exists(filePath+fileName)) { fileName = QString("/3D_View3_"); fileName += QString::number(c); fileName += ".png"; c++; } GetCam()->Elevation( 90 ); GetCam()->Roll( -2.5 ); GenerateHR3DAtlasScreenshots(filePath+fileName); } void QmitkScreenshotMaker::GenerateHR3DAtlasScreenshots(QString fileName) { // only works correctly for 3D RenderWindow vtkRenderer* renderer = m_MultiWidget->mitkWidget4->GetRenderer()->GetVtkRenderer(); if (renderer == NULL) return; this->TakeScreenshot(renderer, this->m_Controls->m_MagFactor->text().toFloat(), fileName); } vtkCamera* QmitkScreenshotMaker::GetCam() { mitk::BaseRenderer* renderer = mitk::BaseRenderer::GetInstance(GetActiveStdMultiWidget()->mitkWidget4->GetRenderWindow()); vtkCamera* cam = 0; const mitk::VtkPropRenderer *propRenderer = dynamic_cast( renderer ); if (propRenderer) { // get vtk renderer vtkRenderer* vtkrenderer = propRenderer->GetVtkRenderer(); if (vtkrenderer) { // get vtk camera vtkCamera* vtkcam = vtkrenderer->GetActiveCamera(); if (vtkcam) { // vtk smart pointer handling cam = vtkcam; cam->Register( NULL ); } } } return cam; } void QmitkScreenshotMaker::View1() { GetCam()->Elevation( 45 ); mitk::RenderingManager::GetInstance()->RequestUpdateAll(); } void QmitkScreenshotMaker::View2() { GetCam()->Azimuth(45); mitk::RenderingManager::GetInstance()->RequestUpdateAll(); } void QmitkScreenshotMaker::View3() { GetCam()->Roll(45); mitk::RenderingManager::GetInstance()->RequestUpdateAll(); } void QmitkScreenshotMaker::OnSelectionChanged( std::vector nodes ) { if(nodes.size()) m_SelectedNode = nodes[0]; } void QmitkScreenshotMaker::CreateQtPartControl(QWidget *parent) { if (!m_Controls) { m_Controls = new Ui::QmitkScreenshotMakerControls; m_Controls->setupUi(parent); // Initialize "Selected Window" combo box const mitk::RenderingManager::RenderWindowVector rwv = mitk::RenderingManager::GetInstance()->GetAllRegisteredRenderWindows(); } this->CreateConnections(); } void QmitkScreenshotMaker::StdMultiWidgetAvailable(QmitkStdMultiWidget& stdMultiWidget) { m_MultiWidget = &stdMultiWidget; m_Parent->setEnabled(true); } void QmitkScreenshotMaker::StdMultiWidgetNotAvailable() { m_MultiWidget = NULL; m_Parent->setEnabled(false); } void QmitkScreenshotMaker::TakeScreenshot(vtkRenderer* renderer, unsigned int magnificationFactor, QString fileName) { if ((renderer == NULL) ||(magnificationFactor < 1) || fileName.isEmpty()) return; bool doubleBuffering( renderer->GetRenderWindow()->GetDoubleBuffer() ); renderer->GetRenderWindow()->DoubleBufferOff(); vtkImageWriter* fileWriter; QFileInfo fi(fileName); QString suffix = fi.suffix(); if (suffix.compare("jpg", Qt::CaseInsensitive) == 0) { vtkJPEGWriter* w = vtkJPEGWriter::New(); w->SetQuality(100); w->ProgressiveOff(); fileWriter = w; } else // default is png { fileWriter = vtkPNGWriter::New(); } vtkRenderLargeImage* magnifier = vtkRenderLargeImage::New(); magnifier->SetInput(renderer); magnifier->SetMagnification(magnificationFactor); //magnifier->Update(); - fileWriter->SetInput(magnifier->GetOutput()); + fileWriter->SetInputConnection(magnifier->GetOutputPort()); fileWriter->SetFileName(fileName.toLatin1()); // vtkRenderLargeImage has problems with different layers, therefore we have to // temporarily deactivate all other layers. // we set the background to white, because it is nicer than black... double oldBackground[3]; renderer->GetBackground(oldBackground); // QColor color = QColorDialog::getColor(); double bgcolor[] = {m_BackgroundColor.red()/255.0, m_BackgroundColor.green()/255.0, m_BackgroundColor.blue()/255.0}; renderer->SetBackground(bgcolor); m_MultiWidget->DisableColoredRectangles(); m_MultiWidget->DisableDepartmentLogo(); m_MultiWidget->DisableGradientBackground(); m_MultiWidget->mitkWidget1->ActivateMenuWidget( false ); m_MultiWidget->mitkWidget2->ActivateMenuWidget( false ); m_MultiWidget->mitkWidget3->ActivateMenuWidget( false ); m_MultiWidget->mitkWidget4->ActivateMenuWidget( false ); fileWriter->Write(); fileWriter->Delete(); m_MultiWidget->mitkWidget1->ActivateMenuWidget( true, m_MultiWidget ); m_MultiWidget->mitkWidget2->ActivateMenuWidget( true, m_MultiWidget ); m_MultiWidget->mitkWidget3->ActivateMenuWidget( true, m_MultiWidget ); m_MultiWidget->mitkWidget4->ActivateMenuWidget( true, m_MultiWidget ); m_MultiWidget->EnableColoredRectangles(); m_MultiWidget->EnableDepartmentLogo(); m_MultiWidget->EnableGradientBackground(); renderer->SetBackground(oldBackground); renderer->GetRenderWindow()->SetDoubleBuffer(doubleBuffering); } void QmitkScreenshotMaker::SelectBackgroundColor() { m_BackgroundColor = QColorDialog::getColor(); m_Controls->m_BackgroundColor->setAutoFillBackground(true); QString styleSheet = "background-color:rgb("; styleSheet.append(QString::number(m_BackgroundColor.red())); styleSheet.append(","); styleSheet.append(QString::number(m_BackgroundColor.green())); styleSheet.append(","); styleSheet.append(QString::number(m_BackgroundColor.blue())); styleSheet.append(")"); m_Controls->m_BackgroundColor->setStyleSheet(styleSheet); } diff --git a/Plugins/org.mitk.gui.qt.tofutil/src/internal/QmitkToFImageBackground.cpp b/Plugins/org.mitk.gui.qt.tofutil/src/internal/QmitkToFImageBackground.cpp index 08ffd30f1f..00444caa68 100644 --- a/Plugins/org.mitk.gui.qt.tofutil/src/internal/QmitkToFImageBackground.cpp +++ b/Plugins/org.mitk.gui.qt.tofutil/src/internal/QmitkToFImageBackground.cpp @@ -1,255 +1,257 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical and Biological Informatics. All rights reserved. This software is distributed WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See LICENSE.txt or http://www.mitk.org for details. ===================================================================*/ #include "QmitkToFImageBackground.h" // MITK includes #include "mitkVtkLayerController.h" #include "mitkRenderingManager.h" // VTK includes #include "vtkSystemIncludes.h" #include "vtkRenderer.h" #include "vtkMapper.h" #include "vtkObjectFactory.h" #include "vtkImageActor.h" #include "vtkRenderWindow.h" #include "vtkImageImport.h" #include "vtkCommand.h" #include "vtkCamera.h" QmitkToFImageBackground::QmitkToFImageBackground() { ResetBackground(); } void QmitkToFImageBackground::ResetBackground() { m_renderWindowVectorInfo.clear(); } QmitkToFImageBackground::~QmitkToFImageBackground() { if ( m_renderWindowVectorInfo.size() > 0 ) { } } /** * Sets the renderwindow, in which the Video background * will be shown. Make sure, you have called this function * before calling Enable() */ /* void QmitkToFImageBackground::AddRenderWindow(vtkRenderWindow* renderWindow ) { RemoveRenderWindow(renderWindow); vtkRenderer* videoRenderer = vtkRenderer::New(); vtkImageActor* videoActor = vtkImageActor::New(); vtkImageImport* videoImport = vtkImageImport::New(); videoImport->SetDataScalarTypeToUnsignedChar(); videoImport->SetNumberOfScalarComponents(3); if(m_VideoSource->GetImageWidth() == 0) m_VideoSource->FetchFrame(); videoImport->SetWholeExtent(0,m_VideoSource->GetImageWidth()-1,0,m_VideoSource->GetImageHeight()-1,0,1-1); videoImport->SetDataExtentToWholeExtent(); mitk::VideoBackgroundVectorInfo v; v.renWin = renderWindow; v.videoRenderer = videoRenderer; v.videoActor = videoActor; v.videoImport = videoImport; m_renderWindowVectorInfo.push_back(v); Modified(); } */ void QmitkToFImageBackground::AddRenderWindow(vtkRenderWindow* renderWindow, int width, int height ) { RemoveRenderWindow(renderWindow); vtkRenderer* videoRenderer = vtkRenderer::New(); vtkImageActor* videoActor = vtkImageActor::New(); vtkImageImport* videoImport = vtkImageImport::New(); videoImport->SetDataScalarTypeToUnsignedChar(); videoImport->SetNumberOfScalarComponents(3); // if(m_VideoSource->GetImageWidth() == 0) // m_VideoSource->FetchFrame(); videoImport->SetWholeExtent(0,width-1,0,height-1,0,1-1); videoImport->SetDataExtentToWholeExtent(); mitk::ToFImageBackgroundVectorInfo v; v.renWin = renderWindow; v.videoRenderer = videoRenderer; v.videoActor = videoActor; v.videoImport = videoImport; m_renderWindowVectorInfo.push_back(v); //Modified(); for(RenderWindowVectorInfoType::iterator it = m_renderWindowVectorInfo.begin(); it != m_renderWindowVectorInfo.end(); it++) { - (*it).videoActor->SetInput((*it).videoImport->GetOutput()); + (*it).videoImport->Update(); + (*it).videoActor->SetInputData((*it).videoImport->GetOutput()); (*it).videoRenderer->AddActor2D((*it).videoActor); (*it).videoRenderer->ResetCamera(); (*it).videoRenderer->InteractiveOff(); (*it).videoRenderer->GetActiveCamera()->ParallelProjectionOn(); (*it).videoRenderer->GetActiveCamera()->SetParallelScale(height/2); if(!mitk::VtkLayerController::GetInstance((*it).renWin)->IsRendererInserted((*it).videoRenderer)) mitk::VtkLayerController::GetInstance((*it).renWin)->InsertBackgroundRenderer((*it).videoRenderer,true); } } void QmitkToFImageBackground::RemoveRenderWindow(vtkRenderWindow* renderWindow ) { for(RenderWindowVectorInfoType::iterator it = m_renderWindowVectorInfo.begin(); it != m_renderWindowVectorInfo.end(); it++) { if((*it).renWin == renderWindow) { // unregister video backround renderer from renderwindow mitk::VtkLayerController::GetInstance((*it).renWin)->RemoveRenderer((*it).videoRenderer); (*it).videoRenderer->Delete(); (*it).videoActor->Delete(); (*it).videoImport->Delete(); m_renderWindowVectorInfo.erase(it); return; //delete &(*it); // memory leak renderwindowvectorinfo ?? } } } bool QmitkToFImageBackground::IsRenderWindowIncluded(vtkRenderWindow* renderWindow ) { for(RenderWindowVectorInfoType::iterator it = m_renderWindowVectorInfo.begin(); it != m_renderWindowVectorInfo.end(); it++) { if((*it).renWin == renderWindow) return true; } return false; } /** * Enables drawing of the color Video background. * If you want to disable it, call the Disable() function. */ /* void QmitkToFImageBackground::Enable() { UpdateVideo(); Modified(); m_QTimer->start(m_TimerDelay); } */ /** * Disables drawing of the color Video background. * If you want to enable it, call the Enable() function. */ /* void QmitkToFImageBackground::Disable() { if ( this->IsEnabled() ) { /*for(RenderWindowVectorInfoType::iterator it = m_renderWindowVectorInfo.begin(); it != m_renderWindowVectorInfo.end(); it++) { mitk::VtkLayerController::GetInstance((*it).renWin)->RemoveRenderer((*it).videoRenderer); }* / m_QTimer->stop(); } } */ /** * Checks, if the Video background is currently * enabled (visible) */ /* bool QmitkToFImageBackground::IsEnabled() { if (m_QTimer->isActive()) return true; else return false; } */ /* void QmitkToFImageBackground::UpdateVideo() { unsigned char *src = 0; src = m_VideoSource->GetVideoTexture(); if(src) { if(m_renderWindowVectorInfo.size()>0) { for(RenderWindowVectorInfoType::iterator it = m_renderWindowVectorInfo.begin(); it != m_renderWindowVectorInfo.end(); it++) { (*it).videoImport->SetImportVoidPointer(src); (*it).videoImport->Modified(); (*it).videoImport->Update(); mitk::RenderingManager::GetInstance()->RequestUpdate((*it).renWin); } } } emit NewFrameAvailable ( m_VideoSource ); } */ void QmitkToFImageBackground::UpdateBackground(unsigned char *src) { if(src) { if(m_renderWindowVectorInfo.size()>0) { for(RenderWindowVectorInfoType::iterator it = m_renderWindowVectorInfo.begin(); it != m_renderWindowVectorInfo.end(); it++) { (*it).videoImport->SetImportVoidPointer(src); (*it).videoImport->Modified(); (*it).videoImport->Update(); mitk::RenderingManager::GetInstance()->RequestUpdate((*it).renWin); } } } //emit NewFrameAvailable ( m_VideoSource ); } void QmitkToFImageBackground::Modified() { // ensures registration of video backrounds in each renderwindow for(RenderWindowVectorInfoType::iterator it = m_renderWindowVectorInfo.begin(); it != m_renderWindowVectorInfo.end(); it++) { - (*it).videoActor->SetInput((*it).videoImport->GetOutput()); + (*it).videoImport->Update(); + (*it).videoActor->SetInputData((*it).videoImport->GetOutput()); (*it).videoRenderer->AddActor2D((*it).videoActor); (*it).videoRenderer->ResetCamera(); (*it).videoRenderer->InteractiveOff(); (*it).videoRenderer->GetActiveCamera()->ParallelProjectionOn(); //(*it).videoRenderer->GetActiveCamera()->SetParallelScale(m_VideoSource->GetImageHeight()/2); if(!mitk::VtkLayerController::GetInstance((*it).renWin)->IsRendererInserted((*it).videoRenderer)) mitk::VtkLayerController::GetInstance((*it).renWin)->InsertBackgroundRenderer((*it).videoRenderer,true); } }