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

#ifndef FLUTTER_FLOW_DISPLAY_LIST_COMPLEXITY_UNITTESTS_H_
#define FLUTTER_FLOW_DISPLAY_LIST_COMPLEXITY_UNITTESTS_H_

#include "flutter/display_list/display_list.h"
#include "flutter/display_list/display_list_builder.h"

#include "third_party/skia/include/core/SkPicture.h"
#include "third_party/skia/include/core/SkPictureRecorder.h"
#include "third_party/skia/include/core/SkSurface.h"
#include "third_party/skia/include/effects/SkBlenders.h"
#include "third_party/skia/include/effects/SkDashPathEffect.h"
#include "third_party/skia/include/effects/SkGradientShader.h"
#include "third_party/skia/include/effects/SkImageFilters.h"

namespace flutter {
namespace testing {

sk_sp<DisplayList> GetSampleDisplayList();
sk_sp<DisplayList> GetSampleDisplayList(int ops);
sk_sp<DisplayList> GetSampleNestedDisplayList();

typedef const std::function<void(DisplayListBuilder&)> DlInvoker;

constexpr SkPoint kEndPoints[] = {
    {0, 0},
    {100, 100},
};
const DlColor kColors[] = {
    DlColor::kGreen(),
    DlColor::kYellow(),
    DlColor::kBlue(),
};
constexpr float kStops[] = {
    0.0,
    0.5,
    1.0,
};
static std::vector<uint32_t> color_vector(kColors, kColors + 3);
static std::vector<float> stops_vector(kStops, kStops + 3);

// clang-format off
constexpr float kRotateColorMatrix[20] = {
    0, 1, 0, 0, 0,
    0, 0, 1, 0, 0,
    1, 0, 0, 0, 0,
    0, 0, 0, 1, 0,
};
constexpr float kInvertColorMatrix[20] = {
    -1.0,    0,    0, 1.0,   0,
       0, -1.0,    0, 1.0,   0,
       0,    0, -1.0, 1.0,   0,
     1.0,  1.0,  1.0, 1.0,   0,
};
// clang-format on

const SkScalar kTestDashes1[] = {4.0, 2.0};
const SkScalar kTestDashes2[] = {1.0, 1.5};

constexpr SkPoint TestPoints[] = {
    {10, 10},
    {20, 20},
    {10, 20},
    {20, 10},
};
#define TestPointCount sizeof(TestPoints) / (sizeof(TestPoints[0]))

static DlImageSampling kNearestSampling = DlImageSampling::kNearestNeighbor;
static DlImageSampling kLinearSampling = DlImageSampling::kLinear;

static sk_sp<DlImage> MakeTestImage(int w, int h, int checker_size) {
  sk_sp<SkSurface> surface = SkSurface::MakeRasterN32Premul(w, h);
  SkCanvas* canvas = surface->getCanvas();
  SkPaint p0, p1;
  p0.setStyle(SkPaint::kFill_Style);
  p0.setColor(SK_ColorGREEN);
  p1.setStyle(SkPaint::kFill_Style);
  p1.setColor(SK_ColorBLUE);
  p1.setAlpha(128);
  for (int y = 0; y < w; y += checker_size) {
    for (int x = 0; x < h; x += checker_size) {
      SkPaint& cellp = ((x + y) & 1) == 0 ? p0 : p1;
      canvas->drawRect(SkRect::MakeXYWH(x, y, checker_size, checker_size),
                       cellp);
    }
  }
  return DlImage::Make(surface->makeImageSnapshot());
}

static auto TestImage1 = MakeTestImage(40, 40, 5);
static auto TestImage2 = MakeTestImage(50, 50, 5);

static const sk_sp<SkBlender> kTestBlender1 =
    SkBlenders::Arithmetic(0.2, 0.2, 0.2, 0.2, false);
static const sk_sp<SkBlender> kTestBlender2 =
    SkBlenders::Arithmetic(0.2, 0.2, 0.2, 0.2, true);
static const sk_sp<SkBlender> kTestBlender3 =
    SkBlenders::Arithmetic(0.3, 0.3, 0.3, 0.3, true);
static const DlImageColorSource kTestSource1(TestImage1->skia_image(),
                                             DlTileMode::kClamp,
                                             DlTileMode::kMirror,
                                             kLinearSampling);
static const std::shared_ptr<DlColorSource> kTestSource2 =
    DlColorSource::MakeLinear(kEndPoints[0],
                              kEndPoints[1],
                              3,
                              kColors,
                              kStops,
                              DlTileMode::kMirror);
static const std::shared_ptr<DlColorSource> kTestSource3 =
    DlColorSource::MakeRadial(kEndPoints[0],
                              10.0,
                              3,
                              kColors,
                              kStops,
                              DlTileMode::kMirror);
static const std::shared_ptr<DlColorSource> kTestSource4 =
    DlColorSource::MakeConical(kEndPoints[0],
                               10.0,
                               kEndPoints[1],
                               200.0,
                               3,
                               kColors,
                               kStops,
                               DlTileMode::kDecal);
static const std::shared_ptr<DlColorSource> kTestSource5 =
    DlColorSource::MakeSweep(kEndPoints[0],
                             0.0,
                             360.0,
                             3,
                             kColors,
                             kStops,
                             DlTileMode::kDecal);
static const DlBlendColorFilter kTestBlendColorFilter1(DlColor::kRed(),
                                                       DlBlendMode::kDstATop);
static const DlBlendColorFilter kTestBlendColorFilter2(DlColor::kBlue(),
                                                       DlBlendMode::kDstATop);
static const DlBlendColorFilter kTestBlendColorFilter3(DlColor::kRed(),
                                                       DlBlendMode::kDstIn);
static const DlMatrixColorFilter kTestMatrixColorFilter1(kRotateColorMatrix);
static const DlMatrixColorFilter kTestMatrixColorFilter2(kInvertColorMatrix);
static const DlBlurImageFilter kTestBlurImageFilter1(5.0,
                                                     5.0,
                                                     DlTileMode::kClamp);
static const DlBlurImageFilter kTestBlurImageFilter2(6.0,
                                                     5.0,
                                                     DlTileMode::kClamp);
static const DlBlurImageFilter kTestBlurImageFilter3(5.0,
                                                     6.0,
                                                     DlTileMode::kClamp);
static const DlBlurImageFilter kTestBlurImageFilter4(5.0,
                                                     5.0,
                                                     DlTileMode::kDecal);
static const DlDilateImageFilter kTestDilateImageFilter1(5.0, 5.0);
static const DlDilateImageFilter kTestDilateImageFilter2(6.0, 5.0);
static const DlDilateImageFilter kTestDilateImageFilter3(5.0, 6.0);
static const DlErodeImageFilter kTestErodeImageFilter1(5.0, 5.0);
static const DlErodeImageFilter kTestErodeImageFilter2(6.0, 5.0);
static const DlErodeImageFilter kTestErodeImageFilter3(5.0, 6.0);
static const DlMatrixImageFilter kTestMatrixImageFilter1(
    SkMatrix::RotateDeg(45),
    kNearestSampling);
static const DlMatrixImageFilter kTestMatrixImageFilter2(
    SkMatrix::RotateDeg(85),
    kNearestSampling);
static const DlMatrixImageFilter kTestMatrixImageFilter3(
    SkMatrix::RotateDeg(45),
    kLinearSampling);
static const DlComposeImageFilter kTestComposeImageFilter1(
    kTestBlurImageFilter1,
    kTestMatrixImageFilter1);
static const DlComposeImageFilter kTestComposeImageFilter2(
    kTestBlurImageFilter2,
    kTestMatrixImageFilter1);
static const DlComposeImageFilter kTestComposeImageFilter3(
    kTestBlurImageFilter1,
    kTestMatrixImageFilter2);
static const DlColorFilterImageFilter kTestCFImageFilter1(
    kTestBlendColorFilter1);
static const DlColorFilterImageFilter kTestCFImageFilter2(
    kTestBlendColorFilter2);
static const std::shared_ptr<DlPathEffect> kTestPathEffect1 =
    DlDashPathEffect::Make(kTestDashes1, 2, 0.0f);
static const std::shared_ptr<DlPathEffect> kTestPathEffect2 =
    DlDashPathEffect::Make(kTestDashes2, 2, 0.0f);
static const DlBlurMaskFilter kTestMaskFilter1(kNormal_SkBlurStyle, 3.0);
static const DlBlurMaskFilter kTestMaskFilter2(kNormal_SkBlurStyle, 5.0);
static const DlBlurMaskFilter kTestMaskFilter3(kSolid_SkBlurStyle, 3.0);
static const DlBlurMaskFilter kTestMaskFilter4(kInner_SkBlurStyle, 3.0);
static const DlBlurMaskFilter kTestMaskFilter5(kOuter_SkBlurStyle, 3.0);
constexpr SkRect kTestBounds = SkRect::MakeLTRB(10, 10, 50, 60);
static const SkRRect kTestRRect = SkRRect::MakeRectXY(kTestBounds, 5, 5);
static const SkRRect kTestRRectRect = SkRRect::MakeRect(kTestBounds);
static const SkRRect kTestInnerRRect =
    SkRRect::MakeRectXY(kTestBounds.makeInset(5, 5), 2, 2);
static const SkPath kTestPathRect = SkPath::Rect(kTestBounds);
static const SkPath kTestPathOval = SkPath::Oval(kTestBounds);
static const SkPath kTestPath1 =
    SkPath::Polygon({{0, 0}, {10, 10}, {10, 0}, {0, 10}}, true);
static const SkPath kTestPath2 =
    SkPath::Polygon({{0, 0}, {10, 10}, {0, 10}, {10, 0}}, true);
static const SkPath kTestPath3 =
    SkPath::Polygon({{0, 0}, {10, 10}, {10, 0}, {0, 10}}, false);
static const SkMatrix kTestMatrix1 = SkMatrix::Scale(2, 2);
static const SkMatrix kTestMatrix2 = SkMatrix::RotateDeg(45);

static std::shared_ptr<const DlVertices> TestVertices1 =
    DlVertices::Make(DlVertexMode::kTriangles,  //
                     3,
                     TestPoints,
                     nullptr,
                     kColors);
static std::shared_ptr<const DlVertices> TestVertices2 =
    DlVertices::Make(DlVertexMode::kTriangleFan,  //
                     3,
                     TestPoints,
                     nullptr,
                     kColors);

static constexpr int kTestDivs1[] = {10, 20, 30};
static constexpr int kTestDivs2[] = {15, 20, 25};
static constexpr int kTestDivs3[] = {15, 25};
static constexpr SkCanvas::Lattice::RectType kTestRTypes[] = {
    SkCanvas::Lattice::RectType::kDefault,
    SkCanvas::Lattice::RectType::kTransparent,
    SkCanvas::Lattice::RectType::kFixedColor,
    SkCanvas::Lattice::RectType::kDefault,
    SkCanvas::Lattice::RectType::kTransparent,
    SkCanvas::Lattice::RectType::kFixedColor,
    SkCanvas::Lattice::RectType::kDefault,
    SkCanvas::Lattice::RectType::kTransparent,
    SkCanvas::Lattice::RectType::kFixedColor,
};
static constexpr SkColor kTestLatticeColors[] = {
    SK_ColorBLUE, SK_ColorGREEN, SK_ColorYELLOW,
    SK_ColorBLUE, SK_ColorGREEN, SK_ColorYELLOW,
    SK_ColorBLUE, SK_ColorGREEN, SK_ColorYELLOW,
};
static constexpr SkIRect kTestLatticeSrcRect = {1, 1, 39, 39};

static sk_sp<SkPicture> MakeTestPicture(int w, int h, SkColor color) {
  SkPictureRecorder recorder;
  SkRTreeFactory rtree_factory;
  SkCanvas* cv = recorder.beginRecording(kTestBounds, &rtree_factory);
  SkPaint paint;
  paint.setColor(color);
  paint.setStyle(SkPaint::kFill_Style);
  cv->drawRect(SkRect::MakeWH(w, h), paint);
  return recorder.finishRecordingAsPicture();
}
static sk_sp<SkPicture> TestPicture1 = MakeTestPicture(20, 20, SK_ColorGREEN);
static sk_sp<SkPicture> TestPicture2 = MakeTestPicture(25, 25, SK_ColorBLUE);

static sk_sp<DisplayList> MakeTestDisplayList(int w, int h, SkColor color) {
  DisplayListBuilder builder;
  builder.setColor(color);
  builder.drawRect(SkRect::MakeWH(w, h));
  return builder.Build();
}
static sk_sp<DisplayList> TestDisplayList1 =
    MakeTestDisplayList(20, 20, SK_ColorGREEN);
static sk_sp<DisplayList> TestDisplayList2 =
    MakeTestDisplayList(25, 25, SK_ColorBLUE);

static sk_sp<SkTextBlob> MakeTextBlob(std::string string) {
  return SkTextBlob::MakeFromText(string.c_str(), string.size(), SkFont(),
                                  SkTextEncoding::kUTF8);
}
static sk_sp<SkTextBlob> TestBlob1 = MakeTextBlob("TestBlob1");
static sk_sp<SkTextBlob> TestBlob2 = MakeTextBlob("TestBlob2");

struct DisplayListInvocation {
  unsigned int op_count_;
  size_t byte_count_;

