diff --git a/Modules/Core/files.cmake b/Modules/Core/files.cmake index 3621706abc..05c30c42e6 100644 --- a/Modules/Core/files.cmake +++ b/Modules/Core/files.cmake @@ -1,316 +1,317 @@ file(GLOB_RECURSE H_FILES RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}" "${CMAKE_CURRENT_SOURCE_DIR}/include/*") set(CPP_FILES mitkCoreActivator.cpp mitkCoreObjectFactoryBase.cpp mitkCoreObjectFactory.cpp mitkCoreServices.cpp mitkException.cpp Algorithms/mitkBaseDataSource.cpp Algorithms/mitkClippedSurfaceBoundsCalculator.cpp Algorithms/mitkCompareImageDataFilter.cpp Algorithms/mitkCompositePixelValueToString.cpp Algorithms/mitkConvert2Dto3DImageFilter.cpp Algorithms/mitkDataNodeSource.cpp Algorithms/mitkExtractSliceFilter.cpp Algorithms/mitkHistogramGenerator.cpp Algorithms/mitkImageChannelSelector.cpp Algorithms/mitkImageSliceSelector.cpp Algorithms/mitkImageSource.cpp Algorithms/mitkImageTimeSelector.cpp Algorithms/mitkImageToImageFilter.cpp Algorithms/mitkImageToSurfaceFilter.cpp Algorithms/mitkMultiComponentImageDataComparisonFilter.cpp Algorithms/mitkPlaneGeometryDataToSurfaceFilter.cpp Algorithms/mitkPointSetSource.cpp Algorithms/mitkPointSetToPointSetFilter.cpp Algorithms/mitkRGBToRGBACastImageFilter.cpp Algorithms/mitkSubImageSelector.cpp Algorithms/mitkSurfaceSource.cpp Algorithms/mitkSurfaceToImageFilter.cpp Algorithms/mitkSurfaceToSurfaceFilter.cpp Algorithms/mitkUIDGenerator.cpp Algorithms/mitkVolumeCalculator.cpp Controllers/mitkBaseController.cpp Controllers/mitkCallbackFromGUIThread.cpp Controllers/mitkCameraController.cpp Controllers/mitkCameraRotationController.cpp Controllers/mitkLimitedLinearUndo.cpp Controllers/mitkOperationEvent.cpp Controllers/mitkPlanePositionManager.cpp Controllers/mitkProgressBar.cpp Controllers/mitkRenderingManager.cpp Controllers/mitkSliceNavigationController.cpp Controllers/mitkSlicesCoordinator.cpp Controllers/mitkStatusBar.cpp Controllers/mitkStepper.cpp Controllers/mitkTestManager.cpp Controllers/mitkUndoController.cpp Controllers/mitkVerboseLimitedLinearUndo.cpp Controllers/mitkVtkLayerController.cpp DataManagement/mitkAnatomicalStructureColorPresets.cpp DataManagement/mitkArbitraryTimeGeometry.cpp DataManagement/mitkAbstractTransformGeometry.cpp DataManagement/mitkAnnotationProperty.cpp DataManagement/mitkApplicationCursor.cpp DataManagement/mitkApplyTransformMatrixOperation.cpp DataManagement/mitkBaseData.cpp DataManagement/mitkBaseGeometry.cpp DataManagement/mitkBaseProperty.cpp DataManagement/mitkChannelDescriptor.cpp DataManagement/mitkClippingProperty.cpp DataManagement/mitkColorProperty.cpp DataManagement/mitkDataNode.cpp DataManagement/mitkDataStorage.cpp DataManagement/mitkEnumerationProperty.cpp DataManagement/mitkFloatPropertyExtension.cpp DataManagement/mitkGeometry3D.cpp DataManagement/mitkGeometryData.cpp DataManagement/mitkGeometryTransformHolder.cpp DataManagement/mitkGroupTagProperty.cpp DataManagement/mitkImageAccessorBase.cpp DataManagement/mitkImageCaster.cpp DataManagement/mitkImageCastPart1.cpp DataManagement/mitkImageCastPart2.cpp DataManagement/mitkImageCastPart3.cpp DataManagement/mitkImageCastPart4.cpp DataManagement/mitkImage.cpp DataManagement/mitkImageDataItem.cpp DataManagement/mitkImageDescriptor.cpp DataManagement/mitkImageReadAccessor.cpp DataManagement/mitkImageStatisticsHolder.cpp DataManagement/mitkImageVtkAccessor.cpp DataManagement/mitkImageVtkReadAccessor.cpp DataManagement/mitkImageVtkWriteAccessor.cpp DataManagement/mitkImageWriteAccessor.cpp DataManagement/mitkIntPropertyExtension.cpp DataManagement/mitkIPersistenceService.cpp DataManagement/mitkIPropertyAliases.cpp DataManagement/mitkIPropertyDescriptions.cpp DataManagement/mitkIPropertyExtensions.cpp DataManagement/mitkIPropertyFilters.cpp DataManagement/mitkIPropertyPersistence.cpp DataManagement/mitkLandmarkProjectorBasedCurvedGeometry.cpp DataManagement/mitkLandmarkProjector.cpp DataManagement/mitkLevelWindow.cpp DataManagement/mitkLevelWindowManager.cpp DataManagement/mitkLevelWindowPreset.cpp DataManagement/mitkLevelWindowProperty.cpp DataManagement/mitkLine.cpp DataManagement/mitkLookupTable.cpp DataManagement/mitkLookupTableProperty.cpp DataManagement/mitkLookupTables.cpp # specializations of GenericLookupTable DataManagement/mitkMaterial.cpp DataManagement/mitkMemoryUtilities.cpp DataManagement/mitkModalityProperty.cpp DataManagement/mitkModifiedLock.cpp DataManagement/mitkNodePredicateAnd.cpp DataManagement/mitkNodePredicateBase.cpp DataManagement/mitkNodePredicateCompositeBase.cpp DataManagement/mitkNodePredicateData.cpp DataManagement/mitkNodePredicateDataType.cpp DataManagement/mitkNodePredicateDimension.cpp DataManagement/mitkNodePredicateFirstLevel.cpp DataManagement/mitkNodePredicateGeometry.cpp DataManagement/mitkNodePredicateNot.cpp DataManagement/mitkNodePredicateOr.cpp DataManagement/mitkNodePredicateProperty.cpp DataManagement/mitkNodePredicateDataProperty.cpp DataManagement/mitkNodePredicateSource.cpp DataManagement/mitkNumericConstants.cpp DataManagement/mitkPlaneGeometry.cpp DataManagement/mitkPlaneGeometryData.cpp DataManagement/mitkPlaneOperation.cpp DataManagement/mitkPlaneOrientationProperty.cpp DataManagement/mitkPointOperation.cpp DataManagement/mitkPointSet.cpp DataManagement/mitkPointSetShapeProperty.cpp DataManagement/mitkProperties.cpp DataManagement/mitkPropertyAliases.cpp DataManagement/mitkPropertyDescriptions.cpp DataManagement/mitkPropertyExtension.cpp DataManagement/mitkPropertyExtensions.cpp DataManagement/mitkPropertyFilter.cpp DataManagement/mitkPropertyFilters.cpp DataManagement/mitkPropertyList.cpp DataManagement/mitkPropertyListReplacedObserver.cpp DataManagement/mitkPropertyNameHelper.cpp DataManagement/mitkPropertyObserver.cpp DataManagement/mitkPropertyPersistence.cpp DataManagement/mitkPropertyPersistenceInfo.cpp DataManagement/mitkProportionalTimeGeometry.cpp DataManagement/mitkRenderingModeProperty.cpp DataManagement/mitkResliceMethodProperty.cpp DataManagement/mitkRestorePlanePositionOperation.cpp DataManagement/mitkRotationOperation.cpp DataManagement/mitkScaleOperation.cpp DataManagement/mitkSlicedData.cpp DataManagement/mitkSlicedGeometry3D.cpp DataManagement/mitkSmartPointerProperty.cpp DataManagement/mitkStandaloneDataStorage.cpp DataManagement/mitkStringProperty.cpp DataManagement/mitkSurface.cpp DataManagement/mitkSurfaceOperation.cpp DataManagement/mitkThinPlateSplineCurvedGeometry.cpp DataManagement/mitkTimeGeometry.cpp DataManagement/mitkTransferFunction.cpp DataManagement/mitkTransferFunctionInitializer.cpp DataManagement/mitkTransferFunctionProperty.cpp DataManagement/mitkTemporoSpatialStringProperty.cpp DataManagement/mitkVector.cpp DataManagement/mitkVectorProperty.cpp DataManagement/mitkVtkInterpolationProperty.cpp DataManagement/mitkVtkRepresentationProperty.cpp DataManagement/mitkVtkResliceInterpolationProperty.cpp DataManagement/mitkVtkScalarModeProperty.cpp DataManagement/mitkVtkVolumeRenderingProperty.cpp DataManagement/mitkWeakPointerProperty.cpp Interactions/mitkAction.cpp Interactions/mitkBindDispatcherInteractor.cpp Interactions/mitkCrosshairPositionEvent.cpp Interactions/mitkDataInteractor.cpp Interactions/mitkDispatcher.cpp Interactions/mitkDisplayCoordinateOperation.cpp Interactions/mitkDisplayInteractor.cpp Interactions/mitkDisplayActionEventBroadcast.cpp Interactions/mitkDisplayActionEventFunctions.cpp Interactions/mitkDisplayActionEventHandler.cpp Interactions/mitkEventConfig.cpp Interactions/mitkEventFactory.cpp Interactions/mitkEventRecorder.cpp Interactions/mitkEventStateMachine.cpp Interactions/mitkInteractionEventConst.cpp Interactions/mitkInteractionEvent.cpp Interactions/mitkInteractionEventHandler.cpp Interactions/mitkInteractionEventObserver.cpp Interactions/mitkInteractionKeyEvent.cpp Interactions/mitkInteractionPositionEvent.cpp + Interactions/mitkInteractionSchemeSwitcher.cpp Interactions/mitkInternalEvent.cpp Interactions/mitkMouseDoubleClickEvent.cpp Interactions/mitkMouseModeSwitcher.cpp Interactions/mitkMouseMoveEvent.cpp Interactions/mitkMousePressEvent.cpp Interactions/mitkMouseReleaseEvent.cpp Interactions/mitkMouseWheelEvent.cpp Interactions/mitkPointSetDataInteractor.cpp Interactions/mitkSinglePointDataInteractor.cpp Interactions/mitkStateMachineAction.cpp Interactions/mitkStateMachineCondition.cpp Interactions/mitkStateMachineContainer.cpp Interactions/mitkStateMachineState.cpp Interactions/mitkStateMachineTransition.cpp Interactions/mitkStdDisplayActionEventHandler.cpp Interactions/mitkVtkEventAdapter.cpp Interactions/mitkVtkInteractorStyle.cxx Interactions/mitkXML2EventParser.cpp IO/mitkAbstractFileIO.cpp IO/mitkAbstractFileReader.cpp IO/mitkAbstractFileWriter.cpp IO/mitkCustomMimeType.cpp IO/mitkDicomSeriesReader.cpp IO/mitkDicomSeriesReaderService.cpp IO/mitkDicomSR_GantryTiltInformation.cpp IO/mitkDicomSR_ImageBlockDescriptor.cpp IO/mitkDicomSR_LoadDICOMRGBPixel4D.cpp IO/mitkDicomSR_LoadDICOMRGBPixel.cpp IO/mitkDicomSR_LoadDICOMScalar4D.cpp IO/mitkDicomSR_LoadDICOMScalar.cpp IO/mitkDicomSR_SliceGroupingResult.cpp IO/mitkFileReader.cpp IO/mitkFileReaderRegistry.cpp IO/mitkFileReaderSelector.cpp IO/mitkFileReaderWriterBase.cpp IO/mitkFileWriter.cpp IO/mitkFileWriterRegistry.cpp IO/mitkFileWriterSelector.cpp IO/mitkGeometry3DToXML.cpp IO/mitkIFileIO.cpp IO/mitkIFileReader.cpp IO/mitkIFileWriter.cpp IO/mitkGeometryDataReaderService.cpp IO/mitkGeometryDataWriterService.cpp IO/mitkImageGenerator.cpp IO/mitkImageVtkLegacyIO.cpp IO/mitkImageVtkXmlIO.cpp IO/mitkIMimeTypeProvider.cpp IO/mitkIOConstants.cpp IO/mitkIOMimeTypes.cpp IO/mitkIOUtil.cpp IO/mitkItkImageIO.cpp IO/mitkItkLoggingAdapter.cpp IO/mitkLegacyFileReaderService.cpp IO/mitkLegacyFileWriterService.cpp IO/mitkLocaleSwitch.cpp IO/mitkLog.cpp IO/mitkMimeType.cpp IO/mitkMimeTypeProvider.cpp IO/mitkOperation.cpp IO/mitkPixelType.cpp IO/mitkPointSetReaderService.cpp IO/mitkPointSetWriterService.cpp IO/mitkProportionalTimeGeometryToXML.cpp IO/mitkRawImageFileReader.cpp IO/mitkStandardFileLocations.cpp IO/mitkSurfaceStlIO.cpp IO/mitkSurfaceVtkIO.cpp IO/mitkSurfaceVtkLegacyIO.cpp IO/mitkSurfaceVtkXmlIO.cpp IO/mitkVtkLoggingAdapter.cpp IO/mitkPreferenceListReaderOptionsFunctor.cpp Rendering/mitkAbstractAnnotationRenderer.cpp Rendering/mitkAnnotationUtils.cpp Rendering/mitkBaseRenderer.cpp #Rendering/mitkGLMapper.cpp Moved to deprecated LegacyGL Module Rendering/mitkGradientBackground.cpp Rendering/mitkImageVtkMapper2D.cpp Rendering/mitkMapper.cpp Rendering/mitkAnnotation.cpp Rendering/mitkPlaneGeometryDataMapper2D.cpp Rendering/mitkPlaneGeometryDataVtkMapper3D.cpp Rendering/mitkPointSetVtkMapper2D.cpp Rendering/mitkPointSetVtkMapper3D.cpp Rendering/mitkRenderWindowBase.cpp Rendering/mitkRenderWindow.cpp Rendering/mitkRenderWindowFrame.cpp #Rendering/mitkSurfaceGLMapper2D.cpp Moved to deprecated LegacyGL Module Rendering/mitkSurfaceVtkMapper2D.cpp Rendering/mitkSurfaceVtkMapper3D.cpp Rendering/mitkVtkEventProvider.cpp Rendering/mitkVtkMapper.cpp Rendering/mitkVtkPropRenderer.cpp Rendering/mitkVtkWidgetRendering.cpp Rendering/vtkMitkLevelWindowFilter.cpp Rendering/vtkMitkRectangleProp.cpp Rendering/vtkMitkRenderProp.cpp Rendering/vtkMitkThickSlicesFilter.cpp Rendering/vtkNeverTranslucentTexture.cpp ) set(RESOURCE_FILES Interactions/globalConfig.xml Interactions/DisplayInteraction.xml Interactions/DisplayConfig.xml Interactions/DisplayConfigPACS.xml Interactions/DisplayConfigPACSPan.xml Interactions/DisplayConfigPACSScroll.xml Interactions/DisplayConfigPACSZoom.xml Interactions/DisplayConfigPACSLevelWindow.xml Interactions/DisplayConfigMITK.xml Interactions/DisplayConfigMITKNoCrosshair.xml Interactions/DisplayConfigMITKRotation.xml Interactions/DisplayConfigMITKRotationUnCoupled.xml Interactions/DisplayConfigMITKSwivel.xml Interactions/DisplayConfigMITKLimited.xml Interactions/PointSet.xml Interactions/Legacy/StateMachine.xml Interactions/Legacy/DisplayConfigMITKTools.xml Interactions/PointSetConfig.xml mitkLevelWindowPresets.xml mitkAnatomicalStructureColorPresets.xml ) diff --git a/Modules/Core/include/mitkInteractionSchemeSwitcher.h b/Modules/Core/include/mitkInteractionSchemeSwitcher.h new file mode 100644 index 0000000000..245f4b2d8d --- /dev/null +++ b/Modules/Core/include/mitkInteractionSchemeSwitcher.h @@ -0,0 +1,111 @@ +/*=================================================================== + +The Medical Imaging Interaction Toolkit (MITK) + +Copyright (c) German Cancer Research Center, +Division of Medical Image Computing. +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 MITKINTERACTIONSCHEMESWITCHER_H +#define MITKINTERACTIONSCHEMESWITCHER_H + +#include "MitkCoreExports.h" + +#include "mitkInteractionEventHandler.h" + +#include + +namespace mitk +{ + /*********************************************************************** + * + * \brief Class that offers a convenient way to switch between different + * interaction schemes and their different modes. + * + * This class offers the possibility to switch between the two different + * interaction schemes that are available: + * + * - MITK : The original interaction scheme + * - left mouse button : setting the cross position in the MPR view + * - middle mouse button : panning + * - right mouse button : zooming + * + * There are 3 different MITK modes that are available in the MITK scheme. + * + * - PACS : An alternative interaction scheme that behaves more like a + * PACS workstation + * - left mouse button : behavior depends on current MouseMode + * - middle mouse button : fast scrolling + * - right mouse button : level-window + * - ctrl + right button : zooming + * - shift+ right button : panning + * + * There are 5 different PACS modes that are available in the PACS scheme. + * Each mode defines the interaction that is performed on a left + * mouse button click: + * - Pointer : sets the cross position for the MPR + * - Scroll + * - Level-Window + * - Zoom + * - Pan + * + * When the interaction scheme is changed, this class sets the corresponding + * interaction .xml-files for a given interaction event handler. + * + ***********************************************************************/ + class MITKCORE_EXPORT InteractionSchemeSwitcher : public itk::Object + { + public: +#pragma GCC visibility push(default) + /** + \brief Can be observed by GUI class to update button states when type is changed programmatically. + */ + itkEventMacro(InteractionSchemeChangedEvent, itk::AnyEvent); +#pragma GCC visibility pop + + mitkClassMacroItkParent(InteractionSchemeSwitcher, itk::Object); + itkFactorylessNewMacro(Self) itkCloneMacro(Self) + + // enum of the different interaction schemes that are available + enum InteractionScheme + { + MITKStandard = 0, + MITKRotationUncoupled, + MITKRotationCoupled, + MITKSwivel, + PACSStandard, + PACSLevelWindow, + PACSPan, + PACSScroll, + PACSZoom + }; + + /** + * @brief Set the current interaction scheme of the given interaction event handler + */ + void SetInteractionScheme(mitk::InteractionEventHandler* interactionEventHandler, InteractionScheme interactionScheme); + /** + * @brief Return the current interaction scheme + */ + InteractionScheme GetInteractionScheme() const { return m_InteractionScheme; }; + + protected: + + InteractionSchemeSwitcher(); + virtual ~InteractionSchemeSwitcher() override; + + private: + + InteractionScheme m_InteractionScheme; + }; +} // namespace mitk + +#endif // MITKINTERACTIONSCHEMESWITCHER_H diff --git a/Modules/Core/include/mitkMouseModeSwitcher.h b/Modules/Core/include/mitkMouseModeSwitcher.h index a728b6a3f7..220a257851 100644 --- a/Modules/Core/include/mitkMouseModeSwitcher.h +++ b/Modules/Core/include/mitkMouseModeSwitcher.h @@ -1,132 +1,130 @@ /*=================================================================== 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 MITKMouseModeSwitcher_H_HEADER_INCLUDED_C10DC4EB #define MITKMouseModeSwitcher_H_HEADER_INCLUDED_C10DC4EB #include "MitkCoreExports.h" #include "mitkDisplayInteractor.h" #include namespace mitk { /*********************************************************************** * * \brief Class that offers a convenient way to switch between different * interaction schemes * * This class offers the possibility to switch between the two different * interaction schemes that are available: * - MITK : The original interaction scheme * - left mouse button : setting the cross position in the MPR view * - middle mouse button : panning * - right mouse button : zooming * * * - PACS : an alternative interaction scheme that behaves more like a * PACS workstation * - left mouse button : behavior depends on current MouseMode * - middle mouse button : fast scrolling * - right mouse button : level-window * - ctrl + right button : zooming * - shift+ right button : panning * * There are 5 different MouseModes that are available in the PACS scheme. * Each MouseMode defines the interaction that is performed on a left * mouse button click: * - Pointer : sets the cross position for the MPR * - Scroll * - Level-Window * - Zoom * - Pan * * When the interaction scheme or the MouseMode is changed, this class * manages the adding and removing of the relevant listeners offering * a convenient way to modify the interaction behavior. * ***********************************************************************/ class MITKCORE_EXPORT MouseModeSwitcher : public itk::Object { public: #pragma GCC visibility push(default) /** \brief Can be observed by GUI class to update button states when mode is changed programatically. */ itkEventMacro(MouseModeChangedEvent, itk::AnyEvent); #pragma GCC visibility pop mitkClassMacroItkParent(MouseModeSwitcher, itk::Object); itkFactorylessNewMacro(Self) itkCloneMacro(Self) // enum of the different interaction schemes that are available enum InteractionScheme { PACS = 0, MITK = 1, ROTATION = 2, ROTATIONLINKED = 3, SWIVEL = 4 }; // enum of available mouse modes for PACS interaction scheme enum MouseMode { MousePointer = 0, Scroll, LevelWindow, Zoom, Pan }; /** * \brief Setter for interaction scheme */ void SetInteractionScheme(InteractionScheme); /** * \brief Setter for mouse mode */ void SelectMouseMode(MouseMode mode); /** * \brief Returns the current mouse mode */ MouseMode GetCurrentMouseMode() const; - DisplayInteractor::Pointer GetCurrentObserver() { return m_CurrentObserver; } - protected: MouseModeSwitcher(); - virtual ~MouseModeSwitcher(); + virtual ~MouseModeSwitcher() override; private: /** * \brief Initializes the listener with the MITK default behavior. */ void InitializeListeners(); InteractionScheme m_ActiveInteractionScheme; MouseMode m_ActiveMouseMode; DisplayInteractor::Pointer m_CurrentObserver; /** * Reference to the service registration of the observer, * it is needed to unregister the observer on unload. */ us::ServiceRegistration m_ServiceRegistration; }; } // namespace mitk #endif /* MITKMouseModeSwitcher_H_HEADER_INCLUDED_C10DC4EB */ diff --git a/Modules/Core/src/Interactions/mitkInteractionSchemeSwitcher.cpp b/Modules/Core/src/Interactions/mitkInteractionSchemeSwitcher.cpp new file mode 100644 index 0000000000..5cb7f5eb82 --- /dev/null +++ b/Modules/Core/src/Interactions/mitkInteractionSchemeSwitcher.cpp @@ -0,0 +1,96 @@ +/*=================================================================== + +The Medical Imaging Interaction Toolkit (MITK) + +Copyright (c) German Cancer Research Center, +Division of Medical Image Computing. +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 "mitkInteractionSchemeSwitcher.h" + +// us +#include "usGetModuleContext.h" +#include "usModuleContext.h" + +// mitk core +#include "mitkInteractionEventObserver.h" + +mitk::InteractionSchemeSwitcher::InteractionSchemeSwitcher() + : m_InteractionScheme(MITKStandard) +{ + // nothing here +} + +mitk::InteractionSchemeSwitcher::~InteractionSchemeSwitcher() +{ + // nothing here +} + +void mitk::InteractionSchemeSwitcher::SetInteractionScheme(mitk::InteractionEventHandler* interactionEventHandler, InteractionScheme interactionScheme) +{ + switch (interactionScheme) + { + // MITK MODE + case MITKStandard: + { + interactionEventHandler->SetEventConfig("DisplayConfigMITK.xml"); + break; + } + case MITKRotationUncoupled: + { + interactionEventHandler->SetEventConfig("DisplayConfigMITKRotationUnCoupled.xml"); + break; + } + case MITKRotationCoupled: + { + interactionEventHandler->SetEventConfig("DisplayConfigMITKRotation.xml"); + break; + } + case MITKSwivel: + { + interactionEventHandler->SetEventConfig("DisplayConfigMITKSwivel.xml"); + break; + } + // PACS MODE + case PACSStandard: + { + interactionEventHandler->SetEventConfig("DisplayConfigPACS.xml"); + break; + } + case PACSLevelWindow: + { + interactionEventHandler->SetEventConfig("DisplayConfigPACS.xml"); + interactionEventHandler->AddEventConfig("DisplayConfigPACSLevelWindow.xml"); + break; + } + case PACSPan: + { + interactionEventHandler->SetEventConfig("DisplayConfigPACS.xml"); + interactionEventHandler->AddEventConfig("DisplayConfigPACSPan.xml"); + break; + } + case PACSScroll: + { + interactionEventHandler->SetEventConfig("DisplayConfigPACS.xml"); + interactionEventHandler->AddEventConfig("DisplayConfigPACSScroll.xml"); + break; + } + case PACSZoom: + { + interactionEventHandler->SetEventConfig("DisplayConfigPACS.xml"); + interactionEventHandler->AddEventConfig("DisplayConfigPACSZoom.xml"); + break; + } + } + + m_InteractionScheme = interactionScheme; + InvokeEvent(InteractionSchemeChangedEvent()); +} diff --git a/Modules/QtWidgets/files.cmake b/Modules/QtWidgets/files.cmake index a80b53a1e1..9408f33867 100644 --- a/Modules/QtWidgets/files.cmake +++ b/Modules/QtWidgets/files.cmake @@ -1,92 +1,94 @@ file(GLOB_RECURSE H_FILES RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}" "${CMAKE_CURRENT_SOURCE_DIR}/include/*") set(CPP_FILES QmitkApplicationCursor.cpp QmitkDataStorageComboBox.cpp QmitkDataStorageListModel.cpp QmitkDataStorageTableModel.cpp QmitkDataStorageTreeModel.cpp QmitkFileReaderOptionsDialog.cpp QmitkFileReaderWriterOptionsWidget.cpp QmitkFileWriterOptionsDialog.cpp + QmitkInteractionSchemeToolBar.cpp QmitkIOUtil.cpp QmitkLevelWindowPresetDefinitionDialog.cpp QmitkLevelWindowRangeChangeDialog.cpp QmitkLevelWindowWidgetContextMenu.cpp QmitkLevelWindowWidget.cpp QmitkLineEditLevelWindowWidget.cpp QmitkMemoryUsageIndicatorView.cpp QmitkMimeTypes.cpp QmitkMultiWidgetConfigurationToolBar.cpp QmitkMultiWidgetLayoutSelectionWidget.cpp QmitkNodeDescriptor.cpp QmitkNodeDescriptorManager.cpp QmitkRenderWindowMenu.cpp QmitkProgressBar.cpp QmitkPropertiesTableEditor.cpp QmitkPropertiesTableModel.cpp QmitkPropertyDelegate.cpp QmitkRegisterClasses.cpp QmitkRenderingManager.cpp QmitkRenderingManagerFactory.cpp QmitkRenderWindow.cpp QmitkRenderWindowWidget.cpp QmitkServiceListWidget.cpp QmitkSliderLevelWindowWidget.cpp QmitkStdMultiWidget.cpp QmitkCustomMultiWidget.cpp QmitkMouseModeSwitcher.cpp QmitkDataStorageFilterProxyModel.cpp QmitkDataStorageComboBoxWithSelectNone.cpp QmitkPropertyItem.cpp QmitkPropertyItemDelegate.cpp QmitkPropertyItemModel.cpp ) set(MOC_H_FILES include/QmitkDataStorageComboBox.h include/QmitkDataStorageTableModel.h include/QmitkFileReaderOptionsDialog.h include/QmitkFileReaderWriterOptionsWidget.h include/QmitkFileWriterOptionsDialog.h + include/QmitkInteractionSchemeToolBar.h include/QmitkLevelWindowPresetDefinitionDialog.h include/QmitkLevelWindowRangeChangeDialog.h include/QmitkLevelWindowWidgetContextMenu.h include/QmitkLevelWindowWidget.h include/QmitkLineEditLevelWindowWidget.h include/QmitkMemoryUsageIndicatorView.h + include/QmitkMouseModeSwitcher.h include/QmitkMultiWidgetConfigurationToolBar.h include/QmitkMultiWidgetLayoutSelectionWidget.h include/QmitkNodeDescriptor.h include/QmitkNodeDescriptorManager.h include/QmitkRenderWindowMenu.h include/QmitkRenderWindowWidget.h include/QmitkProgressBar.h include/QmitkPropertiesTableEditor.h include/QmitkPropertyDelegate.h include/QmitkRenderingManager.h include/QmitkRenderWindow.h include/QmitkServiceListWidget.h include/QmitkSliderLevelWindowWidget.h include/QmitkStdMultiWidget.h include/QmitkCustomMultiWidget.h - include/QmitkMouseModeSwitcher.h include/QmitkDataStorageComboBoxWithSelectNone.h include/QmitkPropertyItemDelegate.h include/QmitkPropertyItemModel.h ) set(UI_FILES src/QmitkFileReaderOptionsDialog.ui src/QmitkFileWriterOptionsDialog.ui src/QmitkLevelWindowPresetDefinition.ui src/QmitkLevelWindowWidget.ui src/QmitkLevelWindowRangeChange.ui src/QmitkMemoryUsageIndicator.ui src/QmitkMultiWidgetLayoutSelectionWidget.ui src/QmitkServiceListWidgetControls.ui ) set(QRC_FILES resource/Qmitk.qrc ) diff --git a/Modules/QtWidgets/include/QmitkCustomMultiWidget.h b/Modules/QtWidgets/include/QmitkCustomMultiWidget.h index 0e6a54dec0..05d162ef32 100644 --- a/Modules/QtWidgets/include/QmitkCustomMultiWidget.h +++ b/Modules/QtWidgets/include/QmitkCustomMultiWidget.h @@ -1,175 +1,171 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical Image Computing. 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 QMITKCUSTOMMULTIWIDGET_H #define QMITKCUSTOMMULTIWIDGET_H // qt widgets module #include "MitkQtWidgetsExports.h" #include "QmitkRenderWindowWidget.h" // mitk core #include #include #include -#include #include // qt #include class QHBoxLayout; class QVBoxLayout; class QGridLayout; class QSpacerItem; class QmitkLevelWindowWidget; class QmitkRenderWindow; namespace mitk { class RenderingManager; } /** * @brief The 'QmitkCustomMultiWidget' is a 'QWidget' that is used to display multiple render windows at once. * * Render windows can dynamically be added and removed to change the layout of the multi widget. */ class MITKQTWIDGETS_EXPORT QmitkCustomMultiWidget : public QWidget { Q_OBJECT public: QmitkCustomMultiWidget(QWidget* parent = 0, Qt::WindowFlags f = 0, mitk::RenderingManager* renderingManager = nullptr, mitk::BaseRenderer::RenderingMode::Type renderingMode = mitk::BaseRenderer::RenderingMode::Standard, const QString& multiWidgetName = "custommulti"); virtual ~QmitkCustomMultiWidget(); void SetDataStorage(mitk::DataStorage* dataStorage); void InitializeRenderWindowWidgets(); + mitk::InteractionEventHandler::Pointer GetInteractionEventHandler() { return m_DisplayActionEventBroadcast.GetPointer(); }; + void ResetLayout(int row, int column); void Synchronize(bool synchronized); using RenderWindowWidgetMap = std::map>; using RenderWindowHash = QHash; RenderWindowWidgetMap GetRenderWindowWidgets() const; std::shared_ptr GetRenderWindowWidget(const QString& widgetID) const; QString CreateRenderWindowWidget(const std::string& cornerAnnotation = ""); void AddToMultiWidgetLayout(int row, int column, const QString& widgetID); void RemoveRenderWindowWidget(const QString& widgetID); QmitkRenderWindow* GetRenderWindow(const QString& widgetID) const; std::shared_ptr GetActiveRenderWindowWidget() const; std::shared_ptr GetFirstRenderWindowWidget() const; std::shared_ptr GetLastRenderWindowWidget() const; unsigned int GetNumberOfRenderWindowWidgets() const; void RequestUpdate(const QString& widgetID); void RequestUpdateAll(); void ForceImmediateUpdate(const QString& widgetID); void ForceImmediateUpdateAll(); - mitk::MouseModeSwitcher* GetMouseModeSwitcher(); - const mitk::Point3D GetCrossPosition(const QString& widgetID) const; public slots: void ShowLevelWindowWidget(const QString& widgetID, bool show); void ShowAllLevelWindowWidgets(bool show); /** * @brief Listener to the CrosshairPositionEvent * * Ensures the CrosshairPositionEvent is handled only once and at the end of the Qt-Event loop */ void HandleCrosshairPositionEvent(); /** * @brief Receives the signal from HandleCrosshairPositionEvent, executes the StatusBar update * */ void HandleCrosshairPositionEventDelayed(); void MoveCrossToPosition(const QString& widgetID, const mitk::Point3D& newPosition); void ResetCrosshair(); // mouse events void wheelEvent(QWheelEvent* e) override; void mousePressEvent(QMouseEvent* e) override; void moveEvent(QMoveEvent* e) override; signals: void WheelMoved(QWheelEvent *); void Moved(); public: enum { AXIAL, SAGITTAL, CORONAL, THREE_D }; private: void InitializeGUI(); void InitializeWidget(); void InitializeDisplayActionEventHandling(); void FillLayout(int row, int column); // #TODO: see T24173 mitk::DataNode::Pointer GetTopLayerNode(mitk::DataStorage::SetOfObjects::ConstPointer nodes); QGridLayout* m_CustomMultiWidgetLayout; RenderWindowWidgetMap m_RenderWindowWidgets; QmitkRenderWindowWidget* m_ActiveRenderWindowWidget; int m_PlaneMode; mitk::RenderingManager* m_RenderingManager; mitk::BaseRenderer::RenderingMode::Type m_RenderingMode; QString m_MultiWidgetName; - mitk::MouseModeSwitcher::Pointer m_MouseModeSwitcher; - mitk::DisplayActionEventBroadcast::Pointer m_DisplayActionEventBroadcast; std::unique_ptr m_DisplayActionEventHandler; - bool m_Synchronized; mitk::DataStorage::Pointer m_DataStorage; bool m_PendingCrosshairPositionEvent; bool m_CrosshairNavigationEnabled; }; #endif // QMITKCUSTOMMULTIWIDGET_H diff --git a/Modules/QtWidgets/include/QmitkInteractionSchemeToolBar.h b/Modules/QtWidgets/include/QmitkInteractionSchemeToolBar.h new file mode 100644 index 0000000000..e9df9eb9a8 --- /dev/null +++ b/Modules/QtWidgets/include/QmitkInteractionSchemeToolBar.h @@ -0,0 +1,60 @@ +/*=================================================================== + +The Medical Imaging Interaction Toolkit (MITK) + +Copyright (c) German Cancer Research Center, +Division of Medical Image Computing. +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 QMITKINTERACTIONSCHEMETOOLBAR_H +#define QMITKINTERACTIONSCHEMETOOLBAR_H + +#include "MitkQtWidgetsExports.h" + +// mitk core +#include "mitkInteractionSchemeSwitcher.h" + +#include +#include + +/** +* @brief +* +* +*/ +class MITKQTWIDGETS_EXPORT QmitkInteractionSchemeToolBar : public QToolBar +{ + Q_OBJECT + +public: + + using InteractionScheme = mitk::InteractionSchemeSwitcher::InteractionScheme; + + QmitkInteractionSchemeToolBar(QWidget* parent = nullptr); + virtual ~QmitkInteractionSchemeToolBar() override; + + void SetInteractionEventHandler(mitk::InteractionEventHandler::Pointer interactionEventHandler); + +protected slots: + + void OnInteractionSchemeChanged(); + void AddButton(InteractionScheme id, const QString& toolName, const QIcon& icon, bool on = false); + +private: + + QActionGroup* m_ActionGroup; + + mitk::InteractionSchemeSwitcher::Pointer m_InteractionSchemeSwitcher; + mitk::InteractionEventHandler::Pointer m_InteractionEventHandler; + +}; + +#endif // QMITKINTERACTIONSCHEMETOOLBAR_H diff --git a/Modules/QtWidgets/include/QmitkMultiWidgetConfigurationToolBar.h b/Modules/QtWidgets/include/QmitkMultiWidgetConfigurationToolBar.h index 5fdf62d152..f1182f5eb3 100644 --- a/Modules/QtWidgets/include/QmitkMultiWidgetConfigurationToolBar.h +++ b/Modules/QtWidgets/include/QmitkMultiWidgetConfigurationToolBar.h @@ -1,67 +1,69 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical Image Computing. 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 QMITKMULTIWIDGETCONFIGURATIONTOOLBAR_H #define QMITKMULTIWIDGETCONFIGURATIONTOOLBAR_H #include "MitkQtWidgetsExports.h" -#include #include // mitk qtwidgets #include "QmitkCustomMultiWidget.h" #include "QmitkMultiWidgetLayoutSelectionWidget.h" /** * @brief * * */ class MITKQTWIDGETS_EXPORT QmitkMultiWidgetConfigurationToolBar : public QToolBar { Q_OBJECT public: + + using ViewDirection = mitk::SliceNavigationController::ViewDirection; + QmitkMultiWidgetConfigurationToolBar(QmitkCustomMultiWidget* customMultiWidget); ~QmitkMultiWidgetConfigurationToolBar() override; signals: void LayoutSet(int row, int column); void Synchronized(bool synchronized); + void ViewDirectionChanged(mitk::SliceNavigationController::ViewDirection); protected slots: void OnSetLayout(); void OnSynchronize(); + void OnViewDirectionChanged(); private: - void InitActionGroup();; + void InitializeToolBar();; void AddButtons(); - QActionGroup* m_ActionGroup; QmitkCustomMultiWidget* m_CustomMultiWidget; QAction* m_SynchronizeAction; - bool m_Synchronized; QmitkMultiWidgetLayoutSelectionWidget* m_LayoutSelectionPopup; }; #endif // QMITKMULTIWIDGETCONFIGURATIONTOOLBAR_H diff --git a/Modules/QtWidgets/resource/cmwViewDirection.png b/Modules/QtWidgets/resource/cmwViewDirection.png new file mode 100644 index 0000000000..880fab30d6 Binary files /dev/null and b/Modules/QtWidgets/resource/cmwViewDirection.png differ diff --git a/Modules/QtWidgets/src/QmitkCustomMultiWidget.cpp b/Modules/QtWidgets/src/QmitkCustomMultiWidget.cpp index 434ae1ba5a..441e4b95bf 100644 --- a/Modules/QtWidgets/src/QmitkCustomMultiWidget.cpp +++ b/Modules/QtWidgets/src/QmitkCustomMultiWidget.cpp @@ -1,576 +1,564 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical Image Computing. 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 "QmitkCustomMultiWidget.h" #include #include #include #include // mitk core #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include // qt #include QmitkCustomMultiWidget::QmitkCustomMultiWidget(QWidget* parent, Qt::WindowFlags f/* = 0*/, mitk::RenderingManager* renderingManager/* = nullptr*/, mitk::BaseRenderer::RenderingMode::Type renderingMode/* = mitk::BaseRenderer::RenderingMode::Standard*/, const QString& multiWidgetName/* = "custommulti"*/) : QWidget(parent, f) , m_CustomMultiWidgetLayout(nullptr) , m_RenderingManager(renderingManager) , m_RenderingMode(renderingMode) , m_MultiWidgetName(multiWidgetName) , m_PendingCrosshairPositionEvent(false) , m_CrosshairNavigationEnabled(false) , m_DisplayActionEventBroadcast(nullptr) , m_DisplayActionEventHandler(nullptr) , m_DataStorage(nullptr) { // create widget manually // create and set layout InitializeGUI(); InitializeWidget(); InitializeDisplayActionEventHandling(); resize(QSize(364, 477).expandedTo(minimumSizeHint())); } QmitkCustomMultiWidget::~QmitkCustomMultiWidget() { // nothing here } void QmitkCustomMultiWidget::SetDataStorage(mitk::DataStorage* dataStorage) { if (dataStorage == m_DataStorage) { return; } m_DataStorage = dataStorage; // set new data storage for the render window widgets for (const auto& renderWindowWidget : m_RenderWindowWidgets) { renderWindowWidget.second->SetDataStorage(m_DataStorage); } } void QmitkCustomMultiWidget::InitializeRenderWindowWidgets() { // create render window (widgets) initially QString UID = CreateRenderWindowWidget("2015-01-14 - CT"); AddToMultiWidgetLayout(0, 0, UID); /* AddRenderWindowWidget(0, 1, "2015-08-19 - CT"); AddRenderWindowWidget(0, 2, "2016-06-29 - CT"); AddRenderWindowWidget(1, 0, "2015-01-14 - MR"); AddRenderWindowWidget(1, 1, "2015-08-19 - MR"); AddRenderWindowWidget(1, 2, "2016-06-29 - MR"); */ } void QmitkCustomMultiWidget::ResetLayout(int row, int column) { int neededRenderWindowWidgets = (row + 1) * (column + 1); int existingRenderWindowWidgets = m_RenderWindowWidgets.size(); int difference = neededRenderWindowWidgets - existingRenderWindowWidgets; while(0 < difference) { // more render window widgets needed CreateRenderWindowWidget(); --difference; } while(0 > difference) { // less render window widgets needed RemoveRenderWindowWidget(m_RenderWindowWidgets.rbegin()->first); ++difference; } InitializeGUI(); if (0 == difference) { FillLayout(row, column); } } void QmitkCustomMultiWidget::Synchronize(bool synchronized) { - m_Synchronized = synchronized; auto allObserverTags = m_DisplayActionEventHandler->GetAllObserverTags(); for (auto observerTag : allObserverTags) { m_DisplayActionEventHandler->DisconnectObserver(observerTag); } - if (m_Synchronized) + if (synchronized) { mitk::StdFunctionCommand::ActionFunction actionFunction = mitk::DisplayActionEventFunctions::MoveCameraSynchronizedAction(); m_DisplayActionEventHandler->ConnectDisplayActionEvent(mitk::DisplayMoveEvent(nullptr, mitk::Vector2D()), actionFunction); actionFunction = mitk::DisplayActionEventFunctions::SetCrosshairSynchronizedAction(); m_DisplayActionEventHandler->ConnectDisplayActionEvent(mitk::DisplaySetCrosshairEvent(nullptr, mitk::Point3D()), actionFunction); actionFunction = mitk::DisplayActionEventFunctions::ZoomCameraSynchronizedAction(); m_DisplayActionEventHandler->ConnectDisplayActionEvent(mitk::DisplayZoomEvent(nullptr, 0.0, mitk::Point2D()), actionFunction); actionFunction = mitk::DisplayActionEventFunctions::ScrollSliceStepperSynchronizedAction(); m_DisplayActionEventHandler->ConnectDisplayActionEvent(mitk::DisplayScrollEvent(nullptr, 0), actionFunction); - - // #TODO: set equal view direction for all render windows } else { mitk::StdFunctionCommand::ActionFunction actionFunction = mitk::DisplayActionEventFunctions::MoveSenderCameraAction(); m_DisplayActionEventHandler->ConnectDisplayActionEvent(mitk::DisplayMoveEvent(nullptr, mitk::Vector2D()), actionFunction); actionFunction = mitk::DisplayActionEventFunctions::SetCrosshairAction(); m_DisplayActionEventHandler->ConnectDisplayActionEvent(mitk::DisplaySetCrosshairEvent(nullptr, mitk::Point3D()), actionFunction); actionFunction = mitk::DisplayActionEventFunctions::ZoomSenderCameraAction(); m_DisplayActionEventHandler->ConnectDisplayActionEvent(mitk::DisplayZoomEvent(nullptr, 0.0, mitk::Point2D()), actionFunction); actionFunction = mitk::DisplayActionEventFunctions::ScrollSliceStepperAction(); m_DisplayActionEventHandler->ConnectDisplayActionEvent(mitk::DisplayScrollEvent(nullptr, 0), actionFunction); } } QmitkCustomMultiWidget::RenderWindowWidgetMap QmitkCustomMultiWidget::GetRenderWindowWidgets() const { return m_RenderWindowWidgets; } std::shared_ptr QmitkCustomMultiWidget::GetRenderWindowWidget(const QString& widgetID) const { RenderWindowWidgetMap::const_iterator it = m_RenderWindowWidgets.find(widgetID); if (it == m_RenderWindowWidgets.end()) { return nullptr; } return it->second; } QString QmitkCustomMultiWidget::CreateRenderWindowWidget(const std::string& cornerAnnotation/* = ""*/) { // create the render window widget and connect signals / slots mitk::UIDGenerator generator; std::string renderWindowUID = generator.GetUID(); QString UID = m_MultiWidgetName + "_" + QString::fromStdString(renderWindowUID); std::shared_ptr renderWindowWidget = std::make_shared(this, UID, m_DataStorage); renderWindowWidget->SetCornerAnnotationText(cornerAnnotation); // create connections //connect(renderWindowWidget.get(), SIGNAL(ResetView()), this, SLOT(ResetCrosshair())); //connect(renderWindowWidget.get(), SIGNAL(ChangeCrosshairRotationMode(int)), this, SLOT(SetWidgetPlaneMode(int))); // store the newly created render window widget with the UID m_RenderWindowWidgets.insert(std::make_pair(UID, renderWindowWidget)); return UID; } void QmitkCustomMultiWidget::AddToMultiWidgetLayout(int row, int column, const QString& widgetID) { std::shared_ptr renderWindowWidget = GetRenderWindowWidget(widgetID); if (nullptr != renderWindowWidget) { m_CustomMultiWidgetLayout->addWidget(renderWindowWidget.get(), row, column); } } void QmitkCustomMultiWidget::RemoveRenderWindowWidget(const QString& widgetID) { auto iterator = m_RenderWindowWidgets.find(widgetID); if (iterator == m_RenderWindowWidgets.end()) { return; } std::shared_ptr renderWindowWidgetToRemove = iterator->second; disconnect(renderWindowWidgetToRemove.get(), 0, 0, 0); // erase the render window from the map m_RenderWindowWidgets.erase(iterator); // remove from layout // #TODO } QmitkRenderWindow* QmitkCustomMultiWidget::GetRenderWindow(const QString& widgetID) const { std::shared_ptr renderWindowWidget = GetRenderWindowWidget(widgetID); if (nullptr != renderWindowWidget) { return renderWindowWidget->GetRenderWindow(); } return nullptr; } std::shared_ptr QmitkCustomMultiWidget::GetActiveRenderWindowWidget() const { //return m_ActiveRenderWindowWidget; return m_RenderWindowWidgets.begin()->second; } std::shared_ptr QmitkCustomMultiWidget::GetFirstRenderWindowWidget() const { if (!m_RenderWindowWidgets.empty()) { return m_RenderWindowWidgets.begin()->second; } else { return nullptr; } } std::shared_ptr QmitkCustomMultiWidget::GetLastRenderWindowWidget() const { if (!m_RenderWindowWidgets.empty()) { return m_RenderWindowWidgets.rbegin()->second; } else { return nullptr; } } unsigned int QmitkCustomMultiWidget::GetNumberOfRenderWindowWidgets() const { return m_RenderWindowWidgets.size(); } void QmitkCustomMultiWidget::RequestUpdate(const QString& widgetID) { std::shared_ptr renderWindowWidget = GetRenderWindowWidget(widgetID); if (nullptr != renderWindowWidget) { return renderWindowWidget->RequestUpdate(); } } void QmitkCustomMultiWidget::RequestUpdateAll() { for (const auto& renderWindowWidget : m_RenderWindowWidgets) { renderWindowWidget.second->RequestUpdate(); } } void QmitkCustomMultiWidget::ForceImmediateUpdate(const QString& widgetID) { std::shared_ptr renderWindowWidget = GetRenderWindowWidget(widgetID); if (nullptr != renderWindowWidget) { renderWindowWidget->ForceImmediateUpdate(); } } void QmitkCustomMultiWidget::ForceImmediateUpdateAll() { for (const auto& renderWindowWidget : m_RenderWindowWidgets) { renderWindowWidget.second->ForceImmediateUpdate(); } } -mitk::MouseModeSwitcher* QmitkCustomMultiWidget::GetMouseModeSwitcher() -{ - return m_MouseModeSwitcher; -} - const mitk::Point3D QmitkCustomMultiWidget::GetCrossPosition(const QString& widgetID) const { /* const mitk::PlaneGeometry *plane1 = mitkWidget1->GetSliceNavigationController()->GetCurrentPlaneGeometry(); const mitk::PlaneGeometry *plane2 = mitkWidget2->GetSliceNavigationController()->GetCurrentPlaneGeometry(); const mitk::PlaneGeometry *plane3 = mitkWidget3->GetSliceNavigationController()->GetCurrentPlaneGeometry(); mitk::Line3D line; if ((plane1 != NULL) && (plane2 != NULL) && (plane1->IntersectionLine(plane2, line))) { mitk::Point3D point; if ((plane3 != NULL) && (plane3->IntersectionPoint(line, point))) { return point; } } // TODO BUG POSITIONTRACKER; mitk::Point3D p; return p; // return m_LastLeftClickPositionSupplier->GetCurrentPoint(); */ return mitk::Point3D(); } ////////////////////////////////////////////////////////////////////////// // PUBLIC SLOTS ////////////////////////////////////////////////////////////////////////// void QmitkCustomMultiWidget::ShowLevelWindowWidget(const QString& widgetID, bool show) { std::shared_ptr renderWindowWidget = GetRenderWindowWidget(widgetID); if (nullptr != renderWindowWidget) { renderWindowWidget->ShowLevelWindowWidget(show); return; } MITK_ERROR << "Level window widget can not be shown for an unknown widget."; } void QmitkCustomMultiWidget::ShowAllLevelWindowWidgets(bool show) { for (const auto& renderWindowWidget : m_RenderWindowWidgets) { renderWindowWidget.second->ShowLevelWindowWidget(show); } } void QmitkCustomMultiWidget::HandleCrosshairPositionEvent() { /* if (!m_PendingCrosshairPositionEvent) { m_PendingCrosshairPositionEvent = true; QTimer::singleShot(0, this, SLOT(HandleCrosshairPositionEventDelayed())); } */ } void QmitkCustomMultiWidget::HandleCrosshairPositionEventDelayed() { /* m_PendingCrosshairPositionEvent = false; // find image with highest layer mitk::TNodePredicateDataType::Pointer isImageData = mitk::TNodePredicateDataType::New(); mitk::DataStorage::SetOfObjects::ConstPointer nodes = this->m_DataStorage->GetSubset(isImageData).GetPointer(); mitk::DataNode::Pointer node; mitk::DataNode::Pointer topSourceNode; mitk::Image::Pointer image; bool isBinary = false; node = this->GetTopLayerNode(nodes); int component = 0; if (node.IsNotNull()) { node->GetBoolProperty("binary", isBinary); if (isBinary) { mitk::DataStorage::SetOfObjects::ConstPointer sourcenodes = m_DataStorage->GetSources(node, NULL, true); if (!sourcenodes->empty()) { topSourceNode = this->GetTopLayerNode(sourcenodes); } if (topSourceNode.IsNotNull()) { image = dynamic_cast(topSourceNode->GetData()); topSourceNode->GetIntProperty("Image.Displayed Component", component); } else { image = dynamic_cast(node->GetData()); node->GetIntProperty("Image.Displayed Component", component); } } else { image = dynamic_cast(node->GetData()); node->GetIntProperty("Image.Displayed Component", component); } } mitk::Point3D crosshairPos = this->GetCrossPosition(); std::string statusText; std::stringstream stream; itk::Index<3> p; mitk::BaseRenderer *baseRenderer = GetRenderWindow()->GetSliceNavigationController()->GetRenderer(); unsigned int timestep = baseRenderer->GetTimeStep(); if (image.IsNotNull() && (image->GetTimeSteps() > timestep)) { image->GetGeometry()->WorldToIndex(crosshairPos, p); stream.precision(2); stream << "Position: <" << std::fixed << crosshairPos[0] << ", " << std::fixed << crosshairPos[1] << ", " << std::fixed << crosshairPos[2] << "> mm"; stream << "; Index: <" << p[0] << ", " << p[1] << ", " << p[2] << "> "; mitk::ScalarType pixelValue; mitkPixelTypeMultiplex5(mitk::FastSinglePixelAccess, image->GetChannelDescriptor().GetPixelType(), image, image->GetVolumeData(baseRenderer->GetTimeStep()), p, pixelValue, component); if (fabs(pixelValue) > 1000000 || fabs(pixelValue) < 0.01) { stream << "; Time: " << baseRenderer->GetTime() << " ms; Pixelvalue: " << std::scientific << pixelValue << " "; } else { stream << "; Time: " << baseRenderer->GetTime() << " ms; Pixelvalue: " << pixelValue << " "; } } else { stream << "No image information at this position!"; } statusText = stream.str(); mitk::StatusBar::GetInstance()->DisplayGreyValueText(statusText.c_str()); */ } void QmitkCustomMultiWidget::MoveCrossToPosition(const QString& widgetID, const mitk::Point3D& newPosition) { std::shared_ptr renderWindowWidget = GetRenderWindowWidget(widgetID); if (nullptr != renderWindowWidget) { renderWindowWidget->GetSliceNavigationController()->SelectSliceByPoint(newPosition); renderWindowWidget->RequestUpdate(); return; } MITK_ERROR << "Geometry plane can not be shown for an unknown widget."; } void QmitkCustomMultiWidget::ResetCrosshair() { // #TODO: new concept: we do not want to initialize all views; // we do not want to rely on the geometry planes /* if (m_DataStorage.IsNotNull()) { m_RenderingManager->InitializeViewsByBoundingObjects(m_DataStorage); // m_RenderingManager->InitializeViews( m_DataStorage->ComputeVisibleBoundingGeometry3D() ); // reset interactor to normal slicing SetWidgetPlaneMode(PLANE_MODE_SLICING); } */ } ////////////////////////////////////////////////////////////////////////// // MOUSE EVENTS ////////////////////////////////////////////////////////////////////////// void QmitkCustomMultiWidget::wheelEvent(QWheelEvent* e) { emit WheelMoved(e); } void QmitkCustomMultiWidget::mousePressEvent(QMouseEvent* e) { } void QmitkCustomMultiWidget::moveEvent(QMoveEvent* e) { QWidget::moveEvent(e); // it is necessary to readjust the position of the overlays as the MultiWidget has moved // unfortunately it's not done by QmitkRenderWindow::moveEvent -> must be done here emit Moved(); } ////////////////////////////////////////////////////////////////////////// // PRIVATE ////////////////////////////////////////////////////////////////////////// void QmitkCustomMultiWidget::InitializeGUI() { delete m_CustomMultiWidgetLayout; m_CustomMultiWidgetLayout = new QGridLayout(this); m_CustomMultiWidgetLayout->setContentsMargins(0, 0, 0, 0); setLayout(m_CustomMultiWidgetLayout); } void QmitkCustomMultiWidget::InitializeWidget() { // #TODO: some things have to be handled globally (hold for all render window (widgets) // analyse those things and design a controlling mechanism - - // necessary here? mouse mode is valid for all render windows (and also used in editor) - //m_MouseModeSwitcher = mitk::MouseModeSwitcher::New(); - //m_MouseModeSwitcher->SetInteractionScheme(mitk::MouseModeSwitcher::InteractionScheme::MITK); } void QmitkCustomMultiWidget::InitializeDisplayActionEventHandling() { m_DisplayActionEventBroadcast = mitk::DisplayActionEventBroadcast::New(); m_DisplayActionEventBroadcast->LoadStateMachine("DisplayInteraction.xml"); m_DisplayActionEventBroadcast->SetEventConfig("DisplayConfigPACS.xml"); m_DisplayActionEventHandler = std::make_unique(); m_DisplayActionEventHandler->SetObservableBroadcast(m_DisplayActionEventBroadcast); Synchronize(true); } void QmitkCustomMultiWidget::FillLayout(int row, int column) { int r = 0; int c = 0; for (const auto& renderWindowWidget : m_RenderWindowWidgets) { AddToMultiWidgetLayout(r, c, renderWindowWidget.first); c += 1; if (c > column) { // first column c = 0; // next row r += 1; if (r > row) { return; } } } } mitk::DataNode::Pointer QmitkCustomMultiWidget::GetTopLayerNode(mitk::DataStorage::SetOfObjects::ConstPointer nodes) { // #TODO: see T24173 return nodes->front(); } diff --git a/Modules/QtWidgets/src/QmitkInteractionSchemeToolBar.cpp b/Modules/QtWidgets/src/QmitkInteractionSchemeToolBar.cpp new file mode 100644 index 0000000000..98d34e39f5 --- /dev/null +++ b/Modules/QtWidgets/src/QmitkInteractionSchemeToolBar.cpp @@ -0,0 +1,82 @@ +/*=================================================================== + +The Medical Imaging Interaction Toolkit (MITK) + +Copyright (c) German Cancer Research Center, +Division of Medical Image Computing. +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 "QmitkInteractionSchemeToolBar.h" + +#include + +QmitkInteractionSchemeToolBar::QmitkInteractionSchemeToolBar(QWidget* parent/* = nullptr*/) + : QToolBar(parent) + , m_ActionGroup(new QActionGroup(this)) + , m_InteractionSchemeSwitcher(nullptr) + , m_InteractionEventHandler(nullptr) +{ + QToolBar::setOrientation(Qt::Vertical); + QToolBar::setIconSize(QSize(17, 17)); + m_ActionGroup->setExclusive(true); // only one selectable action + + AddButton(InteractionScheme::PACSStandard, tr("Pointer"), QIcon(":/Qmitk/mm_pointer.png"), true); + AddButton(InteractionScheme::PACSLevelWindow, tr("Level/Window"), QIcon(":/Qmitk/mm_contrast.png")); + AddButton(InteractionScheme::PACSPan, tr("Pan"), QIcon(":/Qmitk/mm_pan.png")); + AddButton(InteractionScheme::PACSScroll, tr("Scroll"), QIcon(":/Qmitk/mm_scroll.png")); + AddButton(InteractionScheme::PACSZoom, tr("Zoom"), QIcon(":/Qmitk/mm_zoom.png")); + + m_InteractionSchemeSwitcher = mitk::InteractionSchemeSwitcher::New(); +} + +void QmitkInteractionSchemeToolBar::SetInteractionEventHandler(mitk::InteractionEventHandler::Pointer interactionEventHandler) +{ + if (interactionEventHandler == m_InteractionEventHandler) + { + return; + } + + m_InteractionEventHandler = interactionEventHandler; + if (nullptr != m_InteractionEventHandler) + { + m_InteractionSchemeSwitcher->SetInteractionScheme(m_InteractionEventHandler, InteractionScheme::PACSStandard); + } +} + +void QmitkInteractionSchemeToolBar::AddButton(InteractionScheme interactionScheme, const QString& toolName, const QIcon& icon, bool on) +{ + QAction* action = new QAction(icon, toolName, this); + action->setCheckable(true); + action->setActionGroup(m_ActionGroup); + action->setChecked(on); + action->setData(interactionScheme); + connect(action, SIGNAL(triggered()), this, SLOT(OnInteractionSchemeChanged())); + QToolBar::addAction(action); +} + +QmitkInteractionSchemeToolBar::~QmitkInteractionSchemeToolBar() +{ + // nothing here +} + +void QmitkInteractionSchemeToolBar::OnInteractionSchemeChanged() +{ + QAction* action = dynamic_cast(sender()); + if (action) + { + InteractionScheme interactionScheme = static_cast(action->data().toInt()); + + if (m_InteractionEventHandler) + { + m_InteractionSchemeSwitcher->SetInteractionScheme(m_InteractionEventHandler, interactionScheme); + } + } +} diff --git a/Modules/QtWidgets/src/QmitkMultiWidgetConfigurationToolBar.cpp b/Modules/QtWidgets/src/QmitkMultiWidgetConfigurationToolBar.cpp index 2fb804db98..e1f3c40eaa 100644 --- a/Modules/QtWidgets/src/QmitkMultiWidgetConfigurationToolBar.cpp +++ b/Modules/QtWidgets/src/QmitkMultiWidgetConfigurationToolBar.cpp @@ -1,91 +1,122 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical Image Computing. 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 "QmitkMultiWidgetConfigurationToolBar.h" QmitkMultiWidgetConfigurationToolBar::QmitkMultiWidgetConfigurationToolBar(QmitkCustomMultiWidget* customMultiWidget) : QToolBar(customMultiWidget) , m_CustomMultiWidget(customMultiWidget) - , m_ActionGroup(nullptr) { QToolBar::setOrientation(Qt::Vertical); QToolBar::setIconSize(QSize(17, 17)); - InitActionGroup(); + InitializeToolBar(); } QmitkMultiWidgetConfigurationToolBar::~QmitkMultiWidgetConfigurationToolBar() { // nothing here } -void QmitkMultiWidgetConfigurationToolBar::InitActionGroup() +void QmitkMultiWidgetConfigurationToolBar::InitializeToolBar() { - m_ActionGroup = new QActionGroup(this); - m_ActionGroup->setExclusive(true); - // create popup to show a widget to modify the multi widget layout m_LayoutSelectionPopup = new QmitkMultiWidgetLayoutSelectionWidget(this); m_LayoutSelectionPopup->hide(); AddButtons(); connect(m_LayoutSelectionPopup, SIGNAL(LayoutSet(int, int)), SIGNAL(LayoutSet(int, int))); } void QmitkMultiWidgetConfigurationToolBar::AddButtons() { QAction* setLayoutAction = new QAction(QIcon(":/Qmitk/cmwLayout.png"), tr("Set multi widget layout"), this); - setLayoutAction->setActionGroup(m_ActionGroup); connect(setLayoutAction, SIGNAL(triggered()), SLOT(OnSetLayout())); QToolBar::addAction(setLayoutAction); m_SynchronizeAction = new QAction(QIcon(":/Qmitk/cmwSynchronized.png"), tr("Desynchronize render windows"), this); - m_SynchronizeAction->setActionGroup(m_ActionGroup); + m_SynchronizeAction->setCheckable(true); + m_SynchronizeAction->setChecked(true); connect(m_SynchronizeAction, SIGNAL(triggered()), SLOT(OnSynchronize())); - m_Synchronized = true; - QToolBar::addAction(m_SynchronizeAction); + + QAction* setAxialViewDirectionAction = new QAction(tr("Set axial view direction"), this); + setAxialViewDirectionAction->setData(ViewDirection::Axial); + connect(setAxialViewDirectionAction, SIGNAL(triggered()), SLOT(OnViewDirectionChanged())); + + QAction* setSagittalViewDirectionAction = new QAction(tr("Set sagittal view direction"), this); + setSagittalViewDirectionAction->setData(ViewDirection::Sagittal); + connect(setSagittalViewDirectionAction, SIGNAL(triggered()), SLOT(OnViewDirectionChanged())); + + QAction* setCoronalViewDirectionAction = new QAction(tr("Set coronal view direction"), this); + setCoronalViewDirectionAction->setData(ViewDirection::Frontal); + connect(setCoronalViewDirectionAction, SIGNAL(triggered()), SLOT(OnViewDirectionChanged())); + + QToolButton* setViewDirectionToolButton = new QToolButton(this); + setViewDirectionToolButton->setIcon(QIcon(":/Qmitk/cmwViewDirection.png")); + setViewDirectionToolButton->setText(tr("Set synchronized render window view direction")); + + QMenu* menu = new QMenu(); + menu->addAction(setAxialViewDirectionAction); + menu->addAction(setSagittalViewDirectionAction); + menu->addAction(setCoronalViewDirectionAction); + setViewDirectionToolButton->setMenu(menu); + setViewDirectionToolButton->setPopupMode(QToolButton::InstantPopup); + + this->addWidget(setViewDirectionToolButton); } void QmitkMultiWidgetConfigurationToolBar::OnSetLayout() { if (nullptr != m_CustomMultiWidget) { m_LayoutSelectionPopup->setWindowFlags(Qt::Popup); m_LayoutSelectionPopup->move(this->cursor().pos()); m_LayoutSelectionPopup->show(); } } void QmitkMultiWidgetConfigurationToolBar::OnSynchronize() { - m_Synchronized = !m_Synchronized; - if (m_Synchronized) + bool synchronized = m_SynchronizeAction->isChecked(); + if (synchronized) { m_SynchronizeAction->setIcon(QIcon(":/Qmitk/cmwSynchronized.png")); m_SynchronizeAction->setText(tr("Desynchronize render windows")); + } else { m_SynchronizeAction->setIcon(QIcon(":/Qmitk/cmwDesynchronized.png")); m_SynchronizeAction->setText(tr("Synchronize render windows")); } - emit Synchronized(m_Synchronized); + m_SynchronizeAction->setChecked(synchronized); + emit Synchronized(synchronized); +} + +void QmitkMultiWidgetConfigurationToolBar::OnViewDirectionChanged() +{ + QAction* action = dynamic_cast(sender()); + if (action) + { + ViewDirection viewDirection = static_cast(action->data().toInt()); + emit ViewDirectionChanged(viewDirection); + } } diff --git a/Modules/RenderWindowManager/include/mitkRenderWindowLayerUtilities.h b/Modules/RenderWindowManager/include/mitkRenderWindowLayerUtilities.h index e119c43c10..90c176439e 100644 --- a/Modules/RenderWindowManager/include/mitkRenderWindowLayerUtilities.h +++ b/Modules/RenderWindowManager/include/mitkRenderWindowLayerUtilities.h @@ -1,61 +1,61 @@ /*=================================================================== 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 MITKRENDERWINDOWLAYERUTILITIES_H #define MITKRENDERWINDOWLAYERUTILITIES_H // render window manager module #include "MitkRenderWindowManagerExports.h" // mitk core #include #include #include /** * @brief Render window layer helper functions to retrieve the currently valid layer stack */ namespace RenderWindowLayerUtilities { - typedef std::vector RendererVector; + typedef std::vector RendererVector; typedef std::map> LayerStack; /** * The base data node of a renderer is supposed to be on layer 0 (zero), which should be the lowest layer in a render window. */ const int BASE_LAYER_INDEX = 0; /** * The top layer index, denoting that no valid (positive) layer index is given and therefore the index should be resolved into the topmost layer index. */ const int TOP_LAYER_INDEX = -1; /** * @brief Return the stack of layers of the given renderer as std::map, which guarantees ordering of the layers. * Stacked layers are only included if they have their "fixedLayer" property set to true and their "layer" property set. * * If "renderer" = nullptr: a layer stack won't be created and an empty "LayerStack" will be returned. * If "withBaseNode" = true: include the base node in the layer stack, if existing. * If "withBaseNode" = false: exclude the base node from the layer stack. * * @param dataStorage Pointer to a data storage instance whose data nodes should be checked and possibly be included. * @param renderer Pointer to the renderer instance for which the layer stack should be generated. * @param withBaseNode Boolean to decide whether the base node should be included in or excluded from the layer stack. */ MITKRENDERWINDOWMANAGER_EXPORT LayerStack GetLayerStack(const mitk::DataStorage* dataStorage, const mitk::BaseRenderer* renderer, bool withBaseNode); } // namespace RenderWindowLayerUtilities #endif // MITKRENDERWINDOWLAYERUTILITIES_H diff --git a/Modules/RenderWindowManager/include/mitkRenderWindowViewDirectionController.h b/Modules/RenderWindowManager/include/mitkRenderWindowViewDirectionController.h index 40752c35d4..f45de16ade 100644 --- a/Modules/RenderWindowManager/include/mitkRenderWindowViewDirectionController.h +++ b/Modules/RenderWindowManager/include/mitkRenderWindowViewDirectionController.h @@ -1,74 +1,84 @@ /*=================================================================== 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 MITKRENDERWINDOWVIEWDIRECTIONCONTROLLER_H #define MITKRENDERWINDOWVIEWDIRECTIONCONTROLLER_H // render window manager module #include "MitkRenderWindowManagerExports.h" #include "mitkRenderWindowLayerUtilities.h" // mitk core #include #include namespace mitk { /** * The RenderWindowViewDirectionController is used to manipulate the 'sliceNavigationController' of a given base renderer. * The 'sliceNavigationController' is used to set the view direction / camera perspective of a base renderer. * The view direction can changed to 'mitk::SliceNavigationController::Axial', 'mitk::SliceNavigationController::Frontal' * or 'mitk::SliceNavigationController::Sagittal'. * * Functions with 'mitk::BaseRenderer* renderer' have 'nullptr' as their default argument. Using the nullptr * these functions operate on all base renderer. Giving a specific base renderer will modify the node only for the given renderer. */ class MITKRENDERWINDOWMANAGER_EXPORT RenderWindowViewDirectionController { public: + using ViewDirection = mitk::SliceNavigationController::ViewDirection; + RenderWindowViewDirectionController(); /** * @brief Set the data storage on which to work. */ void SetDataStorage(DataStorage::Pointer dataStorage); /** * @brief Set the controlled base renderer. */ void SetControlledRenderer(RenderWindowLayerUtilities::RendererVector controlledRenderer); // wrapper functions to modify the view direction /** * @brief Set the view direction for the given renderer (nullptr = all renderer) - * @param viewDirection The view direction that should be used for this renderer. + * @param viewDirection The view direction that should be used for this renderer as a string. * Currently "axial", "coronal" and "sagittal" is supported. * @param renderer Pointer to the renderer instance for which the view direction should be changed. * If it is a nullptr (default) nothing happens. The view direction can not be changed * for all controlled renderer at the moment. */ void SetViewDirectionOfRenderer(const std::string &viewDirection, BaseRenderer* renderer = nullptr); + /** + * @brief Set the view direction for the given renderer (nullptr = all renderer) + * @param viewDirection The view direction that should be used for this renderer. + * @param renderer Pointer to the renderer instance for which the view direction should be changed. + * If it is a nullptr (default) nothing happens. The view direction can not be changed + * for all controlled renderer at the moment. + */ + void SetViewDirectionOfRenderer(ViewDirection viewDirection, BaseRenderer* renderer = nullptr); private: void InitializeViewByBoundingObjects(const BaseRenderer* renderer); DataStorage::Pointer m_DataStorage; RenderWindowLayerUtilities::RendererVector m_ControlledRenderer; }; } // namespace mitk #endif // MITKRENDERWINDOWVIEWDIRECTIONCONTROLLER_H diff --git a/Modules/RenderWindowManager/src/mitkRenderWindowViewDirectionController.cpp b/Modules/RenderWindowManager/src/mitkRenderWindowViewDirectionController.cpp index 63df9a913e..929cc73d00 100644 --- a/Modules/RenderWindowManager/src/mitkRenderWindowViewDirectionController.cpp +++ b/Modules/RenderWindowManager/src/mitkRenderWindowViewDirectionController.cpp @@ -1,110 +1,132 @@ /*=================================================================== 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 "mitkRenderWindowViewDirectionController.h" // mitk #include #include #include mitk::RenderWindowViewDirectionController::RenderWindowViewDirectionController() : m_DataStorage(nullptr) { // nothing here } void mitk::RenderWindowViewDirectionController::SetDataStorage(DataStorage::Pointer dataStorage) { if (m_DataStorage != dataStorage) { // set the new data storage m_DataStorage = dataStorage; } } void mitk::RenderWindowViewDirectionController::SetControlledRenderer(RenderWindowLayerUtilities::RendererVector controlledRenderer) { if (m_ControlledRenderer != controlledRenderer) { // set the new set of controlled renderer m_ControlledRenderer = controlledRenderer; } } void mitk::RenderWindowViewDirectionController::SetViewDirectionOfRenderer(const std::string &viewDirection, BaseRenderer* renderer /*=nullptr*/) { if (nullptr == renderer) { - // set visibility of data node in all controlled renderer for (auto& renderer : m_ControlledRenderer) { if (renderer.IsNotNull()) { - //SetViewDirectionOfRenderer(viewDirection, renderer); + SetViewDirectionOfRenderer(viewDirection, renderer); } } } else { mitk::SliceNavigationController* sliceNavigationController = renderer->GetSliceNavigationController(); if ("axial" == viewDirection) { - sliceNavigationController->SetDefaultViewDirection(mitk::SliceNavigationController::Axial); + sliceNavigationController->SetDefaultViewDirection(ViewDirection::Axial); } else if ("coronal" == viewDirection) { - sliceNavigationController->SetDefaultViewDirection(mitk::SliceNavigationController::Frontal); + sliceNavigationController->SetDefaultViewDirection(ViewDirection::Frontal); } else if ("sagittal" == viewDirection) { - sliceNavigationController->SetDefaultViewDirection(mitk::SliceNavigationController::Sagittal); + sliceNavigationController->SetDefaultViewDirection(ViewDirection::Sagittal); } // initialize the views to the bounding geometry InitializeViewByBoundingObjects(renderer); } } +void mitk::RenderWindowViewDirectionController::SetViewDirectionOfRenderer(ViewDirection viewDirection , BaseRenderer* renderer /*=nullptr*/) +{ + if (nullptr == renderer) + { + // set visibility of data node in all controlled renderer + for (auto& renderer : m_ControlledRenderer) + { + if (renderer.IsNotNull()) + { + SetViewDirectionOfRenderer(viewDirection, renderer); + } + } + } + else + { + mitk::SliceNavigationController* sliceNavigationController = renderer->GetSliceNavigationController(); + sliceNavigationController->SetDefaultViewDirection(viewDirection); + + // initialize the views to the bounding geometry + InitializeViewByBoundingObjects(renderer); + } +} + void mitk::RenderWindowViewDirectionController::InitializeViewByBoundingObjects(const BaseRenderer* renderer) { if (nullptr == m_DataStorage || nullptr == renderer) { return; } // get all nodes that have not set "includeInBoundingBox" to false mitk::NodePredicateProperty::Pointer includeInBoundingBox = mitk::NodePredicateProperty::New("includeInBoundingBox", mitk::BoolProperty::New(false)); mitk::NodePredicateNot::Pointer notIncludeInBoundingBox = mitk::NodePredicateNot::New(includeInBoundingBox); // get all non-helper objects mitk::NodePredicateProperty::Pointer helperObject = mitk::NodePredicateProperty::New("helper object", mitk::BoolProperty::New(true)); mitk::NodePredicateNot::Pointer notAHelperObject = mitk::NodePredicateNot::New(helperObject); // get all nodes that have a fixed layer for the given renderer mitk::NodePredicateProperty::Pointer fixedLayer = mitk::NodePredicateProperty::New("fixedLayer", mitk::BoolProperty::New(true), renderer); // combine node predicates mitk::NodePredicateAnd::Pointer combinedNodePredicate = mitk::NodePredicateAnd::New(notIncludeInBoundingBox, notAHelperObject, fixedLayer); mitk::DataStorage::SetOfObjects::ConstPointer filteredDataNodes = m_DataStorage->GetSubset(combinedNodePredicate); // calculate bounding geometry of these nodes mitk::TimeGeometry::Pointer bounds = m_DataStorage->ComputeBoundingGeometry3D(filteredDataNodes, "visible", renderer); // initialize the views to the bounding geometry mitk::RenderingManager::GetInstance()->InitializeView(renderer->GetRenderWindow(), bounds); } \ No newline at end of file diff --git a/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/CMakeLists.txt b/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/CMakeLists.txt index c75e38d7a8..308d5992c8 100644 --- a/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/CMakeLists.txt +++ b/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/CMakeLists.txt @@ -1,7 +1,7 @@ project(org_mitk_gui_qt_custommultiwidgeteditor) mitk_create_plugin( EXPORT_DIRECTIVE CUSTOMMULTIWIDGETEDITOR_EXPORT EXPORTED_INCLUDE_SUFFIXES src - MODULE_DEPENDS MitkQtWidgets + MODULE_DEPENDS MitkQtWidgets MitkRenderWindowManager ) diff --git a/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/src/QmitkCustomMultiWidgetEditor.cpp b/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/src/QmitkCustomMultiWidgetEditor.cpp index e64a4f2b89..15691268c3 100644 --- a/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/src/QmitkCustomMultiWidgetEditor.cpp +++ b/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/src/QmitkCustomMultiWidgetEditor.cpp @@ -1,228 +1,263 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical Image Computing. 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 "QmitkCustomMultiWidgetEditor.h" #include #include #include #include #include // mitk core #include #include const QString QmitkCustomMultiWidgetEditor::EDITOR_ID = "org.mitk.editors.custommultiwidget"; QmitkCustomMultiWidgetEditor::QmitkCustomMultiWidgetEditor() : m_CustomMultiWidget(nullptr) - , m_MouseModeSwitcher(nullptr) + , m_InteractionSchemeToolBar(nullptr) , m_ConfigurationToolBar(nullptr) { // nothing here } QmitkCustomMultiWidgetEditor::~QmitkCustomMultiWidgetEditor() { // nothing here } void QmitkCustomMultiWidgetEditor::Activated() { // nothing here } void QmitkCustomMultiWidgetEditor::Deactivated() { // nothing here } void QmitkCustomMultiWidgetEditor::Visible() { // nothing here } void QmitkCustomMultiWidgetEditor::Hidden() { // nothing here } QmitkRenderWindow* QmitkCustomMultiWidgetEditor::GetActiveQmitkRenderWindow() const { if (nullptr != m_CustomMultiWidget) { return m_CustomMultiWidget->GetActiveRenderWindowWidget()->GetRenderWindow(); } return nullptr; } QHash QmitkCustomMultiWidgetEditor::GetQmitkRenderWindows() const { QHash result; if (nullptr == m_CustomMultiWidget) { return result; } // create QHash on demand QmitkCustomMultiWidget::RenderWindowWidgetMap renderWindowWidgets = m_CustomMultiWidget->GetRenderWindowWidgets(); for (const auto& renderWindowWidget : renderWindowWidgets) { result.insert(renderWindowWidget.first, renderWindowWidget.second->GetRenderWindow()); } return result; } QmitkRenderWindow* QmitkCustomMultiWidgetEditor::GetQmitkRenderWindow(const QString& id) const { if (nullptr == m_CustomMultiWidget) { return nullptr; } return m_CustomMultiWidget->GetRenderWindow(id); } mitk::Point3D QmitkCustomMultiWidgetEditor::GetSelectedPosition(const QString& id) const { if (nullptr == m_CustomMultiWidget) { return mitk::Point3D(); } return m_CustomMultiWidget->GetCrossPosition(id); } void QmitkCustomMultiWidgetEditor::SetSelectedPosition(const mitk::Point3D& pos, const QString& id) { if (nullptr != m_CustomMultiWidget) { m_CustomMultiWidget->MoveCrossToPosition(id, pos); } } void QmitkCustomMultiWidgetEditor::EnableDecorations(bool enable, const QStringList& decorations) { m_MultiWidgetDecorationManager->ShowDecorations(enable, decorations); } bool QmitkCustomMultiWidgetEditor::IsDecorationEnabled(const QString& decoration) const { return m_MultiWidgetDecorationManager->IsDecorationVisible(decoration); } QStringList QmitkCustomMultiWidgetEditor::GetDecorations() const { return m_MultiWidgetDecorationManager->GetDecorations(); } void QmitkCustomMultiWidgetEditor::EnableSlicingPlanes(bool enable) { // #TODO: nothing here } bool QmitkCustomMultiWidgetEditor::IsSlicingPlanesEnabled() const { // #TODO: nothing here return false; } QmitkCustomMultiWidget* QmitkCustomMultiWidgetEditor::GetCustomMultiWidget() { return m_CustomMultiWidget; } void QmitkCustomMultiWidgetEditor::OnLayoutSet(int row, int column) { m_CustomMultiWidget->ResetLayout(row, column); + SetControlledRenderer(); } void QmitkCustomMultiWidgetEditor::OnSynchronize(bool synchronized) { m_CustomMultiWidget->Synchronize(synchronized); } +void QmitkCustomMultiWidgetEditor::OnViewDirectionChanged(mitk::SliceNavigationController::ViewDirection viewDirection) +{ + m_RenderWindowViewDirectionController->SetViewDirectionOfRenderer(viewDirection); +} + ////////////////////////////////////////////////////////////////////////// // PRIVATE ////////////////////////////////////////////////////////////////////////// void QmitkCustomMultiWidgetEditor::SetFocus() { if (nullptr != m_CustomMultiWidget) { m_CustomMultiWidget->setFocus(); } } void QmitkCustomMultiWidgetEditor::CreateQtPartControl(QWidget* parent) { if (nullptr == m_CustomMultiWidget) { QHBoxLayout* layout = new QHBoxLayout(parent); layout->setContentsMargins(0, 0, 0, 0); berry::IBerryPreferences* preferences = dynamic_cast(GetPreferences().GetPointer()); mitk::BaseRenderer::RenderingMode::Type renderingMode = static_cast(preferences->GetInt("Rendering Mode", 0)); m_CustomMultiWidget = new QmitkCustomMultiWidget(parent, 0, 0, renderingMode); - // create left toolbar: mouse mode toolbar to switch how the render window navigation behaves - if (nullptr == m_MouseModeSwitcher) + // create left toolbar: interaction scheme toolbar to switch how the render window navigation behaves + if (nullptr == m_InteractionSchemeToolBar) { - m_MouseModeSwitcher = new QmitkMouseModeSwitcher(parent); - layout->addWidget(m_MouseModeSwitcher); + m_InteractionSchemeToolBar = new QmitkInteractionSchemeToolBar(parent); + layout->addWidget(m_InteractionSchemeToolBar); } - m_MouseModeSwitcher->setMouseModeSwitcher(m_CustomMultiWidget->GetMouseModeSwitcher()); + m_InteractionSchemeToolBar->SetInteractionEventHandler(m_CustomMultiWidget->GetInteractionEventHandler()); // add center widget: the custom multi widget layout->addWidget(m_CustomMultiWidget); m_CustomMultiWidget->SetDataStorage(GetDataStorage()); m_CustomMultiWidget->InitializeRenderWindowWidgets(); // create right toolbar: configuration toolbar to change the render window widget layout if (nullptr == m_ConfigurationToolBar) { m_ConfigurationToolBar = new QmitkMultiWidgetConfigurationToolBar(m_CustomMultiWidget); layout->addWidget(m_ConfigurationToolBar); } connect(m_ConfigurationToolBar, SIGNAL(LayoutSet(int, int)), SLOT(OnLayoutSet(int, int))); connect(m_ConfigurationToolBar, SIGNAL(Synchronized(bool)), SLOT(OnSynchronize(bool))); + connect(m_ConfigurationToolBar, SIGNAL(ViewDirectionChanged(mitk::SliceNavigationController::ViewDirection)), SLOT(OnViewDirectionChanged(mitk::SliceNavigationController::ViewDirection))); + m_MultiWidgetDecorationManager = std::make_unique(m_CustomMultiWidget); + m_RenderWindowViewDirectionController = std::make_unique(); + m_RenderWindowViewDirectionController->SetDataStorage(GetDataStorage()); + SetControlledRenderer(); + OnPreferencesChanged(preferences); } } void QmitkCustomMultiWidgetEditor::OnPreferencesChanged(const berry::IBerryPreferences* preferences) { // update decoration preferences m_MultiWidgetDecorationManager->DecorationPreferencesChanged(preferences); // zooming and panning preferences bool constrainedZooming = preferences->GetBool("Use constrained zooming and panning", true); mitk::RenderingManager::GetInstance()->SetConstrainedPanningZooming(constrainedZooming); // level window preferences bool showLevelWindowWidget = preferences->GetBool("Show level-window widget", true); m_CustomMultiWidget->ShowAllLevelWindowWidgets(showLevelWindowWidget); mitk::RenderingManager::GetInstance()->InitializeViewsByBoundingObjects(GetDataStorage()); mitk::RenderingManager::GetInstance()->RequestUpdateAll(); } + +void QmitkCustomMultiWidgetEditor::SetControlledRenderer() +{ + if (nullptr == m_RenderWindowViewDirectionController || nullptr == m_CustomMultiWidget) + { + return; + } + + RenderWindowLayerUtilities::RendererVector controlledRenderer; + auto renderWindowWidgets = m_CustomMultiWidget->GetRenderWindowWidgets(); + for (const auto& renderWindowWidget : renderWindowWidgets) + { + auto renderWindow = renderWindowWidget.second->GetRenderWindow(); + auto vtkRenderWindow = renderWindow->GetRenderWindow(); + mitk::BaseRenderer* baseRenderer = mitk::BaseRenderer::GetInstance(vtkRenderWindow); + if (nullptr != baseRenderer) + { + controlledRenderer.push_back(baseRenderer); + } + } + + m_RenderWindowViewDirectionController->SetControlledRenderer(controlledRenderer); +} diff --git a/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/src/QmitkCustomMultiWidgetEditor.h b/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/src/QmitkCustomMultiWidgetEditor.h index 4036fe03a9..598862755a 100644 --- a/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/src/QmitkCustomMultiWidgetEditor.h +++ b/Plugins/org.mitk.gui.qt.custommultiwidgeteditor/src/QmitkCustomMultiWidgetEditor.h @@ -1,142 +1,150 @@ /*=================================================================== The Medical Imaging Interaction Toolkit (MITK) Copyright (c) German Cancer Research Center, Division of Medical Image Computing. 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 QMITKCUSTOMMULTIWIDGETEDITOR_H #define QMITKCUSTOMMULTIWIDGETEDITOR_H #include #include #include // custom multi widget editor #include #include "QmitkMultiWidgetDecorationManager.h" -// qt widgets module +// mitk qt widgets module #include -#include +#include #include +// mitk render window manager +#include + #include class QmitkMouseModeSwitcher; class CUSTOMMULTIWIDGETEDITOR_EXPORT QmitkCustomMultiWidgetEditor final : public QmitkAbstractRenderEditor, public mitk::ILifecycleAwarePart, public mitk::ILinkedRenderWindowPart { Q_OBJECT public: berryObjectMacro(QmitkCustomMultiWidgetEditor) static const QString EDITOR_ID; QmitkCustomMultiWidgetEditor(); ~QmitkCustomMultiWidgetEditor(); /** * @brief Overridden from mitk::ILifecycleAwarePart */ virtual void Activated() override; /** * @brief Overridden from mitk::ILifecycleAwarePart */ virtual void Deactivated() override; /** * @brief Overridden from mitk::ILifecycleAwarePart */ virtual void Visible() override; /** * @brief Overridden from mitk::ILifecycleAwarePart */ virtual void Hidden() override; /** * @brief Overridden from mitk::ILinkedRenderWindowPart : IRenderWindowPart */ virtual QmitkRenderWindow* GetActiveQmitkRenderWindow() const override; /** * @brief Overridden from mitk::ILinkedRenderWindowPart : IRenderWindowPart */ virtual QHash GetQmitkRenderWindows() const override; /** * @brief Overridden from mitk::ILinkedRenderWindowPart : IRenderWindowPart */ virtual QmitkRenderWindow* GetQmitkRenderWindow(const QString& id) const override; /** * @brief Overridden from mitk::ILinkedRenderWindowPart : IRenderWindowPart */ virtual mitk::Point3D GetSelectedPosition(const QString& id = QString()) const override; /** * @brief Overridden from mitk::ILinkedRenderWindowPart : IRenderWindowPart */ virtual void SetSelectedPosition(const mitk::Point3D& pos, const QString& id = QString()) override; /** * @brief Overridden from mitk::ILinkedRenderWindowPart : IRenderWindowPart */ virtual void EnableDecorations(bool enable, const QStringList& decorations = QStringList()) override; /** * @brief Overridden from mitk::ILinkedRenderWindowPart : IRenderWindowPart */ virtual bool IsDecorationEnabled(const QString& decoration) const override; /** * @brief Overridden from mitk::ILinkedRenderWindowPart : IRenderWindowPart */ virtual QStringList GetDecorations() const override; /** * @brief Overridden from mitk::ILinkedRenderWindowPart */ virtual void EnableSlicingPlanes(bool enable) override; /** * @brief Overridden from mitk::ILinkedRenderWindowPart */ virtual bool IsSlicingPlanesEnabled() const override; QmitkCustomMultiWidget* GetCustomMultiWidget(); private slots: void OnLayoutSet(int row, int column); void OnSynchronize(bool synchronized); + void OnViewDirectionChanged(mitk::SliceNavigationController::ViewDirection viewDirection); private: /** * @brief Overridden from QmitkAbstractRenderEditor */ virtual void SetFocus() override; /** * @brief Overridden from QmitkAbstractRenderEditor */ virtual void CreateQtPartControl(QWidget* parent) override; /** * @brief Overridden from QmitkAbstractRenderEditor */ virtual void OnPreferencesChanged(const berry::IBerryPreferences* preferences) override; + + void SetControlledRenderer(); /** * @brief * * */ void RequestActivateMenuWidget(bool on); QmitkCustomMultiWidget* m_CustomMultiWidget; - QmitkMouseModeSwitcher* m_MouseModeSwitcher; + QmitkInteractionSchemeToolBar* m_InteractionSchemeToolBar; QmitkMultiWidgetConfigurationToolBar* m_ConfigurationToolBar; std::unique_ptr m_MultiWidgetDecorationManager; + std::unique_ptr m_RenderWindowViewDirectionController; + }; #endif // QMITKCUSTOMMULTIWIDGETEDITOR_H