diff --git a/Modules/IGT/Rendering/mitkNavigationDataObjectVisualizationFilter.cpp b/Modules/IGT/Rendering/mitkNavigationDataObjectVisualizationFilter.cpp index d09028d2fb..5585f88a31 100644 --- a/Modules/IGT/Rendering/mitkNavigationDataObjectVisualizationFilter.cpp +++ b/Modules/IGT/Rendering/mitkNavigationDataObjectVisualizationFilter.cpp @@ -1,247 +1,260 @@ /*=================================================================== 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 "mitkNavigationDataObjectVisualizationFilter.h" #include "mitkDataStorage.h" - +#include mitk::NavigationDataObjectVisualizationFilter::NavigationDataObjectVisualizationFilter() -: NavigationDataToNavigationDataFilter(), -m_RepresentationList(), m_TransformPosition(), m_TransformOrientation(), m_RotationMode(RotationStandard) + : NavigationDataToNavigationDataFilter(), + m_RepresentationVectorMap(), + m_TransformPosition(), + m_TransformOrientation(), + m_RotationMode(RotationStandard) { - } - mitk::NavigationDataObjectVisualizationFilter::~NavigationDataObjectVisualizationFilter() { - m_RepresentationList.clear(); + m_RepresentationVectorMap.clear(); m_OffsetList.clear(); } +mitk::BaseData::Pointer mitk::NavigationDataObjectVisualizationFilter::GetRepresentationObject(unsigned int idx) const +{ + auto iter = m_RepresentationVectorMap.find(idx); + if (iter != m_RepresentationVectorMap.end()) + return iter->second.at(0); + + return nullptr; +} -const mitk::BaseData* mitk::NavigationDataObjectVisualizationFilter::GetRepresentationObject(unsigned int idx) +std::vector mitk::NavigationDataObjectVisualizationFilter::GetAllRepresentationObjects(unsigned int idx) const { - RepresentationPointerMap::const_iterator iter = m_RepresentationList.find(idx); - if (iter != m_RepresentationList.end()) + RepresentationVectorPointerMap::const_iterator iter = m_RepresentationVectorMap.find(idx); + if (iter != m_RepresentationVectorMap.end()) return iter->second; - return nullptr; + std::vector empty; + return empty; } mitk::AffineTransform3D::Pointer mitk::NavigationDataObjectVisualizationFilter::GetOffset(int index) { OffsetPointerMap::const_iterator iter = m_OffsetList.find(index); if (iter != m_OffsetList.end()) return iter->second; return nullptr; } +void mitk::NavigationDataObjectVisualizationFilter::SetRepresentationObject(unsigned int idx, BaseData::Pointer data) +{ + std::vector dataVector; + dataVector.push_back(data); + SetRepresentationObjects(idx, dataVector); +} -void mitk::NavigationDataObjectVisualizationFilter::SetRepresentationObject(unsigned int idx, BaseData* data) +void mitk::NavigationDataObjectVisualizationFilter::SetRepresentationObjects(unsigned int idx, const std::vector &data) { - m_RepresentationList[idx] = RepresentationPointer(data); + m_RepresentationVectorMap[idx] = data; } void mitk::NavigationDataObjectVisualizationFilter::SetOffset(int index, mitk::AffineTransform3D::Pointer offset) { -m_OffsetList[index] = offset; + m_OffsetList[index] = offset; } - void mitk::NavigationDataObjectVisualizationFilter::SetRotationMode(RotationMode r) { m_RotationMode = r; } - void mitk::NavigationDataObjectVisualizationFilter::GenerateData() { /*get each input, lookup the associated BaseData and transfer the data*/ - DataObjectPointerArray inputs = this->GetInputs(); //get all inputs - for (unsigned int index=0; index < inputs.size(); index++) + DataObjectPointerArray inputs = this->GetInputs(); // get all inputs + for (unsigned int index = 0; index < inputs.size(); index++) { - //get the needed variables - const mitk::NavigationData* nd = this->GetInput(index); + // get the needed variables + const mitk::NavigationData *nd = this->GetInput(index); assert(nd); - mitk::NavigationData* output = this->GetOutput(index); + mitk::NavigationData *output = this->GetOutput(index); assert(output); - //check if the data is valid + // check if the data is valid if (!nd->IsDataValid()) { output->SetDataValid(false); continue; } output->Graft(nd); // copy all information from input to output - const mitk::BaseData* data = this->GetRepresentationObject(index); - if (data == nullptr) - { - MITK_WARN << "No BaseData associated with input " << index; - continue; - } - //get the transform from data - mitk::AffineTransform3D::Pointer affineTransform = data->GetGeometry()->GetIndexToWorldTransform(); - if (affineTransform.IsNull()) + const std::vector data = + this->GetAllRepresentationObjects(index); + + for (int dataIdx = 0; dataIdx < data.size(); dataIdx++) { - MITK_WARN << "AffineTransform IndexToWorldTransform not initialized!"; - continue; - } + if (data.at(dataIdx) == nullptr) + { + MITK_WARN << "No BaseData associated with input " << index; + continue; + } + + // get the transform from data + mitk::AffineTransform3D::Pointer affineTransform = data.at(dataIdx)->GetGeometry()->GetIndexToWorldTransform(); + if (affineTransform.IsNull()) + { + MITK_WARN << "AffineTransform IndexToWorldTransform not initialized!"; + continue; + } - //check for offset - mitk::AffineTransform3D::Pointer offset = this->GetOffset(index); + // check for offset + mitk::AffineTransform3D::Pointer offset = this->GetOffset(index); - //store the current scaling to set it after transformation - mitk::Vector3D spacing = data->GetGeometry()->GetSpacing(); - //clear spacing of data to be able to set it again afterwards - ScalarType scale[] = {1.0, 1.0, 1.0}; - data->GetGeometry()->SetSpacing(scale); + // store the current scaling to set it after transformation + mitk::Vector3D spacing = data.at(dataIdx)->GetGeometry()->GetSpacing(); + // clear spacing of data to be able to set it again afterwards + ScalarType scale[] = {1.0, 1.0, 1.0}; + data.at(dataIdx)->GetGeometry()->SetSpacing(scale); - /*now bring quaternion to affineTransform by using vnl_Quaternion*/ - affineTransform->SetIdentity(); + /*now bring quaternion to affineTransform by using vnl_Quaternion*/ + affineTransform->SetIdentity(); - if (this->GetTransformOrientation(index) == true) - { - mitk::NavigationData::OrientationType orientation = nd->GetOrientation(); + if (this->GetTransformOrientation(index) == true) + { + mitk::NavigationData::OrientationType orientation = nd->GetOrientation(); - /* because of an itk bug, the transform can not be calculated with float data type. - To use it in the mitk geometry classes, it has to be transfered to mitk::ScalarType which is float */ - static AffineTransform3D::MatrixType m; + /* because of an itk bug, the transform can not be calculated with float data type. + To use it in the mitk geometry classes, it has to be transfered to mitk::ScalarType which is float */ + static AffineTransform3D::MatrixType m; - //convert quaternion to rotation matrix depending on the rotation mode - if(m_RotationMode == RotationStandard) + // convert quaternion to rotation matrix depending on the rotation mode + if (m_RotationMode == RotationStandard) { - //calculate the transform from the quaternions - static itk::QuaternionRigidTransform::Pointer quatTransform = itk::QuaternionRigidTransform::New(); - // convert mitk::ScalarType quaternion to double quaternion because of itk bug - vnl_quaternion doubleQuaternion(orientation.x(), orientation.y(), orientation.z(), orientation.r()); - quatTransform->SetIdentity(); - quatTransform->SetRotation(doubleQuaternion); - quatTransform->Modified(); - mitk::TransferMatrix(quatTransform->GetMatrix(), m); + // calculate the transform from the quaternions + static itk::QuaternionRigidTransform::Pointer quatTransform = + itk::QuaternionRigidTransform::New(); + // convert mitk::ScalarType quaternion to double quaternion because of itk bug + vnl_quaternion doubleQuaternion(orientation.x(), orientation.y(), orientation.z(), orientation.r()); + quatTransform->SetIdentity(); + quatTransform->SetRotation(doubleQuaternion); + quatTransform->Modified(); + mitk::TransferMatrix(quatTransform->GetMatrix(), m); } - else if(m_RotationMode == RotationTransposed) + else if (m_RotationMode == RotationTransposed) { - vnl_matrix_fixed rot = orientation.rotation_matrix_transpose(); - for(int i=0; i<3; i++) for (int j=0; j<3; j++) m[i][j] = rot[i][j]; + vnl_matrix_fixed rot = orientation.rotation_matrix_transpose(); + for (int i = 0; i < 3; i++) + for (int j = 0; j < 3; j++) + m[i][j] = rot[i][j]; } - affineTransform->SetMatrix(m); - - } - if (this->GetTransformPosition(index) == true) - { - ///*set the offset by convert from itkPoint to itkVector and setting offset of transform*/ - mitk::Vector3D pos; - pos.SetVnlVector(nd->GetPosition().GetVnlVector()); - affineTransform->SetOffset(pos); - } - affineTransform->Modified(); - + affineTransform->SetMatrix(m); + } + if (this->GetTransformPosition(index) == true) + { + ///*set the offset by convert from itkPoint to itkVector and setting offset of transform*/ + mitk::Vector3D pos; + pos.SetVnlVector(nd->GetPosition().GetVnlVector()); + affineTransform->SetOffset(pos); + } + affineTransform->Modified(); - //set the transform to data - if(offset.IsNotNull()) //first use offset if there is one. + // set the transform to data + if (offset.IsNotNull()) // first use offset if there is one. { - mitk::AffineTransform3D::Pointer overallTransform = mitk::AffineTransform3D::New(); - overallTransform->SetIdentity(); - overallTransform->Compose(offset); - overallTransform->Compose(affineTransform); - data->GetGeometry()->SetIndexToWorldTransform(overallTransform); + mitk::AffineTransform3D::Pointer overallTransform = mitk::AffineTransform3D::New(); + overallTransform->SetIdentity(); + overallTransform->Compose(offset); + overallTransform->Compose(affineTransform); + data.at(dataIdx)->GetGeometry()->SetIndexToWorldTransform(overallTransform); } - else + else { - data->GetGeometry()->SetIndexToWorldTransform(affineTransform); + data.at(dataIdx)->GetGeometry()->SetIndexToWorldTransform(affineTransform); } - //set the original spacing to keep scaling of the geometrical object - data->GetGeometry()->SetSpacing(spacing); - data->GetGeometry()->Modified(); - data->Modified(); - output->SetDataValid(true); // operation was successful, therefore data of output is valid. + // set the original spacing to keep scaling of the geometrical object + data.at(dataIdx)->GetGeometry()->SetSpacing(spacing); + data.at(dataIdx)->GetGeometry()->Modified(); + data.at(dataIdx)->Modified(); + output->SetDataValid(true); // operation was successful, therefore data of output is valid. + } } } - -void mitk::NavigationDataObjectVisualizationFilter::SetTransformPosition( unsigned int index, bool applyTransform ) +void mitk::NavigationDataObjectVisualizationFilter::SetTransformPosition(unsigned int index, bool applyTransform) { itkDebugMacro("setting TransformPosition for index " << index << " to " << applyTransform); BooleanInputMap::const_iterator it = this->m_TransformPosition.find(index); if ((it != this->m_TransformPosition.end()) && (it->second == applyTransform)) return; this->m_TransformPosition[index] = applyTransform; this->Modified(); } - -bool mitk::NavigationDataObjectVisualizationFilter::GetTransformPosition( unsigned int index ) const +bool mitk::NavigationDataObjectVisualizationFilter::GetTransformPosition(unsigned int index) const { itkDebugMacro("returning TransformPosition for index " << index); BooleanInputMap::const_iterator it = this->m_TransformPosition.find(index); if (it != this->m_TransformPosition.end()) return it->second; else return true; // default to true } - -void mitk::NavigationDataObjectVisualizationFilter::TransformPositionOn( unsigned int index ) +void mitk::NavigationDataObjectVisualizationFilter::TransformPositionOn(unsigned int index) { this->SetTransformPosition(index, true); } - -void mitk::NavigationDataObjectVisualizationFilter::TransformPositionOff( unsigned int index ) +void mitk::NavigationDataObjectVisualizationFilter::TransformPositionOff(unsigned int index) { this->SetTransformPosition(index, false); } - -void mitk::NavigationDataObjectVisualizationFilter::SetTransformOrientation( unsigned int index, bool applyTransform ) +void mitk::NavigationDataObjectVisualizationFilter::SetTransformOrientation(unsigned int index, bool applyTransform) { itkDebugMacro("setting TransformOrientation for index " << index << " to " << applyTransform); BooleanInputMap::const_iterator it = this->m_TransformOrientation.find(index); if ((it != this->m_TransformOrientation.end()) && (it->second == applyTransform)) return; this->m_TransformOrientation[index] = applyTransform; - this->Modified(); \ + this->Modified(); } - -bool mitk::NavigationDataObjectVisualizationFilter::GetTransformOrientation( unsigned int index ) const +bool mitk::NavigationDataObjectVisualizationFilter::GetTransformOrientation(unsigned int index) const { itkDebugMacro("returning TransformOrientation for index " << index); BooleanInputMap::const_iterator it = this->m_TransformOrientation.find(index); if (it != this->m_TransformOrientation.end()) return it->second; else return true; // default to true } - -void mitk::NavigationDataObjectVisualizationFilter::TransformOrientationOn( unsigned int index ) +void mitk::NavigationDataObjectVisualizationFilter::TransformOrientationOn(unsigned int index) { this->SetTransformOrientation(index, true); } - -void mitk::NavigationDataObjectVisualizationFilter::TransformOrientationOff( unsigned int index ) +void mitk::NavigationDataObjectVisualizationFilter::TransformOrientationOff(unsigned int index) { this->SetTransformOrientation(index, false); } diff --git a/Modules/IGT/Rendering/mitkNavigationDataObjectVisualizationFilter.h b/Modules/IGT/Rendering/mitkNavigationDataObjectVisualizationFilter.h index cc002dd6c3..11aa495e59 100644 --- a/Modules/IGT/Rendering/mitkNavigationDataObjectVisualizationFilter.h +++ b/Modules/IGT/Rendering/mitkNavigationDataObjectVisualizationFilter.h @@ -1,156 +1,184 @@ /*=================================================================== 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 MITKNAVIGATIONDATAOBJECTVISUALIZATIONFILTER_H_HEADER_INCLUDED_ #define MITKNAVIGATIONDATAOBJECTVISUALIZATIONFILTER_H_HEADER_INCLUDED_ #include "mitkNavigationDataToNavigationDataFilter.h" #include "mitkNavigationData.h" #include "mitkBaseData.h" namespace mitk { /** * \brief Class that reads NavigationData from input and transfers the information to the geometry of the associated BaseData * * Derived from NavigationDataToNavigationDataFilter * * \ingroup IGT */ class MITKIGT_EXPORT NavigationDataObjectVisualizationFilter : public NavigationDataToNavigationDataFilter { public: mitkClassMacro(NavigationDataObjectVisualizationFilter, NavigationDataToNavigationDataFilter); itkFactorylessNewMacro(Self) itkCloneMacro(Self) /** Defines the rotation modes of this tracking device which results in different representations * of quaternions. * * - Standard: normal representation, rawdata from the device is not changed (DEFAULT) * * - Transposed: the rotation is stored transposed, which is (by mistake!) expected by some older MITK classes due * to an ambigious method naming in VNL. * * CAUTION: The rotation mode can only be changed for backward compatibility of old WRONG code. * PLEASE DO NOT CHANGE THE ROTATION MODE UNLESS YOU ARE KNOWING EXACTLY WHAT YOU ARE DOING! * * use SetRotationMode to change the mode. */ enum RotationMode {RotationStandard, RotationTransposed}; /** * \brief Smart Pointer type to a BaseData. */ - typedef BaseData::ConstPointer RepresentationPointer; + typedef BaseData::Pointer RepresentationPointer; /** - * \brief STL map of index to BaseData . Using map to be able to set non continuous indices - */ + * \brief STL map of index to BaseData . Using map to be able to set non continuous indices + */ typedef std::map RepresentationPointerMap; + /** + * \brief STL vector map of index to BaseData . Using map to be able to set non continuous indices + */ + typedef std::map> RepresentationVectorPointerMap; + /** * \brief Size type of an std::vector */ typedef RepresentationPointerMap::size_type RepresentationPointerMapSizeType; + /** + * \brief Size type of an std::vector + */ + typedef RepresentationVectorPointerMap::size_type RepresentationPointerMapSizeType; + /** * \brief Set the representation object of the input * * \param data The BaseData to be associated to the index * \param index the index with which data will be associated */ - void SetRepresentationObject(unsigned int index, BaseData* data); + void SetRepresentationObject(unsigned int index, BaseData::Pointer data); + /** + * \brief Set the representation objects vector of the input + * + * \param data The BaseData vector to be associated to the index + * \param index the index with which data will be associated + */ + void SetRepresentationObjects(unsigned int index, const std::vector &data); + /** * \brief Get the representation object associated with the index idx * * \param idx the corresponding input number with which the BaseData is associated * \return Returns the desired BaseData if it exists for the given input; Returns nullptr * if no BaseData was found. */ - const BaseData* GetRepresentationObject(unsigned int idx); + BaseData::Pointer GetRepresentationObject(unsigned int idx) const; + + /** + * \brief Get all the representation objects associated with the index idx + * + * \param idx the corresponding input number with which the BaseData is associated + * \return Returns the desired BaseData if it exists for the given input; Returns nullptr + * if no BaseData was found. + */ + std::vector GetAllRepresentationObjects(unsigned int idx) const; virtual void SetTransformPosition(unsigned int index, bool applyTransform); ///< if set to true, the filter will use the position part of the input navigation data at the given index to transform the representation object. If set to false, it will not. If no value is set, it defaults to true. virtual bool GetTransformPosition(unsigned int index) const; ///< returns whether position part of the input navigation data at the given index is used for the transformation of the representation object. virtual void TransformPositionOn(unsigned int index); ///< sets the TransformPosition flag to true for the given index virtual void TransformPositionOff(unsigned int index); ///< sets the TransformPosition flag to false for the given index virtual void SetTransformOrientation(unsigned int index, bool applyTransform); ///< if set to true, the filter will use the orientation part of the input navigation data at the given index to transform the representation object. If set to false, it will not. If no value is set, it defaults to true. virtual bool GetTransformOrientation(unsigned int index) const; ///< returns whether orientation part of the input navigation data at the given index is used for the transformation of the representation object. virtual void TransformOrientationOn(unsigned int index); ///< sets the TransformOrientation flag to true for the given index virtual void TransformOrientationOff(unsigned int index); ///< sets the TransformOrientation flag to false for the given index /** @brief Defines an offset for a representation object. This offset is applied before the object is visualized. * If no offset is given, no offset will be used. To deactivate the offset just set it to nullptr. The offset is deactivated by default. * @param offset The new offset which will be set. Set to nullptr to deactivate the offset. */ void SetOffset(int index, mitk::AffineTransform3D::Pointer offset); /** Sets the rotation mode of this class. See documentation of enum RotationMode for details * on the different modes. * CAUTION: The rotation mode can only be changed for backward compatibility of old WRONG code. * PLEASE DO NOT CHANGE THE ROTATION MODE UNLESS YOU ARE KNOWING EXACTLY WHAT YOU ARE DOING! */ virtual void SetRotationMode(RotationMode r); /** @return Returns the offset of a represenation object. Returns nullptr if there is no offset. */ mitk::AffineTransform3D::Pointer GetOffset(int index); /** *\brief Get the number of added BaseData associated to NavigationData * \return Returns the size of the internal map */ RepresentationPointerMapSizeType GetNumberOfToolRepresentations() const { - return m_RepresentationList.size(); + return m_RepresentationVectorMap.size(); } /* * \brief Transfer the information from the input to the associated BaseData */ void GenerateData() override; protected: typedef std::map BooleanInputMap; typedef std::map OffsetPointerMap; /** * \brief Constructor **/ NavigationDataObjectVisualizationFilter(); /** * \brief Destructor **/ ~NavigationDataObjectVisualizationFilter() override; /** * \brief An array of the BaseData which represent the tools. */ - RepresentationPointerMap m_RepresentationList; + + RepresentationVectorPointerMap m_RepresentationVectorMap; BooleanInputMap m_TransformPosition; ///< if set to true, the filter will use the position part of the input navigation data at the given index for the calculation of the transform. If no entry for the index exists, it defaults to true. BooleanInputMap m_TransformOrientation; ///< if set to true, the filter will use the orientation part of the input navigation data at the given index for the calculation of the transform. If no entry for the index exists, it defaults to true. OffsetPointerMap m_OffsetList; private: RotationMode m_RotationMode; ///< defines the rotation mode Standard or Transposed, Standard is default }; } // namespace mitk #endif /* MITKNAVIGATIONDATAOBJECTVISUALIZATIONFILTER_H_HEADER_INCLUDED_ */