2 // Copyright 2019 Mateusz Loskot <mateusz at loskot dot net>
4 // Distributed under the Boost Software License, Version 1.0
5 // See accompanying file LICENSE_1_0.txt or copy at
6 // http://www.boost.org/LICENSE_1_0.txt
8 #include <boost/gil.hpp>
9 #include <boost/gil/extension/numeric/pixel_numeric_operations.hpp>
12 #include <type_traits>
14 #define BOOST_TEST_MODULE test_ext_numeric_pixel_numeric_operations
15 #include "unit_test.hpp"
16 #include "unit_test_utility.hpp"
17 #include "core/image/test_fixture.hpp" // random_value
18 #include "core/pixel/test_fixture.hpp"
20 namespace gil
= boost::gil
;
21 namespace fixture
= boost::gil::test::fixture
;
23 BOOST_AUTO_TEST_SUITE(pixel_plus_t
)
25 BOOST_AUTO_TEST_CASE_TEMPLATE(plus_integer_same_types
, pixel_t
, fixture::pixel_integer_types
)
27 using channel_t
= typename
gil::channel_type
<pixel_t
>::type
;
28 gil::pixel_plus_t
<pixel_t
, pixel_t
, pixel_t
> f
;
31 gil::static_fill(p0
, static_cast<channel_t
>(0));
32 BOOST_TEST(f(p0
, p0
) == p0
);
36 gil::static_fill(p1
, static_cast<channel_t
>(1));
38 gil::static_fill(r2
, static_cast<channel_t
>(2));
39 BOOST_TEST(f(p1
, p1
) == r2
);
42 // Generates pixels with consecutive channel values: {1} or {1,2,3} or {1,2,3,4} etc.
43 fixture::consecutive_value
<channel_t
> g(1);
45 gil::static_generate(p
, [&g
]() { return g(); });
46 auto const r
= f(p
, p
);
48 BOOST_TEST(gil::at_c
<0>(r
) == (gil::at_c
<0>(p
) + gil::at_c
<0>(p
)));
52 BOOST_AUTO_TEST_SUITE_END() // pixel_plus_t
54 BOOST_AUTO_TEST_SUITE(pixel_minus_t
)
56 BOOST_AUTO_TEST_CASE_TEMPLATE(minus_integer_same_types
, pixel_t
, fixture::pixel_integer_types
)
58 using channel_t
= typename
gil::channel_type
<pixel_t
>::type
;
59 gil::pixel_minus_t
<pixel_t
, pixel_t
, pixel_t
> f
;
62 gil::static_fill(p0
, static_cast<channel_t
>(0));
63 BOOST_TEST(f(p0
, p0
) == p0
);
66 gil::static_fill(p1
, static_cast<channel_t
>(1));
67 gil::static_fill(p2
, static_cast<channel_t
>(2));
69 gil::static_fill(r1
, static_cast<channel_t
>(1));
70 BOOST_TEST(f(p2
, p1
) == r1
);
73 // Generates pixels with consecutive channel values: {1} or {1,2,3} or {1,2,3,4} etc.
74 fixture::consecutive_value
<channel_t
> g(1);
76 gil::static_generate(p
, [&g
]() { return g(); });
77 BOOST_TEST(f(p
, p
) == p0
);
81 BOOST_AUTO_TEST_SUITE_END() // pixel_minus_t
83 BOOST_AUTO_TEST_SUITE(pixel_multiplies_scalar_t
)
85 BOOST_AUTO_TEST_CASE_TEMPLATE(pixel_multiplies_scalar_integer_same_types
, pixel_t
, fixture::pixel_integer_types
)
87 using channel_t
= typename
gil::channel_type
<pixel_t
>::type
;
88 gil::pixel_multiplies_scalar_t
<pixel_t
, channel_t
, pixel_t
> f
;
91 gil::static_fill(p0
, static_cast<channel_t
>(0));
92 BOOST_TEST(f(p0
, 0) == p0
);
96 gil::static_fill(p1
, static_cast<channel_t
>(1));
97 BOOST_TEST(f(p1
, 0) == p0
);
98 BOOST_TEST(f(p1
, 1) == p1
);
101 // Generates pixels with consecutive channel values: {1} or {1,2,3} or {1,2,3,4} etc.
102 fixture::consecutive_value
<channel_t
> g(1);
104 gil::static_generate(p
, [&g
]() { return g(); });
106 // check first channel value is doubled
107 auto const r
= f(p
, 2);
109 BOOST_TEST(gil::at_c
<0>(r
) == (gil::at_c
<0>(p
) * 2));
113 BOOST_AUTO_TEST_SUITE_END() // pixel_multiplies_scalar_t
115 BOOST_AUTO_TEST_SUITE(pixel_multiply_t
)
117 BOOST_AUTO_TEST_CASE_TEMPLATE(pixel_multiply_integer_same_types
, pixel_t
, fixture::pixel_integer_types
)
119 using channel_t
= typename
gil::channel_type
<pixel_t
>::type
;
120 gil::pixel_multiply_t
<pixel_t
, pixel_t
, pixel_t
> f
;
123 gil::static_fill(p0
, static_cast<channel_t
>(0));
124 BOOST_TEST(f(p0
, p0
) == p0
);
127 gil::static_fill(p1
, static_cast<channel_t
>(1));
128 BOOST_TEST(f(p1
, p1
) == p1
);
131 gil::static_fill(p2
, static_cast<channel_t
>(2));
132 BOOST_TEST(f(p1
, p2
) == p2
);
135 BOOST_AUTO_TEST_SUITE_END() // pixel_multiply_t
137 BOOST_AUTO_TEST_SUITE(pixel_divides_scalar_t
)
139 BOOST_AUTO_TEST_CASE_TEMPLATE(pixel_divides_scalar_integer_same_types
, pixel_t
, fixture::pixel_integer_types
)
141 using channel_t
= typename
gil::channel_type
<pixel_t
>::type
;
142 gil::pixel_divides_scalar_t
<pixel_t
, channel_t
, pixel_t
> f
;
145 gil::static_fill(p0
, static_cast<channel_t
>(0));
146 BOOST_TEST(f(p0
, 1) == p0
);
149 gil::static_fill(p1
, static_cast<channel_t
>(1));
150 BOOST_TEST(f(p1
, 1) == p1
);
153 gil::static_fill(p2
, static_cast<channel_t
>(2));
154 BOOST_TEST(f(p2
, 2) == p1
);
157 BOOST_AUTO_TEST_SUITE_END() // pixel_divides_scalar_t
159 BOOST_AUTO_TEST_SUITE(pixel_divide_t
)
161 BOOST_AUTO_TEST_CASE_TEMPLATE(pixel_divide_integer_same_types
, pixel_t
, fixture::pixel_integer_types
)
163 using channel_t
= typename
gil::channel_type
<pixel_t
>::type
;
164 gil::pixel_divide_t
<pixel_t
, pixel_t
, pixel_t
> f
;
167 gil::static_fill(p0
, static_cast<channel_t
>(0));
169 gil::static_fill(p1
, static_cast<channel_t
>(1));
170 BOOST_TEST(f(p0
, p1
) == p0
);
171 BOOST_TEST(f(p1
, p1
) == p1
);
174 gil::static_fill(p2
, static_cast<channel_t
>(2));
175 BOOST_TEST(f(p2
, p1
) == p2
);
178 BOOST_AUTO_TEST_SUITE_END() // pixel_divide_t
180 BOOST_AUTO_TEST_SUITE(pixel_halves_t
)
182 BOOST_AUTO_TEST_CASE_TEMPLATE(pixel_halves_integer_same_types
, pixel_t
, fixture::pixel_integer_types
)
184 using channel_t
= typename
gil::channel_type
<pixel_t
>::type
;
185 gil::pixel_halves_t
<pixel_t
> f
;
188 gil::static_fill(p0
, static_cast<channel_t
>(0));
190 gil::static_fill(p1
, static_cast<channel_t
>(1));
194 BOOST_TEST(f(p
) == p0
);
198 BOOST_TEST(f(p
) == p0
); // truncates toward Zero
202 gil::static_fill(p2
, static_cast<channel_t
>(2));
203 BOOST_TEST(f(p2
) == p1
);
207 BOOST_AUTO_TEST_SUITE_END() // pixel_halves_t
209 BOOST_AUTO_TEST_SUITE(pixel_zeros_t
)
211 BOOST_AUTO_TEST_CASE_TEMPLATE(pixel_zeros_integer_same_types
, pixel_t
, fixture::pixel_integer_types
)
213 using channel_t
= typename
gil::channel_type
<pixel_t
>::type
;
214 gil::pixel_zeros_t
<pixel_t
> f
;
217 gil::static_fill(p0
, static_cast<channel_t
>(0));
220 BOOST_TEST(f(p
) == p0
);
223 fixture::consecutive_value
<channel_t
> g(1);
225 gil::static_generate(p
, [&g
]() { return g(); });
226 BOOST_TEST(f(p
) == p0
);
230 BOOST_AUTO_TEST_SUITE_END() // pixel_zeros_t
232 BOOST_AUTO_TEST_SUITE(zero_channels
)
234 BOOST_AUTO_TEST_CASE_TEMPLATE(zero_channels_integer_same_types
, pixel_t
, fixture::pixel_integer_types
)
236 using channel_t
= typename
gil::channel_type
<pixel_t
>::type
;
239 gil::static_fill(p0
, static_cast<channel_t
>(0));
242 gil::zero_channels(p
);
246 fixture::consecutive_value
<channel_t
> g(1);
248 gil::static_generate(p
, [&g
]() { return g(); });
249 gil::zero_channels(p
);
254 BOOST_AUTO_TEST_SUITE_END() // zero_channels
256 BOOST_AUTO_TEST_SUITE(pixel_assigns_t
)
258 BOOST_AUTO_TEST_CASE_TEMPLATE(pixel_assigns_integer_same_types
, pixel_t
, fixture::pixel_integer_types
)
260 using channel_t
= typename
gil::channel_type
<pixel_t
>::type
;
261 gil::pixel_assigns_t
<pixel_t
, pixel_t
> f
;
265 gil::static_fill(p0
, static_cast<channel_t
>(0));
270 fixture::consecutive_value
<channel_t
> g(1);
272 gil::static_generate(p
, [&g
]() { return g(); });
278 BOOST_AUTO_TEST_SUITE_END() // pixel_assigns_t