1 /*=========================================================================
2  *
3  *  Copyright Insight Software Consortium
4  *
5  *  Licensed under the Apache License, Version 2.0 (the "License");
6  *  you may not use this file except in compliance with the License.
7  *  You may obtain a copy of the License at
8  *
9  *         http://www.apache.org/licenses/LICENSE-2.0.txt
10  *
11  *  Unless required by applicable law or agreed to in writing, software
12  *  distributed under the License is distributed on an "AS IS" BASIS,
13  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  *  See the License for the specific language governing permissions and
15  *  limitations under the License.
16  *
17  *=========================================================================*/
18 #ifndef itkImageRegionExclusionConstIteratorWithIndex_h
19 #define itkImageRegionExclusionConstIteratorWithIndex_h
20 
21 #include "itkImageRegionConstIteratorWithIndex.h"
22 
23 namespace itk
24 {
25 /** \class ImageRegionExclusionConstIteratorWithIndex
26  *
27  *  \brief A multi-dimensional image iterator that walks an image region,
28  *         excluding a second region that may partially or completely
29  *         overlap the first, with read-only access to pixels.
30  *
31  * ImageRegionExclusionConstIteratorWithIndex is a class templated
32  * over the image type that represents a multi-dimensional
33  * iterator. The exclusion region is set after construction. By
34  * default the exclusion region is empty and the iterator will behave
35  * as the itk::ImageRegionConstIteratorWithIndex with a penalty in
36  * performance due to internal bounds checking. There are no
37  * restrictions on valid exclusion regions.
38  *
39  * As with other ITK image iterators,
40  * ImageRegionExclusionConstIteratorWithIndex requires that more
41  * information be specified before the iterator can be used than
42  * conventional iterators. Whereas the std::vector::iterator from the
43  * STL only needs to be passed a pointer to establish the iterator,
44  * the multi-dimensional image iterator needs a pointer, the size of
45  * the buffer, the size of the region, the start index of the buffer,
46  * and the start index of the region. To gain access to this
47  * information, ImageRegionExclusionConstIteratorWithIndex holds a
48  * reference to the image over which it is traversing.
49  *
50  * ImageRegionExclusionConstIteratorWithIndex assumes a particular
51  * layout of the image data. The is arranged in a 1D array as if it
52  * were [][][][slice][row][col] with Index[0] = col, Index[1] = row,
53  * Index[2] = slice, etc.
54  *
55  * The operator++ method provides a simple syntax for walking around a
56  * region of a multidimensional image. operator++ iterates across a
57  * row, constraining the movement to within a region of image. When
58  * the iterator reaches the boundary of the region along a row, the
59  * iterator automatically wraps to the next row, starting at the first
60  * pixel in the row that is part of the region. This allows for simple
61  * processing loops of the form:
62  *
63    \code
64 
65     IteratorType it( image, image->GetRequestedRegion() );
66 
67     it.SetExclusionRegion( exclusionRegion );
68     it.GoToBegin();
69 
70     while( ! it.IsAtEnd() )
71     {
72       it.Set( 100.0 + it.Get() );
73       ++it;
74     }
75 
76    \endcode
77  *
78  *  It also can be used for walking in the reverse direction like
79  *
80    \code
81 
82     IteratorType it( image, image->GetRequestedRegion() );
83 
84     it.SetExclusionRegion( exclusionRegion );
85     it.GoToEnd();
86 
87     while( !it.IsAtBegin() )
88     {
89       it.Set( 100.0 );
90       --it;
91     }
92 
93    \endcode
94  *
95  * \par MORE INFORMATION
96  * For a complete description of the ITK Image Iterators and their API, please
97  * see the Iterators chapter in the ITK Software Guide.  The ITK Software Guide
98  * is available in print and as a free .pdf download from https://www.itk.org.
99  *
100  * \ingroup ImageIterators
101  *
102  * \sa ImageConstIterator \sa ConditionalConstIterator
103  * \sa ConstNeighborhoodIterator \sa ConstShapedNeighborhoodIterator
104  * \sa ConstSliceIterator  \sa CorrespondenceDataStructureIterator
105  * \sa FloodFilledFunctionConditionalConstIterator
106  * \sa FloodFilledImageFunctionConditionalConstIterator
107  * \sa FloodFilledImageFunctionConditionalIterator
108  * \sa FloodFilledSpatialFunctionConditionalConstIterator
109  * \sa FloodFilledSpatialFunctionConditionalIterator
110  * \sa ImageConstIterator \sa ImageConstIteratorWithIndex
111  * \sa ImageIterator \sa ImageIteratorWithIndex
112  * \sa ImageLinearConstIteratorWithIndex  \sa ImageLinearIteratorWithIndex
113  * \sa ImageRandomConstIteratorWithIndex  \sa ImageRandomIteratorWithIndex
114  * \sa ImageRegionConstIterator \sa ImageRegionConstIteratorWithIndex
115  * \sa ImageRegionExclusionConstIteratorWithIndex
116  * \sa ImageRegionExclusionIteratorWithIndex
117  * \sa ImageRegionIterator  \sa ImageRegionIteratorWithIndex
118  * \sa ImageRegionReverseConstIterator  \sa ImageRegionReverseIterator
119  * \sa ImageReverseConstIterator  \sa ImageReverseIterator
120  * \sa ImageSliceConstIteratorWithIndex  \sa ImageSliceIteratorWithIndex
121  * \sa NeighborhoodIterator \sa PathConstIterator  \sa PathIterator
122  * \sa ShapedNeighborhoodIterator  \sa SliceIterator
123  * \sa ImageConstIteratorWithIndex
124  * \ingroup ITKCommon
125  *
126  * \wiki
127  * \wikiexample{Iterators/ImageRegionExclusionConstIteratorWithIndex,Iterator over an image skipping a specified region}
128  * \endwiki
129  */
130 template< typename TImage >
131 class ITK_TEMPLATE_EXPORT ImageRegionExclusionConstIteratorWithIndex:
132   public ImageRegionConstIteratorWithIndex< TImage >
133 {
134 public:
135   /** Standard class type aliases. */
136   using Self = ImageRegionExclusionConstIteratorWithIndex;
137   using Superclass = ImageRegionConstIteratorWithIndex< TImage >;
138 
139   /** Types inherited from the Superclass */
140   using IndexType = typename Superclass::IndexType;
141   using SizeType = typename Superclass::SizeType;
142   using OffsetType = typename Superclass::OffsetType;
143   using RegionType = typename Superclass::RegionType;
144   using ImageType = typename Superclass::ImageType;
145   using PixelContainer = typename Superclass::PixelContainer;
146   using PixelContainerPointer = typename Superclass::PixelContainerPointer;
147   using InternalPixelType = typename Superclass::InternalPixelType;
148   using PixelType = typename Superclass::PixelType;
149   using AccessorType = typename Superclass::AccessorType;
150 
151   /** Default constructor. Needed since we provide a cast constructor. */
152   ImageRegionExclusionConstIteratorWithIndex()= default;
153 
154   /** Constructor establishes an iterator to walk a particular image and a
155    * particular region of that image. */
156   ImageRegionExclusionConstIteratorWithIndex(const ImageType *ptr,
157                                              const RegionType & region);
158 
159   /** Constructor that can be used to cast from an ImageRegionConstIteratorWithIndex
160    * to an ImageRegionExclusionConstIteratorWithIndex. Many routines return an
161    * ImageIterator, but for a particular task, you may want an
162    * ImageRegionExclusionConstIteratorWithIndex. Rather than provide overloaded
163    * APIs that return different types of Iterators, itk returns ImageIterators
164    * and uses constructors to cast from an ImageIterator to a
165    * ImageRegionExclusionConstIteratorWithIndex. */
166   ImageRegionExclusionConstIteratorWithIndex(const Superclass & it);
167 
168   /** Increment (prefix) the fastest moving dimension of the iterator's index.
169    * This operator will constrain the iterator within the region (i.e. the
170    * iterator will automatically wrap from the end of the row of the region
171    * to the beginning of the next row of the region) up until the iterator
172    * tries to moves past the last pixel of the region.  Here, the iterator
173    * will be set to be one pixel past the end of the region.
174    * \sa operator++(int) */
175   Self & operator++();
176 
177   /** Decrement (prefix) the fastest moving dimension of the iterator's index.
178    * This operator will constrain the iterator within the region (i.e. the
179    * iterator will automatically wrap from the beginning of the row of the region
180    * to the end of the next row of the region) up until the iterator
181    * tries to moves past the first pixel of the region.  Here, the iterator
182    * will be set to be one pixel past the beginning of the region.
183    * \sa operator--(int) */
184   Self & operator--();
185 
186   /** Method to define the Exclusion region. The iterator will skip pixels
187    * inside this region.
188    * \warning The exclusion region must be completly contained inside the
189    * normal region used to construct the iterator. A border of at least one
190    * pixel should exist between the normal region and the exclusion region.
191    */
192   void SetExclusionRegion(const RegionType & region);
193 
194   /** Set the exclusion region to be inset one pixel in from the
195    * region the iterator walks. This configures the iterator to only
196    * walk the pixels on the boundary of the region.
197    */
198   void SetExclusionRegionToInsetRegion();
199 
200   /** Move an iterator to the beginning of the non-excluded region. */
201   void GoToBegin();
202 
203   /** Move an iterator to the End of the region. */
204   void GoToReverseBegin();
205 
206 private:
207 
208   RegionType m_ExclusionRegion;
209 
210   IndexType m_ExclusionBegin;
211   IndexType m_ExclusionEnd;
212 };
213 } // end namespace itk
214 
215 #ifndef ITK_MANUAL_INSTANTIATION
216 #include "itkImageRegionExclusionConstIteratorWithIndex.hxx"
217 #endif
218 
219 #endif
220