// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "cc/paint/discardable_image_map.h"

#include <stddef.h>

#include <memory>

#include "base/memory/ref_counted.h"
#include "base/test/gtest_util.h"
#include "base/values.h"
#include "cc/base/region.h"
#include "cc/paint/paint_flags.h"
#include "cc/paint/paint_op_buffer.h"
#include "cc/paint/paint_recorder.h"
#include "cc/test/fake_content_layer_client.h"
#include "cc/test/fake_recording_source.h"
#include "cc/test/skia_common.h"
#include "cc/test/test_paint_worklet_input.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "third_party/skia/include/core/SkCanvas.h"
#include "third_party/skia/include/core/SkGraphics.h"
#include "third_party/skia/include/core/SkImageGenerator.h"
#include "third_party/skia/include/core/SkRefCnt.h"
#include "ui/gfx/color_space.h"
#include "ui/gfx/geometry/rect.h"
#include "ui/gfx/skia_util.h"

namespace cc {
namespace {

struct PositionScaleDrawImage {
  PositionScaleDrawImage(const PaintImage& image,
                         const gfx::Rect& image_rect,
                         const SkSize& scale)
      : image(image), image_rect(image_rect), scale(scale) {}
  PaintImage image;
  gfx::Rect image_rect;
  SkSize scale;
};

sk_sp<PaintOpBuffer> CreateRecording(const PaintImage& discardable_image,
                                     const gfx::Rect& visible_rect) {
  auto buffer = sk_make_sp<PaintOpBuffer>();
  buffer->push<DrawImageOp>(discardable_image, 0.f, 0.f, nullptr);
  return buffer;
}

}  // namespace

class DiscardableImageMapTest : public testing::Test {
 public:
  std::vector<PositionScaleDrawImage> GetDiscardableImagesInRect(
      const DiscardableImageMap& image_map,
      const gfx::Rect& rect) {
    std::vector<const DrawImage*> draw_image_ptrs;
    image_map.GetDiscardableImagesInRect(rect, &draw_image_ptrs);
    std::vector<DrawImage> draw_images;
    for (const auto* image : draw_image_ptrs)
      draw_images.push_back(
          DrawImage(*image, 1.f, PaintImage::kDefaultFrameIndex));

    std::vector<PositionScaleDrawImage> position_draw_images;
    std::vector<DrawImage> results;
    image_map.images_rtree_.Search(rect, &results);
    for (DrawImage& image : results) {
      auto image_id = image.paint_image().stable_id();
      position_draw_images.push_back(PositionScaleDrawImage(
          image.paint_image(),
          ImageRectsToRegion(image_map.GetRectsForImage(image_id)).bounds(),
          image.scale()));
    }

    EXPECT_EQ(draw_images.size(), position_draw_images.size());
    for (size_t i = 0; i < draw_images.size(); ++i) {
      EXPECT_TRUE(draw_images[i].paint_image() ==
                  position_draw_images[i].image);
    }
    return position_draw_images;
  }

