Commit 75028fa6 authored by Khushal's avatar Khushal Committed by Commit Bot

cc/blink: Use same rounding for cc and ImageDecoder mip level sizes.

The JPEGDecoder ceils when rounding floats for mip level sizes while the
cc code floors. This results in 1 pixel differences in the scaled sizes
when using decode to scale. Avoid this by switching the cc mip size
calculations to match the decoder.

R=ericrk@chromium.org, chrishtr@chromium.org

Bug: 761565,558070
Cq-Include-Trybots: luci.chromium.try:android_optional_gpu_tests_rel;luci.chromium.try:linux_layout_tests_slimming_paint_v2;master.tryserver.blink:linux_trusty_blink_rel
Change-Id: I07069a4eff582ffbb621388ccae32b18aedebd3a
Reviewed-on: https://chromium-review.googlesource.com/1107049
Commit-Queue: Khushal <khushalsagar@chromium.org>
Reviewed-by: default avatarEric Seckler <eseckler@chromium.org>
Reviewed-by: default avatarEric Karl <ericrk@chromium.org>
Reviewed-by: default avatarChris Harrelson <chrishtr@chromium.org>
Cr-Commit-Position: refs/heads/master@{#569626}
parent ae149e74
......@@ -4,13 +4,25 @@
#include "cc/tiles/mipmap_util.h"
#include "base/numerics/safe_math.h"
namespace cc {
namespace {
// Calculates the size of |axis_base_size| at the given |mip_level| using
// OpenGL rounding rules.
// Calculates the size of |axis_base_size| at the given |mip_level|. Note that
// the calculation here rounds up for consistency with size calculations in the
// JPEG decoder. This allows us to decode images to the mip size directly.
int ScaleAxisToMipLevel(int axis_base_size, int mip_level) {
DCHECK_GE(mip_level, 0);
DCHECK_LT(mip_level, 32);
if (mip_level == 0)
return axis_base_size;
// Increment the size by (2^mip_level - 1) so we round on when dividing it
// below.
base::CheckedNumeric<int> base_size = axis_base_size;
base_size += (1 << mip_level) - 1;
axis_base_size = base_size.ValueOrDefault(std::numeric_limits<int>::max());
return std::max(1, axis_base_size >> mip_level);
}
......
......@@ -85,8 +85,8 @@ TEST(MipMapUtilTest, NonSquare) {
// Ensures that we handle rounding images correctly.
TEST(MipMapUtilTest, Rounding) {
const gfx::Size src_size(49, 49);
const gfx::Size target_size_larger(25, 25);
const gfx::Size target_size_smaller(24, 24);
const gfx::Size target_size_larger(26, 26);
const gfx::Size target_size_smaller(25, 25);
const int target_level_larger = 0;
const int target_level_smaller = 1;
const SkSize expected_scale_larger = SkSize::Make(1, 1);
......@@ -116,5 +116,15 @@ TEST(MipMapUtilTest, Rounding) {
MipMapUtil::GetScaleAdjustmentForSize(src_size, target_size_smaller));
}
// Ensures that we round up during mip calculation.
TEST(MipMapUtilTest, RoundUp) {
const gfx::Size src_sizes[] = {gfx::Size(3, 3), gfx::Size(5, 7),
gfx::Size(11, 14), gfx::Size(17, 31)};
for (int i = 0; i < 4; ++i) {
EXPECT_EQ(MipMapUtil::GetSizeForLevel(src_sizes[i], i + 1),
gfx::Size(2, 2));
}
}
} // namespace
} // namespace cc
......@@ -396,9 +396,9 @@ TEST(SoftwareImageDecodeCacheTest, ImageKeyMediumQualityAt0_1Scale) {
draw_image, kN32_SkColorType);
EXPECT_EQ(draw_image.frame_key(), key.frame_key());
EXPECT_EQ(key.type(), SoftwareImageDecodeCache::CacheKey::kSubrectAndScale);
EXPECT_EQ(62, key.target_size().width());
EXPECT_EQ(63, key.target_size().width());
EXPECT_EQ(25, key.target_size().height());
EXPECT_EQ(62u * 25u * 4u, key.locked_bytes());
EXPECT_EQ(63u * 25u * 4u, key.locked_bytes());
}
TEST(SoftwareImageDecodeCacheTest, ImageKeyMediumQualityAt0_01Scale) {
......@@ -415,9 +415,9 @@ TEST(SoftwareImageDecodeCacheTest, ImageKeyMediumQualityAt0_01Scale) {
draw_image, kN32_SkColorType);
EXPECT_EQ(draw_image.frame_key(), key.frame_key());
EXPECT_EQ(key.type(), SoftwareImageDecodeCache::CacheKey::kSubrectAndScale);
EXPECT_EQ(7, key.target_size().width());
EXPECT_EQ(3, key.target_size().height());
EXPECT_EQ(7u * 3u * 4u, key.locked_bytes());
EXPECT_EQ(8, key.target_size().width());
EXPECT_EQ(4, key.target_size().height());
EXPECT_EQ(8u * 4u * 4u, key.locked_bytes());
}
TEST(SoftwareImageDecodeCacheTest,
......@@ -477,9 +477,9 @@ TEST(SoftwareImageDecodeCacheTest, ImageKeyHighQualityDropToMediumIfTooLarge) {
draw_image, kN32_SkColorType);
EXPECT_EQ(draw_image.frame_key(), key.frame_key());
EXPECT_EQ(key.type(), SoftwareImageDecodeCache::CacheKey::kSubrectAndScale);
EXPECT_EQ(2277, key.target_size().width());
EXPECT_EQ(2278, key.target_size().width());
EXPECT_EQ(1024, key.target_size().height());
EXPECT_EQ(2277u * 1024u * 4u, key.locked_bytes());
EXPECT_EQ(2278u * 1024u * 4u, key.locked_bytes());
}
TEST(SoftwareImageDecodeCacheTest,
......@@ -1445,7 +1445,7 @@ TEST(SoftwareImageDecodeCacheTest, MediumQualityAt0_1ScaleIsHandled) {
// Decoded image should not be lazy generated.
EXPECT_FALSE(decoded_draw_image.image()->isLazyGenerated());
EXPECT_EQ(kLow_SkFilterQuality, decoded_draw_image.filter_quality());
EXPECT_EQ(62, decoded_draw_image.image()->width());
EXPECT_EQ(63, decoded_draw_image.image()->width());
EXPECT_EQ(25, decoded_draw_image.image()->height());
cache.DrawWithImageFinished(draw_image, decoded_draw_image);
......@@ -1476,8 +1476,8 @@ TEST(SoftwareImageDecodeCacheTest, MediumQualityAt0_01ScaleIsHandled) {
// Decoded image should not be lazy generated.
EXPECT_FALSE(decoded_draw_image.image()->isLazyGenerated());
EXPECT_EQ(kLow_SkFilterQuality, decoded_draw_image.filter_quality());
EXPECT_EQ(7, decoded_draw_image.image()->width());
EXPECT_EQ(3, decoded_draw_image.image()->height());
EXPECT_EQ(8, decoded_draw_image.image()->width());
EXPECT_EQ(4, decoded_draw_image.image()->height());
cache.DrawWithImageFinished(draw_image, decoded_draw_image);
cache.UnrefImage(draw_image);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment