21 #ifndef otbSarDeburstImageFilter_hxx
22 #define otbSarDeburstImageFilter_hxx
27 #include "itkImageScanlineIterator.h"
28 #include "itkImageScanlineConstIterator.h"
29 #include "itkImageRegionIterator.h"
30 #include "itkImageRegionConstIterator.h"
35 template <
class TImage>
41 template <
class TImage>
45 Superclass::GenerateOutputInformation();
48 const ImageType* inputPtr = this->GetInput();
52 if (std::abs(inputPtr->GetSignedSpacing()[1] - 1.) >= std::numeric_limits<double>::epsilon())
53 itkExceptionMacro(
"Can not perform deburst if input image azimuth spacing is not 1.");
56 if (std::abs(inputPtr->GetOrigin()[1] -
static_cast<long>(inputPtr->GetOrigin()[1]) - 0.5) >= std::numeric_limits<double>::epsilon())
57 itkExceptionMacro(
"Can not perform deburst if input image azimuth origin is not N.5");
60 auto imd = inputPtr->GetImageMetadata();
65 bool deburstOk = sarSensorModel.
Deburst(m_LinesRecord, m_SamplesRecord, m_OnlyValidSample);
67 if (!deburstOk || m_LinesRecord.empty())
68 itkExceptionMacro(<<
"Could not deburst SAR sensor model from input image");
71 typename ImageType::RegionType largestPossibleRegion = this->GetInput()->GetLargestPossibleRegion();
72 typename ImageType::PointType origin = this->GetInput()->GetOrigin();
76 long firstInputLine =
static_cast<long>(origin[1] - 0.5);
79 long lastInputLine =
static_cast<long>(origin[1] - 0.5 + largestPossibleRegion.GetSize()[1] - 1);
82 unsigned long outputOriginLine = 0;
85 long originOffset_samples =
static_cast<long>(this->GetInput()->GetOrigin()[0] - 0.5);
86 unsigned long outputOriginSample = 0;
87 if (m_OnlyValidSample)
89 if (
static_cast<int>(m_SamplesRecord.first) > originOffset_samples)
91 outputOriginSample = 0;
95 outputOriginSample = originOffset_samples -
static_cast<int>(m_SamplesRecord.first);
97 origin[0] = 0.5 + outputOriginSample;
100 origin[1] = 0.5 + outputOriginLine;
101 outputPtr->SetOrigin(origin);
106 for (LinesRecordVectorType::const_iterator it = m_LinesRecord.begin(); it != m_LinesRecord.end(); ++it)
109 if ((
long)it->first <= lastInputLine && (long)it->second >= firstInputLine)
112 filteredRecord.first = std::max(
static_cast<long>(filteredRecord.first), firstInputLine);
113 filteredRecord.second = std::min(
static_cast<long>(filteredRecord.second), lastInputLine);
114 filteredRecords.push_back(filteredRecord);
125 typename ImageType::SizeType deburstSize = largestPossibleRegion.GetSize();
129 for (LinesRecordVectorType::const_iterator it = filteredRecords.begin(); it != filteredRecords.end(); ++it)
131 deburstSize[1] += it->second - it->first + 1;
134 if (m_OnlyValidSample)
136 long minEnd =
static_cast<long>(
137 std::min(
static_cast<long>(m_SamplesRecord.second),
static_cast<long>(largestPossibleRegion.GetSize()[0] + originOffset_samples - 1)));
138 long maxStart =
static_cast<long>(std::max(
static_cast<long>(m_SamplesRecord.first), originOffset_samples));
139 deburstSize[0] = minEnd - maxStart + 1;
143 typename ImageType::RegionType outputLargestPossibleRegion = largestPossibleRegion;
144 largestPossibleRegion.SetSize(deburstSize);
145 outputPtr->SetLargestPossibleRegion(largestPossibleRegion);
152 outputPtr->SetImageMetadata(imd);
155 template <
class TImage>
158 PointType outputUperLeft, outputLowerLeft;
160 typename RegionType::IndexType outputUpperLeftIndex = outputRegion.GetIndex();
161 typename RegionType::IndexType outputLowerLeftIndex = outputUpperLeftIndex;
162 outputLowerLeftIndex[1] += outputRegion.GetSize()[1] - 1;
164 this->GetOutput()->TransformIndexToPhysicalPoint(outputUpperLeftIndex, outputUperLeft);
165 this->GetOutput()->TransformIndexToPhysicalPoint(outputLowerLeftIndex, outputLowerLeft);
168 unsigned long upperLeftLine =
static_cast<unsigned long>(outputUperLeft[1] - 0.5);
169 unsigned long lowerLeftLine =
static_cast<unsigned long>(outputLowerLeft[1] - 0.5);
171 unsigned long inputUpperLeftLine, inputLowerLeftLine;
176 long originOffset =
static_cast<long>(this->GetInput()->GetOrigin()[1] - 0.5);
177 long originOffset_samples =
static_cast<long>(this->GetInput()->GetOrigin()[0] - 0.5);
179 inputUpperLeftLine -= originOffset;
180 inputLowerLeftLine -= originOffset;
184 typename RegionType::SizeType size = inputRegion.GetSize();
185 typename RegionType::IndexType index = inputRegion.GetIndex();
187 if (m_OnlyValidSample)
189 if (
static_cast<int>(m_SamplesRecord.first) > originOffset_samples)
191 index[0] += m_SamplesRecord.first - originOffset_samples;
195 index[1] = inputUpperLeftLine;
196 size[1] = inputLowerLeftLine - inputUpperLeftLine + 1;
198 inputRegion.SetIndex(index);
199 inputRegion.SetSize(size);
206 template <
class TImage>
209 RegionType outputRequestedRegion = this->GetOutput()->GetRequestedRegion();
210 RegionType inputRequestedRegion = OutputRegionToInputRegion(outputRequestedRegion);
214 inputPtr->SetRequestedRegion(inputRequestedRegion);
218 template <
class TImage>
221 if (m_OnlyValidSample)
223 this->ThreadedGenerateDataWithOnlyValidSamples(outputRegionForThread, 0);
227 this->ThreadedGenerateDataWithAllSamples(outputRegionForThread, 0);
232 template <
class TImage>
236 RegionType inputRegionForThread = OutputRegionToInputRegion(outputRegionForThread);
238 itk::ImageScanlineConstIterator<ImageType> inputIt(this->GetInput(), inputRegionForThread);
239 itk::ImageScanlineIterator<ImageType> outputIt(this->GetOutput(), outputRegionForThread);
242 outputIt.GoToBegin();
244 while (!inputIt.IsAtEnd() && !outputIt.IsAtEnd())
246 typename ImageType::IndexType currentInputIndex = inputIt.GetIndex();
248 this->GetInput()->TransformIndexToPhysicalPoint(currentInputIndex, currentInputPoint);
250 bool lineToKeep =
false;
252 for (
auto const& record : m_LinesRecord)
254 if (currentInputPoint[1] - 0.5 >= record.first && currentInputPoint[1] - 0.5 <= record.second)
262 for (inputIt.GoToBeginOfLine(), outputIt.GoToBeginOfLine(); !inputIt.IsAtEndOfLine() && !outputIt.IsAtEndOfLine(); ++inputIt, ++outputIt)
264 outputIt.Set(inputIt.Get());
275 template <
class TImage>
279 RegionType inputRegionForThread = OutputRegionToInputRegion(outputRegionForThread);
281 itk::ImageRegionConstIterator<ImageType> inputIt(this->GetInput(), inputRegionForThread);
282 itk::ImageRegionIterator<ImageType> outputIt(this->GetOutput(), outputRegionForThread);
285 outputIt.GoToBegin();
287 while (!inputIt.IsAtEnd() && !outputIt.IsAtEnd())
289 typename ImageType::IndexType currentInputIndex = inputIt.GetIndex();
291 this->GetInput()->TransformIndexToPhysicalPoint(currentInputIndex, currentInputPoint);
293 bool lineToKeep =
false;
294 bool sampleToKeep =
false;
296 for (
auto const& record : m_LinesRecord)
298 if (currentInputPoint[1] - 0.5 >= record.first && currentInputPoint[1] - 0.5 <= record.second)
305 if (currentInputPoint[0] - 0.5 >=
static_cast<int>(m_SamplesRecord.first) && currentInputPoint[1] - 0.5 <=
static_cast<int>(m_SamplesRecord.second))
310 if (lineToKeep && sampleToKeep)
312 outputIt.Set(inputIt.Get());