Ocean
Loading...
Searching...
No Matches
FrameFilterDilation.h
Go to the documentation of this file.
1/*
2 * Copyright (c) Meta Platforms, Inc. and affiliates.
3 *
4 * This source code is licensed under the MIT license found in the
5 * LICENSE file in the root directory of this source tree.
6 */
7
8#ifndef META_OCEAN_CV_FRAME_FILTER_DILATION_H
9#define META_OCEAN_CV_FRAME_FILTER_DILATION_H
10
11#include "ocean/cv/CV.h"
14
15#include "ocean/base/Frame.h"
16#include "ocean/base/Worker.h"
17
18namespace Ocean
19{
20
21namespace CV
22{
23
24/**
25 * This class implements a frame dilation filter.
26 * @ingroup cv
27 */
28class OCEAN_CV_EXPORT FrameFilterDilation : public FrameFilterMorphology
29{
30 public:
31
32 /**
33 * Applies several dilation filter iterations for an 8 bit mask image.
34 * The value of a mask pixel (to be dilated) can be defined, every other pixel value is interpreted as a non-mask pixels.
35 * @param mask The mask frame to be filtered, must be valid
36 * @param width The width of the mask frame in pixel, with range [4, infinity)
37 * @param height The height of the mask frame in pixel, with range [4, infinity)
38 * @param iterations Number of iterations to be applied, best performance when number of iterations is even, with range [1, infinity)
39 * @param maskValue The value of a mask pixel to be dilated, pixels with other values will be untouched, with range [0, 255]
40 * @param maskPaddingElements Optional number of padding elements at the end of each mask row, in elements, with range [0, infinity)
41 * @param worker Optional worker object to distribute the computation
42 * @tparam tDilationFilter The type of the dilation filter to be applied
43 * @see filter1Channel8Bit4Neighbor(), filter1Channel8Bit8Neighbor().
44 */
45 template <MorphologyFilter tDilationFilter>
46 static void filter1Channel8Bit(uint8_t* mask, const unsigned int width, const unsigned int height, const unsigned int iterations, const uint8_t maskValue = 0x00, const unsigned int maskPaddingElements = 0u, Worker* worker = nullptr);
47
48 /**
49 * Applies one dilation filter iteration for an 8 bit mask image using a 4-neighborhood.
50 * The value of a mask pixel (to be dilated) can be defined, every other pixel value is interpreted as a non-mask pixels.
51 * @param mask The mask frame to be filtered, must be valid
52 * @param target The target frame receiving the filter response, must be valid
53 * @param width The width of the mask frame in pixel, with range [2, infinity)
54 * @param height The height of the mask frame in pixel, with range [2, infinity)
55 * @param maskValue The value of a mask pixel to be dilated, pixels with other values will be untouched, with range [0, 255]
56 * @param maskPaddingElements Optional number of padding elements at the end of each mask row, in elements, with range [0, infinity)
57 * @param targetPaddingElements Optional number of padding elements at the end of each target row, in elements, with range [0, infinity)
58 * @param worker Optional worker object to distribute the computation
59 */
60 static inline void filter1Channel8Bit4Neighbor(const uint8_t* mask, uint8_t* target, const unsigned int width, const unsigned int height, const uint8_t maskValue = 0x00, const unsigned int maskPaddingElements = 0u, const unsigned int targetPaddingElements = 0u, Worker* worker = nullptr);
61
62 /**
63 * Applies one dilation filter iteration for an 8 bit mask image using a 8-neighborhood, a 3x3 square kernel.
64 * The value of a mask pixel (to be dilated) can be defined, every other pixel value is interpreted as a non-mask pixels.
65 * @param mask The mask frame to be filtered, must be valid
66 * @param target The target frame receiving the filter response, must be valid
67 * @param width The width of the mask frame in pixel, with range [2, infinity)
68 * @param height The height of the mask frame in pixel, with range [2, infinity)
69 * @param maskValue The value of a mask pixel to be dilated, pixels with other values will be untouched, with range [0, 255]
70 * @param maskPaddingElements Optional number of padding elements at the end of each mask row, in elements, with range [0, infinity)
71 * @param targetPaddingElements Optional number of padding elements at the end of each target row, in elements, with range [0, infinity)
72 * @param worker Optional worker object to distribute the computation
73 */
74 static inline void filter1Channel8Bit8Neighbor(const uint8_t* mask, uint8_t* target, const unsigned int width, const unsigned int height, const uint8_t maskValue = 0x00, const unsigned int maskPaddingElements = 0u, const unsigned int targetPaddingElements = 0u, Worker* worker = nullptr);
75
76 /**
77 * Applies one dilation filter iteration for an 8 bit mask image using a 24-neighborhood, a 5x5 square kernel.
78 * The value of a mask pixel (to be dilated) can be defined, every other pixel value is interpreted as a non-mask pixels.
79 * @param mask The mask frame to be filtered, must be valid
80 * @param target The target frame receiving the filter response, must be valid
81 * @param width The width of the mask frame in pixel, with range [4, infinity)
82 * @param height The height of the mask frame in pixel, with range [4, infinity)
83 * @param maskValue The value of a mask pixel to be dilated, pixels with other values will be untouched, with range [0, 255]
84 * @param maskPaddingElements Optional number of padding elements at the end of each mask row, in elements, with range [0, infinity)
85 * @param targetPaddingElements Optional number of padding elements at the end of each target row, in elements, with range [0, infinity)
86 * @param worker Optional worker object to distribute the computation
87 */
88 static inline void filter1Channel8Bit24Neighbor(const uint8_t* mask, uint8_t* target, const unsigned int width, const unsigned int height, const uint8_t maskValue = 0x00, const unsigned int maskPaddingElements = 0u, const unsigned int targetPaddingElements = 0u, Worker* worker = nullptr);
89
90 private:
91
92 /**
93 * Applies one dilation filter iteration in a subset of an 8 bit mask image using a 4-neighborhood.
94 * @param mask The mask frame to be filtered, must be valid
95 * @param target The target frame receiving the filter response, must be valid
96 * @param width The width of the mask frame in pixel, with range [2, infinity)
97 * @param height The height of the mask frame in pixel, with range [2, infinity)
98 * @param maskValue The value of a mask pixel to be eroded, pixels with other values will be untouched, with range [0, 255]
99 * @param maskPaddingElements Optional number of padding elements at the end of each mask row, in elements, with range [0, infinity)
100 * @param targetPaddingElements Optional number of padding elements at the end of each target row, in elements, with range [0, infinity)
101 * @param firstRow First row to be handled, with range [0, height - 1]
102 * @param numberRows Number of rows to be handled, with range [1, height - firstRow]
103 */
104 static void filter1Channel8Bit4NeighborSubset(const uint8_t* mask, uint8_t* target, const unsigned int width, const unsigned int height, const uint8_t maskValue, const unsigned int maskPaddingElements, const unsigned int targetPaddingElements, const unsigned int firstRow, const unsigned int numberRows);
105
106 /**
107 * Applies one dilation filter iteration in a subset of an 8 bit mask image using a 8-neighborhood.
108 * @param mask The mask frame to be filtered, must be valid
109 * @param target The target frame receiving the filter response, must be valid
110 * @param width The width of the mask frame in pixel, with range [2, infinity)
111 * @param height The height of the mask frame in pixel, with range [2, infinity)
112 * @param maskValue The value of a mask pixel to be eroded, pixels with other values will be untouched, with range [0, 255]
113 * @param maskPaddingElements Optional number of padding elements at the end of each mask row, in elements, with range [0, infinity)
114 * @param targetPaddingElements Optional number of padding elements at the end of each target row, in elements, with range [0, infinity)
115 * @param firstRow First row to be handled, with range [0, height - 1]
116 * @param numberRows Number of rows to be handled, with range [1, height - firstRow]
117 */
118 static void filter1Channel8Bit8NeighborSubset(const uint8_t* mask, uint8_t* target, const unsigned int width, const unsigned int height, const uint8_t maskValue, const unsigned int maskPaddingElements, const unsigned int targetPaddingElements, const unsigned int firstRow, const unsigned int numberRows);
119
120 /**
121 * Applies one dilation filter iteration in a subset of an 8 bit mask image using a 24-neighborhood.
122 * @param mask The mask frame to be filtered, must be valid
123 * @param target The target frame receiving the filter response, must be valid
124 * @param width The width of the mask frame in pixel, with range [4, infinity)
125 * @param height The height of the mask frame in pixel, with range [4, infinity)
126 * @param maskValue The value of a mask pixel to be eroded, pixels with other values will be untouched, with range [0, 255]
127 * @param maskPaddingElements Optional number of padding elements at the end of each mask row, in elements, with range [0, infinity)
128 * @param targetPaddingElements Optional number of padding elements at the end of each target row, in elements, with range [0, infinity)
129 * @param firstRow First row to be handled, with range [0, height - 1]
130 * @param numberRows Number of rows to be handled, with range [1, height - firstRow]
131 */
132 static void filter1Channel8Bit24NeighborSubset(const uint8_t* mask, uint8_t* target, const unsigned int width, const unsigned int height, const uint8_t maskValue, const unsigned int maskPaddingElements, const unsigned int targetPaddingElements, const unsigned int firstRow, const unsigned int numberRows);
133
134 /**
135 * Returns whether each several pixels in a row is not equal to a specified value.
136 * @param maskPixels The first pixel within the row to check, must be valid
137 * @param maskValue The mask value to check, with range [0, 255]
138 * @return True, if so
139 * @tparam tSize The number of pixels in a row to check, with range [1, infinity)
140 */
141 template <unsigned int tSize>
142 static OCEAN_FORCE_INLINE bool eachPixelNotEqual(const uint8_t* const maskPixels, const uint8_t maskValue);
143};
144
145template <FrameFilterDilation::MorphologyFilter tDilationFilter>
146void FrameFilterDilation::filter1Channel8Bit(uint8_t* mask, const unsigned int width, const unsigned int height, const unsigned int iterations, const uint8_t maskValue, const unsigned int maskPaddingElements, Worker* worker)
147{
148 ocean_assert(mask != nullptr);
149 ocean_assert(width >= 2u && height >= 2u);
150 ocean_assert(iterations >= 1u);
151
152 Frame intermediateTarget(FrameType(width, height, FrameType::FORMAT_Y8, FrameType::ORIGIN_UPPER_LEFT));
153
154 switch (tDilationFilter)
155 {
156 case MF_CROSS_3:
157 {
158 for (unsigned int n = 0u; n < iterations / 2u; ++n)
159 {
160 filter1Channel8Bit4Neighbor(mask, intermediateTarget.data<uint8_t>(), width, height, maskValue, maskPaddingElements, intermediateTarget.paddingElements(), worker);
161 filter1Channel8Bit4Neighbor(intermediateTarget.constdata<uint8_t>(), mask, width, height, maskValue, intermediateTarget.paddingElements(), maskPaddingElements, worker);
162 }
163
164 if (iterations % 2u == 1u)
165 {
166 filter1Channel8Bit4Neighbor(mask, intermediateTarget.data<uint8_t>(), width, height, maskValue, maskPaddingElements, intermediateTarget.paddingElements(), worker);
167 }
168
169 break;
170 }
171
172 case MF_SQUARE_3:
173 {
174 for (unsigned int n = 0u; n < iterations / 2u; ++n)
175 {
176 filter1Channel8Bit8Neighbor(mask, intermediateTarget.data<uint8_t>(), width, height, maskValue, maskPaddingElements, intermediateTarget.paddingElements(), worker);
177 filter1Channel8Bit8Neighbor(intermediateTarget.constdata<uint8_t>(), mask, width, height, maskValue, intermediateTarget.paddingElements(), maskPaddingElements, worker);
178 }
179
180 if (iterations % 2u == 1u)
181 {
182 filter1Channel8Bit8Neighbor(mask, intermediateTarget.data<uint8_t>(), width, height, maskValue, maskPaddingElements, intermediateTarget.paddingElements(), worker);
183 }
184
185 break;
186 }
187
188 case MF_SQUARE_5:
189 {
190 for (unsigned int n = 0u; n < iterations / 2u; ++n)
191 {
192 filter1Channel8Bit24Neighbor(mask, intermediateTarget.data<uint8_t>(), width, height, maskValue, maskPaddingElements, intermediateTarget.paddingElements(), worker);
193 filter1Channel8Bit24Neighbor(intermediateTarget.constdata<uint8_t>(), mask, width, height, maskValue, intermediateTarget.paddingElements(), maskPaddingElements, worker);
194 }
195
196 if (iterations % 2u == 1u)
197 {
198 filter1Channel8Bit24Neighbor(mask, intermediateTarget.data<uint8_t>(), width, height, maskValue, maskPaddingElements, intermediateTarget.paddingElements(), worker);
199 }
200
201 break;
202 }
203
204 default:
205 ocean_assert(false && "Invalid dilation filter!");
206 }
207
208 if (iterations % 2u == 1u)
209 {
210 CV::FrameConverter::subFrame<uint8_t>(intermediateTarget.constdata<uint8_t>(), mask, width, height, width, height, 1u, 0u, 0u, 0u, 0u, width, height, intermediateTarget.paddingElements(), maskPaddingElements);
211 }
212}
213
214inline void FrameFilterDilation::filter1Channel8Bit4Neighbor(const uint8_t* mask, uint8_t* target, const unsigned int width, const unsigned int height, const uint8_t maskValue, const unsigned int maskPaddingElements, const unsigned int targetPaddingElements, Worker* worker)
215{
216 ocean_assert(mask && target);
217 ocean_assert(width >= 2u && height >= 2u);
218
219 if (worker)
220 {
221 worker->executeFunction(Worker::Function::createStatic(&FrameFilterDilation::filter1Channel8Bit4NeighborSubset, mask, target, width, height, maskValue, maskPaddingElements, targetPaddingElements, 0u, 0u), 0u, height, 7u, 8u, 20u);
222 }
223 else
224 {
225 filter1Channel8Bit4NeighborSubset(mask, target, width, height, maskValue, maskPaddingElements, targetPaddingElements, 0u, height);
226 }
227}
228
229inline void FrameFilterDilation::filter1Channel8Bit8Neighbor(const uint8_t* mask, uint8_t* target, const unsigned int width, const unsigned int height, const uint8_t maskValue, const unsigned int maskPaddingElements, const unsigned int targetPaddingElements, Worker* worker)
230{
231 ocean_assert(mask && target);
232 ocean_assert(width >= 2u && height >= 2u);
233
234 if (worker)
235 {
236 worker->executeFunction(Worker::Function::createStatic(&FrameFilterDilation::filter1Channel8Bit8NeighborSubset, mask, target, width, height, maskValue, maskPaddingElements, targetPaddingElements, 0u, 0u), 0u, height, 7u, 8u, 20u);
237 }
238 else
239 {
240 filter1Channel8Bit8NeighborSubset(mask, target, width, height, maskValue, maskPaddingElements, targetPaddingElements, 0u, height);
241 }
242}
243
244inline void FrameFilterDilation::filter1Channel8Bit24Neighbor(const uint8_t* mask, uint8_t* target, const unsigned int width, const unsigned int height, const uint8_t maskValue, const unsigned int maskPaddingElements, const unsigned int targetPaddingElements, Worker* worker)
245{
246 ocean_assert(mask && target);
247 ocean_assert(width >= 4u && height >= 4u);
248
249 if (worker)
250 {
251 worker->executeFunction(Worker::Function::createStatic(&FrameFilterDilation::filter1Channel8Bit24NeighborSubset, mask, target, width, height, maskValue, maskPaddingElements, targetPaddingElements, 0u, 0u), 0u, height, 7u, 8u, 20u);
252 }
253 else
254 {
255 filter1Channel8Bit24NeighborSubset(mask, target, width, height, maskValue, maskPaddingElements, targetPaddingElements, 0u, height);
256 }
257}
258
259template <>
260OCEAN_FORCE_INLINE bool FrameFilterDilation::eachPixelNotEqual<3u>(const uint8_t* const maskPixels, const uint8_t maskValue)
261{
262 ocean_assert(maskPixels != nullptr);
263
264 return maskPixels[0] != maskValue && maskPixels[1] != maskValue && maskPixels[2] != maskValue;
265}
266
267template <>
268OCEAN_FORCE_INLINE bool FrameFilterDilation::eachPixelNotEqual<4u>(const uint8_t* const maskPixels, const uint8_t maskValue)
269{
270 ocean_assert(maskPixels != nullptr);
271
272 return maskPixels[0] != maskValue && maskPixels[1] != maskValue && maskPixels[2] != maskValue && maskPixels[3] != maskValue;
273}
274
275template <>
276OCEAN_FORCE_INLINE bool FrameFilterDilation::eachPixelNotEqual<5u>(const uint8_t* const maskPixels, const uint8_t maskValue)
277{
278 ocean_assert(maskPixels != nullptr);
279
280 return maskPixels[0] != maskValue && maskPixels[1] != maskValue && maskPixels[2] != maskValue && maskPixels[3] != maskValue && maskPixels[4] != maskValue;
281}
282
283}
284
285}
286
287#endif // META_OCEAN_CV_FRAME_FILTER_DILATION_H
This class implements a frame dilation filter.
Definition FrameFilterDilation.h:29
static void filter1Channel8Bit8Neighbor(const uint8_t *mask, uint8_t *target, const unsigned int width, const unsigned int height, const uint8_t maskValue=0x00, const unsigned int maskPaddingElements=0u, const unsigned int targetPaddingElements=0u, Worker *worker=nullptr)
Applies one dilation filter iteration for an 8 bit mask image using a 8-neighborhood,...
Definition FrameFilterDilation.h:229
static void filter1Channel8Bit4NeighborSubset(const uint8_t *mask, uint8_t *target, const unsigned int width, const unsigned int height, const uint8_t maskValue, const unsigned int maskPaddingElements, const unsigned int targetPaddingElements, const unsigned int firstRow, const unsigned int numberRows)
Applies one dilation filter iteration in a subset of an 8 bit mask image using a 4-neighborhood.
static void filter1Channel8Bit24NeighborSubset(const uint8_t *mask, uint8_t *target, const unsigned int width, const unsigned int height, const uint8_t maskValue, const unsigned int maskPaddingElements, const unsigned int targetPaddingElements, const unsigned int firstRow, const unsigned int numberRows)
Applies one dilation filter iteration in a subset of an 8 bit mask image using a 24-neighborhood.
static void filter1Channel8Bit4Neighbor(const uint8_t *mask, uint8_t *target, const unsigned int width, const unsigned int height, const uint8_t maskValue=0x00, const unsigned int maskPaddingElements=0u, const unsigned int targetPaddingElements=0u, Worker *worker=nullptr)
Applies one dilation filter iteration for an 8 bit mask image using a 4-neighborhood.
Definition FrameFilterDilation.h:214
static void filter1Channel8Bit(uint8_t *mask, const unsigned int width, const unsigned int height, const unsigned int iterations, const uint8_t maskValue=0x00, const unsigned int maskPaddingElements=0u, Worker *worker=nullptr)
Applies several dilation filter iterations for an 8 bit mask image.
Definition FrameFilterDilation.h:146
static OCEAN_FORCE_INLINE bool eachPixelNotEqual(const uint8_t *const maskPixels, const uint8_t maskValue)
Returns whether each several pixels in a row is not equal to a specified value.
static void filter1Channel8Bit8NeighborSubset(const uint8_t *mask, uint8_t *target, const unsigned int width, const unsigned int height, const uint8_t maskValue, const unsigned int maskPaddingElements, const unsigned int targetPaddingElements, const unsigned int firstRow, const unsigned int numberRows)
Applies one dilation filter iteration in a subset of an 8 bit mask image using a 8-neighborhood.
static void filter1Channel8Bit24Neighbor(const uint8_t *mask, uint8_t *target, const unsigned int width, const unsigned int height, const uint8_t maskValue=0x00, const unsigned int maskPaddingElements=0u, const unsigned int targetPaddingElements=0u, Worker *worker=nullptr)
Applies one dilation filter iteration for an 8 bit mask image using a 24-neighborhood,...
Definition FrameFilterDilation.h:244
This class implements the base class for all morphology frame filter.
Definition FrameFilterMorphology.h:26
@ MF_SQUARE_3
Square mask filter defined by one center point and 8 surrounded filter pixels with an area of 3x3.
Definition FrameFilterMorphology.h:37
@ MF_CROSS_3
Cross mask filter defined by one center point and 4 (north, south, west, east) filter pixels with an ...
Definition FrameFilterMorphology.h:35
@ MF_SQUARE_5
Square mask filter defined by one center point and 24 surrounded filter pixels with an area of 5x5.
Definition FrameFilterMorphology.h:39
static Caller< void > createStatic(typename StaticFunctionPointerMaker< void, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass, NullClass >::Type function)
Creates a new caller container for a static function with no function parameter.
Definition Caller.h:2876
This class implements Ocean's image class.
Definition Frame.h:1808
const T * constdata(const unsigned int planeIndex=0u) const
Returns a pointer to the read-only pixel data of a specific plane.
Definition Frame.h:4248
T * data(const unsigned int planeIndex=0u)
Returns a pointer to the pixel data of a specific plane.
Definition Frame.h:4239
unsigned int paddingElements(const unsigned int planeIndex=0u) const
Returns the optional number of padding elements at the end of each row for a specific plane.
Definition Frame.h:4122
Definition of a frame type composed by the frame dimension, pixel format and pixel origin.
Definition Frame.h:30
@ FORMAT_Y8
Pixel format for grayscale images with byte order Y and 8 bits per pixel.
Definition Frame.h:594
@ ORIGIN_UPPER_LEFT
The first pixel lies in the upper left corner, the last pixel in the lower right corner.
Definition Frame.h:1050
This class implements a worker able to distribute function calls over different threads.
Definition Worker.h:33
bool executeFunction(const Function &function, const unsigned int first, const unsigned int size, const unsigned int firstIndex=(unsigned int)(-1), const unsigned int sizeIndex=(unsigned int)(-1), const unsigned int minimalIterations=1u, const unsigned int threadIndex=(unsigned int)(-1))
Executes a callback function separable by two function parameters.
The namespace covering the entire Ocean framework.
Definition Accessor.h:15