diff --git a/include/otbMosaicFromDirectoryHandler.h b/include/otbMosaicFromDirectoryHandler.h new file mode 100644 index 0000000000000000000000000000000000000000..96b9565adac4ee517bafb64b15da9659b6dfcded --- /dev/null +++ b/include/otbMosaicFromDirectoryHandler.h @@ -0,0 +1,134 @@ +/* + * otbMosaicFromDirectoryHandler.h + * + * Created on: 24 mars 2016 + * Author: cresson + */ + +#ifndef MODULES_REMOTE_OTB_MosaicFromDirectoryHandler_INCLUDE_OTBMosaicFromDirectoryHandler_H_ +#define MODULES_REMOTE_OTB_MosaicFromDirectoryHandler_INCLUDE_OTBMosaicFromDirectoryHandler_H_ + +#include "itkImageSource.h" +#include "itkExceptionObject.h" +#include "itkImageRegion.h" + +#include "otbStreamingSimpleMosaicFilter.h" + +#include "otbImageFileReader.h" +#include "itkDirectory.h" +#include "otbImageIOBase.h" +#include "otbImageIOFactory.h" + +#include "otbMultiToMonoChannelExtractROI.h" +#include "otbGenericRSResampleImageFilter.h" +#include "itkNearestNeighborInterpolateImageFunction.h" + +namespace otb +{ +/** \class MosaicFromDirectoryHandler + * \brief This ImageSource produces an otb::image from multiple rasters + * stored in the m_Directory. + * TODO: Currently only .tif extension is supported. Might be nice to change it. + * + * + * \ingroup OTBMosaic + * + */ +template <class TOutputImage, class TReferenceImage> +class ITK_EXPORT MosaicFromDirectoryHandler : public itk::ImageSource<TOutputImage> +{ +public: + /** Standard class typedefs. */ + typedef MosaicFromDirectoryHandler Self; + typedef itk::ImageSource<TOutputImage> Superclass; + typedef itk::SmartPointer<Self> Pointer; + + /** Method for creation through the object factory. */ + itkNewMacro(Self); + + /** Run-time type information (and related methods). */ + itkTypeMacro(MosaicFromDirectoryHandler, ImageSource); + + /** Typedefs for output image */ + typedef typename TOutputImage::SizeType SizeType; + typedef typename TOutputImage::IndexType IndexType; + typedef typename TOutputImage::SpacingType SpacingType; + typedef typename TOutputImage::PointType PointType; + typedef typename TOutputImage::RegionType ImageRegionType; + typedef typename TOutputImage::InternalPixelType OutputImagePixelType; + + /** Typedefs for mosaic filter */ + typedef otb::VectorImage<OutputImagePixelType> InternalMaskImageType; + typedef otb::StreamingSimpleMosaicFilter< + InternalMaskImageType> MosaicFilterType; + typedef typename MosaicFilterType::Pointer MosaicFilterPointerType; + + /** Typedefs for image reader */ + typedef otb::ImageFileReader<InternalMaskImageType> ReaderType; + typedef typename ReaderType::Pointer ReaderPointerType; + + /** Typedefs for casting the image */ + typedef otb::MultiToMonoChannelExtractROI< + OutputImagePixelType, OutputImagePixelType> CastFilterType; + typedef typename CastFilterType::Pointer CastFilterPointerType; + + /** Typedefs for image reprojection */ + typedef otb::GenericRSResampleImageFilter< + InternalMaskImageType, InternalMaskImageType> ResamplerType; + typedef typename ResamplerType::Pointer ResamplerPointerType; + typedef itk::NearestNeighborInterpolateImageFunction< + InternalMaskImageType, double> NNInterpolatorType; + + /** Input directory accessors */ + itkGetMacro(Directory, std::string); + itkSetMacro(Directory, std::string); + + /** Output parameters setters */ + itkSetMacro(OutputSpacing, SpacingType); + itkSetMacro(OutputSize, SizeType); + itkSetMacro(OutputOrigin, PointType); + void SetReferenceImage(TReferenceImage * ptr){m_RefImagePtr = ptr;} + itkSetMacro(UseReferenceImage, bool); + + /** Prepare image allocation at the first call of the pipeline processing */ + virtual void GenerateOutputInformation(void); + + /** Does the real work. */ + virtual void GenerateData(); + +protected: + MosaicFromDirectoryHandler(); + virtual ~MosaicFromDirectoryHandler(); + + // Masks directory + std::string m_Directory; + + // Output parameters + SpacingType m_OutputSpacing; + SizeType m_OutputSize; + PointType m_OutputOrigin; + + // Internal filters + MosaicFilterPointerType mosaicFilter; + CastFilterPointerType castFilter; + std::vector<ReaderPointerType> readers; + std::vector<ResamplerPointerType> resamplers; + + // Reference image pointer + bool m_UseReferenceImage; + TReferenceImage * m_RefImagePtr; + +private: + + MosaicFromDirectoryHandler(const Self &); //purposely not implemented + void operator =(const Self&); //purposely not implemented + +}; + +} //namespace otb + +#ifndef OTB_MANUAL_INSTANTIATION +#include <otbMosaicFromDirectoryHandler.txx> +#endif + +#endif /* MODULES_REMOTE_OTB_MosaicFromDirectoryHandler_INCLUDE_OTBMosaicFromDirectoryHandler_H_ */ diff --git a/include/otbMosaicFromDirectoryHandler.txx b/include/otbMosaicFromDirectoryHandler.txx new file mode 100644 index 0000000000000000000000000000000000000000..ecb024bf7787edbeadbc1ed76ad97d3aa1c2fd51 --- /dev/null +++ b/include/otbMosaicFromDirectoryHandler.txx @@ -0,0 +1,147 @@ +/* + * otbMosaicFromDirectoryHandler.hxx + * + * Created on: 24 mars 2016 + * Author: cresson + */ + +#ifndef MODULES_REMOTE_OTB_MosaicFromDirectoryHandler_INCLUDE_OTBMosaicFromDirectoryHandler_HXX_ +#define MODULES_REMOTE_OTB_MosaicFromDirectoryHandler_INCLUDE_OTBMosaicFromDirectoryHandler_HXX_ + +#include "otbMosaicFromDirectoryHandler.h" +#include "otbImageFileWriter.h" + +namespace otb +{ + +template <class TOutputImage, class TReferenceImage> +MosaicFromDirectoryHandler<TOutputImage, TReferenceImage> +::MosaicFromDirectoryHandler() + { + mosaicFilter = MosaicFilterType::New(); + castFilter = CastFilterType::New(); + m_UseReferenceImage = false; + m_RefImagePtr = 0; + } + +template <class TOutputImage, class TReferenceImage> +MosaicFromDirectoryHandler<TOutputImage, TReferenceImage> +::~MosaicFromDirectoryHandler() +{ +} + +template <class TOutputImage, class TReferenceImage> +void +MosaicFromDirectoryHandler<TOutputImage, TReferenceImage> +::GenerateOutputInformation() + { + if (m_Directory[m_Directory.size()-1] != '/') + { + // If not, we add the separator + m_Directory.append("/"); + } + + // Get the list of files in the directory + itk::Directory::Pointer dir = itk::Directory::New(); + if (!dir->Load(m_Directory.c_str())) + { + itkExceptionMacro(<< "Unable to browse directory " << m_Directory); + } + + // Instanciate a new mosaic filter + mosaicFilter = MosaicFilterType::New(); + mosaicFilter->SetGlobalWarningDisplay(false); + readers.clear(); + resamplers.clear(); + + // Browse the directory + for (unsigned int i = 0; i < dir->GetNumberOfFiles(); i++) + { + const char *filename = dir->GetFile(i); + std::string sfilename(filename); + sfilename = m_Directory + sfilename; + + // Try to read the file + otb::ImageIOBase::Pointer imageIO = + otb::ImageIOFactory::CreateImageIO(sfilename.c_str(),otb::ImageIOFactory::ReadMode); + if( imageIO.IsNotNull() ) + { + // create reader + ReaderPointerType reader = ReaderType::New(); + reader->SetFileName(sfilename); + reader->UpdateOutputInformation(); + + readers.push_back(reader); + + if (m_UseReferenceImage) + { + ResamplerPointerType resampler = ResamplerType::New(); + resampler->SetInput(reader->GetOutput()); + + // Setup transform through projRef and Keywordlist + SpacingType defSpacing = m_RefImagePtr->GetSignedSpacing(); + defSpacing[0] *= 10; + defSpacing[1] *= 10; + resampler->SetDisplacementFieldSpacing(defSpacing); + resampler->SetInputKeywordList(reader->GetOutput()->GetImageKeywordlist()); + resampler->SetInputProjectionRef(reader->GetOutput()->GetProjectionRef()); + resampler->SetOutputKeywordList(m_RefImagePtr->GetImageKeywordlist()); + resampler->SetOutputProjectionRef(m_RefImagePtr->GetProjectionRef()); + resampler->SetOutputOrigin(m_RefImagePtr->GetOrigin()); + resampler->SetOutputSpacing(m_RefImagePtr->GetSignedSpacing()); + resampler->SetOutputSize(m_RefImagePtr->GetLargestPossibleRegion().GetSize()); + resampler->SetOutputStartIndex(m_RefImagePtr->GetLargestPossibleRegion().GetIndex()); + + typename NNInterpolatorType::Pointer interpolator = NNInterpolatorType::New(); + resampler->SetInterpolator(interpolator); + + resamplers.push_back(resampler); + + mosaicFilter->PushBackInput(resampler->GetOutput()); + } + else + { + mosaicFilter->PushBackInput(reader->GetOutput()); + } + } + else + { + // itkWarningMacro(<<"Unable to read file " << sfilename); + } + + } + + if (m_UseReferenceImage) + { + mosaicFilter->SetOutputOrigin(m_RefImagePtr->GetOrigin()); + mosaicFilter->SetOutputSpacing(m_RefImagePtr->GetSignedSpacing()); + mosaicFilter->SetOutputSize(m_RefImagePtr->GetLargestPossibleRegion().GetSize()); + } + else + { + mosaicFilter->SetOutputOrigin(m_OutputOrigin); + mosaicFilter->SetOutputSpacing(m_OutputSpacing); + mosaicFilter->SetOutputSize(m_OutputSize); + } + mosaicFilter->SetAutomaticOutputParametersComputation(false); + + castFilter->SetInput(mosaicFilter->GetOutput()); + + castFilter->GraftOutput( this->GetOutput() ); + castFilter->UpdateOutputInformation(); + this->GraftOutput( castFilter->GetOutput() ); + } + +template <class TOutputImage, class TReferenceImage> +void +MosaicFromDirectoryHandler<TOutputImage, TReferenceImage> +::GenerateData() + { + castFilter->GraftOutput( this->GetOutput() ); + castFilter->Update(); + this->GraftOutput( castFilter->GetOutput() ); + } + +} // end namespace otb + +#endif /* MODULES_REMOTE_OTB_MosaicFromDirectoryHandler_INCLUDE_OTBMosaicFromDirectoryHandler_HXX_ */