  // Note that the image rtree outsets the images by 1, see the comment in
  // DiscardableImagesMetadataCanvas::AddImage.
  std::vector<gfx::Rect> InsetImageRects(
      const std::vector<PositionScaleDrawImage>& images) {
    std::vector<gfx::Rect> result;
    for (auto& image : images) {
      result.push_back(image.image_rect);
      result.back().Inset(1, 1, 1, 1);
    }
    return result;
  }
};

TEST_F(DiscardableImageMapTest, GetDiscardableImagesInRectTest) {
  gfx::Rect visible_rect(2048, 2048);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  // Discardable pixel refs are found in the following grids:
  // |---|---|---|---|
  // |   | x |   | x |
  // |---|---|---|---|
  // | x |   | x |   |
  // |---|---|---|---|
  // |   | x |   | x |
  // |---|---|---|---|
  // | x |   | x |   |
  // |---|---|---|---|
  PaintImage discardable_image[4][4];
  for (int y = 0; y < 4; ++y) {
    for (int x = 0; x < 4; ++x) {
      if ((x + y) & 1) {
        discardable_image[y][x] =
            CreateDiscardablePaintImage(gfx::Size(500, 500));
        PaintFlags flags;
        content_layer_client.add_draw_image(
            discardable_image[y][x], gfx::Point(x * 512 + 6, y * 512 + 6),
            flags);
      }
    }
  }

  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();

  for (int y = 0; y < 4; ++y) {
    for (int x = 0; x < 4; ++x) {
      std::vector<PositionScaleDrawImage> images = GetDiscardableImagesInRect(
          image_map, gfx::Rect(x * 512, y * 512, 500, 500));
      std::vector<gfx::Rect> inset_rects = InsetImageRects(images);
      if ((x + y) & 1) {
        EXPECT_EQ(1u, images.size()) << x << " " << y;
        EXPECT_TRUE(images[0].image == discardable_image[y][x])
            << x << " " << y;
        EXPECT_EQ(gfx::Rect(x * 512 + 6, y * 512 + 6, 500, 500),
                  inset_rects[0]);
      } else {
        EXPECT_EQ(0u, images.size()) << x << " " << y;
      }
    }
  }

  // Capture 4 pixel refs.
  std::vector<PositionScaleDrawImage> images =
      GetDiscardableImagesInRect(image_map, gfx::Rect(512, 512, 2048, 2048));
  std::vector<gfx::Rect> inset_rects = InsetImageRects(images);
  EXPECT_EQ(4u, images.size());

  EXPECT_TRUE(images[0].image == discardable_image[1][2]);
  EXPECT_EQ(gfx::Rect(2 * 512 + 6, 512 + 6, 500, 500), inset_rects[0]);

  EXPECT_TRUE(images[1].image == discardable_image[2][1]);
  EXPECT_EQ(gfx::Rect(512 + 6, 2 * 512 + 6, 500, 500), inset_rects[1]);

  EXPECT_TRUE(images[2].image == discardable_image[2][3]);
  EXPECT_EQ(gfx::Rect(3 * 512 + 6, 2 * 512 + 6, 500, 500), inset_rects[2]);

  EXPECT_TRUE(images[3].image == discardable_image[3][2]);
  EXPECT_EQ(gfx::Rect(2 * 512 + 6, 3 * 512 + 6, 500, 500), inset_rects[3]);
}

TEST_F(DiscardableImageMapTest, GetDiscardableImagesInRectNonZeroLayer) {
  gfx::Rect visible_rect(1024, 0, 2048, 2048);
  // Make sure visible rect fits into the layer size.
  gfx::Size layer_size(visible_rect.right(), visible_rect.bottom());
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(layer_size);

  // Discardable pixel refs are found in the following grids:
  // |---|---|---|---|
  // |   | x |   | x |
  // |---|---|---|---|
  // | x |   | x |   |
  // |---|---|---|---|
  // |   | x |   | x |
  // |---|---|---|---|
  // | x |   | x |   |
  // |---|---|---|---|
  PaintImage discardable_image[4][4];
  for (int y = 0; y < 4; ++y) {
    for (int x = 0; x < 4; ++x) {
      if ((x + y) & 1) {
        discardable_image[y][x] =
            CreateDiscardablePaintImage(gfx::Size(500, 500));
        PaintFlags flags;
        content_layer_client.add_draw_image(
            discardable_image[y][x],
            gfx::Point(1024 + x * 512 + 6, y * 512 + 6), flags);
      }
    }
  }

  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();

  for (int y = 0; y < 4; ++y) {
    for (int x = 0; x < 4; ++x) {
      std::vector<PositionScaleDrawImage> images = GetDiscardableImagesInRect(
          image_map, gfx::Rect(1024 + x * 512, y * 512, 500, 500));
      std::vector<gfx::Rect> inset_rects = InsetImageRects(images);
      if ((x + y) & 1) {
        EXPECT_EQ(1u, images.size()) << x << " " << y;
        EXPECT_TRUE(images[0].image == discardable_image[y][x])
            << x << " " << y;
        EXPECT_EQ(gfx::Rect(1024 + x * 512 + 6, y * 512 + 6, 500, 500),
                  inset_rects[0]);
      } else {
        EXPECT_EQ(0u, images.size()) << x << " " << y;
      }
    }
  }
  // Capture 4 pixel refs.
  {
    std::vector<PositionScaleDrawImage> images = GetDiscardableImagesInRect(
        image_map, gfx::Rect(1024 + 512, 512, 2048, 2048));
    std::vector<gfx::Rect> inset_rects = InsetImageRects(images);
    EXPECT_EQ(4u, images.size());

    EXPECT_TRUE(images[0].image == discardable_image[1][2]);
    EXPECT_EQ(gfx::Rect(1024 + 2 * 512 + 6, 512 + 6, 500, 500), inset_rects[0]);

    EXPECT_TRUE(images[1].image == discardable_image[2][1]);
    EXPECT_EQ(gfx::Rect(1024 + 512 + 6, 2 * 512 + 6, 500, 500), inset_rects[1]);

    EXPECT_TRUE(images[2].image == discardable_image[2][3]);
    EXPECT_EQ(gfx::Rect(1024 + 3 * 512 + 6, 2 * 512 + 6, 500, 500),
              inset_rects[2]);

    EXPECT_TRUE(images[3].image == discardable_image[3][2]);
    EXPECT_EQ(gfx::Rect(1024 + 2 * 512 + 6, 3 * 512 + 6, 500, 500),
              inset_rects[3]);
  }

  // Non intersecting rects
  {
    std::vector<PositionScaleDrawImage> images =
        GetDiscardableImagesInRect(image_map, gfx::Rect(0, 0, 1000, 1000));
    EXPECT_EQ(0u, images.size());
  }
  {
    std::vector<PositionScaleDrawImage> images =
        GetDiscardableImagesInRect(image_map, gfx::Rect(3500, 0, 1000, 1000));
    EXPECT_EQ(0u, images.size());
  }
  {
    std::vector<PositionScaleDrawImage> images =
        GetDiscardableImagesInRect(image_map, gfx::Rect(0, 1100, 1000, 1000));
    EXPECT_EQ(0u, images.size());
  }
  {
    std::vector<PositionScaleDrawImage> images = GetDiscardableImagesInRect(
        image_map, gfx::Rect(3500, 1100, 1000, 1000));
    EXPECT_EQ(0u, images.size());
  }

  // Image not present in the list.
  {
    PaintImage image = CreateDiscardablePaintImage(gfx::Size(500, 500));
    EXPECT_EQ(image_map.GetRectsForImage(image.stable_id())->size(), 0u);
  }
}

TEST_F(DiscardableImageMapTest, GetDiscardableImagesInRectOnePixelQuery) {
  gfx::Rect visible_rect(2048, 2048);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  // Discardable pixel refs are found in the following grids:
  // |---|---|---|---|
  // |   | x |   | x |
  // |---|---|---|---|
  // | x |   | x |   |
  // |---|---|---|---|
  // |   | x |   | x |
  // |---|---|---|---|
  // | x |   | x |   |
  // |---|---|---|---|
  PaintImage discardable_image[4][4];
  for (int y = 0; y < 4; ++y) {
    for (int x = 0; x < 4; ++x) {
      if ((x + y) & 1) {
        discardable_image[y][x] =
            CreateDiscardablePaintImage(gfx::Size(500, 500));
        PaintFlags flags;
        content_layer_client.add_draw_image(
            discardable_image[y][x], gfx::Point(x * 512 + 6, y * 512 + 6),
            flags);
      }
    }
  }

  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();

  for (int y = 0; y < 4; ++y) {
    for (int x = 0; x < 4; ++x) {
      std::vector<PositionScaleDrawImage> images = GetDiscardableImagesInRect(
          image_map, gfx::Rect(x * 512 + 256, y * 512 + 256, 1, 1));
      std::vector<gfx::Rect> inset_rects = InsetImageRects(images);
      if ((x + y) & 1) {
        EXPECT_EQ(1u, images.size()) << x << " " << y;
        EXPECT_TRUE(images[0].image == discardable_image[y][x])
            << x << " " << y;
        EXPECT_EQ(gfx::Rect(x * 512 + 6, y * 512 + 6, 500, 500),
                  inset_rects[0]);
      } else {
        EXPECT_EQ(0u, images.size()) << x << " " << y;
      }
    }
  }
}

TEST_F(DiscardableImageMapTest, GetDiscardableImagesInRectMassiveImage) {
  gfx::Rect visible_rect(2048, 2048);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  PaintImage discardable_image =
      CreateDiscardablePaintImage(gfx::Size(1 << 25, 1 << 25), nullptr,
                                  false /* allocate_encoded_memory */);
  PaintFlags flags;
  content_layer_client.add_draw_image(discardable_image, gfx::Point(0, 0),
                                      flags);

  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();

  std::vector<PositionScaleDrawImage> images =
      GetDiscardableImagesInRect(image_map, gfx::Rect(0, 0, 1, 1));
  std::vector<gfx::Rect> inset_rects = InsetImageRects(images);
  EXPECT_EQ(1u, images.size());
  EXPECT_TRUE(images[0].image == discardable_image);
  EXPECT_EQ(gfx::Rect(0, 0, 2048, 2048), inset_rects[0]);
}

TEST_F(DiscardableImageMapTest, PaintDestroyedWhileImageIsDrawn) {
  gfx::Rect visible_rect(2048, 2048);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  PaintImage discardable_image = CreateDiscardablePaintImage(gfx::Size(10, 10));
  sk_sp<PaintRecord> record = CreateRecording(discardable_image, visible_rect);

  scoped_refptr<DisplayItemList> display_list = new DisplayItemList;
  PaintFlags paint;
  display_list->StartPaint();
  SkRect visible_sk_rect(gfx::RectToSkRect(visible_rect));
  display_list->push<SaveLayerOp>(&visible_sk_rect, &paint);
  display_list->push<DrawRecordOp>(std::move(record));
  display_list->push<RestoreOp>();
  display_list->EndPaintOfUnpaired(visible_rect);
  display_list->Finalize();

  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();
  std::vector<PositionScaleDrawImage> images =
      GetDiscardableImagesInRect(image_map, gfx::Rect(0, 0, 1, 1));
  EXPECT_EQ(1u, images.size());
  EXPECT_TRUE(images[0].image == discardable_image);
}

TEST_F(DiscardableImageMapTest, NullPaintOnSaveLayer) {
  gfx::Rect visible_rect(2048, 2048);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  PaintImage discardable_image = CreateDiscardablePaintImage(gfx::Size(10, 10));
  sk_sp<PaintRecord> record = CreateRecording(discardable_image, visible_rect);

  scoped_refptr<DisplayItemList> display_list = new DisplayItemList;
  display_list->StartPaint();
  SkRect visible_sk_rect(gfx::RectToSkRect(visible_rect));
  display_list->push<SaveLayerOp>(&visible_sk_rect, nullptr);
  display_list->push<DrawRecordOp>(std::move(record));
  display_list->push<RestoreOp>();
  display_list->EndPaintOfUnpaired(visible_rect);
  display_list->Finalize();

  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();
  std::vector<PositionScaleDrawImage> images =
      GetDiscardableImagesInRect(image_map, gfx::Rect(0, 0, 1, 1));
  EXPECT_EQ(1u, images.size());
  EXPECT_TRUE(images[0].image == discardable_image);
}

TEST_F(DiscardableImageMapTest, GetDiscardableImagesInRectMaxImage) {
  gfx::Rect visible_rect(2048, 2048);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  int dimension = std::numeric_limits<int>::max();
  sk_sp<SkColorSpace> no_color_space;
  PaintImage discardable_image = CreateDiscardablePaintImage(
      gfx::Size(dimension, dimension), no_color_space,
      false /* allocate_encoded_memory */);
  PaintFlags flags;
  content_layer_client.add_draw_image(discardable_image, gfx::Point(42, 42),
                                      flags);

  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();

  std::vector<PositionScaleDrawImage> images =
      GetDiscardableImagesInRect(image_map, gfx::Rect(42, 42, 1, 1));
  std::vector<gfx::Rect> inset_rects = InsetImageRects(images);
  EXPECT_EQ(1u, images.size());
  EXPECT_TRUE(images[0].image == discardable_image);
  EXPECT_EQ(gfx::Rect(42, 42, 2006, 2006), inset_rects[0]);
}

TEST_F(DiscardableImageMapTest, GetDiscardableImagesInRectMaxImageMaxLayer) {
  // At large values of integer x, x != static_cast<int>(static_cast<float>(x)).
  // So, make sure the dimension can be converted back and forth for the
  // purposes of the unittest. Also, at near max int values, Skia seems to skip
  // some draw calls, so we subtract 64 since we only care about "really large"
  // values, not necessarily max int values.
  int dimension = static_cast<int>(
      static_cast<float>(std::numeric_limits<int>::max() - 64));
  gfx::Rect visible_rect(dimension, dimension);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  sk_sp<SkColorSpace> no_color_space;
  PaintImage discardable_image1 = CreateDiscardablePaintImage(
      gfx::Size(dimension, dimension), no_color_space,
      false /* allocate_encoded_memory */);
  PaintImage discardable_image2 = CreateDiscardablePaintImage(
      gfx::Size(dimension, dimension), no_color_space,
      false /* allocate_encoded_memory */);
  PaintImage discardable_image3 = CreateDiscardablePaintImage(
      gfx::Size(dimension, dimension), no_color_space,
      false /* allocate_encoded_memory */);

  PaintFlags flags;
  content_layer_client.add_draw_image(discardable_image1, gfx::Point(0, 0),
                                      flags);
  content_layer_client.add_draw_image(discardable_image2, gfx::Point(10000, 0),
                                      flags);
  content_layer_client.add_draw_image(discardable_image3,
                                      gfx::Point(-10000, 500), flags);

  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();

  std::vector<PositionScaleDrawImage> images =
      GetDiscardableImagesInRect(image_map, gfx::Rect(0, 0, 1, 1));
  std::vector<gfx::Rect> inset_rects = InsetImageRects(images);
  EXPECT_EQ(1u, images.size());
  EXPECT_EQ(gfx::Rect(0, 0, dimension, dimension), inset_rects[0]);

  images = GetDiscardableImagesInRect(image_map, gfx::Rect(10000, 0, 1, 1));
  inset_rects = InsetImageRects(images);
  EXPECT_EQ(2u, images.size());
  EXPECT_EQ(gfx::Rect(10000, 0, dimension - 10000, dimension), inset_rects[1]);
  EXPECT_EQ(gfx::Rect(0, 0, dimension, dimension), inset_rects[0]);

  // Since we adjust negative offsets before using ToEnclosingRect, the expected
  // width will be converted to float, which means that we lose some precision.
  // The expected value is whatever the value is converted to float and then
  // back to int.
  int expected10k = static_cast<int>(static_cast<float>(dimension - 10000));
  images = GetDiscardableImagesInRect(image_map, gfx::Rect(0, 500, 1, 1));
  inset_rects = InsetImageRects(images);
  EXPECT_EQ(2u, images.size());
  EXPECT_EQ(gfx::Rect(0, 500, expected10k, dimension - 500), inset_rects[1]);
  EXPECT_EQ(gfx::Rect(0, 0, dimension, dimension), inset_rects[0]);
}

TEST_F(DiscardableImageMapTest, GetDiscardableImagesRectInBounds) {
  gfx::Rect visible_rect(1000, 1000);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  PaintImage discardable_image1 =
      CreateDiscardablePaintImage(gfx::Size(100, 100));
  PaintImage discardable_image2 =
      CreateDiscardablePaintImage(gfx::Size(100, 100));
  PaintImage long_discardable_image =
      CreateDiscardablePaintImage(gfx::Size(10000, 100));

  PaintFlags flags;
  content_layer_client.add_draw_image(discardable_image1, gfx::Point(-10, -11),
                                      flags);
  content_layer_client.add_draw_image(discardable_image2, gfx::Point(950, 951),
                                      flags);
  content_layer_client.add_draw_image(long_discardable_image,
                                      gfx::Point(-100, 500), flags);

  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();

  std::vector<PositionScaleDrawImage> images =
      GetDiscardableImagesInRect(image_map, gfx::Rect(0, 0, 1, 1));
  std::vector<gfx::Rect> inset_rects = InsetImageRects(images);

  ASSERT_EQ(1u, images.size());
  EXPECT_EQ(gfx::Rect(0, 0, 90, 89), inset_rects[0]);

  images = GetDiscardableImagesInRect(image_map, gfx::Rect(999, 999, 1, 1));
  inset_rects = InsetImageRects(images);
  ASSERT_EQ(1u, images.size());
  EXPECT_EQ(gfx::Rect(950, 951, 50, 49), inset_rects[0]);

  images = GetDiscardableImagesInRect(image_map, gfx::Rect(0, 500, 1, 1));
  inset_rects = InsetImageRects(images);
  ASSERT_EQ(1u, images.size());
  EXPECT_EQ(gfx::Rect(0, 500, 1000, 100), inset_rects[0]);
}

TEST_F(DiscardableImageMapTest, GetDiscardableImagesInShader) {
  gfx::Rect visible_rect(2048, 2048);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  // Discardable pixel refs are found in the following grids:
  // |---|---|---|---|
  // |   | x |   | x |
  // |---|---|---|---|
  // | x |   | x |   |
  // |---|---|---|---|
  // |   | x |   | x |
  // |---|---|---|---|
  // | x |   | x |   |
  // |---|---|---|---|
  PaintImage discardable_image[4][4];

  // Skia doesn't allow shader instantiation with non-invertible local
  // transforms, so we can't let the scale drop all the way to 0.
  static constexpr float kMinScale = 0.1f;

  for (int y = 0; y < 4; ++y) {
    for (int x = 0; x < 4; ++x) {
      if ((x + y) & 1) {
        discardable_image[y][x] =
            PaintImageBuilder::WithDefault()
                .set_id(y * 4 + x)
                .set_paint_image_generator(
                    CreatePaintImageGenerator(gfx::Size(500, 500)))
                .TakePaintImage();
        SkMatrix scale = SkMatrix::MakeScale(std::max(x * 0.5f, kMinScale),
                                             std::max(y * 0.5f, kMinScale));
        PaintFlags flags;
        flags.setShader(PaintShader::MakeImage(
            discardable_image[y][x], SkShader::kClamp_TileMode,
            SkShader::kClamp_TileMode, &scale));
        content_layer_client.add_draw_rect(
            gfx::Rect(x * 512 + 6, y * 512 + 6, 500, 500), flags);
      }
    }
  }

  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();

  for (int y = 0; y < 4; ++y) {
    for (int x = 0; x < 4; ++x) {
      std::vector<const DrawImage*> draw_images;
      image_map.GetDiscardableImagesInRect(
          gfx::Rect(x * 512, y * 512, 500, 500), &draw_images);
      if ((x + y) & 1) {
        EXPECT_EQ(1u, draw_images.size()) << x << " " << y;
        EXPECT_TRUE(draw_images[0]->paint_image() == discardable_image[y][x])
            << x << " " << y;
        EXPECT_EQ(std::max(x * 0.5f, kMinScale),
                  draw_images[0]->scale().fWidth);
        EXPECT_EQ(std::max(y * 0.5f, kMinScale),
                  draw_images[0]->scale().fHeight);
      } else {
        EXPECT_EQ(0u, draw_images.size()) << x << " " << y;
      }
    }
  }

  // Capture 4 pixel refs.
  std::vector<const DrawImage*> draw_images;
  image_map.GetDiscardableImagesInRect(gfx::Rect(512, 512, 2048, 2048),
                                       &draw_images);
  EXPECT_EQ(4u, draw_images.size());
  EXPECT_TRUE(draw_images[0]->paint_image() == discardable_image[1][2]);
  EXPECT_TRUE(draw_images[1]->paint_image() == discardable_image[2][1]);
  EXPECT_TRUE(draw_images[2]->paint_image() == discardable_image[2][3]);
  EXPECT_TRUE(draw_images[3]->paint_image() == discardable_image[3][2]);
}

TEST_F(DiscardableImageMapTest, ClipsImageRects) {
  gfx::Rect visible_rect(500, 500);

  PaintImage discardable_image =
      CreateDiscardablePaintImage(gfx::Size(500, 500));
  sk_sp<PaintRecord> record = CreateRecording(discardable_image, visible_rect);

  scoped_refptr<DisplayItemList> display_list = new DisplayItemList;

  display_list->StartPaint();
  display_list->push<ClipRectOp>(gfx::RectToSkRect(gfx::Rect(250, 250)),
                                 SkClipOp::kIntersect, false);
  display_list->push<DrawRecordOp>(std::move(record));
  display_list->EndPaintOfUnpaired(gfx::Rect(250, 250));

  display_list->Finalize();

  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();
  std::vector<PositionScaleDrawImage> images =
      GetDiscardableImagesInRect(image_map, visible_rect);
  std::vector<gfx::Rect> inset_rects = InsetImageRects(images);
  EXPECT_EQ(1u, images.size());
  EXPECT_TRUE(images[0].image == discardable_image);
  EXPECT_EQ(gfx::Rect(250, 250), inset_rects[0]);
}

TEST_F(DiscardableImageMapTest, GathersDiscardableImagesFromNestedOps) {
  // This |discardable_image| is in a PaintOpBuffer that gets added to
  // the root buffer.
  auto internal_record = sk_make_sp<PaintOpBuffer>();
  PaintImage discardable_image =
      CreateDiscardablePaintImage(gfx::Size(100, 100));
  internal_record->push<DrawImageOp>(discardable_image, 0.f, 0.f, nullptr);

  // This |discardable_image2| is in a DisplayItemList that gets added
  // to the root buffer.
  PaintImage discardable_image2 =
      CreateDiscardablePaintImage(gfx::Size(100, 100));

  scoped_refptr<DisplayItemList> display_list =
      new DisplayItemList(DisplayItemList::kToBeReleasedAsPaintOpBuffer);
  display_list->StartPaint();
  display_list->push<DrawImageOp>(discardable_image2, 100.f, 100.f, nullptr);
  display_list->EndPaintOfUnpaired(gfx::Rect(100, 100, 100, 100));
  display_list->Finalize();

  sk_sp<PaintRecord> record2 = display_list->ReleaseAsRecord();

  PaintOpBuffer root_buffer;
  root_buffer.push<DrawRecordOp>(internal_record);
  root_buffer.push<DrawRecordOp>(record2);
  DiscardableImageMap image_map;
  image_map.Generate(&root_buffer, gfx::Rect(200, 200));

  std::vector<const DrawImage*> images;
  image_map.GetDiscardableImagesInRect(gfx::Rect(0, 0, 5, 95), &images);
  EXPECT_EQ(1u, images.size());
  EXPECT_TRUE(discardable_image == images[0]->paint_image());

  images.clear();
  image_map.GetDiscardableImagesInRect(gfx::Rect(105, 105, 5, 95), &images);
  EXPECT_EQ(1u, images.size());
  EXPECT_TRUE(discardable_image2 == images[0]->paint_image());
}

TEST_F(DiscardableImageMapTest, GathersAnimatedImages) {
  gfx::Rect visible_rect(1000, 1000);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  std::vector<FrameMetadata> frames = {
      FrameMetadata(true, base::TimeDelta::FromMilliseconds(2)),
      FrameMetadata(true, base::TimeDelta::FromMilliseconds(3))};

  gfx::Size image_size(100, 100);
  PaintImage static_image = CreateDiscardablePaintImage(image_size);
  PaintImage animated_loop_none =
      CreateAnimatedImage(image_size, frames, kAnimationNone);
  PaintImage animation_loop_infinite =
      CreateAnimatedImage(image_size, frames, 1u);

  PaintFlags flags;
  content_layer_client.add_draw_image(static_image, gfx::Point(0, 0), flags);
  content_layer_client.add_draw_image(animated_loop_none, gfx::Point(100, 100),
                                      flags);
  content_layer_client.add_draw_image(animation_loop_infinite,
                                      gfx::Point(200, 200), flags);

  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const auto& animated_images_metadata =
      display_list->discardable_image_map().animated_images_metadata();

  ASSERT_EQ(animated_images_metadata.size(), 1u);
  EXPECT_EQ(animated_images_metadata[0].paint_image_id,
            animation_loop_infinite.stable_id());
  EXPECT_EQ(animated_images_metadata[0].completion_state,
            animation_loop_infinite.completion_state());
  EXPECT_EQ(animated_images_metadata[0].frames,
            animation_loop_infinite.GetFrameMetadata());
  EXPECT_EQ(animated_images_metadata[0].repetition_count,
            animation_loop_infinite.repetition_count());

  std::vector<const DrawImage*> images;
  display_list->discardable_image_map().GetDiscardableImagesInRect(visible_rect,
                                                                   &images);
  ASSERT_EQ(images.size(), 3u);
  EXPECT_EQ(images[0]->paint_image(), static_image);
  EXPECT_DCHECK_DEATH(images[0]->frame_index());
  EXPECT_EQ(images[1]->paint_image(), animated_loop_none);
  EXPECT_DCHECK_DEATH(images[1]->frame_index());
  EXPECT_EQ(images[2]->paint_image(), animation_loop_infinite);
  EXPECT_DCHECK_DEATH(images[2]->frame_index());
}

TEST_F(DiscardableImageMapTest, CapturesImagesInPaintRecordShaders) {
  // Create the record to use in the shader.
  auto shader_record = sk_make_sp<PaintOpBuffer>();
  shader_record->push<ScaleOp>(2.0f, 2.0f);

  PaintImage static_image = CreateDiscardablePaintImage(gfx::Size(100, 100));
  shader_record->push<DrawImageOp>(static_image, 0.f, 0.f, nullptr);

  std::vector<FrameMetadata> frames = {
      FrameMetadata(true, base::TimeDelta::FromMilliseconds(1)),
      FrameMetadata(true, base::TimeDelta::FromMilliseconds(1))};
  PaintImage animated_image = CreateAnimatedImage(gfx::Size(100, 100), frames);
  shader_record->push<DrawImageOp>(animated_image, 0.f, 0.f, nullptr);

  gfx::Rect visible_rect(500, 500);
  scoped_refptr<DisplayItemList> display_list = new DisplayItemList();
  display_list->StartPaint();
  display_list->push<ScaleOp>(2.0f, 2.0f);
  PaintFlags flags;
  SkRect tile = SkRect::MakeWH(100, 100);
  flags.setShader(PaintShader::MakePaintRecord(
      shader_record, tile, SkShader::TileMode::kClamp_TileMode,
      SkShader::TileMode::kClamp_TileMode, nullptr));
  display_list->push<DrawRectOp>(SkRect::MakeWH(200, 200), flags);
  display_list->EndPaintOfUnpaired(visible_rect);
  display_list->Finalize();

  EXPECT_EQ(flags.getShader()->image_analysis_state(),
            ImageAnalysisState::kNoAnalysis);
  display_list->GenerateDiscardableImagesMetadata();
  EXPECT_EQ(flags.getShader()->image_analysis_state(),
            ImageAnalysisState::kAnimatedImages);
  const auto& image_map = display_list->discardable_image_map();

  // The image rect is set to the rect for the DrawRectOp, and only animated
  // images in a shader are tracked.
  std::vector<PositionScaleDrawImage> draw_images =
      GetDiscardableImagesInRect(image_map, visible_rect);
  std::vector<gfx::Rect> inset_rects = InsetImageRects(draw_images);
  ASSERT_EQ(draw_images.size(), 1u);
  EXPECT_EQ(draw_images[0].image, animated_image);
  // The position of the image is the position of the DrawRectOp that uses the
  // shader.
  EXPECT_EQ(gfx::Rect(400, 400), inset_rects[0]);
  // The scale of the image includes the scale at which the shader record is
  // rasterized.
  EXPECT_EQ(SkSize::Make(4.f, 4.f), draw_images[0].scale);
}

TEST_F(DiscardableImageMapTest, CapturesImagesInPaintFilters) {
  // Create the record to use in the filter.
  auto filter_record = sk_make_sp<PaintOpBuffer>();

  PaintImage static_image = CreateDiscardablePaintImage(gfx::Size(100, 100));
  filter_record->push<DrawImageOp>(static_image, 0.f, 0.f, nullptr);

  std::vector<FrameMetadata> frames = {
      FrameMetadata(true, base::TimeDelta::FromMilliseconds(1)),
      FrameMetadata(true, base::TimeDelta::FromMilliseconds(1))};
  PaintImage animated_image = CreateAnimatedImage(gfx::Size(100, 100), frames);
  filter_record->push<DrawImageOp>(animated_image, 0.f, 0.f, nullptr);

  gfx::Rect visible_rect(500, 500);
  scoped_refptr<DisplayItemList> display_list = new DisplayItemList();
  display_list->StartPaint();
  PaintFlags flags;
  flags.setImageFilter(sk_make_sp<RecordPaintFilter>(
      filter_record, SkRect::MakeWH(100.f, 100.f)));
  display_list->push<DrawRectOp>(SkRect::MakeWH(200, 200), flags);
  display_list->EndPaintOfUnpaired(visible_rect);
  display_list->Finalize();

  EXPECT_EQ(flags.getImageFilter()->image_analysis_state(),
            ImageAnalysisState::kNoAnalysis);
  display_list->GenerateDiscardableImagesMetadata();
  EXPECT_EQ(flags.getImageFilter()->image_analysis_state(),
            ImageAnalysisState::kAnimatedImages);
  const auto& image_map = display_list->discardable_image_map();

  // The image rect is set to the rect for the DrawRectOp, and only animated
  // images in a filter are tracked.
  std::vector<PositionScaleDrawImage> draw_images =
      GetDiscardableImagesInRect(image_map, visible_rect);
  std::vector<gfx::Rect> inset_rects = InsetImageRects(draw_images);
  ASSERT_EQ(draw_images.size(), 1u);
  EXPECT_EQ(draw_images[0].image, animated_image);
  // The position of the image is the position of the DrawRectOp that uses the
  // filter.
  EXPECT_EQ(gfx::Rect(200, 200), inset_rects[0]);
  // Images in a filter are decoded at the original size.
  EXPECT_EQ(SkSize::Make(1.f, 1.f), draw_images[0].scale);
}

TEST_F(DiscardableImageMapTest, CapturesImagesInSaveLayers) {
  PaintFlags flags;
  PaintImage image = CreateDiscardablePaintImage(gfx::Size(100, 100));
  flags.setShader(PaintShader::MakeImage(image, SkShader::kClamp_TileMode,
                                         SkShader::kClamp_TileMode, nullptr));

  gfx::Rect visible_rect(500, 500);
  scoped_refptr<DisplayItemList> display_list = new DisplayItemList();
  display_list->StartPaint();
  display_list->push<SaveLayerOp>(nullptr, &flags);
  display_list->push<DrawColorOp>(SK_ColorBLUE, SkBlendMode::kSrc);
  display_list->EndPaintOfUnpaired(visible_rect);
  display_list->Finalize();

  display_list->GenerateDiscardableImagesMetadata();
  const auto& image_map = display_list->discardable_image_map();
  std::vector<PositionScaleDrawImage> draw_images =
      GetDiscardableImagesInRect(image_map, visible_rect);
  std::vector<gfx::Rect> inset_rects = InsetImageRects(draw_images);
  ASSERT_EQ(draw_images.size(), 1u);
  EXPECT_EQ(draw_images[0].image, image);
  EXPECT_EQ(gfx::Rect(500, 500), inset_rects[0]);
  EXPECT_EQ(SkSize::Make(1.f, 1.f), draw_images[0].scale);
}

TEST_F(DiscardableImageMapTest, EmbeddedShaderWithAnimatedImages) {
  // Create the record with animated image to use in the shader.
  SkRect tile = SkRect::MakeWH(100, 100);
  auto shader_record = sk_make_sp<PaintOpBuffer>();
  std::vector<FrameMetadata> frames = {
      FrameMetadata(true, base::TimeDelta::FromMilliseconds(1)),
      FrameMetadata(true, base::TimeDelta::FromMilliseconds(1))};
  PaintImage animated_image = CreateAnimatedImage(gfx::Size(100, 100), frames);
  shader_record->push<DrawImageOp>(animated_image, 0.f, 0.f, nullptr);
  auto shader_with_image = PaintShader::MakePaintRecord(
      shader_record, tile, SkShader::TileMode::kClamp_TileMode,
      SkShader::TileMode::kClamp_TileMode, nullptr);

  // Create a second shader which uses the shader above.
  auto second_shader_record = sk_make_sp<PaintOpBuffer>();
  PaintFlags flags;
  flags.setShader(shader_with_image);
  second_shader_record->push<DrawRectOp>(SkRect::MakeWH(200, 200), flags);
  auto shader_with_shader_with_image = PaintShader::MakePaintRecord(
      second_shader_record, tile, SkShader::TileMode::kClamp_TileMode,
      SkShader::TileMode::kClamp_TileMode, nullptr);

  gfx::Rect visible_rect(500, 500);
  scoped_refptr<DisplayItemList> display_list = new DisplayItemList();
  display_list->StartPaint();
  flags.setShader(shader_with_shader_with_image);
  display_list->push<DrawRectOp>(SkRect::MakeWH(200, 200), flags);
  display_list->EndPaintOfUnpaired(visible_rect);
  display_list->Finalize();
  display_list->GenerateDiscardableImagesMetadata();
  EXPECT_EQ(shader_with_image->image_analysis_state(),
            ImageAnalysisState::kAnimatedImages);
  EXPECT_EQ(shader_with_shader_with_image->image_analysis_state(),
            ImageAnalysisState::kAnimatedImages);
}

TEST_F(DiscardableImageMapTest, BuildPaintWorkletImage) {
  gfx::SizeF size(100, 50);
  scoped_refptr<TestPaintWorkletInput> input =
      base::MakeRefCounted<TestPaintWorkletInput>(size);
  PaintImage paint_image = PaintImageBuilder::WithDefault()
                               .set_id(1)
                               .set_paint_worklet_input(std::move(input))
                               .TakePaintImage();
  EXPECT_TRUE(paint_image.paint_worklet_input());
  EXPECT_EQ(paint_image.width(), size.width());
  EXPECT_EQ(paint_image.height(), size.height());
}

TEST_F(DiscardableImageMapTest, DecodingModeHintsBasic) {
  gfx::Rect visible_rect(100, 100);
  PaintImage unspecified_image =
      PaintImageBuilder::WithCopy(
          CreateDiscardablePaintImage(gfx::Size(10, 10)))
          .set_id(1)
          .set_decoding_mode(PaintImage::DecodingMode::kUnspecified)
          .TakePaintImage();
  PaintImage async_image =
      PaintImageBuilder::WithCopy(
          CreateDiscardablePaintImage(gfx::Size(10, 10)))
          .set_id(2)
          .set_decoding_mode(PaintImage::DecodingMode::kAsync)
          .TakePaintImage();
  PaintImage sync_image =
      PaintImageBuilder::WithCopy(
          CreateDiscardablePaintImage(gfx::Size(10, 10)))
          .set_id(3)
          .set_decoding_mode(PaintImage::DecodingMode::kSync)
          .TakePaintImage();

  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());
  content_layer_client.add_draw_image(unspecified_image, gfx::Point(0, 0),
                                      PaintFlags());
  content_layer_client.add_draw_image(async_image, gfx::Point(10, 10),
                                      PaintFlags());
  content_layer_client.add_draw_image(sync_image, gfx::Point(20, 20),
                                      PaintFlags());
  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  auto decode_hints = display_list->TakeDecodingModeMap();
  ASSERT_EQ(decode_hints.size(), 3u);
  ASSERT_TRUE(decode_hints.find(1) != decode_hints.end());
  ASSERT_TRUE(decode_hints.find(2) != decode_hints.end());
  ASSERT_TRUE(decode_hints.find(3) != decode_hints.end());
  EXPECT_EQ(decode_hints[1], PaintImage::DecodingMode::kUnspecified);
  EXPECT_EQ(decode_hints[2], PaintImage::DecodingMode::kAsync);
  EXPECT_EQ(decode_hints[3], PaintImage::DecodingMode::kSync);