  // in some cases, running the sequence through an SkCanvas will result
  // in fewer ops/bytes. Attribute invocations are recorded in an SkPaint
  // and not forwarded on, and SkCanvas culls unused save/restore/transforms.
  int sk_op_count_;
  size_t sk_byte_count_;

  DlInvoker invoker;
  bool supports_group_opacity_ = false;

  bool sk_version_matches() {
    return (static_cast<int>(op_count_) == sk_op_count_ &&
            byte_count_ == sk_byte_count_);
  }

  // A negative sk_op_count means "do not test this op".
  // Used mainly for these cases:
  // - we cannot encode a DrawShadowRec (Skia private header)
  // - SkCanvas cannot receive a DisplayList
  // - SkCanvas may or may not inline an SkPicture
  bool sk_testing_invalid() { return sk_op_count_ < 0; }

  bool is_empty() { return byte_count_ == 0; }

  bool supports_group_opacity() { return supports_group_opacity_; }

  unsigned int op_count() { return op_count_; }
  // byte count for the individual ops, no DisplayList overhead
  size_t raw_byte_count() { return byte_count_; }
  // byte count for the ops with DisplayList overhead, comparable
  // to |DisplayList.byte_count().
  size_t byte_count() { return sizeof(DisplayList) + byte_count_; }

  int sk_op_count() { return sk_op_count_; }
  // byte count for the ops with DisplayList overhead as translated
  // through an SkCanvas interface, comparable to |DisplayList.byte_count().
  size_t sk_byte_count() { return sizeof(DisplayList) + sk_byte_count_; }

  void Invoke(DisplayListBuilder& builder) { invoker(builder); }

  sk_sp<DisplayList> Build() {
    DisplayListBuilder builder;
    invoker(builder);
    return builder.Build();
  }
};

struct DisplayListInvocationGroup {
  std::string op_name;
  std::vector<DisplayListInvocation> variants;
};

std::vector<DisplayListInvocationGroup> CreateAllRenderingOps();
std::vector<DisplayListInvocationGroup> CreateAllGroups();

}  // namespace testing
}  // namespace flutter

#endif  // FLUTTER_FLOW_DISPLAY_LIST_COMPLEXITY_UNITTESTS_H_
