Ocean
Loading...
Searching...
No Matches
TestFrameInterpolatorBilinear.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_TEST_TESTCV_TEST_FRAME_INTERPOLATOR_BILINEAR_H
9#define META_OCEAN_TEST_TESTCV_TEST_FRAME_INTERPOLATOR_BILINEAR_H
10
12
13#include "ocean/base/Frame.h"
14#include "ocean/base/Worker.h"
15
17
18#include "ocean/math/Lookup2.h"
20#include "ocean/math/Vector2.h"
21
23
24namespace Ocean
25{
26
27namespace Test
28{
29
30namespace TestCV
31{
32
33/**
34 * This class implements a bilinear frame interpolation test.
35 * @ingroup testcv
36 */
37class OCEAN_TEST_CV_EXPORT TestFrameInterpolatorBilinear
38{
39 public:
40
41 /**
42 * Tests all bilinear interpolation filter functions.
43 * @param width The width of the source frame in pixel
44 * @param height The height of the source frame in pixel
45 * @param testDuration Number of seconds for each test, with range (0, infinity)
46 * @param worker The worker object to distribute the CPU load
47 * @param selector The test selector to control which tests to run
48 * @return True, if succeeded
49 */
50 static bool test(const unsigned int width, const unsigned int height, const double testDuration, Worker& worker, const TestSelector& selector = TestSelector());
51
52 /**
53 * Tests the pixel interpolation function for frames with 8 bit per channel.
54 * @param testDuration Number of seconds for each test, with range (0, infinity)
55 * @return True, if succeeded
56 */
57 static bool testInterpolatePixel8BitPerChannel(const double testDuration);
58
59 /**
60 * Tests the pixel interpolation function for frames with 8 bit per channel.
61 * @param testDuration Number of seconds for each test, with range (0, infinity)
62 * @param pixelCenter The pixel center to be used
63 * @return True, if succeeded
64 * @tparam TScalar The data type of the scalar to be used, either 'float' or 'double'
65 */
66 template <typename TScalar>
67 static bool testInterpolatePixel8BitPerChannel(const CV::PixelCenter pixelCenter, const double testDuration);
68
69 /**
70 * Tests the pixel interpolation function for frames with arbitrary data type.
71 * @param testDuration Number of seconds for each test, with range (0, infinity)
72 * @return True, if succeeded
73 */
74 static bool testInterpolatePixel(const double testDuration);
75
76 /**
77 * Tests the pixel interpolation function for frames arbitrary data type.
78 * @param testDuration Number of seconds for each test, with range (0, infinity)
79 * @param pixelCenter The pixel center to be used
80 * @return True, if succeeded
81 * @tparam TSource The data type of the source to be used
82 * @tparam TTarget The data type of the target to be used
83 * @tparam TScalar The data type of the scalar to be used, either 'float' or 'double'
84 */
85 template <typename TSource, typename TTarget, typename TScalar>
86 static bool testInterpolatePixel(const CV::PixelCenter pixelCenter, const double testDuration);
87
88 /**
89 * Tests the affine transformation function using a constant color for unknown image content.
90 * @param testDuration Number of seconds for each test, with range (0, infinity)
91 * @param worker The worker object to distribute the CPU load
92 * @return True, if succeeded
93 */
94 static bool testAffine(const double testDuration, Worker& worker);
95
96 /**
97 * Tests the homography transformation function supporting arbitrary pixel formats using a constant color for unknown image content.
98 * @param testDuration Number of seconds for each test, with range (0, infinity)
99 * @param worker The worker object to distribute the CPU load
100 * @return True, if succeeded
101 * @tparam T The data type of each pixel channel, e.g., 'float', 'double', 'int', ...
102 */
103 template <typename T>
104 static bool testHomography(const double testDuration, Worker& worker);
105
106 /**
107 * Tests the homography transformation function defining a binary mask for known and unknown image content.
108 * @param testDuration Number of seconds for each test, with range (0, infinity)
109 * @param worker The worker object to distribute the CPU load
110 * @return True, if succeeded
111 */
112 static bool testHomographyMask(const double testDuration, Worker& worker);
113
114 /**
115 * Tests the bilinear resize function for extreme image resolutions.
116 * @param testDuration Number of seconds for each test, with range (0, infinity)
117 * @param worker The worker object to distribute the CPU load
118 * @return True, if succeeded
119 */
120 static bool testResizeExtremeResolutions(const double testDuration, Worker& worker);
121
122 /**
123 * Tests the bilinear resize function.
124 * @param testDuration Number of seconds for each test, with range (0, infinity)
125 * @param worker The worker object to distribute the CPU load
126 * @return True, if succeeded
127 */
128 static bool testResize(const double testDuration, Worker& worker);
129
130 /**
131 * Tests the bilinear resize function supporting arbitrary data types.
132 * @param testDuration Number of seconds for each test, with range (0, infinity)
133 * @param worker The worker object to distribute the CPU load
134 * @return True, if succeeded
135 * @tparam T The data type of each pixel channel, e.g., `uint8_t`, 'float', 'double', ...
136 */
137 template <typename T>
138 static bool testResize(const double testDuration, Worker& worker);
139
140 /**
141 * Tests the bilinear scale function with scale factors which are not derived from the frame dimensions.
142 * @param testDuration Number of seconds for each test, with range (0, infinity)
143 * @param worker The worker object to distribute the CPU load
144 * @return True, if succeeded
145 */
146 static bool testScale(const double testDuration, Worker& worker);
147
148 /**
149 * Tests the frame transformation function applying a lookup table.
150 * @param testDuration Number of seconds for each test, with range (0, infinity)
151 * @param worker The worker object to distribute the CPU load
152 * @return True, if succeeded
153 */
154 static bool testLookup(const double testDuration, Worker& worker);
155
156 /**
157 * Tests the frame transformation function applying a lookup table.
158 * @param testDuration Number of seconds for each test, with range (0, infinity)
159 * @param worker The worker object to distribute the CPU load
160 * @return True, if succeeded
161 * @tparam T The data type of each pixel channel, e.g., `uint8_t`, 'float', 'double', ...
162 */
163 template <typename T>
164 static bool testLookup(const double testDuration, Worker& worker);
165
166 /**
167 * Tests the frame mask transformation function applying a lookup table.
168 * @param width The width of the test frame in pixel, with range [1, infinity)
169 * @param height The height of the test frame in pixel, with range [1, infinity)
170 * @param testDuration Number of seconds for each test, with range (0, infinity)
171 * @param worker The worker object to distribute the CPU load
172 * @return True, if succeeded
173 */
174 static bool testLookupMask(const unsigned int width, const unsigned int height, const double testDuration, Worker& worker);
175
176 /**
177 * Tests the frame rotate function.
178 * @param width The width of the test frame in pixel, with range [1, infinity)
179 * @param height The height of the test frame in pixel, with range [1, infinity)
180 * @param testDuration Number of seconds for each test, with range (0, infinity)
181 * @param worker The worker object to distribute the CPU load
182 * @return True, if succeeded
183 */
184 static bool testRotateFrame(const unsigned int width, const unsigned int height, const double testDuration, Worker& worker);
185
186 /**
187 * Tests the intensity sum of an image patch with sub-pixel location in a 1-channel frame using an integral image.
188 * @param width The width of the frame in pixel, with range [64, infinity)
189 * @param height The height of the frame in pixel, with range [64, infinity)
190 * @param testDuration Number of seconds for each test, with range (0, infinity)
191 * @return True, if succeeded
192 */
193 static bool testPatchIntensitySum1Channel(const unsigned int width, const unsigned int height, const double testDuration);
194
195 /**
196 * Tests the function for affine transformations (with constant color for unknown image content) for a given frame dimension and channel number.
197 * @param width The width of the frame in pixel, with range [1, infinity)
198 * @param height The height of the frame in pixel, with range [1, infinity)
199 * @param channels The number of frame channels, with range [1, 4]
200 * @param testDuration Number of seconds for each test, with range (0, infinity)
201 * @param worker The worker object to distribute the CPU load
202 * @return True, if succeeded
203 */
204 static bool testAffine(const unsigned int width, const unsigned int height, const unsigned int channels, const double testDuration, Worker& worker);
205
206 /**
207 * Tests the homography transformation function (with constant color for unknown image content) for arbitrary data types and for a given frame dimension and channel number.
208 * @param width The width of the frame in pixel, with range [1, infinity)
209 * @param height The height of the frame in pixel, with range [1, infinity)
210 * @param channels The number of frame channels, with range [1, 4]
211 * @param testDuration Number of seconds for each test, with range (0, infinity)
212 * @param worker The worker object to distribute the CPU load
213 * @return True, if succeeded
214 * @tparam T The data type of each pixel channel, e.g., 'float', 'double', 'int', ...
215 */
216 template <typename T>
217 static bool testHomography(const unsigned int width, const unsigned int height, const unsigned int channels, const double testDuration, Worker& worker);
218
219 /**
220 * Tests the homography transformation function (with binary mask defining known and unknown image content) for a given frame dimension and channel number.
221 * @param width The width of the frame in pixel, with range [1, infinity)
222 * @param height The height of the frame in pixel, with range [1, infinity)
223 * @param channels The number of frame channels, with range [1, 4]
224 * @param testDuration Number of seconds for each test, with range (0, infinity)
225 * @param worker The worker object to distribute the CPU load
226 * @return True, if succeeded
227 */
228 static bool testHomographyMask(const unsigned int width, const unsigned int height, const unsigned int channels, const double testDuration, Worker& worker);
229
230 /**
231 * Tests the bilinear resize function for a given frame dimension and channel number.
232 * @param sourceWidth Width of the source frame in pixel
233 * @param sourceHeight Height of the source frame in pixel
234 * @param sourceChannels Number of the data channels of the source frame, with range [1, 4]
235 * @param targetWidth Width of the target frame in pixel
236 * @param targetHeight Height of the target frame in pixel
237 * @param testDuration Number of seconds for each test, with range (0, infinity)
238 * @param worker The worker object to distribute the CPU load
239 * @return True, if succeeded
240 */
241 static bool testResize(const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int sourceChannels, const unsigned int targetWidth, const unsigned int targetHeight, const double testDuration, Worker& worker);
242
243 /**
244 * Tests the bilinear resize function for arbitrary data types and for a given frame dimension and channel number.
245 * @param sourceWidth Width of the source frame in pixel
246 * @param sourceHeight Height of the source frame in pixel
247 * @param sourceChannels Number of the data channels of the source frame
248 * @param targetWidth Width of the target frame in pixel
249 * @param targetHeight Height of the target frame in pixel
250 * @param testDuration Number of seconds for each test, with range (0, infinity)
251 * @param worker The worker object to distribute the CPU load
252 * @return True, if succeeded
253 * @tparam T The data type of each pixel channel, e.g., 'float', 'double', 'int', ...
254 */
255 template <typename T>
256 static bool testResize(const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int sourceChannels, const unsigned int targetWidth, const unsigned int targetHeight, const double testDuration, Worker& worker);
257
258 /**
259 * Tests the bilinear scale function for a given frame dimension, channel number, and pair of scale factors.
260 * @param sourceWidth Width of the source frame in pixel
261 * @param sourceHeight Height of the source frame in pixel
262 * @param channels Number of the data channels of the source frame, with range [1, 4]
263 * @param targetWidth Width of the target frame in pixel
264 * @param targetHeight Height of the target frame in pixel
265 * @param xSource_s_xTarget The horizontal scale factor converting a location in the target frame to a location in the source frame, with range (0, infinity)
266 * @param ySource_s_yTarget The vertical scale factor converting a location in the target frame to a location in the source frame, with range (0, infinity)
267 * @param testDuration Number of seconds for each test, with range (0, infinity)
268 * @param worker The worker object to distribute the CPU load
269 * @return True, if succeeded
270 */
271 static bool testScale(const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int channels, const unsigned int targetWidth, const unsigned int targetHeight, const double xSource_s_xTarget, const double ySource_s_yTarget, const double testDuration, Worker& worker);
272
273 /**
274 * Tests the special case resize function for image resolutions from 400x400 to 256x256.
275 * @param testDuration Number of seconds for each test, with range (0, infinity)
276 * @return True, if succeeded
277 */
278 static bool testSpecialCasesResize400x400To256x256_8BitPerChannel(const double testDuration);
279
280 /**
281 * Tests the special case resize function for image resolutions from 400x400 to 224x224.
282 * @param testDuration Number of seconds for each test, with range (0, infinity)
283 * @return True, if succeeded
284 */
285 static bool testSpecialCasesResize400x400To224x224_8BitPerChannel(const double testDuration);
286
287 /**
288 * Tests the frame transformation function applying a lookup table.
289 * @param width The width of the test frame in pixel, with range [20, infinity)
290 * @param height The height of the test frame in pixel, with range [20, infinity)
291 * @param channels The number of frame channels, with range [1, infinity)
292 * @param testDuration Number of seconds for each test, with range (0, infinity)
293 * @param worker The worker object to distribute the CPU load
294 * @return True, if succeeded
295 * @tparam T The data type of each pixel channel, e.g., 'float', 'double', 'int', ...
296 */
297 template <typename T>
298 static bool testLookup(const unsigned int width, const unsigned int height, const unsigned int channels, const double testDuration, Worker& worker);
299
300 /**
301 * Tests the function to re-sample a camera image.
302 * @param testDuration Number of seconds for each test, with range (0, infinity)
303 * @param worker The worker object to distribute the CPU load
304 * @return True, if succeeded
305 */
306 static bool testResampleCameraImage(const double testDuration, Worker& worker);
307
308 /**
309 * Tests the function to re-sample a camera image.
310 * @param testDuration Number of seconds for each test, with range (0, infinity)
311 * @param worker The worker object to distribute the CPU load
312 * @return True, if succeeded
313 * @tparam T The data type of each pixel channel, e.g., 'float', 'double', 'int', ...
314 */
315 template <typename T>
316 static bool testResampleCameraImage(const double testDuration, Worker& worker);
317
318 /**
319 * Validates the bilinear frame resize function.
320 * @param source The source frame that has been resized, must be valid
321 * @param sourceWidth The width of the source frame in pixel, with range [1, infinity)
322 * @param sourceHeight The height of the source frame in pixel, with range [1, infinity)
323 * @param channels Number of the data channels of the source (and target) frame, with range [1, 4]
324 * @param target The resized target frame to be verified, must be valid
325 * @param targetWidth The width of the target frame in pixel, with range [1, infinity)
326 * @param targetHeight The height of the target frame in pixel, with range [1, infinity)
327 * @param xTargetToSource The horizontal scale factor transforming a location in the target frame to a location in the source frame, with range (0, infinity)
328 * @param yTargetToSource The vertical scale factor transforming a location in the target frame to a location in the source frame, with range (0, infinity)
329 * @param sourcePaddingElements Optional padding at the end of each source row in elements, with range [0, infinity)
330 * @param targetPaddingElements Optional padding at the end of each target row in elements, with range [0, infinity)
331 * @param averageAbsErrorToInteger Optional resulting average absolute error between the converted result and the ground truth integer result (rounded result), with range [0, 256)
332 * @param maximalAbsErrorToInteger Optional resulting maximal absolute error between the converted result and the ground truth integer result (rounded result), with range [0, 256)
333 * @param groundTruth Optional resulting ground truth data (the resized image content determined with floating point accuracy), nullptr otherwise
334 */
335 static void validateScaleFrame(const unsigned char* source, const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int channels, const unsigned char* target, const unsigned int targetWidth, const unsigned int targetHeight, const double xTargetToSource, const double yTargetToSource, const unsigned int sourcePaddingElements, const unsigned int targetPaddingElements, double* averageAbsErrorToInteger, unsigned int* maximalAbsErrorToInteger, unsigned char* groundTruth = nullptr);
336
337 /**
338 * Validates the bilinear frame resize function for arbitrary data types.
339 * @param source The source frame that has been resized, must be valid
340 * @param sourceWidth The width of the source frame in pixel, with range [1, infinity)
341 * @param sourceHeight The height of the source frame in pixel, with range [1, infinity)
342 * @param channels Number of the data channels of the source (and target) frame, with range [1, 4]
343 * @param target The resized target frame to be verified, must be valid
344 * @param targetWidth The width of the target frame in pixel, with range [1, infinity)
345 * @param targetHeight The height of the target frame in pixel, with range [1, infinity)
346 * @param xSource_s_xTarget The horizontal scale factor transforming a location in the target frame to a location in the source frame, with range (0, infinity)
347 * @param ySource_s_yTarget The vertical scale factor transforming a location in the target frame to a location in the source frame, with range (0, infinity)
348 * @param sourcePaddingElements Optional padding at the end of each source row in elements, with range [0, infinity)
349 * @param targetPaddingElements Optional padding at the end of each target row in elements, with range [0, infinity)
350 * @param averageAbsError Optional resulting average absolute error between the converted result and the ground truth result, with range (-infinity, infinity)
351 * @param maximalAbsError Optional resulting maximal absolute error between the converted result and the ground truth result, with range (-infinity, infinity)
352 * @param groundTruth Optional resulting ground truth data (the resized image content determined with floating point accuracy), nullptr otherwise
353 * @tparam T The data type of each pixel channel, e.g., 'float', 'double', 'int', ...
354 */
355 template <typename T>
356 static void validateScaleFrame(const T* source, const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int channels, const T* target, const unsigned int targetWidth, const unsigned int targetHeight, const double xSource_s_xTarget, const double ySource_s_yTarget, const unsigned int sourcePaddingElements, const unsigned int targetPaddingElements, double* averageAbsError, double* maximalAbsError, T* groundTruth = nullptr);
357
358 /**
359 * Validates the homography interpolation function for (almost) arbitrary pixel formats (using a constant background color for unknown image content).
360 * @param input The input frame which has been used for the interpolation, must be valid
361 * @param output The output frame holding the interpolated image information of the input frame, must be valid
362 * @param input_H_output The homography that has been used to interpolate/warp the frame, transforming points int he output frame to points in the input frame, must not be singular
363 * @param backgroundColor The background color for all pixels for which no valid source pixel exists, one for each frame channel, must be valid
364 * @param interpolatedFrameOrigin The origin of the interpolated frame defining the global position of the interpolated frame's pixel coordinate (0, 0), with range (-infinity, infinity)x(-infinity, infinity)
365 * @param averageAbsError Optional resulting average absolute error between the converted result and the ground truth result, with range (-infinity, infinity)
366 * @param maximalAbsError Optional resulting maximal absolute error between the converted result and the ground truth result, with range (-infinity, infinity)
367 * @param groundTruth Optional resulting ground truth frame (the resized image content determined with floating point accuracy), nullptr if not of interest
368 * @tparam T The data type of each pixel channel, e.g., 'float', 'double', 'int', ...
369 */
370 template <typename T>
371 static void validateHomography(const Frame& input, const Frame& output, const SquareMatrix3& input_H_output, const T* backgroundColor, const CV::PixelPositionI& interpolatedFrameOrigin, double* averageAbsError, double* maximalAbsError, Frame* groundTruth = nullptr);
372
373 protected:
374
375 /**
376 * Tests the intensity sum of an image patch with sub-pixel location in a 1-channel frame using an integral image.
377 * @param width The width of the frame, in pixel, with range [patchWidth + 1u, infinity)
378 * @param height The height of the frame, in pixel, with range [patchHeight + 1u, infinity)
379 * @param patchWidth Width of the patch, in pixel, with range [1, infinity)
380 * @param patchHeight Height of the patch, in pixel, with range [1, infinity)
381 * @param testDuration Number of seconds for each test, with range (0, infinity)
382 * @return True, if succeeded
383 */
384 static bool testPatchIntensitySum1Channel(const unsigned int width, const unsigned int height, const unsigned int patchWidth, const unsigned int patchHeight, const double testDuration);
385
386 /**
387 * Validates a pixel interpolation result for frame with 8 bit per channel.
388 * @param frame The frame in pixel the pixel interpolation was applied, must be valid
389 * @param position The position for which the interpolated pixel will be determined, with ranges [0, frame.width() - 1]x[0, frame.height() - 1] for PC_TOP_LEFT, [0, frame.width()]x[0, frame.height()] for PC_CENTER
390 * @param pixelCenter The pixel center to be used during interpolation
391 * @param interpolationResult The interpolation result to be verified, one for each frame channel
392 * @param threshold The maximal distance between interpolated result and ground-truth result so that the result is valid, with range [0, 255)
393 * @return True, if the interpolation is correct
394 * @tparam TScalar The data type of a scalar, either 'float' or 'double'
395 */
396 template <typename TScalar>
397 static bool validateInterpolatePixel8BitPerChannel(const Frame& frame, const VectorT2<TScalar>& position, const CV::PixelCenter pixelCenter, const uint8_t* const interpolationResult, const TScalar threshold);
398
399 /**
400 * Validates a pixel interpolation result for frame with arbitrary data type.
401 * @param frame The frame in pixel the pixel interpolation was applied, must be valid
402 * @param position The position for which the interpolated pixel will be determined, with ranges [0, frame.width() - 1]x[0, frame.height() - 1] for PC_TOP_LEFT, [0, frame.width()]x[0, frame.height()] for PC_CENTER
403 * @param pixelCenter The pixel center to be used during interpolation
404 * @param interpolationResult The interpolation result to be verified, one for each frame channel
405 * @param threshold The maximal distance between interpolated result and ground-truth result so that the result is valid, with range [0, 255)
406 * @return True, if the interpolation is correct
407 * @tparam TSource The data type of the source to be used
408 * @tparam TTarget The data type of the target to be used
409 * @tparam TScalar The data type of a scalar, either 'float' or 'double'
410 */
411 template <typename TSource, typename TTarget, typename TScalar>
412 static bool validateInterpolatePixel(const Frame& frame, const VectorT2<TScalar>& position, const CV::PixelCenter pixelCenter, const TTarget* const interpolationResult, const TScalar threshold);
413
414 /**
415 * Validation function for the bilinear interpolation of 2D homogeneous image transformations (+ constant background color for unknown image content).
416 * @param source The frame which will be interpolated based on the homography, must be valid
417 * @param validationTarget The interpolated frame that will be validated, must the same pixel format and origin as 'source' and must be valid
418 * @param source_H_target The 2D homogeneous image transformation that has been used to interpolate/warp the frame, transforming points defined in the interpolatedFrame to the source frame, i.e. pointFrame = transformation * pointInterpolatedFrame, must not be singular
419 * @param backgroundColor The background color for all pixels for which no valid source pixel exists, one for each frame channel, must be valid
420 * @param interpolatedFrameOrigin The origin of the interpolated frame defining the global position of the interpolated frame's pixel coordinate (0, 0), with range (-infinity, infinity)x(-infinity, infinity)
421 * @return True, if the interpolation is correct
422 */
423 static bool validateTransformation8BitPerChannel(const Frame& source, const Frame& validationTarget, const SquareMatrix3& source_H_target, const uint8_t* backgroundColor, const CV::PixelPositionI& interpolatedFrameOrigin);
424
425 /**
426 * Validates the homography interpolation function (using a binary mask to define known and unknown image content).
427 * @param frame The frame which will be interpolated based on the homography, must be valid
428 * @param interpolatedFrame The interpolated/warped frame to be validated, width same pixel format and pixel origin as 'frame, must be valid
429 * @param interpolatedMask The binary mask corresponding to the interpolated/warped frame specifying known and unknown image content, a mask value of 0xFF defined known image content, 0x00 defines unknown image content, with same pixel origin and frame resolution as 'interpolatedFrame'
430 * @param input_H_output The homography that has been used to interpolate/warp the frame, transforming points in the output frame to points in the input frame, must not be singular
431 * @param interpolatedFrameOrigin The origin of the interpolated frame defining the global position of the interpolated frame's pixel coordinate (0, 0), with range (-infinity, infinity)x(-infinity, infinity)
432 * @return True, if the interpolation is correct
433 */
434 static bool validateHomographyMask8BitPerChannel(const Frame& frame, const Frame& interpolatedFrame, const Frame& interpolatedMask, const SquareMatrix3& input_H_output, const CV::PixelPositionI& interpolatedFrameOrigin);
435
436 /**
437 * Validates the frame transformation function applying a lookup table.
438 * @param sourceFrame The source frame which has been transformed, must be valid
439 * @param targetFrame The target frame which holds the transformed input frame, must be valid
440 * @param lookupTable The lookup table which has been used for the transformation, must be valid
441 * @param offset True, to interpret the lookup values as offset values; False, to interpret the lookup values as absolute locations
442 * @param backgroundColor The background color to be used, must be valid
443 * @return True, if succeeded
444 * @tparam T The data type of each pixel channel, e.g., 'float', 'double', 'int', ...
445 */
446 template <typename T>
447 static bool validateLookup(const Frame& sourceFrame, const Frame& targetFrame, const LookupCorner2<Vector2>& lookupTable, const bool offset, const T* backgroundColor);
448
449 /**
450 * Validates the frame mask transformation function applying a lookup table.
451 * @param sourceFrame The source frame which has been transformed, must be valid
452 * @param targetFrame The target frame which holds the transformed input frame, must be valid
453 * @param targetMask The mask associated with the target frame, must be valid
454 * @param lookupTable The lookup table which has been used for the transformation, must be valid
455 * @param offset True, to interpret the lookup values as offset values; False, to interpret the lookup values as absolute locations
456 * @return True, if succeeded
457 */
458 static bool validateLookupMask(const Frame& sourceFrame, const Frame& targetFrame, const Frame& targetMask, const LookupCorner2<Vector2>& lookupTable, const bool offset);
459
460 /**
461 * Validates the rotation of a frame using a bilinear interpolation.
462 * @param source The source frame to be rotated, must be valid
463 * @param target The target frame which will receive the rotated image, with same frame type as the source frame, must be valid
464 * @param anchorX Position of the rotation anchor in the horizontal direction, with range (-infinity, infinity)
465 * @param anchorY Position of the rotation anchor in the vertical direction, with range (-infinity, infinity)
466 * @param angle The counter clockwise rotation angle in radian, with range [0, 2PI)
467 */
468 static bool validateRotatedFrame(const Frame& source, const Frame& target, const Scalar anchorX, const Scalar anchorY, const Scalar angle);
469
470 /**
471 * Validate the intensity sum of an image patch with sub-pixel location in a 1-channel frame.
472 * @param yFrame The frame in which the intensity sum is determined, with pixel format FORMAT_Y8, must be valid
473 * @param patchWidth The width of the patch, in pixel, with range [1, infinity)
474 * @param patchHeight The height of the patch, in pixel, with range [1, infinity)
475 * @param center The center of the image patch to be used
476 * @param pixelCenter The pixel center to be used
477 * @param intensity The intensity sum to verify
478 * @return True, if succeeded
479 */
480 static bool validatePatchIntensitySum1Channel(const Frame& yFrame, const unsigned int patchWidth, const unsigned int patchHeight, const Vector2& center, const CV::PixelCenter pixelCenter, const Scalar intensity);
481
482 /**
483 * Validate the bilinear extraction of frame patches
484 * @param source Pointer to the data of the source frame, must be valid
485 * @param validationTarget Pointer to the data of the target frame that will validated, must be valid
486 * @param sourceWidth Width of the source frame in pixels, range: [targetWidth, infinity)
487 * @param sourceHeight Height of the source frame in pixels, range: [targetWidth, infinity)
488 * @param x Horizontal center position of the patch, range: [targetWidth/2, sourceWidth - targetWidth/2)
489 * @param y Vertical center position of the patch, range: [targetHeight/2, sourceHeight - targetHeight/2)
490 * @param validationTargetWidth Width of the target frame, range: all odd values in range [1, sourceWidth]
491 * @param validationTargetHeight Height of the target frame, range: all odd values in range [1, sourceHeight]
492 * @param sourcePaddingElements Optional number of padding elements of the source frame
493 * @param validationTargetPaddingElements Optional number of padding elements of the target frame
494 * @return True if the validation was successful, otherwise false.
495 * @tparam tChannels Number of data channels of the given source frame, range: [1, infinity)
496 */
497 template <uint32_t tChannels>
498 static bool validatePatchFrame8BitPerChannel(const uint8_t* const source, const uint8_t* const validationTarget, const uint32_t sourceWidth, const uint32_t sourceHeight, const Scalar x, const Scalar y, const uint32_t validationTargetWidth, const uint32_t validationTargetHeight, const uint32_t sourcePaddingElements, const uint32_t validationTargetPaddingElements);
499
500 /**
501 * Validates the bilinear frame resize function for uint8_t data types using 7-bit integer precision.
502 * This function first interpolates two rows and stores the interpolated result as uint8_t values, followed by an interpolation within the row.
503 * @param source The source frame that has been resized, must be valid
504 * @param sourceWidth The width of the source frame in pixel, with range [1, infinity)
505 * @param sourceHeight The height of the source frame in pixel, with range [1, infinity)
506 * @param channels Number of the data channels of the source (and target) frame, with range [1, 4]
507 * @param target The resized target frame to be verified, must be valid
508 * @param targetWidth The width of the target frame in pixel, with range [1, infinity)
509 * @param targetHeight The height of the target frame in pixel, with range [1, infinity)
510 * @param xSource_s_xTarget The horizontal scale factor transforming a location in the target frame to a location in the source frame, with range (0, infinity)
511 * @param ySource_s_yTarget The vertical scale factor transforming a location in the target frame to a location in the source frame, with range (0, infinity)
512 * @param sourcePaddingElements Optional padding at the end of each source row in elements, with range [0, infinity)
513 * @param targetPaddingElements Optional padding at the end of each target row in elements, with range [0, infinity)
514 * @param averageAbsError Optional resulting average absolute error between the converted result and the ground truth result, with range (-infinity, infinity)
515 * @param maximalAbsError Optional resulting maximal absolute error between the converted result and the ground truth result, with range (-infinity, infinity)
516 * @param groundTruth Optional resulting ground truth data (the resized image content determined with floating point accuracy), nullptr otherwise
517 */
518 static void validateScaleFramePrecision7Bit(const uint8_t* source, const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int channels, const uint8_t* target, const unsigned int targetWidth, const unsigned int targetHeight, const double xSource_s_xTarget, const double ySource_s_yTarget, const unsigned int sourcePaddingElements, const unsigned int targetPaddingElements, double* averageAbsError, double* maximalAbsError, uint8_t* groundTruth = nullptr);
519};
520
521template <typename T>
522void TestFrameInterpolatorBilinear::validateScaleFrame(const T* source, const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int channels, const T* target, const unsigned int targetWidth, const unsigned int targetHeight, const double xSource_s_xTarget, const double ySource_s_yTarget, const unsigned int sourcePaddingElements, const unsigned int targetPaddingElements, double* averageAbsError, double* maximalAbsError, T* groundTruth)
523{
524 ocean_assert(source != nullptr && target != nullptr);
525 ocean_assert(sourceWidth != 0u && sourceHeight != 0u);
526 ocean_assert(targetWidth != 0u && targetHeight != 0u);
527 ocean_assert(channels >= 1u);
528 ocean_assert(xSource_s_xTarget > 0.0 && ySource_s_yTarget > 0.0);
529
530 const unsigned int sourceStrideElements = sourceWidth * channels + sourcePaddingElements;
531 const unsigned int targetStrideElements = targetWidth * channels + targetPaddingElements;
532
533 std::vector<T> result(channels, T(0));
534
535 if (averageAbsError)
536 {
537 *averageAbsError = NumericD::maxValue();
538 }
539
540 if (maximalAbsError)
541 {
542 *maximalAbsError = NumericD::maxValue();
543 }
544
545 double sumAbsError = 0.0;
546 double maxAbsError = 0.0;
547
548 for (unsigned int y = 0u; y < targetHeight; ++y)
549 {
550 for (unsigned int x = 0u; x < targetWidth; ++x)
551 {
552 const double sx = minmax(0.0, (double(x) + 0.5) * xSource_s_xTarget - 0.5, double(sourceWidth - 1u));
553 const double sy = minmax(0.0, (double(y) + 0.5) * ySource_s_yTarget - 0.5, double(sourceHeight - 1u));
554
555 const unsigned int leftPixel = (unsigned int)sx;
556 const unsigned int rightPixel = min(leftPixel + 1u, sourceWidth - 1u);
557 ocean_assert(leftPixel < sourceWidth && rightPixel < sourceWidth);
558
559 const unsigned int topPixel = (unsigned int)sy;
560 const unsigned int bottomPixel = min(topPixel + 1u, sourceHeight - 1u);
561 ocean_assert(topPixel < sourceHeight && bottomPixel < sourceHeight);
562
563 const double rightFactor = sx - double(leftPixel);
564 const double bottomFactor = sy - double(topPixel);
565
566 ocean_assert(rightFactor >= 0.0 && rightFactor <= 1.0);
567 ocean_assert(bottomFactor >= 0.0 && bottomFactor <= 1.0);
568
569 const double leftFactor = 1.0 - rightFactor;
570 const double topFactor = 1.0 - bottomFactor;
571
572 const T* sourceTopLeft = source + sourceStrideElements * topPixel + leftPixel * channels;
573 const T* sourceTopRight = source + sourceStrideElements * topPixel + rightPixel * channels;
574
575 const T* sourceBottomLeft = source + sourceStrideElements * bottomPixel + leftPixel * channels;
576 const T* sourceBottomRight = source + sourceStrideElements * bottomPixel + rightPixel * channels;
577
578 for (unsigned int n = 0u; n < channels; ++n)
579 {
580 const double top = double(sourceTopLeft[n]) * leftFactor + double(sourceTopRight[n]) * rightFactor;
581 const double bottom = double(sourceBottomLeft[n]) * leftFactor + double(sourceBottomRight[n]) * rightFactor;
582
583 const double interpolated = top * topFactor + bottom * bottomFactor;
584
585 result[n] = T(interpolated);
586 }
587
588 const T* const targetValue = target + targetStrideElements * y + x * channels;
589
590 for (unsigned int n = 0u; n < channels; ++n)
591 {
592 const double absError = NumericD::abs(double(result[n]) - double(targetValue[n]));
593
594 sumAbsError += absError;
595 maxAbsError = max(maxAbsError, absError);
596 }
597
598 if (groundTruth)
599 {
600 memcpy(groundTruth + (y * targetWidth + x) * channels, result.data(), sizeof(T) * channels);
601 }
602 }
603 }
604
605 if (averageAbsError)
606 {
607 *averageAbsError = sumAbsError / double(targetWidth * targetHeight * channels);
608 }
609
610 if (maximalAbsError)
611 {
612 *maximalAbsError = maxAbsError;
613 }
614}
615
616template <typename T>
617void TestFrameInterpolatorBilinear::validateHomography(const Frame& input, const Frame& output, const SquareMatrix3& input_H_output, const T* backgroundColor, const CV::PixelPositionI& interpolatedFrameOrigin, double* averageAbsError, double* maximalAbsError, Frame* groundTruth)
618{
619 ocean_assert(input.isValid() && output.isValid());
620 ocean_assert(input.isPixelFormatCompatible(output.pixelFormat()));
621
622 ocean_assert(!input_H_output.isSingular());
623 ocean_assert(backgroundColor != nullptr);
624
625 const Scalar frameBorderEps = Scalar(0.5);
626
627 ocean_assert(input.numberPlanes() == 1u);
628
629 const unsigned int channels = input.channels();
630 ocean_assert(channels >= 1u);
631
632 std::vector<T> result(channels, T(0));
633
634 if (averageAbsError != nullptr)
635 {
636 *averageAbsError = NumericD::maxValue();
637 }
638
639 if (maximalAbsError != nullptr)
640 {
641 *maximalAbsError = NumericD::maxValue();
642 }
643
644 if (groundTruth != nullptr)
645 {
646 groundTruth->set(output.frameType(), false /*forceOwner*/, true /*forceWritable*/);
647 }
648
649 double sumAbsError = 0.0;
650 double maxAbsError = 0.0;
651 unsigned long long measurements = 0ull;
652
653 for (unsigned int yOutput = 0u; yOutput < output.height(); ++yOutput)
654 {
655 for (unsigned int xOutput = 0u; xOutput < output.width(); ++xOutput)
656 {
657 const T* const outputPixel = output.constpixel<T>(xOutput, yOutput);
658
659 const Vector2 outputPosition = Vector2(Scalar(xOutput) + Scalar(interpolatedFrameOrigin.x()), Scalar(yOutput) + Scalar(interpolatedFrameOrigin.y()));
660 const Vector2 inputPosition = input_H_output * outputPosition;
661
662 if (inputPosition.x() >= Scalar(0) && inputPosition.y() >= Scalar(0) && inputPosition.x() <= Scalar(input.width() - 1u) && inputPosition.y() <= Scalar(input.height() - 1u))
663 {
664 const unsigned int inputLeftPixel = (unsigned int)(inputPosition.x());
665 const unsigned int inputRightPixel = min(inputLeftPixel + 1u, input.width() - 1u);
666
667 const unsigned int inputTopPixel = (unsigned int)(inputPosition.y());
668 const unsigned int inputBottomPixel = min(inputTopPixel + 1u, input.height() - 1u);
669
670 const double rightFactor = double(inputPosition.x()) - double(inputLeftPixel);
671 const double bottomFactor = double(inputPosition.y()) - double(inputTopPixel);
672
673 ocean_assert(rightFactor >= 0.0 && rightFactor <= 1.0);
674 ocean_assert(bottomFactor >= 0.0 && bottomFactor <= 1.0);
675
676 const double leftFactor = 1.0 - rightFactor;
677 const double topFactor = 1.0 - bottomFactor;
678
679 const T* const inputTopLeft = input.constpixel<T>(inputLeftPixel, inputTopPixel);
680 const T* const inputTopRight = input.constpixel<T>(inputRightPixel, inputTopPixel);
681
682 const T* const inputBottomLeft = input.constpixel<T>(inputLeftPixel, inputBottomPixel);
683 const T* const inputBottomRight = input.constpixel<T>(inputRightPixel, inputBottomPixel);
684
685 for (unsigned int n = 0u; n < channels; ++n)
686 {
687 const double top = double(inputTopLeft[n]) * leftFactor + double(inputTopRight[n]) * rightFactor;
688 const double bottom = double(inputBottomLeft[n]) * leftFactor + double(inputBottomRight[n]) * rightFactor;
689
690 const double interpolated = top * topFactor + bottom * bottomFactor;
691
692 result[n] = T(interpolated);
693 }
694
695 // we do not check the result if we are very close to the frame boundaries
696 if (Numeric::isNotEqual(inputPosition.x(), Scalar(0), frameBorderEps) && Numeric::isNotEqual(inputPosition.x(), Scalar(input.width() - 1u), frameBorderEps)
697 && Numeric::isNotEqual(inputPosition.y(), Scalar(0), frameBorderEps) && Numeric::isNotEqual(inputPosition.y(), Scalar(input.height() - 1u), frameBorderEps))
698 {
699 for (unsigned int n = 0u; n < channels; ++n)
700 {
701 const double absError = NumericD::abs(double(result[n]) - double(outputPixel[n]));
702
703 sumAbsError += absError;
704 maxAbsError = max(maxAbsError, absError);
705
706 measurements++;
707 }
708 }
709
710 if (groundTruth != nullptr)
711 {
712 memcpy(groundTruth->pixel<T>(xOutput, yOutput), result.data(), sizeof(T) * channels);
713 }
714 }
715 else
716 {
717 // we do not check the result if we are very close to the frame boundaries
718 if (Numeric::isNotEqual(inputPosition.x(), Scalar(0), frameBorderEps) && Numeric::isNotEqual(inputPosition.x(), Scalar(input.width() - 1u), frameBorderEps)
719 && Numeric::isNotEqual(inputPosition.y(), Scalar(0), frameBorderEps) && Numeric::isNotEqual(inputPosition.y(), Scalar(input.height() - 1u), frameBorderEps))
720 {
721 for (unsigned int n = 0u; n < channels; ++n)
722 {
723 const double absError = NumericD::abs(double(backgroundColor[n]) - double(outputPixel[n]));
724
725 sumAbsError += absError;
726 maxAbsError = max(maxAbsError, absError);
727
728 measurements++;
729 }
730 }
731
732 if (groundTruth != nullptr)
733 {
734 memcpy(groundTruth->pixel<T>(xOutput, yOutput), backgroundColor, sizeof(T) * channels);
735 }
736 }
737 }
738 }
739
740 ocean_assert(measurements != 0ull || input.width() <= 2u || input.height() <= 2u || output.width() <= 2u || output.height() <= 2u);
741
742 if (averageAbsError && measurements != 0ull)
743 {
744 *averageAbsError = sumAbsError / double(measurements);
745 }
746
747 if (maximalAbsError)
748 {
749 *maximalAbsError = maxAbsError;
750 }
751}
752
753}
754
755}
756
757}
758
759#endif // META_OCEAN_TEST_TESTCV_TEST_FRAME_INTERPOLATOR_BILINEAR_H
This class implements a 2D pixel position with pixel precision.
Definition PixelPosition.h:63
T y() const
Returns the vertical coordinate position of this object.
Definition PixelPosition.h:468
T x() const
Returns the horizontal coordinate position of this object.
Definition PixelPosition.h:456
This class implements Ocean's image class.
Definition Frame.h:1969
const FrameType & frameType() const
Returns the frame type of this frame.
Definition Frame.h:4029
bool isValid() const
Returns whether this frame is valid.
Definition Frame.h:4705
T * pixel(const unsigned int x, const unsigned int y, const unsigned int planeIndex=0u)
Returns the pointer to the data of a specific pixel.
Definition Frame.h:4466
bool set(const FrameType &frameType, const bool forceOwner, const bool forceWritable=false, const Indices32 &planePaddingElements=Indices32(), const Timestamp &timestamp=Timestamp(false), bool *reallocated=nullptr)
Sets a new frame type for this frame.
const T * constpixel(const unsigned int x, const unsigned int y, const unsigned int planeIndex=0u) const
Returns the pointer to the constant data of a specific pixel.
Definition Frame.h:4507
unsigned int width() const
Returns the width of the frame format in pixel.
Definition Frame.h:3334
uint32_t numberPlanes() const
Returns the number of planes of the pixel format of this frame.
Definition Frame.h:3374
PixelFormat pixelFormat() const
Returns the pixel format of the frame.
Definition Frame.h:3344
unsigned int height() const
Returns the height of the frame in pixel.
Definition Frame.h:3339
bool isPixelFormatCompatible(const PixelFormat pixelFormat) const
Returns whether the pixel format of this frame type is compatible with a given pixel format.
Definition Frame.h:3391
unsigned int channels() const
Returns the number of individual channels the frame has.
Definition Frame.h:3364
This class implements a 2D lookup object with values at the bins' corners defining the individual loo...
Definition Lookup2.h:636
static T abs(const T value)
Returns the absolute value of a given value.
Definition Numeric.h:1220
static bool isNotEqual(const T first, const T second)
Returns whether two values are not equal up to a small epsilon.
Definition Numeric.h:2622
static constexpr T maxValue()
Returns the max scalar value.
Definition Numeric.h:3253
bool isSingular() const
Returns whether this matrix is singular (and thus cannot be inverted).
Definition SquareMatrix3.h:1342
This class implements a bilinear frame interpolation test.
Definition TestFrameInterpolatorBilinear.h:38
static bool testResampleCameraImage(const double testDuration, Worker &worker)
Tests the function to re-sample a camera image.
static bool testSpecialCasesResize400x400To256x256_8BitPerChannel(const double testDuration)
Tests the special case resize function for image resolutions from 400x400 to 256x256.
static bool testLookup(const double testDuration, Worker &worker)
Tests the frame transformation function applying a lookup table.
static bool testSpecialCasesResize400x400To224x224_8BitPerChannel(const double testDuration)
Tests the special case resize function for image resolutions from 400x400 to 224x224.
static bool testRotateFrame(const unsigned int width, const unsigned int height, const double testDuration, Worker &worker)
Tests the frame rotate function.
static bool validateRotatedFrame(const Frame &source, const Frame &target, const Scalar anchorX, const Scalar anchorY, const Scalar angle)
Validates the rotation of a frame using a bilinear interpolation.
static bool testResize(const double testDuration, Worker &worker)
Tests the bilinear resize function.
static bool testInterpolatePixel(const double testDuration)
Tests the pixel interpolation function for frames with arbitrary data type.
static bool testLookup(const double testDuration, Worker &worker)
Tests the frame transformation function applying a lookup table.
static bool testPatchIntensitySum1Channel(const unsigned int width, const unsigned int height, const unsigned int patchWidth, const unsigned int patchHeight, const double testDuration)
Tests the intensity sum of an image patch with sub-pixel location in a 1-channel frame using an integ...
static bool testInterpolatePixel8BitPerChannel(const CV::PixelCenter pixelCenter, const double testDuration)
Tests the pixel interpolation function for frames with 8 bit per channel.
static bool testResampleCameraImage(const double testDuration, Worker &worker)
Tests the function to re-sample a camera image.
static bool testPatchIntensitySum1Channel(const unsigned int width, const unsigned int height, const double testDuration)
Tests the intensity sum of an image patch with sub-pixel location in a 1-channel frame using an integ...
static bool testScale(const double testDuration, Worker &worker)
Tests the bilinear scale function with scale factors which are not derived from the frame dimensions.
static bool validateInterpolatePixel8BitPerChannel(const Frame &frame, const VectorT2< TScalar > &position, const CV::PixelCenter pixelCenter, const uint8_t *const interpolationResult, const TScalar threshold)
Validates a pixel interpolation result for frame with 8 bit per channel.
static bool testHomography(const double testDuration, Worker &worker)
Tests the homography transformation function supporting arbitrary pixel formats using a constant colo...
static bool testResize(const double testDuration, Worker &worker)
Tests the bilinear resize function supporting arbitrary data types.
static bool testAffine(const double testDuration, Worker &worker)
Tests the affine transformation function using a constant color for unknown image content.
static bool testResize(const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int sourceChannels, const unsigned int targetWidth, const unsigned int targetHeight, const double testDuration, Worker &worker)
Tests the bilinear resize function for arbitrary data types and for a given frame dimension and chann...
static bool testAffine(const unsigned int width, const unsigned int height, const unsigned int channels, const double testDuration, Worker &worker)
Tests the function for affine transformations (with constant color for unknown image content) for a g...
static void validateHomography(const Frame &input, const Frame &output, const SquareMatrix3 &input_H_output, const T *backgroundColor, const CV::PixelPositionI &interpolatedFrameOrigin, double *averageAbsError, double *maximalAbsError, Frame *groundTruth=nullptr)
Validates the homography interpolation function for (almost) arbitrary pixel formats (using a constan...
Definition TestFrameInterpolatorBilinear.h:617
static bool testResizeExtremeResolutions(const double testDuration, Worker &worker)
Tests the bilinear resize function for extreme image resolutions.
static void validateScaleFrame(const unsigned char *source, const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int channels, const unsigned char *target, const unsigned int targetWidth, const unsigned int targetHeight, const double xTargetToSource, const double yTargetToSource, const unsigned int sourcePaddingElements, const unsigned int targetPaddingElements, double *averageAbsErrorToInteger, unsigned int *maximalAbsErrorToInteger, unsigned char *groundTruth=nullptr)
Validates the bilinear frame resize function.
static bool testLookup(const unsigned int width, const unsigned int height, const unsigned int channels, const double testDuration, Worker &worker)
Tests the frame transformation function applying a lookup table.
static bool validatePatchIntensitySum1Channel(const Frame &yFrame, const unsigned int patchWidth, const unsigned int patchHeight, const Vector2 &center, const CV::PixelCenter pixelCenter, const Scalar intensity)
Validate the intensity sum of an image patch with sub-pixel location in a 1-channel frame.
static bool testHomographyMask(const unsigned int width, const unsigned int height, const unsigned int channels, const double testDuration, Worker &worker)
Tests the homography transformation function (with binary mask defining known and unknown image conte...
static bool validateLookup(const Frame &sourceFrame, const Frame &targetFrame, const LookupCorner2< Vector2 > &lookupTable, const bool offset, const T *backgroundColor)
Validates the frame transformation function applying a lookup table.
static bool testInterpolatePixel8BitPerChannel(const double testDuration)
Tests the pixel interpolation function for frames with 8 bit per channel.
static bool testInterpolatePixel(const CV::PixelCenter pixelCenter, const double testDuration)
Tests the pixel interpolation function for frames arbitrary data type.
static bool testLookupMask(const unsigned int width, const unsigned int height, const double testDuration, Worker &worker)
Tests the frame mask transformation function applying a lookup table.
static bool validateLookupMask(const Frame &sourceFrame, const Frame &targetFrame, const Frame &targetMask, const LookupCorner2< Vector2 > &lookupTable, const bool offset)
Validates the frame mask transformation function applying a lookup table.
static bool test(const unsigned int width, const unsigned int height, const double testDuration, Worker &worker, const TestSelector &selector=TestSelector())
Tests all bilinear interpolation filter functions.
static bool testScale(const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int channels, const unsigned int targetWidth, const unsigned int targetHeight, const double xSource_s_xTarget, const double ySource_s_yTarget, const double testDuration, Worker &worker)
Tests the bilinear scale function for a given frame dimension, channel number, and pair of scale fact...
static bool testHomographyMask(const double testDuration, Worker &worker)
Tests the homography transformation function defining a binary mask for known and unknown image conte...
static bool testResize(const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int sourceChannels, const unsigned int targetWidth, const unsigned int targetHeight, const double testDuration, Worker &worker)
Tests the bilinear resize function for a given frame dimension and channel number.
static bool testHomography(const unsigned int width, const unsigned int height, const unsigned int channels, const double testDuration, Worker &worker)
Tests the homography transformation function (with constant color for unknown image content) for arbi...
static bool validateHomographyMask8BitPerChannel(const Frame &frame, const Frame &interpolatedFrame, const Frame &interpolatedMask, const SquareMatrix3 &input_H_output, const CV::PixelPositionI &interpolatedFrameOrigin)
Validates the homography interpolation function (using a binary mask to define known and unknown imag...
static bool validateTransformation8BitPerChannel(const Frame &source, const Frame &validationTarget, const SquareMatrix3 &source_H_target, const uint8_t *backgroundColor, const CV::PixelPositionI &interpolatedFrameOrigin)
Validation function for the bilinear interpolation of 2D homogeneous image transformations (+ constan...
static void validateScaleFramePrecision7Bit(const uint8_t *source, const unsigned int sourceWidth, const unsigned int sourceHeight, const unsigned int channels, const uint8_t *target, const unsigned int targetWidth, const unsigned int targetHeight, const double xSource_s_xTarget, const double ySource_s_yTarget, const unsigned int sourcePaddingElements, const unsigned int targetPaddingElements, double *averageAbsError, double *maximalAbsError, uint8_t *groundTruth=nullptr)
Validates the bilinear frame resize function for uint8_t data types using 7-bit integer precision.
static bool validatePatchFrame8BitPerChannel(const uint8_t *const source, const uint8_t *const validationTarget, const uint32_t sourceWidth, const uint32_t sourceHeight, const Scalar x, const Scalar y, const uint32_t validationTargetWidth, const uint32_t validationTargetHeight, const uint32_t sourcePaddingElements, const uint32_t validationTargetPaddingElements)
Validate the bilinear extraction of frame patches.
static bool validateInterpolatePixel(const Frame &frame, const VectorT2< TScalar > &position, const CV::PixelCenter pixelCenter, const TTarget *const interpolationResult, const TScalar threshold)
Validates a pixel interpolation result for frame with arbitrary data type.
This class implements a test selector that parses test function strings and determines which tests sh...
Definition TestSelector.h:51
This class implements a vector with two elements.
Definition Vector2.h:96
const T & x() const noexcept
Returns the x value.
Definition Vector2.h:703
const T & y() const noexcept
Returns the y value.
Definition Vector2.h:715
This class implements a worker able to distribute function calls over different threads.
Definition Worker.h:33
T minmax(const T &lowerBoundary, const T &value, const T &upperBoundary)
This function fits a given parameter into a specified value range.
Definition base/Utilities.h:973
PixelCenter
Definition of individual centers of pixels.
Definition CV.h:117
float Scalar
Definition of a scalar type.
Definition Math.h:129
VectorT2< Scalar > Vector2
Definition of a 2D vector.
Definition Vector2.h:28
The namespace covering the entire Ocean framework.
Definition Accessor.h:15