  decode_hints = display_list->TakeDecodingModeMap();
  EXPECT_EQ(decode_hints.size(), 0u);
}

TEST_F(DiscardableImageMapTest, DecodingModeHintsDuplicates) {
  gfx::Rect visible_rect(100, 100);
  PaintImage unspecified_image1 =
      PaintImageBuilder::WithCopy(
          CreateDiscardablePaintImage(gfx::Size(10, 10)))
          .set_id(1)
          .set_decoding_mode(PaintImage::DecodingMode::kUnspecified)
          .TakePaintImage();
  PaintImage async_image1 =
      PaintImageBuilder::WithCopy(
          CreateDiscardablePaintImage(gfx::Size(10, 10)))
          .set_id(1)
          .set_decoding_mode(PaintImage::DecodingMode::kAsync)
          .TakePaintImage();

  PaintImage unspecified_image2 =
      PaintImageBuilder::WithCopy(
          CreateDiscardablePaintImage(gfx::Size(10, 10)))
          .set_id(2)
          .set_decoding_mode(PaintImage::DecodingMode::kUnspecified)
          .TakePaintImage();
  PaintImage sync_image2 =
      PaintImageBuilder::WithCopy(
          CreateDiscardablePaintImage(gfx::Size(10, 10)))
          .set_id(2)
          .set_decoding_mode(PaintImage::DecodingMode::kSync)
          .TakePaintImage();

  PaintImage async_image3 =
      PaintImageBuilder::WithCopy(
          CreateDiscardablePaintImage(gfx::Size(10, 10)))
          .set_id(3)
          .set_decoding_mode(PaintImage::DecodingMode::kAsync)
          .TakePaintImage();
  PaintImage sync_image3 =
      PaintImageBuilder::WithCopy(
          CreateDiscardablePaintImage(gfx::Size(10, 10)))
          .set_id(3)
          .set_decoding_mode(PaintImage::DecodingMode::kSync)
          .TakePaintImage();

  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());
  content_layer_client.add_draw_image(unspecified_image1, gfx::Point(0, 0),
                                      PaintFlags());
  content_layer_client.add_draw_image(async_image1, gfx::Point(10, 10),
                                      PaintFlags());
  content_layer_client.add_draw_image(unspecified_image2, gfx::Point(20, 20),
                                      PaintFlags());
  content_layer_client.add_draw_image(sync_image2, gfx::Point(30, 30),
                                      PaintFlags());
  content_layer_client.add_draw_image(async_image3, gfx::Point(40, 40),
                                      PaintFlags());
  content_layer_client.add_draw_image(sync_image3, gfx::Point(50, 50),
                                      PaintFlags());
  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();

  auto decode_hints = display_list->TakeDecodingModeMap();
  ASSERT_EQ(decode_hints.size(), 3u);
  ASSERT_TRUE(decode_hints.find(1) != decode_hints.end());
  ASSERT_TRUE(decode_hints.find(2) != decode_hints.end());
  ASSERT_TRUE(decode_hints.find(3) != decode_hints.end());
  // 1 was unspecified and async, so the result should be unspecified.
  EXPECT_EQ(decode_hints[1], PaintImage::DecodingMode::kUnspecified);
  // 2 was unspecified and sync, so the result should be sync.
  EXPECT_EQ(decode_hints[2], PaintImage::DecodingMode::kSync);
  // 3 was async and sync, so the result should be sync
  EXPECT_EQ(decode_hints[3], PaintImage::DecodingMode::kSync);

  decode_hints = display_list->TakeDecodingModeMap();
  EXPECT_EQ(decode_hints.size(), 0u);
}

