diff --git a/Core/Code/IO/mitkPixelType.cpp b/Core/Code/IO/mitkPixelType.cpp index 997c705431..e719ee3853 100644 --- a/Core/Code/IO/mitkPixelType.cpp +++ b/Core/Code/IO/mitkPixelType.cpp @@ -1,149 +1,175 @@ /*=================================================================== 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 "mitkPixelType.h" #include #include #include #include #include #include "itkDiffusionTensor3D.h" #define HUNDRED_VECS(HUN) \ TEN_VECS(HUN) \ TEN_VECS(HUN+10) \ TEN_VECS(HUN+20) \ TEN_VECS(HUN+30) \ TEN_VECS(HUN+40) \ TEN_VECS(HUN+50) \ TEN_VECS(HUN+60) \ TEN_VECS(HUN+70) \ TEN_VECS(HUN+80) \ TEN_VECS(HUN+90) \ #define TEN_VECS(TEN) \ if(false){} \ N_VEC(TEN+ 1) \ N_VEC(TEN+ 2) \ N_VEC(TEN+ 3) \ N_VEC(TEN+ 4) \ N_VEC(TEN+ 5) \ N_VEC(TEN+ 6) \ N_VEC(TEN+ 7) \ N_VEC(TEN+ 8) \ N_VEC(TEN+ 9) \ N_VEC(TEN+10) \ #define N_VEC(N_DIRS) \ _N_VEC(N_DIRS,double) \ _N_VEC(N_DIRS,float) \ _N_VEC(N_DIRS,short) \ #define _N_VEC(N_DIRS,PIXTYPE) \ else if ( *m_TypeId == typeid( itk::Vector )) \ { \ found = true; \ m_TypeId = & typeid( PIXTYPE ); \ m_NumberOfComponents *= N_DIRS; \ m_Type = mitkIpPicFloat; \ m_Bpe = sizeof(PIXTYPE) * 8 * m_NumberOfComponents; \ m_ItkTypeId = &typeid( itk::Vector ); \ } \ + +const std::type_info &mitk::GetPixelTypeFromITKImageIO(const itk::ImageIOBase::Pointer imageIO) +{ + // return the component type for scalar types + if( imageIO->GetNumberOfComponents() == 1) + { + return imageIO->GetComponentTypeInfo(); + } + else + { + itk::ImageIOBase::IOPixelType ptype = imageIO->GetPixelType(); + + switch(ptype) + { + case itk::ImageIOBase::RGBA: + return typeid( itk::RGBAPixel< unsigned char> ); + break; + case itk::ImageIOBase::RGB: + return typeid( itk::RGBPixel< unsigned char>); + break; + default: + return imageIO->GetComponentTypeInfo(); + } + } +} + mitk::PixelType::PixelType( const mitk::PixelType& other ) : m_ComponentType( other.m_ComponentType ), m_PixelType( other.m_PixelType), m_ComponentTypeName( other.m_ComponentTypeName ), m_PixelTypeName( other.m_PixelTypeName ), m_NumberOfComponents( other.m_NumberOfComponents ), m_BytesPerComponent( other.m_BytesPerComponent ) { } bool mitk::PixelType::operator==(const mitk::PixelType& rhs) const { MITK_DEBUG << "operator==" << std::endl; MITK_DEBUG << "m_NumberOfComponents = " << m_NumberOfComponents << " " << rhs.m_NumberOfComponents << std::endl; MITK_DEBUG << "m_BytesPerComponent = " << m_BytesPerComponent << " " << rhs.m_BytesPerComponent << std::endl; return ( this->m_PixelType == rhs.m_PixelType && this->m_ComponentType == rhs.m_ComponentType && this->m_NumberOfComponents == rhs.m_NumberOfComponents && this->m_BytesPerComponent == rhs.m_BytesPerComponent ); } bool mitk::PixelType::operator ==(const std::type_info& typeId) const { if( m_NumberOfComponents ==1 ) return (m_ComponentType == typeId); else return (m_PixelType == typeId); } bool mitk::PixelType::operator!=(const mitk::PixelType& rhs) const { return !(this->operator==(rhs)); } bool mitk::PixelType::operator!=(const std::type_info& typeId) const { return !(this->operator==(typeId)); } #define SET_ITK_TYPE_ID(anItkIoPixelType_test, numberOfComponents_test, ITK_TYPE) \ if ( (itk::ImageIOBase::anItkIoPixelType_test == anItkIoPixelType ) && \ (numberOfComponents_test == m_NumberOfComponents) \ ) \ { * \ m_ItkTypeId = &typeid(ITK_TYPE); \ } #define SET_TYPE(TYPE, IPPIC_TYPE) \ if ( *m_TypeId == typeid( TYPE ) ) \ { \ m_Type = IPPIC_TYPE; \ m_Bpe = sizeof(TYPE) * 8 * m_NumberOfComponents; \ \ typedef itk::Vector Vector3Type; \ typedef itk::CovariantVector CovariantVector3Type; \ typedef itk::Point Point3Type; \ typedef itk::Vector Vector2Type; \ typedef itk::CovariantVector CovariantVector2Type; \ typedef itk::Point Point2Type; \ \ SET_ITK_TYPE_ID(UNKNOWNPIXELTYPE, 1, TYPE ) else \ SET_ITK_TYPE_ID(SCALAR, 1, TYPE ) else \ \ SET_ITK_TYPE_ID(VECTOR, 2, Vector2Type ) else \ SET_ITK_TYPE_ID(COVARIANTVECTOR, 2, CovariantVector2Type ) else \ SET_ITK_TYPE_ID(POINT, 2, Point2Type ) else \ \ SET_ITK_TYPE_ID(RGB, 3, itk::RGBPixel ) else \ /*SET_ITK_TYPE_ID(DIFFUSIONTENSOR3D, 6, itk::DiffusionTensor3D ) else */ \ SET_ITK_TYPE_ID(VECTOR, 3, Vector3Type ) else \ SET_ITK_TYPE_ID(COVARIANTVECTOR, 3, CovariantVector3Type ) else \ SET_ITK_TYPE_ID(POINT, 3, Point3Type ) else \ \ SET_ITK_TYPE_ID(RGBA, 4, itk::RGBAPixel ) else \ { \ } \ } \ else diff --git a/Core/Code/IO/mitkPixelType.h b/Core/Code/IO/mitkPixelType.h index 8d4c2aae3c..8fbc3111a2 100644 --- a/Core/Code/IO/mitkPixelType.h +++ b/Core/Code/IO/mitkPixelType.h @@ -1,258 +1,270 @@ /*=================================================================== 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 PIXELTYPE_H_HEADER_INCLUDED_C1EBF565 #define PIXELTYPE_H_HEADER_INCLUDED_C1EBF565 #include #include "mitkCommon.h" #include "mitkPixelTypeTraits.h" #include #include #include #include namespace mitk { template< typename ComponentT> const char* ComponentTypeToString() { return typeid(ComponentT).name(); } template const char* PixelTypeToString() { return typeid(PixelT).name(); } //##Documentation //## @brief Class for defining the data type of pixels //## //## To obtain additional type information not provided by this class //## itk::ImageIOBase can be used by passing the return value of //## PixelType::GetItkTypeId() to itk::ImageIOBase::SetPixelTypeInfo //## and using the itk::ImageIOBase methods GetComponentType, //## GetComponentTypeAsString, GetPixelType, GetPixelTypeAsString. //## @ingroup Data class MITK_CORE_EXPORT PixelType { public: typedef itk::ImageIOBase::IOPixelType ItkIOPixelType; PixelType(const mitk::PixelType & aPixelType); /** \brief Get the \a type_info of the scalar (!) type. Each element * may contain m_NumberOfComponents (more than one) of these scalars. * */ inline const std::type_info& GetTypeId() const { return m_ComponentType; } /** \brief Get the \a type_info of the whole pixel type. * * If you want the type information for the component of a compound type use the * GetTypeId() method */ inline const std::type_info& GetPixelTypeId() const { return m_PixelType; } /** \brief Returns a string containing the ItkTypeName, * * The string provides the same information as GetPixelTypeId.name() */ std::string GetItkTypeAsString() const { return m_PixelTypeName; } /** \brief Returns a string containing the type name of the component, * * The string provides the same information as GetTypeId.name() */ std::string GetComponentTypeAsString() const { return m_ComponentTypeName; } /** \brief Get size of the PixelType in bytes * * A RGBA PixelType of floats will return 4 * sizeof(float) */ size_t GetSize() const { return (m_NumberOfComponents * m_BytesPerComponent); } /** \brief Get the number of bits per element (of an * element) * * A vector of double with three components will return * 8*sizeof(double)*3. * \sa GetBitsPerComponent * \sa GetItkTypeId * \sa GetTypeId */ size_t GetBpe() const { return this->GetSize() * 8; } /** \brief Get the number of components of which each element consists * * Each pixel can consist of multiple components, e.g. RGB. */ inline size_t GetNumberOfComponents() const { return m_NumberOfComponents; } /** \brief Get the number of bits per components * \sa GetBitsPerComponent */ inline size_t GetBitsPerComponent() const { return m_BytesPerComponent * 8; } bool operator==(const PixelType& rhs) const; bool operator!=(const PixelType& rhs) const; bool operator==(const std::type_info& typeId) const; bool operator!=(const std::type_info& typeId) const; ~PixelType() {} private: friend class ItkImageFileReader; friend class NrrdTbssImageReader; friend class NrrdTbssRoiImageReader; template< typename ComponentT, typename PixelT, std::size_t numberOfComponents > friend PixelType MakePixelType(); template< typename ItkImageType > friend PixelType MakePixelType(); PixelType( const std::type_info& componentType, const std::type_info& pixelType, std::size_t bytesPerComponent, std::size_t numberOfComponents, const char* componentTypeName = 0, const char* pixelTypeName = 0 ) : m_ComponentType( componentType ), m_PixelType( pixelType ), m_NumberOfComponents( numberOfComponents ), m_BytesPerComponent( bytesPerComponent ) { if(componentTypeName) m_ComponentTypeName = componentTypeName; else m_ComponentTypeName = componentType.name(); if(pixelTypeName) m_PixelTypeName = pixelTypeName; else m_PixelTypeName = pixelType.name(); } // default constructor is disabled on purpose PixelType(void); // assignment operator declared private on purpose PixelType& operator=(const PixelType& other); /** \brief the \a type_info of the scalar (!) component type. Each element may contain m_NumberOfComponents (more than one) of these scalars. */ const std::type_info& m_ComponentType; const std::type_info& m_PixelType; std::string m_ComponentTypeName; std::string m_PixelTypeName; std::size_t m_NumberOfComponents; std::size_t m_BytesPerComponent; }; /** \brief A template method for creating a pixel type. */ template< typename ComponentT, typename PixelT, std::size_t numOfComponents > PixelType MakePixelType() { typedef itk::Image< PixelT, numOfComponents> ItkImageType; return PixelType( typeid(ComponentT), typeid(ItkImageType), sizeof(ComponentT), numOfComponents, ComponentTypeToString(), PixelTypeToString() ); } /** \brief A template method for creating a pixel type from an ItkImageType * * For fixed size vector images ( i.e. images of type itk::FixedArray<3,float> ) also the number of components * is propagated to the constructor */ template< typename ItkImageType > PixelType MakePixelType() { // define new type, since the ::PixelType is used to distinguish between simple and compound types typedef typename ItkImageType::PixelType ImportPixelType; // get the component type ( is either directly ImportPixelType or ImportPixelType::ValueType for compound types ) typedef typename GetComponentType::ComponentType ComponentT; // The PixelType is the same as the ComponentT for simple types typedef typename ItkImageType::PixelType PixelT; // Get the length of compound type ( initialized to 1 for simple types and variable-length vector images) size_t numComp = ComponentsTrait< (isPrimitiveType::value || isVectorImage::value), ItkImageType >::Size; // call the constructor return PixelType( typeid(ComponentT), typeid(PixelT), sizeof(ComponentT), numComp, ComponentTypeToString(), PixelTypeToString() ); } /** \brief An interface to the MakePixelType method for creating scalar pixel types. * * Usage: for example MakeScalarPixelType() for a scalar short image */ template< typename T> PixelType MakeScalarPixelType() { return MakePixelType(); } +/** + * @brief Translate the itk::ImageIOBase::IOType to a std::type_info + * + * The functionality is similar to the itk::ImageIOBase::GetComponentTypeInfo but this one can also handle composite pixel types. + * + * @param imageIO the ImageIO associated with an image to be read-in + * @return the typeid() of the given type for composite types, calls internal GetComponentTypeInfo for simple types + */ +const std::type_info& GetPixelTypeFromITKImageIO( const itk::ImageIOBase::Pointer imageIO); + } // namespace mitk + + #endif /* PIXELTYPE_H_HEADER_INCLUDED_C1EBF565 */