[DisplayList] Migrate rendering tests and benchmarks to DL geometry (#163766)

Migrating the benchmark and rendering tests to using DL geometry with DL
rendering calls.
This commit is contained in:
Jim Graham 2025-02-20 16:15:39 -08:00 committed by GitHub
parent f6543c3d45
commit d0e2fc72bc
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
27 changed files with 1189 additions and 1050 deletions

View File

@ -10,12 +10,8 @@
#include "third_party/skia/include/core/SkBitmap.h"
#include "third_party/skia/include/core/SkImage.h"
#include "third_party/skia/include/core/SkPoint.h"
#include "third_party/skia/include/core/SkSurface.h"
#include "third_party/skia/include/core/SkTextBlob.h"
#include "third_party/skia/include/gpu/ganesh/GrDirectContext.h"
#include "third_party/skia/include/gpu/ganesh/GrRecordingContext.h"
#include "third_party/skia/include/gpu/ganesh/GrTypes.h"
namespace flutter {
namespace testing {
@ -43,16 +39,6 @@ DlPaint GetPaintForRun(unsigned attributes) {
return paint;
}
static void FlushSubmitCpuSync(const sk_sp<SkSurface>& surface) {
if (!surface) {
return;
}
if (GrDirectContext* dContext =
GrAsDirectContext(surface->recordingContext())) {
dContext->flushAndSubmit(surface.get(), GrSyncCpu::kYes);
}
}
void AnnotateAttributes(unsigned attributes,
benchmark::State& state,
const DisplayListAttributeFlags flags) {
@ -98,8 +84,8 @@ void BM_DrawLine(benchmark::State& state,
size_t length = state.range(0);
surface_provider->InitializeSurface(length, length);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
state.counters["DrawCallCount"] = kLinesToDraw;
for (size_t i = 0; i < kLinesToDraw; i++) {
@ -111,8 +97,8 @@ void BM_DrawLine(benchmark::State& state,
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawLine-" +
@ -136,23 +122,25 @@ void BM_DrawRect(benchmark::State& state,
size_t length = state.range(0);
size_t canvas_size = length * 2;
surface_provider->InitializeSurface(canvas_size, canvas_size);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
// As rects have DlScalar dimensions, we want to ensure that we also
// draw rects with non-integer position and size
const DlScalar offset = 0.5f;
DlRect rect = DlRect::MakeLTRB(0, 0, length, length);
const DlPoint offset(0.5f, 0.5f);
DlPoint origin;
DlSize size(length, length);
state.counters["DrawCallCount"] = kRectsToDraw;
for (size_t i = 0; i < kRectsToDraw; i++) {
DlRect rect = DlRect::MakeOriginSize(origin, size);
builder.DrawRect(rect, paint);
rect = rect.Shift(offset, offset);
if (rect.GetRight() > canvas_size) {
rect = rect.Shift(-canvas_size, 0);
origin += offset;
if (origin.x + size.width > canvas_size) {
origin.x -= canvas_size;
}
if (rect.GetBottom() > canvas_size) {
rect = rect.Shift(0, -canvas_size);
origin.y -= canvas_size;
}
}
@ -160,8 +148,8 @@ void BM_DrawRect(benchmark::State& state,
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawRect-" +
@ -185,29 +173,31 @@ void BM_DrawOval(benchmark::State& state,
size_t length = state.range(0);
size_t canvas_size = length * 2;
surface_provider->InitializeSurface(canvas_size, canvas_size);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
DlRect rect = DlRect::MakeXYWH(0, 0, length * 1.5f, length);
const DlScalar offset = 0.5f;
const DlPoint offset(0.5f, 0.5f);
DlPoint origin;
DlSize size(length * 1.5f, length);
state.counters["DrawCallCount"] = kOvalsToDraw;
for (size_t i = 0; i < kOvalsToDraw; i++) {
DlRect rect = DlRect::MakeOriginSize(origin, size);
builder.DrawOval(rect, paint);
rect = rect.Shift(offset, offset);
if (rect.GetRight() > canvas_size) {
rect = rect.Shift(-canvas_size, 0);
origin += offset;
if (origin.x + size.width > canvas_size) {
origin.x -= canvas_size;
}
if (rect.GetBottom() > canvas_size) {
rect = rect.Shift(0, -canvas_size);
if (origin.y + size.height > canvas_size) {
origin.y -= canvas_size;
}
}
auto display_list = builder.Build();
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawOval-" +
@ -231,19 +221,18 @@ void BM_DrawCircle(benchmark::State& state,
size_t length = state.range(0);
size_t canvas_size = length * 2;
surface_provider->InitializeSurface(canvas_size, canvas_size);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
DlScalar radius = length / 2.0f;
const DlScalar offset = 0.5f;
const DlPoint offset(0.5f, 0.5f);
DlPoint center = DlPoint(radius, radius);
DlPoint shift = DlPoint(offset, offset);
state.counters["DrawCallCount"] = kCirclesToDraw;
for (size_t i = 0; i < kCirclesToDraw; i++) {
builder.DrawCircle(center, radius, paint);
center += shift;
center += offset;
if (center.x + radius > canvas_size) {
center.x = radius;
}
@ -255,8 +244,8 @@ void BM_DrawCircle(benchmark::State& state,
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawCircle-" +
@ -281,8 +270,8 @@ void BM_DrawRRect(benchmark::State& state,
size_t length = state.range(0);
size_t canvas_size = length * 2;
surface_provider->InitializeSurface(canvas_size, canvas_size);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
DlRoundingRadii radii;
switch (type) {
@ -329,8 +318,8 @@ void BM_DrawRRect(benchmark::State& state,
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawRRect-" +
@ -358,8 +347,8 @@ void BM_DrawDRRect(benchmark::State& state,
size_t length = state.range(0);
size_t canvas_size = length * 2;
surface_provider->InitializeSurface(canvas_size, canvas_size);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
DlRoundingRadii radii;
switch (type) {
@ -412,8 +401,8 @@ void BM_DrawDRRect(benchmark::State& state,
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawDRRect-" +
@ -434,30 +423,32 @@ void BM_DrawArc(benchmark::State& state,
size_t length = state.range(0);
size_t canvas_size = length * 2;
surface_provider->InitializeSurface(canvas_size, canvas_size);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
DlScalar starting_angle = 0.0f;
DlScalar offset = 0.5f;
DlPoint offset(0.5f, 0.5f);
// Just some random sweeps that will mostly circumnavigate the circle
std::vector<DlScalar> segment_sweeps = {5.5f, -10.0f, 42.0f, 71.7f, 90.0f,
37.5f, 17.9f, 32.0f, 379.4f};
DlRect bounds = DlRect::MakeLTRB(0, 0, length, length);
DlPoint origin;
DlSize size(length, length);
state.counters["DrawCallCount"] = kArcSweepSetsToDraw * segment_sweeps.size();
for (size_t i = 0; i < kArcSweepSetsToDraw; i++) {
DlRect bounds = DlRect::MakeOriginSize(origin, size);
for (DlScalar sweep : segment_sweeps) {
builder.DrawArc(bounds, starting_angle, sweep, false, paint);
starting_angle += sweep + 5.0f;
}
bounds = bounds.Shift(offset, offset);
if (bounds.GetRight() > canvas_size) {
bounds = bounds.Shift(-canvas_size, 0);
origin += offset;
if (origin.x + size.width > canvas_size) {
origin.x -= canvas_size;
}
if (bounds.GetBottom() > canvas_size) {
bounds = bounds.Shift(0, -canvas_size);
if (origin.y + size.height > canvas_size) {
origin.y -= canvas_size;
}
}
@ -465,8 +456,8 @@ void BM_DrawArc(benchmark::State& state,
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawArc-" +
@ -474,18 +465,18 @@ void BM_DrawArc(benchmark::State& state,
surface_provider->Snapshot(filename);
}
// Returns a list of SkPoints that represent `n` points equally spaced out
// Returns a list of DlPoints that represent `n` points equally spaced out
// along the circumference of a circle with radius `r` and centered on `center`.
std::vector<SkPoint> GetPolygonPoints(size_t n, SkPoint center, DlScalar r) {
std::vector<SkPoint> points;
std::vector<DlPoint> GetPolygonPoints(size_t n, DlPoint center, DlScalar r) {
std::vector<DlPoint> points;
DlScalar x, y;
float angle;
float full_circle = 2.0f * M_PI;
for (size_t i = 0; i < n; i++) {
angle = (full_circle / static_cast<float>(n)) * static_cast<float>(i);
x = center.x() + r * std::cosf(angle);
y = center.y() + r * std::sinf(angle);
points.push_back(SkPoint::Make(x, y));
x = center.x + r * std::cosf(angle);
y = center.y + r * std::sinf(angle);
points.emplace_back(x, y);
}
return points;
}
@ -496,14 +487,17 @@ std::vector<SkPoint> GetPolygonPoints(size_t n, SkPoint center, DlScalar r) {
// `radius` and `center`.
//
// The path segment connecting each control point is a line segment.
void GetLinesPath(SkPath& path, size_t sides, SkPoint center, float radius) {
std::vector<SkPoint> points = GetPolygonPoints(sides, center, radius);
path.moveTo(points[0]);
void GetLinesPath(DlPathBuilder& path_builder,
size_t sides,
DlPoint center,
float radius) {
std::vector<DlPoint> points = GetPolygonPoints(sides, center, radius);
path_builder.MoveTo(points[0]);
for (size_t i = 1; i < sides; i++) {
path.lineTo(points[i]);
path_builder.LineTo(points[i]);
}
path.lineTo(points[0]);
path.close();
path_builder.LineTo(points[0]);
path_builder.Close();
}
// Creates a path that represents a regular polygon with `sides` sides,
@ -515,17 +509,20 @@ void GetLinesPath(SkPath& path, size_t sides, SkPoint center, float radius) {
// bezier control point being on a circle with 80% of `radius` and with the
// control point angle half way between the start and end point angles for the
// polygon segment.
void GetQuadsPath(SkPath& path, size_t sides, SkPoint center, float radius) {
std::vector<SkPoint> points = GetPolygonPoints(sides, center, radius);
std::vector<SkPoint> control_points =
void GetQuadsPath(DlPathBuilder& path_builder,
size_t sides,
DlPoint center,
float radius) {
std::vector<DlPoint> points = GetPolygonPoints(sides, center, radius);
std::vector<DlPoint> control_points =
GetPolygonPoints(sides * 2, center, radius * 0.8f);
path.moveTo(points[0]);
path_builder.MoveTo(points[0]);
for (size_t i = 1; i < sides; i++) {
path.quadTo(control_points[2 * i - 1], points[i]);
path_builder.QuadraticCurveTo(control_points[2 * i - 1], points[i]);
}
path.quadTo(control_points[2 * sides - 1], points[0]);
path.close();
path_builder.QuadraticCurveTo(control_points[2 * sides - 1], points[0]);
path_builder.Close();
}
// Creates a path that represents a regular polygon with `sides` sides,
@ -537,17 +534,20 @@ void GetQuadsPath(SkPath& path, size_t sides, SkPoint center, float radius) {
// control point being on a circle with 80% of `radius` and with the
// control point angle half way between the start and end point angles for the
// polygon segment, and the conic weight set to 3.7f.
void GetConicsPath(SkPath& path, size_t sides, SkPoint center, float radius) {
std::vector<SkPoint> points = GetPolygonPoints(sides, center, radius);
std::vector<SkPoint> control_points =
void GetConicsPath(DlPathBuilder& path_builder,
size_t sides,
DlPoint center,
float radius) {
std::vector<DlPoint> points = GetPolygonPoints(sides, center, radius);
std::vector<DlPoint> control_points =
GetPolygonPoints(sides * 2, center, radius * 0.8f);
path.moveTo(points[0]);
path_builder.MoveTo(points[0]);
for (size_t i = 1; i < sides; i++) {
path.conicTo(control_points[2 * i - 1], points[i], 3.7f);
path_builder.ConicCurveTo(control_points[2 * i - 1], points[i], 3.7f);
}
path.conicTo(control_points[2 * sides - 1], points[0], 3.7f);
path.close();
path_builder.ConicCurveTo(control_points[2 * sides - 1], points[0], 3.7f);
path_builder.Close();
}
// Creates a path that represents a regular polygon with `sides` sides,
@ -560,21 +560,24 @@ void GetConicsPath(SkPath& path, size_t sides, SkPoint center, float radius) {
// control point being on a circle with 120% of `radius`. The first
// control point is 1/3, and the second control point is 2/3, of the angle
// between the start and end point angles for the polygon segment.
void GetCubicsPath(SkPath& path, size_t sides, SkPoint center, float radius) {
std::vector<SkPoint> points = GetPolygonPoints(sides, center, radius);
std::vector<SkPoint> inner_control_points =
void GetCubicsPath(DlPathBuilder& path_builder,
size_t sides,
DlPoint center,
float radius) {
std::vector<DlPoint> points = GetPolygonPoints(sides, center, radius);
std::vector<DlPoint> inner_control_points =
GetPolygonPoints(sides * 3, center, radius * 0.8f);
std::vector<SkPoint> outer_control_points =
std::vector<DlPoint> outer_control_points =
GetPolygonPoints(sides * 3, center, radius * 1.2f);
path.moveTo(points[0]);
path_builder.MoveTo(points[0]);
for (size_t i = 1; i < sides; i++) {
path.cubicTo(inner_control_points[3 * i - 2],
outer_control_points[3 * i - 1], points[i]);
path_builder.CubicCurveTo(inner_control_points[3 * i - 2],
outer_control_points[3 * i - 1], points[i]);
}
path.cubicTo(inner_control_points[3 * sides - 2],
outer_control_points[3 * sides - 1], points[0]);
path.close();
path_builder.CubicCurveTo(inner_control_points[3 * sides - 2],
outer_control_points[3 * sides - 1], points[0]);
path_builder.Close();
}
// Returns a path generated by one of the above path generators
@ -585,28 +588,28 @@ void GetCubicsPath(SkPath& path, size_t sides, SkPoint center, float radius) {
// Each of the polygons will have `sides` sides, and the resulting path will be
// bounded by a circle with radius of 150% of `radius` (or another 20% on top of
// that for cubics)
void MultiplyPath(SkPath& path,
SkPath::Verb type,
SkPoint center,
void MultiplyPath(DlPathBuilder& path_builder,
PathVerb type,
DlPoint center,
size_t sides,
size_t number,
float radius) {
std::vector<SkPoint> center_points =
std::vector<DlPoint> center_points =
GetPolygonPoints(number, center, radius / 2.0f);
for (SkPoint p : center_points) {
for (DlPoint p : center_points) {
switch (type) {
case SkPath::Verb::kLine_Verb:
GetLinesPath(path, sides, p, radius);
case PathVerb::kLine:
GetLinesPath(path_builder, sides, p, radius);
break;
case SkPath::Verb::kQuad_Verb:
GetQuadsPath(path, sides, p, radius);
case PathVerb::kQuad:
GetQuadsPath(path_builder, sides, p, radius);
break;
case SkPath::Verb::kConic_Verb:
GetConicsPath(path, sides, p, radius);
case PathVerb::kConic:
GetConicsPath(path_builder, sides, p, radius);
break;
case SkPath::Verb::kCubic_Verb:
GetCubicsPath(path, sides, p, radius);
case PathVerb::kCubic:
GetCubicsPath(path_builder, sides, p, radius);
break;
default:
break;
@ -614,15 +617,15 @@ void MultiplyPath(SkPath& path,
}
}
std::string VerbToString(SkPath::Verb type) {
std::string VerbToString(PathVerb type) {
switch (type) {
case SkPath::Verb::kLine_Verb:
case PathVerb::kLine:
return "Lines";
case SkPath::Verb::kQuad_Verb:
case PathVerb::kQuad:
return "Quads";
case SkPath::Verb::kConic_Verb:
case PathVerb::kConic:
return "Conics";
case SkPath::Verb::kCubic_Verb:
case PathVerb::kCubic:
return "Cubics";
default:
return "Unknown";
@ -630,7 +633,7 @@ std::string VerbToString(SkPath::Verb type) {
}
// Draws a series of overlapping 20-sided polygons where the path segment
// between each point is one of the verb types defined in SkPath.
// between each point is one of the verb types defined in PathVerb.
//
// The number of polygons drawn will be varied to get an overall path
// with approximately 20*N verbs, so we can get an idea of the fixed
@ -639,7 +642,7 @@ std::string VerbToString(SkPath::Verb type) {
void BM_DrawPath(benchmark::State& state,
BackendType backend_type,
unsigned attributes,
SkPath::Verb type) {
PathVerb type) {
auto surface_provider = DlSurfaceProvider::Create(backend_type);
DisplayListBuilder builder;
DlPaint paint = GetPaintForRun(attributes);
@ -648,28 +651,33 @@ void BM_DrawPath(benchmark::State& state,
size_t length = kFixedCanvasSize;
surface_provider->InitializeSurface(length, length);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
SkPath path;
DlPathBuilder path_builder;
std::string label = VerbToString(type);
SkPoint center = SkPoint::Make(length / 2.0f, length / 2.0f);
DlPoint center = DlPoint(length / 2.0f, length / 2.0f);
float radius = length * 0.25f;
state.SetComplexityN(state.range(0));
MultiplyPath(path, type, center, 20, state.range(0), radius);
MultiplyPath(path_builder, type, center, 20, state.range(0), radius);
DlPath path = DlPath(path_builder);
state.counters["VerbCount"] = path.countVerbs();
state.counters["VerbCount"] = path.GetPath().GetComponentCount();
state.counters["DrawCallCount"] = 1;
builder.DrawPath(path, paint);
auto display_list = builder.Build();
// Prime any path conversions
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawPath-" + label +
@ -689,16 +697,16 @@ void BM_DrawPath(benchmark::State& state,
// and the final vertex being the center point of the disc.
//
// Each vertex colour will alternate through Red, Green, Blue and Cyan.
std::shared_ptr<DlVertices> GetTestVertices(SkPoint center,
std::shared_ptr<DlVertices> GetTestVertices(DlPoint center,
float radius,
size_t vertex_count,
DlVertexMode mode,
size_t& final_vertex_count) {
size_t outer_vertex_count = vertex_count / 2;
std::vector<SkPoint> outer_points =
std::vector<DlPoint> outer_points =
GetPolygonPoints(outer_vertex_count, center, radius);
std::vector<SkPoint> vertices;
std::vector<DlPoint> vertices;
std::vector<DlColor> colors;
switch (mode) {
@ -750,8 +758,8 @@ std::shared_ptr<DlVertices> GetTestVertices(SkPoint center,
}
final_vertex_count = vertices.size();
return DlVertices::Make(mode, vertices.size(), ToDlPoints(vertices.data()),
nullptr, colors.data());
return DlVertices::Make(mode, vertices.size(), vertices.data(), nullptr,
colors.data());
}
std::string VertexModeToString(DlVertexMode mode) {
@ -786,21 +794,21 @@ void BM_DrawVertices(benchmark::State& state,
size_t length = kFixedCanvasSize;
surface_provider->InitializeSurface(length, length);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
SkPoint center = SkPoint::Make(length / 2.0f, length / 2.0f);
DlPoint center = DlPoint(length / 2.0f, length / 2.0f);
float radius = length / 4.0f;
size_t vertex_count, total_vertex_count = 0;
size_t disc_count = state.range(0);
std::vector<SkPoint> center_points =
std::vector<DlPoint> center_points =
GetPolygonPoints(disc_count, center, radius / 4.0f);
state.counters["DrawCallCount"] = center_points.size();
for (SkPoint p : center_points) {
for (DlPoint p : center_points) {
std::shared_ptr<DlVertices> vertices =
GetTestVertices(p, radius, 50, mode, vertex_count);
total_vertex_count += vertex_count;
@ -814,8 +822,8 @@ void BM_DrawVertices(benchmark::State& state,
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawVertices-" +
@ -830,22 +838,23 @@ void BM_DrawVertices(benchmark::State& state,
// chosen to appear somewhat random.
//
// The points generated will wrap in x and y for the bounds of `canvas_size`.
std::vector<SkPoint> GetTestPoints(size_t count, SkISize canvas_size) {
std::vector<SkPoint> points;
std::vector<DlPoint> GetTestPoints(size_t count, DlISize canvas_size) {
std::vector<DlPoint> points;
// Some arbitrary offsets to use when building the list of points
std::vector<SkScalar> delta_x = {10.0f, 6.3f, 15.0f, 3.5f, 22.6f, 4.7f};
std::vector<SkScalar> delta_y = {9.3f, -5.4f, 8.5f, -12.0f, 19.2f, -19.6f};
std::vector<DlScalar> delta_x = {10.0f, 6.3f, 15.0f, 3.5f, 22.6f, 4.7f};
std::vector<DlScalar> delta_y = {9.3f, -5.4f, 8.5f, -12.0f, 19.2f, -19.6f};
SkPoint current = SkPoint::Make(0.0f, 0.0f);
DlPoint current;
for (size_t i = 0; i < count; i++) {
points.push_back(current);
current.offset(delta_x[i % delta_x.size()], delta_y[i % delta_y.size()]);
if (current.x() > canvas_size.width()) {
current.offset(-canvas_size.width(), 25.0f);
current +=
DlPoint(delta_x[i % delta_x.size()], delta_y[i % delta_y.size()]);
if (current.x > canvas_size.width) {
current += DlPoint(-canvas_size.width, 25.0f);
}
if (current.y() > canvas_size.height()) {
current.offset(0.0f, -canvas_size.height());
if (current.y > canvas_size.height) {
current += DlPoint(0.0f, -canvas_size.height);
}
}
@ -895,23 +904,23 @@ void BM_DrawPoints(benchmark::State& state,
size_t length = kFixedCanvasSize;
surface_provider->InitializeSurface(length, length);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
size_t point_count = state.range(0);
state.SetComplexityN(point_count);
state.counters["PointCount"] = point_count;
state.counters["DrawCallCount"] = 1;
std::vector<SkPoint> points =
GetTestPoints(point_count, SkISize::Make(length, length));
std::vector<DlPoint> points =
GetTestPoints(point_count, DlISize(length, length));
builder.DrawPoints(mode, points.size(), points.data(), paint);
auto display_list = builder.Build();
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawPoints-" +
@ -946,8 +955,8 @@ void BM_DrawImage(benchmark::State& state,
size_t bitmap_size = state.range(0);
size_t canvas_size = 2 * bitmap_size;
surface_provider->InitializeSurface(canvas_size, canvas_size);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
sk_sp<SkImage> image;
std::shared_ptr<DlSurfaceInstance> offscreen_instance;
@ -967,8 +976,8 @@ void BM_DrawImage(benchmark::State& state,
offscreen->getCanvas()->clear(SK_ColorRED);
}
SkScalar offset = 0.5f;
SkPoint dst = SkPoint::Make(0, 0);
const DlPoint offset(0.5f, 0.5f);
DlPoint dst;
state.counters["DrawCallCount"] = kImagesToDraw;
for (size_t i = 0; i < kImagesToDraw; i++) {
@ -976,20 +985,20 @@ void BM_DrawImage(benchmark::State& state,
: offscreen->makeImageSnapshot();
builder.DrawImage(DlImage::Make(image), dst, options, &paint);
dst.offset(offset, offset);
if (dst.x() + bitmap_size > canvas_size) {
dst.set(0, dst.y());
dst += offset;
if (dst.x + bitmap_size > canvas_size) {
dst.x = 0;
}
if (dst.y() + bitmap_size > canvas_size) {
dst.set(dst.x(), 0);
if (dst.y + bitmap_size > canvas_size) {
dst.y = 0;
}
}
auto display_list = builder.Build();
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawImage-" +
@ -1029,8 +1038,8 @@ void BM_DrawImageRect(benchmark::State& state,
size_t bitmap_size = state.range(0);
size_t canvas_size = 2 * bitmap_size;
surface_provider->InitializeSurface(canvas_size, canvas_size);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
sk_sp<SkImage> image;
std::shared_ptr<DlSurfaceInstance> offscreen_instance;
@ -1050,32 +1059,33 @@ void BM_DrawImageRect(benchmark::State& state,
offscreen->getCanvas()->clear(SK_ColorRED);
}
SkScalar offset = 0.5f;
SkRect src = SkRect::MakeXYWH(bitmap_size / 4.0f, bitmap_size / 4.0f,
const DlPoint offset(0.5f, 0.5f);
DlRect src = DlRect::MakeXYWH(bitmap_size / 4.0f, bitmap_size / 4.0f,
bitmap_size / 2.0f, bitmap_size / 2.0f);
SkRect dst =
SkRect::MakeXYWH(0.0f, 0.0f, bitmap_size * 0.75f, bitmap_size * 0.75f);
DlPoint origin;
DlSize size(bitmap_size * 0.75f, bitmap_size * 0.75f);
state.counters["DrawCallCount"] = kImagesToDraw;
for (size_t i = 0; i < kImagesToDraw; i++) {
image = upload_bitmap ? ImageFromBitmapWithNewID(bitmap)
: offscreen->makeImageSnapshot();
DlRect dst = DlRect::MakeOriginSize(origin, size);
builder.DrawImageRect(DlImage::Make(image), src, dst, options, &paint,
constraint);
dst.offset(offset, offset);
if (dst.right() > canvas_size) {
dst.offsetTo(0, dst.y());
origin += offset;
if (origin.x + size.width > canvas_size) {
origin.x = 0.0f;
}
if (dst.bottom() > canvas_size) {
dst.offsetTo(dst.x(), 0);
if (origin.y + size.height > canvas_size) {
origin.y = 0.0f;
}
}
auto display_list = builder.Build();
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawImageRect-" +
@ -1116,10 +1126,10 @@ void BM_DrawImageNine(benchmark::State& state,
size_t bitmap_size = state.range(0);
size_t canvas_size = 2 * bitmap_size;
surface_provider->InitializeSurface(canvas_size, canvas_size);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
SkIRect center = SkIRect::MakeXYWH(bitmap_size / 4, bitmap_size / 4,
DlIRect center = DlIRect::MakeXYWH(bitmap_size / 4, bitmap_size / 4,
bitmap_size / 2, bitmap_size / 2);
sk_sp<SkImage> image;
@ -1140,29 +1150,30 @@ void BM_DrawImageNine(benchmark::State& state,
offscreen->getCanvas()->clear(SK_ColorRED);
}
SkScalar offset = 0.5f;
SkRect dst =
SkRect::MakeXYWH(0.0f, 0.0f, bitmap_size * 0.75f, bitmap_size * 0.75f);
const DlPoint offset(0.5f, 0.5f);
DlPoint origin;
DlSize size(bitmap_size * 0.75f, bitmap_size * 0.75f);
state.counters["DrawCallCount"] = kImagesToDraw;
for (size_t i = 0; i < kImagesToDraw; i++) {
image = upload_bitmap ? ImageFromBitmapWithNewID(bitmap)
: offscreen->makeImageSnapshot();
DlRect dst = DlRect::MakeOriginSize(origin, size);
builder.DrawImageNine(DlImage::Make(image), center, dst, filter, &paint);
dst.offset(offset, offset);
if (dst.right() > canvas_size) {
dst.offsetTo(0, dst.y());
origin += offset;
if (origin.x + size.width > canvas_size) {
origin.x = 0.0f;
}
if (dst.bottom() > canvas_size) {
dst.offsetTo(dst.x(), 0);
if (origin.y + size.height > canvas_size) {
origin.y = 0.0f;
}
}
auto display_list = builder.Build();
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawImageNine-" +
@ -1191,9 +1202,10 @@ void BM_DrawTextBlob(benchmark::State& state,
size_t draw_calls = state.range(0);
size_t canvas_size = kFixedCanvasSize;
surface_provider->InitializeSurface(canvas_size, canvas_size);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
state.SetComplexityN(draw_calls);
state.counters["DrawCallCount_Varies"] = draw_calls;
state.counters["GlyphCount"] = draw_calls;
char character[2] = {'A', '\0'};
@ -1207,8 +1219,8 @@ void BM_DrawTextBlob(benchmark::State& state,
auto display_list = builder.Build();
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawTextBlob-" +
@ -1228,7 +1240,7 @@ void BM_DrawShadow(benchmark::State& state,
BackendType backend_type,
unsigned attributes,
bool transparent_occluder,
SkPath::Verb type) {
PathVerb type) {
auto surface_provider = DlSurfaceProvider::Create(backend_type);
DisplayListBuilder builder;
DlPaint paint = GetPaintForRun(attributes);
@ -1237,26 +1249,26 @@ void BM_DrawShadow(benchmark::State& state,
size_t length = kFixedCanvasSize;
surface_provider->InitializeSurface(length, length);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
SkPath path;
DlPathBuilder path_builder;
SkPoint center = SkPoint::Make(length / 2.0f, length / 2.0f);
DlPoint center = DlPoint(length / 2.0f, length / 2.0f);
float radius = length * 0.25f;
switch (type) {
case SkPath::Verb::kLine_Verb:
GetLinesPath(path, 10, center, radius);
case PathVerb::kLine:
GetLinesPath(path_builder, 10, center, radius);
break;
case SkPath::Verb::kQuad_Verb:
GetQuadsPath(path, 10, center, radius);
case PathVerb::kQuad:
GetQuadsPath(path_builder, 10, center, radius);
break;
case SkPath::Verb::kConic_Verb:
GetConicsPath(path, 10, center, radius);
case PathVerb::kConic:
GetConicsPath(path_builder, 10, center, radius);
break;
case SkPath::Verb::kCubic_Verb:
GetCubicsPath(path, 10, center, radius);
case PathVerb::kCubic:
GetCubicsPath(path_builder, 10, center, radius);
break;
default:
break;
@ -1265,16 +1277,22 @@ void BM_DrawShadow(benchmark::State& state,
float elevation = state.range(0);
state.counters["DrawCallCount"] = 1;
DlPath path = DlPath(path_builder);
// We can hardcode dpr to 1.0f as we're varying elevation, and dpr is only
// ever used in conjunction with elevation.
builder.DrawShadow(path, DlColor(SK_ColorBLUE), elevation,
transparent_occluder, 1.0f);
auto display_list = builder.Build();
// Prime the path conversion.
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-DrawShadow-" +
@ -1302,20 +1320,20 @@ void BM_SaveLayer(benchmark::State& state,
size_t length = kFixedCanvasSize;
surface_provider->InitializeSurface(length, length);
auto surface = surface_provider->GetPrimarySurface()->sk_surface();
auto canvas = DlSkCanvasAdapter(surface->getCanvas());
auto surface = surface_provider->GetPrimarySurface();
auto canvas = surface->GetCanvas();
size_t save_layer_calls = state.range(0);
// Ensure we draw two overlapping rects to avoid any peephole optimisations
SkRect rect1 = SkRect::MakeLTRB(0, 0, 0.75f * length, 0.75f * length);
SkRect rect2 =
SkRect::MakeLTRB(0.25f * length, 0.25f * length, length, length);
DlRect rect1 = DlRect::MakeLTRB(0, 0, 0.75f * length, 0.75f * length);
DlRect rect2 =
DlRect::MakeLTRB(0.25f * length, 0.25f * length, length, length);
state.counters["DrawCallCount_Varies"] = save_layer_calls * save_depth;
for (size_t i = 0; i < save_layer_calls; i++) {
for (size_t j = 0; j < save_depth; j++) {
builder.SaveLayer(nullptr, nullptr);
builder.SaveLayer(std::nullopt, nullptr);
builder.DrawRect(rect1, paint);
builder.DrawRect(rect2, paint);
}
@ -1327,8 +1345,8 @@ void BM_SaveLayer(benchmark::State& state,
// We only want to time the actual rasterization.
for ([[maybe_unused]] auto _ : state) {
canvas.DrawDisplayList(display_list);
FlushSubmitCpuSync(surface);
canvas->DrawDisplayList(display_list);
surface->FlushSubmitCpuSync();
}
auto filename = surface_provider->backend_name() + "-SaveLayer-" +

View File

@ -11,10 +11,6 @@
#include "flutter/display_list/testing/dl_test_surface_provider.h"
#include "third_party/benchmark/include/benchmark/benchmark.h"
#include "third_party/skia/include/core/SkCanvas.h"
#include "third_party/skia/include/core/SkPath.h"
#include "third_party/skia/include/core/SkRRect.h"
#include "third_party/skia/include/core/SkSurface.h"
namespace flutter {
namespace testing {
@ -33,6 +29,13 @@ enum class RRectType {
kComplex,
};
enum class PathVerb {
kLine,
kQuad,
kConic,
kCubic,
};
DlPaint GetPaintForRun(unsigned attributes);
using BackendType = DlSurfaceProvider::BackendType;
@ -65,7 +68,7 @@ void BM_DrawDRRect(benchmark::State& state,
void BM_DrawPath(benchmark::State& state,
BackendType backend_type,
unsigned attributes,
SkPath::Verb type);
PathVerb type);
void BM_DrawPoints(benchmark::State& state,
BackendType backend_type,
unsigned attributes,
@ -97,7 +100,7 @@ void BM_DrawShadow(benchmark::State& state,
BackendType backend_type,
unsigned attributes,
bool transparent_occluder,
SkPath::Verb type);
PathVerb type);
void BM_SaveLayer(benchmark::State& state,
BackendType backend_type,
unsigned attributes,
@ -160,7 +163,7 @@ void BM_SaveLayer(benchmark::State& state,
Lines/BACKEND, \
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
SkPath::Verb::kLine_Verb) \
PathVerb::kLine) \
->RangeMultiplier(2) \
->Range(8, 512) \
->UseRealTime() \
@ -171,7 +174,7 @@ void BM_SaveLayer(benchmark::State& state,
Quads/BACKEND, \
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
SkPath::Verb::kQuad_Verb) \
PathVerb::kQuad) \
->RangeMultiplier(2) \
->Range(8, 512) \
->UseRealTime() \
@ -182,7 +185,7 @@ void BM_SaveLayer(benchmark::State& state,
Conics/BACKEND, \
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
SkPath::Verb::kConic_Verb) \
PathVerb::kConic) \
->RangeMultiplier(2) \
->Range(8, 512) \
->UseRealTime() \
@ -193,7 +196,7 @@ void BM_SaveLayer(benchmark::State& state,
Cubics/BACKEND, \
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
SkPath::Verb::kCubic_Verb) \
PathVerb::kCubic) \
->RangeMultiplier(2) \
->Range(8, 512) \
->UseRealTime() \
@ -205,7 +208,7 @@ void BM_SaveLayer(benchmark::State& state,
BENCHMARK_CAPTURE(BM_DrawPoints, Points/BACKEND, \
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
DlPointMode::kPoints) \
DlPointMode::kPoints) \
->RangeMultiplier(2) \
->Range(1024, 32768) \
->UseRealTime() \
@ -214,7 +217,7 @@ void BM_SaveLayer(benchmark::State& state,
BENCHMARK_CAPTURE(BM_DrawPoints, Lines/BACKEND, \
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
DlPointMode::kLines) \
DlPointMode::kLines) \
->RangeMultiplier(2) \
->Range(1024, 32768) \
->UseRealTime() \
@ -223,7 +226,7 @@ void BM_SaveLayer(benchmark::State& state,
BENCHMARK_CAPTURE(BM_DrawPoints, Polygon/BACKEND, \
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
DlPointMode::kPolygon) \
DlPointMode::kPolygon) \
->RangeMultiplier(2) \
->Range(1024, 32768) \
->UseRealTime() \
@ -443,7 +446,7 @@ void BM_SaveLayer(benchmark::State& state,
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
true, \
SkPath::Verb::kLine_Verb) \
PathVerb::kLine) \
->RangeMultiplier(2) \
->Range(1, 32) \
->UseRealTime() \
@ -453,7 +456,7 @@ void BM_SaveLayer(benchmark::State& state,
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
true, \
SkPath::Verb::kQuad_Verb) \
PathVerb::kQuad) \
->RangeMultiplier(2) \
->Range(1, 32) \
->UseRealTime() \
@ -463,7 +466,7 @@ void BM_SaveLayer(benchmark::State& state,
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
true, \
SkPath::Verb::kConic_Verb) \
PathVerb::kConic) \
->RangeMultiplier(2) \
->Range(1, 32) \
->UseRealTime() \
@ -473,7 +476,7 @@ void BM_SaveLayer(benchmark::State& state,
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
true, \
SkPath::Verb::kCubic_Verb) \
PathVerb::kCubic) \
->RangeMultiplier(2) \
->Range(1, 32) \
->UseRealTime() \
@ -483,7 +486,7 @@ void BM_SaveLayer(benchmark::State& state,
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
false, \
SkPath::Verb::kLine_Verb) \
PathVerb::kLine) \
->RangeMultiplier(2) \
->Range(1, 32) \
->UseRealTime() \
@ -493,7 +496,7 @@ void BM_SaveLayer(benchmark::State& state,
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
false, \
SkPath::Verb::kQuad_Verb) \
PathVerb::kQuad) \
->RangeMultiplier(2) \
->Range(1, 32) \
->UseRealTime() \
@ -503,7 +506,7 @@ void BM_SaveLayer(benchmark::State& state,
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
false, \
SkPath::Verb::kConic_Verb) \
PathVerb::kConic) \
->RangeMultiplier(2) \
->Range(1, 32) \
->UseRealTime() \
@ -513,7 +516,7 @@ void BM_SaveLayer(benchmark::State& state,
BackendType::k##BACKEND##Backend, \
ATTRIBUTES, \
false, \
SkPath::Verb::kCubic_Verb) \
PathVerb::kCubic) \
->RangeMultiplier(2) \
->Range(1, 32) \
->UseRealTime() \

View File

@ -145,7 +145,7 @@ static void BM_DisplayListBuilderWithGlobalSaveLayer(
DisplayListBuilder builder(prepare_rtree);
builder.Scale(3.5, 3.5);
builder.Translate(10.3, 6.9);
builder.SaveLayer(nullptr, nullptr);
builder.SaveLayer(std::nullopt, nullptr);
builder.Translate(45.3, 27.9);
DlOpReceiver& receiver = DisplayListBuilderBenchmarkAccessor(builder);
for (auto& group : allRenderingOps) {
@ -169,7 +169,7 @@ static void BM_DisplayListBuilderWithSaveLayer(
for (auto& group : allRenderingOps) {
for (size_t i = 0; i < group.variants.size(); i++) {
auto& invocation = group.variants[i];
builder.SaveLayer(nullptr, nullptr);
builder.SaveLayer(std::nullopt, nullptr);
invocation.Invoke(receiver);
builder.Restore();
}

View File

@ -531,9 +531,9 @@ void DisplayListGLComplexityCalculator::GLHelper::drawImage(
// If we don't need to upload, then the cost scales linearly with the
// length of the image. If it needs uploading, the cost scales linearly
// with the square of the area (!!!).
SkISize dimensions = image->dimensions();
unsigned int length = (dimensions.width() + dimensions.height()) / 2;
unsigned int area = dimensions.width() * dimensions.height();
DlISize dimensions = image->GetSize();
unsigned int length = (dimensions.width + dimensions.height) / 2;
unsigned int area = dimensions.Area();
// m = 1/13
// c = 0
@ -561,7 +561,7 @@ void DisplayListGLComplexityCalculator::GLHelper::drawImage(
}
void DisplayListGLComplexityCalculator::GLHelper::ImageRect(
const SkISize& size,
const DlISize& size,
bool texture_backed,
bool render_with_attributes,
bool enforce_src_edges) {
@ -579,12 +579,12 @@ void DisplayListGLComplexityCalculator::GLHelper::ImageRect(
unsigned int complexity;
if (!texture_backed || (texture_backed && render_with_attributes &&
enforce_src_edges && IsAntiAliased())) {
unsigned int area = size.width() * size.height();
unsigned int area = size.Area();
// m = 1/4000
// c = 5
complexity = (area + 20000) / 10;
} else {
unsigned int length = (size.width() + size.height()) / 2;
unsigned int length = (size.width + size.height) / 2;
// There's a little bit of spread here but the numbers are pretty large
// anyway.
//
@ -606,8 +606,8 @@ void DisplayListGLComplexityCalculator::GLHelper::drawImageNine(
return;
}
SkISize dimensions = image->dimensions();
unsigned int area = dimensions.width() * dimensions.height();
DlISize dimensions = image->GetSize();
unsigned int area = dimensions.Area();
// m = 1/3600
// c = 3

View File

@ -85,7 +85,7 @@ class DisplayListGLComplexityCalculator
DlScalar dpr) override;
protected:
void ImageRect(const SkISize& size,
void ImageRect(const DlISize& size,
bool texture_backed,
bool render_with_attributes,
bool enforce_src_edges) override;

View File

@ -104,7 +104,7 @@ class ComplexityCalculatorHelper
void setInvertColors(bool invert) override {}
void setStrokeCap(DlStrokeCap cap) override {}
void setStrokeJoin(DlStrokeJoin join) override {}
void setStrokeMiter(SkScalar limit) override {}
void setStrokeMiter(DlScalar limit) override {}
void setColor(DlColor color) override {}
void setBlendMode(DlBlendMode mode) override {}
void setColorSource(const DlColorSource* source) override {}
@ -122,7 +122,7 @@ class ComplexityCalculatorHelper
current_paint_.setDrawStyle(style);
}
void setStrokeWidth(SkScalar width) override {
void setStrokeWidth(DlScalar width) override {
current_paint_.setStrokeWidth(width);
}
@ -153,7 +153,7 @@ class ComplexityCalculatorHelper
if (IsComplex()) {
return;
}
ImageRect(image->dimensions(), image->isTextureBacked(),
ImageRect(image->GetBounds().GetSize(), image->isTextureBacked(),
render_with_attributes,
constraint == DlSrcRectConstraint::kStrict);
}
@ -173,7 +173,7 @@ class ComplexityCalculatorHelper
// This API just does a series of drawImage calls from the atlas
// This is equivalent to calling drawImageRect lots of times
for (int i = 0; i < count; i++) {
ImageRect(SkISize::Make(tex[i].GetWidth(), tex[i].GetHeight()), true,
ImageRect(DlIRect::RoundOut(tex[i]).GetSize(), true,
render_with_attributes, true);
}
}
@ -220,32 +220,30 @@ class ComplexityCalculatorHelper
unsigned int quad_verb_cost,
unsigned int conic_verb_cost,
unsigned int cubic_verb_cost) {
const SkPath& path = dl_path.GetSkPath();
int verb_count = path.countVerbs();
std::vector<uint8_t> verbs(verb_count);
path.getVerbs(verbs.data(), verbs.size());
const impeller::Path& path = dl_path.GetPath();
unsigned int complexity = 0;
for (int i = 0; i < verb_count; i++) {
switch (verbs[i]) {
case SkPath::Verb::kLine_Verb:
for (auto it = path.begin(), end = path.end(); it != end; ++it) {
switch (it.type()) {
case impeller::Path::ComponentType::kLinear:
complexity += line_verb_cost;
break;
case SkPath::Verb::kQuad_Verb:
case impeller::Path::ComponentType::kQuadratic:
complexity += quad_verb_cost;
break;
case SkPath::Verb::kConic_Verb:
case impeller::Path::ComponentType::kConic:
complexity += conic_verb_cost;
break;
case SkPath::Verb::kCubic_Verb:
case impeller::Path::ComponentType::kCubic:
complexity += cubic_verb_cost;
break;
case impeller::Path::ComponentType::kContour:
break;
}
}
return complexity;
}
virtual void ImageRect(const SkISize& size,
virtual void ImageRect(const DlISize& size,
bool texture_backed,
bool render_with_attributes,
bool enforce_src_edges) = 0;

View File

@ -481,8 +481,8 @@ void DisplayListMetalComplexityCalculator::MetalHelper::drawImage(
// If we don't need to upload, then the cost scales linearly with the
// area of the image. If it needs uploading, the cost scales linearly
// with the square of the area (!!!).
SkISize dimensions = image->dimensions();
unsigned int area = dimensions.width() * dimensions.height();
DlISize dimensions = image->GetSize();
unsigned int area = dimensions.Area();
// m = 1/17000
// c = 3
@ -502,7 +502,7 @@ void DisplayListMetalComplexityCalculator::MetalHelper::drawImage(
}
void DisplayListMetalComplexityCalculator::MetalHelper::ImageRect(
const SkISize& size,
const DlISize& size,
bool texture_backed,
bool render_with_attributes,
bool enforce_src_edges) {
@ -513,7 +513,7 @@ void DisplayListMetalComplexityCalculator::MetalHelper::ImageRect(
//
// Within each group, they all perform within a few % of each other *except*
// when we have a strict constraint and anti-aliasing enabled.
unsigned int area = size.width() * size.height();
unsigned int area = size.Area();
// These values were worked out by creating a straight line graph (y=mx+c)
// approximately matching the measured data, normalising the data so that
@ -554,8 +554,8 @@ void DisplayListMetalComplexityCalculator::MetalHelper::drawImageNine(
}
// Whether uploading or not, the performance is comparable across all
// variations.
SkISize dimensions = image->dimensions();
unsigned int area = dimensions.width() * dimensions.height();
DlISize dimensions = image->GetSize();
unsigned int area = dimensions.Area();
// m = 1/8000
// c = 3

View File

@ -85,7 +85,7 @@ class DisplayListMetalComplexityCalculator
DlScalar dpr) override;
protected:
void ImageRect(const SkISize& size,
void ImageRect(const DlISize& size,
bool texture_backed,
bool render_with_attributes,
bool enforce_src_edges) override;

View File

@ -11,10 +11,6 @@
#include "flutter/display_list/testing/dl_test_snippets.h"
#include "flutter/testing/testing.h"
#include "third_party/skia/include/core/SkBitmap.h"
#include "third_party/skia/include/core/SkColor.h"
#include "third_party/skia/include/core/SkImage.h"
namespace flutter {
namespace testing {
@ -31,13 +27,13 @@ std::vector<DisplayListComplexityCalculator*> AccumulatorCalculators() {
DisplayListGLComplexityCalculator::GetInstance()};
}
std::vector<SkPoint> GetTestPoints() {
std::vector<SkPoint> points;
points.push_back(SkPoint::Make(0, 0));
points.push_back(SkPoint::Make(10, 0));
points.push_back(SkPoint::Make(10, 10));
points.push_back(SkPoint::Make(20, 10));
points.push_back(SkPoint::Make(20, 20));
std::vector<DlPoint> GetTestPoints() {
std::vector<DlPoint> points;
points.emplace_back(0, 0);
points.emplace_back(10, 0);
points.emplace_back(10, 10);
points.emplace_back(20, 10);
points.emplace_back(20, 20);
return points;
}
@ -79,12 +75,11 @@ TEST(DisplayListComplexity, NestedDisplayList) {
TEST(DisplayListComplexity, AntiAliasing) {
DisplayListBuilder builder_no_aa;
builder_no_aa.DrawLine(SkPoint::Make(0, 0), SkPoint::Make(100, 100),
DlPaint());
builder_no_aa.DrawLine(DlPoint(0, 0), DlPoint(100, 100), DlPaint());
auto display_list_no_aa = builder_no_aa.Build();
DisplayListBuilder builder_aa;
builder_aa.DrawLine(SkPoint::Make(0, 0), SkPoint::Make(100, 100),
builder_aa.DrawLine(DlPoint(0, 0), DlPoint(100, 100),
DlPaint().setAntiAlias(true));
auto display_list_aa = builder_aa.Build();
@ -97,12 +92,12 @@ TEST(DisplayListComplexity, AntiAliasing) {
TEST(DisplayListComplexity, StrokeWidth) {
DisplayListBuilder builder_stroke_0;
builder_stroke_0.DrawLine(SkPoint::Make(0, 0), SkPoint::Make(100, 100),
builder_stroke_0.DrawLine(DlPoint(0, 0), DlPoint(100, 100),
DlPaint().setStrokeWidth(0.0f));
auto display_list_stroke_0 = builder_stroke_0.Build();
DisplayListBuilder builder_stroke_1;
builder_stroke_1.DrawLine(SkPoint::Make(0, 0), SkPoint::Make(100, 100),
builder_stroke_1.DrawLine(DlPoint(0, 0), DlPoint(100, 100),
DlPaint().setStrokeWidth(1.0f));
auto display_list_stroke_1 = builder_stroke_1.Build();
@ -115,12 +110,12 @@ TEST(DisplayListComplexity, StrokeWidth) {
TEST(DisplayListComplexity, Style) {
DisplayListBuilder builder_filled;
builder_filled.DrawRect(SkRect::MakeXYWH(10, 10, 80, 80),
builder_filled.DrawRect(DlRect::MakeXYWH(10, 10, 80, 80),
DlPaint().setDrawStyle(DlDrawStyle::kFill));
auto display_list_filled = builder_filled.Build();
DisplayListBuilder builder_stroked;
builder_stroked.DrawRect(SkRect::MakeXYWH(10, 10, 80, 80),
builder_stroked.DrawRect(DlRect::MakeXYWH(10, 10, 80, 80),
DlPaint().setDrawStyle(DlDrawStyle::kStroke));
auto display_list_stroked = builder_stroked.Build();
@ -133,7 +128,7 @@ TEST(DisplayListComplexity, Style) {
TEST(DisplayListComplexity, SaveLayers) {
DisplayListBuilder builder;
builder.SaveLayer(nullptr, nullptr);
builder.SaveLayer(std::nullopt, nullptr);
auto display_list = builder.Build();
auto calculators = AccumulatorCalculators();
@ -144,35 +139,35 @@ TEST(DisplayListComplexity, SaveLayers) {
TEST(DisplayListComplexity, DrawPath) {
DisplayListBuilder builder_line;
SkPath line_path;
line_path.moveTo(SkPoint::Make(0, 0));
line_path.lineTo(SkPoint::Make(10, 10));
line_path.close();
builder_line.DrawPath(line_path, DlPaint());
DlPathBuilder line_path_builder;
line_path_builder.MoveTo(DlPoint(0, 0));
line_path_builder.LineTo(DlPoint(10, 10));
line_path_builder.Close();
builder_line.DrawPath(DlPath(line_path_builder), DlPaint());
auto display_list_line = builder_line.Build();
DisplayListBuilder builder_quad;
SkPath quad_path;
quad_path.moveTo(SkPoint::Make(0, 0));
quad_path.quadTo(SkPoint::Make(10, 10), SkPoint::Make(10, 20));
quad_path.close();
builder_quad.DrawPath(quad_path, DlPaint());
DlPathBuilder quad_path_builder;
quad_path_builder.MoveTo(DlPoint(0, 0));
quad_path_builder.QuadraticCurveTo(DlPoint(10, 10), DlPoint(10, 20));
quad_path_builder.Close();
builder_quad.DrawPath(DlPath(quad_path_builder), DlPaint());
auto display_list_quad = builder_quad.Build();
DisplayListBuilder builder_conic;
SkPath conic_path;
conic_path.moveTo(SkPoint::Make(0, 0));
conic_path.conicTo(SkPoint::Make(10, 10), SkPoint::Make(10, 20), 1.5f);
conic_path.close();
builder_conic.DrawPath(conic_path, DlPaint());
DlPathBuilder conic_path_builder;
conic_path_builder.MoveTo(DlPoint(0, 0));
conic_path_builder.ConicCurveTo(DlPoint(10, 10), DlPoint(10, 20), 1.5f);
conic_path_builder.Close();
builder_conic.DrawPath(DlPath(conic_path_builder), DlPaint());
auto display_list_conic = builder_conic.Build();
DisplayListBuilder builder_cubic;
SkPath cubic_path;
cubic_path.moveTo(SkPoint::Make(0, 0));
cubic_path.cubicTo(SkPoint::Make(10, 10), SkPoint::Make(10, 20),
SkPoint::Make(20, 20));
builder_cubic.DrawPath(cubic_path, DlPaint());
DlPathBuilder cubic_path_builder;
cubic_path_builder.MoveTo(DlPoint(0, 0));
cubic_path_builder.CubicCurveTo(DlPoint(10, 10), DlPoint(10, 20),
DlPoint(20, 20));
builder_cubic.DrawPath(DlPath(cubic_path_builder), DlPaint());
auto display_list_cubic = builder_cubic.Build();
auto calculators = AccumulatorCalculators();
@ -186,37 +181,39 @@ TEST(DisplayListComplexity, DrawPath) {
TEST(DisplayListComplexity, DrawShadow) {
DisplayListBuilder builder_line;
SkPath line_path;
line_path.moveTo(SkPoint::Make(0, 0));
line_path.lineTo(SkPoint::Make(10, 10));
line_path.close();
builder_line.DrawShadow(line_path, DlColor(SK_ColorRED), 10.0f, false, 1.0f);
DlPathBuilder line_path_builder;
line_path_builder.MoveTo(DlPoint(0, 0));
line_path_builder.LineTo(DlPoint(10, 10));
line_path_builder.Close();
builder_line.DrawShadow(DlPath(line_path_builder), DlColor(SK_ColorRED),
10.0f, false, 1.0f);
auto display_list_line = builder_line.Build();
DisplayListBuilder builder_quad;
SkPath quad_path;
quad_path.moveTo(SkPoint::Make(0, 0));
quad_path.quadTo(SkPoint::Make(10, 10), SkPoint::Make(10, 20));
quad_path.close();
builder_quad.DrawShadow(quad_path, DlColor(SK_ColorRED), 10.0f, false, 1.0f);
DlPathBuilder quad_path_builder;
quad_path_builder.MoveTo(DlPoint(0, 0));
quad_path_builder.QuadraticCurveTo(DlPoint(10, 10), DlPoint(10, 20));
quad_path_builder.Close();
builder_quad.DrawShadow(DlPath(quad_path_builder), DlColor(SK_ColorRED),
10.0f, false, 1.0f);
auto display_list_quad = builder_quad.Build();
DisplayListBuilder builder_conic;
SkPath conic_path;
conic_path.moveTo(SkPoint::Make(0, 0));
conic_path.conicTo(SkPoint::Make(10, 10), SkPoint::Make(10, 20), 1.5f);
conic_path.close();
builder_conic.DrawShadow(conic_path, DlColor(SK_ColorRED), 10.0f, false,
1.0f);
DlPathBuilder conic_path_builder;
conic_path_builder.MoveTo(DlPoint(0, 0));
conic_path_builder.ConicCurveTo(DlPoint(10, 10), DlPoint(10, 20), 1.5f);
conic_path_builder.Close();
builder_conic.DrawShadow(DlPath(conic_path_builder), DlColor(SK_ColorRED),
10.0f, false, 1.0f);
auto display_list_conic = builder_conic.Build();
DisplayListBuilder builder_cubic;
SkPath cubic_path;
cubic_path.moveTo(SkPoint::Make(0, 0));
cubic_path.cubicTo(SkPoint::Make(10, 10), SkPoint::Make(10, 20),
SkPoint::Make(20, 20));
builder_cubic.DrawShadow(cubic_path, DlColor(SK_ColorRED), 10.0f, false,
1.0f);
DlPathBuilder cubic_path_builder;
cubic_path_builder.MoveTo(DlPoint(0, 0));
cubic_path_builder.CubicCurveTo(DlPoint(10, 10), DlPoint(10, 20),
DlPoint(20, 20));
builder_cubic.DrawShadow(DlPath(cubic_path_builder), DlColor(SK_ColorRED),
10.0f, false, 1.0f);
auto display_list_cubic = builder_cubic.Build();
auto calculators = AccumulatorCalculators();
@ -230,7 +227,7 @@ TEST(DisplayListComplexity, DrawShadow) {
TEST(DisplayListComplexity, DrawOval) {
DisplayListBuilder builder;
builder.DrawOval(SkRect::MakeXYWH(10, 10, 100, 80), DlPaint());
builder.DrawOval(DlRect::MakeXYWH(10, 10, 100, 80), DlPaint());
auto display_list = builder.Build();
auto calculators = AccumulatorCalculators();
@ -241,7 +238,7 @@ TEST(DisplayListComplexity, DrawOval) {
TEST(DisplayListComplexity, DrawCircle) {
DisplayListBuilder builder;
builder.DrawCircle(SkPoint::Make(50, 50), 10.0f, DlPaint());
builder.DrawCircle(DlPoint(50, 50), 10.0f, DlPaint());
auto display_list = builder.Build();
auto calculators = AccumulatorCalculators();
@ -250,10 +247,10 @@ TEST(DisplayListComplexity, DrawCircle) {
}
}
TEST(DisplayListComplexity, DrawRRect) {
TEST(DisplayListComplexity, DrawRoundRect) {
DisplayListBuilder builder;
builder.DrawRRect(
SkRRect::MakeRectXY(SkRect::MakeXYWH(10, 10, 80, 80), 2.0f, 3.0f),
builder.DrawRoundRect(
DlRoundRect::MakeRectXY(DlRect::MakeXYWH(10, 10, 80, 80), 2.0f, 3.0f),
DlPaint());
auto display_list = builder.Build();
@ -263,13 +260,13 @@ TEST(DisplayListComplexity, DrawRRect) {
}
}
TEST(DisplayListComplexity, DrawDRRect) {
TEST(DisplayListComplexity, DrawDiffRoundRect) {
DisplayListBuilder builder;
SkRRect outer =
SkRRect::MakeRectXY(SkRect::MakeXYWH(10, 10, 80, 80), 2.0f, 3.0f);
SkRRect inner =
SkRRect::MakeRectXY(SkRect::MakeXYWH(15, 15, 70, 70), 1.5f, 1.5f);
builder.DrawDRRect(outer, inner, DlPaint());
DlRoundRect outer =
DlRoundRect::MakeRectXY(DlRect::MakeXYWH(10, 10, 80, 80), 2.0f, 3.0f);
DlRoundRect inner =
DlRoundRect::MakeRectXY(DlRect::MakeXYWH(15, 15, 70, 70), 1.5f, 1.5f);
builder.DrawDiffRoundRect(outer, inner, DlPaint());
auto display_list = builder.Build();
auto calculators = AccumulatorCalculators();
@ -280,7 +277,7 @@ TEST(DisplayListComplexity, DrawDRRect) {
TEST(DisplayListComplexity, DrawArc) {
DisplayListBuilder builder;
builder.DrawArc(SkRect::MakeXYWH(10, 10, 100, 80), 0.0f, 10.0f, true,
builder.DrawArc(DlRect::MakeXYWH(10, 10, 100, 80), 0.0f, 10.0f, true,
DlPaint());
auto display_list = builder.Build();
@ -293,7 +290,7 @@ TEST(DisplayListComplexity, DrawArc) {
TEST(DisplayListComplexity, DrawVertices) {
auto points = GetTestPoints();
auto vertices = DlVertices::Make(DlVertexMode::kTriangles, points.size(),
ToDlPoints(points.data()), nullptr, nullptr);
points.data(), nullptr, nullptr);
DisplayListBuilder builder;
builder.DrawVertices(vertices, DlBlendMode::kSrc, DlPaint());
auto display_list = builder.Build();
@ -305,8 +302,8 @@ TEST(DisplayListComplexity, DrawVertices) {
}
TEST(DisplayListComplexity, DrawTextBlob) {
auto text_blob = SkTextBlob::MakeFromString(
"The quick brown fox jumps over the lazy dog.", CreateTestFontOfSize(20));
auto text_blob =
GetTestTextBlob("The quick brown fox jumps over the lazy dog.", 20.0f);
DisplayListBuilder builder;
builder.DrawTextBlob(text_blob, 0.0f, 0.0f, DlPaint());
@ -351,16 +348,11 @@ TEST(DisplayListComplexity, DrawPoints) {
}
TEST(DisplayListComplexity, DrawImage) {
SkImageInfo info =
SkImageInfo::Make(50, 50, SkColorType::kRGBA_8888_SkColorType,
SkAlphaType::kPremul_SkAlphaType);
SkBitmap bitmap;
bitmap.allocPixels(info, 0);
auto image = SkImages::RasterFromBitmap(bitmap);
auto image = MakeTestImage(50, 50, DlColor::kBlue().withAlphaF(0.5));
DisplayListBuilder builder;
builder.DrawImage(DlImage::Make(image), SkPoint::Make(0, 0),
DlImageSampling::kNearestNeighbor, nullptr);
builder.DrawImage(image, DlPoint(0, 0), DlImageSampling::kNearestNeighbor,
nullptr);
auto display_list = builder.Build();
auto calculators = AccumulatorCalculators();
@ -370,19 +362,13 @@ TEST(DisplayListComplexity, DrawImage) {
}
TEST(DisplayListComplexity, DrawImageNine) {
SkImageInfo info =
SkImageInfo::Make(50, 50, SkColorType::kRGBA_8888_SkColorType,
SkAlphaType::kPremul_SkAlphaType);
SkBitmap bitmap;
bitmap.allocPixels(info, 0);
auto image = SkImages::RasterFromBitmap(bitmap);
auto image = MakeTestImage(50, 50, DlColor::kBlue().withAlphaF(0.5));
SkIRect center = SkIRect::MakeXYWH(5, 5, 20, 20);
SkRect dest = SkRect::MakeXYWH(0, 0, 50, 50);
DlIRect center = DlIRect::MakeXYWH(5, 5, 20, 20);
DlRect dest = DlRect::MakeXYWH(0, 0, 50, 50);
DisplayListBuilder builder;
builder.DrawImageNine(DlImage::Make(image), center, dest,
DlFilterMode::kNearest, nullptr);
builder.DrawImageNine(image, center, dest, DlFilterMode::kNearest, nullptr);
auto display_list = builder.Build();
auto calculators = AccumulatorCalculators();
@ -392,19 +378,14 @@ TEST(DisplayListComplexity, DrawImageNine) {
}
TEST(DisplayListComplexity, DrawImageRect) {
SkImageInfo info =
SkImageInfo::Make(50, 50, SkColorType::kRGBA_8888_SkColorType,
SkAlphaType::kPremul_SkAlphaType);
SkBitmap bitmap;
bitmap.allocPixels(info, 0);
auto image = SkImages::RasterFromBitmap(bitmap);
auto image = MakeTestImage(50, 50, DlColor::kBlue().withAlphaF(0.5));
SkRect src = SkRect::MakeXYWH(0, 0, 50, 50);
SkRect dest = SkRect::MakeXYWH(0, 0, 50, 50);
DlRect src = DlRect::MakeXYWH(0, 0, 50, 50);
DlRect dest = DlRect::MakeXYWH(0, 0, 50, 50);
DisplayListBuilder builder;
builder.DrawImageRect(DlImage::Make(image), src, dest,
DlImageSampling::kNearestNeighbor, nullptr);
builder.DrawImageRect(image, src, dest, DlImageSampling::kNearestNeighbor,
nullptr);
auto display_list = builder.Build();
auto calculators = AccumulatorCalculators();
@ -414,12 +395,7 @@ TEST(DisplayListComplexity, DrawImageRect) {
}
TEST(DisplayListComplexity, DrawAtlas) {
SkImageInfo info =
SkImageInfo::Make(50, 50, SkColorType::kRGBA_8888_SkColorType,
SkAlphaType::kPremul_SkAlphaType);
SkBitmap bitmap;
bitmap.allocPixels(info, 0);
auto image = SkImages::RasterFromBitmap(bitmap);
auto image = MakeTestImage(50, 50, DlColor::kBlue().withAlphaF(0.5));
std::vector<DlRect> rects;
std::vector<DlRSTransform> xforms;
@ -429,8 +405,8 @@ TEST(DisplayListComplexity, DrawAtlas) {
}
DisplayListBuilder builder;
builder.DrawAtlas(DlImage::Make(image), xforms.data(), rects.data(), nullptr,
10, DlBlendMode::kSrc, DlImageSampling::kNearestNeighbor,
builder.DrawAtlas(image, xforms.data(), rects.data(), nullptr, 10,
DlBlendMode::kSrc, DlImageSampling::kNearestNeighbor,
nullptr, nullptr);
auto display_list = builder.Build();

View File

@ -149,8 +149,8 @@ DlISize DisplayListBuilder::GetBaseLayerDimensions() const {
}
SkImageInfo DisplayListBuilder::GetImageInfo() const {
SkISize size = GetBaseLayerSize();
return SkImageInfo::MakeUnknown(size.width(), size.height());
DlISize size = GetBaseLayerDimensions();
return SkImageInfo::MakeUnknown(size.width, size.height);
}
void DisplayListBuilder::onSetAntiAlias(bool aa) {
@ -1288,7 +1288,7 @@ void DisplayListBuilder::drawPoints(DlPointMode mode,
}
FML_DCHECK(count < DlOpReceiver::kMaxDrawPointsCount);
int bytes = count * sizeof(SkPoint);
int bytes = count * sizeof(DlPoint);
AccumulationRect accumulator;
for (size_t i = 0; i < count; i++) {
accumulator.accumulate(pts[i]);

View File

@ -84,6 +84,11 @@ class DlImage : public SkRefCnt {
///
virtual SkISize dimensions() const = 0;
//----------------------------------------------------------------------------
/// @return The dimensions of the pixel grid.
///
virtual DlISize GetSize() const = 0;
//----------------------------------------------------------------------------
/// @return The approximate byte size of the allocation of this image.
/// This takes into account details such as mip-mapping. The

View File

@ -47,6 +47,11 @@ SkISize DlImageSkia::dimensions() const {
return image_ ? image_->dimensions() : SkISize::MakeEmpty();
}
// |DlImage|
DlISize DlImageSkia::GetSize() const {
return image_ ? ToDlISize(image_->dimensions()) : DlISize();
}
// |DlImage|
size_t DlImageSkia::GetApproximateByteSize() const {
auto size = sizeof(*this);

View File

@ -35,6 +35,9 @@ class DlImageSkia final : public DlImage {
// |DlImage|
SkISize dimensions() const override;
// |DlImage|
DlISize GetSize() const override;
// |DlImage|
size_t GetApproximateByteSize() const override;

View File

@ -16,13 +16,16 @@ namespace testing {
class DlMetalSurfaceInstance : public DlSurfaceInstance {
public:
explicit DlMetalSurfaceInstance(std::unique_ptr<TestMetalSurface> metal_surface)
: metal_surface_(std::move(metal_surface)) {}
: metal_surface_(std::move(metal_surface)),
adapter_(metal_surface_->GetSurface()->getCanvas()) {}
~DlMetalSurfaceInstance() = default;
sk_sp<SkSurface> sk_surface() const override { return metal_surface_->GetSurface(); }
DlCanvas* GetCanvas() override { return &adapter_; }
private:
std::unique_ptr<TestMetalSurface> metal_surface_;
DlSkCanvasAdapter adapter_;
};
bool DlMetalSurfaceProvider::InitializeSurface(size_t width, size_t height, PixelFormat format) {

View File

@ -9,6 +9,7 @@
#include "third_party/skia/include/core/SkImage.h"
#include "third_party/skia/include/core/SkSurface.h"
#include "third_party/skia/include/encode/SkPngEncoder.h"
#include "third_party/skia/include/gpu/ganesh/GrDirectContext.h"
namespace flutter::testing {
@ -73,4 +74,15 @@ std::unique_ptr<DlSurfaceProvider> DlSurfaceProvider::CreateMetal() {
}
#endif
void DlSurfaceInstance::FlushSubmitCpuSync() {
auto surface = sk_surface();
if (!surface) {
return;
}
if (GrDirectContext* dContext =
GrAsDirectContext(surface->recordingContext())) {
dContext->flushAndSubmit(surface.get(), GrSyncCpu::kYes);
}
}
} // namespace flutter::testing

View File

@ -9,6 +9,7 @@
#include "flutter/display_list/display_list.h"
#include "flutter/display_list/image/dl_image.h"
#include "flutter/display_list/skia/dl_sk_canvas.h"
#include "flutter/fml/mapping.h"
#include "flutter/testing/testing.h"
@ -32,6 +33,8 @@ class DlSurfaceInstance {
virtual ~DlSurfaceInstance() = default;
virtual sk_sp<SkSurface> sk_surface() const = 0;
virtual DlCanvas* GetCanvas() = 0;
void FlushSubmitCpuSync();
int width() const { return sk_surface()->width(); }
int height() const { return sk_surface()->height(); }
@ -40,13 +43,15 @@ class DlSurfaceInstance {
class DlSurfaceInstanceBase : public DlSurfaceInstance {
public:
explicit DlSurfaceInstanceBase(sk_sp<SkSurface> surface)
: surface_(std::move(surface)) {}
: surface_(std::move(surface)), adapter_(surface_->getCanvas()) {}
~DlSurfaceInstanceBase() = default;
sk_sp<SkSurface> sk_surface() const override { return surface_; }
DlCanvas* GetCanvas() override { return &adapter_; }
private:
sk_sp<SkSurface> surface_;
DlSkCanvasAdapter adapter_;
};
class DlSurfaceProvider {

View File

@ -109,6 +109,13 @@ SkISize DlImageImpeller::dimensions() const {
return SkISize::Make(size.width, size.height);
}
// |DlImage|
flutter::DlISize DlImageImpeller::GetSize() const {
// texture |GetSize()| returns a 64-bit size, but we need a 32-bit size,
// so we need to convert to DlISize (the 32-bit variant) either way.
return texture_ ? flutter::DlISize(texture_->GetSize()) : flutter::DlISize();
}
// |DlImage|
size_t DlImageImpeller::GetApproximateByteSize() const {
auto size = sizeof(*this);

View File

@ -50,6 +50,9 @@ class DlImageImpeller final : public flutter::DlImage {
// |DlImage|
SkISize dimensions() const override;
// |DlImage|
flutter::DlISize GetSize() const override;
// |DlImage|
size_t GetApproximateByteSize() const override;

View File

@ -16,7 +16,6 @@
#include "impeller/geometry/point.h"
#include "impeller/geometry/rect.h"
#include "third_party/skia/include/core/SkColorType.h"
#include "third_party/skia/include/core/SkPath.h"
#include "third_party/skia/include/core/SkPoint.h"
#include "third_party/skia/include/core/SkRRect.h"
#include "third_party/skia/include/core/SkTextBlob.h"

View File

@ -76,6 +76,11 @@ SkISize DlDeferredImageGPUImpeller::dimensions() const {
return wrapper_->size();
}
// |DlImage|
DlISize DlDeferredImageGPUImpeller::GetSize() const {
return wrapper_ ? ToDlISize(wrapper_->size()) : DlISize();
}
// |DlImage|
size_t DlDeferredImageGPUImpeller::GetApproximateByteSize() const {
auto size = sizeof(DlDeferredImageGPUImpeller);

View File

@ -50,6 +50,9 @@ class DlDeferredImageGPUImpeller final : public DlImage {
// |DlImage|
SkISize dimensions() const override;
// |DlImage|
DlISize GetSize() const override;
// |DlImage|
size_t GetApproximateByteSize() const override;

View File

@ -89,6 +89,12 @@ SkISize DlDeferredImageGPUSkia::dimensions() const {
: SkISize::MakeEmpty();
}
// |DlImage|
DlISize DlDeferredImageGPUSkia::GetSize() const {
return image_wrapper_ ? ToDlISize(image_wrapper_->image_info().dimensions())
: DlISize();
}
// |DlImage|
size_t DlDeferredImageGPUSkia::GetApproximateByteSize() const {
return sizeof(*this) +

View File

@ -64,6 +64,9 @@ class DlDeferredImageGPUSkia final : public DlImage {
// |DlImage|
SkISize dimensions() const override;
// |DlImage|
DlISize GetSize() const override;
// |DlImage|
virtual size_t GetApproximateByteSize() const override;

View File

@ -56,6 +56,12 @@ SkISize DlImageGPU::dimensions() const {
return image ? image->dimensions() : SkISize::MakeEmpty();
}
// |DlImage|
DlISize DlImageGPU::GetSize() const {
const auto image = skia_image();
return image ? ToDlISize(image->dimensions()) : DlISize();
}
// |DlImage|
size_t DlImageGPU::GetApproximateByteSize() const {
auto size = sizeof(*this);

View File

@ -36,6 +36,9 @@ class DlImageGPU final : public DlImage {
// |DlImage|
SkISize dimensions() const override;
// |DlImage|
DlISize GetSize() const override;
// |DlImage|
virtual size_t GetApproximateByteSize() const override;

View File

@ -44,6 +44,7 @@ class MockDlImage : public DlImage {
MOCK_METHOD(bool, isTextureBacked, (), (const, override));
MOCK_METHOD(bool, isUIThreadSafe, (), (const, override));
MOCK_METHOD(SkISize, dimensions, (), (const, override));
MOCK_METHOD(DlISize, GetSize, (), (const, override));
MOCK_METHOD(size_t, GetApproximateByteSize, (), (const, override));
};