Commit 7c845027 authored by Guillaume Pasero's avatar Guillaume Pasero

ENH: OutputImageParameter refactored with fewer dynamic_cast

parent 31232585
......@@ -117,14 +117,8 @@ protected:
/** Destructor */
~OutputImageParameter() override;
template <class TInputVectorImageType>
void SwitchVectorImageWrite();
template <class TInputVectorImageType>
void SwitchRGBImageWrite();
template <class TInputVectorImageType>
void SwitchRGBAImageWrite();
template <class TInput>
int SwitchInput(TInput *img);
//FloatVectorImageType::Pointer m_Image;
ImageBaseType::Pointer m_Image;
......@@ -132,46 +126,28 @@ protected:
ImagePixelType m_PixelType;
ImagePixelType m_DefaultPixelType;
typedef otb::ImageFileWriter<UInt8VectorImageType> VectorUInt8WriterType;
typedef otb::ImageFileWriter<Int16VectorImageType> VectorInt16WriterType;
typedef otb::ImageFileWriter<UInt16VectorImageType> VectorUInt16WriterType;
typedef otb::ImageFileWriter<Int32VectorImageType> VectorInt32WriterType;
typedef otb::ImageFileWriter<UInt32VectorImageType> VectorUInt32WriterType;
typedef otb::ImageFileWriter<FloatVectorImageType> VectorFloatWriterType;
typedef otb::ImageFileWriter<DoubleVectorImageType> VectorDoubleWriterType;
typedef otb::ImageFileWriter<UInt8RGBAImageType> RGBAUInt8WriterType;
typedef otb::ImageFileWriter<UInt8RGBImageType> RGBUInt8WriterType;
typedef otb::ImageFileWriter<ComplexInt16VectorImageType> ComplexVectorInt16WriterType;
typedef otb::ImageFileWriter<ComplexInt32VectorImageType> ComplexVectorInt32WriterType;
typedef otb::ImageFileWriter<ComplexFloatVectorImageType> ComplexVectorFloatWriterType;
typedef otb::ImageFileWriter<ComplexDoubleVectorImageType> ComplexVectorDoubleWriterType;
VectorUInt8WriterType::Pointer m_VectorUInt8Writer;
VectorInt16WriterType::Pointer m_VectorInt16Writer;
VectorUInt16WriterType::Pointer m_VectorUInt16Writer;
VectorInt32WriterType::Pointer m_VectorInt32Writer;
VectorUInt32WriterType::Pointer m_VectorUInt32Writer;
VectorFloatWriterType::Pointer m_VectorFloatWriter;
VectorDoubleWriterType::Pointer m_VectorDoubleWriter;
RGBUInt8WriterType::Pointer m_RGBUInt8Writer;
RGBAUInt8WriterType::Pointer m_RGBAUInt8Writer;
ComplexVectorInt16WriterType::Pointer m_ComplexVectorInt16Writer;
ComplexVectorInt32WriterType::Pointer m_ComplexVectorInt32Writer;
ComplexVectorFloatWriterType::Pointer m_ComplexVectorFloatWriter;
ComplexVectorDoubleWriterType::Pointer m_ComplexVectorDoubleWriter;
private:
OutputImageParameter(const Parameter &); //purposely not implemented
void operator =(const Parameter&); //purposely not implemented
unsigned int m_RAMValue;
itk::ProcessObject::Pointer m_Caster;
itk::ProcessObject::Pointer m_Writer;
}; // End class OutputImage Parameter
// Declare specialisation for UInt8RGBAImageType
template <>
int
OutputImageParameter::SwitchInput(UInt8RGBAImageType *img);
// Declare specialisation for UInt8RGBImageType
template <>
int
OutputImageParameter::SwitchInput(UInt8RGBImageType *img);
} // End namespace Wrapper
} // End namespace otb
......
......@@ -477,7 +477,6 @@ int Application::ExecuteAndWriteOutput()
if(outputParam!=ITK_NULLPTR)
{
outputParam->InitializeWriters();
std::string checkReturn = outputParam->CheckFileName(true);
if (!checkReturn.empty())
{
......@@ -487,6 +486,7 @@ int Application::ExecuteAndWriteOutput()
{
outputParam->SetRAMValue(ram);
}
outputParam->InitializeWriters();
std::ostringstream progressId;
progressId << "Writing " << outputParam->GetFileName() << "...";
AddProcess(outputParam->GetWriter(), progressId.str());
......
......@@ -42,7 +42,9 @@ namespace Wrapper
OutputImageParameter::OutputImageParameter()
: m_PixelType(ImagePixelType_float),
m_DefaultPixelType(ImagePixelType_float),
m_RAMValue(0)
m_RAMValue(0),
m_Caster(nullptr),
m_Writer(nullptr)
{
this->SetName("Output Image");
this->SetKey("out");
......@@ -149,35 +151,102 @@ OutputImageParameter::ConvertStringToPixelType(const std::string &value, ImagePi
void OutputImageParameter::InitializeWriters()
{
m_VectorUInt8Writer = VectorUInt8WriterType::New();
m_VectorInt16Writer = VectorInt16WriterType::New();
m_VectorUInt16Writer = VectorUInt16WriterType::New();
m_VectorInt32Writer = VectorInt32WriterType::New();
m_VectorUInt32Writer = VectorUInt32WriterType::New();
m_VectorFloatWriter = VectorFloatWriterType::New();
m_VectorDoubleWriter = VectorDoubleWriterType::New();
m_RGBUInt8Writer = RGBUInt8WriterType::New();
m_RGBAUInt8Writer = RGBAUInt8WriterType::New();
m_ComplexVectorInt16Writer = ComplexVectorInt16WriterType::New();
m_ComplexVectorInt32Writer = ComplexVectorInt32WriterType::New();
m_ComplexVectorFloatWriter = ComplexVectorFloatWriterType::New();
m_ComplexVectorDoubleWriter = ComplexVectorDoubleWriterType::New();
ImageBaseType* imgBase = m_Image.GetPointer();
// Guess the image type
std::string className(m_Image->GetNameOfClass());
if (className == "VectorImage")
{
UInt8VectorImageType* imgUInt8 = dynamic_cast<UInt8VectorImageType*>(imgBase);
if (imgUInt8 && SwitchInput(imgUInt8)) return;
Int16VectorImageType* imgInt16 = dynamic_cast<Int16VectorImageType*>(imgBase);
if (imgInt16 && SwitchInput(imgInt16)) return;
UInt16VectorImageType* imgUInt16 = dynamic_cast<UInt16VectorImageType*>(imgBase);
if (imgUInt16 && SwitchInput(imgUInt16)) return;
Int32VectorImageType* imgInt32 = dynamic_cast<Int32VectorImageType*>(imgBase);
if (imgInt32 && SwitchInput(imgInt32)) return;
UInt32VectorImageType* imgUInt32 = dynamic_cast<UInt32VectorImageType*>(imgBase);
if (imgUInt32 && SwitchInput(imgUInt32)) return;
FloatVectorImageType* imgFloat = dynamic_cast<FloatVectorImageType*>(imgBase);
if (imgFloat && SwitchInput(imgFloat)) return;
DoubleVectorImageType* imgDouble = dynamic_cast<DoubleVectorImageType*>(imgBase);
if (imgDouble && SwitchInput(imgDouble)) return;
ComplexInt16VectorImageType* imgCInt16 = dynamic_cast<ComplexInt16VectorImageType*>(imgBase);
if (imgCInt16 && SwitchInput(imgCInt16)) return;
ComplexInt32VectorImageType* imgCInt32 = dynamic_cast<ComplexInt32VectorImageType*>(imgBase);
if (imgCInt32 && SwitchInput(imgCInt32)) return;
ComplexFloatVectorImageType* imgCFloat = dynamic_cast<ComplexFloatVectorImageType*>(imgBase);
if (imgCFloat && SwitchInput(imgCFloat)) return;
ComplexDoubleVectorImageType* imgCDouble = dynamic_cast<ComplexDoubleVectorImageType*>(imgBase);
if (imgCDouble && SwitchInput(imgCDouble)) return;
}
else
{
UInt8ImageType* imgUInt8 = dynamic_cast<UInt8ImageType*>(imgBase);
if (imgUInt8 && SwitchInput(imgUInt8)) return;
Int16ImageType* imgInt16 = dynamic_cast<Int16ImageType*>(imgBase);
if (imgInt16 && SwitchInput(imgInt16)) return;
UInt16ImageType* imgUInt16 = dynamic_cast<UInt16ImageType*>(imgBase);
if (imgUInt16 && SwitchInput(imgUInt16)) return;
Int32ImageType* imgInt32 = dynamic_cast<Int32ImageType*>(imgBase);
if (imgInt32 && SwitchInput(imgInt32)) return;
UInt32ImageType* imgUInt32 = dynamic_cast<UInt32ImageType*>(imgBase);
if (imgUInt32 && SwitchInput(imgUInt32)) return;
FloatImageType* imgFloat = dynamic_cast<FloatImageType*>(imgBase);
if (imgFloat && SwitchInput(imgFloat)) return;
DoubleImageType* imgDouble = dynamic_cast<DoubleImageType*>(imgBase);
if (imgDouble && SwitchInput(imgDouble)) return;
ComplexInt16ImageType* imgCInt16 = dynamic_cast<ComplexInt16ImageType*>(imgBase);
if (imgCInt16 && SwitchInput(imgCInt16)) return;
ComplexInt32ImageType* imgCInt32 = dynamic_cast<ComplexInt32ImageType*>(imgBase);
if (imgCInt32 && SwitchInput(imgCInt32)) return;
ComplexFloatImageType* imgCFloat = dynamic_cast<ComplexFloatImageType*>(imgBase);
if (imgCFloat && SwitchInput(imgCFloat)) return;
ComplexDoubleImageType* imgCDouble = dynamic_cast<ComplexDoubleImageType*>(imgBase);
if (imgCDouble && SwitchInput(imgCDouble)) return;
UInt8RGBImageType* imgRGB = dynamic_cast<UInt8RGBImageType*>(imgBase);
if (imgRGB && SwitchInput(imgRGB)) return;
UInt8RGBAImageType* imgRGBA = dynamic_cast<UInt8RGBAImageType*>(imgBase);
if (imgRGBA && SwitchInput(imgRGBA)) return;
}
itkExceptionMacro("Unknown image type");
}
template <typename TInput, typename TOutput>
void
ClampAndWriteVectorImage( itk::ImageBase<2> * in ,
otb::ImageFileWriter<TOutput> * writer ,
std::pair<itk::ProcessObject::Pointer,itk::ProcessObject::Pointer>
ClampAndWriteVectorImage( TInput * in ,
const std::string & filename ,
const unsigned int & ramValue )
{
std::pair<itk::ProcessObject::Pointer,itk::ProcessObject::Pointer> ret;
typedef ClampImageFilter < TInput , TOutput > ClampFilterType;
typename ClampFilterType::Pointer clampFilter ( ClampFilterType::New() );
clampFilter->SetInput( dynamic_cast<TInput*>(in));
clampFilter->SetInput( in);
ret.first = clampFilter.GetPointer();
bool useStandardWriter = true;
......@@ -195,7 +264,8 @@ ClampAndWriteVectorImage( itk::ImageBase<2> * in ,
if(extension == ".vrt")
{
// Use the WriteMPI function
WriteMPI(clampFilter->GetOutput(),filename,ramValue);
// TODO : create a dedicated filter
//~ WriteMPI(clampFilter->GetOutput(),filename,ramValue);
}
#ifdef OTB_USE_SPTW
else if (extension == ".tif")
......@@ -207,7 +277,7 @@ ClampAndWriteVectorImage( itk::ImageBase<2> * in ,
sptWriter->SetFileName(filename);
sptWriter->SetInput(clampFilter->GetOutput());
sptWriter->SetAutomaticAdaptativeStreaming(ramValue);
sptWriter->Update();
ret.second = sptWriter.GetPointer();
}
#endif
......@@ -222,115 +292,110 @@ ClampAndWriteVectorImage( itk::ImageBase<2> * in ,
if(useStandardWriter)
{
typename otb::ImageFileWriter<TOutput>::Pointer writer =
otb::ImageFileWriter<TOutput>::New();
writer->SetFileName( filename );
writer->SetInput(clampFilter->GetOutput());
writer->SetAutomaticAdaptativeStreaming(ramValue);
writer->Update();
ret.second = writer.GetPointer();
}
return ret;
}
template <class TInput>
void
OutputImageParameter::SwitchVectorImageWrite()
{
int
OutputImageParameter::SwitchInput(TInput *img)
{
if (! img) return 0;
std::pair<itk::ProcessObject::Pointer,itk::ProcessObject::Pointer> ret;
switch(m_PixelType )
{
case ImagePixelType_uint8:
{
ClampAndWriteVectorImage< TInput , UInt8VectorImageType > (
m_Image ,
m_VectorUInt8Writer ,
ret = ClampAndWriteVectorImage< TInput , UInt8VectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
}
case ImagePixelType_int16:
{
ClampAndWriteVectorImage< TInput , Int16VectorImageType > (
m_Image ,
m_VectorInt16Writer ,
ret = ClampAndWriteVectorImage< TInput , Int16VectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
}
case ImagePixelType_uint16:
{
ClampAndWriteVectorImage< TInput , UInt16VectorImageType > (
m_Image ,
m_VectorUInt16Writer ,
ret = ClampAndWriteVectorImage< TInput , UInt16VectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
}
case ImagePixelType_int32:
{
ClampAndWriteVectorImage< TInput , Int32VectorImageType > (
m_Image ,
m_VectorInt32Writer ,
ret = ClampAndWriteVectorImage< TInput , Int32VectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
}
case ImagePixelType_uint32:
{
ClampAndWriteVectorImage< TInput , UInt32VectorImageType > (
m_Image ,
m_VectorUInt32Writer ,
ret = ClampAndWriteVectorImage< TInput , UInt32VectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
}
case ImagePixelType_float:
{
ClampAndWriteVectorImage< TInput , FloatVectorImageType > (
m_Image ,
m_VectorFloatWriter ,
ret = ClampAndWriteVectorImage< TInput , FloatVectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
}
case ImagePixelType_double:
{
ClampAndWriteVectorImage< TInput , DoubleVectorImageType > (
m_Image ,
m_VectorDoubleWriter ,
ret = ClampAndWriteVectorImage< TInput , DoubleVectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
}
case ImagePixelType_cint16:
{
ClampAndWriteVectorImage < TInput , ComplexInt16VectorImageType > (
m_Image ,
m_ComplexVectorInt16Writer ,
ret = ClampAndWriteVectorImage < TInput , ComplexInt16VectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
}
case ImagePixelType_cint32:
{
ClampAndWriteVectorImage < TInput , ComplexInt32VectorImageType > (
m_Image ,
m_ComplexVectorInt32Writer ,
ret = ClampAndWriteVectorImage < TInput , ComplexInt32VectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
}
case ImagePixelType_cfloat:
{
ClampAndWriteVectorImage < TInput , ComplexFloatVectorImageType > (
m_Image ,
m_ComplexVectorFloatWriter ,
ret = ClampAndWriteVectorImage < TInput , ComplexFloatVectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
}
case ImagePixelType_cdouble:
{
ClampAndWriteVectorImage < TInput , ComplexDoubleVectorImageType > (
m_Image ,
m_ComplexVectorDoubleWriter ,
ret = ClampAndWriteVectorImage < TInput , ComplexDoubleVectorImageType > (
img ,
m_FileName ,
m_RAMValue );
break;
......@@ -338,256 +403,28 @@ OutputImageParameter::SwitchVectorImageWrite()
default:
break;
}
}
template <class TInputRGBAImageType>
void
OutputImageParameter::SwitchRGBAImageWrite()
{
if( m_PixelType == ImagePixelType_uint8 )
{
m_RGBAUInt8Writer->SetFileName( this->GetFileName() );
m_RGBAUInt8Writer->SetInput(dynamic_cast<UInt8RGBAImageType*>(m_Image.GetPointer()) );
m_RGBAUInt8Writer->SetAutomaticAdaptativeStreaming(m_RAMValue);
m_RGBAUInt8Writer->Update();
}
else
itkExceptionMacro("Unknown PixelType for RGBA Image. Only uint8 is supported.");
}
// Save the caster and writer
m_Caster = ret.first;
m_Writer = ret.second;
return 1;
}
template <class TInputRGBImageType>
void
OutputImageParameter::SwitchRGBImageWrite()
{
if( m_PixelType == ImagePixelType_uint8 )
{
m_RGBUInt8Writer->SetFileName( this->GetFileName() );
m_RGBUInt8Writer->SetInput(dynamic_cast<UInt8RGBImageType*>(m_Image.GetPointer()) );
m_RGBUInt8Writer->SetAutomaticAdaptativeStreaming(m_RAMValue);
m_RGBUInt8Writer->Update();
}
else
itkExceptionMacro("Unknown PixelType for RGB Image. Only uint8 is supported.");
}
void
OutputImageParameter::Write()
{
m_Image->UpdateOutputInformation();
m_Writer->Update();
if (dynamic_cast<UInt8ImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<UInt8ImageType>();
}
else if (dynamic_cast<Int16ImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<Int16ImageType>();
}
else if (dynamic_cast<UInt16ImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<UInt16ImageType>();
}
else if (dynamic_cast<Int32ImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<Int32ImageType>();
}
else if (dynamic_cast<UInt32ImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<UInt32ImageType>();
}
else if (dynamic_cast<FloatImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<FloatImageType>();
}
else if (dynamic_cast<DoubleImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<DoubleImageType>();
}
else if (dynamic_cast<ComplexInt16ImageType*>(m_Image.GetPointer()) )
{
SwitchVectorImageWrite<ComplexInt16ImageType>();
}
else if (dynamic_cast<ComplexInt32ImageType*>(m_Image.GetPointer()) )
{
SwitchVectorImageWrite<ComplexInt32ImageType>();
}
else if (dynamic_cast<ComplexFloatImageType*>(m_Image.GetPointer()) )
{
SwitchVectorImageWrite<ComplexFloatImageType>();
}
else if (dynamic_cast<ComplexDoubleImageType*>(m_Image.GetPointer()) )
{
SwitchVectorImageWrite<ComplexDoubleImageType>();
}
else if (dynamic_cast<UInt8VectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<UInt8VectorImageType>();
}
else if (dynamic_cast<Int16VectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<Int16VectorImageType>();
}
else if (dynamic_cast<UInt16VectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<UInt16VectorImageType>();
}
else if (dynamic_cast<Int32VectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<Int32VectorImageType>();
}
else if (dynamic_cast<UInt32VectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<UInt32VectorImageType>();
}
else if (dynamic_cast<FloatVectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<FloatVectorImageType>();
}
else if (dynamic_cast<DoubleVectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<DoubleVectorImageType>();
}
else if (dynamic_cast<ComplexInt16VectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<ComplexInt16VectorImageType>();
}
else if (dynamic_cast<ComplexInt32VectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<ComplexInt32VectorImageType>();
}
else if (dynamic_cast<ComplexFloatVectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<ComplexFloatVectorImageType>();
}
else if (dynamic_cast<ComplexDoubleVectorImageType*>(m_Image.GetPointer()))
{
SwitchVectorImageWrite<ComplexDoubleVectorImageType>();
}
else if (dynamic_cast<UInt8RGBImageType*>(m_Image.GetPointer()))
{
SwitchRGBImageWrite<UInt8RGBImageType>();
}
else if (dynamic_cast<UInt8RGBAImageType*>(m_Image.GetPointer()))
{
SwitchRGBAImageWrite<UInt8RGBAImageType>();
}
else
{
itkExceptionMacro("Unknown image type");
}
}
// Clean internal filters
m_Caster = nullptr;
m_Writer = nullptr;
}
itk::ProcessObject*
OutputImageParameter::GetWriter()
{
int type = 1;
// 0 : image
// 1 : VectorImage
// 2 : RGBAImage
// 3 : RGBImage
itk::ProcessObject* writer = ITK_NULLPTR;
if (dynamic_cast<UInt8RGBAImageType*> (m_Image.GetPointer()))
{
type = 2;
writer = m_RGBAUInt8Writer;
itkWarningMacro("UInt8RGBAImageType will be saved in UInt8 format.");
return writer;
}
else if (dynamic_cast<UInt8RGBImageType*> (m_Image.GetPointer()))
{
type = 3;
writer = m_RGBUInt8Writer;
itkWarningMacro("UInt8RGBImageType will be saved in UInt8 format.");
return writer;
}
switch (GetPixelType())
{
case ImagePixelType_uint8:
{
switch(type)
{
case 1:
writer = m_VectorUInt8Writer;
break;
case 2:
writer = m_RGBAUInt8Writer;
break;
default:
writer = m_RGBUInt8Writer;
break;
}
break;
}
case ImagePixelType_int16:
{
if (type == 1)
writer = m_VectorInt16Writer;
break;
}
case ImagePixelType_uint16:
{
if (type == 1)
writer = m_VectorUInt16Writer;
break;
}
case ImagePixelType_int32:
{
if (type == 1)
writer = m_VectorInt32Writer;
break;