diff --git a/include/otbSARTemporalCorrelationGridImageFilter.h b/include/otbSARTemporalCorrelationGridImageFilter.h index f0085955f9b0275bbd3fe18e986da48925cfb9c0..3ed5d683e764ec4fec9cdafaaf5edf448ce6fcb8 100644 --- a/include/otbSARTemporalCorrelationGridImageFilter.h +++ b/include/otbSARTemporalCorrelationGridImageFilter.h @@ -184,7 +184,7 @@ namespace otb /** * OutputRegionToInputRegion assigne master and slave regions */ - void OutputRegionToInputRegion(const ImageOutRegionType& outputRegion) const; + void OutputRegionToInputRegion(const ImageOutRegionType& outputRegion); /** SARTemporalCorrelationGridImageFilter can be implemented as a multithreaded filter. * Therefore, this implementation provides a ThreadedGenerateData() routine @@ -242,6 +242,9 @@ namespace otb ImageInPointer * m_masterExtractPieceTab; ImageInPointer * m_slaveExtractPieceTab; + // Boolean to add an offset on the first L/C on the grid + bool m_FirstLCOffset; + }; } // End namespace otb diff --git a/include/otbSARTemporalCorrelationGridImageFilter.txx b/include/otbSARTemporalCorrelationGridImageFilter.txx index d51e18eda9176506f8526ee8ba5a70b2dc14b1e0..38191291b28e81fe7b017e0fef437c6d08ba991d 100644 --- a/include/otbSARTemporalCorrelationGridImageFilter.txx +++ b/include/otbSARTemporalCorrelationGridImageFilter.txx @@ -65,6 +65,8 @@ namespace otb m_CorrelationThreshold = 0.3; + m_FirstLCOffset = true; + m_MLran = 3; m_MLazi = 3; } @@ -224,25 +226,42 @@ namespace otb ImageOutSpacingType outputSpacing = static_cast<ImageOutSpacingType>(masterPtr->GetSpacing()); ImageOutPointType outputOrigin = static_cast<ImageOutPointType>(masterPtr->GetOrigin()); - // First/Last Colunm and row - int firstC = std::max (1 + m_WinCor_ran, 1 + m_WinCor_ran - m_RoughShift_ran + m_WinAround_ShiftRan); - int firstL = std::max (1 + m_WinCor_azi, 1 + m_WinCor_azi - m_RoughShift_azi + m_WinAround_ShiftAzi); - int lastC = std::min(slavePtr->GetLargestPossibleRegion().GetSize()[0] - m_RoughShift_ran - - m_WinAround_ShiftRan - m_WinCor_ran, masterPtr->GetLargestPossibleRegion().GetSize()[0] - - m_WinCor_ran); - int lastL = std::min(slavePtr->GetLargestPossibleRegion().GetSize()[1] - m_RoughShift_azi - - m_WinAround_ShiftAzi- m_WinCor_azi, masterPtr->GetLargestPossibleRegion().GetSize()[1] - - m_WinCor_azi); + // First/Last Colunm and row with an offet + int firstC_master = 0; + int firstL_master = 0; + if (m_FirstLCOffset) + { + int firstC = std::max (1 + m_WinCor_ran, 1 + m_WinCor_ran - m_RoughShift_ran + m_WinAround_ShiftRan); + int firstL = std::max (1 + m_WinCor_azi, 1 + m_WinCor_azi - m_RoughShift_azi + m_WinAround_ShiftAzi); + int lastC = std::min(slavePtr->GetLargestPossibleRegion().GetSize()[0] - m_RoughShift_ran - + m_WinAround_ShiftRan - m_WinCor_ran, + masterPtr->GetLargestPossibleRegion().GetSize()[0]- m_WinCor_ran); + int lastL = std::min(slavePtr->GetLargestPossibleRegion().GetSize()[1] - m_RoughShift_azi - + m_WinAround_ShiftAzi- m_WinCor_azi, + masterPtr->GetLargestPossibleRegion().GetSize()[1] - m_WinCor_azi); - outputSize[0]= lastC - firstC + 1; - outputSize[1] = lastL - firstL + 1; - + outputSize[0]= lastC - firstC + 1; + outputSize[1] = lastL - firstL + 1; + + for(unsigned int dim = 0; dim < ImageOutType::ImageDimension; ++dim) + { + outputSize[dim] = (outputSize[dim] - outputSize[dim]%m_GridStep_ML[dim]) / m_GridStep_ML[dim]; + outputSpacing[dim] *= m_GridStep_ML[dim]; + } + + firstL_master = firstL + (lastL - firstL + 1 - m_GridStep_ML[1] * (outputSize[1])) / 2; + firstC_master = firstC + (lastC - firstC + 1 - m_GridStep_ML[0] * (outputSize[0])) / 2; + } + else + { + for(unsigned int dim = 0; dim < ImageOutType::ImageDimension; ++dim) + { + outputSize[dim] = (outputSize[dim] - outputSize[dim]%m_GridStep_ML[dim]) / m_GridStep_ML[dim]; + outputSpacing[dim] *= m_GridStep_ML[dim]; + } + } - for(unsigned int dim = 0; dim < ImageOutType::ImageDimension; ++dim) - { - outputSize[dim] = (outputSize[dim] - outputSize[dim]%m_GridStep_ML[dim]) / m_GridStep_ML[dim]; - outputSpacing[dim] *= m_GridStep_ML[dim]; - } + // Set spacing outputPtr->SetSpacing(outputSpacing); @@ -259,6 +278,16 @@ namespace otb outputKWL.AddKey("support_data.gridstep.range", std::to_string(m_GridStep[0])); outputKWL.AddKey("support_data.gridstep.azimut", std::to_string(m_GridStep[1])); + if (m_FirstLCOffset) + { + // Add first L/C into SLC geometry + float firstC_SLC = (firstC_master)*m_MLran; + float firstL_SLC = (firstL_master)*m_MLazi; + + outputKWL.AddKey("support_data.grid.first_row", std::to_string(firstL_SLC)); + outputKWL.AddKey("support_data.grid.first_column", std::to_string(firstC_SLC)); + } + outputPtr->SetImageKeywordList(outputKWL); } @@ -268,11 +297,13 @@ namespace otb template<class TImageIn, class TImageOut> void SARTemporalCorrelationGridImageFilter< TImageIn, TImageOut > - ::OutputRegionToInputRegion(const ImageOutRegionType& outputRegion) const + ::OutputRegionToInputRegion(const ImageOutRegionType& outputRegion) { // Get pointers to inputs ImageInType * masterPtr = const_cast<ImageInType * >(GetMasterInput()); ImageInType * slavePtr = const_cast<ImageInType * >(GetSlaveInput()); + + ImageOutPointer outputPtr = this->GetOutput(); int nbColSlave = slavePtr->GetLargestPossibleRegion().GetSize()[0]; int nbLinesSlave = slavePtr->GetLargestPossibleRegion().GetSize()[1]; @@ -295,14 +326,32 @@ namespace otb masterRequestedIndex[dim] *= m_GridStep_ML[dim]; } - int firstC_Grid = std::max (1 + m_WinCor_ran, 1 + m_WinCor_ran - m_RoughShift_ran + m_WinAround_ShiftRan); - int firstL_Grid = std::max (1 + m_WinCor_azi, 1 + m_WinCor_azi - m_RoughShift_azi + m_WinAround_ShiftAzi); - + int firstC_Grid = 0; + int firstL_Grid = 0; + + if (m_FirstLCOffset) + { + int firstC = std::max (1 + m_WinCor_ran, 1 + m_WinCor_ran - m_RoughShift_ran + m_WinAround_ShiftRan); + int firstL = std::max (1 + m_WinCor_azi, 1 + m_WinCor_azi - m_RoughShift_azi + m_WinAround_ShiftAzi); + int lastC = std::min(slavePtr->GetLargestPossibleRegion().GetSize()[0] - m_RoughShift_ran - + m_WinAround_ShiftRan - m_WinCor_ran, + masterPtr->GetLargestPossibleRegion().GetSize()[0]- m_WinCor_ran); + int lastL = std::min(slavePtr->GetLargestPossibleRegion().GetSize()[1] - m_RoughShift_azi - + m_WinAround_ShiftAzi- m_WinCor_azi, + masterPtr->GetLargestPossibleRegion().GetSize()[1] - m_WinCor_azi); + + + firstC_Grid = firstC + (lastC - firstC + 1 - m_GridStep_ML[0] * + (outputPtr->GetLargestPossibleRegion().GetSize()[0])) / 2; + firstL_Grid = firstL + (lastL - firstL + 1 - m_GridStep_ML[1] * + (outputPtr->GetLargestPossibleRegion().GetSize()[1])) / 2; + } + // With correlation window and first row/colunm masterRequestedIndex[0] -= (m_WinCor_ran - firstC_Grid); masterRequestedIndex[1] -= (m_WinCor_azi - firstL_Grid); - masterRequestedSize[0] += (2*m_WinCor_ran+1) + firstC_Grid; - masterRequestedSize[1] += (2*m_WinCor_azi+1) + firstL_Grid; + masterRequestedSize[0] += (2*m_WinCor_ran+1); + masterRequestedSize[1] += (2*m_WinCor_azi+1); masterRequestedRegion.SetSize(masterRequestedSize); masterRequestedRegion.SetIndex(masterRequestedIndex); @@ -424,6 +473,8 @@ namespace otb const ImageInType * masterPtr = this->GetMasterInput(); const ImageInType * slavePtr = this->GetSlaveInput(); + ImageOutPointer outPtr = this->GetOutput(); + // Typedef for iterators typedef itk::ImageScanlineIterator< ImageOutType > OutputIterator; typedef itk::ImageRegionConstIterator<ImageInType> MasterSlaveIt; @@ -463,10 +514,26 @@ namespace otb std::vector<double> slave; // First L/C for the grid - int firstC = std::max (1 + m_WinCor_ran, 1 + m_WinCor_ran - m_RoughShift_ran + m_WinAround_ShiftRan); - int firstL = std::max (1 + m_WinCor_azi, 1 + m_WinCor_azi - m_RoughShift_azi + m_WinAround_ShiftAzi); - - + int firstC_Grid = 0; + int firstL_Grid = 0; + + if (m_FirstLCOffset) + { + int firstC = std::max (1 + m_WinCor_ran, 1 + m_WinCor_ran - m_RoughShift_ran + m_WinAround_ShiftRan); + int firstL = std::max (1 + m_WinCor_azi, 1 + m_WinCor_azi - m_RoughShift_azi + m_WinAround_ShiftAzi); + int lastC = std::min(slavePtr->GetLargestPossibleRegion().GetSize()[0] - m_RoughShift_ran - + m_WinAround_ShiftRan - m_WinCor_ran, + masterPtr->GetLargestPossibleRegion().GetSize()[0]- m_WinCor_ran); + int lastL = std::min(slavePtr->GetLargestPossibleRegion().GetSize()[1] - m_RoughShift_azi - + m_WinAround_ShiftAzi- m_WinCor_azi, + masterPtr->GetLargestPossibleRegion().GetSize()[1] - m_WinCor_azi); + + firstC_Grid = firstC + (lastC - firstC + 1 - m_GridStep_ML[0] * + (outPtr->GetLargestPossibleRegion().GetSize()[0])) / 2; + firstL_Grid = firstL + (lastL - firstL + 1 - m_GridStep_ML[1] * + (outPtr->GetLargestPossibleRegion().GetSize()[1])) / 2; + } + // For each line of output while ( !OutIt.IsAtEnd()) { @@ -484,8 +551,8 @@ namespace otb } // To center correlation estimation and shift to the first L/C - masterIndex[0] -= (m_WinCor_ran-firstC); - masterIndex[1] -= (m_WinCor_azi-firstL); + masterIndex[0] -= (m_WinCor_ran-firstC_Grid); + masterIndex[1] -= (m_WinCor_azi-firstL_Grid); // Build the master region (for correlation estimation) ImageInRegionType masterCurrentRegion;