diff --git a/Plugins/PluginList.cmake b/Plugins/PluginList.cmake
index b4ff345857..6c452fede7 100644
--- a/Plugins/PluginList.cmake
+++ b/Plugins/PluginList.cmake
@@ -1,51 +1,52 @@
# Plug-ins must be ordered according to their dependencies
set(MITK_EXT_PLUGINS
org.mitk.core.services:ON
org.mitk.gui.common:ON
org.mitk.planarfigure:ON
org.mitk.core.ext:OFF
org.mitk.core.jobs:OFF
org.mitk.diffusionimaging:OFF
org.mitk.simulation:OFF
org.mitk.gui.qt.application:ON
org.mitk.gui.qt.coreapplication:OFF
org.mitk.gui.qt.ext:OFF
org.mitk.gui.qt.extapplication:OFF
org.mitk.gui.qt.common:ON
org.mitk.gui.qt.stdmultiwidgeteditor:ON
org.mitk.gui.qt.common.legacy:OFF
org.mitk.gui.qt.cmdlinemodules:OFF
org.mitk.gui.qt.diffusionimagingapp:OFF
org.mitk.gui.qt.datamanager:ON
org.mitk.gui.qt.datamanagerlight:OFF
org.mitk.gui.qt.properties:ON
org.mitk.gui.qt.basicimageprocessing:OFF
org.mitk.gui.qt.dicom:OFF
org.mitk.gui.qt.diffusionimaging:OFF
org.mitk.gui.qt.dtiatlasapp:OFF
org.mitk.gui.qt.geometrytools:OFF
org.mitk.gui.qt.igtexamples:OFF
org.mitk.gui.qt.igttracking:OFF
org.mitk.gui.qt.imagecropper:OFF
org.mitk.gui.qt.imagenavigator:ON
org.mitk.gui.qt.viewnavigator:OFF
org.mitk.gui.qt.materialeditor:OFF
org.mitk.gui.qt.measurementtoolbox:OFF
org.mitk.gui.qt.moviemaker:OFF
org.mitk.gui.qt.pointsetinteraction:OFF
org.mitk.gui.qt.python:OFF
org.mitk.gui.qt.registration:OFF
org.mitk.gui.qt.remeshing:OFF
org.mitk.gui.qt.segmentation:OFF
org.mitk.gui.qt.simulation:OFF
org.mitk.gui.qt.aicpregistration:OFF
org.mitk.gui.qt.toftutorial:OFF
org.mitk.gui.qt.tofutil:OFF
org.mitk.gui.qt.ugvisualization:OFF
org.mitk.gui.qt.ultrasound:OFF
org.mitk.gui.qt.volumevisualization:OFF
org.mitk.gui.qt.eventrecorder:OFF
org.mitk.gui.qt.xnat:OFF
+ org.mitk.gui.qt.multilabelsegmentation:ON
)
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/CMakeLists.txt b/Plugins/org.mitk.gui.qt.multilabelsegmentation/CMakeLists.txt
new file mode 100644
index 0000000000..2f2d9179b6
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/CMakeLists.txt
@@ -0,0 +1,9 @@
+project(org_mitk_gui_qt_multilabelsegmentation)
+
+include_directories(${CTK_INCLUDE_DIRS})
+
+MACRO_CREATE_MITK_CTK_PLUGIN(
+ EXPORT_DIRECTIVE MITK_QT_SEGMENTATION
+ EXPORTED_INCLUDE_SUFFIXES src
+ MODULE_DEPENDS MitkSegmentation MitkSegmentationUI
+)
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/QmitkSegmentationTechnical.dox b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/QmitkSegmentationTechnical.dox
new file mode 100644
index 0000000000..b8992e8a55
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/QmitkSegmentationTechnical.dox
@@ -0,0 +1,101 @@
+/**
+
+\page QmitkSegmentationTechnicalPage Technical design of QmitkSegmentation
+
+\li \ref QmitkSegmentationTechnicalPage2
+\li \ref QmitkSegmentationTechnicalPage3
+\li \ref QmitkSegmentationTechnicalPage4
+
+\section QmitkSegmentationTechnicalPage2 Introduction
+
+QmitkSegmentation was designed for the liver resection planning
+project "ReLiver".
+The goal was a stable, well-documented, extensible, and testable
+re-implementation of a functionality called "ERIS", which was used for manual
+segmentation in 2D slices of 3D or 3D+t images.
+Re-implementation was chosen because it seemed to be easier to write
+documentation and tests for newly developed code. In addition, the old code had
+some design weaknesses (e.g. a monolithic class), which would be hard to
+maintain in the future.
+
+By now Segmentation is a well tested and easily extensible vehicle for all kinds of interactive
+segmentation applications. A separate page describes how you can extend Segmentation with new
+tools in a shared object (DLL): \ref toolextensions.
+
+\section QmitkSegmentationTechnicalPage3 Overview of tasks
+
+We identified the following major tasks:
+
+
+ Management of images : what is the original patient image, what
+images are the active segmentations?
+ Management of drawing tools : there is a set of drawing tools, one at
+a time is active, that is, someone has to decide which tool will receive mouse
+(and other) events.
+ Drawing tools : each tool can modify a segmentation in reaction to
+user interaction. To do so, the tools have to know about the relevant images.
+ Slice manipulation : drawing tools need to have means to extract a
+single slice from an image volume and to write a single slice back into an image
+volume.
+ Interpolation of unsegmented slices : some class has to keep track of
+all the segmentations in a volume and generate suggestions for missing slices.
+This should be possible in all three orthogonal slice direction.
+ Undo : Slice manipulations should be undoable, no matter whether a
+tool or the interpolation mechanism changed something.
+ GUI : Integration of everything.
+
+
+
+\section QmitkSegmentationTechnicalPage4 Classes involved
+
+The above blocks correspond to a number of classes. Here is an overview of all
+related classes with their responsibilities and relations:
+
+\imageMacro{"interactive_segmentation_classes.png","html",12}
+
+
+ Management of images : mitk::ToolManager has a set of reference
+data (original images) and a second set of working data (segmentations).
+mitk::Tool objects know a ToolManager and can ask the manager for the currently
+relevant images. There are two GUI elements that enable
+the user to modify the set of reference and working images (QmitkToolReferenceDataSelectionBox and QmitkToolWorkingDataSelectionBox). GUI and non-GUI
+classes are coupled by itk::Events (non-GUI to GUI) and direct method calls (GUI
+to non-GUI).
+ Management of drawing tools : As a second task, ToolManager manages all available tools and makes sure that one at a time is able to receive MITK events.
+The GUI for selecting tools is implemented in QmitkToolSelectionBox.
+ Drawing tools : Drawing tools all inherit from mitk::Tool, which is a
+mitk::StateMachine. There is a number of derivations from Tool, each offering
+some helper methods for specific sub-classes, like manipulation of 2D slices.
+Tools are instantiated through the itk::ObjectFactory, which means that there is
+also one factory for each tool (e.g. mitk::AddContourToolFactory). For the GUI representation, each tool has an
+identification, consisting of a name and an icon (XPM). The actual drawing
+methods are mainly implemented in mitk::SegTool2D (helper methods) and its
+sub-classes for region growing, freehand drawing, etc.
+ Slice manipulation : There are two filters for manipulation of slices
+inside a 3D image volume. mitk::ExtractImageFilter retrieves a single 2D slice
+from a 3D volume. mitk::OverwriteSliceImageFilter replaces a slice inside a 3D
+volume with a second slice which is a parameter to the filter. These classes are
+used extensively by most of the tools to fulfill their task.
+mitk::OverwriteSliceImageFilter cooperates with the interpolation classes to
+inform them of single slice modifications.
+ Interpolation of unsegmented slices : There are two classes involved
+in interpolation: mitk::SegmentationInterpolationController knows a mitk::Image (the
+segmentation) and scans its contents for slices with non-zero pixels. It keeps
+track of changes in the image and is always able to tell, which neighbors of a
+slice (in the three orthogonal slice directions) contain segmentations. The
+class also performs this interpolation for single slices on demand.
+Again, we have a second class responsible for the GUI:
+QmitkSlicesInterpolator enables/disables interpolation and offers to
+accept interpolations for one or all slices.
+ Undo : Undo functionality is implemented in mitk::OverwriteSliceImageFilter,
+since this is the central place where all image modifications are made. The filter stores a binary difference image
+to the undo stack as a mitk::ApplyDiffImageOperation. When the user requests undo, this ApplyDiffImageOperation
+will be executed by a singleton class DiffImageApplier. The operation itself observes the image, which it refers to,
+for itk::DeleteEvent, so no undo operation will be executed on/for images that have already been destroyed.
+ GUI : The top-level GUI is the functionality
+QmitkSegmentation, which is very thin in comparison to ERIS. There are
+separate widgets for image and tool selection, for interpolation. Additionaly,
+there are some methods to create, delete, crop, load and save segmentations.
+
+
+**/
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/ToolExtensionsGeneralOverview.dox b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/ToolExtensionsGeneralOverview.dox
new file mode 100644
index 0000000000..6df1762137
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/ToolExtensionsGeneralOverview.dox
@@ -0,0 +1,181 @@
+/**
+
+\page toolextensions How to extend the Segmentation view with external tools
+
+
+ \ref ToolExtensionsGeneralOverview2
+ \ref ToolExtensionsGeneralOverview3
+
+ \ref ToolExtensionsGeneralOverview31
+ \ref ToolExtensionsGeneralOverview32
+ \ref ToolExtensionsGeneralOverview33
+
+ \ref ToolExtensionsGeneralOverview4
+ \ref ToolExtensionsGeneralOverview5
+ \ref ToolExtensionsGeneralOverview6
+
+
+\section ToolExtensionsGeneralOverview2 Introduction
+
+The application for manual segmentation in MITK (Segmentation view) comes
+with a tool class framework that is extensible with new tools (description at
+\ref QmitkSegmentationTechnicalPage). The usual way
+to create new tools (since it is mostly used inside DKFZ) is to just add new
+files to the MITK source code tree. However, this requires to be familiar with
+the MITK build system and turnaround time during development might be long
+(recompiling parts of MITK again and again).
+
+For external users who just want to use
+MITK as a library and application, there is a way to create new segmentation
+tools in an MITK external project, which will compile the new tools into a
+shared object (DLL). Such shared objects can be loaded via the ITK object factory
+and its autoload feature on application startup. This document describes
+how to build such external extensions.
+
+Example files can be found in the MITK source code in the directory
+${MITK_SOURCE_DIR}/QApplications/ToolExtensionsExample/ .
+
+\section ToolExtensionsGeneralOverview3 What might be part of an extension
+
+The extension concept assumes that you want to create one or several new
+interactive segmentation tools for Segmentation or another MITK
+functionality that uses the tools infrastructure. In the result you
+will create a shared object (DLL), which contains several tools and their GUI
+counterparts, plus optional code that your extension requires. The following
+sections shortly describe each of these parts.
+
+\subsection ToolExtensionsGeneralOverview31 Tool classes
+
+A tool is basically any subclass of mitk::Tool. Tools are created at runtime
+through the ITK object factory (so they inherit from itk::Object). Tools
+should handle the interaction part of a segmentation method, i.e. create
+seed points, draw contours, etc., in order to parameterize segmentation algorithms.
+Simple algorithms can even be part of a tool. A tools is identified by icon (XPM format),
+name (short string) and optionally a group name (e.g. the group name for Segmentation
+is "default").
+
+There is a naming convention : you should put a tool called \c mitk::ExternalTool into
+files called \c mitkExternalTool.h and \c mitkExternalTool.cpp. This is \e required if
+you use the convenience macros described below, because there need to be ITK factories,
+which names are directly derived from the file names of the tools. For the example of mitk::ExternalTool
+there would be a factory called \c mitk::ExternalToolFactory in a file named \c mitkExternalToolFactory.cpp.
+
+\subsection ToolExtensionsGeneralOverview32 GUI classes for tools
+
+Tools are non-graphical classes that only implement interactions in renderwindows. However,
+some tools will need a means to allow the user to set some parameters -- a graphical user interface, GUI.
+In the Qt3 case, tool GUIs inherit from QmitkToolGUI, which is a mixture of QWidget and itk::Object.
+Tool GUIs are also created through the ITK object factory.
+
+Tools inform their GUIs about state changes by messages. Tool GUIs communicate with their associated tools
+via direct method calls (they know their tools). See mitk::BinaryThresholdTool for examples.
+
+Again a naming convention : if the convenience macros for tool extension shared objects are used,
+you have to put a tool GUI called \c QmitkExternalToolGUI into a files named \c QmitkExternalToolGUI.cpp
+and \c QmitkExternalToolGUI.h. The convenience macro will create a factory called \c QmitkExternalToolGUIFactory
+into a file named \c QmitkExternalToolGUIFactory.cpp.
+
+\subsection ToolExtensionsGeneralOverview33 Additional files
+
+If you are writing tools MITK externally, these tools might depend on additional files, e.g.
+segmentation algorithms. These can also be compiled into a tool extension shared object.
+
+\section ToolExtensionsGeneralOverview4 Writing a CMake file for a tool extension
+
+Summing up the last section, an example tool extension could comprise the following files:
+\verbatim
+mitkExternalTool.h \
+mitkExternalTool.xpm >--- implementing mitk::ExternalTool (header, icon, implementation)
+mitkExternalTool.cpp /
+
+QmitkExternalToolGUI.h ,-- implementing a GUI for mitk::ExternalTool
+QmitkExternalToolGUI.cpp /
+
+externalalgorithm.h \
+externalalgorithm.cpp \
+externalalgorithmsolver.h >-- a couple of files (not related to MITK tools)
+externalalgorithmsolver.cpp /
+\endverbatim
+
+This should all be compiled into one shared object. Just like ITK, VTK and MITK we
+will use CMake for this purpose (I assume you either know or are willing to learn about
+www.cmake.org )
+A CMake file for the above example would look like this:
+
+\code
+project( ExternalTool )
+
+find_package(ITK)
+find_package(MITK)
+find_package(Qt3)
+
+add_definitions(${QT_DEFINITIONS})
+
+set( TOOL_QT3GUI_FILES
+ QmitkExternalToolGUI.cpp
+ )
+
+set( TOOL_FILES
+ mitkExternalTool.cpp
+ )
+
+set( TOOL_ADDITIONAL_CPPS
+ externalalgorithm.cpp
+ externalalgorithmsolver.cpp
+ )
+
+set( TOOL_ADDITIONAL_MOC_H
+)
+
+MITK_GENERATE_TOOLS_LIBRARY(mitkExternalTools)
+\endcode
+
+Basically, you only have to change the definitions of \c TOOL_FILES and, optionally,
+\c TOOL_QT3GUI_FILES, \c TOOL_ADDITIONAL_CPPS and \c TOOL_ADDITIONAL_MOC_H.
+For all .cpp files in \c TOOL_FILES and \c TOOL_QT3GUI_FILES there will be factories
+created assuming the naming conventions described in the sections above.
+Files listed in \c TOOL_ADDITIONAL_CPPS will just be compiled. Files listed in
+\c TOOL_ADDITIONAL_MOC_H will be run through Qts meta object compiler \c moc --
+this is neccessary for all objects that have the Q_OBJECT macro in their declaration.
+\c moc will create new files that will also be compiled into the library.
+
+\section ToolExtensionsGeneralOverview5 Compiling the extension
+
+For compiling a tool extension, you will need a compiled version of MITK. We will
+assume MITK was compiled into /home/user/mitk/debug. You need to build MITK with
+BUILD_SHARED_CORE turned on!
+
+You build the tool extension just like any other CMake based project:
+\li know where your source code is (e.g. /home/user/mitk/tool-extension-src)
+\li change into the directory, where you want to compile the shared object (e.g. /home/user/mitk/tool-extension-debug)
+\li invoke cmake: ccmake /home/user/mitk/tool-extension-src
+\li configure (press c or the "configure" button)
+\li set the ITK_DIR variable to the directory, where you compiled ITK
+\li set the MITK_DIR variable to the directory, where you compiled MITK: /home/user/mitk/debug
+\li configure (press "c" or the "configure" button)
+\li generate (press "g" or the "generate" button)
+
+This should do it and leave you with a or project file or Makefile that you can compile (using make or VisualStudio).
+
+\section ToolExtensionsGeneralOverview6 Configuring ITK autoload
+
+If the compile succeeds, you will get a library mitkExternalTools.dll or libmitkExternalTools.so.
+This library exports a symbol \c itkLoad which is expected by the ITK object factory.
+
+On application startup the ITK object factory will search a list of directories from
+the environment variable \c ITK_AUTOLOAD_PATH. Set this environment variable to your
+binary directory (/home/user/mitk/tool-extension-debug ).
+
+The ITK object factory will load all shared objects that it finds in the specified directories
+and will test if they contain a symbol (function pointer) \c itkLoad, which is expected
+to return a pointer to a itk::ObjectFactoryBase instance. If such a symbol is found, the
+returned factory will be registered with the ITK object factory.
+
+If you successfully followed all the steps above, MITK will find your mitk::ExternalTool on
+application startup, when the ITK object factory is asked to create all known instances of
+mitk::Tool. Furthermore, if your mitk::ExternalTool claims to be part of the "default" group,
+there will be a new icon in Segmentation, which activates your tool.
+
+Have fun! (And Windows users: welcome to the world of DLLs)
+
+**/
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/interactive_segmentation_classes.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/interactive_segmentation_classes.png
new file mode 100644
index 0000000000..9a9a4382f7
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/interactive_segmentation_classes.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/interactive_segmentation_classes.xcf b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/interactive_segmentation_classes.xcf
new file mode 100644
index 0000000000..6e37987eb4
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/interactive_segmentation_classes.xcf differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/multilabelsegmentation.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/multilabelsegmentation.png
new file mode 100644
index 0000000000..d13c72b5b6
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/multilabelsegmentation.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_multilabelsegmentation.dox b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_multilabelsegmentation.dox
new file mode 100644
index 0000000000..590a1d9e9d
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_multilabelsegmentation.dox
@@ -0,0 +1,395 @@
+/**
+\page org_mitk_views_multilabelsegmentation User Manual
+
+\imageMacro{"multilabelsegmentation.png", "html", 12}
+
+Some of the features described below are closed source additions to the open source toolkit MITK and are not
+available in every application.
+
+Available sections:
+
+ - \ref org_mitk_gui_qt_segmentationUserManualOverview
+ - \ref org_mitk_gui_qt_segmentationUserManualTechnical
+ - \ref org_mitk_gui_qt_segmentationUserManualCreateOpenSaveImportAdd
+ - \ref org_mitk_gui_qt_segmentationUserManualLabelTable
+ - \ref org_mitk_gui_qt_segmentationUserManualLabelCreation
+ - \ref org_mitk_gui_qt_segmentationUserManualLayerCreation
+ - \ref org_mitk_gui_qt_segmentationUserManualLabelSearch
+ - \ref org_mitk_gui_qt_segmentationUserManualLabelEditing
+ - \ref org_mitk_gui_qt_segmentationUserManualContouring
+ - \ref org_mitk_gui_qt_segmentationUserManualInterpolation
+ - \ref org_mitk_gui_qt_segmentationUserManualOrganSegmentation
+ - \ref org_mitk_gui_qt_segmentationUserManualOrganSegmentation1
+ - \ref org_mitk_gui_qt_segmentationUserManualOrganSegmentation2
+ - \ref org_mitk_gui_qt_segmentationUserManualOrganSegmentation99
+ - \ref org_mitk_gui_qt_segmentationUserManualLesionSegmentation
+ - \ref org_mitk_gui_qt_segmentationUserManualOperationsOnLabels
+ - \ref org_mitk_gui_qt_segmentationUserManualOperationsOnSingleSelection
+ - \ref org_mitk_gui_qt_segmentationUserManualOperationsOnMultipleSelection
+ - \ref org_mitk_gui_qt_segmentationUserManualSegmentationUtilities
+ - \ref org_mitk_gui_qt_segmentationUserManualTechnicalDetail
+
+\section org_mitk_gui_qt_segmentationUserManualOverview Overview
+
+The Segmentation Perspective allows to create segmentations of structures of interest in biomedical and biological
+images. Examples of such structures are an organ, a vessel or a lesion in a CT or MR image, or a cell or organelle in microscopy
+images. The perspective groups a number of tools which can be used for:
+
+ fully-automatic segmentation
+ semi-automatic segmentation
+ manual segmentation
+
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGapplication.png", "Segmentation perspective consisting of the Data Manager view, the
+Segmentation view and the Segmentation Utilities view.", 12}
+
+If you wonder what segmentations are good for, we shortly revisit the concept of a segmentation here.
+A CT or MR image is made up of volume of physical measurements (volume elements are called voxels).
+In CT images, for example, the gray value of each voxel corresponds to the mass absorption coefficient
+for X-rays in this voxel, which is similar in many %parts of the human body.
+The gray value does not contain any further information, so the computer does not know whether a given
+voxel is part of the body or the background, nor can it tell a brain from a liver.
+However, the distinction between voxels belonging to an object and a background structure is required when:
+
+you want to know the volume of a given organ (the computer needs to know which %parts of the image belong to this organ)
+ you want to create 3D polygon visualizations (the computer needs to know the surfaces of structures that should be drawn)
+ as a necessary preprocessing step for therapy planning, therapy support, and therapy monitoring
+
+
+This distinction between voxels inside and object and background is called segmentation .
+Since many objects might be segmented on an image, each segmentation is assigned a different label . A label
+has a name, a color, and a number of properties that we will describe later.
+The current implementation of the Segmentation perspective uses a voxel-based approach for segmentations, i.e. each voxel
+of an image must be completely assigned to either a label or background. In a future version of the toolkit we will also enable
+the generation of segmentations based on contours. In this way, the user will be able to better define the borders of the
+segmented objects by taking advantage of his/her medical knowledge. Segmentations based on contours are not restricted to
+the voxel size of the medical image and can be arbitrarily positioned.
+
+The remainder of this document will summarize the features of the Segmentation perspective and how they are used.
+
+\subsection org_mitk_gui_qt_segmentationUserManualTechnical Technical Issues
+
+The Segmentation Perspective makes a number of assumptions. To know what this view can be used for, it will help you to know that:
+
+ Images must be 2D, 3D, or 3D+t.
+ Images must be single-values, i.e. CT, MRI or "typical" ultrasound. Images from color doppler, microscopy or
+photographs (RGB) are not yet supported.
+ Segmentations are handled as multi-labeled images of the same extent as the original medical image.
+
+
+\section org_mitk_gui_qt_segmentationUserManualCreateOpenSaveImportAdd Start Segmenting
+
+To start using the Segmentation Perspective you will have to either create a new segmentation session or
+load an existing one from disk. The Segmentation toolbar collects buttons for the these actions:
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGtoolbar.png", "Segmentation toolbar", 12}
+
+
+ Create segmentation session a new segmentation session is created.
+ Load segmentation session a segmentation session can be loaded from disk (.lset file extensions).
+ Save segmentation session the current segmentation session can be saved to disk.
+ Import segmentation session a segmentation session can be incorporated into the current one. All new labels will be appended
+ at the end of the table.
+ Add label a new label is appended to the current segmentation session, at the end of the table.
+
+
+\section org_mitk_gui_qt_segmentationUserManualLabelTable The Label Table
+
+The following label properties are readily available to modify:
+
+
+ Name the name of the label. Can be a predefined one or any other.
+ Color the color of the label.
+ Visible whether the label is currently visible or hiden.
+ Locked whether the label is locked or editable. A locked label cannot be overwritten by another.
+
+
+The Label Table is shown below:
+
+\imageMacro{org_mitk_gui_qt_segmentationIMGlabeltable.png", "The Label Table showing all the labels in the current segmentation session", 12}
+
+\section org_mitk_gui_qt_segmentationUserManualLabelCreation Creating a New Label
+
+Click the "New Label" button to add a new label. A dialog will show-up to enter the name and color. Preset organ names and
+corresponding colors are offered while you type in, but you can set any name. The new name if not known will be automatically
+remembered and made available the next time you create a new label. In the current implementation of the plugin,
+the maximum number of labels is restricted to 255. If you need more, you will have to create a new segmentation session.
+
+\section org_mitk_gui_qt_segmentationUserManualLayerCreation Creating a New Layer
+
+A layer is a set of labels that occupy a non-overlapping anatomical space. The best way to describe them is by a real use
+case. Imagine you are working on a radiotherpay planning application. In the first layer of your segmentation
+session you would like to trace the contours of the liver and neighboring organs. You can accomodate all these segmentations
+in separate labels because they all occupy different anamical regions and do not overlap. Now say you would like to segment
+the arteries and veins inside the liver. If you don´t trace them in a different layer, you will overwrite the previous ones.
+You may also need a third layer for segmenting the different irrigation territories in the liver and a fourth layer to contain
+the lession you would like to treat.
+
+The next figure illustrates the Layer Manager . The buttons in it contained serve for adding a new layer, selecting the
+previous and the next one. The active layer is shown together with the buttons.
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGlayerManager.png", "Correction Tool",12}
+
+\section org_mitk_gui_qt_segmentationUserManualLabelSearch Searching a Label
+
+It may happen that many labels (e.g. > 200) are present in a segmentation session and therefore manual searching is time consuming.
+The Label Search edit box allows for quickly finding the label you want. Just start writing its name and and you will get
+assitance for completing its name. If the label you were searching is found, press enter and it will became the active one.
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGsearchlabel.png", "Label search", 12}
+
+\section org_mitk_gui_qt_segmentationUserManualLabelEditing Label Editing
+
+First of all, you have to select the active label by clicking on the corresponding row in the Label Table . Only one label
+can be active at the time. Then you can select an editing tool in the toolbox.
+The selected editing tool will be active and its corresponding button will stay pressed until you click the same button again.
+Selecting a different tool also deactivates the previous one. If you are familiar with the MITK Workbench, you know that
+clicking and moving the mouse in any of the 2D windows will move around the crosshair that defines the position in
+the image you are standing on. Depending on the tool that you activate, this behavior may be disabled during segmenting
+-- otherwise you might have a hard time concentrating on the contour you are drawing --.
+
+If you have to delineate a lot of images, you should try using shortcuts to switch tools. Just hit the first letter of each
+tool to activate it (e.g. "A" for Add, "S" for Subtract, etc.). If you hover the cursor on a tool button you will get a tip
+message reminding you this.
+
+\subsection org_mitk_gui_qt_segmentationUserManualManualEditingTools Manual Editing Tools
+
+All of the editing tools work by the same principle: you use the mouse (left button) to click anywhere in a 2D
+window (any of the orientations axial, sagittal, or frontal), move the mouse while holding the mouse button and
+release to finish the editing action.
+
+At any time you can undo or redo your past actions with corresponding buttons in the application\'s toolbar.
+
+\subsection org_mitk_gui_qt_segmentationUserManualContouring Manual Contouring
+
+The "Add" and "Subtract" tools allow for freely tracing a contour around an organ or structure in an image.
+You might also use manual contouring to further enhance or correct a segmentation resulting from sub-optimal automatic methods.
+The drawback of manual contouring is that you might need to define contours on many 2D slices to segment the whole structure.
+However, this is moderated by the interpolation tools, which are described later.
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGiconAddSubtract.png", "Add and Subtract Tools",12}
+
+Use the left mouse button to draw a closed contour. When releasing the mouse button, the contour will be added (Add tool) to or
+removed from (Subtract tool) the current segmentation.
+Hold down the CTRL / CMD key to invert the operation (this will switch tools temporarily to allow for quick corrections).
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGiconPaintWipe.png", "Paint and Wipe Tools", 12cm}
+
+Use the slider below the toolbox to change the radius of the paintbrush tool. Move the mouse
+in any 2D window and press the left button to draw or erase the active label.
+As the Add/Subtract tools, holding CTRL/CMD while drawing will invert the current tool's behavior.
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGiconRegionGrowing.png", "Region Growing Tool", 12}
+
+Click with the left button at one point in a 2D window and move up or down while keeping it pressed. This action
+will make your segmentation grow (up) or shrink (down). When working on an image with a high range of grey values,
+the selection range can be influenced more strongly by moving the cursor at higher velocity. The region growing algorithm
+tool selects all pixels around the mouse cursor that have a similar gray value as the pixel below the first clicked position.
+This enables you to quickly create segmentations of structures that have a good contrast to surrounding tissue, e.g. the lungs.
+
+A common issue with region growing is the so called "leakage" which happens when the structure of interest is connected to
+other pixels, of similar gray values, through a narrow "bridge" at the border of the structure.
+The Region Growing tool comes with a "leakage detection/removal" feature. If leakage happens, you can left-click into the
+leakage region and the tool will try to automatically remove this region (see illustration below).
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGleakage.png", "Leakage correction feature of the Region Growing tool", 12}
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGiconCorrection.png", "Correction Tool", 12}
+
+The corrector tool is used to perform small corrective changes. The following figure illustrates its use:
+
+ if the user draws a line which %starts and ends outside the active label, the
+endpoints of the line are connected and the region inside the resulting contour is incorporated to the active label.
+ if the user draws a line which %starts and ends outside the active label, the smaller region on the side is cut off (left image)
+ if the line is drawn fully inside the active label, the marked region is added to the segmentation (right image)
+
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGcorrectionActions.png", "Actions of the Correction tool illustrated.", 12}
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGiconFillErase.png", "Fill and Erase Tools", 12}
+
+The Fill Tool works by filling a hole surrounded by the active label, at the clicked position. If you click outside the
+hole (but yet inside the label) all holes found surrounded by the active label will be filled.
+
+The Erase Tool removes a connected region of the active label around the clicked position.
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGiconLiveWire.png", "LiveWire Tool", 12}
+
+The LiveWire tool acts as a magnetic lasso with a contour snapping to edges of objects.
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGLiveWireUsage.png", "Steps for using LiveWire Tool", 12}
+
+
+(1) To start the Tool you have to double click near the edge of the object you want to segment. The initial anchor point will
+snap to the edge within a 3x3 region.
+ (2) Move the mouse. You don't have trace the edge of the object. The contour will automatically snap to it.
+ (3) To fix a segment you can set anchor points by single left mouse button click.
+ (4) Go on with moving the mouse and setting anchor points.
+ (5) To close the contour double click on the initial anchor point.
+ (6) After closing the contour, it can further be edited by dragging, inserting and deleting anchor points.
+
+
+The contour will be transferred to the active label when the tool is deactivated.
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGiconFastMarching2D.png", "FastMarching Tool", 12}
+
+The FastMarching tool ...
+
+\subsection org_mitk_gui_qt_segmentationUserManualInterpolation Interpolation
+
+Segmenting modern CT and MR volumes is very time-consuming, because structures of interest can easily
+cover a range of 50 or more slices. The Segmentation plugin offers two helpful features for these cases:
+
+
+ 3D Interpolation
+ 2D Interpolation
+
+
+
+The 3D interpolation is activated by default when using the manual segmentation tools. That means if you start
+contouring, from the second contour onwards, the surface of the segmented area will be interpolated based on the available contours.
+The interpolation works with all available manual tools. Please note that this is currently a pure geometrical interpolation,
+i.e. image intensity information is not taken into account. With each new contour that the user traces, the interpolation result
+will improve, but the more contours you provide the longer the recalculation will take. To optimize the interpolation result you
+should try to provide sparse contours in arbitrary oriented planes. Generating parallel contours along a given direction is not
+a good approach. During interpolation recalculation, the generated surface blinks in yellow/white. When the interpolation
+has finished the surface is shown yellow with a small opacity. Additional to the surface, black contours are shown in the 3D render
+window. They mark the positions of all the drawn contours which were used for the interpolation. You can navigate between the drawn
+contours by clicking on the „Position“ - Nodes in the Data Manager which are located below the active segmentation. If you don't
+want to see these nodes just unckeck the „Show Position Nodes“ Checkbox and these nodes will
+be hidden. If you want to delete a drawn contour we recommend to use the Erase-Tool since Redo/Undo is not yet working for 3D
+interpolation.
+
+\imageMacro{"org_mitk_gui_qt_segmentation3DInterpolationWrongRight.png", "3D Interpolation HowTo", 12}
+
+Finally, you can accept the interpolation result by clicking the "Accept" - button below the toolbox. The region inside the surface is
+assigned to the active label.
+
+
+The 2D Interpolation creates suggestions for extending the active label into neighboring slices provided
+
+ a segmentation of the same active label is available a couple of slices away AND
+ is completely clear of the active label in between -- i.e. there will be no interpolation suggestion if there is even only
+a single pixel of the active label between the aforementioned slices.
+
+
+Interpolated suggestions are displayed as contours with the same color as the active label. To accept an interpolation suggestion
+in a single slice, click the "Accept" button. You can also accept all interpolated suggestions at once in a
+given window, by pressing the "Accept All" button.
+
+\imageMacro{"org_mitk_gui_qt_segmentation2DInterpolation.png", "2D Interpolation", 12}
+
+\section org_mitk_gui_qt_segmentationUserManualOrganSegmentation Organ Segmentation
+
+\note This feature is only available in our 3M3 Demo Application (http://www.mint-medical.de/productssolutions/mitk3m3/mitk3m3/#downloads) but not in the open source part of MITK
+
+The manual contouring described above is a fallback option that will work for any kind of images and structures of interest.
+However, manual contouring is very time-consuming and tedious.
+This is why a major part of image analysis research is working towards automatic segmentation methods.
+The Segmentation View comprises a number of easy-to-use tools for segmentation of CT images (Liver) and MR image (left ventricle and wall, left and right lung).
+
+\subsection org_mitk_gui_qt_segmentationUserManualOrganSegmentation1 Liver on CT Images
+
+On CT image volumes, preferably with a contrast agent in the portal venous phase, the Liver tool will fully automatically analyze and segment the image.
+All you have to do is to load and select the image, then click the "Liver" button.
+During the process, which takes a minute or two, you will get visual progress feedback by means of a contour that moves closer and closer to the real liver boundaries.
+
+\subsection org_mitk_gui_qt_segmentationUserManualOrganSegmentation2 Heart, Lung, and Hippocampus on MRI
+
+While liver segmentation is performed fully automatic, the following tools for segmentation of the heart, the lungs, and the hippocampus need a minimum amount of guidance.
+Click one of the buttons on the "Organ segmentation" page to add an average %model of the respective organ to the image.
+This %model can be dragged to the right position by using the left mouse button while holding down the CTRL key.
+You can also use CTRL + middle mouse button to rotate or CTRL + right mouse button to scale the %model.
+
+Before starting the automatic segmentation process by clicking the "Start segmentation" button, try placing the %model closely to the organ in the MR image
+(in most cases, you do not need to rotate or scale the %model).
+During the segmentation process, a green contour that moves closer and closer to the real liver boundaries will provide you with visual feedback of the segmentation progress.
+
+The algorithms used for segmentation of the heart and lung are method which need training by a number of example images.
+They will not work well with other kind of images, so here is a list of the image types that were used for training:
+
+ Hippocampus segmentation: T1-weighted MR images, 1.5 Tesla scanner (Magnetom Vision, Siemens Medical Solutions), 1.0 mm isotropic resolution
+ Heart: Left ventricle inner segmentation (LV Model): MRI; velocity encoded cine (VEC-cine) MRI sequence; trained on systole and diastole
+ Heart: Left ventricular wall segmentation (LV Inner Wall, LV Outer Wall): 4D MRI; short axis 12 slice spin lock sequence(SA_12_sl); trained on whole heart cycle
+ Lung segmentation: 3D and 4D MRI; works best on FLASH3D and TWIST4D sequences
+
+
+\subsection org_mitk_gui_qt_segmentationUserManualOrganSegmentation99 Other Organs
+
+As mentioned in the Heart/Lung section, most of the underlying methods are based on "training".
+The basic algorithm is versatile and can be applied on all kinds of segmentation problems where the structure of interest is topologically like a sphere (and not like a torus etc.).
+If you are interested in other organs than those offered by the current version of the Segmentation view,
+please contact our research team.
+
+\subsection org_mitk_gui_qt_segmentationUserManualLesionSegmentation Lesion Segmentation
+
+\note This feature is only available in our 3M3 Demo Application (http://www.mint-medical.de/productssolutions/mitk3m3/mitk3m3/#downloads) but not in the open source part of MITK
+
+Lesion segmentation is a little different from organ segmentation. Since lesions are not part of the healthy body, they sometimes have a diffused border,
+and are often found in varying places all over the body.
+The tools in this section offer efficient ways to create 3D segmentations of such lesions.
+
+The Segmentation View currently offers support for enlarged lymph nodes.
+
+To segment an enlarged lymph node, find a more or less central slice of it, activate the "Lymph Node" tool and draw a rough contour on the inside of the lymph node.
+When releasing the mouse button, a segmentation algorithm is started in a background task. The result will become visible after a couple of seconds, but you do not have to wait for it.
+If you need to segment several lymph nodes, you can continue to inspect the image right after closing the drawn contour.
+
+If the lymph node segmentation is not to your content, you can select the "Lymph Node Correction" tool and drag %parts of the lymph node surface towards the right position (works in 3D, not slice-by-slice).
+This kind of correction helps in many cases.
+If nothing else helps, you can still use the pure manual tools as a fallback.
+
+\section org_mitk_gui_qt_segmentationUserManualOperationsOnLabels Operations on Labels
+
+Depending on your selection in the Label Table , several actions are offered:
+
+\subsection org_mitk_gui_qt_segmentationUserManualOperationsOnSingleSelection Single Label Selection
+
+If you right click on any label in the table, a menu will pop-up offering the following actions to be performed on the selected label:
+
+
+ Rename... : change the name and/or color of the selected label.
+ Remove label : delete the selected label.
+ Erase label : only clear the contents of the selected label.
+ Random color : generate a surface mesh out of the selected label.
+ View only : generate a mask out of the selected label. A mask is a binary image with "1" inside and "0" outside.
+ View/Hide all : generate a mask out of the selected label. A mask is a binary image with "1" inside and "0" outside.
+ Lock/Unlock all : generate a mask out of the selected label. A mask is a binary image with "1" inside and "0" outside.
+ Create surface : generate a surface out of the selected label.
+ Create mask : generate a mask out of the selected label. A mask is a binary image with "1" inside and "0" outside.
+
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGLabelTableSingleSelectionContextMenu.png", "Context menu for single label selection", 12}
+
+\subsection org_mitk_gui_qt_segmentationUserManualOperationsOnMultipleSelection Multiple Label Selection
+
+If more than one label is selected, a different menu will show up:
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGLabelTableMultipleSelectionContextMenu.png", "Context menu for multiple label selection", 12}
+
+
+ Merge selection on current label : transfer the contents of the selected labels in the Label Table into the current one.
+ Remove selected labels : delete the selected labels.
+ Erase selected labels : only clear the contents of the selected labels.
+ Create a surface for each selected label : generate a surface mesh out of each selected label.
+ Combine and create a surface : generate a surface out of the combination of the selected labels.
+ Create a mask for each selected label : generate a mask out of each selected label. A mask is a binary image with "1" inside and "0" outside.
+ Combine and create a mask : generate a mask out of the combination of the selected labels.
+
+
+\section org_mitk_gui_qt_segmentationUserManualSegmentationUtilities Segmentation Utilities
+
+The Segmentation Utilities view ...
+
+One is the surface masking utility. It is used for create a new label from a surface. The surface is used as a "mask": the region inside
+the surface is assigned a new label.
+
+\imageMacro{"org_mitk_gui_qt_segmentationIMGsurfacemask.png", "Surface masking utility", 12}
+
+Select the image and the surface in the corresponding drop-down boxes (both are selected automatically if there is just one image and one surface)
+
+\section org_mitk_gui_qt_segmentationUserManualTechnicalDetail Technical Information for Developers
+
+For technical specifications see : \subpage QmitkSegmentationTechnicalPage and for information on the extensions of the tools system : \subpage toolextensions.
+
+*/
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentation2DInterpolation.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentation2DInterpolation.png
new file mode 100644
index 0000000000..09ed1e4f17
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentation2DInterpolation.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentation3DInterpolationWrongRight.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentation3DInterpolationWrongRight.png
new file mode 100644
index 0000000000..d2e65a8600
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentation3DInterpolationWrongRight.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGLabelTableMultipleSelectionContextMenu.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGLabelTableMultipleSelectionContextMenu.png
new file mode 100644
index 0000000000..ac71514fe9
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGLabelTableMultipleSelectionContextMenu.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGLabelTableSingleSelectionContextMenu.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGLabelTableSingleSelectionContextMenu.png
new file mode 100644
index 0000000000..13f648df2a
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGLabelTableSingleSelectionContextMenu.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGLiveWireUsage.PNG b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGLiveWireUsage.PNG
new file mode 100644
index 0000000000..3e963ce632
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGLiveWireUsage.PNG differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGapplication.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGapplication.png
new file mode 100644
index 0000000000..7d01cb32bc
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGapplication.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGcorrectionActions.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGcorrectionActions.png
new file mode 100644
index 0000000000..dc8dc8ce03
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGcorrectionActions.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGdatamanagerview.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGdatamanagerview.png
new file mode 100644
index 0000000000..abf6e7f638
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGdatamanagerview.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconAddSubtract.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconAddSubtract.png
new file mode 100644
index 0000000000..53927a9ec2
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconAddSubtract.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconCorrection.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconCorrection.png
new file mode 100644
index 0000000000..41f21628e6
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconCorrection.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconFastMarching2D.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconFastMarching2D.png
new file mode 100644
index 0000000000..ac6c4eddc8
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconFastMarching2D.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconFill.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconFill.png
new file mode 100644
index 0000000000..33b9498598
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconFill.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconFillErase.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconFillErase.png
new file mode 100644
index 0000000000..6acdb3acdc
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconFillErase.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconLiveWire.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconLiveWire.png
new file mode 100644
index 0000000000..8c28ce7bf6
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconLiveWire.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconPaintWipe.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconPaintWipe.png
new file mode 100644
index 0000000000..c034048640
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconPaintWipe.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconRegionGrowing.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconRegionGrowing.png
new file mode 100644
index 0000000000..4479918187
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGiconRegionGrowing.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGlabeltable.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGlabeltable.png
new file mode 100644
index 0000000000..351020c950
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGlabeltable.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGlayerManager.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGlayerManager.png
new file mode 100644
index 0000000000..8bfd980219
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGlayerManager.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGleakage.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGleakage.png
new file mode 100644
index 0000000000..a2e27f3df1
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGleakage.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGsearchlabel.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGsearchlabel.png
new file mode 100644
index 0000000000..5beb87e00e
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGsearchlabel.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGselection.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGselection.png
new file mode 100644
index 0000000000..25db6192cb
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGselection.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGsurfacemask.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGsurfacemask.png
new file mode 100644
index 0000000000..cb81d900a8
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGsurfacemask.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGtoolbar.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGtoolbar.png
new file mode 100644
index 0000000000..ddb08b0449
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/org_mitk_gui_qt_segmentationIMGtoolbar.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/segmentationFromSurfaceBefore.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/segmentationFromSurfaceBefore.png
new file mode 100644
index 0000000000..d12d44fb9f
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/UserManual/segmentationFromSurfaceBefore.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/doxygen/MultiLabelSegmentationProperties.dox b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/doxygen/MultiLabelSegmentationProperties.dox
new file mode 100644
index 0000000000..e4d8347623
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/documentation/doxygen/MultiLabelSegmentationProperties.dox
@@ -0,0 +1,10 @@
+/**
+\page MultiLabelSegmentationPropertiesPage The Segmentation properties
+
+These properties control how a segmentation is rendered:
+
+
+ property #1
+ property #2
+
+*/
\ No newline at end of file
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/files.cmake b/Plugins/org.mitk.gui.qt.multilabelsegmentation/files.cmake
new file mode 100644
index 0000000000..d9c8851988
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/files.cmake
@@ -0,0 +1,90 @@
+set(SRC_CPP_FILES
+ QmitkMultiLabelSegmentationPreferencePage.cpp
+ QmitkLabelSetWidget.cpp
+)
+
+set(INTERNAL_CPP_FILES
+ mitkPluginActivator.cpp
+ QmitkMultiLabelSegmentationView.cpp
+ QmitkThresholdAction.cpp
+ QmitkCreatePolygonModelAction.cpp
+ QmitkAutocropAction.cpp
+ QmitkConvertSurfaceToLabelAction.cpp
+ QmitkConvertMaskToLabelAction.cpp
+ QmitkConvertToMultiLabelSegmentationAction.cpp
+ QmitkCreateMultiLabelSegmentationAction.cpp
+ QmitkLoadMultiLabelPresetAction.cpp
+ QmitkCreateMultiLabelPresetAction.cpp
+ Common/QmitkDataSelectionWidget.cpp
+ SegmentationUtilities/QmitkMultiLabelSegmentationUtilitiesView.cpp
+ SegmentationUtilities/QmitkSegmentationUtilityWidget.cpp
+ SegmentationUtilities/BooleanOperations/QmitkBooleanOperationsWidget.cpp
+ SegmentationUtilities/MorphologicalOperations/QmitkMorphologicalOperationsWidget.cpp
+ SegmentationUtilities/SurfaceToImage/QmitkSurfaceToImageWidget.cpp
+ SegmentationUtilities/ImageMasking/QmitkImageMaskingWidget.cpp
+)
+
+set(UI_FILES
+ src/internal/QmitkMultiLabelSegmentationControls.ui
+ src/internal/Common/QmitkDataSelectionWidgetControls.ui
+ src/internal/SegmentationUtilities/QmitkMultiLabelSegmentationUtilitiesViewControls.ui
+ src/internal/SegmentationUtilities/BooleanOperations/QmitkBooleanOperationsWidgetControls.ui
+ src/internal/SegmentationUtilities/MorphologicalOperations/QmitkMorphologicalOperationsWidgetControls.ui
+ src/internal/SegmentationUtilities/SurfaceToImage/QmitkSurfaceToImageWidgetControls.ui
+ src/internal/SegmentationUtilities/ImageMasking/QmitkImageMaskingWidgetControls.ui
+ src/QmitkLabelSetWidgetControls.ui
+)
+
+set(MOC_H_FILES
+ src/QmitkMultiLabelSegmentationPreferencePage.h
+ src/QmitkLabelSetWidget.h
+ src/internal/mitkPluginActivator.h
+ src/internal/QmitkMultiLabelSegmentationView.h
+ src/internal/QmitkThresholdAction.h
+ src/internal/QmitkCreatePolygonModelAction.h
+ src/internal/QmitkAutocropAction.h
+ src/internal/QmitkConvertSurfaceToLabelAction.h
+ src/internal/QmitkLoadMultiLabelPresetAction.h
+ src/internal/QmitkCreateMultiLabelPresetAction.h
+ src/internal/QmitkConvertMaskToLabelAction.h
+ src/internal/QmitkConvertToMultiLabelSegmentationAction.h
+ src/internal/QmitkCreateMultiLabelSegmentationAction.h
+ src/internal/Common/QmitkDataSelectionWidget.h
+ src/internal/SegmentationUtilities/QmitkMultiLabelSegmentationUtilitiesView.h
+ src/internal/SegmentationUtilities/QmitkSegmentationUtilityWidget.h
+ src/internal/SegmentationUtilities/BooleanOperations/QmitkBooleanOperationsWidget.h
+ src/internal/SegmentationUtilities/MorphologicalOperations/QmitkMorphologicalOperationsWidget.h
+ src/internal/SegmentationUtilities/SurfaceToImage/QmitkSurfaceToImageWidget.h
+ src/internal/SegmentationUtilities/ImageMasking/QmitkImageMaskingWidget.h
+)
+
+set(CACHED_RESOURCE_FILES
+ resources/multilabelsegmentation.png
+ resources/MultiLabelSegmentationUtilities_48x48.png
+ plugin.xml
+)
+
+set(QRC_FILES
+ resources/multilabelsegmentation.qrc
+ resources/MultiLabelSegmentationUtilities.qrc
+ resources/MorphologicalOperationsWidget.qrc
+ resources/BooleanOperationsWidget.qrc
+)
+
+set(CPP_FILES)
+
+foreach(file ${SRC_CPP_FILES})
+ set(CPP_FILES ${CPP_FILES} src/${file})
+endforeach(file ${SRC_CPP_FILES})
+
+#usFunctionEmbedResources(
+#CPP_FILES
+# LIBRARY_NAME "liborg_mitk_gui_qt_multilabelsegmentation"
+#ROOT_DIR resources
+#FILES Interactions/SegmentationInteraction.xml
+# Interactions/ConfigSegmentation.xml
+#)
+
+foreach(file ${INTERNAL_CPP_FILES})
+ set(CPP_FILES ${CPP_FILES} src/internal/${file})
+endforeach(file ${INTERNAL_CPP_FILES})
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/manifest_headers.cmake b/Plugins/org.mitk.gui.qt.multilabelsegmentation/manifest_headers.cmake
new file mode 100644
index 0000000000..ca346536b9
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/manifest_headers.cmake
@@ -0,0 +1,5 @@
+set(Plugin-Name "MITK MultiLabelSegmentation")
+set(Plugin-Version "1.0.0")
+set(Plugin-Vendor "DKFZ, Medical and Biological Informatics")
+set(Plugin-ContactAddress "http://www.mitk.org")
+set(Require-Plugin org.mitk.gui.qt.common org.mitk.gui.qt.datamanager)
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/plugin.xml b/Plugins/org.mitk.gui.qt.multilabelsegmentation/plugin.xml
new file mode 100644
index 0000000000..312edde71f
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/plugin.xml
@@ -0,0 +1,42 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanDifference_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanDifference_48x48.png
new file mode 100644
index 0000000000..424faa7fe5
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanDifference_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanIntersection_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanIntersection_48x48.png
new file mode 100644
index 0000000000..2db4c0dc89
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanIntersection_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanOperationsWidget.qrc b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanOperationsWidget.qrc
new file mode 100644
index 0000000000..ef0eab4b45
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanOperationsWidget.qrc
@@ -0,0 +1,7 @@
+
+
+ BooleanDifference_48x48.png
+ BooleanIntersection_48x48.png
+ BooleanUnion_48x48.png
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanOperations_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanOperations_48x48.png
new file mode 100644
index 0000000000..27d28f9926
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanOperations_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanUnion_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanUnion_48x48.png
new file mode 100644
index 0000000000..891740c7c1
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/BooleanUnion_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/CTKWidgets_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/CTKWidgets_48x48.png
new file mode 100644
index 0000000000..ed7caf5cad
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/CTKWidgets_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Closing_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Closing_48x48.png
new file mode 100644
index 0000000000..2d998a55cf
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Closing_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Dilate_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Dilate_48x48.png
new file mode 100644
index 0000000000..669f95d156
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Dilate_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Erode_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Erode_48x48.png
new file mode 100644
index 0000000000..eaa6f4884e
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Erode_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/FillHoles_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/FillHoles_48x48.png
new file mode 100644
index 0000000000..30ea751927
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/FillHoles_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Icons.svg b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Icons.svg
new file mode 100644
index 0000000000..2fd004fb64
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Icons.svg
@@ -0,0 +1,3069 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ image/svg+xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ AND
+ OR
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/ImageMasking_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/ImageMasking_48x48.png
new file mode 100644
index 0000000000..9c05e9fb20
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/ImageMasking_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Interactions/ConfigSegmentation.xml b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Interactions/ConfigSegmentation.xml
new file mode 100644
index 0000000000..11d05617e4
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Interactions/ConfigSegmentation.xml
@@ -0,0 +1,54 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Interactions/SegmentationInteraction.xml b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Interactions/SegmentationInteraction.xml
new file mode 100644
index 0000000000..3f55840cd2
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Interactions/SegmentationInteraction.xml
@@ -0,0 +1,12 @@
+
+
+
+
+
+
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MorphologicalOperationsWidget.qrc b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MorphologicalOperationsWidget.qrc
new file mode 100644
index 0000000000..3fe0afc1f8
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MorphologicalOperationsWidget.qrc
@@ -0,0 +1,9 @@
+
+
+ Dilate_48x48.png
+ Erode_48x48.png
+ Closing_48x48.png
+ Opening_48x48.png
+ FillHoles_48x48.png
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MorphologicalOperations_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MorphologicalOperations_48x48.png
new file mode 100644
index 0000000000..f19c6714e3
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MorphologicalOperations_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MultiLabelSegmentationUtilities.qrc b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MultiLabelSegmentationUtilities.qrc
new file mode 100644
index 0000000000..0ba8817c3d
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MultiLabelSegmentationUtilities.qrc
@@ -0,0 +1,10 @@
+
+
+ BooleanOperations_48x48.png
+ ImageMasking_48x48.png
+ MorphologicalOperations_48x48.png
+ SurfaceToImage_48x48.png
+ MultiLabelSegmentationUtilities_48x48.png
+ CTKWidgets_48x48.png
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MultiLabelSegmentationUtilities_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MultiLabelSegmentationUtilities_48x48.png
new file mode 100644
index 0000000000..d441187899
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/MultiLabelSegmentationUtilities_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/NewLabel_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/NewLabel_48x48.png
new file mode 100644
index 0000000000..c98380621e
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/NewLabel_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/NewSegmentationSession_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/NewSegmentationSession_48x48.png
new file mode 100644
index 0000000000..6818f12b4a
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/NewSegmentationSession_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Opening_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Opening_48x48.png
new file mode 100644
index 0000000000..14095dfdd2
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/Opening_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/SurfaceToImage_48x48.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/SurfaceToImage_48x48.png
new file mode 100644
index 0000000000..6ad6070caa
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/SurfaceToImage_48x48.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/deformablePlane.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/deformablePlane.png
new file mode 100644
index 0000000000..28c5fb54e8
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/deformablePlane.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/multilabelsegmentation.png b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/multilabelsegmentation.png
new file mode 100644
index 0000000000..d13c72b5b6
Binary files /dev/null and b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/multilabelsegmentation.png differ
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/multilabelsegmentation.qrc b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/multilabelsegmentation.qrc
new file mode 100644
index 0000000000..5a5003c555
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/resources/multilabelsegmentation.qrc
@@ -0,0 +1,7 @@
+
+
+ multilabelsegmentation.png
+ NewLabel_48x48.png
+ NewSegmentationSession_48x48.png
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkLabelSetWidget.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkLabelSetWidget.cpp
new file mode 100644
index 0000000000..07f4512cd4
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkLabelSetWidget.cpp
@@ -0,0 +1,1249 @@
+/*===================================================================
+
+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 "QmitkLabelSetWidget.h"
+
+// mitk
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+// Qmitk
+#include
+#include
+#include
+
+// Qt
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+// itk
+#include
+
+// todo:
+// berry
+//#include
+
+QmitkLabelSetWidget::QmitkLabelSetWidget(QWidget* parent)
+: QWidget(parent)
+, m_ToolManager(NULL)
+, m_DataStorage(NULL)
+, m_Completer(NULL)
+{
+ m_Controls.setupUi(this);
+
+ m_ColorSequenceRainbow.GoToBegin();
+
+ m_ToolManager = mitk::ToolManagerProvider::GetInstance()->GetToolManager();
+ assert(m_ToolManager);
+
+ m_Controls.m_LabelSearchBox->setAlwaysShowClearIcon(true);
+ m_Controls.m_LabelSearchBox->setShowSearchIcon(true);
+
+ QStringList completionList;
+ completionList << "";
+ m_Completer = new QCompleter(completionList, this);
+ m_Completer->setCaseSensitivity(Qt::CaseInsensitive);
+ m_Controls.m_LabelSearchBox->setCompleter(m_Completer);
+
+ connect( m_Controls.m_LabelSearchBox, SIGNAL(returnPressed()), this, SLOT(OnSearchLabel()) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(labelListModified(const QStringList&)), this, SLOT( OnLabelListModified(const QStringList&)) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(mergeLabel(int)), this, SLOT( OnMergeLabel(int)) );
+
+ QStringListModel* completeModel = static_cast (m_Completer->model());
+ completeModel->setStringList(GetLabelStringList());
+
+ m_Controls.m_LabelSearchBox->setEnabled(false);
+
+
+ m_Controls.m_lblCaption->setText("");
+
+ InitializeTableWidget();
+
+}
+
+QmitkLabelSetWidget::~QmitkLabelSetWidget()
+{
+}
+
+
+void QmitkLabelSetWidget::OnTableViewContextMenuRequested(const QPoint& pos)
+{
+ QTableWidgetItem *itemAt = m_Controls.m_LabelSetTableWidget->itemAt(pos);
+
+ //OnItemClicked(itemAt);
+
+ if (!itemAt) return;
+ int pixelValue = itemAt->data(Qt::UserRole).toInt();
+ QMenu* menu = new QMenu(m_Controls.m_LabelSetTableWidget);
+
+ if (m_Controls.m_LabelSetTableWidget->selectedItems().size()>1)
+ {
+ QAction* mergeAction = new QAction(QIcon(":/Qmitk/MergeLabels.png"), "Merge selection on current label", this );
+ mergeAction->setEnabled(true);
+ QObject::connect( mergeAction, SIGNAL( triggered(bool) ), this, SLOT( OnMergeLabels(bool) ) );
+ menu->addAction(mergeAction);
+
+ QAction* removeLabelsAction = new QAction(QIcon(":/Qmitk/RemoveLabel.png"), "Remove selected labels", this );
+ removeLabelsAction->setEnabled(true);
+ QObject::connect( removeLabelsAction, SIGNAL( triggered(bool) ), this, SLOT( OnRemoveLabels(bool) ) );
+ menu->addAction(removeLabelsAction);
+
+ QAction* eraseLabelsAction = new QAction(QIcon(":/Qmitk/EraseLabel.png"), "Erase selected labels", this );
+ eraseLabelsAction->setEnabled(true);
+ QObject::connect( eraseLabelsAction, SIGNAL( triggered(bool) ), this, SLOT( OnEraseLabels(bool) ) );
+ menu->addAction(eraseLabelsAction);
+
+ QAction* combineAndCreateSurfaceAction = new QAction(QIcon(":/Qmitk/CreateSurface.png"), "Combine and create a surface", this );
+ combineAndCreateSurfaceAction->setEnabled(true);
+ QObject::connect( combineAndCreateSurfaceAction, SIGNAL( triggered(bool) ), this, SLOT( OnCombineAndCreateSurface(bool) ) );
+ menu->addAction(combineAndCreateSurfaceAction);
+
+ QAction* createMasksAction = new QAction(QIcon(":/Qmitk/CreateMask.png"), "Create a mask for each selected label", this );
+ createMasksAction->setEnabled(true);
+ QObject::connect( createMasksAction, SIGNAL( triggered(bool) ), this, SLOT( OnCreateMasks(bool) ) );
+ menu->addAction(createMasksAction);
+
+ QAction* combineAndCreateMaskAction = new QAction(QIcon(":/Qmitk/CreateMask.png"), "Combine and create a mask", this );
+ combineAndCreateMaskAction->setEnabled(true);
+ QObject::connect( combineAndCreateMaskAction, SIGNAL( triggered(bool) ), this, SLOT( OnCombineAndCreateMask(bool) ) );
+ menu->addAction(combineAndCreateMaskAction);
+ }
+ else
+ {
+ QAction* renameAction = new QAction(QIcon(":/Qmitk/RenameLabel.png"), "Rename...", this );
+ renameAction->setEnabled(true);
+ QObject::connect( renameAction, SIGNAL( triggered(bool) ), this, SLOT( OnRenameLabel(bool) ) );
+ menu->addAction(renameAction);
+
+ QAction* removeAction = new QAction(QIcon(":/Qmitk/RemoveLabel.png"), "Remove...", this );
+ removeAction->setEnabled(true);
+ QObject::connect( removeAction, SIGNAL( triggered(bool) ), this, SLOT( OnRemoveLabel(bool) ) );
+ menu->addAction(removeAction);
+
+ QAction* eraseAction = new QAction(QIcon(":/Qmitk/EraseLabel.png"), "Erase...", this );
+ eraseAction->setEnabled(true);
+ QObject::connect( eraseAction, SIGNAL( triggered(bool) ), this, SLOT( OnEraseLabel(bool) ) );
+ menu->addAction(eraseAction);
+
+ QAction* mergeAction = new QAction(QIcon(":/Qmitk/MergeLabels.png"), "Merge...", this );
+ mergeAction->setEnabled(true);
+ QObject::connect( mergeAction, SIGNAL( triggered(bool) ), this, SLOT( OnMergeLabel(bool) ) );
+ menu->addAction(mergeAction);
+
+ QAction* randomColorAction = new QAction(QIcon(":/Qmitk/RandomColor.png"), "Random color", this );
+ randomColorAction->setEnabled(true);
+ QObject::connect( randomColorAction, SIGNAL( triggered(bool) ), this, SLOT( OnRandomColor(bool) ) );
+ menu->addAction(randomColorAction);
+
+ QAction* viewOnlyAction = new QAction(QIcon(":/Qmitk/visible.png"), "View only", this );
+ viewOnlyAction->setEnabled(true);
+ QObject::connect( viewOnlyAction, SIGNAL( triggered(bool) ), this, SLOT( OnSetOnlyActiveLabelVisible(bool) ) );
+ menu->addAction(viewOnlyAction);
+
+ QAction* viewAllAction = new QAction(QIcon(":/Qmitk/visible.png"), "View all", this );
+ viewAllAction->setEnabled(true);
+ QObject::connect( viewAllAction, SIGNAL( triggered(bool) ), this, SLOT( OnSetAllLabelsVisible(bool) ) );
+ menu->addAction(viewAllAction);
+
+ QAction* hideAllAction = new QAction(QIcon(":/Qmitk/invisible.png"), "Hide all", this );
+ hideAllAction->setEnabled(true);
+ QObject::connect( hideAllAction, SIGNAL( triggered(bool) ), this, SLOT( OnSetAllLabelsInvisible(bool) ) );
+ menu->addAction(hideAllAction);
+
+ QAction* lockAllAction = new QAction(QIcon(":/Qmitk/lock.png"), "Lock all", this );
+ lockAllAction->setEnabled(true);
+ QObject::connect( lockAllAction, SIGNAL( triggered(bool) ), this, SLOT( OnLockAllLabels(bool) ) );
+ menu->addAction(lockAllAction);
+
+ QAction* unlockAllAction = new QAction(QIcon(":/Qmitk/unlock.png"), "Unlock all", this );
+ unlockAllAction->setEnabled(true);
+ QObject::connect( unlockAllAction, SIGNAL( triggered(bool) ), this, SLOT( OnUnlockAllLabels(bool) ) );
+ menu->addAction(unlockAllAction);
+
+ QAction* createSurfaceAction = new QAction(QIcon(":/Qmitk/CreateSurface.png"), "Create surface", this );
+ createSurfaceAction->setEnabled(true);
+ createSurfaceAction->setMenu(new QMenu());
+
+ QAction* tmp1 = createSurfaceAction->menu()->addAction(QString("Detailed"));
+ QAction* tmp2 = createSurfaceAction->menu()->addAction(QString("Smoothed"));
+
+ QObject::connect( tmp1, SIGNAL( triggered(bool) ), this, SLOT( OnCreateDetailedSurface(bool) ) );
+ QObject::connect( tmp2, SIGNAL( triggered(bool) ), this, SLOT( OnCreateSmoothedSurface(bool) ) );
+
+ menu->addAction(createSurfaceAction);
+
+ QAction* createMaskAction = new QAction(QIcon(":/Qmitk/CreateMask.png"), "Create mask", this );
+ createMaskAction->setEnabled(true);
+ QObject::connect( createMaskAction, SIGNAL( triggered(bool) ), this, SLOT( OnCreateMask(bool) ) );
+
+ menu->addAction(createMaskAction);
+
+ QAction* createCroppedMaskAction = new QAction(QIcon(":/Qmitk/CreateMask.png"), "Create cropped mask", this );
+ createCroppedMaskAction->setEnabled(true);
+ QObject::connect( createCroppedMaskAction, SIGNAL( triggered(bool) ), this, SLOT( OnCreateCroppedMask(bool) ) );
+
+// QAction* importAction = new QAction(QIcon(":/Qmitk/RenameLabel.png"), "Import...", this );
+// importAction->setEnabled(true);
+// QObject::connect( importAction, SIGNAL( triggered(bool) ), this, SLOT( OnImportSegmentationSession(bool) ) );
+// menu->addAction(importAction);
+
+ menu->addAction(createCroppedMaskAction);
+
+ QSlider * opacitySlider = new QSlider;
+ opacitySlider->setMinimum(0);
+ opacitySlider->setMaximum(100);
+ opacitySlider->setOrientation(Qt::Horizontal);
+ QObject::connect( opacitySlider, SIGNAL( valueChanged(int) ), this, SLOT( OnOpacityChanged(int) ) );
+
+ QLabel* _OpacityLabel = new QLabel("Opacity: ");
+ QVBoxLayout* _OpacityWidgetLayout = new QVBoxLayout;
+ _OpacityWidgetLayout->setContentsMargins(4,4,4,4);
+ _OpacityWidgetLayout->addWidget(_OpacityLabel);
+ _OpacityWidgetLayout->addWidget(opacitySlider);
+ QWidget* _OpacityWidget = new QWidget;
+ _OpacityWidget->setLayout(_OpacityWidgetLayout);
+
+ QWidgetAction * OpacityAction = new QWidgetAction(this);
+ OpacityAction->setDefaultWidget(_OpacityWidget);
+ // QObject::connect( m_OpacityAction, SIGNAL( changed() ), this, SLOT( OpacityActionChanged() ) );
+ opacitySlider->setValue(static_cast(GetWorkingImage()->GetLabel(pixelValue)->GetOpacity()*100));
+
+ menu->addAction(OpacityAction);
+ }
+ menu->popup(QCursor::pos());
+}
+
+void QmitkLabelSetWidget::OnUnlockAllLabels(bool /*value*/)
+{
+ GetWorkingImage()->GetLabelSet()->SetAllLabelsLocked(false);
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+}
+
+void QmitkLabelSetWidget::OnLockAllLabels(bool /*value*/)
+{
+ GetWorkingImage()->GetLabelSet()->SetAllLabelsLocked(true);
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+}
+
+void QmitkLabelSetWidget::OnSetAllLabelsVisible(bool /*value*/)
+{
+ GetWorkingImage()->GetLabelSet()->SetAllLabelsVisible(true);
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+ UpdateAllTableWidgetItems();
+}
+
+void QmitkLabelSetWidget::OnSetAllLabelsInvisible(bool /*value*/)
+{
+ GetWorkingImage()->GetLabelSet()->SetAllLabelsVisible(false);
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+ UpdateAllTableWidgetItems();
+}
+
+void QmitkLabelSetWidget::OnSetOnlyActiveLabelVisible(bool /*value*/)
+{
+ mitk::LabelSetImage * workingImage = GetWorkingImage();
+ int pixelValue = GetPixelValueOfSelectedItem();
+
+ workingImage->GetActiveLabelSet()->SetAllLabelsVisible(false);
+ workingImage->GetLabel(pixelValue)->SetVisible(true);
+
+ GetWorkingImage()->GetActiveLabelSet()->UpdateLookupTable(pixelValue);
+
+ this->WaitCursorOn();
+ const mitk::Point3D& pos = workingImage->GetLabel(pixelValue)->GetCenterOfMassCoordinates();
+ this->WaitCursorOff();
+ if (pos.GetVnlVector().max_value() > 0.0)
+ emit goToLabel(pos);
+
+ UpdateAllTableWidgetItems();
+}
+
+
+void QmitkLabelSetWidget::OnMergeLabel(bool /*value*/)
+{
+ QmitkSearchLabelDialog dialog(this);
+ dialog.setWindowTitle("Select a second label..");
+ dialog.SetLabelSuggestionList(GetLabelStringList());
+ int dialogReturnValue = dialog.exec();
+ if ( dialogReturnValue == QDialog::Rejected ) return;
+
+ int pixelValue = -1;
+ for(int i = 0 ; i < m_Controls.m_LabelSetTableWidget->columnCount();i++)
+ {
+ if( dialog.GetLabelSetWidgetTableCompleteWord() == QString( m_Controls.m_LabelSetTableWidget->item( i ,0)->text() ) )
+ pixelValue = m_Controls.m_LabelSetTableWidget->item(i ,0)->data(Qt::UserRole).toInt();
+ }
+
+ if(pixelValue == -1 )
+ {
+ MITK_INFO << "unknown label";;
+ return;
+ }
+
+ GetWorkingImage()->MergeLabel(pixelValue);
+
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+}
+
+void QmitkLabelSetWidget::OnEraseLabel(bool /*value*/)
+{
+ int pixelValue = GetPixelValueOfSelectedItem();
+ QString question = "Do you really want to erase the contents of label \"";
+ question.append(QString::fromStdString(GetWorkingImage()->GetLabel(pixelValue)->GetName()));
+ question.append("\"?");
+
+ QMessageBox::StandardButton answerButton = QMessageBox::question( this, "Erase label",
+ question, QMessageBox::Yes | QMessageBox::Cancel, QMessageBox::Yes);
+
+ if (answerButton == QMessageBox::Yes)
+ {
+ this->WaitCursorOn();
+ GetWorkingImage()->EraseLabel(pixelValue);
+ this->WaitCursorOff();
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+ }
+}
+
+void QmitkLabelSetWidget::OnRemoveLabel(bool /*value*/)
+{
+ int pixelValue = GetPixelValueOfSelectedItem();
+ QString question = "Do you really want to remove label \"";
+ question.append(QString::fromStdString(GetWorkingImage()->GetLabel(pixelValue)->GetName()));
+ question.append("\"?");
+
+ QMessageBox::StandardButton answerButton = QMessageBox::question( this, "Remove label",
+ question, QMessageBox::Yes | QMessageBox::Cancel, QMessageBox::Yes);
+
+ if (answerButton == QMessageBox::Yes)
+ {
+ this->WaitCursorOn();
+ GetWorkingImage()->GetActiveLabelSet()->RemoveLabel(pixelValue);
+ GetWorkingImage()->EraseLabel(pixelValue);
+ this->WaitCursorOff();
+ }
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+}
+
+void QmitkLabelSetWidget::OnRenameLabel(bool /*value*/)
+{
+
+ QmitkNewSegmentationDialog dialog(this);
+ dialog.setWindowTitle("Rename Label");
+ dialog.SetSuggestionList( m_OrganColors );
+ dialog.SetColor(GetWorkingImage()->GetActiveLabel()->GetColor());
+ dialog.SetSegmentationName(GetWorkingImage()->GetActiveLabel()->GetName());
+
+ if ( dialog.exec() == QDialog::Rejected ) return;
+ int pixelValue = GetWorkingImage()->GetActiveLabel()->GetValue();
+
+ GetWorkingImage()->GetLabel(pixelValue)->SetColor(dialog.GetColor());
+ GetWorkingImage()->GetLabel(pixelValue)->SetName(dialog.GetSegmentationName().toStdString());
+ GetWorkingImage()->GetActiveLabelSet()->UpdateLookupTable(pixelValue);
+}
+
+void QmitkLabelSetWidget::OnCombineAndCreateMask( bool /*value*/ )
+{
+ m_Controls.m_LabelSetTableWidget->selectedRanges();
+ // ...to do... //
+}
+
+void QmitkLabelSetWidget::OnCreateMasks(bool /*value*/)
+{
+ m_Controls.m_LabelSetTableWidget->selectedRanges();
+ // ..to do.. //
+}
+
+void QmitkLabelSetWidget::OnCombineAndCreateSurface(bool /*value*/)
+{
+ m_Controls.m_LabelSetTableWidget->selectedRanges();
+ // ..to do.. //
+}
+
+void QmitkLabelSetWidget::OnEraseLabels(bool /*value*/)
+{
+ QString question = "Do you really want to erase the selected labels?";
+
+ QMessageBox::StandardButton answerButton = QMessageBox::question( this, "Erase selected labels",
+ question, QMessageBox::Yes | QMessageBox::Cancel, QMessageBox::Yes);
+
+ if (answerButton == QMessageBox::Yes)
+ {
+ QList ranges = m_Controls.m_LabelSetTableWidget->selectedRanges();
+ if ( ranges.isEmpty() )
+ return;
+
+ std::vector VectorOfLablePixelValues;
+ foreach (QTableWidgetSelectionRange a, ranges)
+ for(int i = a.topRow(); i <= a.bottomRow(); i++)
+ VectorOfLablePixelValues.push_back(m_Controls.m_LabelSetTableWidget->item(i,0)->data(Qt::UserRole).toInt());
+
+ this->WaitCursorOn();
+ GetWorkingImage()->EraseLabels(VectorOfLablePixelValues);
+ this->WaitCursorOff();
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+ }
+}
+
+void QmitkLabelSetWidget::OnRemoveLabels(bool /*value*/)
+{
+ QString question = "Do you really want to remove selected labels?";
+ QMessageBox::StandardButton answerButton = QMessageBox::question( this, "Remove selected labels",
+ question, QMessageBox::Yes | QMessageBox::Cancel, QMessageBox::Yes);
+
+ if (answerButton == QMessageBox::Yes)
+ {
+ QList ranges = m_Controls.m_LabelSetTableWidget->selectedRanges();
+ if ( ranges.isEmpty() )
+ return;
+
+ std::vector VectorOfLablePixelValues;
+ foreach (QTableWidgetSelectionRange a, ranges)
+ for(int i = a.topRow(); i <= a.bottomRow(); i++)
+ VectorOfLablePixelValues.push_back(m_Controls.m_LabelSetTableWidget->item(i,0)->data(Qt::UserRole).toInt());
+
+ this->WaitCursorOn();
+ GetWorkingImage()->RemoveLabels(VectorOfLablePixelValues);
+ this->WaitCursorOff();
+ }
+
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+}
+
+void QmitkLabelSetWidget::OnMergeLabels(bool /*value*/)
+{
+ int pixelValue = GetPixelValueOfSelectedItem();
+ QString question = "Do you really want to merge selected labels into \"";
+ question.append(QString::fromStdString(GetWorkingImage()->GetLabel(pixelValue)->GetName()));
+ question.append("\"?");
+
+ QMessageBox::StandardButton answerButton = QMessageBox::question( this, "Merge selected label",
+ question, QMessageBox::Yes | QMessageBox::Cancel, QMessageBox::Yes);
+
+ if (answerButton == QMessageBox::Yes)
+ {
+ QList ranges = m_Controls.m_LabelSetTableWidget->selectedRanges();
+ if ( ranges.isEmpty() )
+ return;
+
+ std::vector VectorOfLablePixelValues;
+ foreach (QTableWidgetSelectionRange a, ranges)
+ for(int i = a.topRow(); i <= a.bottomRow(); i++)
+ VectorOfLablePixelValues.push_back(m_Controls.m_LabelSetTableWidget->item(i,0)->data(Qt::UserRole).toInt());
+
+ this->WaitCursorOn();
+ int pixelValue = m_Controls.m_LabelSetTableWidget->item(m_Controls.m_LabelSetTableWidget->currentRow(),0)->data(Qt::UserRole).toInt();
+ GetWorkingImage()->MergeLabels(VectorOfLablePixelValues,pixelValue);
+ this->WaitCursorOff();
+
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+ }
+}
+
+void QmitkLabelSetWidget::OnLockedButtonClicked()
+{
+ int row;
+ for(int i=0; irowCount(); i++)
+ {
+ if (sender() == m_Controls.m_LabelSetTableWidget->cellWidget(i,LOCKED_COL))
+ {
+ row = i;
+ }
+ }
+ if (row >= 0 && row < m_Controls.m_LabelSetTableWidget->rowCount())
+ {
+ int pixelValue = m_Controls.m_LabelSetTableWidget->item(row,0)->data(Qt::UserRole).toInt();
+ GetWorkingImage()->GetLabel(pixelValue)->SetLocked(!GetWorkingImage()->GetLabel(pixelValue)->GetLocked() );
+ }
+}
+
+void QmitkLabelSetWidget::OnVisibleButtonClicked()
+{
+ int row;
+ for(int i=0; irowCount(); i++)
+ {
+ if (sender() == m_Controls.m_LabelSetTableWidget->cellWidget(i,VISIBLE_COL))
+ {
+ row = i;
+ break;
+ }
+ }
+
+ if (row >= 0 && row < m_Controls.m_LabelSetTableWidget->rowCount())
+ {
+ QTableWidgetItem * item = m_Controls.m_LabelSetTableWidget->item(row,0);
+ OnItemClicked(item);
+ int pixelValue = item->data(Qt::UserRole).toInt();
+ GetWorkingImage()->GetLabel(pixelValue)->SetVisible(!GetWorkingImage()->GetLabel(pixelValue)->GetVisible() );
+ GetWorkingImage()->GetActiveLabelSet()->UpdateLookupTable(pixelValue);
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+ }
+}
+
+void QmitkLabelSetWidget::OnColorButtonClicked()
+{
+ int row;
+ for(int i=0; irowCount(); i++)
+ {
+ if (sender() == m_Controls.m_LabelSetTableWidget->cellWidget(i,COLOR_COL))
+ {
+ row = i;
+ }
+ }
+
+ if (row >= 0 && row < m_Controls.m_LabelSetTableWidget->rowCount())
+ {
+ int pixelValue = m_Controls.m_LabelSetTableWidget->item(row,0)->data(Qt::UserRole).toInt();
+ const mitk::Color& color = GetWorkingImage()->GetLabel(pixelValue)->GetColor();
+ QColor initial(color.GetRed()*255,color.GetGreen()*255,color.GetBlue()*255);
+ QColor qcolor = QColorDialog::getColor(initial,0,QString("Change color"));
+ if (!qcolor.isValid())
+ return;
+
+ QPushButton* button = (QPushButton*) m_Controls.m_LabelSetTableWidget->cellWidget(row,COLOR_COL);
+ if (!button) return;
+
+ button->setAutoFillBackground(true);
+
+ QString styleSheet = "background-color:rgb(";
+ styleSheet.append(QString::number(qcolor.red()));
+ styleSheet.append(",");
+ styleSheet.append(QString::number(qcolor.green()));
+ styleSheet.append(",");
+ styleSheet.append(QString::number(qcolor.blue()));
+ styleSheet.append(")");
+ button->setStyleSheet(styleSheet);
+
+ mitk::Color newColor;
+ newColor.SetRed(qcolor.red()/255.0);
+ newColor.SetGreen(qcolor.green()/255.0);
+ newColor.SetBlue(qcolor.blue()/255.0);
+
+ GetWorkingImage()->GetLabel(pixelValue)->SetColor(newColor);
+
+ GetWorkingImage()->GetActiveLabelSet()->UpdateLookupTable(pixelValue);
+ }
+}
+
+void QmitkLabelSetWidget::OnRandomColor(bool /*value*/)
+{
+ int pixelValue = GetPixelValueOfSelectedItem();
+ GetWorkingImage()->GetLabel(pixelValue)->SetColor(m_ColorSequenceRainbow.GetNextColor() );
+ GetWorkingImage()->GetActiveLabelSet()->UpdateLookupTable(pixelValue);
+}
+
+void QmitkLabelSetWidget::SetOrganColors(const QStringList& organColors)
+{
+ m_OrganColors = organColors;
+}
+
+void QmitkLabelSetWidget::OnActiveLabelChanged(int pixelValue)
+{
+ mitk::LabelSetImage* workingImage = GetWorkingImage();
+ assert(workingImage);
+ workingImage->GetActiveLabelSet()->SetActiveLabel(pixelValue);
+ //MITK_INFO << "Active Label set to << " << pixelValue;
+
+ mitk::SurfaceBasedInterpolationController* interpolator = mitk::SurfaceBasedInterpolationController::GetInstance();
+ if (interpolator)
+ interpolator->SetActiveLabel(pixelValue);
+}
+
+void QmitkLabelSetWidget::OnItemClicked(QTableWidgetItem *item)
+{
+ if (!item) return;
+
+ int pixelValue = item->data(Qt::UserRole).toInt();
+
+ QList ranges = m_Controls.m_LabelSetTableWidget->selectedRanges();
+ if(!ranges.empty() && ranges.back().rowCount() == 1)
+ {
+ SelectLabelByPixelValue(pixelValue);
+ OnActiveLabelChanged(pixelValue);
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+ }
+
+}
+
+void QmitkLabelSetWidget::OnItemDoubleClicked(QTableWidgetItem *item)
+{
+ if (!item) return;
+ int pixelValue = item->data(Qt::UserRole).toInt();
+ //OnItemClicked(item); <<-- Double click first call OnItemClicked
+ WaitCursorOn();
+ mitk::LabelSetImage * workingImage = GetWorkingImage();
+ workingImage->UpdateCenterOfMass(pixelValue);
+ const mitk::Point3D& pos = workingImage->GetLabel(pixelValue)->GetCenterOfMassCoordinates();
+ WaitCursorOff();
+ if (pos.GetVnlVector().max_value() > 0.0) emit goToLabel(pos);
+}
+
+void QmitkLabelSetWidget::SelectLabelByPixelValue(int pixelValue)
+{
+
+ //MITK_INFO << "QmitkLabelSetWidget::SelectLabelByPixelValue " << pixelValue;
+
+ if(!GetWorkingImage()->ExistLabel(pixelValue)) return;
+ for(int row = 0 ; row < m_Controls.m_LabelSetTableWidget->rowCount(); row++)
+ {
+ if(m_Controls.m_LabelSetTableWidget->item(row,0)->data(Qt::UserRole).toInt() == pixelValue)
+ {
+ m_Controls.m_LabelSetTableWidget->clearSelection();
+ m_Controls.m_LabelSetTableWidget->setSelectionMode(QAbstractItemView::SingleSelection);
+ m_Controls.m_LabelSetTableWidget->selectRow(row);
+ m_Controls.m_LabelSetTableWidget->scrollToItem(m_Controls.m_LabelSetTableWidget->item(row,0));
+ m_Controls.m_LabelSetTableWidget->setSelectionMode(QAbstractItemView::ExtendedSelection);
+ //SelectTableWidgetItem(m_Controls.m_LabelSetTableWidget->item(i,0));
+ //emit resetView();
+ //GetWorkingImage()->Modified();
+ return;
+ }
+ }
+}
+
+void QmitkLabelSetWidget::InsertTableWidgetItem(mitk::Label * label)
+{
+ const mitk::Color& color = label->GetColor();
+
+ QTableWidget * tableWidget = m_Controls.m_LabelSetTableWidget;
+
+ QString styleSheet = "background-color:rgb(";
+ styleSheet.append(QString::number(color[0]*255));
+ styleSheet.append(",");
+ styleSheet.append(QString::number(color[1]*255));
+ styleSheet.append(",");
+ styleSheet.append(QString::number(color[2]*255));
+ styleSheet.append(")");
+
+ int colWidth = (tableWidget->columnWidth(NAME_COL) < 180) ? 180 : tableWidget->columnWidth(NAME_COL)-2;
+ QString text = fontMetrics().elidedText(label->GetName().c_str(), Qt::ElideMiddle, colWidth);
+ QTableWidgetItem *nameItem = new QTableWidgetItem(text);
+ nameItem->setTextAlignment(Qt::AlignCenter | Qt::AlignLeft);
+ // ---!---
+ // IMPORTANT: ADD PIXELVALUE TO TABLEWIDGETITEM.DATA
+ nameItem->setData(Qt::UserRole,QVariant(label->GetValue()));
+ // ---!---
+
+ QPushButton * pbColor = new QPushButton(tableWidget);
+ pbColor->setFixedSize(24,24);
+ pbColor->setCheckable(false);
+ pbColor->setAutoFillBackground(true);
+ pbColor->setToolTip("Change label color");
+ pbColor->setStyleSheet(styleSheet);
+
+ connect( pbColor, SIGNAL(clicked()), this, SLOT(OnColorButtonClicked()) );
+
+ QPushButton * pbLocked = new QPushButton(tableWidget);
+ pbLocked->setFixedSize(24,24);
+ QIcon * iconLocked = new QIcon();
+ iconLocked->addFile(QString::fromUtf8(":/Qmitk/lock.png"), QSize(), QIcon::Normal, QIcon::Off);
+ iconLocked->addFile(QString::fromUtf8(":/Qmitk/unlock.png"), QSize(), QIcon::Normal, QIcon::On);
+ pbLocked->setIcon(*iconLocked);
+ pbLocked->setIconSize(QSize(24,24));
+ pbLocked->setCheckable(true);
+ pbLocked->setToolTip("Lock/unlock label");
+ pbLocked->setChecked(!label->GetLocked());
+ connect( pbLocked, SIGNAL(clicked()), this, SLOT(OnLockedButtonClicked()) );
+
+ QPushButton * pbVisible = new QPushButton(tableWidget);
+ pbVisible->setFixedSize(24,24);
+ pbVisible->setAutoRepeat(false);
+ QIcon * iconVisible = new QIcon();
+ iconVisible->addFile(QString::fromUtf8(":/Qmitk/visible.png"), QSize(), QIcon::Normal, QIcon::Off);
+ iconVisible->addFile(QString::fromUtf8(":/Qmitk/invisible.png"), QSize(), QIcon::Normal, QIcon::On);
+ pbVisible->setIcon(*iconVisible);
+ pbVisible->setIconSize(QSize(24,24));
+ pbVisible->setCheckable(true);
+ pbVisible->setToolTip("Show/hide label");
+ pbVisible->setChecked(!label->GetVisible());
+
+ connect( pbVisible, SIGNAL(clicked()), this, SLOT(OnVisibleButtonClicked()) );
+
+ int row = tableWidget->rowCount();
+ tableWidget->insertRow(row);
+ tableWidget->setRowHeight(row,24);
+ tableWidget->setItem(row, 0, nameItem );
+ tableWidget->setCellWidget(row, 1, pbLocked);
+ tableWidget->setCellWidget(row, 2, pbColor);
+ tableWidget->setCellWidget(row, 3, pbVisible);
+ tableWidget->selectRow(row);
+
+ //m_LabelSetImage->SetActiveLabel(label->GetPixelValue());
+ //m_ToolManager->WorkingDataModified.Send();
+ //emit activeLabelChanged(label->GetPixelValue());
+
+ if (row == 0)
+ tableWidget->hideRow(row); // hide exterior label
+
+ mitk::LabelSetImage * workingImage;
+ if((workingImage = GetWorkingImage()) == NULL) return;
+
+}
+
+void QmitkLabelSetWidget::UpdateAllTableWidgetItems()
+{
+ QTableWidget * tableWidget = m_Controls.m_LabelSetTableWidget;
+
+ mitk::LabelSetImage * workingImage = GetWorkingImage();
+ if(!workingImage) return;
+
+ // add all labels
+ m_LabelStringList.clear();
+ for(int i = 0 ; i < tableWidget->rowCount(); i++)
+ {
+ UpdateTableWidgetItem(tableWidget->item(i,0));
+ m_LabelStringList.append( tableWidget->item(i,0)->text() );
+ }
+
+ OnLabelListModified(m_LabelStringList);
+
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+}
+
+void QmitkLabelSetWidget::UpdateTableWidgetItem(QTableWidgetItem *item)
+{
+ mitk::LabelSetImage * workingImage = GetWorkingImage();
+ mitk::Label * label = workingImage->GetLabel(item->data(Qt::UserRole).toInt());
+
+ const mitk::Color& color = label->GetColor();
+
+ QTableWidget * tableWidget = m_Controls.m_LabelSetTableWidget;
+
+ QString styleSheet = "background-color:rgb(";
+ styleSheet.append(QString::number(color[0]*255));
+ styleSheet.append(",");
+ styleSheet.append(QString::number(color[1]*255));
+ styleSheet.append(",");
+ styleSheet.append(QString::number(color[2]*255));
+ styleSheet.append(")");
+
+ // Update text Label tableWdget->item(row,0)
+ int colWidth = (tableWidget->columnWidth(NAME_COL) < 180) ? 180 : tableWidget->columnWidth(NAME_COL)-2;
+ QString text = fontMetrics().elidedText(label->GetName().c_str(), Qt::ElideMiddle, colWidth);
+ item->setText(text);
+
+ QPushButton * pbLocked = dynamic_cast(tableWidget->cellWidget(item->row(),1));
+ pbLocked->setChecked(!label->GetLocked());
+
+ QPushButton * pbColor = dynamic_cast(tableWidget->cellWidget(item->row(),2));
+ pbColor->setStyleSheet(styleSheet);
+
+ QPushButton * pbVisible = dynamic_cast(tableWidget->cellWidget(item->row(),3));
+ pbVisible->setChecked(!label->GetVisible());
+
+ if (item->row() == 0)tableWidget->hideRow(item->row()); // hide exterior label
+}
+
+
+void QmitkLabelSetWidget::ResetAllTableWidgetItems()
+{
+ QTableWidget * tableWidget = m_Controls.m_LabelSetTableWidget;
+ // remove all rows
+ while (tableWidget->rowCount())
+ tableWidget->removeRow( 0 );
+
+ mitk::LabelSetImage * workingImage = GetWorkingImage();
+ if(!workingImage) return;
+
+ // add all labels
+ m_LabelStringList.clear();
+
+ mitk::LabelSet::LabelContainerConstIteratorType it = workingImage->GetActiveLabelSet()->IteratorConstBegin();
+ mitk::LabelSet::LabelContainerConstIteratorType end = workingImage->GetActiveLabelSet()->IteratorConstEnd();
+
+ int pixelValue =-1;
+ while (it != end)
+ {
+ InsertTableWidgetItem(it->second);
+ if(GetWorkingImage()->GetActiveLabel() == it->second) // get active
+ pixelValue = it->first;
+ m_LabelStringList.append( QString(it->second->GetName().c_str()) );
+ it++;
+ }
+
+ SelectLabelByPixelValue(pixelValue);
+
+ OnLabelListModified(m_LabelStringList);
+
+ std::stringstream captionText;
+ captionText << "Number of labels: " << workingImage->GetNumberOfLabels() - 1;
+ m_Controls.m_lblCaption->setText(captionText.str().c_str());
+
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+}
+
+int QmitkLabelSetWidget::GetPixelValueOfSelectedItem()
+{
+ if(m_Controls.m_LabelSetTableWidget->currentItem())
+ return m_Controls.m_LabelSetTableWidget->currentItem()->data(Qt::UserRole).toInt();
+ return -1;
+}
+
+QStringList & QmitkLabelSetWidget::GetLabelStringList()
+{
+ return m_LabelStringList;
+}
+
+void QmitkLabelSetWidget::InitializeTableWidget()
+{
+ QTableWidget * tableWidged = m_Controls.m_LabelSetTableWidget;
+
+ tableWidged->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Maximum);
+ tableWidged->setTabKeyNavigation(false);
+ tableWidged->setAlternatingRowColors(false);
+ tableWidged->setFocusPolicy(Qt::NoFocus);
+ tableWidged->setColumnCount(4);
+ tableWidged->resizeColumnToContents(NAME_COL);
+ tableWidged->setColumnWidth(LOCKED_COL,25);
+ tableWidged->setColumnWidth(COLOR_COL,25);
+ tableWidged->setColumnWidth(VISIBLE_COL,25);
+ tableWidged->horizontalHeader()->setResizeMode( 0, QHeaderView::Stretch );
+ tableWidged->setContextMenuPolicy(Qt::CustomContextMenu);
+ tableWidged->horizontalHeader()->hide();
+ tableWidged->setSortingEnabled ( false );
+ tableWidged->verticalHeader()->hide();
+ tableWidged->setEditTriggers(QAbstractItemView::NoEditTriggers);
+ tableWidged->setSelectionMode(QAbstractItemView::ExtendedSelection);
+ tableWidged->setSelectionBehavior(QAbstractItemView::SelectRows);
+
+ connect(tableWidged, SIGNAL(itemClicked(QTableWidgetItem *)), this, SLOT(OnItemClicked(QTableWidgetItem *)));
+ connect(tableWidged, SIGNAL(itemDoubleClicked(QTableWidgetItem *)), this, SLOT(OnItemDoubleClicked(QTableWidgetItem *)));
+ connect(tableWidged, SIGNAL(customContextMenuRequested(const QPoint&)), this, SLOT(OnTableViewContextMenuRequested(const QPoint&)) );
+
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(activeLabelChanged(int)), this, SLOT(OnActiveLabelChanged(int)) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(importSegmentation()), this, SLOT( OnImportSegmentation()) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(importLabeledImage()), this, SLOT( OnImportLabeledImage()) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(renameLabel(int, const mitk::Color&, const std::string&)), this, SLOT(OnRenameLabel(int, const mitk::Color&, const std::string&)) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(createSurface(int, bool)), this, SLOT(OnCreateSurface(int, bool)) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(toggleOutline(bool)), this, SLOT(OnToggleOutline(bool)) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(goToLabel(const mitk::Point3D&)), this, SIGNAL(goToLabel(const mitk::Point3D&)) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(combineAndCreateSurface( const QList& )),
+ // this, SLOT(OnCombineAndCreateSurface( const QList&)) );
+
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(createMask(int)), this, SLOT(OnCreateMask(int)) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(createCroppedMask(int)), this, SLOT(OnCreateCroppedMask(int)) );
+ //connect( m_Controls.m_LabelSetTableWidget, SIGNAL(combineAndCreateMask( const QList& )),
+ // this, SLOT(OnCombineAndCreateMask( const QList&)) );
+}
+
+void QmitkLabelSetWidget::OnOpacityChanged(int value)
+{
+ int pixelValue = m_Controls.m_LabelSetTableWidget->currentItem()->data(Qt::UserRole).toInt();
+ float opacity = static_cast(value)/100.0f;
+ GetWorkingImage()->GetLabel(pixelValue)->SetOpacity(opacity);
+ GetWorkingImage()->GetActiveLabelSet()->UpdateLookupTable(pixelValue);
+}
+
+void QmitkLabelSetWidget::setEnabled(bool enabled)
+{
+ QWidget::setEnabled(enabled);
+ UpdateControls();
+}
+
+void QmitkLabelSetWidget::SetDataStorage( mitk::DataStorage* storage )
+{
+ m_DataStorage = storage;
+}
+
+void QmitkLabelSetWidget::OnSearchLabel()
+{
+ std::string text = m_Controls.m_LabelSearchBox->text().toStdString();
+ int pixelValue = -1;
+ int row = -1;
+ for(int i = 0; i < m_Controls.m_LabelSetTableWidget->rowCount(); i++){
+ if( m_Controls.m_LabelSetTableWidget->item(i,0)->text().toStdString().compare(text) == 0)
+ {
+ pixelValue = m_Controls.m_LabelSetTableWidget->item(i,0)->data(Qt::UserRole).toInt();
+ row = i;
+ break;
+ }
+ }
+ if(pixelValue == -1) return;
+ GetWorkingImage()->GetActiveLabelSet()->SetActiveLabel(pixelValue);
+
+ QTableWidgetItem* nameItem = m_Controls.m_LabelSetTableWidget->item(row,NAME_COL);
+ if (!nameItem) return;
+
+ m_Controls.m_LabelSetTableWidget->clearSelection();
+ m_Controls.m_LabelSetTableWidget->setSelectionMode(QAbstractItemView::SingleSelection);
+ m_Controls.m_LabelSetTableWidget->selectRow(row);
+ m_Controls.m_LabelSetTableWidget->scrollToItem(nameItem);
+ m_Controls.m_LabelSetTableWidget->setSelectionMode(QAbstractItemView::ExtendedSelection);
+
+ this->WaitCursorOn();
+ mitk::Point3D pos = GetWorkingImage()->GetLabel(pixelValue)->GetCenterOfMassCoordinates();
+
+ m_ToolManager->WorkingDataModified.Send();
+
+ if (pos.GetVnlVector().max_value() > 0.0)
+ emit goToLabel(pos);
+ else
+ {
+ GetWorkingImage()->UpdateCenterOfMass(pixelValue);
+ mitk::Point3D pos = GetWorkingImage()->GetLabel(pixelValue)->GetCenterOfMassCoordinates();
+ emit goToLabel(pos);
+ }
+
+ this->WaitCursorOff();
+}
+
+void QmitkLabelSetWidget::OnLabelListModified(const QStringList& list)
+{
+ QStringListModel* completeModel = static_cast (m_Completer->model());
+ completeModel->setStringList(list);
+}
+
+mitk::LabelSetImage * QmitkLabelSetWidget::GetWorkingImage()
+{
+ mitk::DataNode* workingNode = GetWorkingNode();
+ mitk::LabelSetImage* workingImage = dynamic_cast(workingNode->GetData());
+ assert(workingImage);
+ return workingImage;
+}
+
+mitk::DataNode * QmitkLabelSetWidget::GetWorkingNode()
+{
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ assert(workingNode);
+ return workingNode;
+}
+
+
+void QmitkLabelSetWidget::UpdateControls()
+{
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ bool hasWorkingData = (workingNode != NULL);
+
+ m_Controls.m_LabelSetTableWidget->setEnabled(hasWorkingData);
+ m_Controls.m_LabelSearchBox->setEnabled(hasWorkingData);
+
+ if (!hasWorkingData) return;
+
+ QStringListModel* completeModel = static_cast (m_Completer->model());
+ completeModel->setStringList(GetLabelStringList());
+
+}
+
+
+
+void QmitkLabelSetWidget::OnCreateCroppedMask(bool)
+{
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode* workingNode = GetWorkingNode();
+ mitk::LabelSetImage* workingImage = GetWorkingImage();
+
+ mitk::Image::Pointer maskImage;
+
+ int pixelValue = GetPixelValueOfSelectedItem();
+ try
+ {
+ this->WaitCursorOn();
+
+ mitk::AutoCropImageFilter::Pointer cropFilter = mitk::AutoCropImageFilter::New();
+ cropFilter->SetInput( workingImage->CreateLabelMask(pixelValue) );
+ cropFilter->SetBackgroundValue( 0 );
+ cropFilter->SetMarginFactor(1.15);
+ cropFilter->Update();
+
+ maskImage = cropFilter->GetOutput();
+
+ this->WaitCursorOff();
+ }
+ catch ( mitk::Exception& e )
+ {
+ this->WaitCursorOff();
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ QMessageBox::information(this, "Create Mask", "Could not create a mask out of the selected label.\n");
+ return;
+ }
+
+ if (maskImage.IsNull())
+ {
+ QMessageBox::information(this, "Create Mask", "Could not create a mask out of the selected label.\n");
+ return;
+ }
+
+ mitk::DataNode::Pointer maskNode = mitk::DataNode::New();
+ std::string name = workingImage->GetLabel(pixelValue, workingImage->GetActiveLayer())->GetName();
+ name += "-mask";
+ maskNode->SetName(name);
+ maskNode->SetData(maskImage);
+ maskNode->SetBoolProperty("binary", true);
+ maskNode->SetBoolProperty("outline binary", true);
+ maskNode->SetBoolProperty("outline binary shadow", true);
+ maskNode->SetFloatProperty("outline width", 2.0);
+ maskNode->SetColor(workingImage->GetLabel(pixelValue)->GetColor());
+ maskNode->SetOpacity(1.0);
+
+ m_DataStorage->Add(maskNode, workingNode);
+}
+
+void QmitkLabelSetWidget::OnCreateMask(bool /*triggered*/)
+{
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode* workingNode = GetWorkingNode();
+ mitk::LabelSetImage* workingImage = GetWorkingImage();
+
+ mitk::Image::Pointer maskImage;
+
+ int pixelValue = GetPixelValueOfSelectedItem();
+
+ try
+ {
+ this->WaitCursorOn();
+ maskImage = workingImage->CreateLabelMask(pixelValue);
+ this->WaitCursorOff();
+ }
+ catch ( mitk::Exception& e )
+ {
+ this->WaitCursorOff();
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ QMessageBox::information(this, "Create Mask", "Could not create a mask out of the selected label.\n");
+ return;
+ }
+
+ if (maskImage.IsNull())
+ {
+ QMessageBox::information(this, "Create Mask", "Could not create a mask out of the selected label.\n");
+ return;
+ }
+
+ mitk::DataNode::Pointer maskNode = mitk::DataNode::New();
+ std::string name = workingImage->GetLabel(pixelValue, workingImage->GetActiveLayer())->GetName();
+ name += "-mask";
+ maskNode->SetName(name);
+ maskNode->SetData(maskImage);
+ maskNode->SetBoolProperty("binary", true);
+ maskNode->SetBoolProperty("outline binary", true);
+ maskNode->SetBoolProperty("outline binary shadow", true);
+ maskNode->SetFloatProperty("outline width", 2.0);
+ maskNode->SetColor(workingImage->GetLabel(pixelValue)->GetColor());
+ maskNode->SetOpacity(1.0);
+
+ m_DataStorage->Add(maskNode, workingNode);
+}
+
+void QmitkLabelSetWidget::OnToggleOutline(bool value)
+{
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ assert(workingNode);
+
+ workingNode->SetBoolProperty( "labelset.contour.all", value);
+ workingNode->GetData()->Modified(); // fixme: workaround to force data-type rendering (and not only property-type)
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+}
+
+void QmitkLabelSetWidget::OnCreateSmoothedSurface(bool /*triggered*/)
+{
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode::Pointer workingNode = GetWorkingNode();
+ mitk::LabelSetImage* workingImage = GetWorkingImage();
+ int pixelValue = GetPixelValueOfSelectedItem();
+
+ mitk::LabelSetImageToSurfaceThreadedFilter::Pointer surfaceFilter = mitk::LabelSetImageToSurfaceThreadedFilter::New();
+
+ itk::SimpleMemberCommand::Pointer successCommand = itk::SimpleMemberCommand::New();
+ successCommand->SetCallbackFunction(this, &QmitkLabelSetWidget::OnThreadedCalculationDone);
+ surfaceFilter->AddObserver(mitk::ResultAvailable(), successCommand);
+
+ itk::SimpleMemberCommand::Pointer errorCommand = itk::SimpleMemberCommand::New();
+ errorCommand->SetCallbackFunction(this, &QmitkLabelSetWidget::OnThreadedCalculationDone);
+ surfaceFilter->AddObserver(mitk::ProcessingError(), errorCommand);
+
+ mitk::DataNode::Pointer groupNode = workingNode;
+ surfaceFilter->SetPointerParameter("Group node", groupNode);
+ surfaceFilter->SetPointerParameter("Input", workingImage);
+ surfaceFilter->SetParameter("RequestedLabel", pixelValue);
+ surfaceFilter->SetParameter("Smooth", true);
+ surfaceFilter->SetDataStorage( *m_DataStorage );
+
+ mitk::StatusBar::GetInstance()->DisplayText("Surface creation is running in background...");
+
+ try
+ {
+ surfaceFilter->StartAlgorithm();
+ }
+ catch ( mitk::Exception & e )
+ {
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ QMessageBox::information(this, "Create Surface", "Could not create a surface mesh out of the selected label. See error log for details.\n");
+ }
+
+}
+
+void QmitkLabelSetWidget::OnCreateDetailedSurface(bool /*triggered*/)
+{
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode::Pointer workingNode = GetWorkingNode();
+ mitk::LabelSetImage* workingImage = GetWorkingImage();
+ int pixelValue = GetPixelValueOfSelectedItem();
+
+ mitk::LabelSetImageToSurfaceThreadedFilter::Pointer surfaceFilter = mitk::LabelSetImageToSurfaceThreadedFilter::New();
+
+ itk::SimpleMemberCommand::Pointer successCommand = itk::SimpleMemberCommand::New();
+ successCommand->SetCallbackFunction(this, &QmitkLabelSetWidget::OnThreadedCalculationDone);
+ surfaceFilter->AddObserver(mitk::ResultAvailable(), successCommand);
+
+ itk::SimpleMemberCommand::Pointer errorCommand = itk::SimpleMemberCommand::New();
+ errorCommand->SetCallbackFunction(this, &QmitkLabelSetWidget::OnThreadedCalculationDone);
+ surfaceFilter->AddObserver(mitk::ProcessingError(), errorCommand);
+
+ mitk::DataNode::Pointer groupNode = workingNode;
+ surfaceFilter->SetPointerParameter("Group node", groupNode);
+ surfaceFilter->SetPointerParameter("Input", workingImage);
+ surfaceFilter->SetParameter("RequestedLabel", pixelValue);
+ surfaceFilter->SetParameter("Smooth", false);
+ surfaceFilter->SetDataStorage( *m_DataStorage );
+
+ mitk::StatusBar::GetInstance()->DisplayText("Surface creation is running in background...");
+
+ try
+ {
+ surfaceFilter->StartAlgorithm();
+ }
+ catch ( mitk::Exception & e )
+ {
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ QMessageBox::information(this, "Create Surface", "Could not create a surface mesh out of the selected label. See error log for details.\n");
+ }
+
+}
+
+void QmitkLabelSetWidget::OnImportLabeledImage()
+{
+/*
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode* referenceNode = m_ToolManager->GetReferenceData(0);
+ assert(referenceNode);
+
+ // Ask the user for a list of files to open
+ QStringList fileNames = QFileDialog::getOpenFileNames( this, "Open Image", m_LastFileOpenPath,
+ mitk::CoreObjectFactory::GetInstance()->GetFileExtensions());
+
+ if (fileNames.empty())
+ return;
+
+ try
+ {
+ this->WaitCursorOn();
+ mitk::Image::Pointer image = mitk::IOUtil::LoadImage( fileNames.front().toStdString() );
+ if (image.IsNull())
+ {
+ this->WaitCursorOff();
+ QMessageBox::information(this, "Import Labeled Image", "Could not load the selected segmentation.\n");
+ return;
+ }
+
+ mitk::LabelSetImage::Pointer newImage = mitk::LabelSetImage::New();
+ newImage->InitializeByLabeledImage(image);
+ this->WaitCursorOff();
+
+ mitk::DataNode::Pointer newNode = mitk::DataNode::New();
+ std::string newName = referenceNode->GetName();
+ newName += "-labels";
+ newNode->SetName(newName);
+ newNode->SetData(newImage);
+ m_DataStorage->Add(newNode, referenceNode);
+ }
+ catch (mitk::Exception & e)
+ {
+ this->WaitCursorOff();
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ QMessageBox::information(this, "Import Labeled Image", "Could not load the selected segmentation. See error log for details.\n");
+ return;
+ }
+
+ this->UpdateControls();
+
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+ */
+}
+
+void QmitkLabelSetWidget::OnImportSegmentation()
+{
+/*
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ assert(workingNode);
+
+ mitk::LabelSetImage* workingImage = dynamic_cast( workingNode->GetData() );
+ assert(workingImage);
+
+ std::string fileExtensions("Segmentation files (*.lset);;");
+ QString qfileName = QFileDialog::getOpenFileName(this, "Import Segmentation", m_LastFileOpenPath, fileExtensions.c_str() );
+ if (qfileName.isEmpty() ) return;
+
+ mitk::NrrdLabelSetImageReader::Pointer reader = mitk::NrrdLabelSetImageReader::New();
+ reader->SetFileName(qfileName.toLatin1());
+
+ try
+ {
+ this->WaitCursorOn();
+ reader->Update();
+ mitk::LabelSetImage::Pointer newImage = reader->GetOutput();
+ workingImage->Concatenate(newImage);
+ this->WaitCursorOff();
+ }
+ catch ( mitk::Exception& e )
+ {
+ this->WaitCursorOff();
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ QMessageBox::information(this, "Import Segmentation", "Could not import the selected segmentation session.\n See error log for details.\n");
+ }
+*/
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+}
+
+void QmitkLabelSetWidget::WaitCursorOn()
+{
+ QApplication::setOverrideCursor( QCursor(Qt::WaitCursor) );
+}
+
+void QmitkLabelSetWidget::WaitCursorOff()
+{
+ this->RestoreOverrideCursor();
+}
+
+void QmitkLabelSetWidget::RestoreOverrideCursor()
+{
+ QApplication::restoreOverrideCursor();
+}
+
+void QmitkLabelSetWidget::OnThreadedCalculationDone()
+{
+ mitk::StatusBar::GetInstance()->Clear();
+}
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkLabelSetWidget.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkLabelSetWidget.h
new file mode 100644
index 0000000000..262a5ab860
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkLabelSetWidget.h
@@ -0,0 +1,158 @@
+/*===================================================================
+
+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 QmitkLabelSetWidget_h
+#define QmitkLabelSetWidget_h
+
+#include "MitkSegmentationUIExports.h"
+
+#include
+#include "mitkColorSequenceRainbow.h"
+#include "mitkVector.h"
+
+
+class QmitkDataStorageComboBox;
+class QCompleter;
+
+namespace mitk {
+ class LabelSetImage;
+ class LabelSet;
+ class Label;
+ class DataStorage;
+ class ToolManager;
+ class DataNode;
+}
+
+class MitkSegmentationUI_EXPORT QmitkLabelSetWidget : public QWidget
+{
+ Q_OBJECT
+
+public:
+
+ explicit QmitkLabelSetWidget(QWidget* parent = NULL);
+ ~QmitkLabelSetWidget();
+
+ void SetDataStorage( mitk::DataStorage* storage );
+
+ void SetOrganColors(const QStringList& organColors);
+
+ void UpdateControls();
+
+ virtual void setEnabled(bool enabled);
+
+ QStringList &GetLabelStringList();
+
+
+signals:
+
+ /// \brief Send a signal when it was requested to go to a label.
+ void goToLabel(const mitk::Point3D&);
+ void resetView();
+
+public slots:
+
+ void ResetAllTableWidgetItems();
+ void UpdateAllTableWidgetItems();
+ void SelectLabelByPixelValue(int pixelValue);
+
+private slots:
+
+ // Label Set Dependend
+ void OnOpacityChanged(int);
+ void OnUnlockAllLabels(bool);
+ void OnLockAllLabels(bool);
+ void OnSetAllLabelsVisible(bool);
+ void OnSetAllLabelsInvisible(bool);
+ void OnSetOnlyActiveLabelVisible(bool);
+ void OnRandomColor(bool);
+ void OnRemoveLabel(bool);
+ void OnRemoveLabels(bool);
+ void OnRenameLabel(bool);
+ void OnLockedButtonClicked();
+ void OnVisibleButtonClicked();
+ void OnColorButtonClicked();
+ void OnItemClicked(QTableWidgetItem *item);
+ void OnItemDoubleClicked(QTableWidgetItem *item);
+ void OnTableViewContextMenuRequested(const QPoint&);
+ void InsertTableWidgetItem(mitk::Label * label);
+ void UpdateTableWidgetItem(QTableWidgetItem *item);
+ // reaction to "returnPressed" signal from ...
+ void OnSearchLabel();
+ // reaction to the button "Change Label"
+ void OnActiveLabelChanged(int pixelValue);
+
+ //LabelSetImage Dependet
+ void OnCreateDetailedSurface(bool);
+ void OnCreateSmoothedSurface(bool);
+ // reaction to the signal "createMask" from QmitkLabelSetTableWidget
+ void OnCreateMask(bool);
+ void OnCreateMasks(bool);
+ // reaction to the signal "createCroppedMask" from QmitkLabelSetTableWidget
+ void OnCreateCroppedMask(bool);
+ void OnCombineAndCreateMask(bool);
+ void OnCombineAndCreateSurface(bool);
+ void OnEraseLabel(bool);
+ void OnEraseLabels(bool);
+ // reaction to signal "mergeLabel" from QmitkLabelSetTableWidget
+ void OnMergeLabel(bool);
+ void OnMergeLabels(bool);
+ // reaction to the button "Import Segmentation"
+ void OnImportSegmentation();
+ // reaction to the button "Import Labeled Image"
+ void OnImportLabeledImage();
+
+ // reaction to signal "labelListModified" from QmitkLabelSetTableWidget
+ void OnLabelListModified(const QStringList& list);
+ // reaction to the signal "toggleOutline" from QmitkLabelSetTableWidget
+ void OnToggleOutline(bool);
+
+private:
+
+ enum TableColumns { NAME_COL=0, LOCKED_COL, COLOR_COL, VISIBLE_COL };
+
+ void WaitCursorOn();
+
+ void WaitCursorOff();
+
+ void RestoreOverrideCursor();
+
+ void OnThreadedCalculationDone();
+
+ void InitializeTableWidget();
+
+ int GetPixelValueOfSelectedItem();
+
+ mitk::LabelSetImage * GetWorkingImage();
+
+ mitk::DataNode * GetWorkingNode();
+
+ Ui::QmitkLabelSetWidgetControls m_Controls;
+
+ mitk::ColorSequenceRainbow m_ColorSequenceRainbow;
+
+ QCompleter* m_Completer;
+
+ mitk::DataStorage* m_DataStorage;
+
+ mitk::ToolManager* m_ToolManager;
+
+ QStringList m_OrganColors;
+
+ QStringList m_LabelStringList;
+
+};
+
+#endif
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkLabelSetWidgetControls.ui b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkLabelSetWidgetControls.ui
new file mode 100644
index 0000000000..a9b4c069a3
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkLabelSetWidgetControls.ui
@@ -0,0 +1,66 @@
+
+
+ QmitkLabelSetWidgetControls
+
+
+
+ 0
+ 0
+ 312
+ 366
+
+
+
+
+ 0
+ 0
+
+
+
+
+
+
+
+ 6
+
+
+ 6
+
+
+ 6
+
+
+ 6
+
+ -
+
+
+ Caption
+
+
+
+ -
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+
+
+
+
+ ctkSearchBox
+ QLineEdit
+
+
+
+
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkMultiLabelSegmentationPreferencePage.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkMultiLabelSegmentationPreferencePage.cpp
new file mode 100644
index 0000000000..ee96ac78ca
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkMultiLabelSegmentationPreferencePage.cpp
@@ -0,0 +1,171 @@
+/*===================================================================
+
+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 "QmitkMultiLabelSegmentationPreferencePage.h"
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+#include
+#include
+
+QmitkMultiLabelSegmentationPreferencePage::QmitkMultiLabelSegmentationPreferencePage()
+: m_MainControl(0)
+, m_Initializing(false)
+{
+
+}
+
+QmitkMultiLabelSegmentationPreferencePage::~QmitkMultiLabelSegmentationPreferencePage()
+{
+
+}
+
+void QmitkMultiLabelSegmentationPreferencePage::Init(berry::IWorkbench::Pointer )
+{
+
+}
+
+void QmitkMultiLabelSegmentationPreferencePage::CreateQtControl(QWidget* parent)
+{
+ m_Initializing = true;
+ berry::IPreferencesService::Pointer prefService
+ = berry::Platform::GetServiceRegistry()
+ .GetServiceById(berry::IPreferencesService::ID);
+
+ m_SegmentationPreferencesNode = prefService->GetSystemPreferences()->Node("/org.mitk.views.segmentation");
+
+ m_MainControl = new QWidget(parent);
+
+ QVBoxLayout* displayOptionsLayout = new QVBoxLayout;
+ m_RadioOutline = new QRadioButton( "Draw as outline", m_MainControl);
+ displayOptionsLayout->addWidget( m_RadioOutline );
+ m_RadioOverlay = new QRadioButton( "Draw as transparent overlay", m_MainControl);
+ displayOptionsLayout->addWidget( m_RadioOverlay );
+
+ QFormLayout *formLayout = new QFormLayout;
+ formLayout->setHorizontalSpacing(8);
+ formLayout->setVerticalSpacing(24);
+ formLayout->addRow( "2D display", displayOptionsLayout );
+
+ m_VolumeRenderingCheckBox = new QCheckBox( "Show as volume rendering", m_MainControl );
+ formLayout->addRow( "3D display", m_VolumeRenderingCheckBox );
+ connect( m_VolumeRenderingCheckBox, SIGNAL(stateChanged(int)), this, SLOT(OnVolumeRenderingCheckboxChecked(int)) );
+
+ QFormLayout* surfaceLayout = new QFormLayout;
+ surfaceLayout->setSpacing(8);
+
+ m_SmoothingSpinBox = new QDoubleSpinBox(m_MainControl);
+ m_SmoothingSpinBox->setMinimum(0.0);
+ m_SmoothingSpinBox->setSingleStep(0.5);
+ m_SmoothingSpinBox->setValue(0.1);
+ m_SmoothingSpinBox->setToolTip("The Smoothing value is used as Sigma for a gaussian blur.");
+ surfaceLayout->addRow("Smoothing value (mm)", m_SmoothingSpinBox);
+
+ m_DecimationSpinBox = new QDoubleSpinBox(m_MainControl);
+ m_DecimationSpinBox->setMinimum(0.0);
+ m_DecimationSpinBox->setMaximum(0.99);
+ m_DecimationSpinBox->setSingleStep(0.1);
+ m_DecimationSpinBox->setValue(0.5);
+ m_DecimationSpinBox->setToolTip("Valid range is [0, 1). High values increase decimation, especially when very close to 1. A value of 0 disables decimation.");
+ surfaceLayout->addRow("Decimation rate", m_DecimationSpinBox);
+
+ m_SelectionModeCheckBox = new QCheckBox("Enable auto-selection mode", m_MainControl);
+ m_SelectionModeCheckBox->setToolTip("If checked the segmentation plugin ensures that only one segmentation and the according greyvalue image are visible at one time.");
+ formLayout->addRow("Data node selection mode",m_SelectionModeCheckBox);
+
+ formLayout->addRow("Smoothed surface creation", surfaceLayout);
+
+ m_MainControl->setLayout(formLayout);
+ this->Update();
+ m_Initializing = false;
+}
+
+QWidget* QmitkMultiLabelSegmentationPreferencePage::GetQtControl() const
+{
+ return m_MainControl;
+}
+
+bool QmitkMultiLabelSegmentationPreferencePage::PerformOk()
+{
+ m_SegmentationPreferencesNode->PutBool("draw outline", m_RadioOutline->isChecked());
+ m_SegmentationPreferencesNode->PutBool("volume rendering", m_VolumeRenderingCheckBox->isChecked());
+ m_SegmentationPreferencesNode->PutDouble("smoothing value", m_SmoothingSpinBox->value());
+ m_SegmentationPreferencesNode->PutDouble("decimation rate", m_DecimationSpinBox->value());
+ m_SegmentationPreferencesNode->PutBool("auto selection", m_SelectionModeCheckBox->isChecked());
+ return true;
+}
+
+void QmitkMultiLabelSegmentationPreferencePage::PerformCancel()
+{
+
+}
+
+void QmitkMultiLabelSegmentationPreferencePage::Update()
+{
+ //m_EnableSingleEditing->setChecked(m_SegmentationPreferencesNode->GetBool("Single click property editing", true));
+ if (m_SegmentationPreferencesNode->GetBool("draw outline", true) )
+ {
+ m_RadioOutline->setChecked( true );
+ }
+ else
+ {
+ m_RadioOverlay->setChecked( true );
+ }
+
+ m_VolumeRenderingCheckBox->setChecked( m_SegmentationPreferencesNode->GetBool("volume rendering", false) );
+
+ if (m_SegmentationPreferencesNode->GetBool("smoothing hint", true))
+ {
+ m_SmoothingSpinBox->setDisabled(true);
+ }
+ else
+ {
+ m_SmoothingSpinBox->setEnabled(true);
+ }
+
+ m_SelectionModeCheckBox->setChecked( m_SegmentationPreferencesNode->GetBool("auto selection", true) );
+
+ m_SmoothingSpinBox->setValue(m_SegmentationPreferencesNode->GetDouble("smoothing value", 0.1));
+ m_DecimationSpinBox->setValue(m_SegmentationPreferencesNode->GetDouble("decimation rate", 0.5));
+}
+
+void QmitkMultiLabelSegmentationPreferencePage::OnVolumeRenderingCheckboxChecked(int state)
+{
+ if (m_Initializing) return;
+
+ if ( state != Qt::Unchecked )
+ {
+ QMessageBox::information(NULL,
+ "Memory warning",
+ "Turning on volume rendering of segmentations will make the application more memory intensive (and potentially prone to crashes).\n\n"
+ "If you encounter out-of-memory problems, try turning off volume rendering again.");
+ }
+}
+
+void QmitkMultiLabelSegmentationPreferencePage::OnSmoothingCheckboxChecked(int state)
+{
+ if (state != Qt::Unchecked)
+ m_SmoothingSpinBox->setDisabled(true);
+ else
+ m_SmoothingSpinBox->setEnabled(true);
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkMultiLabelSegmentationPreferencePage.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkMultiLabelSegmentationPreferencePage.h
new file mode 100644
index 0000000000..95cb8c74c4
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/QmitkMultiLabelSegmentationPreferencePage.h
@@ -0,0 +1,81 @@
+/*===================================================================
+
+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 QmitkMultiLabelSegmentationPreferencePage_h_included
+#define QmitkMultiLabelSegmentationPreferencePage_h_included
+
+#include "berryIQtPreferencePage.h"
+#include "org_mitk_gui_qt_multilabelsegmentation_Export.h"
+#include
+
+class QWidget;
+class QCheckBox;
+class QRadioButton;
+class QDoubleSpinBox;
+
+class MITK_QT_SEGMENTATION QmitkMultiLabelSegmentationPreferencePage : public QObject, public berry::IQtPreferencePage
+{
+ Q_OBJECT
+ Q_INTERFACES(berry::IPreferencePage)
+
+public:
+
+ QmitkMultiLabelSegmentationPreferencePage();
+ ~QmitkMultiLabelSegmentationPreferencePage();
+
+ void Init(berry::IWorkbench::Pointer workbench);
+
+ void CreateQtControl(QWidget* widget);
+
+ QWidget* GetQtControl() const;
+
+ ///
+ /// \see IPreferencePage::PerformOk()
+ ///
+ virtual bool PerformOk();
+
+ ///
+ /// \see IPreferencePage::PerformCancel()
+ ///
+ virtual void PerformCancel();
+
+ ///
+ /// \see IPreferencePage::Update()
+ ///
+ virtual void Update();
+
+protected slots:
+
+ void OnVolumeRenderingCheckboxChecked(int);
+ void OnSmoothingCheckboxChecked(int);
+
+protected:
+
+ QWidget* m_MainControl;
+ QRadioButton* m_RadioOutline;
+ QRadioButton* m_RadioOverlay;
+ QCheckBox* m_VolumeRenderingCheckBox;
+ QDoubleSpinBox* m_SmoothingSpinBox;
+ QDoubleSpinBox* m_DecimationSpinBox;
+ QCheckBox* m_SelectionModeCheckBox;
+
+ bool m_Initializing;
+
+ berry::IPreferences::Pointer m_SegmentationPreferencesNode;
+};
+
+#endif /* QMITKDATAMANAGERPREFERENCEPAGE_H_ */
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/Common/QmitkDataSelectionWidget.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/Common/QmitkDataSelectionWidget.cpp
new file mode 100644
index 0000000000..e4e7147c83
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/Common/QmitkDataSelectionWidget.cpp
@@ -0,0 +1,181 @@
+/*===================================================================
+
+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 "QmitkDataSelectionWidget.h"
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+static mitk::NodePredicateBase::Pointer CreatePredicate(QmitkDataSelectionWidget::PredicateType predicateType)
+{
+
+ mitk::NodePredicateAnd::Pointer segmentationPredicate = mitk::NodePredicateAnd::New();
+ segmentationPredicate->AddPredicate(mitk::TNodePredicateDataType::New());
+ segmentationPredicate->AddPredicate(mitk::NodePredicateNot::New(mitk::NodePredicateProperty::New("helper object")));
+
+ mitk::NodePredicateAnd::Pointer maskPredicate = mitk::NodePredicateAnd::New();
+ maskPredicate->AddPredicate(mitk::NodePredicateProperty::New("binary", mitk::BoolProperty::New(true)));
+ maskPredicate->AddPredicate(mitk::NodePredicateNot::New(mitk::NodePredicateProperty::New("helper object", mitk::BoolProperty::New(true))));
+
+ mitk::NodePredicateDataType::Pointer isDwi = mitk::NodePredicateDataType::New("DiffusionImage");
+ mitk::NodePredicateDataType::Pointer isDti = mitk::NodePredicateDataType::New("TensorImage");
+ mitk::NodePredicateDataType::Pointer isQbi = mitk::NodePredicateDataType::New("QBallImage");
+ mitk::TNodePredicateDataType::Pointer isImage = mitk::TNodePredicateDataType::New();
+
+ mitk::NodePredicateOr::Pointer validImages = mitk::NodePredicateOr::New();
+ validImages->AddPredicate(isImage);
+ validImages->AddPredicate(isDwi);
+ validImages->AddPredicate(isDti);
+ validImages->AddPredicate(isQbi);
+
+ mitk::NodePredicateAnd::Pointer imagePredicate = mitk::NodePredicateAnd::New();
+ imagePredicate->AddPredicate(validImages);
+ imagePredicate->AddPredicate(mitk::NodePredicateNot::New(segmentationPredicate));
+ imagePredicate->AddPredicate(mitk::NodePredicateNot::New(mitk::NodePredicateProperty::New("binary", mitk::BoolProperty::New(true))));
+ imagePredicate->AddPredicate(mitk::NodePredicateNot::New(mitk::NodePredicateProperty::New("helper object", mitk::BoolProperty::New(true))));
+
+ mitk::NodePredicateAnd::Pointer surfacePredicate = mitk::NodePredicateAnd::New();
+ surfacePredicate->AddPredicate(mitk::TNodePredicateDataType::New());
+ surfacePredicate->AddPredicate(mitk::NodePredicateNot::New(mitk::NodePredicateProperty::New("helper object", mitk::BoolProperty::New(true))));
+
+ switch(predicateType)
+ {
+ case QmitkDataSelectionWidget::ImagePredicate:
+ return imagePredicate.GetPointer();
+
+ case QmitkDataSelectionWidget::MaskPredicate:
+ return maskPredicate.GetPointer();
+
+ case QmitkDataSelectionWidget::SegmentationPredicate:
+ return segmentationPredicate.GetPointer();
+
+ case QmitkDataSelectionWidget::SurfacePredicate:
+ return surfacePredicate.GetPointer();
+
+ default:
+ assert(false && "Unknown predefined predicate!");
+ return NULL;
+ }
+}
+
+QmitkDataSelectionWidget::QmitkDataSelectionWidget(QWidget* parent)
+ : QWidget(parent)
+{
+ m_Controls.setupUi(this);
+ m_Controls.helpLabel->hide();
+}
+
+QmitkDataSelectionWidget::~QmitkDataSelectionWidget()
+{
+}
+
+unsigned int QmitkDataSelectionWidget::AddDataStorageComboBox(QmitkDataSelectionWidget::PredicateType predicate)
+{
+ return this->AddDataStorageComboBox("", predicate);
+}
+
+unsigned int QmitkDataSelectionWidget::AddDataStorageComboBox(mitk::NodePredicateBase* predicate)
+{
+ return this->AddDataStorageComboBox("", predicate);
+}
+
+unsigned int QmitkDataSelectionWidget::AddDataStorageComboBox(const QString &labelText, QmitkDataSelectionWidget::PredicateType predicate)
+{
+ return this->AddDataStorageComboBox(labelText, CreatePredicate(predicate));
+}
+
+unsigned int QmitkDataSelectionWidget::AddDataStorageComboBox(const QString &labelText, mitk::NodePredicateBase* predicate)
+{
+ int row = m_Controls.gridLayout->rowCount();
+
+ if (!labelText.isEmpty())
+ {
+ QLabel* label = new QLabel(labelText, m_Controls.dataSelectionWidget);
+ label->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Preferred);
+ m_Controls.gridLayout->addWidget(label, row, 0);
+ }
+
+ QmitkDataStorageComboBox* comboBox = new QmitkDataStorageComboBox(this->GetDataStorage(), predicate, m_Controls.dataSelectionWidget);
+ connect(comboBox, SIGNAL(OnSelectionChanged(const mitk::DataNode *)), this, SLOT(OnSelectionChanged(const mitk::DataNode *)));
+ comboBox->SetAutoSelectNewItems(true);
+ m_Controls.gridLayout->addWidget(comboBox, row, 1);
+
+ m_DataStorageComboBoxes.push_back(comboBox);
+ return static_cast(m_DataStorageComboBoxes.size() - 1);
+}
+
+mitk::DataStorage::Pointer QmitkDataSelectionWidget::GetDataStorage() const
+{
+ mitk::IDataStorageService::Pointer service =
+ berry::Platform::GetServiceRegistry().GetServiceById(mitk::IDataStorageService::ID);
+
+ assert(service.IsNotNull());
+
+ return service->GetDefaultDataStorage()->GetDataStorage();
+}
+
+mitk::DataNode::Pointer QmitkDataSelectionWidget::GetSelection(unsigned int index)
+{
+ assert(index < m_DataStorageComboBoxes.size());
+ return m_DataStorageComboBoxes[index]->GetSelectedNode();
+}
+
+void QmitkDataSelectionWidget::SetPredicate(unsigned int index, PredicateType predicate)
+{
+ this->SetPredicate(index, CreatePredicate(predicate));
+}
+
+void QmitkDataSelectionWidget::SetPredicate(unsigned int index, mitk::NodePredicateBase* predicate)
+{
+ assert(index < m_DataStorageComboBoxes.size());
+ m_DataStorageComboBoxes[index]->SetPredicate(predicate);
+}
+
+void QmitkDataSelectionWidget::SetHelpText(const QString& text)
+{
+ if (!text.isEmpty())
+ {
+ m_Controls.helpLabel->setText(text);
+
+ if (!m_Controls.helpLabel->isVisible())
+ m_Controls.helpLabel->show();
+ }
+ else
+ {
+ m_Controls.helpLabel->hide();
+ }
+}
+
+void QmitkDataSelectionWidget::OnSelectionChanged(const mitk::DataNode* selection)
+{
+ std::vector::iterator it = std::find(m_DataStorageComboBoxes.begin(), m_DataStorageComboBoxes.end(), sender());
+ assert(it != m_DataStorageComboBoxes.end());
+
+ emit SelectionChanged(std::distance(m_DataStorageComboBoxes.begin(), it), selection);
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/Common/QmitkDataSelectionWidget.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/Common/QmitkDataSelectionWidget.h
new file mode 100644
index 0000000000..3ccd830c98
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/Common/QmitkDataSelectionWidget.h
@@ -0,0 +1,70 @@
+/*===================================================================
+
+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 QmitkDataSelectionWidget_h
+#define QmitkDataSelectionWidget_h
+
+#include
+#include
+#include
+#include
+
+namespace mitk
+{
+ class NodePredicateBase;
+}
+
+class QmitkDataStorageComboBox;
+
+class QmitkDataSelectionWidget : public QWidget
+{
+ Q_OBJECT
+
+public:
+ enum PredicateType
+ {
+ ImagePredicate,
+ MaskPredicate,
+ SegmentationPredicate,
+ SurfacePredicate
+ };
+
+ explicit QmitkDataSelectionWidget(QWidget* parent = NULL);
+ ~QmitkDataSelectionWidget();
+
+ unsigned int AddDataStorageComboBox(PredicateType predicate);
+ unsigned int AddDataStorageComboBox(mitk::NodePredicateBase* predicate = NULL);
+ unsigned int AddDataStorageComboBox(const QString &labelText, PredicateType predicate);
+ unsigned int AddDataStorageComboBox(const QString &labelText, mitk::NodePredicateBase* predicate = NULL);
+
+ mitk::DataStorage::Pointer GetDataStorage() const;
+ mitk::DataNode::Pointer GetSelection(unsigned int index);
+ void SetPredicate(unsigned int index, PredicateType predicate);
+ void SetPredicate(unsigned int index, mitk::NodePredicateBase* predicate);
+ void SetHelpText(const QString& text);
+
+signals:
+ void SelectionChanged(unsigned int index, const mitk::DataNode* selection);
+
+private slots:
+ void OnSelectionChanged(const mitk::DataNode* selection);
+
+private:
+ Ui::QmitkDataSelectionWidgetControls m_Controls;
+ std::vector m_DataStorageComboBoxes;
+};
+
+#endif
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/Common/QmitkDataSelectionWidgetControls.ui b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/Common/QmitkDataSelectionWidgetControls.ui
new file mode 100644
index 0000000000..1849a496d9
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/Common/QmitkDataSelectionWidgetControls.ui
@@ -0,0 +1,64 @@
+
+
+ QmitkDataSelectionWidgetControls
+
+
+
+ 0
+ 0
+ 333
+ 191
+
+
+
+
+
+
+
+ 0
+
+ -
+
+
+
+
+
+ Data Selection
+
+
+ -
+
+
+
+ 0
+
+
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+ color: red
+
+
+
+
+
+ true
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkAutocropAction.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkAutocropAction.cpp
new file mode 100644
index 0000000000..c15ae4f6e0
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkAutocropAction.cpp
@@ -0,0 +1,197 @@
+/*===================================================================
+
+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 "QmitkAutocropAction.h"
+
+#include "mitkAutoCropImageFilter.h"
+#include "mitkImageCast.h"
+#include "mitkRenderingManager.h"
+#include "mitkProgressBar.h"
+
+#include
+
+//needed for qApp
+#include
+
+QmitkAutocropAction::QmitkAutocropAction()
+{
+}
+
+QmitkAutocropAction::~QmitkAutocropAction()
+{
+}
+
+void QmitkAutocropAction::Run( const QList &selectedNodes )
+{
+ foreach ( mitk::DataNode::Pointer node, selectedNodes )
+ {
+ if (node)
+ {
+ mitk::Image::Pointer image = dynamic_cast( node->GetData() );
+ if (image.IsNull()) return;
+
+ mitk::ProgressBar::GetInstance()->AddStepsToDo(10);
+ mitk::ProgressBar::GetInstance()->Progress(2);
+
+ qApp->processEvents();
+
+ mitk::AutoCropImageFilter::Pointer cropFilter = mitk::AutoCropImageFilter::New();
+ cropFilter->SetInput( image );
+ cropFilter->SetBackgroundValue( 0 );
+ cropFilter->SetMarginFactor(1.5);
+ try
+ {
+ cropFilter->Update();
+
+ image = cropFilter->GetOutput();
+
+ if (image.IsNotNull())
+ {
+
+ if (image->GetDimension() == 4)
+ {
+ MITK_INFO << "4D AUTOCROP DOES NOT WORK AT THE MOMENT";
+ throw "4D AUTOCROP DOES NOT WORK AT THE MOMENT";
+
+ unsigned int timesteps = image->GetDimension(3);
+ for (unsigned int i = 0; i < timesteps; i++)
+ {
+ mitk::ImageTimeSelector::Pointer imageTimeSelector = mitk::ImageTimeSelector::New();
+ imageTimeSelector->SetInput(image);
+ imageTimeSelector->SetTimeNr(i);
+ imageTimeSelector->UpdateLargestPossibleRegion();
+
+ // We split a long nested code line into separate calls for debugging:
+ mitk::ImageSource::OutputImageType *_3dSlice = imageTimeSelector->GetOutput();
+ mitk::Image::Pointer _cropped3dSlice = this->IncreaseCroppedImageSize(_3dSlice);
+
+ // +++ BUG +++ BUG +++ BUG +++ BUG +++ BUG +++ BUG +++ BUG +++
+ void *_data = _cropped3dSlice->GetData();
+
+ //
+ // We write some stripes into the image
+ if ((i & 1) == 0)
+ {
+ int depth = _cropped3dSlice->GetDimension(2);
+ int height = _cropped3dSlice->GetDimension(1);
+ int width = _cropped3dSlice->GetDimension(0);
+
+ for (int z = 0; z < depth; ++z)
+ for (int y = 0; y < height; ++y)
+ for (int x = 0; x < width; ++x)
+ reinterpret_cast(_data)[(width * height * z) + (width * y) + x] = x & 1;
+ //
+ }
+
+ image->SetVolume(_data, i);
+ }
+ node->SetData( image ); // bug fix 3145
+ }
+ else
+ {
+ node->SetData( this->IncreaseCroppedImageSize(image) ); // bug fix 3145
+ }
+ // Reinit node
+ mitk::RenderingManager::GetInstance()->InitializeViews(
+ node->GetData()->GetTimeSlicedGeometry(), mitk::RenderingManager::REQUEST_UPDATE_ALL, true );
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+
+ }
+ }
+ catch(...)
+ {
+ MITK_ERROR << "Cropping image failed...";
+ }
+ mitk::ProgressBar::GetInstance()->Progress(8);
+ }
+ else
+ {
+ MITK_INFO << " a NULL node selected";
+ }
+ }
+}
+
+mitk::Image::Pointer QmitkAutocropAction::IncreaseCroppedImageSize( mitk::Image::Pointer image )
+{
+ typedef itk::Image< short, 3 > ImageType;
+ typedef itk::Image< unsigned char, 3 > PADOutputImageType;
+
+ ImageType::Pointer itkTransformImage = ImageType::New();
+ mitk::CastToItkImage( image, itkTransformImage );
+
+ typedef itk::ConstantPadImageFilter< ImageType, PADOutputImageType > PadFilterType;
+ PadFilterType::Pointer padFilter = PadFilterType::New();
+
+ unsigned long upperPad[3];
+ unsigned long lowerPad[3];
+ int borderLiner = 3;
+
+ mitk::Point3D mitkOriginPoint;
+ double origin[3];
+ origin[0]=0;
+ origin[1]=0;
+ origin[2]=0;
+ itkTransformImage->SetOrigin(origin);
+
+ lowerPad[0]=borderLiner;
+ lowerPad[1]=borderLiner;
+ lowerPad[2]=borderLiner;
+
+ upperPad[0]=borderLiner;
+ upperPad[1]=borderLiner;
+ upperPad[2]=borderLiner;
+
+ padFilter->SetInput(itkTransformImage);
+ padFilter->SetConstant(0);
+ padFilter->SetPadUpperBound(upperPad);
+ padFilter->SetPadLowerBound(lowerPad);
+ padFilter->UpdateLargestPossibleRegion();
+
+
+ mitk::Image::Pointer paddedImage = mitk::Image::New();
+ paddedImage->InitializeByItk(padFilter->GetOutput());
+ mitk::CastToMitkImage(padFilter->GetOutput(), paddedImage);
+
+ //calculate translation according to padding to get the new origin
+ mitk::Point3D paddedOrigin = image->GetGeometry()->GetOrigin();
+ mitk::Vector3D spacing = image->GetGeometry()->GetSpacing();
+ paddedOrigin[0] -= (borderLiner)*spacing[0];
+ paddedOrigin[1] -= (borderLiner)*spacing[1];
+ paddedOrigin[2] -= (borderLiner)*spacing[2];
+
+ paddedImage->GetGeometry()->SetOrigin( paddedOrigin );
+
+ return paddedImage;
+}
+
+void QmitkAutocropAction::SetSmoothed(bool /*smoothed*/)
+{
+ //not needed
+}
+
+void QmitkAutocropAction::SetDecimated(bool /*decimated*/)
+{
+ //not needed
+}
+
+void QmitkAutocropAction::SetDataStorage(mitk::DataStorage* /*dataStorage*/)
+{
+ //not needed
+}
+
+void QmitkAutocropAction::SetFunctionality(berry::QtViewPart* /*functionality*/)
+{
+ //not needed
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkAutocropAction.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkAutocropAction.h
new file mode 100644
index 0000000000..acb9ae57d9
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkAutocropAction.h
@@ -0,0 +1,56 @@
+/*===================================================================
+
+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 QMITK_AUTOCROPACTION_H
+#define QMITK_AUTOCROPACTION_H
+
+#include "mitkIContextMenuAction.h"
+
+#include "org_mitk_gui_qt_multilabelsegmentation_Export.h"
+
+#include "vector"
+#include "mitkDataNode.h"
+#include "mitkImage.h"
+
+class QmitkStdMultiWidget;
+
+class MITK_QT_SEGMENTATION QmitkAutocropAction : public QObject, public mitk::IContextMenuAction
+{
+ Q_OBJECT
+ Q_INTERFACES(mitk::IContextMenuAction)
+
+public:
+
+ QmitkAutocropAction();
+ virtual ~QmitkAutocropAction();
+
+ //interface methods
+ void Run( const QList& selectedNodes );
+ void SetDataStorage(mitk::DataStorage* dataStorage);
+ void SetSmoothed(bool smoothed);
+ void SetDecimated(bool decimated);
+ void SetFunctionality(berry::QtViewPart* functionality);
+
+protected:
+
+ mitk::Image::Pointer IncreaseCroppedImageSize( mitk::Image::Pointer image );
+
+private:
+
+ typedef QList NodeList;
+
+};
+
+#endif // QMITK_AUTOCROPACTION_H
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertMaskToLabelAction.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertMaskToLabelAction.cpp
new file mode 100644
index 0000000000..4d4dfd16b5
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertMaskToLabelAction.cpp
@@ -0,0 +1,102 @@
+/*===================================================================
+
+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 "QmitkConvertMaskToLabelAction.h"
+
+#include "mitkRenderingManager.h"
+#include "mitkLabelSetImage.h"
+#include "mitkToolManagerProvider.h"
+
+//needed for qApp
+#include
+
+QmitkConvertMaskToLabelAction::QmitkConvertMaskToLabelAction()
+{
+}
+
+QmitkConvertMaskToLabelAction::~QmitkConvertMaskToLabelAction()
+{
+}
+
+void QmitkConvertMaskToLabelAction::Run( const QList &selectedNodes )
+{
+ mitk::ToolManager::Pointer toolManager = mitk::ToolManagerProvider::GetInstance()->GetToolManager();
+ assert(toolManager);
+
+ mitk::DataNode* workingNode = toolManager->GetWorkingData(0);
+ if (!workingNode)
+ {
+ MITK_INFO << "There is no available segmentation. Please load or create one before using this tool.";
+ return;
+ }
+
+ mitk::LabelSetImage* workingImage = dynamic_cast( workingNode->GetData() );
+ assert(workingImage);
+
+ foreach ( mitk::DataNode::Pointer maskNode, selectedNodes )
+ {
+ if (maskNode)
+ {
+ mitk::Image* mask = dynamic_cast(maskNode->GetData() );
+ if (!mask) continue;
+
+ std::string name = maskNode->GetName();
+ mitk::Color color;
+ mitk::ColorProperty::Pointer colorProp;
+ maskNode->GetProperty(colorProp,"color");
+ if (colorProp.IsNull()) continue;
+ color = colorProp->GetValue();
+ workingImage->GetLabelSet()->AddLabel(name,color);
+ //workingImage->AddLabelEvent.Send();
+
+ try
+ {
+ workingImage->MaskStamp( mask, false );
+ }
+ catch ( mitk::Exception& e )
+ {
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ return;
+ }
+
+ maskNode->SetVisibility(false);
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+ }
+ else
+ {
+ MITK_INFO << " a NULL node was selected";
+ }
+ }
+}
+
+void QmitkConvertMaskToLabelAction::SetSmoothed(bool /*smoothed*/)
+{
+ //not needed
+}
+
+void QmitkConvertMaskToLabelAction::SetDecimated(bool /*decimated*/)
+{
+ //not needed
+}
+
+void QmitkConvertMaskToLabelAction::SetDataStorage(mitk::DataStorage* /*dataStorage*/)
+{
+ //not needed
+}
+
+void QmitkConvertMaskToLabelAction::SetFunctionality(berry::QtViewPart* /*functionality*/)
+{
+ //not needed
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertMaskToLabelAction.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertMaskToLabelAction.h
new file mode 100644
index 0000000000..cc89d03990
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertMaskToLabelAction.h
@@ -0,0 +1,54 @@
+/*===================================================================
+
+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 __QmitkConvertMaskToLabelAction_H_
+#define __QmitkConvertMaskToLabelAction_H_
+
+#include "mitkIContextMenuAction.h"
+
+#include "org_mitk_gui_qt_multilabelsegmentation_Export.h"
+
+#include "vector"
+#include "mitkDataNode.h"
+#include "mitkImage.h"
+
+class QmitkStdMultiWidget;
+
+class MITK_QT_SEGMENTATION QmitkConvertMaskToLabelAction : public QObject, public mitk::IContextMenuAction
+{
+ Q_OBJECT
+ Q_INTERFACES(mitk::IContextMenuAction)
+
+public:
+
+ QmitkConvertMaskToLabelAction();
+ virtual ~QmitkConvertMaskToLabelAction();
+
+ //interface methods
+ void Run( const QList& selectedNodes );
+ void SetDataStorage(mitk::DataStorage* dataStorage);
+ void SetSmoothed(bool smoothed);
+ void SetDecimated(bool decimated);
+ void SetFunctionality(berry::QtViewPart* functionality);
+
+protected:
+
+private:
+
+ typedef QList NodeList;
+
+};
+
+#endif // __QmitkConvertMaskToLabelAction_H_
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertSurfaceToLabelAction.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertSurfaceToLabelAction.cpp
new file mode 100644
index 0000000000..386189a80f
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertSurfaceToLabelAction.cpp
@@ -0,0 +1,106 @@
+/*===================================================================
+
+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 "QmitkConvertSurfaceToLabelAction.h"
+
+#include "mitkRenderingManager.h"
+#include "mitkLabelSetImage.h"
+#include "mitkToolManagerProvider.h"
+
+//needed for qApp
+#include
+#include
+
+QmitkConvertSurfaceToLabelAction::QmitkConvertSurfaceToLabelAction()
+{
+}
+
+QmitkConvertSurfaceToLabelAction::~QmitkConvertSurfaceToLabelAction()
+{
+}
+
+void QmitkConvertSurfaceToLabelAction::Run( const QList &selectedNodes )
+{
+ mitk::ToolManager::Pointer toolManager = mitk::ToolManagerProvider::GetInstance()->GetToolManager();
+ assert(toolManager);
+
+ mitk::DataNode* workingNode = toolManager->GetWorkingData(0);
+ if (!workingNode)
+ {
+ MITK_INFO << "There is no available segmentation. Please load or create one before using this tool.";
+ return;
+ }
+
+ mitk::LabelSetImage* workingImage = dynamic_cast( workingNode->GetData() );
+ assert(workingImage);
+
+ foreach ( mitk::DataNode::Pointer surfaceNode, selectedNodes )
+ {
+ if (surfaceNode)
+ {
+ mitk::Surface* surface = dynamic_cast(surfaceNode->GetData() );
+ if (!surface) continue;
+
+ std::string name = surfaceNode->GetName();
+ mitk::Color color;
+ mitk::ColorProperty::Pointer colorProp;
+ surfaceNode->GetProperty(colorProp,"color");
+ if (colorProp.IsNull()) continue;
+ color = colorProp->GetValue();
+ workingImage->GetLabelSet()->AddLabel(name,color);
+ //workingImage->AddLabelEvent.Send();
+
+ try
+ {
+ QApplication::setOverrideCursor( QCursor(Qt::WaitCursor) );
+ workingImage->SurfaceStamp( surface, false );
+ QApplication::restoreOverrideCursor();
+ }
+ catch ( mitk::Exception& e )
+ {
+ QApplication::restoreOverrideCursor();
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ return;
+ }
+
+ surfaceNode->SetVisibility(false);
+ mitk::RenderingManager::GetInstance()->RequestUpdateAll();
+ }
+ else
+ {
+ MITK_INFO << " a NULL node was selected";
+ }
+ }
+}
+
+void QmitkConvertSurfaceToLabelAction::SetSmoothed(bool /*smoothed*/)
+{
+ //not needed
+}
+
+void QmitkConvertSurfaceToLabelAction::SetDecimated(bool /*decimated*/)
+{
+ //not needed
+}
+
+void QmitkConvertSurfaceToLabelAction::SetDataStorage(mitk::DataStorage* /*dataStorage*/)
+{
+ //not needed
+}
+
+void QmitkConvertSurfaceToLabelAction::SetFunctionality(berry::QtViewPart* /*functionality*/)
+{
+ //not needed
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertSurfaceToLabelAction.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertSurfaceToLabelAction.h
new file mode 100644
index 0000000000..5cbde8ed99
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertSurfaceToLabelAction.h
@@ -0,0 +1,54 @@
+/*===================================================================
+
+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 __QmitkConvertSurfaceToLabelAction_H_
+#define __QmitkConvertSurfaceToLabelAction_H_
+
+#include "mitkIContextMenuAction.h"
+
+#include "org_mitk_gui_qt_multilabelsegmentation_Export.h"
+
+#include "vector"
+#include "mitkDataNode.h"
+#include "mitkImage.h"
+
+class QmitkStdMultiWidget;
+
+class MITK_QT_SEGMENTATION QmitkConvertSurfaceToLabelAction : public QObject, public mitk::IContextMenuAction
+{
+ Q_OBJECT
+ Q_INTERFACES(mitk::IContextMenuAction)
+
+public:
+
+ QmitkConvertSurfaceToLabelAction();
+ virtual ~QmitkConvertSurfaceToLabelAction();
+
+ //interface methods
+ void Run( const QList& selectedNodes );
+ void SetDataStorage(mitk::DataStorage* dataStorage);
+ void SetSmoothed(bool smoothed);
+ void SetDecimated(bool decimated);
+ void SetFunctionality(berry::QtViewPart* functionality);
+
+protected:
+
+private:
+
+ typedef QList NodeList;
+
+};
+
+#endif // __QmitkConvertSurfaceToLabelAction_H_
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertToMultiLabelSegmentationAction.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertToMultiLabelSegmentationAction.cpp
new file mode 100644
index 0000000000..d256668004
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertToMultiLabelSegmentationAction.cpp
@@ -0,0 +1,83 @@
+/*===================================================================
+
+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 "QmitkConvertToMultiLabelSegmentationAction.h"
+
+#include "mitkLabelSetImage.h"
+#include "mitkRenderingManager.h"
+
+//needed for qApp
+#include
+
+QmitkConvertToMultiLabelSegmentationAction::QmitkConvertToMultiLabelSegmentationAction()
+{
+}
+
+QmitkConvertToMultiLabelSegmentationAction::~QmitkConvertToMultiLabelSegmentationAction()
+{
+}
+
+void QmitkConvertToMultiLabelSegmentationAction::Run( const QList &selectedNodes )
+{
+ foreach ( mitk::DataNode::Pointer referenceNode, selectedNodes )
+ {
+ if (referenceNode.IsNotNull())
+ {
+ mitk::Image::Pointer referenceImage = dynamic_cast( referenceNode->GetData() );
+ if (referenceImage.IsNull()) return;
+
+ mitk::LabelSetImage::Pointer lsImage = mitk::LabelSetImage::New();
+ try
+ {
+ lsImage->InitializeByLabeledImage(referenceImage);
+ }
+ catch (mitk::Exception &e)
+ {
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ return;
+ }
+ if (m_DataStorage.IsNotNull())
+ {
+ mitk::DataNode::Pointer newNode = mitk::DataNode::New();
+ std::string newName = referenceNode->GetName();
+ newName += "-labels";
+ newNode->SetName(newName);
+ newNode->SetData(lsImage);
+ m_DataStorage->Add(newNode,referenceNode);
+ }
+ lsImage->Modified();
+ }
+ }
+}
+
+void QmitkConvertToMultiLabelSegmentationAction::SetDataStorage(mitk::DataStorage* dataStorage)
+{
+ m_DataStorage = dataStorage;
+}
+
+void QmitkConvertToMultiLabelSegmentationAction::SetFunctionality(berry::QtViewPart* /*functionality*/)
+{
+ //not needed
+}
+
+void QmitkConvertToMultiLabelSegmentationAction::SetSmoothed(bool smoothed)
+{
+ //not needed
+}
+
+void QmitkConvertToMultiLabelSegmentationAction::SetDecimated(bool decimated)
+{
+ //not needed
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertToMultiLabelSegmentationAction.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertToMultiLabelSegmentationAction.h
new file mode 100644
index 0000000000..72fc44ca80
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkConvertToMultiLabelSegmentationAction.h
@@ -0,0 +1,51 @@
+/*===================================================================
+
+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 QMITK_ConvertToMultiLabelSegmentation_H
+#define QMITK_ConvertToMultiLabelSegmentation_H
+
+#include "mitkIContextMenuAction.h"
+
+#include "org_mitk_gui_qt_multilabelsegmentation_Export.h"
+
+#include "vector"
+#include "mitkDataNode.h"
+//#include "mitkImage.h"
+
+class MITK_QT_SEGMENTATION QmitkConvertToMultiLabelSegmentationAction : public QObject, public mitk::IContextMenuAction
+{
+ Q_OBJECT
+ Q_INTERFACES(mitk::IContextMenuAction)
+
+public:
+
+ QmitkConvertToMultiLabelSegmentationAction();
+ virtual ~QmitkConvertToMultiLabelSegmentationAction();
+
+ //interface methods
+ virtual void Run( const QList& selectedNodes );
+ virtual void SetDataStorage(mitk::DataStorage* dataStorage);
+ virtual void SetFunctionality(berry::QtViewPart* functionality);
+ virtual void SetSmoothed(bool smoothed);
+ virtual void SetDecimated(bool decimated);
+
+private:
+
+ typedef QList NodeList;
+
+ mitk::DataStorage::Pointer m_DataStorage;
+};
+
+#endif // QMITK_ConvertToMultiLabelSegmentation_H
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelPresetAction.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelPresetAction.cpp
new file mode 100644
index 0000000000..bf09d77e7c
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelPresetAction.cpp
@@ -0,0 +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.
+
+===================================================================*/
+#include "QmitkCreateMultiLabelPresetAction.h"
+#include "mitkLabelSetImage.h"
+#include "QMessageBox"
+#include
+#include "QFileDialog"
+#include "mitkLabelSetImageWriter.h"
+#include "tinyxml.h"
+
+QmitkCreateMultiLabelPresetAction::QmitkCreateMultiLabelPresetAction()
+{
+}
+
+QmitkCreateMultiLabelPresetAction::~QmitkCreateMultiLabelPresetAction()
+{
+}
+
+void QmitkCreateMultiLabelPresetAction::Run( const QList &selectedNodes )
+{
+ foreach ( mitk::DataNode::Pointer referenceNode, selectedNodes )
+ {
+ if (referenceNode.IsNotNull())
+ {
+
+ mitk::LabelSetImage::Pointer referenceImage = dynamic_cast( referenceNode->GetData() );
+ assert(referenceImage);
+
+ if(referenceImage->GetNumberOfLabels() <= 1)
+ {
+ QMessageBox::information(NULL, "Create LabelSetImage Preset", "Could not create a LabelSetImage preset.\nNo Labels defined!\n");\
+ return;
+ }
+
+ std::string sName = referenceNode->GetName();
+ QString qName;
+ qName.sprintf("%s.lsetp",sName.c_str());
+ QString filename = QFileDialog::getSaveFileName( NULL,"save file dialog",QString(),"LabelSet Preset(*.lsetp)");
+ if ( filename.isEmpty() )
+ return;
+
+ bool wasSaved = mitk::LabelSetImageWriter::SaveLabelSetImagePreset(filename.toStdString(),referenceImage);
+
+ if(!wasSaved)
+ {
+ QMessageBox::information(NULL, "Create LabelSetImage Preset", "Could not save a LabelSetImage preset as Xml.\n");\
+ return;
+ }
+ }
+ }
+}
+
+void QmitkCreateMultiLabelPresetAction::SetDataStorage(mitk::DataStorage* dataStorage)
+{
+ m_DataStorage = dataStorage;
+}
+
+void QmitkCreateMultiLabelPresetAction::SetFunctionality(berry::QtViewPart* /*functionality*/)
+{
+ //not needed
+}
+
+void QmitkCreateMultiLabelPresetAction::SetSmoothed(bool smoothed)
+{
+ //not needed
+}
+
+void QmitkCreateMultiLabelPresetAction::SetDecimated(bool decimated)
+{
+ //not needed
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelPresetAction.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelPresetAction.h
new file mode 100644
index 0000000000..a9d9849c51
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelPresetAction.h
@@ -0,0 +1,50 @@
+/*===================================================================
+
+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 QMITK_QmitkCreateMultiLabelPresetAction_H
+#define QMITK_QmitkCreateMultiLabelPresetAction_H
+
+#include "mitkIContextMenuAction.h"
+
+#include "org_mitk_gui_qt_multilabelsegmentation_Export.h"
+
+#include "vector"
+#include "mitkDataNode.h"
+
+class MITK_QT_SEGMENTATION QmitkCreateMultiLabelPresetAction : public QObject, public mitk::IContextMenuAction
+{
+ Q_OBJECT
+ Q_INTERFACES(mitk::IContextMenuAction)
+
+public:
+
+ QmitkCreateMultiLabelPresetAction();
+ virtual ~QmitkCreateMultiLabelPresetAction();
+
+ //interface methods
+ virtual void Run( const QList& selectedNodes );
+ virtual void SetDataStorage(mitk::DataStorage* dataStorage);
+ virtual void SetFunctionality(berry::QtViewPart* functionality);
+ virtual void SetSmoothed(bool smoothed);
+ virtual void SetDecimated(bool decimated);
+
+private:
+
+ typedef QList NodeList;
+
+ mitk::DataStorage::Pointer m_DataStorage;
+};
+
+#endif // QMITK_CreateMultiLabelSegmentation_H
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelSegmentationAction.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelSegmentationAction.cpp
new file mode 100644
index 0000000000..578c9699cb
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelSegmentationAction.cpp
@@ -0,0 +1,113 @@
+/*===================================================================
+
+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 "QmitkCreateMultiLabelSegmentationAction.h"
+
+#include "mitkLabelSetImage.h"
+#include "mitkRenderingManager.h"
+
+#include "QInputDialog"
+#include "QMessageBox"
+
+#include "QmitkNewSegmentationDialog.h"
+#include "QmitkMultiLabelSegmentationView.h"
+#include "QmitkMultiLabelSegmentationOrganNamesHandling.cpp"
+//needed for qApp
+#include
+
+QmitkCreateMultiLabelSegmentationAction::QmitkCreateMultiLabelSegmentationAction()
+{
+}
+
+QmitkCreateMultiLabelSegmentationAction::~QmitkCreateMultiLabelSegmentationAction()
+{
+}
+
+void QmitkCreateMultiLabelSegmentationAction::Run( const QList &selectedNodes )
+{
+ foreach ( mitk::DataNode::Pointer referenceNode, selectedNodes )
+ {
+ if (referenceNode.IsNotNull())
+ {
+
+ mitk::Image* referenceImage = dynamic_cast( referenceNode->GetData() );
+ assert(referenceImage);
+
+ QString newName = QString::fromStdString(referenceNode->GetName());
+ newName.append("-labels");
+
+ bool ok = false;
+ newName = QInputDialog::getText(NULL, "New Segmentation Session", "New name:", QLineEdit::Normal, newName, &ok);
+ if(!ok) return;
+
+ mitk::LabelSetImage::Pointer workingImage = mitk::LabelSetImage::New();
+
+ try
+ {
+ workingImage->Initialize(referenceImage);
+ }
+ catch ( mitk::Exception& e )
+ {
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ QMessageBox::information(NULL, "New Segmentation Session", "Could not create a new segmentation session.\n");
+ return;
+ }
+
+ mitk::DataNode::Pointer workingNode = mitk::DataNode::New();
+ workingNode->SetData(workingImage);
+ workingNode->SetName(newName.toStdString());
+
+ // set additional image information
+ workingImage->GetExteriorLabel()->SetProperty("name.parent",mitk::StringProperty::New(referenceNode->GetName().c_str()));
+ workingImage->GetExteriorLabel()->SetProperty("name.image",mitk::StringProperty::New(newName.toStdString().c_str()));
+
+ if (!m_DataStorage->Exists(workingNode))
+ m_DataStorage->Add(workingNode, referenceNode);
+
+ QmitkNewSegmentationDialog* dialog = new QmitkNewSegmentationDialog( );
+ dialog->SetSuggestionList( mitk::OrganNamesHandling::GetDefaultOrganColorString());
+ dialog->setWindowTitle("New Label");
+
+ int dialogReturnValue = dialog->exec();
+
+ if ( dialogReturnValue == QDialog::Rejected ) return;
+
+ QString segName = dialog->GetSegmentationName();
+ if(segName.isEmpty()) segName = "Unnamed";
+ workingImage->GetActiveLabelSet()->AddLabel(segName.toStdString(), dialog->GetColor());
+
+ }
+ }
+}
+
+void QmitkCreateMultiLabelSegmentationAction::SetDataStorage(mitk::DataStorage* dataStorage)
+{
+ m_DataStorage = dataStorage;
+}
+
+void QmitkCreateMultiLabelSegmentationAction::SetFunctionality(berry::QtViewPart* /*functionality*/)
+{
+ //not needed
+}
+
+void QmitkCreateMultiLabelSegmentationAction::SetSmoothed(bool smoothed)
+{
+ //not needed
+}
+
+void QmitkCreateMultiLabelSegmentationAction::SetDecimated(bool decimated)
+{
+ //not needed
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelSegmentationAction.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelSegmentationAction.h
new file mode 100644
index 0000000000..7cc8b4e1d6
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreateMultiLabelSegmentationAction.h
@@ -0,0 +1,50 @@
+/*===================================================================
+
+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 QMITK_CreateMultiLabelSegmentation_H
+#define QMITK_CreateMultiLabelSegmentation_H
+
+#include "mitkIContextMenuAction.h"
+
+#include "org_mitk_gui_qt_multilabelsegmentation_Export.h"
+
+#include "vector"
+#include "mitkDataNode.h"
+
+class MITK_QT_SEGMENTATION QmitkCreateMultiLabelSegmentationAction : public QObject, public mitk::IContextMenuAction
+{
+ Q_OBJECT
+ Q_INTERFACES(mitk::IContextMenuAction)
+
+public:
+
+ QmitkCreateMultiLabelSegmentationAction();
+ virtual ~QmitkCreateMultiLabelSegmentationAction();
+
+ //interface methods
+ virtual void Run( const QList& selectedNodes );
+ virtual void SetDataStorage(mitk::DataStorage* dataStorage);
+ virtual void SetFunctionality(berry::QtViewPart* functionality);
+ virtual void SetSmoothed(bool smoothed);
+ virtual void SetDecimated(bool decimated);
+
+private:
+
+ typedef QList NodeList;
+
+ mitk::DataStorage::Pointer m_DataStorage;
+};
+
+#endif // QMITK_CreateMultiLabelSegmentation_H
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreatePolygonModelAction.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreatePolygonModelAction.cpp
new file mode 100644
index 0000000000..3aa73a17b5
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreatePolygonModelAction.cpp
@@ -0,0 +1,171 @@
+/*===================================================================
+
+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 "QmitkCreatePolygonModelAction.h"
+
+// MITK
+#include
+#include
+#include
+#include
+#include
+
+#include
+#include
+
+// Blueberry
+#include
+#include
+#include
+
+using namespace berry;
+using namespace mitk;
+using namespace std;
+
+QmitkCreatePolygonModelAction::QmitkCreatePolygonModelAction()
+{
+}
+
+QmitkCreatePolygonModelAction::~QmitkCreatePolygonModelAction()
+{
+}
+
+void QmitkCreatePolygonModelAction::Run(const QList &selectedNodes)
+{
+ DataNode::Pointer selectedNode = selectedNodes[0];
+ Image::Pointer image = dynamic_cast(selectedNode->GetData());
+
+ if (image.IsNull())
+ return;
+
+ try
+ {
+ if (!m_IsSmoothed)
+ {
+ ShowSegmentationAsSurface::Pointer surfaceFilter = ShowSegmentationAsSurface::New();
+
+ itk::SimpleMemberCommand::Pointer successCommand = itk::SimpleMemberCommand::New();
+ successCommand->SetCallbackFunction(this, &QmitkCreatePolygonModelAction::OnSurfaceCalculationDone);
+ surfaceFilter->AddObserver(ResultAvailable(), successCommand);
+
+ itk::SimpleMemberCommand::Pointer errorCommand = itk::SimpleMemberCommand::New();
+ errorCommand->SetCallbackFunction(this, &QmitkCreatePolygonModelAction::OnSurfaceCalculationDone);
+ surfaceFilter->AddObserver(ProcessingError(), errorCommand);
+
+ surfaceFilter->SetDataStorage(*m_DataStorage);
+ surfaceFilter->SetPointerParameter("Input", image);
+ surfaceFilter->SetPointerParameter("Group node", selectedNode);
+ surfaceFilter->SetParameter("Show result", true);
+ surfaceFilter->SetParameter("Sync visibility", false);
+ surfaceFilter->SetParameter("Smooth", false);
+ surfaceFilter->SetParameter("Apply median", false);
+ surfaceFilter->SetParameter("Median kernel size", 3u);
+ surfaceFilter->SetParameter("Gaussian SD", 1.5f);
+ surfaceFilter->SetParameter("Decimate mesh", m_IsDecimated);
+ surfaceFilter->SetParameter("Decimation rate", 0.8f);
+
+ StatusBar::GetInstance()->DisplayText("Surface creation started in background...");
+
+ surfaceFilter->StartAlgorithm();
+ }
+ else
+ {
+ ShowSegmentationAsSmoothedSurface::Pointer surfaceFilter = ShowSegmentationAsSmoothedSurface::New();
+
+ itk::SimpleMemberCommand::Pointer successCommand = itk::SimpleMemberCommand::New();
+ successCommand->SetCallbackFunction(this, &QmitkCreatePolygonModelAction::OnSurfaceCalculationDone);
+ surfaceFilter->AddObserver(mitk::ResultAvailable(), successCommand);
+
+ itk::SimpleMemberCommand::Pointer errorCommand = itk::SimpleMemberCommand::New();
+ errorCommand->SetCallbackFunction(this, &QmitkCreatePolygonModelAction::OnSurfaceCalculationDone);
+ surfaceFilter->AddObserver(mitk::ProcessingError(), errorCommand);
+
+ surfaceFilter->SetDataStorage(*m_DataStorage);
+ surfaceFilter->SetPointerParameter("Input", image);
+ surfaceFilter->SetPointerParameter("Group node", selectedNode);
+
+ berry::IWorkbenchPart::Pointer activePart =
+ berry::PlatformUI::GetWorkbench()->GetActiveWorkbenchWindow()->GetActivePage()->GetActivePart();
+ mitk::IRenderWindowPart* renderPart = dynamic_cast(activePart.GetPointer());
+ mitk::SliceNavigationController* timeNavController = 0;
+ if (renderPart != 0)
+ {
+ timeNavController = renderPart->GetRenderingManager()->GetTimeNavigationController();
+ }
+
+ int timeNr = timeNavController != 0 ? timeNavController->GetTime()->GetPos() : 0;
+ surfaceFilter->SetParameter("TimeNr", timeNr);
+
+ IPreferencesService::Pointer prefService = Platform::GetServiceRegistry().GetServiceById(IPreferencesService::ID);
+ IPreferences::Pointer segPref = prefService->GetSystemPreferences()->Node("/org.mitk.views.segmentation");
+
+ bool smoothingHint = segPref->GetBool("smoothing hint", true);
+ ScalarType smoothing = segPref->GetDouble("smoothing value", 1.0);
+ ScalarType decimation = segPref->GetDouble("decimation rate", 0.5);
+ ScalarType closing = segPref->GetDouble("closing ratio", 0.0);
+
+ if (smoothingHint)
+ {
+ smoothing = 0.0;
+ Vector3D spacing = image->GetGeometry()->GetSpacing();
+
+ for (Vector3D::Iterator iter = spacing.Begin(); iter != spacing.End(); ++iter)
+ smoothing = max(smoothing, *iter);
+ }
+
+ surfaceFilter->SetParameter("Smoothing", smoothing);
+ surfaceFilter->SetParameter("Decimation", decimation);
+ surfaceFilter->SetParameter("Closing", closing);
+
+ ProgressBar::GetInstance()->AddStepsToDo(8);
+ StatusBar::GetInstance()->DisplayText("Smoothed surface creation started in background...");
+
+ try {
+ surfaceFilter->StartAlgorithm();
+ } catch (...)
+ {
+ MITK_ERROR<<"Error creating smoothed polygon model: Not enough memory!";
+ }
+ }
+ }
+ catch(...)
+ {
+ MITK_ERROR << "Surface creation failed!";
+ }
+}
+
+void QmitkCreatePolygonModelAction::OnSurfaceCalculationDone()
+{
+ StatusBar::GetInstance()->Clear();
+}
+
+void QmitkCreatePolygonModelAction::SetDataStorage(DataStorage *dataStorage)
+{
+ m_DataStorage = dataStorage;
+}
+
+void QmitkCreatePolygonModelAction::SetSmoothed(bool smoothed)
+{
+ m_IsSmoothed = smoothed;
+}
+
+void QmitkCreatePolygonModelAction::SetDecimated(bool decimated)
+{
+ m_IsDecimated = decimated;
+}
+
+void QmitkCreatePolygonModelAction::SetFunctionality(QtViewPart *)
+{
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreatePolygonModelAction.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreatePolygonModelAction.h
new file mode 100644
index 0000000000..b7adfaaed8
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkCreatePolygonModelAction.h
@@ -0,0 +1,57 @@
+/*===================================================================
+
+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 QMITKCREATEPOLYGONMODELACTION_H
+#define QMITKCREATEPOLYGONMODELACTION_H
+
+#include
+
+// Parent classes
+#include
+#include
+
+// Data members
+#include
+
+class QmitkStdMultiWidget;
+
+class MITK_QT_SEGMENTATION QmitkCreatePolygonModelAction : public QObject, public mitk::IContextMenuAction
+{
+ Q_OBJECT
+ Q_INTERFACES(mitk::IContextMenuAction)
+
+public:
+ QmitkCreatePolygonModelAction();
+ ~QmitkCreatePolygonModelAction();
+
+ // IContextMenuAction
+ void Run(const QList &selectedNodes);
+ void SetDataStorage(mitk::DataStorage *dataStorage);
+ void SetSmoothed(bool smoothed);
+ void SetDecimated(bool decimated);
+ void SetFunctionality(berry::QtViewPart *functionality);
+
+ void OnSurfaceCalculationDone();
+
+private:
+ QmitkCreatePolygonModelAction(const QmitkCreatePolygonModelAction &);
+ QmitkCreatePolygonModelAction & operator=(const QmitkCreatePolygonModelAction &);
+
+ mitk::DataStorage::Pointer m_DataStorage;
+ bool m_IsSmoothed;
+ bool m_IsDecimated;
+};
+
+#endif
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkLoadMultiLabelPresetAction.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkLoadMultiLabelPresetAction.cpp
new file mode 100644
index 0000000000..010f83431f
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkLoadMultiLabelPresetAction.cpp
@@ -0,0 +1,74 @@
+/*===================================================================
+
+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 "QmitkLoadMultiLabelPresetAction.h"
+
+#include "mitkLabelSetImage.h"
+#include "mitkRenderingManager.h"
+#include "mitkLabelSetImageIO.h"
+
+#include "QInputDialog"
+#include "QMessageBox"
+#include "QFileDialog"
+#include "tinyxml.h"
+
+QmitkLoadMultiLabelPresetAction::QmitkLoadMultiLabelPresetAction()
+{
+}
+
+QmitkLoadMultiLabelPresetAction::~QmitkLoadMultiLabelPresetAction()
+{
+}
+
+void QmitkLoadMultiLabelPresetAction::Run( const QList &selectedNodes )
+{
+ foreach ( mitk::DataNode::Pointer referenceNode, selectedNodes )
+ {
+
+ if (referenceNode.IsNull()) return;
+
+ mitk::LabelSetImage::Pointer referenceImage = dynamic_cast( referenceNode->GetData() );
+ assert(referenceImage);
+
+ std::string sName = referenceNode->GetName();
+ QString qName;
+ qName.sprintf("%s.lsetp",sName.c_str());
+ QString filename = QFileDialog::getOpenFileName(NULL,"Load file",QString(),"LabelSet Preset(*.lsetp)");
+ if ( filename.isEmpty() )
+ return;
+
+ mitk::LabelSetImageIO::LoadLabelSetImagePreset(filename.toStdString(), referenceImage);
+ }
+}
+
+void QmitkLoadMultiLabelPresetAction::SetDataStorage(mitk::DataStorage* dataStorage)
+{
+ m_DataStorage = dataStorage;
+}
+
+void QmitkLoadMultiLabelPresetAction::SetFunctionality(berry::QtViewPart* /*functionality*/)
+{
+ //not needed
+}
+
+void QmitkLoadMultiLabelPresetAction::SetSmoothed(bool smoothed)
+{
+ //not needed
+}
+
+void QmitkLoadMultiLabelPresetAction::SetDecimated(bool decimated)
+{
+ //not needed
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkLoadMultiLabelPresetAction.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkLoadMultiLabelPresetAction.h
new file mode 100644
index 0000000000..eb888d6a6d
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkLoadMultiLabelPresetAction.h
@@ -0,0 +1,50 @@
+/*===================================================================
+
+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 QMITK_QmitkLoadMultiLabelPresetAction_H
+#define QMITK_QmitkLoadMultiLabelPresetAction_H
+
+#include "mitkIContextMenuAction.h"
+
+#include "org_mitk_gui_qt_multilabelsegmentation_Export.h"
+
+#include "vector"
+#include "mitkDataNode.h"
+
+class MITK_QT_SEGMENTATION QmitkLoadMultiLabelPresetAction : public QObject, public mitk::IContextMenuAction
+{
+ Q_OBJECT
+ Q_INTERFACES(mitk::IContextMenuAction)
+
+public:
+
+ QmitkLoadMultiLabelPresetAction();
+ virtual ~QmitkLoadMultiLabelPresetAction();
+
+ //interface methods
+ virtual void Run( const QList& selectedNodes );
+ virtual void SetDataStorage(mitk::DataStorage* dataStorage);
+ virtual void SetFunctionality(berry::QtViewPart* functionality);
+ virtual void SetSmoothed(bool smoothed);
+ virtual void SetDecimated(bool decimated);
+
+private:
+
+ typedef QList NodeList;
+
+ mitk::DataStorage::Pointer m_DataStorage;
+};
+
+#endif // QMITK_CreateMultiLabelSegmentation_H
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationControls.ui b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationControls.ui
new file mode 100644
index 0000000000..138b48b36a
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationControls.ui
@@ -0,0 +1,810 @@
+
+
+ QmitkMultiLabelSegmentationControls
+
+
+
+ 0
+ 0
+ 191
+ 454
+
+
+
+
+ 0
+ 0
+
+
+
+
+ 0
+ 0
+
+
+
+
+ MS Shell Dlg 2
+ 8
+ 50
+ false
+ false
+ false
+ false
+
+
+
+ QmitkSegmentation
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+ Patient Image
+
+
+
+ 2
+
+
+ 4
+
+
+ 2
+
+
+ 4
+
+
+ 2
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+ Segmentation
+
+
+
+ 2
+
+
+ 4
+
+
+ 2
+
+
+ 4
+
+
+ 2
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+
+
+
+ -
+
+
+ 3
+
+
+ 4
+
+ -
+
+
+ Create a new segmentation session
+
+
+ ...
+
+
+
+ :/multilabelsegmentation/NewSegmentationSession_48x48.png :/multilabelsegmentation/NewSegmentationSession_48x48.png
+
+
+
+ 28
+ 28
+
+
+
+ N
+
+
+ true
+
+
+
+ -
+
+
+ Add a new label to the current segmentation session
+
+
+ ...
+
+
+
+ :/multilabelsegmentation/NewLabel_48x48.png :/multilabelsegmentation/NewLabel_48x48.png
+
+
+
+ 28
+ 28
+
+
+
+ N
+
+
+ true
+
+
+
+ -
+
+
+ Qt::Horizontal
+
+
+
+ 5
+ 20
+
+
+
+
+ -
+
+
+
+ 0
+ 34
+
+
+
+ Show a table with all labels in the current segmentation session
+
+
+ >>
+
+
+
+ 28
+ 28
+
+
+
+ true
+
+
+ false
+
+
+ Qt::NoArrow
+
+
+
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+ 0
+ 20
+
+
+
+
+ -
+
+
+ 2
+
+
+ QLayout::SetDefaultConstraint
+
+ -
+
+
+ Disable the active tool
+
+
+ ...
+
+
+
+ :/Qmitk/SegmentationInteractor_48x48.png :/Qmitk/SegmentationInteractor_48x48.png
+
+
+
+ 28
+ 28
+
+
+
+ false
+
+
+ true
+
+
+
+ -
+
+
+ Lock/Unlock exterior
+
+
+ ...
+
+
+
+ :/Qmitk/UnlockExterior_48x48.png
+ :/Qmitk/LockExterior_48x48.png :/Qmitk/UnlockExterior_48x48.png
+
+
+
+ 28
+ 28
+
+
+
+ true
+
+
+ true
+
+
+
+ -
+
+
+ Add a layer to the current segmentation session
+
+
+ ...
+
+
+
+ :/Qmitk/AddLayer_48x48.png :/Qmitk/AddLayer_48x48.png
+
+
+
+ 28
+ 28
+
+
+
+ true
+
+
+
+ -
+
+
+ Delete the active layer
+
+
+ ...
+
+
+
+ :/Qmitk/DeleteLayer_48x48.png :/Qmitk/DeleteLayer_48x48.png
+
+
+
+ 28
+ 28
+
+
+
+ true
+
+
+
+ -
+
+
+ Change to the previous available layer
+
+
+ ...
+
+
+
+ :/Qmitk/PreviousLayer_48x48.png :/Qmitk/PreviousLayer_48x48.png
+
+
+
+ 28
+ 28
+
+
+
+ true
+
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+ 50
+ 30
+
+
+
+
+ 40
+ 30
+
+
+
+
+ 12
+
+
+
+ Switch to a layer
+
+ -
+
+ 0
+
+
+
+
+ -
+
+
+ Change to the next available layer
+
+
+ ...
+
+
+
+ :/Qmitk/NextLayer_48x48.png :/Qmitk/NextLayer_48x48.png
+
+
+
+ 28
+ 28
+
+
+
+ true
+
+
+
+ -
+
+
+ Qt::Horizontal
+
+
+
+ 0
+ 20
+
+
+
+
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+ QTabWidget::tab-bar { alignment: middle; }
+
+
+ 0
+
+
+ true
+
+
+ false
+
+
+
+ 2D Tools
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+ 50
+ false
+
+
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+ 50
+ false
+
+
+
+
+ -
+
+
+ Qt::Vertical
+
+
+
+ 20
+ 40
+
+
+
+
+
+
+
+
+ 3D Tools
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+ 50
+ false
+
+
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+ 50
+ false
+
+
+
+
+ -
+
+
+ Qt::Vertical
+
+
+
+ 20
+ 40
+
+
+
+
+
+
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+ Interpolation
+
+
+
+ 2
+
+
+ QLayout::SetMinimumSize
+
+
+ 2
+
+
+ 2
+
+
+ 2
+
+
+ 2
+
+ -
+
+
+
+ 0
+ 0
+
+
+ -
+
+ Disabled
+
+
+ -
+
+ 2D Interpolation
+
+
+ -
+
+ 3D Interpolation
+
+
+
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+ 1
+
+
+
+
+ 0
+ 0
+
+
+
+
+ QLayout::SetMinimumSize
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+ 0
+ 0
+
+
+
+
+ 50
+ false
+
+
+
+
+
+
+
+
+
+ 0
+ 0
+
+
+
+
+ QLayout::SetMinimumSize
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+
+ 0
+
+ -
+
+
+
+ 0
+ 0
+
+
+
+
+ 0
+ 50
+
+
+
+
+ 50
+ false
+
+
+
+
+
+
+
+
+
+ 0
+ 0
+
+
+
+
+
+
+
+
+ -
+
+
+ Qt::Vertical
+
+
+
+ 20
+ 40
+
+
+
+
+
+ groupBox_4
+ m_LabelSetWidget
+ groupBox
+ m_tw2DTools
+ m_gbInterpolation
+ verticalSpacer
+
+
+
+
+ QmitkDataStorageComboBox
+ QComboBox
+ QmitkDataStorageComboBox.h
+
+
+ QmitkToolSelectionBox
+ QWidget
+
+
+
+ QmitkToolGUIArea
+ QWidget
+
+
+
+ QmitkLabelSetWidget
+ QWidget
+ Qmitk/QmitkLabelSetWidget.h
+ 1
+
+
+ QmitkSliceBasedInterpolatorWidget
+ QWidget
+ QmitkSliceBasedInterpolatorWidget.h
+ 1
+
+
+ QmitkSurfaceBasedInterpolatorWidget
+ QWidget
+ QmitkSurfaceBasedInterpolatorWidget.h
+ 1
+
+
+
+ QmitkToolReferenceDataSelectionBox.h
+ QmitkToolGUIArea.h
+ QmitkToolSelectionBox.h
+
+
+
+
+
+
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationOrganNamesHandling.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationOrganNamesHandling.cpp
new file mode 100644
index 0000000000..574320c919
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationOrganNamesHandling.cpp
@@ -0,0 +1,105 @@
+/*===================================================================
+
+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
+
+namespace mitk
+{
+struct OrganNamesHandling
+{
+ static QStringList GetDefaultOrganColorString()
+ {
+ QStringList organColors;
+
+ AppendToOrganList(organColors, "Ankle", 255, 255, 153);
+ AppendToOrganList(organColors, "Appendix", 161, 107, 54);
+ AppendToOrganList(organColors, "Blood vessels", 255, 49, 49);
+ AppendToOrganList(organColors, "Bone", 255, 255, 153);
+ AppendToOrganList(organColors, "Brain", 255, 156, 202);
+ AppendToOrganList(organColors, "Bronchial tree", 0, 160, 209);
+ AppendToOrganList(organColors, "Coccyx", 255, 255, 153);
+ AppendToOrganList(organColors, "Colon", 161, 107, 54);
+ AppendToOrganList(organColors, "Cyst", 150, 189, 228);
+ AppendToOrganList(organColors, "Elbow", 255, 255, 153);
+ AppendToOrganList(organColors, "Eye", 18, 7, 161);
+ AppendToOrganList(organColors, "Fallopian tube", 161, 19, 39);
+ AppendToOrganList(organColors, "Fat", 237, 255, 41);
+ AppendToOrganList(organColors, "Gall Bladder", 86, 127, 24);
+ AppendToOrganList(organColors, "Hand", 255, 222, 199);
+ AppendToOrganList(organColors, "Heart", 153, 0, 0);
+ AppendToOrganList(organColors, "Hip", 255, 255, 153);
+ AppendToOrganList(organColors, "Kidney", 250, 89, 0);
+ AppendToOrganList(organColors, "Knee", 255, 255, 153);
+ AppendToOrganList(organColors, "Larynx", 102, 0, 0);
+ AppendToOrganList(organColors, "Liver", 194, 142, 0);
+ AppendToOrganList(organColors, "Lung", 107, 220, 255);
+ AppendToOrganList(organColors, "Lymph node", 10, 250, 56);
+ AppendToOrganList(organColors, "Muscle", 102, 0, 0);
+ AppendToOrganList(organColors, "Nerve", 255, 234, 79);
+ AppendToOrganList(organColors, "Nose", 255, 222, 199);
+ AppendToOrganList(organColors, "Oesophagus", 102, 0, 0);
+ AppendToOrganList(organColors, "Ovaries", 234, 0, 117);
+ AppendToOrganList(organColors, "Pancreas", 249, 171, 61);
+ AppendToOrganList(organColors, "Pelvis", 255, 255, 153);
+ AppendToOrganList(organColors, "Penis", 255, 222, 199);
+ AppendToOrganList(organColors, "Pharynx", 102, 0, 0);
+ AppendToOrganList(organColors, "Prostate", 209, 163, 117);
+ AppendToOrganList(organColors, "Rectum", 161, 107, 54);
+ AppendToOrganList(organColors, "Sacrum", 255, 255, 153);
+ AppendToOrganList(organColors, "Seminal vesicle", 199, 232, 255);
+ AppendToOrganList(organColors, "Shoulder", 255, 255, 153);
+ AppendToOrganList(organColors, "Spinal cord", 255, 234, 79);
+ AppendToOrganList(organColors, "Spleen", 249, 108, 61);
+ AppendToOrganList(organColors, "Stomach", 161, 107, 54);
+ AppendToOrganList(organColors, "Teeth", 255, 252, 216);
+ AppendToOrganList(organColors, "Testicles", 199, 232, 255);
+ AppendToOrganList(organColors, "Thyroid", 255, 179, 184);
+ AppendToOrganList(organColors, "Tongue", 102, 0, 0);
+ AppendToOrganList(organColors, "Tumor", 147, 112, 17);
+ AppendToOrganList(organColors, "Urethra", 197, 204, 0);
+ AppendToOrganList(organColors, "Urinary bladder", 197, 204, 0);
+ AppendToOrganList(organColors, "Uterus", 161, 19, 39);
+ AppendToOrganList(organColors, "Vagina", 161, 19, 39);
+ AppendToOrganList(organColors, "Vertebra", 255, 255, 153);
+ AppendToOrganList(organColors, "Wrist", 255, 255, 153);
+ return organColors;
+ }
+
+ static void UpdateOrganList(QStringList& organColors, const QString& organname, mitk::Color color)
+ {
+ QString listElement( organname + QColor(color.GetRed() * 255 , color.GetGreen() * 255 , color.GetBlue() * 255).name() );
+
+ // remove previous definition if necessary
+ int oldIndex = organColors.indexOf( QRegExp(QRegExp::escape(organname) + "#......", Qt::CaseInsensitive));
+ if (oldIndex < 0 || organColors.at(oldIndex) != listElement )
+ {
+ if (oldIndex >= 0)
+ {
+ organColors.removeAt( oldIndex );
+ }
+
+ // add colored organ name AND sort list
+ organColors.append( listElement );
+ organColors.sort();
+ }
+ }
+
+ static void AppendToOrganList(QStringList& organColors, const QString& organname, int r, int g, int b)
+ {
+ organColors.append( organname + QColor(r, g, b).name() );
+ }
+};
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationView.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationView.cpp
new file mode 100644
index 0000000000..62a81db415
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationView.cpp
@@ -0,0 +1,895 @@
+/*===================================================================
+
+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 "QmitkMultiLabelSegmentationView.h"
+
+// blueberry
+#include
+#include
+
+// mitk
+#include "mitkLabelSetImage.h"
+#include "mitkStatusBar.h"
+#include "mitkApplicationCursor.h"
+#include "mitkToolManagerProvider.h"
+//#include "mitkSegmentationObjectFactory.h"
+#include "mitkSegTool2D.h"
+#include "mitkPlanePositionManager.h"
+#include "mitkPluginActivator.h"
+#include "mitkInteractionEventObserver.h"
+
+// Qmitk
+#include "QmitkMultiLabelSegmentationOrganNamesHandling.cpp"
+#include "QmitkRenderWindow.h"
+#include "QmitkNewSegmentationDialog.h"
+
+// us
+#include
+#include
+#include
+#include
+#include
+
+// Qt
+#include
+#include
+#include
+#include
+
+#include "tinyxml.h"
+
+#include
+
+const std::string QmitkMultiLabelSegmentationView::VIEW_ID = "org.mitk.views.multilabelsegmentation";
+
+QmitkMultiLabelSegmentationView::QmitkMultiLabelSegmentationView() :
+ m_Parent(NULL),
+ m_IRenderWindowPart(NULL),
+ m_ReferenceNode(NULL),
+ m_WorkingNode(NULL),
+ m_ToolManager(NULL),
+ m_MouseCursorSet(false)
+{
+ m_SegmentationPredicate = mitk::NodePredicateAnd::New();
+ m_SegmentationPredicate->AddPredicate(mitk::TNodePredicateDataType::New());
+ m_SegmentationPredicate->AddPredicate(mitk::NodePredicateNot::New(mitk::NodePredicateProperty::New("helper object")));
+ m_SegmentationPredicate->AddPredicate(mitk::NodePredicateProperty::New("visible", mitk::BoolProperty::New(true)));
+
+ mitk::TNodePredicateDataType::Pointer isImage = mitk::TNodePredicateDataType::New();
+ mitk::NodePredicateProperty::Pointer isBinary = mitk::NodePredicateProperty::New("binary", mitk::BoolProperty::New(true));
+ mitk::NodePredicateAnd::Pointer isMask = mitk::NodePredicateAnd::New(isBinary, isImage);
+
+ mitk::NodePredicateDataType::Pointer isDwi = mitk::NodePredicateDataType::New("DiffusionImage");
+ mitk::NodePredicateDataType::Pointer isDti = mitk::NodePredicateDataType::New("TensorImage");
+ mitk::NodePredicateDataType::Pointer isQbi = mitk::NodePredicateDataType::New("QBallImage");
+
+ mitk::NodePredicateOr::Pointer validImages = mitk::NodePredicateOr::New();
+ validImages->AddPredicate(isImage);
+ validImages->AddPredicate(isDwi);
+ validImages->AddPredicate(isDti);
+ validImages->AddPredicate(isQbi);
+
+ m_ReferencePredicate = mitk::NodePredicateAnd::New();
+ m_ReferencePredicate->AddPredicate(validImages);
+ m_ReferencePredicate->AddPredicate(mitk::NodePredicateNot::New(m_SegmentationPredicate));
+ m_ReferencePredicate->AddPredicate(mitk::NodePredicateNot::New(isMask));
+ m_ReferencePredicate->AddPredicate(mitk::NodePredicateNot::New(mitk::NodePredicateProperty::New("helper object")));
+}
+
+QmitkMultiLabelSegmentationView::~QmitkMultiLabelSegmentationView()
+{
+ m_ToolManager->ActivateTool(-1);
+ /*
+ todo: check this
+ m_Controls.m_SliceBasedInterpolatorWidget->EnableInterpolation(false);
+ ctkPluginContext* context = mitk::PluginActivator::getContext();
+ ctkServiceReference ppmRef = context->getServiceReference();
+ mitk::PlanePositionManagerService* service = context->getService(ppmRef);
+ service->RemoveAllPlanePositions();
+ context->ungetService(ppmRef);
+*/
+ m_ToolManager->SetReferenceData(NULL);
+ m_ToolManager->SetWorkingData(NULL);
+
+ m_ServiceRegistration.Unregister();
+}
+
+void QmitkMultiLabelSegmentationView::CreateQtPartControl(QWidget* parent)
+{
+ // setup the basic GUI of this view
+ m_Parent = parent;
+ m_Controls.setupUi(parent);
+
+ m_Controls.m_cbReferenceNodeSelector->SetDataStorage(this->GetDataStorage());
+ m_Controls.m_cbReferenceNodeSelector->SetPredicate(m_ReferencePredicate);
+ m_Controls.m_cbReferenceNodeSelector->SetAutoSelectNewItems(true);
+
+ m_Controls.m_cbWorkingNodeSelector->SetDataStorage(this->GetDataStorage());
+ m_Controls.m_cbWorkingNodeSelector->SetPredicate(m_SegmentationPredicate);
+ m_Controls.m_cbWorkingNodeSelector->SetAutoSelectNewItems(true);
+
+ m_ToolManager = mitk::ToolManagerProvider::GetInstance()->GetToolManager();
+ assert(m_ToolManager);
+
+ m_ToolManager->SetDataStorage( *(this->GetDataStorage()) );
+ m_ToolManager->InitializeTools();
+
+ //use the same ToolManager instance for our 3D Tools
+ m_Controls.m_ManualToolSelectionBox3D->SetToolManager(*m_ToolManager);
+
+ m_Controls.m_LabelSetWidget->SetDataStorage(this->GetDataStorage());
+ m_Controls.m_LabelSetWidget->SetOrganColors(mitk::OrganNamesHandling::GetDefaultOrganColorString());
+ m_Controls.m_LabelSetWidget->hide();
+
+ m_Controls.m_SurfaceBasedInterpolatorWidget->SetDataStorage( *(this->GetDataStorage()) );
+ m_Controls.m_SliceBasedInterpolatorWidget->SetDataStorage( *(this->GetDataStorage()) );
+
+ // all part of open source MITK
+ m_Controls.m_ManualToolSelectionBox2D->SetGenerateAccelerators(true);
+ m_Controls.m_ManualToolSelectionBox2D->SetToolGUIArea( m_Controls.m_ManualToolGUIContainer2D );
+ //m_Controls.m_ManualToolSelectionBox2D->SetDisplayedToolGroups();
+ m_Controls.m_ManualToolSelectionBox2D->SetDisplayedToolGroups("Add Subtract Fill Erase Paint Wipe 'Region Growing' FastMarching2D Correction 'Live Wire'");// todo: "Correction 'Live Wire'"
+ m_Controls.m_ManualToolSelectionBox2D->SetEnabledMode( QmitkToolSelectionBox::EnabledWithReferenceAndWorkingDataVisible );
+ connect( m_Controls.m_ManualToolSelectionBox2D, SIGNAL(ToolSelected(int)), this, SLOT(OnManualTool2DSelected(int)) );
+
+ //setup 3D Tools
+ m_Controls.m_ManualToolSelectionBox3D->SetGenerateAccelerators(true);
+ m_Controls.m_ManualToolSelectionBox3D->SetToolGUIArea( m_Controls.m_ManualToolGUIContainer3D );
+ //specify tools to be added to 3D Tool area
+ m_Controls.m_ManualToolSelectionBox3D->SetDisplayedToolGroups("Threshold 'Two Thresholds' 'Auto Threshold' 'Multiple Otsu'"); // todo add : FastMarching3D RegionGrowing Watershed
+
+ m_Controls.m_ManualToolSelectionBox3D->SetLayoutColumns(2);
+ m_Controls.m_ManualToolSelectionBox3D->SetEnabledMode( QmitkToolSelectionBox::EnabledWithReferenceAndWorkingDataVisible );
+
+ connect( m_Controls.m_cbReferenceNodeSelector, SIGNAL( OnSelectionChanged( const mitk::DataNode* ) ),
+ this, SLOT( OnReferenceSelectionChanged( const mitk::DataNode* ) ) );
+
+ connect( m_Controls.m_cbWorkingNodeSelector, SIGNAL( OnSelectionChanged( const mitk::DataNode* ) ),
+ this, SLOT( OnSegmentationSelectionChanged( const mitk::DataNode* ) ) );
+
+ connect( m_Controls.m_pbNewLabel, SIGNAL(clicked()), this, SLOT( OnNewLabel()) );
+ connect( m_Controls.m_pbNewSegmentationSession, SIGNAL(clicked()), this, SLOT( OnNewSegmentationSession()) );
+ connect( m_Controls.m_pbShowLabelTable, SIGNAL(toggled(bool)), this, SLOT( OnShowLabelTable(bool)) );
+
+ connect(m_Controls.m_LabelSetWidget, SIGNAL(goToLabel(const mitk::Point3D&)), this, SLOT(OnGoToLabel(const mitk::Point3D&)) );
+ connect(m_Controls.m_LabelSetWidget, SIGNAL(resetView()), this, SLOT(OnResetView()) );
+
+ connect( m_Controls.m_cbInterpolation, SIGNAL( activated (int) ), this, SLOT( OnInterpolationSelectionChanged(int) ) );
+
+ m_Controls.m_cbInterpolation->setCurrentIndex(0);
+ m_Controls.m_swInterpolation->hide();
+
+ this->OnReferenceSelectionChanged( m_Controls.m_cbReferenceNodeSelector->GetSelectedNode() );
+
+ m_IRenderWindowPart = this->GetRenderWindowPart();
+ if (m_IRenderWindowPart)
+ {
+ QList controllers;
+ controllers.push_back(m_IRenderWindowPart->GetQmitkRenderWindow("axial")->GetSliceNavigationController());
+ controllers.push_back(m_IRenderWindowPart->GetQmitkRenderWindow("sagittal")->GetSliceNavigationController());
+ controllers.push_back(m_IRenderWindowPart->GetQmitkRenderWindow("coronal")->GetSliceNavigationController());
+ m_Controls.m_SliceBasedInterpolatorWidget->SetSliceNavigationControllers(controllers);
+ // m_Controls.m_LabelSetWidget->SetRenderWindowPart(this->m_IRenderWindowPart);
+ }
+
+ this->InitializeListeners();
+
+ connect( m_Controls.m_btAddLayer, SIGNAL(clicked()), this, SLOT( OnAddLayer()) );
+ connect( m_Controls.m_btDeleteLayer, SIGNAL(clicked()), this, SLOT( OnDeleteLayer()) );
+ connect( m_Controls.m_btPreviousLayer, SIGNAL(clicked()), this, SLOT( OnPreviousLayer()) );
+ connect( m_Controls.m_btNextLayer, SIGNAL(clicked()), this, SLOT( OnNextLayer()) );
+ connect( m_Controls.m_btLockExterior, SIGNAL(toggled(bool)), this, SLOT( OnLockExteriorToggled(bool)) );
+ connect( m_Controls.m_btDeactivateTool, SIGNAL(clicked()), this, SLOT( OnDeactivateActiveTool()) );
+ connect( m_Controls.m_cbActiveLayer, SIGNAL(currentIndexChanged(int)), this, SLOT( OnChangeLayer(int)) );
+
+ m_Controls.m_btAddLayer->hide();
+ m_Controls.m_btDeactivateTool->hide();
+ m_Controls.m_btDeleteLayer->hide();
+ m_Controls.m_btLockExterior->hide();
+ m_Controls.m_btNextLayer->hide();
+ m_Controls.m_btPreviousLayer->hide();
+ m_Controls.m_cbActiveLayer->hide();
+
+}
+
+void QmitkMultiLabelSegmentationView::InitializeListeners()
+{
+ if (m_Interactor.IsNull())
+ {
+ us::Module* module = us::GetModuleContext()->GetModule();
+ std::vector resources = module->FindResources("/", "*", true);
+ for (std::vector::iterator iter = resources.begin(); iter != resources.end(); ++iter)
+ {
+ MITK_INFO << iter->GetResourcePath();
+ }
+
+ m_Interactor = mitk::SegmentationInteractor::New();
+ if (!m_Interactor->LoadStateMachine("SegmentationInteraction.xml", module))
+ {
+ MITK_WARN << "Error loading state machine";
+ }
+
+ if (!m_Interactor->SetEventConfig ("ConfigSegmentation.xml", module))
+ {
+ MITK_WARN << "Error loading state machine configuration";
+ }
+
+ // Register as listener via micro services
+ us::ServiceProperties props;
+ props["name"] = std::string("SegmentationInteraction");
+ m_ServiceRegistration = us::GetModuleContext()->RegisterService(m_Interactor.GetPointer(), props);
+ }
+}
+
+void QmitkMultiLabelSegmentationView::SetFocus ()
+{
+}
+
+bool QmitkMultiLabelSegmentationView::CheckForSameGeometry(const mitk::Image *image1, const mitk::Image *image2) const
+{
+ bool isSameGeometry(true);
+
+ if (image1 && image2)
+ {
+ mitk::Geometry3D* geo1 = image1->GetGeometry();
+ mitk::Geometry3D* geo2 = image2->GetGeometry();
+
+ isSameGeometry = isSameGeometry && mitk::Equal(geo1->GetOrigin(), geo2->GetOrigin());
+ isSameGeometry = isSameGeometry && mitk::Equal(geo1->GetExtent(0), geo2->GetExtent(0));
+ isSameGeometry = isSameGeometry && mitk::Equal(geo1->GetExtent(1), geo2->GetExtent(1));
+ isSameGeometry = isSameGeometry && mitk::Equal(geo1->GetExtent(2), geo2->GetExtent(2));
+ isSameGeometry = isSameGeometry && mitk::Equal(geo1->GetSpacing(), geo2->GetSpacing());
+ isSameGeometry = isSameGeometry && mitk::MatrixEqualElementWise(geo1->GetIndexToWorldTransform()->GetMatrix(), geo2->GetIndexToWorldTransform()->GetMatrix());
+
+ return isSameGeometry;
+ }
+ else
+ {
+ return false;
+ }
+}
+
+void QmitkMultiLabelSegmentationView::RenderWindowPartActivated(mitk::IRenderWindowPart* renderWindowPart)
+{
+ if (m_IRenderWindowPart != renderWindowPart)
+ {
+ m_IRenderWindowPart = renderWindowPart;
+ m_Parent->setEnabled(true);
+
+ QList controllers;
+ controllers.push_back(renderWindowPart->GetQmitkRenderWindow("axial")->GetSliceNavigationController());
+ controllers.push_back(renderWindowPart->GetQmitkRenderWindow("sagittal")->GetSliceNavigationController());
+ controllers.push_back(renderWindowPart->GetQmitkRenderWindow("coronal")->GetSliceNavigationController());
+ m_Controls.m_SliceBasedInterpolatorWidget->SetSliceNavigationControllers(controllers);
+ }
+}
+
+void QmitkMultiLabelSegmentationView::RenderWindowPartDeactivated(mitk::IRenderWindowPart* /*renderWindowPart*/)
+{
+ m_ToolManager->ActivateTool(-1);
+ m_IRenderWindowPart = 0;
+ m_Parent->setEnabled(false);
+}
+
+int QmitkMultiLabelSegmentationView::GetSizeFlags(bool width)
+{
+ if(!width)
+ {
+ return berry::Constants::MIN | berry::Constants::MAX | berry::Constants::FILL;
+ }
+ else
+ {
+ return 0;
+ }
+}
+
+int QmitkMultiLabelSegmentationView::ComputePreferredSize(bool width, int /*availableParallel*/, int /*availablePerpendicular*/, int preferredResult)
+{
+ if(width==false)
+ {
+ return 100;
+ }
+ else
+ {
+ return preferredResult;
+ }
+}
+
+void QmitkMultiLabelSegmentationView::UpdateControls()
+{
+ mitk::DataNode* referenceNode = m_ToolManager->GetReferenceData(0);
+ bool hasReferenceNode = referenceNode != NULL;
+
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ bool hasWorkingNode = workingNode != NULL;
+
+ m_Controls.m_pbNewSegmentationSession->setEnabled(false);
+ m_Controls.m_pbNewLabel->setEnabled(false);
+ m_Controls.m_gbInterpolation->setEnabled(false);
+ m_Controls.m_SliceBasedInterpolatorWidget->setEnabled(false);
+ m_Controls.m_SurfaceBasedInterpolatorWidget->setEnabled(false);
+ m_Controls.m_btDeactivateTool->setEnabled(false);
+ m_Controls.m_LabelSetWidget->setEnabled(false);
+ m_Controls.m_btAddLayer->setEnabled(false);
+ m_Controls.m_btDeleteLayer->setEnabled(false);
+ m_Controls.m_cbActiveLayer->setEnabled(false);
+ m_Controls.m_btPreviousLayer->setEnabled(false);
+ m_Controls.m_btNextLayer->setEnabled(false);
+ m_Controls.m_btLockExterior->setChecked(false);
+ m_Controls.m_pbShowLabelTable->setChecked(false);
+
+ m_Controls.m_ManualToolSelectionBox3D->SetEnabledMode(QmitkToolSelectionBox::EnabledWithReferenceAndWorkingDataVisible);
+ m_Controls.m_ManualToolSelectionBox2D->SetEnabledMode(QmitkToolSelectionBox::EnabledWithReferenceAndWorkingDataVisible);
+
+ if(hasReferenceNode)
+ {
+ m_Controls.m_pbNewSegmentationSession->setEnabled(true);
+ }
+
+ if(hasWorkingNode)
+ {
+ m_Controls.m_pbNewLabel->setEnabled(true);
+ m_Controls.m_gbInterpolation->setEnabled(true);
+ m_Controls.m_SliceBasedInterpolatorWidget->setEnabled(true);
+ m_Controls.m_SurfaceBasedInterpolatorWidget->setEnabled(true);
+ m_Controls.m_btDeactivateTool->setEnabled(true);
+ m_Controls.m_LabelSetWidget->setEnabled(true);
+ m_Controls.m_btAddLayer->setEnabled(true);
+
+ mitk::LabelSetImage* workingImage = dynamic_cast(workingNode->GetData());
+
+ int activeLayer = workingImage->GetActiveLayer();
+ int numberOfLayers = workingImage->GetNumberOfLayers();
+
+ m_Controls.m_cbActiveLayer->blockSignals(true);
+ m_Controls.m_cbActiveLayer->clear();
+ for (int lidx=0; lidxGetNumberOfLayers(); ++lidx)
+ m_Controls.m_cbActiveLayer->addItem(QString::number(lidx));
+ m_Controls.m_cbActiveLayer->setCurrentIndex(activeLayer);
+ m_Controls.m_cbActiveLayer->blockSignals(false);
+
+ m_Controls.m_btDeleteLayer->setEnabled(numberOfLayers>1);
+ m_Controls.m_cbActiveLayer->setEnabled(numberOfLayers>1);
+ m_Controls.m_btPreviousLayer->setEnabled(activeLayer>0);
+ m_Controls.m_btNextLayer->setEnabled(activeLayer!=numberOfLayers-1);
+ m_Controls.m_btLockExterior->setChecked(workingImage->GetLabel(0)->GetLocked());
+
+ m_Controls.m_pbShowLabelTable->setChecked(workingImage->GetNumberOfLabels() > 1 /*1st is exterior*/);
+
+ m_Controls.m_ManualToolSelectionBox2D->SetEnabledMode(QmitkToolSelectionBox::EnabledWithWorkingDataVisible);
+ }
+
+ if(hasWorkingNode && hasReferenceNode)
+ {
+ int layer = -1;
+ referenceNode->GetIntProperty("layer", layer);
+ workingNode->SetIntProperty("layer", layer+1);
+ }
+
+ this->RequestRenderWindowUpdate(mitk::RenderingManager::REQUEST_UPDATE_ALL);
+}
+
+void QmitkMultiLabelSegmentationView::OnNewSegmentationSession()
+{
+ mitk::DataNode* referenceNode = m_Controls.m_cbReferenceNodeSelector->GetSelectedNode();
+
+ if (!referenceNode)
+ {
+ QMessageBox::information( m_Parent, "New Segmentation Session", "Please load and select a patient image before starting some action.");
+ return;
+ }
+
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::Image* referenceImage = dynamic_cast( referenceNode->GetData() );
+ assert(referenceImage);
+
+ QString newName = QString::fromStdString(referenceNode->GetName());
+ newName.append("-labels");
+
+ bool ok = false;
+ newName = QInputDialog::getText(m_Parent, "New Segmentation Session", "New name:", QLineEdit::Normal, newName, &ok);
+
+ if(!ok) return;
+
+ this->WaitCursorOn();
+
+ mitk::LabelSetImage::Pointer workingImage = mitk::LabelSetImage::New();
+
+ try
+ {
+ workingImage->Initialize(referenceImage);
+ }
+ catch ( mitk::Exception& e )
+ {
+ this->WaitCursorOff();
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ QMessageBox::information(m_Parent, "New Segmentation Session", "Could not create a new segmentation session.\n");
+ return;
+ }
+
+ this->WaitCursorOff();
+
+ mitk::DataNode::Pointer workingNode = mitk::DataNode::New();
+ workingNode->SetData(workingImage);
+ workingNode->SetName(newName.toStdString());
+ workingImage->GetExteriorLabel()->SetProperty("name.parent",mitk::StringProperty::New(referenceNode->GetName().c_str()));
+ workingImage->GetExteriorLabel()->SetProperty("name.image",mitk::StringProperty::New(newName.toStdString().c_str()));
+
+ if (!this->GetDataStorage()->Exists(workingNode))
+ this->GetDataStorage()->Add(workingNode, referenceNode);
+
+ m_Controls.m_LabelSetWidget->ResetAllTableWidgetItems();
+
+ OnNewLabel();
+
+ m_Controls.m_LabelSetWidget->ResetAllTableWidgetItems();
+}
+
+void QmitkMultiLabelSegmentationView::OnNewLabel()
+{
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ assert(workingNode);
+
+ mitk::LabelSetImage* workingImage = dynamic_cast(workingNode->GetData());
+ assert(workingImage);
+
+ QmitkNewSegmentationDialog* dialog = new QmitkNewSegmentationDialog( m_Parent );
+ dialog->SetSuggestionList( mitk::OrganNamesHandling::GetDefaultOrganColorString() );
+ dialog->setWindowTitle("New Label");
+
+ int dialogReturnValue = dialog->exec();
+
+ if ( dialogReturnValue == QDialog::Rejected ) return;
+
+ QString segName = dialog->GetSegmentationName();
+ if(segName.isEmpty()) segName = "Unnamed";
+ workingImage->GetActiveLabelSet()->AddLabel(segName.toStdString(), dialog->GetColor());
+
+ UpdateControls();
+}
+
+void QmitkMultiLabelSegmentationView::OnShowLabelTable(bool value)
+{
+ if (value)
+ {
+ m_Controls.m_LabelSetWidget->show();
+ m_Controls.m_btAddLayer->show();
+ m_Controls.m_btDeactivateTool->show();
+ m_Controls.m_btDeleteLayer->show();
+ m_Controls.m_btLockExterior->show();
+ m_Controls.m_btNextLayer->show();
+ m_Controls.m_btPreviousLayer->show();
+ m_Controls.m_cbActiveLayer->show();
+ }
+ else
+ {
+ m_Controls.m_LabelSetWidget->hide();
+ m_Controls.m_btAddLayer->hide();
+ m_Controls.m_btDeactivateTool->hide();
+ m_Controls.m_btDeleteLayer->hide();
+ m_Controls.m_btLockExterior->hide();
+ m_Controls.m_btNextLayer->hide();
+ m_Controls.m_btPreviousLayer->hide();
+ m_Controls.m_cbActiveLayer->hide();
+ }
+}
+
+void QmitkMultiLabelSegmentationView::OnNextLayer()
+{
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ assert(workingNode);
+ mitk::LabelSetImage* workingImage = dynamic_cast(workingNode->GetData());
+ assert(workingImage);
+
+ OnChangeLayer(workingImage->GetActiveLayer() + 1 );
+}
+
+void QmitkMultiLabelSegmentationView::OnPreviousLayer()
+{
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ assert(workingNode);
+ mitk::LabelSetImage* workingImage = dynamic_cast(workingNode->GetData());
+ assert(workingImage);
+
+ OnChangeLayer(workingImage->GetActiveLayer() - 1 );
+}
+
+
+void QmitkMultiLabelSegmentationView::OnChangeLayer(int layer)
+{
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ assert(workingNode);
+
+ mitk::LabelSetImage* workingImage = dynamic_cast(workingNode->GetData());
+ assert(workingImage);
+
+ this->WaitCursorOn();
+ workingImage->SetActiveLayer( layer );
+ this->WaitCursorOff();
+
+ UpdateControls();
+ m_Controls.m_LabelSetWidget->ResetAllTableWidgetItems();
+}
+
+void QmitkMultiLabelSegmentationView::OnDeleteLayer()
+{
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ assert(workingNode);
+
+ mitk::LabelSetImage* workingImage = dynamic_cast(workingNode->GetData());
+ assert(workingImage);
+
+ if (workingImage->GetNumberOfLayers() < 2)
+ return;
+
+ QString question = "Do you really want to delete the current layer?";
+
+ QMessageBox::StandardButton answerButton = QMessageBox::question( m_Controls.m_LabelSetWidget, "Delete layer",
+ question, QMessageBox::Yes | QMessageBox::Cancel, QMessageBox::Yes);
+
+ if (answerButton != QMessageBox::Yes) return;
+
+ try
+ {
+ this->WaitCursorOn();
+ workingImage->RemoveLayer();
+ this->WaitCursorOff();
+ }
+ catch ( mitk::Exception& e )
+ {
+ this->WaitCursorOff();
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ QMessageBox::information(m_Controls.m_LabelSetWidget, "Delete Layer", "Could not delete the currently active layer. See error log for details.\n");
+ return;
+ }
+
+ UpdateControls();
+ m_Controls.m_LabelSetWidget->ResetAllTableWidgetItems();
+}
+
+void QmitkMultiLabelSegmentationView::OnAddLayer()
+{
+ m_ToolManager->ActivateTool(-1);
+
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ assert(workingNode);
+
+ mitk::LabelSetImage* workingImage = dynamic_cast(workingNode->GetData());
+ assert(workingImage);
+
+ QString question = "Do you really want to add a layer to the current segmentation session?";
+ QMessageBox::StandardButton answerButton = QMessageBox::question( m_Controls.m_LabelSetWidget, "Add layer",
+ question, QMessageBox::Yes | QMessageBox::Cancel, QMessageBox::Yes);
+
+ if (answerButton != QMessageBox::Yes) return;
+
+ int newLabelSetId = -1;
+ try
+ {
+ WaitCursorOn();
+ newLabelSetId = workingImage->AddLayer();
+ WaitCursorOff();
+ }
+ catch ( mitk::Exception& e )
+ {
+ WaitCursorOff();
+ MITK_ERROR << "Exception caught: " << e.GetDescription();
+ QMessageBox::information(m_Controls.m_LabelSetWidget, "Add Layer", "Could not add a new layer. See error log for details.\n");
+ return;
+ }
+
+ // Update controls and label set list for direct response
+ m_Controls.m_LabelSetWidget->ResetAllTableWidgetItems();
+ OnNewLabel();
+ UpdateControls();
+}
+
+void QmitkMultiLabelSegmentationView::OnDeactivateActiveTool()
+{
+ m_ToolManager->ActivateTool(-1);
+}
+
+void QmitkMultiLabelSegmentationView::OnLockExteriorToggled(bool checked)
+{
+ mitk::DataNode* workingNode = m_ToolManager->GetWorkingData(0);
+ assert(workingNode);
+
+ mitk::LabelSetImage* workingImage = dynamic_cast(workingNode->GetData());
+ assert(workingImage);
+
+ workingImage->GetLabel(0)->SetLocked(checked);
+}
+
+void QmitkMultiLabelSegmentationView::NodeAdded(const mitk::DataNode* node)
+{
+ /*
+ bool isHelperObject(false);
+ node->GetBoolProperty("helper object", isHelperObject);
+ if (isHelperObject) return;
+
+ if (m_ReferenceNode.IsNotNull() && dynamic_cast(node->GetData()))
+ {
+ mitk::LabelSetImage* workingImage = dynamic_cast(node->GetData());
+
+ if (workingImage->GetNumberOfLabels() > 2)
+ m_Controls.m_LabelSetWidget->show();
+ else
+ m_Controls.m_LabelSetWidget->hide();
+ }
+ */
+}
+
+void QmitkMultiLabelSegmentationView::NodeRemoved(const mitk::DataNode* node)
+{
+ bool isHelperObject(false);
+ node->GetBoolProperty("helper object", isHelperObject);
+ if (isHelperObject) return;
+
+ if (m_ReferenceNode.IsNotNull() && dynamic_cast(node->GetData()))
+ {
+ // remove all possible contour markers of the segmentation
+ mitk::DataStorage::SetOfObjects::ConstPointer allContourMarkers =
+ this->GetDataStorage()->GetDerivations(node, mitk::NodePredicateProperty::New("isContourMarker", mitk::BoolProperty::New(true)));
+
+ ctkPluginContext* context = mitk::PluginActivator::getContext();
+ ctkServiceReference ppmRef = context->getServiceReference();
+ mitk::PlanePositionManagerService* service = context->getService(ppmRef);
+
+ for (mitk::DataStorage::SetOfObjects::ConstIterator it = allContourMarkers->Begin(); it != allContourMarkers->End(); ++it)
+ {
+ std::string nodeName = node->GetName();
+ unsigned int t = nodeName.find_last_of(" ");
+ unsigned int id = atof(nodeName.substr(t+1).c_str())-1;
+
+ service->RemovePlanePosition(id);
+
+ this->GetDataStorage()->Remove(it->Value());
+ }
+
+ context->ungetService(ppmRef);
+ service = NULL;
+ }
+}
+
+void QmitkMultiLabelSegmentationView::OnInterpolationSelectionChanged(int index)
+{
+ if (index == 1)
+ {
+ m_Controls.m_SurfaceBasedInterpolatorWidget->m_Controls.m_btStart->setChecked(false);//OnToggleWidgetActivation(false);
+ m_Controls.m_swInterpolation->setCurrentIndex(0);
+ m_Controls.m_swInterpolation->show();
+ }
+ else if (index == 2)
+ {
+ m_Controls.m_SliceBasedInterpolatorWidget->m_Controls.m_btStart->setChecked(false);
+ m_Controls.m_swInterpolation->setCurrentIndex(1);
+ m_Controls.m_swInterpolation->show();
+ }
+ else
+ {
+ m_Controls.m_SurfaceBasedInterpolatorWidget->m_Controls.m_btStart->setChecked(false);
+ m_Controls.m_SliceBasedInterpolatorWidget->m_Controls.m_btStart->setChecked(false);
+ m_Controls.m_swInterpolation->setCurrentIndex(2);
+ m_Controls.m_swInterpolation->hide();
+ }
+}
+
+void QmitkMultiLabelSegmentationView::OnReferenceSelectionChanged( const mitk::DataNode* node )
+{
+ m_ToolManager->ActivateTool(-1);
+
+ m_ReferenceNode = const_cast(node);
+
+ m_ToolManager->SetReferenceData(m_ReferenceNode);
+
+ //check match of segmentation and reference image geometries
+ if (node && m_WorkingNode.IsNotNull())
+ {
+ mitk::Image* workingImage = dynamic_cast(m_WorkingNode->GetData());
+ assert(workingImage);
+
+ mitk::Image* refImage = dynamic_cast(node->GetData());
+ assert(refImage);
+
+ if (!this->CheckForSameGeometry(refImage, workingImage))
+ return;
+ }
+
+ this->UpdateControls();
+ //m_Controls.m_LabelSetWidget->ResetAllTableWidgetItems();
+}
+
+void QmitkMultiLabelSegmentationView::OnEstablishLabelSetConnection()
+{
+ MITK_INFO << "Connection Established";
+ mitk::LabelSetImage* workingImage = dynamic_cast(m_WorkingNode->GetData());
+ assert(workingImage);
+
+ workingImage->GetActiveLabelSet()->AddLabelEvent
+ += mitk::MessageDelegate(m_Controls.m_LabelSetWidget,&QmitkLabelSetWidget::ResetAllTableWidgetItems);
+ workingImage->GetActiveLabelSet()->RemoveLabelEvent
+ += mitk::MessageDelegate(m_Controls.m_LabelSetWidget,&QmitkLabelSetWidget::ResetAllTableWidgetItems);
+ workingImage->GetActiveLabelSet()->ModifyLabelEvent
+ += mitk::MessageDelegate(m_Controls.m_LabelSetWidget,&QmitkLabelSetWidget::UpdateAllTableWidgetItems);
+ workingImage->GetActiveLabelSet()->AllLabelsModifiedEvent
+ += mitk::MessageDelegate(m_Controls.m_LabelSetWidget,&QmitkLabelSetWidget::UpdateAllTableWidgetItems);
+ workingImage->GetActiveLabelSet()->ActiveLabelEvent
+ += mitk::MessageDelegate1(m_Controls.m_LabelSetWidget,&QmitkLabelSetWidget::SelectLabelByPixelValue);
+}
+
+
+void QmitkMultiLabelSegmentationView::OnLooseLabelSetConnection()
+{
+ MITK_INFO << "Connection Lost";
+ mitk::LabelSetImage* workingImage = dynamic_cast(m_WorkingNode->GetData());
+ assert(workingImage);
+
+ // Reset LabelSetWidget Events
+ workingImage->GetActiveLabelSet()->AddLabelEvent
+ -= mitk::MessageDelegate(m_Controls.m_LabelSetWidget,&QmitkLabelSetWidget::ResetAllTableWidgetItems);
+ workingImage->GetActiveLabelSet()->RemoveLabelEvent
+ -= mitk::MessageDelegate(m_Controls.m_LabelSetWidget,&QmitkLabelSetWidget::ResetAllTableWidgetItems);
+ workingImage->GetActiveLabelSet()->ModifyLabelEvent
+ -= mitk::MessageDelegate(m_Controls.m_LabelSetWidget,&QmitkLabelSetWidget::UpdateAllTableWidgetItems);
+ workingImage->GetActiveLabelSet()->AllLabelsModifiedEvent
+ -= mitk::MessageDelegate(m_Controls.m_LabelSetWidget,&QmitkLabelSetWidget::UpdateAllTableWidgetItems);
+ workingImage->GetActiveLabelSet()->ActiveLabelEvent
+ -= mitk::MessageDelegate1(m_Controls.m_LabelSetWidget,&QmitkLabelSetWidget::SelectLabelByPixelValue);
+
+}
+
+void QmitkMultiLabelSegmentationView::OnSegmentationSelectionChanged(const mitk::DataNode *node)
+{
+ m_ToolManager->ActivateTool(-1);
+
+ if(m_WorkingNode.IsNotNull())
+ {
+ mitk::LabelSetImage* workingImage = dynamic_cast(m_WorkingNode->GetData());
+ assert(workingImage);
+
+ //Loose LabelSetConnections
+ OnLooseLabelSetConnection();
+
+ workingImage->BeforeChangeLayerEvent
+ -= mitk::MessageDelegate(this,&QmitkMultiLabelSegmentationView::OnLooseLabelSetConnection);
+ workingImage->AfterchangeLayerEvent
+ -= mitk::MessageDelegate(this,&QmitkMultiLabelSegmentationView::OnEstablishLabelSetConnection);
+ }
+
+ m_WorkingNode = const_cast(node);
+
+ if(m_WorkingNode.IsNotNull())
+ {
+ mitk::LabelSetImage* workingImage = dynamic_cast(m_WorkingNode->GetData());
+ assert(workingImage);
+
+ //Establish LabelSetConnection
+ OnEstablishLabelSetConnection();
+
+ workingImage->BeforeChangeLayerEvent
+ += mitk::MessageDelegate(this,&QmitkMultiLabelSegmentationView::OnLooseLabelSetConnection);
+ workingImage->AfterchangeLayerEvent
+ += mitk::MessageDelegate(this,&QmitkMultiLabelSegmentationView::OnEstablishLabelSetConnection);
+ }
+
+ m_ToolManager->SetWorkingData(m_WorkingNode);
+
+ //check match of segmentation and reference image geometries
+ if (node && m_ReferenceNode.IsNotNull())
+ {
+ mitk::Image* refImage = dynamic_cast(m_ReferenceNode->GetData());
+ assert(refImage);
+
+ mitk::Image* workingImage = dynamic_cast(node->GetData());
+ assert(workingImage);
+
+ if (!this->CheckForSameGeometry(refImage, workingImage))
+ return;
+ }
+
+ if (m_WorkingNode.IsNotNull())
+ {
+ mitk::DataStorage::SetOfObjects::ConstPointer segNodes = this->GetDataStorage()->GetSubset(m_SegmentationPredicate);
+ for(mitk::DataStorage::SetOfObjects::const_iterator iter = segNodes->begin(); iter != segNodes->end(); ++iter)
+ {
+ mitk::DataNode* _segNode = *iter;
+ _segNode->SetVisibility(false);
+ }
+
+ m_WorkingNode->SetVisibility(true);
+ }
+
+ this->UpdateControls();
+
+ if (m_WorkingNode.IsNotNull())
+ {
+ m_Controls.m_LabelSetWidget->ResetAllTableWidgetItems();
+ }
+}
+
+void QmitkMultiLabelSegmentationView::OnManualTool2DSelected(int id)
+{
+ this->ResetMouseCursor();
+ mitk::StatusBar::GetInstance()->DisplayText("");
+
+ if (id >= 0)
+ {
+ std::string text = "Active Tool: \"";
+ text += m_ToolManager->GetToolById(id)->GetName();
+ text += "\"";
+ mitk::StatusBar::GetInstance()->DisplayText(text.c_str());
+
+ us::ModuleResource resource = m_ToolManager->GetToolById(id)->GetCursorIconResource();
+ if (resource.IsValid())
+ this->SetMouseCursor(resource, 0, 0);
+ }
+}
+
+void QmitkMultiLabelSegmentationView::ResetMouseCursor()
+{
+ if ( m_MouseCursorSet )
+ {
+ mitk::ApplicationCursor::GetInstance()->PopCursor();
+ m_MouseCursorSet = false;
+ }
+}
+
+void QmitkMultiLabelSegmentationView::SetMouseCursor( const us::ModuleResource resource, int hotspotX, int hotspotY )
+{
+ // Remove previously set mouse cursor
+ if ( m_MouseCursorSet )
+ {
+ mitk::ApplicationCursor::GetInstance()->PopCursor();
+ }
+
+ us::ModuleResourceStream cursor(resource, std::ios::binary);
+ mitk::ApplicationCursor::GetInstance()->PushCursor( cursor, hotspotX, hotspotY );
+ m_MouseCursorSet = true;
+}
+
+void QmitkMultiLabelSegmentationView::OnGoToLabel(const mitk::Point3D& pos)
+{
+ if (m_IRenderWindowPart)
+ m_IRenderWindowPart->SetSelectedPosition(pos);
+}
+
+void QmitkMultiLabelSegmentationView::OnResetView()
+{
+ if (m_IRenderWindowPart)
+ m_IRenderWindowPart->ForceImmediateUpdate();
+}
+
+QString QmitkMultiLabelSegmentationView::GetLastFileOpenPath()
+{
+ return QString::fromStdString(this->GetPreferences()->Get("LastFileOpenPath", ""));
+}
+
+void QmitkMultiLabelSegmentationView::SetLastFileOpenPath(const QString& path)
+{
+ this->GetPreferences()->Put("LastFileOpenPath", path.toStdString());
+ this->GetPreferences()->Flush();
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationView.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationView.h
new file mode 100644
index 0000000000..e96cc77024
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkMultiLabelSegmentationView.h
@@ -0,0 +1,172 @@
+/*===================================================================
+
+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 QmitkMultiLabelSegmentationView_h
+#define QmitkMultiLabelSegmentationView_h
+
+#include
+#include
+
+#include
+#include
+#include "mitkSegmentationInteractor.h"
+
+#include "ui_QmitkMultiLabelSegmentationControls.h"
+
+
+class QmitkRenderWindow;
+
+/**
+ * \ingroup ToolManagerEtAl
+ * \ingroup org_mitk_gui_qt_multilabelsegmentation_internal
+ */
+class QmitkMultiLabelSegmentationView : public QmitkAbstractView,
+ public mitk::IRenderWindowPartListener, public berry::ISizeProvider
+{
+ Q_OBJECT
+
+public:
+
+ static const std::string VIEW_ID;
+
+ QmitkMultiLabelSegmentationView();
+ virtual ~QmitkMultiLabelSegmentationView();
+
+ typedef std::map NodeTagMapType;
+
+ // GUI setup
+ void CreateQtPartControl(QWidget* parent);
+
+ virtual int GetSizeFlags(bool width);
+ virtual int ComputePreferredSize(bool width, int /*availableParallel*/, int /*availablePerpendicular*/, int preferredResult);
+
+protected slots:
+
+ /// \brief reaction to the selection of a new patient (reference) image in the DataStorage combobox
+ void OnReferenceSelectionChanged(const mitk::DataNode* node);
+
+ /// \brief reaction to the selection of a new Segmentation (working) image in the DataStorage combobox
+ void OnSegmentationSelectionChanged(const mitk::DataNode *node);
+
+ /// \brief reaction to ...
+ void OnInterpolationSelectionChanged(int);
+
+ /// \brief reaction to the selection of any 2D segmentation tool
+ void OnManualTool2DSelected(int id);
+
+ /// \brief reaction to button "New Label"
+ void OnNewLabel();
+
+ /// \brief reaction to button "Show Label Table"
+ void OnShowLabelTable(bool value);
+
+ /// \brief reaction to button "New Segmentation Session"
+ void OnNewSegmentationSession();
+
+ /// \brief reaction to signal "goToLabel" from labelset widget
+ void OnGoToLabel(const mitk::Point3D& pos);
+
+ void OnResetView();
+
+ // reaction to the button "Add Layer"
+ void OnAddLayer();
+
+ // reaction to the button "Delete Layer"
+ void OnDeleteLayer();
+
+ // reaction to the button "Previous Layer"
+ void OnPreviousLayer();
+
+ // reaction to the button "Next Layer"
+ void OnNextLayer();
+
+ // reaction to the combobox change "Change Layer"
+ void OnChangeLayer(int);
+
+ // reaction to the button "Deactive Active Tool"
+ void OnDeactivateActiveTool();
+
+ // reaction to the button "Lock exterior"
+ void OnLockExteriorToggled(bool);
+
+protected:
+
+ void OnEstablishLabelSetConnection();
+ void OnLooseLabelSetConnection();
+
+ void SetFocus();
+
+ void UpdateControls();
+
+ void RenderWindowPartActivated(mitk::IRenderWindowPart *renderWindowPart);
+
+ void RenderWindowPartDeactivated(mitk::IRenderWindowPart *renderWindowPart);
+
+ void ResetMouseCursor();
+
+ void SetMouseCursor(const us::ModuleResource, int hotspotX, int hotspotY );
+
+ void InitializeListeners();
+
+ /// \brief Checks if two images have the same size and geometry
+ bool CheckForSameGeometry(const mitk::Image *image1, const mitk::Image *image2) const;
+
+ /// \brief Reimplemented from QmitkAbstractView
+ virtual void NodeAdded(const mitk::DataNode* node);
+
+ /// \brief Reimplemented from QmitkAbstractView
+ virtual void NodeRemoved(const mitk::DataNode* node);
+
+ QString GetLastFileOpenPath();
+
+ void SetLastFileOpenPath(const QString& path);
+
+ // handling of a list of known (organ name, organ color) combination
+ // ATTENTION these methods are defined in QmitkSegmentationOrganNamesHandling.cpp
+// QStringList GetDefaultOrganColorString();
+// void UpdateOrganList(QStringList& organColors, const QString& organname, mitk::Color colorname);
+// void AppendToOrganList(QStringList& organColors, const QString& organname, int r, int g, int b);
+
+ /// \brief the Qt parent of our GUI (NOT of this object)
+ QWidget* m_Parent;
+
+ /// \brief Qt GUI file
+ Ui::QmitkMultiLabelSegmentationControls m_Controls;
+
+ mitk::IRenderWindowPart* m_IRenderWindowPart;
+
+ mitk::ToolManager* m_ToolManager;
+
+ mitk::DataNode::Pointer m_ReferenceNode;
+ mitk::DataNode::Pointer m_WorkingNode;
+
+ mitk::NodePredicateAnd::Pointer m_ReferencePredicate;
+ mitk::NodePredicateAnd::Pointer m_SegmentationPredicate;
+
+ bool m_MouseCursorSet;
+
+ mitk::SegmentationInteractor::Pointer m_Interactor;
+
+ /**
+ * Reference to the service registration of the observer,
+ * it is needed to unregister the observer on unload.
+ */
+ us::ServiceRegistration m_ServiceRegistration;
+
+
+};
+
+#endif // QmitkMultiLabelSegmentationView_h
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkThresholdAction.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkThresholdAction.cpp
new file mode 100644
index 0000000000..7b0547a5e1
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkThresholdAction.cpp
@@ -0,0 +1,117 @@
+/*===================================================================
+
+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 "QmitkThresholdAction.h"
+
+// MITK
+#include
+#include
+#include
+
+// Qt
+#include
+#include
+#include
+#include
+
+using namespace berry;
+using namespace mitk;
+using namespace std;
+
+QmitkThresholdAction::QmitkThresholdAction()
+{
+}
+
+QmitkThresholdAction::~QmitkThresholdAction()
+{
+}
+
+void QmitkThresholdAction::Run(const QList &selectedNodes)
+{
+ m_ThresholdingToolManager = ToolManager::New(m_DataStorage);
+
+ m_ThresholdingToolManager->RegisterClient();
+
+ Tool *binaryThresholdTool = m_ThresholdingToolManager->GetToolById(m_ThresholdingToolManager->GetToolIdByToolType());
+ if (binaryThresholdTool != NULL)
+ {
+ QmitkBinaryThresholdToolGUI *gui = dynamic_cast(binaryThresholdTool->GetGUI("Qmitk", "GUI").GetPointer());
+ if (gui != NULL)
+ {
+ QDialog thresholdingDialog(QApplication::activeWindow(), Qt::Window | Qt::WindowStaysOnTopHint);
+
+ thresholdingDialog.setWindowFlags(thresholdingDialog.windowFlags() & ~Qt::WindowMinimizeButtonHint);
+
+ QDialogButtonBox* buttonBox = new QDialogButtonBox(QDialogButtonBox::Cancel);
+ connect(buttonBox, SIGNAL(rejected()), &thresholdingDialog, SLOT(reject()));
+ connect(gui, SIGNAL(thresholdAccepted()), &thresholdingDialog, SLOT(reject()));
+
+ QVBoxLayout *layout = new QVBoxLayout;
+ layout->setContentsMargins(3, 3, 3, 3);
+
+ gui->SetTool(binaryThresholdTool);
+ gui->setParent(&thresholdingDialog);
+
+ layout->addWidget(gui);
+ layout->addWidget(buttonBox);
+
+ thresholdingDialog.setLayout(layout);
+ thresholdingDialog.setMinimumWidth(350);
+
+ m_SelectedNode = selectedNodes[0];
+ m_ThresholdingToolManager->SetReferenceData(selectedNodes[0]);
+ m_ThresholdingToolManager->ActivateTool(m_ThresholdingToolManager->GetToolIdByToolType());
+
+ m_ThresholdingToolManager->ActiveToolChanged += mitk::MessageDelegate(this, &QmitkThresholdAction::OnThresholdingToolManagerToolModified);
+ thresholdingDialog.exec();
+ m_ThresholdingToolManager->ActiveToolChanged -= mitk::MessageDelegate(this, &QmitkThresholdAction::OnThresholdingToolManagerToolModified);
+
+ m_ThresholdingToolManager->SetReferenceData(NULL);
+ m_ThresholdingToolManager->ActivateTool(-1);
+ m_SelectedNode = 0;
+ }
+ }
+
+ m_ThresholdingToolManager->UnregisterClient();
+}
+
+void QmitkThresholdAction::OnThresholdingToolManagerToolModified()
+{
+ if (m_ThresholdingToolManager.IsNotNull())
+ {
+ if (m_ThresholdingToolManager->GetActiveToolID() < 0)
+ {
+ m_ThresholdingToolManager->SetReferenceData(m_SelectedNode);
+ m_ThresholdingToolManager->ActivateTool(m_ThresholdingToolManager->GetToolIdByToolType());
+ }
+ }
+}
+
+void QmitkThresholdAction::SetDataStorage(DataStorage *dataStorage)
+{
+ m_DataStorage = dataStorage;
+}
+
+void QmitkThresholdAction::SetSmoothed(bool)
+{
+}
+
+void QmitkThresholdAction::SetDecimated(bool)
+{
+}
+
+void QmitkThresholdAction::SetFunctionality(QtViewPart* /*functionality*/)
+{
+}
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkThresholdAction.h b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkThresholdAction.h
new file mode 100644
index 0000000000..53f3169acd
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/QmitkThresholdAction.h
@@ -0,0 +1,57 @@
+/*===================================================================
+
+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 QMITKTHRESHOLDACTION_H
+#define QMITKTHRESHOLDACTION_H
+
+#include
+
+// Parent classes
+#include
+#include
+
+// Data members
+#include
+#include
+
+
+class MITK_QT_SEGMENTATION QmitkThresholdAction : public QObject, public mitk::IContextMenuAction
+{
+ Q_OBJECT
+ Q_INTERFACES(mitk::IContextMenuAction)
+
+public:
+ QmitkThresholdAction();
+ ~QmitkThresholdAction();
+
+ // IContextMenuAction
+ void Run(const QList &selectedNodes);
+ void SetDataStorage(mitk::DataStorage *dataStorage);
+ void SetSmoothed(bool smoothed);
+ void SetDecimated(bool decimated);
+ void SetFunctionality(berry::QtViewPart *functionality);
+
+ void OnThresholdingToolManagerToolModified();
+
+private:
+ QmitkThresholdAction(const QmitkThresholdAction &);
+ QmitkThresholdAction & operator=(const QmitkThresholdAction &);
+
+ mitk::DataNode::Pointer m_SelectedNode;
+ mitk::DataStorage::Pointer m_DataStorage;
+ mitk::ToolManager::Pointer m_ThresholdingToolManager;
+};
+
+#endif
diff --git a/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/SegmentationUtilities/BooleanOperations/QmitkBooleanOperationsWidget.cpp b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/SegmentationUtilities/BooleanOperations/QmitkBooleanOperationsWidget.cpp
new file mode 100644
index 0000000000..ce40d43b5c
--- /dev/null
+++ b/Plugins/org.mitk.gui.qt.multilabelsegmentation/src/internal/SegmentationUtilities/BooleanOperations/QmitkBooleanOperationsWidget.cpp
@@ -0,0 +1,144 @@
+/*===================================================================
+
+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 "QmitkBooleanOperationsWidget.h"
+#include "../../Common/QmitkDataSelectionWidget.h"
+#include
+#include
+#include
+
+static const char* const HelpText = "Select two different masks above";
+
+std::string GetPrefix(mitk::BooleanOperation::Type type)
+{
+ switch (type)
+ {
+ case mitk::BooleanOperation::Difference:
+ return "DifferenceFrom_";
+
+ case mitk::BooleanOperation::Intersection:
+ return "IntersectionWith_";
+
+ case mitk::BooleanOperation::Union:
+ return "UnionWith_";
+
+ default:
+ assert(false && "Unknown boolean operation type");
+ return "UNKNOWN_BOOLEAN_OPERATION_WITH_";
+ }
+}
+
+void AddToDataStorage(mitk::DataStorage::Pointer dataStorage, mitk::Image::Pointer segmentation, const std::string& name, mitk::DataNode::Pointer parent = NULL)
+{
+ mitk::DataNode::Pointer dataNode = mitk::DataNode::New();
+
+ dataNode->SetBoolProperty("binary", true);
+ dataNode->SetName(name);
+ dataNode->SetData(segmentation);
+
+ dataStorage->Add(dataNode, parent);
+}
+
+QmitkBooleanOperationsWidget::QmitkBooleanOperationsWidget(mitk::SliceNavigationController* timeNavigationController, QWidget* parent)
+ : QmitkSegmentationUtilityWidget(timeNavigationController, parent)
+{
+ m_Controls.setupUi(this);
+
+ m_Controls.dataSelectionWidget->AddDataStorageComboBox(QmitkDataSelectionWidget::MaskPredicate);
+ m_Controls.dataSelectionWidget->AddDataStorageComboBox(QmitkDataSelectionWidget::MaskPredicate);
+
+ m_Controls.dataSelectionWidget->SetHelpText(HelpText);
+
+ connect(m_Controls.dataSelectionWidget, SIGNAL(SelectionChanged(unsigned int, const mitk::DataNode*)), this, SLOT(OnSelectionChanged(unsigned int, const mitk::DataNode*)));
+ connect(m_Controls.differenceButton, SIGNAL(clicked()), this, SLOT(OnDifferenceButtonClicked()));
+ connect(m_Controls.intersectionButton, SIGNAL(clicked()), this, SLOT(OnIntersectionButtonClicked()));
+ connect(m_Controls.unionButton, SIGNAL(clicked()), this, SLOT(OnUnionButtonClicked()));
+}
+
+QmitkBooleanOperationsWidget::~QmitkBooleanOperationsWidget()
+{
+}
+
+void QmitkBooleanOperationsWidget::OnSelectionChanged(unsigned int index, const mitk::DataNode* selection)
+{
+ QmitkDataSelectionWidget* dataSelectionWidget = m_Controls.dataSelectionWidget;
+
+ mitk::DataNode::Pointer node0 = dataSelectionWidget->GetSelection(0);
+ mitk::DataNode::Pointer node1 = dataSelectionWidget->GetSelection(1);
+
+ if (node0.IsNotNull() && node1.IsNotNull() && node0 != node1)
+ {
+ dataSelectionWidget->SetHelpText("");
+ this->EnableButtons();
+ }
+ else
+ {
+ dataSelectionWidget->SetHelpText(HelpText);
+ this->EnableButtons(false);
+ }
+}
+
+void QmitkBooleanOperationsWidget::EnableButtons(bool enable)
+{
+ m_Controls.differenceButton->setEnabled(enable);
+ m_Controls.intersectionButton->setEnabled(enable);
+ m_Controls.unionButton->setEnabled(enable);
+}
+
+void QmitkBooleanOperationsWidget::OnDifferenceButtonClicked()
+{
+ this->DoBooleanOperation(mitk::BooleanOperation::Difference);
+}
+
+void QmitkBooleanOperationsWidget::OnIntersectionButtonClicked()
+{
+ this->DoBooleanOperation(mitk::BooleanOperation::Intersection);
+}
+
+void QmitkBooleanOperationsWidget::OnUnionButtonClicked()
+{
+ this->DoBooleanOperation(mitk::BooleanOperation::Union);
+}
+
+void QmitkBooleanOperationsWidget::DoBooleanOperation(mitk::BooleanOperation::Type type)
+{
+ mitk::SliceNavigationController* timeNavigationController = this->GetTimeNavigationController();
+ assert(timeNavigationController != NULL);
+
+ mitk::Image::Pointer segmentation0 = static_cast