Commit e3b7da9e authored by Dana Jansens's avatar Dana Jansens

cc: Remove and Create the correct tiles when resizing live tiles rect

When removing tiles, we need to remove everything outside the live
tiles rect even if it has borders inside the live tiles rect. The
DifferenceIterator includes borders when deciding if a tile is in the
included rect, so tiles that are only in the included rect with a border
were not being removed from the tiling. This lead to us having tiles
outside the rect, and to creating a tile that already existed.

When adding tiles, the same problem existed. The DifferenceIterator
includes borders when deciding which tiles are to be excluded, so a
tile that was inside the old live tiles rect with borders only would
not have existed, but it would be excluded by the DifferenceIterator.
This prevented us from making tiles that were inside the live tiles
rect.

Depends on: https://codereview.chromium.org/513903002/

R=enne@chromium.org, vmpstr@chromium.org, enne, vmpstr
BUG=405427

Review URL: https://codereview.chromium.org/505913003

Cr-Commit-Position: refs/heads/master@{#292417}
parent a1733ee3
...@@ -126,7 +126,7 @@ int TilingData::LastBorderTileYIndexFromSrcCoord(int src_position) const { ...@@ -126,7 +126,7 @@ int TilingData::LastBorderTileYIndexFromSrcCoord(int src_position) const {
return std::min(std::max(y, 0), num_tiles_y_ - 1); return std::min(std::max(y, 0), num_tiles_y_ - 1);
} }
gfx::Rect TilingData::ExpandRectIgnoringBordersToTileBoundsWithBorders( gfx::Rect TilingData::ExpandRectIgnoringBordersToTileBounds(
const gfx::Rect& rect) const { const gfx::Rect& rect) const {
if (rect.IsEmpty() || has_empty_bounds()) if (rect.IsEmpty() || has_empty_bounds())
return gfx::Rect(); return gfx::Rect();
...@@ -137,8 +137,8 @@ gfx::Rect TilingData::ExpandRectIgnoringBordersToTileBoundsWithBorders( ...@@ -137,8 +137,8 @@ gfx::Rect TilingData::ExpandRectIgnoringBordersToTileBoundsWithBorders(
int index_right = TileXIndexFromSrcCoord(rect.right() - 1); int index_right = TileXIndexFromSrcCoord(rect.right() - 1);
int index_bottom = TileYIndexFromSrcCoord(rect.bottom() - 1); int index_bottom = TileYIndexFromSrcCoord(rect.bottom() - 1);
gfx::Rect rect_top_left(TileBoundsWithBorder(index_x, index_y)); gfx::Rect rect_top_left(TileBounds(index_x, index_y));
gfx::Rect rect_bottom_right(TileBoundsWithBorder(index_right, index_bottom)); gfx::Rect rect_bottom_right(TileBounds(index_right, index_bottom));
return gfx::UnionRects(rect_top_left, rect_bottom_right); return gfx::UnionRects(rect_top_left, rect_bottom_right);
} }
...@@ -379,24 +379,17 @@ TilingData::DifferenceIterator::DifferenceIterator( ...@@ -379,24 +379,17 @@ TilingData::DifferenceIterator::DifferenceIterator(
return; return;
} }
consider_left_ = consider_left_ = tiling_data_->TileXIndexFromSrcCoord(consider.x());
tiling_data_->FirstBorderTileXIndexFromSrcCoord(consider.x()); consider_top_ = tiling_data_->TileYIndexFromSrcCoord(consider.y());
consider_top_ = consider_right_ = tiling_data_->TileXIndexFromSrcCoord(consider.right() - 1);
tiling_data_->FirstBorderTileYIndexFromSrcCoord(consider.y());
consider_right_ =
tiling_data_->LastBorderTileXIndexFromSrcCoord(consider.right() - 1);
consider_bottom_ = consider_bottom_ =
tiling_data_->LastBorderTileYIndexFromSrcCoord(consider.bottom() - 1); tiling_data_->TileYIndexFromSrcCoord(consider.bottom() - 1);
if (!ignore.IsEmpty()) { if (!ignore.IsEmpty()) {
ignore_left_ = ignore_left_ = tiling_data_->TileXIndexFromSrcCoord(ignore.x());
tiling_data_->FirstBorderTileXIndexFromSrcCoord(ignore.x()); ignore_top_ = tiling_data_->TileYIndexFromSrcCoord(ignore.y());
ignore_top_ = ignore_right_ = tiling_data_->TileXIndexFromSrcCoord(ignore.right() - 1);
tiling_data_->FirstBorderTileYIndexFromSrcCoord(ignore.y()); ignore_bottom_ = tiling_data_->TileYIndexFromSrcCoord(ignore.bottom() - 1);
ignore_right_ =
tiling_data_->LastBorderTileXIndexFromSrcCoord(ignore.right() - 1);
ignore_bottom_ =
tiling_data_->LastBorderTileYIndexFromSrcCoord(ignore.bottom() - 1);
// Clamp ignore indices to consider indices. // Clamp ignore indices to consider indices.
ignore_left_ = std::max(ignore_left_, consider_left_); ignore_left_ = std::max(ignore_left_, consider_left_);
...@@ -488,21 +481,17 @@ TilingData::SpiralDifferenceIterator::SpiralDifferenceIterator( ...@@ -488,21 +481,17 @@ TilingData::SpiralDifferenceIterator::SpiralDifferenceIterator(
return; return;
} }
consider_left_ = consider_left_ = tiling_data_->TileXIndexFromSrcCoord(consider.x());
tiling_data_->FirstBorderTileXIndexFromSrcCoord(consider.x()); consider_top_ = tiling_data_->TileYIndexFromSrcCoord(consider.y());
consider_top_ = tiling_data_->FirstBorderTileYIndexFromSrcCoord(consider.y()); consider_right_ = tiling_data_->TileXIndexFromSrcCoord(consider.right() - 1);
consider_right_ =
tiling_data_->LastBorderTileXIndexFromSrcCoord(consider.right() - 1);
consider_bottom_ = consider_bottom_ =
tiling_data_->LastBorderTileYIndexFromSrcCoord(consider.bottom() - 1); tiling_data_->TileYIndexFromSrcCoord(consider.bottom() - 1);
if (!ignore.IsEmpty()) { if (!ignore.IsEmpty()) {
ignore_left_ = tiling_data_->FirstBorderTileXIndexFromSrcCoord(ignore.x()); ignore_left_ = tiling_data_->TileXIndexFromSrcCoord(ignore.x());
ignore_top_ = tiling_data_->FirstBorderTileYIndexFromSrcCoord(ignore.y()); ignore_top_ = tiling_data_->TileYIndexFromSrcCoord(ignore.y());
ignore_right_ = ignore_right_ = tiling_data_->TileXIndexFromSrcCoord(ignore.right() - 1);
tiling_data_->LastBorderTileXIndexFromSrcCoord(ignore.right() - 1); ignore_bottom_ = tiling_data_->TileYIndexFromSrcCoord(ignore.bottom() - 1);
ignore_bottom_ =
tiling_data_->LastBorderTileYIndexFromSrcCoord(ignore.bottom() - 1);
// Clamp ignore indices to consider indices. // Clamp ignore indices to consider indices.
ignore_left_ = std::max(ignore_left_, consider_left_); ignore_left_ = std::max(ignore_left_, consider_left_);
...@@ -524,7 +513,7 @@ TilingData::SpiralDifferenceIterator::SpiralDifferenceIterator( ...@@ -524,7 +513,7 @@ TilingData::SpiralDifferenceIterator::SpiralDifferenceIterator(
else if (center.x() > tiling_data->tiling_size().width()) else if (center.x() > tiling_data->tiling_size().width())
around_left = tiling_data->num_tiles_x(); around_left = tiling_data->num_tiles_x();
else else
around_left = tiling_data->FirstBorderTileXIndexFromSrcCoord(center.x()); around_left = tiling_data->TileXIndexFromSrcCoord(center.x());
// Determine around top, such that it is between -1 and num_tiles_y. // Determine around top, such that it is between -1 and num_tiles_y.
int around_top = 0; int around_top = 0;
...@@ -533,7 +522,7 @@ TilingData::SpiralDifferenceIterator::SpiralDifferenceIterator( ...@@ -533,7 +522,7 @@ TilingData::SpiralDifferenceIterator::SpiralDifferenceIterator(
else if (center.y() > tiling_data->tiling_size().height()) else if (center.y() > tiling_data->tiling_size().height())
around_top = tiling_data->num_tiles_y(); around_top = tiling_data->num_tiles_y();
else else
around_top = tiling_data->FirstBorderTileYIndexFromSrcCoord(center.y()); around_top = tiling_data->TileYIndexFromSrcCoord(center.y());
// Determine around right, such that it is between -1 and num_tiles_x. // Determine around right, such that it is between -1 and num_tiles_x.
int right_src_coord = center.right() - 1; int right_src_coord = center.right() - 1;
...@@ -543,8 +532,7 @@ TilingData::SpiralDifferenceIterator::SpiralDifferenceIterator( ...@@ -543,8 +532,7 @@ TilingData::SpiralDifferenceIterator::SpiralDifferenceIterator(
} else if (right_src_coord > tiling_data->tiling_size().width()) { } else if (right_src_coord > tiling_data->tiling_size().width()) {
around_right = tiling_data->num_tiles_x(); around_right = tiling_data->num_tiles_x();
} else { } else {
around_right = around_right = tiling_data->TileXIndexFromSrcCoord(right_src_coord);
tiling_data->LastBorderTileXIndexFromSrcCoord(right_src_coord);
} }
// Determine around bottom, such that it is between -1 and num_tiles_y. // Determine around bottom, such that it is between -1 and num_tiles_y.
...@@ -555,8 +543,7 @@ TilingData::SpiralDifferenceIterator::SpiralDifferenceIterator( ...@@ -555,8 +543,7 @@ TilingData::SpiralDifferenceIterator::SpiralDifferenceIterator(
} else if (bottom_src_coord > tiling_data->tiling_size().height()) { } else if (bottom_src_coord > tiling_data->tiling_size().height()) {
around_bottom = tiling_data->num_tiles_y(); around_bottom = tiling_data->num_tiles_y();
} else { } else {
around_bottom = around_bottom = tiling_data->TileYIndexFromSrcCoord(bottom_src_coord);
tiling_data->LastBorderTileYIndexFromSrcCoord(bottom_src_coord);
} }
vertical_step_count_ = around_bottom - around_top + 1; vertical_step_count_ = around_bottom - around_top + 1;
......
...@@ -52,8 +52,7 @@ class CC_EXPORT TilingData { ...@@ -52,8 +52,7 @@ class CC_EXPORT TilingData {
int LastBorderTileXIndexFromSrcCoord(int src_position) const; int LastBorderTileXIndexFromSrcCoord(int src_position) const;
int LastBorderTileYIndexFromSrcCoord(int src_position) const; int LastBorderTileYIndexFromSrcCoord(int src_position) const;
gfx::Rect ExpandRectIgnoringBordersToTileBoundsWithBorders( gfx::Rect ExpandRectIgnoringBordersToTileBounds(const gfx::Rect& rect) const;
const gfx::Rect& rect) const;
gfx::Rect ExpandRectToTileBounds(const gfx::Rect& rect) const; gfx::Rect ExpandRectToTileBounds(const gfx::Rect& rect) const;
gfx::Rect TileBounds(int i, int j) const; gfx::Rect TileBounds(int i, int j) const;
...@@ -103,14 +102,13 @@ class CC_EXPORT TilingData { ...@@ -103,14 +102,13 @@ class CC_EXPORT TilingData {
int bottom_; int bottom_;
}; };
// Iterate through all indices whose bounds + border intersect with // Iterate through all indices whose bounds (not including borders) intersect
// |consider| but which also do not intersect with |ignore|. // with |consider| but which also do not intersect with |ignore|.
class CC_EXPORT DifferenceIterator : public BaseIterator { class CC_EXPORT DifferenceIterator : public BaseIterator {
public: public:
DifferenceIterator( DifferenceIterator(const TilingData* tiling_data,
const TilingData* tiling_data, const gfx::Rect& consider_rect,
const gfx::Rect& consider_rect, const gfx::Rect& ignore_rect);
const gfx::Rect& ignore_rect);
DifferenceIterator& operator++(); DifferenceIterator& operator++();
private: private:
......
...@@ -773,92 +773,82 @@ TEST(TilingDataTest, SetMaxTextureSizeBorders) { ...@@ -773,92 +773,82 @@ TEST(TilingDataTest, SetMaxTextureSizeBorders) {
EXPECT_EQ(10, data.num_tiles_y()); EXPECT_EQ(10, data.num_tiles_y());
} }
TEST(TilingDataTest, ExpandRectIgnoringBordersToTileBoundsWithBordersEmpty) { TEST(TilingDataTest, ExpandRectIgnoringBordersToTileBoundsEmpty) {
TilingData empty_total_size(gfx::Size(0, 0), gfx::Size(8, 8), true); TilingData empty_total_size(gfx::Size(0, 0), gfx::Size(8, 8), true);
EXPECT_RECT_EQ( EXPECT_RECT_EQ(
gfx::Rect(), gfx::Rect(),
empty_total_size.ExpandRectIgnoringBordersToTileBoundsWithBorders( empty_total_size.ExpandRectIgnoringBordersToTileBounds(gfx::Rect()));
gfx::Rect())); EXPECT_RECT_EQ(gfx::Rect(),
EXPECT_RECT_EQ( empty_total_size.ExpandRectIgnoringBordersToTileBounds(
gfx::Rect(), gfx::Rect(100, 100, 100, 100)));
empty_total_size.ExpandRectIgnoringBordersToTileBoundsWithBorders( EXPECT_RECT_EQ(gfx::Rect(),
gfx::Rect(100, 100, 100, 100))); empty_total_size.ExpandRectIgnoringBordersToTileBounds(
EXPECT_RECT_EQ( gfx::Rect(100, 100)));
gfx::Rect(),
empty_total_size.ExpandRectIgnoringBordersToTileBoundsWithBorders(
gfx::Rect(100, 100)));
TilingData empty_max_texture_size(gfx::Size(8, 8), gfx::Size(0, 0), true); TilingData empty_max_texture_size(gfx::Size(8, 8), gfx::Size(0, 0), true);
EXPECT_RECT_EQ( EXPECT_RECT_EQ(gfx::Rect(),
gfx::Rect(), empty_max_texture_size.ExpandRectIgnoringBordersToTileBounds(
empty_max_texture_size.ExpandRectIgnoringBordersToTileBoundsWithBorders( gfx::Rect()));
gfx::Rect())); EXPECT_RECT_EQ(gfx::Rect(),
EXPECT_RECT_EQ( empty_max_texture_size.ExpandRectIgnoringBordersToTileBounds(
gfx::Rect(), gfx::Rect(100, 100, 100, 100)));
empty_max_texture_size.ExpandRectIgnoringBordersToTileBoundsWithBorders( EXPECT_RECT_EQ(gfx::Rect(),
gfx::Rect(100, 100, 100, 100))); empty_max_texture_size.ExpandRectIgnoringBordersToTileBounds(
EXPECT_RECT_EQ( gfx::Rect(100, 100)));
gfx::Rect(),
empty_max_texture_size.ExpandRectIgnoringBordersToTileBoundsWithBorders(
gfx::Rect(100, 100)));
} }
TEST(TilingDataTest, ExpandRectIgnoringBordersToTileBoundsWithBorders) { TEST(TilingDataTest, ExpandRectIgnoringBordersToTileBounds) {
TilingData data(gfx::Size(4, 4), gfx::Size(16, 32), true); TilingData data(gfx::Size(4, 4), gfx::Size(16, 32), true);
// Small rect at origin rounds up to tile 0, 0. // Small rect at origin rounds up to tile 0, 0.
gfx::Rect at_origin_src(1, 1); gfx::Rect at_origin_src(1, 1);
gfx::Rect at_origin_result(data.TileBoundsWithBorder(0, 0)); gfx::Rect at_origin_result(data.TileBounds(0, 0));
EXPECT_NE(at_origin_src, at_origin_result); EXPECT_NE(at_origin_src, at_origin_result);
EXPECT_RECT_EQ( EXPECT_RECT_EQ(at_origin_result,
at_origin_result, data.ExpandRectIgnoringBordersToTileBounds(at_origin_src));
data.ExpandRectIgnoringBordersToTileBoundsWithBorders(at_origin_src));
// Arbitrary internal rect. // Arbitrary internal rect.
gfx::Rect rect_src(6, 6, 1, 3); gfx::Rect rect_src(6, 6, 1, 3);
// Tile 2, 2 => gfx::Rect(4, 4, 4, 4) // Tile 2, 2 => gfx::Rect(4, 4, 4, 4)
// Tile 2, 3 => gfx::Rect(4, 6, 4, 4) // Tile 2, 3 => gfx::Rect(4, 6, 4, 4)
gfx::Rect rect_result(gfx::UnionRects(data.TileBoundsWithBorder(2, 2), gfx::Rect rect_result(
data.TileBoundsWithBorder(2, 3))); gfx::UnionRects(data.TileBounds(2, 2), data.TileBounds(2, 3)));
EXPECT_NE(rect_src, rect_result); EXPECT_NE(rect_src, rect_result);
EXPECT_RECT_EQ( EXPECT_RECT_EQ(rect_result,
rect_result, data.ExpandRectIgnoringBordersToTileBounds(rect_src));
data.ExpandRectIgnoringBordersToTileBoundsWithBorders(rect_src));
// On tile bounds does not round up to next tile (ignores the border). // On tile bounds does not round up to next tile (ignores the border).
gfx::Rect border_rect_src( gfx::Rect border_rect_src(
gfx::UnionRects(data.TileBounds(1, 2), data.TileBounds(3, 4))); gfx::UnionRects(data.TileBounds(1, 2), data.TileBounds(3, 4)));
gfx::Rect border_rect_result(gfx::UnionRects( gfx::Rect border_rect_result(
data.TileBoundsWithBorder(1, 2), data.TileBoundsWithBorder(3, 4))); gfx::UnionRects(data.TileBounds(1, 2), data.TileBounds(3, 4)));
EXPECT_RECT_EQ( EXPECT_RECT_EQ(border_rect_result,
border_rect_result, data.ExpandRectIgnoringBordersToTileBounds(border_rect_src));
data.ExpandRectIgnoringBordersToTileBoundsWithBorders(border_rect_src));
// Equal to tiling rect. // Equal to tiling rect.
EXPECT_RECT_EQ(gfx::Rect(data.tiling_size()), EXPECT_RECT_EQ(gfx::Rect(data.tiling_size()),
data.ExpandRectIgnoringBordersToTileBoundsWithBorders( data.ExpandRectIgnoringBordersToTileBounds(
gfx::Rect(data.tiling_size()))); gfx::Rect(data.tiling_size())));
// Containing, but larger than tiling rect. // Containing, but larger than tiling rect.
EXPECT_RECT_EQ(gfx::Rect(data.tiling_size()), EXPECT_RECT_EQ(
data.ExpandRectIgnoringBordersToTileBoundsWithBorders( gfx::Rect(data.tiling_size()),
gfx::Rect(100, 100))); data.ExpandRectIgnoringBordersToTileBounds(gfx::Rect(100, 100)));
// Non-intersecting with tiling rect. // Non-intersecting with tiling rect.
gfx::Rect non_intersect(200, 200, 100, 100); gfx::Rect non_intersect(200, 200, 100, 100);
EXPECT_FALSE(non_intersect.Intersects(gfx::Rect(data.tiling_size()))); EXPECT_FALSE(non_intersect.Intersects(gfx::Rect(data.tiling_size())));
EXPECT_RECT_EQ( EXPECT_RECT_EQ(gfx::Rect(),
gfx::Rect(), data.ExpandRectIgnoringBordersToTileBounds(non_intersect));
data.ExpandRectIgnoringBordersToTileBoundsWithBorders(non_intersect));
TilingData data2(gfx::Size(8, 8), gfx::Size(32, 64), true); TilingData data2(gfx::Size(8, 8), gfx::Size(32, 64), true);
// Inside other tile border texels doesn't include other tiles. // Inside other tile border texels doesn't include other tiles.
gfx::Rect inner_rect_src(data2.TileBounds(1, 1)); gfx::Rect inner_rect_src(data2.TileBounds(1, 1));
inner_rect_src.Inset(data2.border_texels(), data.border_texels()); inner_rect_src.Inset(data2.border_texels(), data.border_texels());
gfx::Rect inner_rect_result(data2.TileBoundsWithBorder(1, 1)); gfx::Rect inner_rect_result(data2.TileBounds(1, 1));
gfx::Rect expanded = gfx::Rect expanded =
data2.ExpandRectIgnoringBordersToTileBoundsWithBorders(inner_rect_src); data2.ExpandRectIgnoringBordersToTileBounds(inner_rect_src);
EXPECT_EQ(inner_rect_result.ToString(), expanded.ToString()); EXPECT_EQ(inner_rect_result.ToString(), expanded.ToString());
} }
...@@ -1086,11 +1076,11 @@ void TestIterate(const TilingData& data, ...@@ -1086,11 +1076,11 @@ void TestIterate(const TilingData& data,
} }
// Make sure this also works with a difference iterator and an empty ignore. // Make sure this also works with a difference iterator and an empty ignore.
// The difference iterator always includes borders, so ignore it otherwise. // The difference iterator never includes borders, so ignore it otherwise.
if (include_borders) { if (!include_borders) {
std::vector<std::pair<int, int> > expected = original_expected; std::vector<std::pair<int, int> > expected = original_expected;
for (TilingData::DifferenceIterator iter(&data, rect, gfx::Rect()); for (TilingData::DifferenceIterator iter(&data, rect, gfx::Rect()); iter;
iter; ++iter) { ++iter) {
bool found = false; bool found = false;
for (size_t i = 0; i < expected.size(); ++i) { for (size_t i = 0; i < expected.size(); ++i) {
if (expected[i] == iter.index()) { if (expected[i] == iter.index()) {
...@@ -1250,16 +1240,14 @@ TEST(TilingDataTest, IteratorNoTiles) { ...@@ -1250,16 +1240,14 @@ TEST(TilingDataTest, IteratorNoTiles) {
TestIterateAll(data, gfx::Rect(100, 100), 0, 0, -1, -1); TestIterateAll(data, gfx::Rect(100, 100), 0, 0, -1, -1);
} }
void TestDiff( void TestDiff(const TilingData& data,
const TilingData& data, gfx::Rect consider,
gfx::Rect consider, gfx::Rect ignore,
gfx::Rect ignore, size_t num_tiles) {
size_t num_tiles) {
std::vector<std::pair<int, int> > expected; std::vector<std::pair<int, int> > expected;
for (int y = 0; y < data.num_tiles_y(); ++y) { for (int y = 0; y < data.num_tiles_y(); ++y) {
for (int x = 0; x < data.num_tiles_x(); ++x) { for (int x = 0; x < data.num_tiles_x(); ++x) {
gfx::Rect bounds = data.TileBoundsWithBorder(x, y); gfx::Rect bounds = data.TileBounds(x, y);
if (bounds.Intersects(consider) && !bounds.Intersects(ignore)) if (bounds.Intersects(consider) && !bounds.Intersects(ignore))
expected.push_back(std::make_pair(x, y)); expected.push_back(std::make_pair(x, y));
} }
...@@ -1268,8 +1256,8 @@ void TestDiff( ...@@ -1268,8 +1256,8 @@ void TestDiff(
// Sanity check the test. // Sanity check the test.
EXPECT_EQ(num_tiles, expected.size()); EXPECT_EQ(num_tiles, expected.size());
for (TilingData::DifferenceIterator iter(&data, consider, ignore); for (TilingData::DifferenceIterator iter(&data, consider, ignore); iter;
iter; ++iter) { ++iter) {
bool found = false; bool found = false;
for (size_t i = 0; i < expected.size(); ++i) { for (size_t i = 0; i < expected.size(); ++i) {
if (expected[i] == iter.index()) { if (expected[i] == iter.index()) {
...@@ -1339,16 +1327,26 @@ TEST(TilingDataTest, DifferenceIteratorIgnoreGeometry) { ...@@ -1339,16 +1327,26 @@ TEST(TilingDataTest, DifferenceIteratorIgnoreGeometry) {
TEST(TilingDataTest, DifferenceIteratorManyBorderTexels) { TEST(TilingDataTest, DifferenceIteratorManyBorderTexels) {
// X border index by src coord: [0-50), [10-60), [20-65) // X border index by src coord: [0-50), [10-60), [20-65)
// Y border index by src coord: [0-60), [20-80), [40-100), [60-110) // Y border index by src coord: [0-60), [20-80), [40-100), [60-110)
// X tile bounds by src coord: [0-30), [30-40), [40-65)
// Y tile bounds by src coord: [0-40), [40-60), [60-80), [80-110)
TilingData data(gfx::Size(50, 60), gfx::Size(65, 110), 20); TilingData data(gfx::Size(50, 60), gfx::Size(65, 110), 20);
// Ignore one column, three rows // Knock out two rows, but not the left column.
TestDiff(data, gfx::Rect(0, 30, 55, 80), gfx::Rect(5, 30, 5, 15), 9); TestDiff(data, gfx::Rect(10, 30, 55, 80), gfx::Rect(30, 59, 20, 2), 8);
// Knock out three columns, leaving only one. // Knock out one row.
TestDiff(data, gfx::Rect(10, 30, 55, 80), gfx::Rect(30, 59, 20, 1), 3); TestDiff(data, gfx::Rect(10, 30, 55, 80), gfx::Rect(29, 59, 20, 1), 9);
// Overlap all tiles with ignore rect. // Overlap all tiles with ignore rect.
TestDiff(data, gfx::Rect(65, 110), gfx::Rect(30, 59, 1, 2), 0); TestDiff(data, gfx::Rect(65, 110), gfx::Rect(29, 39, 12, 42), 0);
gfx::Rect tile = data.TileBounds(1, 1);
// Ignore one tile.
TestDiff(data, gfx::Rect(20, 30, 45, 80), tile, 11);
// Include one tile.
TestDiff(data, tile, gfx::Rect(), 1);
} }
TEST(TilingDataTest, DifferenceIteratorOneTile) { TEST(TilingDataTest, DifferenceIteratorOneTile) {
......
...@@ -11,6 +11,7 @@ ...@@ -11,6 +11,7 @@
#include "base/debug/trace_event.h" #include "base/debug/trace_event.h"
#include "base/debug/trace_event_argument.h" #include "base/debug/trace_event_argument.h"
#include "base/logging.h"
#include "cc/base/math_util.h" #include "cc/base/math_util.h"
#include "cc/resources/tile.h" #include "cc/resources/tile.h"
#include "cc/resources/tile_priority.h" #include "cc/resources/tile_priority.h"
...@@ -147,7 +148,7 @@ Tile* PictureLayerTiling::CreateTile(int i, ...@@ -147,7 +148,7 @@ Tile* PictureLayerTiling::CreateTile(int i,
void PictureLayerTiling::CreateMissingTilesInLiveTilesRect() { void PictureLayerTiling::CreateMissingTilesInLiveTilesRect() {
const PictureLayerTiling* twin_tiling = client_->GetTwinTiling(this); const PictureLayerTiling* twin_tiling = client_->GetTwinTiling(this);
bool include_borders = true; bool include_borders = false;
for (TilingData::Iterator iter( for (TilingData::Iterator iter(
&tiling_data_, live_tiles_rect_, include_borders); &tiling_data_, live_tiles_rect_, include_borders);
iter; iter;
...@@ -158,6 +159,8 @@ void PictureLayerTiling::CreateMissingTilesInLiveTilesRect() { ...@@ -158,6 +159,8 @@ void PictureLayerTiling::CreateMissingTilesInLiveTilesRect() {
continue; continue;
CreateTile(key.first, key.second, twin_tiling); CreateTile(key.first, key.second, twin_tiling);
} }
VerifyLiveTilesRect();
} }
void PictureLayerTiling::UpdateTilesToCurrentPile( void PictureLayerTiling::UpdateTilesToCurrentPile(
...@@ -173,10 +176,60 @@ void PictureLayerTiling::UpdateTilesToCurrentPile( ...@@ -173,10 +176,60 @@ void PictureLayerTiling::UpdateTilesToCurrentPile(
gfx::Size tile_size = tiling_data_.max_texture_size(); gfx::Size tile_size = tiling_data_.max_texture_size();
if (layer_bounds_ != old_layer_bounds) { if (layer_bounds_ != old_layer_bounds) {
// Drop tiles outside the new layer bounds if the layer shrank. // The SetLiveTilesRect() method would drop tiles outside the new bounds,
SetLiveTilesRect( // but may do so incorrectly if resizing the tiling causes the number of
gfx::IntersectRects(live_tiles_rect_, gfx::Rect(content_bounds))); // tiles in the tiling_data_ to change.
gfx::Rect content_rect(content_bounds);
int before_left = tiling_data_.TileXIndexFromSrcCoord(live_tiles_rect_.x());
int before_top = tiling_data_.TileYIndexFromSrcCoord(live_tiles_rect_.y());
int before_right =
tiling_data_.TileXIndexFromSrcCoord(live_tiles_rect_.right() - 1);
int before_bottom =
tiling_data_.TileYIndexFromSrcCoord(live_tiles_rect_.bottom() - 1);
// The live_tiles_rect_ is clamped to stay within the tiling size as we
// change it.
live_tiles_rect_.Intersect(content_rect);
tiling_data_.SetTilingSize(content_bounds); tiling_data_.SetTilingSize(content_bounds);
int after_right = -1;
int after_bottom = -1;
if (!live_tiles_rect_.IsEmpty()) {
after_right =
tiling_data_.TileXIndexFromSrcCoord(live_tiles_rect_.right() - 1);
after_bottom =
tiling_data_.TileYIndexFromSrcCoord(live_tiles_rect_.bottom() - 1);
}
// There is no recycled twin since this is run on the pending tiling.
PictureLayerTiling* recycled_twin = NULL;
DCHECK_EQ(recycled_twin, client_->GetRecycledTwinTiling(this));
DCHECK_EQ(PENDING_TREE, client_->GetTree());
// Drop tiles outside the new layer bounds if the layer shrank.
for (int i = after_right + 1; i <= before_right; ++i) {
for (int j = before_top; j <= before_bottom; ++j)
RemoveTileAt(i, j, recycled_twin);
}
for (int i = before_left; i <= after_right; ++i) {
for (int j = after_bottom + 1; j <= before_bottom; ++j)
RemoveTileAt(i, j, recycled_twin);
}
// If the layer grew, the live_tiles_rect_ is not changed, but a new row
// and/or column of tiles may now exist inside the same live_tiles_rect_.
const PictureLayerTiling* twin_tiling = client_->GetTwinTiling(this);
if (after_right > before_right) {
DCHECK_EQ(after_right, before_right + 1);
for (int j = before_top; j <= after_bottom; ++j)
CreateTile(after_right, j, twin_tiling);
}
if (after_bottom > before_bottom) {
DCHECK_EQ(after_bottom, before_bottom + 1);
for (int i = before_left; i <= before_right; ++i)
CreateTile(i, after_bottom, twin_tiling);
}
tile_size = client_->CalculateTileSize(content_bounds); tile_size = client_->CalculateTileSize(content_bounds);
} }
...@@ -192,6 +245,7 @@ void PictureLayerTiling::UpdateTilesToCurrentPile( ...@@ -192,6 +245,7 @@ void PictureLayerTiling::UpdateTilesToCurrentPile(
PicturePileImpl* pile = client_->GetPile(); PicturePileImpl* pile = client_->GetPile();
for (TileMap::const_iterator it = tiles_.begin(); it != tiles_.end(); ++it) for (TileMap::const_iterator it = tiles_.begin(); it != tiles_.end(); ++it)
it->second->set_picture_pile(pile); it->second->set_picture_pile(pile);
VerifyLiveTilesRect();
} }
void PictureLayerTiling::RemoveTilesInRegion(const Region& layer_region) { void PictureLayerTiling::RemoveTilesInRegion(const Region& layer_region) {
...@@ -208,18 +262,24 @@ void PictureLayerTiling::DoInvalidate(const Region& layer_region, ...@@ -208,18 +262,24 @@ void PictureLayerTiling::DoInvalidate(const Region& layer_region,
bool recreate_invalidated_tiles) { bool recreate_invalidated_tiles) {
std::vector<TileMapKey> new_tile_keys; std::vector<TileMapKey> new_tile_keys;
gfx::Rect expanded_live_tiles_rect = gfx::Rect expanded_live_tiles_rect =
tiling_data_.ExpandRectIgnoringBordersToTileBoundsWithBorders( tiling_data_.ExpandRectIgnoringBordersToTileBounds(live_tiles_rect_);
live_tiles_rect_);
for (Region::Iterator iter(layer_region); iter.has_rect(); iter.next()) { for (Region::Iterator iter(layer_region); iter.has_rect(); iter.next()) {
gfx::Rect layer_rect = iter.rect(); gfx::Rect layer_rect = iter.rect();
gfx::Rect content_rect = gfx::Rect content_rect =
gfx::ScaleToEnclosingRect(layer_rect, contents_scale_); gfx::ScaleToEnclosingRect(layer_rect, contents_scale_);
// Consider tiles inside the live tiles rect even if only their border
// pixels intersect the invalidation. But don't consider tiles outside
// the live tiles rect with the same conditions, as they won't exist.
int border_pixels = tiling_data_.border_texels();
content_rect.Inset(-border_pixels, -border_pixels);
// Avoid needless work by not bothering to invalidate where there aren't // Avoid needless work by not bothering to invalidate where there aren't
// tiles. // tiles.
content_rect.Intersect(expanded_live_tiles_rect); content_rect.Intersect(expanded_live_tiles_rect);
if (content_rect.IsEmpty()) if (content_rect.IsEmpty())
continue; continue;
bool include_borders = true; // Since the content_rect includes border pixels already, don't include
// borders when iterating to avoid double counting them.
bool include_borders = false;
for (TilingData::Iterator iter( for (TilingData::Iterator iter(
&tiling_data_, content_rect, include_borders); &tiling_data_, content_rect, include_borders);
iter; iter;
...@@ -522,7 +582,7 @@ void PictureLayerTiling::UpdateTilePriorities( ...@@ -522,7 +582,7 @@ void PictureLayerTiling::UpdateTilePriorities(
float content_to_screen_scale = ideal_contents_scale / contents_scale_; float content_to_screen_scale = ideal_contents_scale / contents_scale_;
// Assign now priority to all visible tiles. // Assign now priority to all visible tiles.
bool include_borders = true; bool include_borders = false;
has_visible_rect_tiles_ = false; has_visible_rect_tiles_ = false;
for (TilingData::Iterator iter( for (TilingData::Iterator iter(
&tiling_data_, visible_rect_in_content_space, include_borders); &tiling_data_, visible_rect_in_content_space, include_borders);
...@@ -656,6 +716,30 @@ void PictureLayerTiling::SetLiveTilesRect( ...@@ -656,6 +716,30 @@ void PictureLayerTiling::SetLiveTilesRect(
} }
live_tiles_rect_ = new_live_tiles_rect; live_tiles_rect_ = new_live_tiles_rect;
VerifyLiveTilesRect();
}
void PictureLayerTiling::VerifyLiveTilesRect() {
#if DCHECK_IS_ON
for (TileMap::iterator it = tiles_.begin(); it != tiles_.end(); ++it) {
if (!it->second.get())
continue;
DCHECK(it->first.first < tiling_data_.num_tiles_x())
<< this << " " << it->first.first << "," << it->first.second
<< " num_tiles_x " << tiling_data_.num_tiles_x() << " live_tiles_rect "
<< live_tiles_rect_.ToString();
DCHECK(it->first.second < tiling_data_.num_tiles_y())
<< this << " " << it->first.first << "," << it->first.second
<< " num_tiles_y " << tiling_data_.num_tiles_y() << " live_tiles_rect "
<< live_tiles_rect_.ToString();
DCHECK(tiling_data_.TileBounds(it->first.first, it->first.second)
.Intersects(live_tiles_rect_))
<< this << " " << it->first.first << "," << it->first.second
<< " tile bounds "
<< tiling_data_.TileBounds(it->first.first, it->first.second).ToString()
<< " live_tiles_rect " << live_tiles_rect_.ToString();
}
#endif
} }
void PictureLayerTiling::DidBecomeRecycled() { void PictureLayerTiling::DidBecomeRecycled() {
...@@ -956,7 +1040,7 @@ PictureLayerTiling::TilingRasterTileIterator::TilingRasterTileIterator( ...@@ -956,7 +1040,7 @@ PictureLayerTiling::TilingRasterTileIterator::TilingRasterTileIterator(
visible_iterator_ = TilingData::Iterator(&tiling_->tiling_data_, visible_iterator_ = TilingData::Iterator(&tiling_->tiling_data_,
tiling_->current_visible_rect_, tiling_->current_visible_rect_,
true /* include_borders */); false /* include_borders */);
if (!visible_iterator_) { if (!visible_iterator_) {
AdvancePhase(); AdvancePhase();
return; return;
......
...@@ -298,6 +298,7 @@ class CC_EXPORT PictureLayerTiling { ...@@ -298,6 +298,7 @@ class CC_EXPORT PictureLayerTiling {
const gfx::Size& layer_bounds, const gfx::Size& layer_bounds,
PictureLayerTilingClient* client); PictureLayerTilingClient* client);
void SetLiveTilesRect(const gfx::Rect& live_tiles_rect); void SetLiveTilesRect(const gfx::Rect& live_tiles_rect);
void VerifyLiveTilesRect();
Tile* CreateTile(int i, int j, const PictureLayerTiling* twin_tiling); Tile* CreateTile(int i, int j, const PictureLayerTiling* twin_tiling);
// Returns true if the Tile existed and was removed from the tiling. // Returns true if the Tile existed and was removed from the tiling.
bool RemoveTileAt(int i, int j, PictureLayerTiling* recycled_twin); bool RemoveTileAt(int i, int j, PictureLayerTiling* recycled_twin);
......
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