mirror of
https://github.com/python-pillow/Pillow.git
synced 2025-07-05 12:23:18 +03:00
turn on ImagingReduce5x5 special case
This commit is contained in:
parent
b655e81d39
commit
e54b9b3720
|
@ -6,11 +6,29 @@ from .helper import PillowTestCase, hopper, convert_to_comparable
|
||||||
class TestImageReduce(PillowTestCase):
|
class TestImageReduce(PillowTestCase):
|
||||||
# There are several internal implementations
|
# There are several internal implementations
|
||||||
remarkable_factors = [
|
remarkable_factors = [
|
||||||
1, 2, 3, 4, 5, 6, # special implementations
|
# special implementations
|
||||||
(1, 2), (1, 3), (1, 4), (1, 7), # 1xN implementation
|
1,
|
||||||
(2, 1), (3, 1), (4, 1), (7, 1), # Nx1 implementation
|
2,
|
||||||
|
3,
|
||||||
|
4,
|
||||||
|
5,
|
||||||
|
6,
|
||||||
|
# 1xN implementation
|
||||||
|
(1, 2),
|
||||||
|
(1, 3),
|
||||||
|
(1, 4),
|
||||||
|
(1, 7),
|
||||||
|
# Nx1 implementation
|
||||||
|
(2, 1),
|
||||||
|
(3, 1),
|
||||||
|
(4, 1),
|
||||||
|
(7, 1),
|
||||||
# general implementation with different paths
|
# general implementation with different paths
|
||||||
(4, 6), (5, 6), (4, 7), (5, 7), (19, 17),
|
(4, 6),
|
||||||
|
(5, 6),
|
||||||
|
(4, 7),
|
||||||
|
(5, 7),
|
||||||
|
(19, 17),
|
||||||
]
|
]
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
|
@ -70,7 +88,7 @@ class TestImageReduce(PillowTestCase):
|
||||||
|
|
||||||
def get_image(self, mode):
|
def get_image(self, mode):
|
||||||
mode_info = ImageMode.getmode(mode)
|
mode_info = ImageMode.getmode(mode)
|
||||||
if mode_info.basetype == 'L':
|
if mode_info.basetype == "L":
|
||||||
bands = [self.gradients_image]
|
bands = [self.gradients_image]
|
||||||
for _ in mode_info.bands[1:]:
|
for _ in mode_info.bands[1:]:
|
||||||
# rotate previous image
|
# rotate previous image
|
||||||
|
@ -78,7 +96,7 @@ class TestImageReduce(PillowTestCase):
|
||||||
bands.append(band)
|
bands.append(band)
|
||||||
# Correct alpha channel to exclude completely transparent pixels.
|
# Correct alpha channel to exclude completely transparent pixels.
|
||||||
# Low alpha values also emphasize error after alpha multiplication.
|
# Low alpha values also emphasize error after alpha multiplication.
|
||||||
if mode.endswith('A'):
|
if mode.endswith("A"):
|
||||||
bands[-1] = bands[-1].point(lambda x: int(85 + x / 1.5))
|
bands[-1] = bands[-1].point(lambda x: int(85 + x / 1.5))
|
||||||
im = Image.merge(mode, bands)
|
im = Image.merge(mode, bands)
|
||||||
else:
|
else:
|
||||||
|
@ -136,10 +154,8 @@ class TestImageReduce(PillowTestCase):
|
||||||
self.assert_compare_images(reduced, reference, average_diff, max_diff)
|
self.assert_compare_images(reduced, reference, average_diff, max_diff)
|
||||||
|
|
||||||
def assert_compare_images(self, a, b, max_average_diff, max_diff=255):
|
def assert_compare_images(self, a, b, max_average_diff, max_diff=255):
|
||||||
self.assertEqual(
|
self.assertEqual(a.mode, b.mode, "got mode %r, expected %r" % (a.mode, b.mode))
|
||||||
a.mode, b.mode, "got mode %r, expected %r" % (a.mode, b.mode))
|
self.assertEqual(a.size, b.size, "got size %r, expected %r" % (a.size, b.size))
|
||||||
self.assertEqual(
|
|
||||||
a.size, b.size, "got size %r, expected %r" % (a.size, b.size))
|
|
||||||
|
|
||||||
a, b = convert_to_comparable(a, b)
|
a, b = convert_to_comparable(a, b)
|
||||||
|
|
||||||
|
@ -148,19 +164,25 @@ class TestImageReduce(PillowTestCase):
|
||||||
ch_diff = ImageMath.eval("convert(abs(a - b), 'L')", a=ach, b=bch)
|
ch_diff = ImageMath.eval("convert(abs(a - b), 'L')", a=ach, b=bch)
|
||||||
ch_hist = ch_diff.histogram()
|
ch_hist = ch_diff.histogram()
|
||||||
|
|
||||||
average_diff = (sum(i * num for i, num in enumerate(ch_hist))
|
average_diff = sum(i * num for i, num in enumerate(ch_hist)) / float(
|
||||||
/ float(a.size[0] * a.size[1]))
|
a.size[0] * a.size[1]
|
||||||
|
)
|
||||||
self.assertGreaterEqual(
|
self.assertGreaterEqual(
|
||||||
max_average_diff, average_diff,
|
max_average_diff,
|
||||||
("average pixel value difference {:.4f} > expected {:.4f} "
|
average_diff,
|
||||||
"for '{}' band").format(average_diff, max_average_diff, band),
|
(
|
||||||
|
"average pixel value difference {:.4f} > expected {:.4f} "
|
||||||
|
"for '{}' band"
|
||||||
|
).format(average_diff, max_average_diff, band),
|
||||||
)
|
)
|
||||||
|
|
||||||
last_diff = [i for i, num in enumerate(ch_hist) if num > 0][-1]
|
last_diff = [i for i, num in enumerate(ch_hist) if num > 0][-1]
|
||||||
self.assertGreaterEqual(
|
self.assertGreaterEqual(
|
||||||
max_diff, last_diff,
|
max_diff,
|
||||||
"max pixel value difference {} > expected {} for '{}' band"
|
last_diff,
|
||||||
.format(last_diff, max_diff, band),
|
"max pixel value difference {} > expected {} for '{}' band".format(
|
||||||
|
last_diff, max_diff, band
|
||||||
|
),
|
||||||
)
|
)
|
||||||
|
|
||||||
def test_mode_L(self):
|
def test_mode_L(self):
|
||||||
|
@ -175,7 +197,7 @@ class TestImageReduce(PillowTestCase):
|
||||||
self.compare_reduce_with_reference(im, factor, 0.8, 5)
|
self.compare_reduce_with_reference(im, factor, 0.8, 5)
|
||||||
|
|
||||||
# With opaque alpha, error should be way smaller
|
# With opaque alpha, error should be way smaller
|
||||||
im.putalpha(Image.new('L', im.size, 255))
|
im.putalpha(Image.new("L", im.size, 255))
|
||||||
for factor in self.remarkable_factors:
|
for factor in self.remarkable_factors:
|
||||||
self.compare_reduce_with_reference(im, factor)
|
self.compare_reduce_with_reference(im, factor)
|
||||||
self.compare_reduce_with_box(im, factor)
|
self.compare_reduce_with_box(im, factor)
|
||||||
|
@ -198,7 +220,7 @@ class TestImageReduce(PillowTestCase):
|
||||||
self.compare_reduce_with_reference(im, factor, 0.8, 5)
|
self.compare_reduce_with_reference(im, factor, 0.8, 5)
|
||||||
|
|
||||||
# With opaque alpha, error should be way smaller
|
# With opaque alpha, error should be way smaller
|
||||||
im.putalpha(Image.new('L', im.size, 255))
|
im.putalpha(Image.new("L", im.size, 255))
|
||||||
for factor in self.remarkable_factors:
|
for factor in self.remarkable_factors:
|
||||||
self.compare_reduce_with_reference(im, factor)
|
self.compare_reduce_with_reference(im, factor)
|
||||||
self.compare_reduce_with_box(im, factor)
|
self.compare_reduce_with_box(im, factor)
|
||||||
|
|
|
@ -983,12 +983,16 @@ ImagingReduce5x5(Imaging imOut, Imaging imIn, int box[4])
|
||||||
for (x = 0; x < box[2] / xscale; x++) {
|
for (x = 0; x < box[2] / xscale; x++) {
|
||||||
int xx = box[0] + x*xscale;
|
int xx = box[0] + x*xscale;
|
||||||
UINT32 v;
|
UINT32 v;
|
||||||
ss0 = line0[xx*4 + 0] + line0[xx*4 + 4] + line0[xx*4 + 8] +
|
ss0 = line0[xx*4 + 0] + line0[xx*4 + 4] + line0[xx*4 + 8] + line0[xx*4 + 12] + line0[xx*4 + 16] +
|
||||||
line1[xx*4 + 0] + line1[xx*4 + 4] + line1[xx*4 + 8] +
|
line1[xx*4 + 0] + line1[xx*4 + 4] + line1[xx*4 + 8] + line1[xx*4 + 12] + line1[xx*4 + 16] +
|
||||||
line2[xx*4 + 0] + line2[xx*4 + 4] + line2[xx*4 + 8];
|
line2[xx*4 + 0] + line2[xx*4 + 4] + line2[xx*4 + 8] + line2[xx*4 + 12] + line2[xx*4 + 16] +
|
||||||
ss3 = line0[xx*4 + 3] + line0[xx*4 + 7] + line0[xx*4 + 11] +
|
line3[xx*4 + 0] + line3[xx*4 + 4] + line3[xx*4 + 8] + line3[xx*4 + 12] + line3[xx*4 + 16] +
|
||||||
line1[xx*4 + 3] + line1[xx*4 + 7] + line1[xx*4 + 11] +
|
line4[xx*4 + 0] + line4[xx*4 + 4] + line4[xx*4 + 8] + line4[xx*4 + 12] + line4[xx*4 + 16];
|
||||||
line2[xx*4 + 3] + line2[xx*4 + 7] + line2[xx*4 + 11];
|
ss3 = line0[xx*4 + 3] + line0[xx*4 + 7] + line0[xx*4 + 11] + line0[xx*4 + 15] + line0[xx*4 + 19] +
|
||||||
|
line1[xx*4 + 3] + line1[xx*4 + 7] + line1[xx*4 + 11] + line1[xx*4 + 15] + line1[xx*4 + 19] +
|
||||||
|
line2[xx*4 + 3] + line2[xx*4 + 7] + line2[xx*4 + 11] + line2[xx*4 + 15] + line2[xx*4 + 19] +
|
||||||
|
line3[xx*4 + 3] + line3[xx*4 + 7] + line3[xx*4 + 11] + line3[xx*4 + 15] + line3[xx*4 + 19] +
|
||||||
|
line4[xx*4 + 3] + line4[xx*4 + 7] + line4[xx*4 + 11] + line4[xx*4 + 15] + line4[xx*4 + 19];
|
||||||
v = MAKE_UINT32(
|
v = MAKE_UINT32(
|
||||||
((ss0 + amend) * multiplier) >> 24, 0,
|
((ss0 + amend) * multiplier) >> 24, 0,
|
||||||
0, ((ss3 + amend) * multiplier) >> 24);
|
0, ((ss3 + amend) * multiplier) >> 24);
|
||||||
|
@ -998,15 +1002,21 @@ ImagingReduce5x5(Imaging imOut, Imaging imIn, int box[4])
|
||||||
for (x = 0; x < box[2] / xscale; x++) {
|
for (x = 0; x < box[2] / xscale; x++) {
|
||||||
int xx = box[0] + x*xscale;
|
int xx = box[0] + x*xscale;
|
||||||
UINT32 v;
|
UINT32 v;
|
||||||
ss0 = line0[xx*4 + 0] + line0[xx*4 + 4] + line0[xx*4 + 8] +
|
ss0 = line0[xx*4 + 0] + line0[xx*4 + 4] + line0[xx*4 + 8] + line0[xx*4 + 12] + line0[xx*4 + 16] +
|
||||||
line1[xx*4 + 0] + line1[xx*4 + 4] + line1[xx*4 + 8] +
|
line1[xx*4 + 0] + line1[xx*4 + 4] + line1[xx*4 + 8] + line1[xx*4 + 12] + line1[xx*4 + 16] +
|
||||||
line2[xx*4 + 0] + line2[xx*4 + 4] + line2[xx*4 + 8];
|
line2[xx*4 + 0] + line2[xx*4 + 4] + line2[xx*4 + 8] + line2[xx*4 + 12] + line2[xx*4 + 16] +
|
||||||
ss1 = line0[xx*4 + 1] + line0[xx*4 + 5] + line0[xx*4 + 9] +
|
line3[xx*4 + 0] + line3[xx*4 + 4] + line3[xx*4 + 8] + line3[xx*4 + 12] + line3[xx*4 + 16] +
|
||||||
line1[xx*4 + 1] + line1[xx*4 + 5] + line1[xx*4 + 9] +
|
line4[xx*4 + 0] + line4[xx*4 + 4] + line4[xx*4 + 8] + line4[xx*4 + 12] + line4[xx*4 + 16];
|
||||||
line2[xx*4 + 1] + line2[xx*4 + 5] + line2[xx*4 + 9];
|
ss1 = line0[xx*4 + 1] + line0[xx*4 + 5] + line0[xx*4 + 9] + line0[xx*4 + 13] + line0[xx*4 + 17] +
|
||||||
ss2 = line0[xx*4 + 2] + line0[xx*4 + 6] + line0[xx*4 + 10] +
|
line1[xx*4 + 1] + line1[xx*4 + 5] + line1[xx*4 + 9] + line1[xx*4 + 13] + line1[xx*4 + 17] +
|
||||||
line1[xx*4 + 2] + line1[xx*4 + 6] + line1[xx*4 + 10] +
|
line2[xx*4 + 1] + line2[xx*4 + 5] + line2[xx*4 + 9] + line2[xx*4 + 13] + line2[xx*4 + 17] +
|
||||||
line2[xx*4 + 2] + line2[xx*4 + 6] + line2[xx*4 + 10];
|
line3[xx*4 + 1] + line3[xx*4 + 5] + line3[xx*4 + 9] + line3[xx*4 + 13] + line3[xx*4 + 17] +
|
||||||
|
line4[xx*4 + 1] + line4[xx*4 + 5] + line4[xx*4 + 9] + line4[xx*4 + 13] + line4[xx*4 + 17];
|
||||||
|
ss2 = line0[xx*4 + 2] + line0[xx*4 + 6] + line0[xx*4 + 10] + line0[xx*4 + 14] + line0[xx*4 + 18] +
|
||||||
|
line1[xx*4 + 2] + line1[xx*4 + 6] + line1[xx*4 + 10] + line1[xx*4 + 14] + line1[xx*4 + 18] +
|
||||||
|
line2[xx*4 + 2] + line2[xx*4 + 6] + line2[xx*4 + 10] + line2[xx*4 + 14] + line2[xx*4 + 18] +
|
||||||
|
line3[xx*4 + 2] + line3[xx*4 + 6] + line3[xx*4 + 10] + line3[xx*4 + 14] + line3[xx*4 + 18] +
|
||||||
|
line4[xx*4 + 2] + line4[xx*4 + 6] + line4[xx*4 + 10] + line4[xx*4 + 14] + line4[xx*4 + 18];
|
||||||
v = MAKE_UINT32(
|
v = MAKE_UINT32(
|
||||||
((ss0 + amend) * multiplier) >> 24, ((ss1 + amend) * multiplier) >> 24,
|
((ss0 + amend) * multiplier) >> 24, ((ss1 + amend) * multiplier) >> 24,
|
||||||
((ss2 + amend) * multiplier) >> 24, 0);
|
((ss2 + amend) * multiplier) >> 24, 0);
|
||||||
|
@ -1397,7 +1407,7 @@ ImagingReduce(Imaging imIn, int xscale, int yscale, int box[4])
|
||||||
} else {
|
} else {
|
||||||
ImagingReduceNx1(imOut, imIn, box, xscale);
|
ImagingReduceNx1(imOut, imIn, box, xscale);
|
||||||
}
|
}
|
||||||
} else if (xscale == yscale && xscale <= 4) {
|
} else if (xscale == yscale && xscale <= 5) {
|
||||||
if (xscale == 2) {
|
if (xscale == 2) {
|
||||||
ImagingReduce2x2(imOut, imIn, box);
|
ImagingReduce2x2(imOut, imIn, box);
|
||||||
} else if (xscale == 3) {
|
} else if (xscale == 3) {
|
||||||
|
|
Loading…
Reference in New Issue
Block a user