TEST_F(DiscardableImageMapTest, TracksImageRegions) {
  gfx::Rect visible_rect(500, 500);
  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());

  std::vector<FrameMetadata> frames = {
      FrameMetadata(true, base::TimeDelta::FromMilliseconds(1)),
      FrameMetadata(true, base::TimeDelta::FromMilliseconds(1)),
  };
  auto image = CreateAnimatedImage(gfx::Size(100, 100), frames);
  PaintFlags flags;
  content_layer_client.add_draw_image(image, gfx::Point(0, 0), flags);
  content_layer_client.add_draw_image(image, gfx::Point(400, 400), flags);

  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const auto& image_map = display_list->discardable_image_map();

  std::vector<gfx::Rect> rects = {gfx::Rect(100, 100),
                                  gfx::Rect(400, 400, 100, 100)};
  Region expected_region;
  for (auto& rect : rects) {
    rect.Inset(-1, -1);
    expected_region.Union(rect);
  }

  EXPECT_EQ(ImageRectsToRegion(image_map.GetRectsForImage(image.stable_id())),
            expected_region);
}

class DiscardableImageMapColorSpaceTest
    : public DiscardableImageMapTest,
      public testing::WithParamInterface<gfx::ColorSpace> {};

TEST_P(DiscardableImageMapColorSpaceTest, ColorSpace) {
  const gfx::ColorSpace image_color_space = GetParam();
  gfx::Rect visible_rect(500, 500);
  PaintImage discardable_image = CreateDiscardablePaintImage(
      gfx::Size(500, 500), image_color_space.ToSkColorSpace());

  FakeContentLayerClient content_layer_client;
  content_layer_client.set_bounds(visible_rect.size());
  content_layer_client.add_draw_image(discardable_image, gfx::Point(0, 0),
                                      PaintFlags());
  scoped_refptr<DisplayItemList> display_list =
      content_layer_client.PaintContentsToDisplayList(
          ContentLayerClient::PAINTING_BEHAVIOR_NORMAL);
  display_list->GenerateDiscardableImagesMetadata();
  const DiscardableImageMap& image_map = display_list->discardable_image_map();

  if (!image_color_space.IsValid())
    EXPECT_TRUE(image_map.all_images_are_srgb());
  else if (image_color_space == gfx::ColorSpace::CreateSRGB())
    EXPECT_TRUE(image_map.all_images_are_srgb());
  else
    EXPECT_FALSE(image_map.all_images_are_srgb());
}

gfx::ColorSpace test_color_spaces[] = {
    gfx::ColorSpace(), gfx::ColorSpace::CreateSRGB(),
    gfx::ColorSpace::CreateDisplayP3D65(),
};

INSTANTIATE_TEST_CASE_P(ColorSpace,
                        DiscardableImageMapColorSpaceTest,
                        testing::ValuesIn(test_color_spaces));

}  // namespace cc
