1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138
|
/*
* Copyright (C) 1999-2011 Insight Software Consortium
* Copyright (C) 2005-2022 Centre National d'Etudes Spatiales (CNES)
*
* This file is part of Orfeo Toolbox
*
* https://www.orfeo-toolbox.org/
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <iostream>
// This example shows how to read a list of images and concatenate
// them into a vector image. We will write a program which is able to
// perform this operation taking advantage of the streaming
// functionalities of the processing pipeline. We will assume that
// all the input images have the same size and a single band.
//
// The following header files will be needed:
#include "otbImage.h"
#include "otbVectorImage.h"
#include "otbImageFileReader.h"
#include "otbImageList.h"
#include "otbImageListToVectorImageFilter.h"
#include "otbImageFileWriter.h"
int main(int argc, char** argv)
{
if (argc < 4)
{
std::cerr << "Usage: " << argv[0];
std::cerr << "outputImage image1 image2 ... " << std::endl;
}
const unsigned int NbImages = argc - 2;
std::cout << "Concat of " << NbImages << " images into a multi-band image " << std::endl;
// We will start by defining the types for the input images and the
// associated readers.
using PixelType = unsigned short;
const unsigned int Dimension = 2;
using InputImageType = otb::Image<PixelType, Dimension>;
using ImageReaderType = otb::ImageFileReader<InputImageType>;
// We will use a list of image file readers in order to open all the
// input images at once. For this, we use the
// \doxygen{otb}{ObjectList} object and we template it over the type
// of the readers.
using ReaderListType = otb::ObjectList<ImageReaderType>;
ReaderListType::Pointer readerList = ReaderListType::New();
// We will also build a list of input images in order to store the
// smart pointers obtained at the output of each reader. This allows
// us to build a pipeline without really reading the images and using
// lots of RAM. The \doxygen{otb}{ImageList} object will be used.
using ImageListType = otb::ImageList<InputImageType>;
ImageListType::Pointer imageList = ImageListType::New();
// We can now loop over the input image list in order to populate the
// reader list and the input image list.
for (unsigned int i = 0; i < NbImages; ++i)
{
ImageReaderType::Pointer imageReader = ImageReaderType::New();
imageReader->SetFileName(argv[i + 2]);
std::cout << "Adding image " << argv[i + 2] << std::endl;
imageReader->UpdateOutputInformation();
imageList->PushBack(imageReader->GetOutput());
readerList->PushBack(imageReader);
}
// All the input images will be concatenated into a single output
// vector image. For this matter, we will use the
// \doxygen{otb}{ImageListToVectorImageFilter} which is templated
// over the input image list type and the output vector image type.
using VectorImageType = otb::VectorImage<PixelType, Dimension>;
using ImageListToVectorImageFilterType = otb::ImageListToVectorImageFilter<ImageListType, VectorImageType>;
ImageListToVectorImageFilterType::Pointer iL2VI = ImageListToVectorImageFilterType::New();
// We plug the image list as input of the filter and use a
// \doxygen{otb}{ImageFileWriter} to write the result image
// to a file, so that the streaming capabilities of all the readers
// and the filter are used.
iL2VI->SetInput(imageList);
using ImageWriterType = otb::ImageFileWriter<VectorImageType>;
ImageWriterType::Pointer imageWriter = ImageWriterType::New();
imageWriter->SetFileName(argv[1]);
// We can tune the size of the image tiles, so that the
// total memory footprint of the pipeline is constant
// for any execution of the program.
unsigned long memoryConsumptionInMB = 10;
std::cout << "Memory consumption: " << memoryConsumptionInMB << std::endl;
imageWriter->SetAutomaticTiledStreaming(memoryConsumptionInMB);
imageWriter->SetInput(iL2VI->GetOutput());
imageWriter->Update();
return EXIT_SUCCESS;
}
|