1 // Unit tests for FFTConvolutionEffect.
6 #include "effect_chain.h"
7 #include "gtest/gtest.h"
8 #include "image_format.h"
10 #include "fft_convolution_effect.h"
14 TEST(FFTConvolutionEffectTest, Identity) {
17 float data[size * size] = {
23 float out_data[size * size];
25 for (int convolve_size = 1; convolve_size < 10; ++convolve_size) {
26 float kernel[convolve_size * convolve_size];
27 for (int i = 0; i < convolve_size * convolve_size; ++i) {
32 EffectChainTester tester(nullptr, size, size, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR);
33 tester.add_input(data, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR, size, size);
35 FFTConvolutionEffect *fft_effect = new FFTConvolutionEffect(size, size, convolve_size, convolve_size);
36 tester.get_chain()->add_effect(fft_effect);
37 fft_effect->set_convolution_kernel(kernel);
38 tester.run(out_data, GL_RED, COLORSPACE_sRGB, GAMMA_LINEAR, OUTPUT_ALPHA_FORMAT_PREMULTIPLIED);
40 expect_equal(data, out_data, size, size, 0.02, 0.003);
44 TEST(FFTConvolutionEffectTest, Constant) {
45 const int size = 4, convolve_size = 17;
48 float data[size * size] = {
54 float expected_data[size * size] = {
55 f * 0.1f, f * 1.1f, f * 2.1f, f * 3.1f,
56 f * 0.2f, f * 1.2f, f * 2.2f, f * 3.2f,
57 f * 0.3f, f * 1.3f, f * 2.3f, f * 3.3f,
58 f * 0.4f, f * 1.4f, f * 2.4f, f * 3.4f,
60 float out_data[size * size];
61 float kernel[convolve_size * convolve_size];
62 for (int i = 0; i < convolve_size * convolve_size; ++i) {
67 EffectChainTester tester(nullptr, size, size, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR);
68 tester.add_input(data, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR, size, size);
70 FFTConvolutionEffect *fft_effect = new FFTConvolutionEffect(size, size, convolve_size, convolve_size);
71 tester.get_chain()->add_effect(fft_effect);
72 fft_effect->set_convolution_kernel(kernel);
73 tester.run(out_data, GL_RED, COLORSPACE_sRGB, GAMMA_LINEAR, OUTPUT_ALPHA_FORMAT_PREMULTIPLIED);
75 // Somewhat looser bounds due to the higher magnitude.
76 expect_equal(expected_data, out_data, size, size, f * 0.03, f * 0.004);
79 TEST(FFTConvolutionEffectTest, MoveRight) {
80 const int size = 4, convolve_size = 3;
82 float data[size * size] = {
88 float kernel[convolve_size * convolve_size] = {
93 float expected_data[size * size] = {
99 float out_data[size * size];
101 EffectChainTester tester(nullptr, size, size, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR);
102 tester.add_input(data, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR, size, size);
104 FFTConvolutionEffect *fft_effect = new FFTConvolutionEffect(size, size, convolve_size, convolve_size);
105 tester.get_chain()->add_effect(fft_effect);
106 fft_effect->set_convolution_kernel(kernel);
107 tester.run(out_data, GL_RED, COLORSPACE_sRGB, GAMMA_LINEAR, OUTPUT_ALPHA_FORMAT_PREMULTIPLIED);
109 expect_equal(expected_data, out_data, size, size, 0.02, 0.003);
112 TEST(FFTConvolutionEffectTest, MoveDown) {
113 const int size = 4, convolve_size = 3;
115 float data[size * size] = {
121 float kernel[convolve_size * convolve_size] = {
126 float expected_data[size * size] = {
132 float out_data[size * size];
134 EffectChainTester tester(nullptr, size, size, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR);
135 tester.add_input(data, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR, size, size);
137 FFTConvolutionEffect *fft_effect = new FFTConvolutionEffect(size, size, convolve_size, convolve_size);
138 tester.get_chain()->add_effect(fft_effect);
139 fft_effect->set_convolution_kernel(kernel);
140 tester.run(out_data, GL_RED, COLORSPACE_sRGB, GAMMA_LINEAR, OUTPUT_ALPHA_FORMAT_PREMULTIPLIED);
142 expect_equal(expected_data, out_data, size, size, 0.02, 0.003);
145 TEST(FFTConvolutionEffectTest, MergeWithLeft) {
146 const int size = 4, convolve_size = 3;
148 float data[size * size] = {
154 float kernel[convolve_size * convolve_size] = {
159 float expected_data[size * size] = {
160 0.1 + 0.1, 0.1 + 1.1, 1.1 + 2.1, 2.1 + 3.1,
161 0.2 + 0.2, 0.2 + 1.2, 1.2 + 2.2, 2.2 + 3.2,
162 0.3 + 0.3, 0.3 + 1.3, 1.3 + 2.3, 2.3 + 3.3,
163 0.4 + 0.4, 0.4 + 1.4, 1.4 + 2.4, 2.4 + 3.4,
165 float out_data[size * size];
167 EffectChainTester tester(nullptr, size, size, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR);
168 tester.add_input(data, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR, size, size);
170 FFTConvolutionEffect *fft_effect = new FFTConvolutionEffect(size, size, convolve_size, convolve_size);
171 tester.get_chain()->add_effect(fft_effect);
172 fft_effect->set_convolution_kernel(kernel);
173 tester.run(out_data, GL_RED, COLORSPACE_sRGB, GAMMA_LINEAR, OUTPUT_ALPHA_FORMAT_PREMULTIPLIED);
175 expect_equal(expected_data, out_data, size, size, 0.02, 0.003);
178 TEST(FFTConvolutionEffectTest, NegativeCoefficients) {
180 const int convolve_width = 3, convolve_height = 2;
182 float data[size * size] = {
188 float kernel[convolve_width * convolve_height] = {
192 float expected_data[size * size] = {
193 0.1 - 0.5 * 0.1, 1.1 - 0.5 * 0.1, 2.1 - 0.5 * 0.1, 3.1 - 0.5 * 1.1,
194 0.2 - 0.5 * 0.1, 1.2 - 0.5 * 0.1, 2.2 - 0.5 * 0.1, 3.2 - 0.5 * 1.1,
195 0.3 - 0.5 * 0.2, 1.3 - 0.5 * 0.2, 2.3 - 0.5 * 0.2, 3.3 - 0.5 * 1.2,
196 0.4 - 0.5 * 0.3, 1.4 - 0.5 * 0.3, 2.4 - 0.5 * 0.3, 3.4 - 0.5 * 1.3,
198 float out_data[size * size];
200 EffectChainTester tester(nullptr, size, size, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR);
201 tester.add_input(data, FORMAT_GRAYSCALE, COLORSPACE_sRGB, GAMMA_LINEAR, size, size);
203 FFTConvolutionEffect *fft_effect = new FFTConvolutionEffect(size, size, convolve_width, convolve_height);
204 tester.get_chain()->add_effect(fft_effect);
205 fft_effect->set_convolution_kernel(kernel);
206 tester.run(out_data, GL_RED, COLORSPACE_sRGB, GAMMA_LINEAR, OUTPUT_ALPHA_FORMAT_PREMULTIPLIED);
208 expect_equal(expected_data, out_data, size, size, 0.02, 0.003);