diff --git a/modules/imgproc/test/test_imgwarp.cpp b/modules/imgproc/test/test_imgwarp.cpp index 2260cf510b..c2cf2bfc69 100644 --- a/modules/imgproc/test/test_imgwarp.cpp +++ b/modules/imgproc/test/test_imgwarp.cpp @@ -1538,6 +1538,108 @@ TEST(Imgproc_resize_area, regression) ASSERT_EQ(cvtest::norm(one_channel_diff, cv::NORM_INF), 0); } +TEST(Imgproc_resize_area, regression_half_round) +{ + static uchar input_data[32 * 32]; + for(int i = 0; i < 32 * 32; ++i) + input_data[i] = i % 2 + 253 + i / (16 * 32); + + static uchar expected_data[16 * 16]; + for(int i = 0; i < 16 * 16; ++i) + expected_data[i] = 254 + i / (16 * 8); + + cv::Mat src(32, 32, CV_8UC1, input_data); + cv::Mat expected(16, 16, CV_8UC1, expected_data); + cv::Mat actual(expected.size(), expected.type()); + + cv::resize(src, actual, cv::Size(), 0.5, 0.5, INTER_AREA); + + ASSERT_EQ(actual.type(), expected.type()); + ASSERT_EQ(actual.size(), expected.size()); + + Mat diff; + absdiff(actual, expected, diff); + + float elem_diff = 0.5f; + Size dsize = actual.size(); + bool next = true; + for (int dy = 0; dy < dsize.height && next; ++dy) + { + uchar* eD = expected.ptr(dy); + uchar* aD = actual.ptr(dy); + + for (int dx = 0; dx < dsize.width && next; ++dx) + if (fabs(static_cast(aD[dx] - eD[dx])) > elem_diff) + { + cvtest::TS::ptr()->printf(cvtest::TS::SUMMARY, "Inf norm: %f\n", static_cast(norm(actual, expected, NORM_INF))); + cvtest::TS::ptr()->printf(cvtest::TS::SUMMARY, "Error in : (%d, %d)\n", dx, dy); + + const int radius = 3; + int rmin = MAX(dy - radius, 0), rmax = MIN(dy + radius, dsize.height); + int cmin = MAX(dx - radius, 0), cmax = MIN(dx + radius, dsize.width); + + std::cout << "Abs diff:" << std::endl << diff << std::endl; + std::cout << "actual result:\n" << actual(Range(rmin, rmax), Range(cmin, cmax)) << std::endl; + std::cout << "expected result:\n" << expected(Range(rmin, rmax), Range(cmin, cmax)) << std::endl; + + next = false; + } + } + + ASSERT_EQ(norm(diff, cv::NORM_INF), 0); +} + +TEST(Imgproc_resize_area, regression_quarter_round) +{ + static uchar input_data[32 * 32]; + for(int i = 0; i < 32 * 32; ++i) + input_data[i] = i % 2 + 253 + i / (16 * 32); + + static uchar expected_data[8 * 8]; + for(int i = 0; i < 8 * 8; ++i) + expected_data[i] = 254; + + cv::Mat src(32, 32, CV_8UC1, input_data); + cv::Mat expected(8, 8, CV_8UC1, expected_data); + cv::Mat actual(expected.size(), expected.type()); + + cv::resize(src, actual, cv::Size(), 0.25, 0.25, INTER_AREA); + + ASSERT_EQ(actual.type(), expected.type()); + ASSERT_EQ(actual.size(), expected.size()); + + Mat diff; + absdiff(actual, expected, diff); + + float elem_diff = 0.5f; + Size dsize = actual.size(); + bool next = true; + for (int dy = 0; dy < dsize.height && next; ++dy) + { + uchar* eD = expected.ptr(dy); + uchar* aD = actual.ptr(dy); + + for (int dx = 0; dx < dsize.width && next; ++dx) + if (fabs(static_cast(aD[dx] - eD[dx])) > elem_diff) + { + cvtest::TS::ptr()->printf(cvtest::TS::SUMMARY, "Inf norm: %f\n", static_cast(norm(actual, expected, NORM_INF))); + cvtest::TS::ptr()->printf(cvtest::TS::SUMMARY, "Error in : (%d, %d)\n", dx, dy); + + const int radius = 3; + int rmin = MAX(dy - radius, 0), rmax = MIN(dy + radius, dsize.height); + int cmin = MAX(dx - radius, 0), cmax = MIN(dx + radius, dsize.width); + + std::cout << "Abs diff:" << std::endl << diff << std::endl; + std::cout << "actual result:\n" << actual(Range(rmin, rmax), Range(cmin, cmax)) << std::endl; + std::cout << "expected result:\n" << expected(Range(rmin, rmax), Range(cmin, cmax)) << std::endl; + + next = false; + } + } + + ASSERT_EQ(norm(diff, cv::NORM_INF), 0); +} + //////////////////////////////////////////////////////////////////////////