diff --git a/Examples/DataRepresentation/Image/CMakeLists.txt b/Examples/DataRepresentation/Image/CMakeLists.txt index 3b706111ba270fc9861f58b0c7990291474d3f74..83fdc2b70763123e229dfcd8bf488bfb86d45b2f 100644 --- a/Examples/DataRepresentation/Image/CMakeLists.txt +++ b/Examples/DataRepresentation/Image/CMakeLists.txt @@ -24,15 +24,15 @@ TARGET_LINK_LIBRARIES(RGBImage OTBCommon OTBIO ITKCommon ITKIO) ADD_EXECUTABLE(VectorImage VectorImage.cxx ) TARGET_LINK_LIBRARIES(VectorImage OTBCommon ITKCommon OTBIO ITKIO) -#ADD_EXECUTABLE(ImageAdaptor1 ImageAdaptor1.cxx ) -#TARGET_LINK_LIBRARIES(ImageAdaptor1 ITKCommon ITKIO) +ADD_EXECUTABLE(ImageAdaptor1 ImageAdaptor1.cxx ) +TARGET_LINK_LIBRARIES(ImageAdaptor1 OTBCommon ITKCommon OTBIO ITKIO) -#ADD_EXECUTABLE(ImageAdaptor2 ImageAdaptor2.cxx ) -#TARGET_LINK_LIBRARIES(ImageAdaptor2 ITKCommon ITKIO) +ADD_EXECUTABLE(ImageAdaptor2 ImageAdaptor2.cxx ) +TARGET_LINK_LIBRARIES(ImageAdaptor2 OTBCommon ITKCommon OTBIO ITKIO) -#ADD_EXECUTABLE(ImageAdaptor3 ImageAdaptor3.cxx ) -#TARGET_LINK_LIBRARIES(ImageAdaptor3 ITKCommon ITKIO) +ADD_EXECUTABLE(ImageAdaptor3 ImageAdaptor3.cxx ) +TARGET_LINK_LIBRARIES(ImageAdaptor3 OTBCommon ITKCommon OTBIO ITKIO) -#ADD_EXECUTABLE(ImageAdaptor4 ImageAdaptor4.cxx ) -#TARGET_LINK_LIBRARIES(ImageAdaptor4 ITKCommon ITKIO) +ADD_EXECUTABLE(ImageAdaptor4 ImageAdaptor4.cxx ) +TARGET_LINK_LIBRARIES(ImageAdaptor4 OTBCommon ITKCommon OTBIO ITKIO) diff --git a/Examples/DataRepresentation/Image/ImageAdaptor1.cxx b/Examples/DataRepresentation/Image/ImageAdaptor1.cxx new file mode 100644 index 0000000000000000000000000000000000000000..ab7a0e161021948f4afab3195f1b0823d3434f76 --- /dev/null +++ b/Examples/DataRepresentation/Image/ImageAdaptor1.cxx @@ -0,0 +1,191 @@ +/*========================================================================= + + Program: Insight Segmentation & Registration Toolkit + Module: $RCSfile: ImageAdaptor1.cxx,v $ + Language: C++ + Date: $Date: 2004/12/28 14:45:15 $ + Version: $Revision: 1.12 $ + + Copyright (c) Insight Software Consortium. All rights reserved. + See ITKCopyright.txt or http://www.itk.org/HTML/Copyright.htm for details. + + This software is distributed WITHOUT ANY WARRANTY; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. See the above copyright notices for more information. + +=========================================================================*/ + +#if defined(_MSC_VER) +#pragma warning ( disable : 4786 ) +#endif + + +// Software Guide : BeginLatex +// +//This example illustrates how the \doxygen{itk}{ImageAdaptor} can be used to cast +// an image from one pixel type to another. In particular, we will +// \emph{adapt} an \code{unsigned char} image to make it appear as an image of +// pixel type \code{float}. +// +// \index{itk::ImageAdaptor!Instantiation} +// \index{itk::ImageAdaptor!Header} +// +// We begin by including the relevant headers. +// +// Software Guide : EndLatex + +// Software Guide : BeginCodeSnippet +#include "otbImage.h" +#include "itkImageAdaptor.h" +// Software Guide : EndCodeSnippet + + +#include "itkImageRegionIteratorWithIndex.h" +#include "otbImageFileReader.h" + + +// Software Guide : BeginLatex +// +// First, we need to define a \emph{pixel accessor} class that does the actual +// conversion. Note that in general, the only valid operations for pixel +// accessors are those that only require the value of the input pixel. As +// such, neighborhood type operations are not possible. A pixel accessor must +// provide methods \code{Set()} and \code{Get()}, and define the types of +// \code{InternalPixelType} and \code{ExternalPixelType}. The +// \code{InternalPixelType} corresponds to the pixel type of the image to be +// adapted (\code{unsigned char} in this example). The \code{ExternalPixelType} +// corresponds to the pixel type we wish to emulate with the ImageAdaptor +// (\code{float} in this case). +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet +class CastPixelAccessor +{ +public: + typedef unsigned char InternalType; + typedef float ExternalType; + + static void Set(InternalType & output, const ExternalType & input) + { + output = static_cast<InternalType>( input ); + } + + static ExternalType Get( const InternalType & input ) + { + return static_cast<ExternalType>( input ); + } +}; +// Software Guide : EndCodeSnippet + + +//------------------------- +// +// Main code +// +//------------------------- + +int main( int argc, char *argv[] ) +{ + if( argc < 2 ) + { + std::cerr << "Usage: " << std::endl; + std::cerr << "ImageAdaptor1 inputFileName" << std::endl; + return -1; + } + + +// Software Guide : BeginLatex +// +// The CastPixelAccessor class simply applies a +// \code{static\_cast} to the pixel values. We now use this pixel accessor +// to define the image adaptor type and create an instance using +// the standard \code{New()} method. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef unsigned char InputPixelType; + const unsigned int Dimension = 2; + typedef otb::Image< InputPixelType, Dimension > ImageType; + + typedef itk::ImageAdaptor< ImageType, CastPixelAccessor > ImageAdaptorType; + ImageAdaptorType::Pointer adaptor = ImageAdaptorType::New(); +// Software Guide : EndCodeSnippet + +// Software Guide : BeginLatex +// +// We also create an image reader templated over the input image type and +// read the input image from file. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef otb::ImageFileReader< ImageType > ReaderType; + ReaderType::Pointer reader = ReaderType::New(); +// Software Guide : EndCodeSnippet + + + reader->SetFileName( argv[1] ); + reader->Update(); + + +// Software Guide : BeginLatex +// +// The output of the reader is then connected as the input to the image +// adaptor. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + adaptor->SetImage( reader->GetOutput() ); +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// In the following code, we visit the image using an iterator +// instantiated using the adapted image type and compute the +// sum of the pixel values. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef itk::ImageRegionIteratorWithIndex< ImageAdaptorType > IteratorType; + IteratorType it( adaptor, adaptor->GetBufferedRegion() ); + + double sum = 0.0; + it.GoToBegin(); + while( !it.IsAtEnd() ) + { + float value = it.Get(); + sum += value; + ++it; + } +// Software Guide : EndCodeSnippet + + +std::cout << "Sum of pixels is: " << sum << std::endl; + + +// Software Guide : BeginLatex +// +// Although in this example, we are just performing a simple summation, the key +// concept is that access to pixels is performed as if the pixel is of type +// \code{float}. Additionally, it should be noted that the adaptor is used +// as if it was an actual image and not as a filter. ImageAdaptors conform +// to the same API as the \doxygen{otb}{Image} class. +// +// Software Guide : EndLatex + + + return 0; +} + + + diff --git a/Examples/DataRepresentation/Image/ImageAdaptor2.cxx b/Examples/DataRepresentation/Image/ImageAdaptor2.cxx new file mode 100644 index 0000000000000000000000000000000000000000..d147bba61e3e0800153858aecbcf29dd775f544c --- /dev/null +++ b/Examples/DataRepresentation/Image/ImageAdaptor2.cxx @@ -0,0 +1,262 @@ +/*========================================================================= + + Program: Insight Segmentation & Registration Toolkit + Module: $RCSfile: ImageAdaptor2.cxx,v $ + Language: C++ + Date: $Date: 2005/11/20 13:27:52 $ + Version: $Revision: 1.14 $ + + Copyright (c) Insight Software Consortium. All rights reserved. + See ITKCopyright.txt or http://www.itk.org/HTML/Copyright.htm for details. + + This software is distributed WITHOUT ANY WARRANTY; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. See the above copyright notices for more information. + +=========================================================================*/ + +#if defined(_MSC_VER) +#pragma warning ( disable : 4786 ) +#endif + + +// Software Guide : BeginLatex +// +// This example illustrates how to use the \doxygen{itk}{ImageAdaptor} +// to access the individual components of an RGB image. In this case, we +// create an ImageAdaptor that will accept a RGB image as input and +// presents it as a scalar image. The pixel data +// will be taken directly from the red channel of the original image. +// +// \index{itk::ImageAdaptor!Instantiation} +// \index{itk::ImageAdaptor!Header} +// +// Software Guide : EndLatex + +#include "otbImage.h" +#include "itkImageAdaptor.h" +#include "itkImageRegionIteratorWithIndex.h" +#include "otbImageFileReader.h" +#include "otbImageFileWriter.h" +#include "itkRescaleIntensityImageFilter.h" + + +// Software Guide : BeginLatex +// +// As with the previous example, the bulk of the effort in creating the image +// adaptor is associated with the definition of the pixel accessor class. In +// this case, the accessor converts a RGB vector to a scalar containing the +// red channel component. Note that in the following, we do not need to define +// the \code{Set()} method since we only expect the adaptor to be used for +// reading data from the image. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet +class RedChannelPixelAccessor +{ +public: + typedef itk::RGBPixel<float> InternalType; + typedef float ExternalType; + + static ExternalType Get( const InternalType & input ) + { + return static_cast<ExternalType>( input.GetRed() ); + } +}; +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// The \code{Get()} method simply calls the \code{GetRed()} method +// defined in the \doxygen{itk}{RGBPixel} class. +// +// Software Guide : EndLatex + + +//------------------------- +// +// Main code +// +//------------------------- + +int main( int argc, char *argv[] ) +{ + if( argc < 3 ) + { + std::cerr << "Usage: " << std::endl; + std::cerr << "ImageAdaptor2 inputRGBFileName outputRedChannelFileName" << std::endl; + return -1; + } + + +// Software Guide : BeginLatex +// +// Now we use the internal pixel type of the pixel accessor to define the +// input image type, and then proceed to instantiate the ImageAdaptor type. +// +// \index{PixelAccessor!RGB red channel} +// \index{itk::ImageAdaptor!RGB red channel} +// \index{ImageAdaptor!RGB red channel} +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef RedChannelPixelAccessor::InternalType InputPixelType; + const unsigned int Dimension = 2; + typedef otb::Image< InputPixelType, Dimension > ImageType; + + typedef itk::ImageAdaptor< ImageType, + RedChannelPixelAccessor > ImageAdaptorType; + + ImageAdaptorType::Pointer adaptor = ImageAdaptorType::New(); +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// We create an image reader and connect the output to the adaptor +// as before. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef otb::ImageFileReader< ImageType > ReaderType; + ReaderType::Pointer reader = ReaderType::New(); +// Software Guide : EndCodeSnippet + + reader->SetFileName( argv[1] ); + reader->Update(); + +// Software Guide : BeginCodeSnippet + adaptor->SetImage( reader->GetOutput() ); +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// We create an \doxygen{itk}{RescaleIntensityImageFilter} and an +// \doxygen{otb}{ImageFileWriter} to rescale the dynamic range of the pixel values +// and send the extracted channel to an image file. Note that the image type +// used for the rescaling filter is the \code{ImageAdaptorType} itself. That +// is, the adaptor type is used in the same context as an image type. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef otb::Image< unsigned char, Dimension > OutputImageType; + typedef itk::RescaleIntensityImageFilter< ImageAdaptorType, + OutputImageType + > RescalerType; + + RescalerType::Pointer rescaler = RescalerType::New(); + typedef otb::ImageFileWriter< OutputImageType > WriterType; + WriterType::Pointer writer = WriterType::New(); +// Software Guide : EndCodeSnippet + + + writer->SetFileName( argv[2] ); + + +// Software Guide : BeginLatex +// +// Now we connect the adaptor as the input to the rescaler and set the +// parameters for the intensity rescaling. +// +// Software Guide : EndLatex + +// Software Guide : BeginCodeSnippet + rescaler->SetOutputMinimum( 0 ); + rescaler->SetOutputMaximum( 255 ); + + rescaler->SetInput( adaptor ); + writer->SetInput( rescaler->GetOutput() ); +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// Finally, we invoke the \code{Update()} method on the writer and take +// precautions to catch any exception that may be thrown during +// the execution of the pipeline. +// +// Software Guide : EndLatex + +// Software Guide : BeginCodeSnippet + try + { + writer->Update(); + } + catch( itk::ExceptionObject & excp ) + { + std::cerr << "Exception caught " << excp << std::endl; + return 1; + } +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// ImageAdaptors for the green and blue channels can easily be implemented by +// modifying the pixel accessor of the red channel and then using the +// new pixel accessor for instantiating the type of an image adaptor. +// The following define a green channel pixel accessor. +// +// \index{PixelAccessor!RGB green channel} +// \index{itk::ImageAdaptor!RGB green channel} +// \index{ImageAdaptor!RGB green channel} +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + class GreenChannelPixelAccessor + { + public: + typedef itk::RGBPixel<float> InternalType; + typedef float ExternalType; + + static ExternalType Get( const InternalType & input ) + { + return static_cast<ExternalType>( input.GetGreen() ); + } + }; +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// A blue channel pixel accessor is similarly defined. +// +// \index{PixelAccessor!RGB blue channel} +// \index{itk::ImageAdaptor!RGB blue channel} +// \index{ImageAdaptor!RGB blue channel} +// +// Software Guide : EndLatex + +// Software Guide : BeginCodeSnippet + class BlueChannelPixelAccessor + { + public: + typedef itk::RGBPixel<float> InternalType; + typedef float ExternalType; + + static ExternalType Get( const InternalType & input ) + { + return static_cast<ExternalType>( input.GetBlue() ); + } + }; +// Software Guide : EndCodeSnippet + + + + return 0; +} + + + diff --git a/Examples/DataRepresentation/Image/ImageAdaptor3.cxx b/Examples/DataRepresentation/Image/ImageAdaptor3.cxx new file mode 100644 index 0000000000000000000000000000000000000000..badb77456acacee92349802c51a979a56fa25153 --- /dev/null +++ b/Examples/DataRepresentation/Image/ImageAdaptor3.cxx @@ -0,0 +1,235 @@ +/*========================================================================= + + Program: Insight Segmentation & Registration Toolkit + Module: $RCSfile: ImageAdaptor3.cxx,v $ + Language: C++ + Date: $Date: 2005/11/20 13:27:52 $ + Version: $Revision: 1.13 $ + + Copyright (c) Insight Software Consortium. All rights reserved. + See ITKCopyright.txt or http://www.itk.org/HTML/Copyright.htm for details. + + This software is distributed WITHOUT ANY WARRANTY; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. See the above copyright notices for more information. + +=========================================================================*/ + +#if defined(_MSC_VER) +#pragma warning ( disable : 4786 ) +#endif + + +// Software Guide : BeginLatex +// +// This example illustrates the use of \doxygen{itk}{ImageAdaptor} +// to obtain access to the components of a vector image. +// Specifically, it shows how to manage pixel accessors containing +// internal parameters. In this example we create an image of vectors by using +// a gradient filter. Then, we use an image adaptor to extract one of the +// components of the vector image. The vector type used by the gradient filter +// is the \doxygen{itk}{CovariantVector} class. +// +// We start by including the relevant headers. +// +// \index{itk::ImageAdaptor!Instantiation} +// \index{itk::ImageAdaptor!Header} +// \index{itk::PixelAccessor!with parameters} +// +// Software Guide : EndLatex + +#include "otbImage.h" +#include "itkImageAdaptor.h" +#include "itkImageRegionIteratorWithIndex.h" +#include "otbImageFileReader.h" +#include "otbImageFileWriter.h" +#include "itkRescaleIntensityImageFilter.h" + + +// Software Guide : BeginCodeSnippet +#include "itkCovariantVector.h" +#include "itkGradientRecursiveGaussianImageFilter.h" +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// A pixel accessors class may have internal parameters that affect the +// operations performed on input pixel data. Image adaptors support +// parameters in their internal pixel accessor by using +// the assignment operator. Any pixel accessor which has internal +// parameters must therefore implement the assignment operator. +// The following defines a pixel accessor for extracting +// components from a vector pixel. The +// \code{m\_Index} member variable is used to select the vector component +// to be returned. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet +class VectorPixelAccessor +{ +public: + typedef itk::CovariantVector<float,2> InternalType; + typedef float ExternalType; + + void operator=( const VectorPixelAccessor & vpa ) + { + m_Index = vpa.m_Index; + } + ExternalType Get( const InternalType & input ) const + { + return static_cast<ExternalType>( input[ m_Index ] ); + } + void SetIndex( unsigned int index ) + { + m_Index = index; + } +private: + unsigned int m_Index; +}; +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// The \code{Get()} method simply returns the \emph{i}-th component of +// the vector as indicated by the index. The assignment operator transfers the +// value of the index member variable from one instance of the pixel accessor +// to another. +// +// Software Guide : EndLatex + + +//------------------------- +// +// Main code +// +//------------------------- + +int main( int argc, char *argv[] ) +{ + if( argc < 4 ) + { + std::cerr << "Usage: " << std::endl; + std::cerr << "ImageAdaptor3 inputFileName outputComponentFileName "; + std::cerr << " indexOfComponentToExtract" << std::endl; + return -1; + } + + +// Software Guide : BeginLatex +// +// In order to test the pixel accessor, we generate an image of vectors using +// the \doxygen{itk}{GradientRecursiveGaussianImageFilter}. This +// filter produces an output image of \doxygen{itk}{CovariantVector} pixel type. +// Covariant vectors are the natural representation for gradients since they +// are the equivalent of normals to iso-values manifolds. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef unsigned char InputPixelType; + const unsigned int Dimension = 2; + typedef otb::Image< InputPixelType, Dimension > InputImageType; + typedef itk::CovariantVector< float, Dimension > VectorPixelType; + typedef otb::Image< VectorPixelType, Dimension > VectorImageType; + typedef itk::GradientRecursiveGaussianImageFilter< InputImageType, + VectorImageType> GradientFilterType; + + GradientFilterType::Pointer gradient = GradientFilterType::New(); +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// We instantiate the ImageAdaptor using the vector image type as +// the first template parameter and the pixel accessor as the second +// template parameter. +// +// Software Guide : EndLatex + + + +// Software Guide : BeginCodeSnippet + typedef itk::ImageAdaptor< VectorImageType, + VectorPixelAccessor > ImageAdaptorType; + + ImageAdaptorType::Pointer adaptor = ImageAdaptorType::New(); +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// The index of the component to be extracted is specified +// from the command line. In the following, we create the accessor, +// set the index and connect the accessor to the image adaptor using +// the \code{SetPixelAccessor()} method. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + VectorPixelAccessor accessor; + accessor.SetIndex( atoi( argv[3] ) ); + adaptor->SetPixelAccessor( accessor ); +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// We create a reader to load the image specified from the +// command line and pass its output as the input to the gradient filter. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef otb::ImageFileReader< InputImageType > ReaderType; + ReaderType::Pointer reader = ReaderType::New(); + gradient->SetInput( reader->GetOutput() ); + + reader->SetFileName( argv[1] ); + gradient->Update(); +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// We now connect the output of the gradient filter as input to the +// image adaptor. The adaptor emulates a scalar image whose pixel values +// are taken from the selected component of the vector image. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + adaptor->SetImage( gradient->GetOutput() ); +// Software Guide : EndCodeSnippet + + + typedef otb::Image< unsigned char, Dimension > OutputImageType; + typedef itk::RescaleIntensityImageFilter< ImageAdaptorType, OutputImageType> + RescalerType; + RescalerType::Pointer rescaler = RescalerType::New(); + typedef otb::ImageFileWriter< OutputImageType > WriterType; + WriterType::Pointer writer = WriterType::New(); + + writer->SetFileName( argv[2] ); + + rescaler->SetOutputMinimum( 0 ); + rescaler->SetOutputMaximum( 255 ); + + rescaler->SetInput( adaptor ); + writer->SetInput( rescaler->GetOutput() ); + writer->Update(); + + + + return 0; +} + + + diff --git a/Examples/DataRepresentation/Image/ImageAdaptor4.cxx b/Examples/DataRepresentation/Image/ImageAdaptor4.cxx new file mode 100644 index 0000000000000000000000000000000000000000..adecafe65b905f75d983e3333c8a47bb2d0a815d --- /dev/null +++ b/Examples/DataRepresentation/Image/ImageAdaptor4.cxx @@ -0,0 +1,231 @@ +/*========================================================================= + + Program: Insight Segmentation & Registration Toolkit + Module: $RCSfile: ImageAdaptor4.cxx,v $ + Language: C++ + Date: $Date: 2005/11/20 13:27:52 $ + Version: $Revision: 1.12 $ + + Copyright (c) Insight Software Consortium. All rights reserved. + See ITKCopyright.txt or http://www.itk.org/HTML/Copyright.htm for details. + + This software is distributed WITHOUT ANY WARRANTY; without even + the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + PURPOSE. See the above copyright notices for more information. + +=========================================================================*/ + +#if defined(_MSC_VER) +#pragma warning ( disable : 4786 ) +#endif + +// Software Guide : BeginCommandLineArgs +// INPUTS: {QB_Suburb.png} +// OUTPUTS: {ImageAdaptorThresholdingA.png} +// 100 +// Software Guide : EndCommandLineArgs +// Software Guide : BeginCommandLineArgs +// INPUTS: {QB_Suburb.png} +// OUTPUTS: {ImageAdaptorThresholdingB.png} +// 200 +// Software Guide : EndCommandLineArgs + +// Software Guide : BeginLatex +// +// Image adaptors can also be used to perform simple pixel-wise computations +// on image data. The following example illustrates how to use the +// \doxygen{itk}{ImageAdaptor} for image thresholding. +// +// \index{itk::ImageAdaptor!Instantiation} +// \index{itk::ImageAdaptor!Header} +// \index{itk::ImageAdaptor!performing computation} +// \index{itk::PixelAccessor!with parameters} +// \index{itk::PixelAccessor!performing computation} +// +// Software Guide : EndLatex + +#include "otbImage.h" +#include "itkImageAdaptor.h" +#include "otbImageFileReader.h" +#include "otbImageFileWriter.h" +#include "itkRescaleIntensityImageFilter.h" + + +// Software Guide : BeginLatex +// +// A pixel accessor for image thresholding requires that the accessor +// maintain the threshold value. Therefore, it must also implement the +// assignment operator to set this internal parameter. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet +class ThresholdingPixelAccessor +{ +public: + typedef unsigned char InternalType; + typedef unsigned char ExternalType; + + ExternalType Get( const InternalType & input ) const + { + return (input > m_Threshold) ? 1 : 0; + } + void SetThreshold( const InternalType threshold ) + { + m_Threshold = threshold; + } + + void operator=( const ThresholdingPixelAccessor & vpa ) + { + m_Threshold = vpa.m_Threshold; + } +private: + InternalType m_Threshold; +}; +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// The \code{Get()} method returns one if the input pixel is above +// the threshold and zero otherwise. The assignment operator transfers +// the value of the threshold member +// variable from one instance of the pixel accessor to another. +// +// Software Guide : EndLatex + + +//------------------------- +// +// Main code +// +//------------------------- + +int main( int argc, char *argv[] ) +{ + if( argc < 4 ) + { + std::cerr << "Usage: " << std::endl; + std::cerr << "ImageAdaptor4 inputFileName outputBinaryFileName "; + std::cerr << " thresholdValue" << std::endl; + return -1; + } + + +// Software Guide : BeginLatex +// +// To create an image adaptor, we first instantiate an image type +// whose pixel type is the same as the internal pixel type of the pixel +// accessor. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef ThresholdingPixelAccessor::InternalType PixelType; + const unsigned int Dimension = 2; + typedef otb::Image< PixelType, Dimension > ImageType; +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// We instantiate the ImageAdaptor using the image type as the +// first template parameter and the pixel accessor as the second template +// parameter. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef itk::ImageAdaptor< ImageType, + ThresholdingPixelAccessor > ImageAdaptorType; + + ImageAdaptorType::Pointer adaptor = ImageAdaptorType::New(); +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// The threshold value is set from the command line. A threshold +// pixel accessor is created and connected to the image adaptor +// in the same manner as in the previous example. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + ThresholdingPixelAccessor accessor; + accessor.SetThreshold( atoi( argv[3] ) ); + adaptor->SetPixelAccessor( accessor ); +// Software Guide : EndCodeSnippet + + +// Software Guide : BeginLatex +// +// We create a reader to load the input image and connect the output +// of the reader as the input to the adaptor. +// +// Software Guide : EndLatex + + +// Software Guide : BeginCodeSnippet + typedef otb::ImageFileReader< ImageType > ReaderType; + ReaderType::Pointer reader = ReaderType::New(); + reader->SetFileName( argv[1] ); + reader->Update(); + + adaptor->SetImage( reader->GetOutput() ); +// Software Guide : EndCodeSnippet + + + typedef itk::RescaleIntensityImageFilter< ImageAdaptorType, + ImageType > RescalerType; + + RescalerType::Pointer rescaler = RescalerType::New(); + typedef otb::ImageFileWriter< ImageType > WriterType; + WriterType::Pointer writer = WriterType::New(); + + + writer->SetFileName( argv[2] ); + + rescaler->SetOutputMinimum( 0 ); + rescaler->SetOutputMaximum( 255 ); + + rescaler->SetInput( adaptor ); + writer->SetInput( rescaler->GetOutput() ); + writer->Update(); + + +// Software Guide : BeginLatex +// +// \begin{figure} \center +// \includegraphics[width=0.32\textwidth]{QB_Suburb.eps} +// \includegraphics[width=0.32\textwidth]{ImageAdaptorThresholdingA.eps} +// \includegraphics[width=0.32\textwidth]{ImageAdaptorThresholdingB.eps} +// \itkcaption[Image Adaptor for performing computations]{Using +// ImageAdaptor to perform a simple image computation. An +// ImageAdaptor is used to perform binary thresholding on +// the input image on the left. The center image was created using a +// threshold of 100, while the +// image on the right corresponds to a threshold of 200.} +// \label{fig:ImageAdaptorThresholding} +// \end{figure} +// +// As before, we rescale the emulated scalar image before writing it +// out to file. +// Figure~\ref{fig:ImageAdaptorThresholding} illustrates the result of +// applying the thresholding adaptor to a typical gray scale image using two +// different threshold values. Note that the same effect could have been +// achieved by using the \doxygen{itk}{BinaryThresholdImageFilter} but at the +// price of holding an extra copy of the image in memory. +// +// Software Guide : EndLatex + + + return 0; +} + + +