Flutter Engine
The Flutter Engine
aiks_blend_unittests.cc
Go to the documentation of this file.
1// Copyright 2013 The Flutter Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "flutter/impeller/aiks/aiks_unittests.h"
6
7#include "flutter/testing/testing.h"
12
13////////////////////////////////////////////////////////////////////////////////
14// This is for tests of Canvas that are interested the results of rendering
15// blends.
16////////////////////////////////////////////////////////////////////////////////
17
18namespace impeller {
19namespace testing {
20
21TEST_P(AiksTest, CanRenderAdvancedBlendColorFilterWithSaveLayer) {
22 Canvas canvas;
23
24 Rect layer_rect = Rect::MakeXYWH(0, 0, 500, 500);
25 canvas.ClipRect(layer_rect);
26
27 canvas.SaveLayer(
28 {
30 Color(0, 1, 0, 0.5)),
31 },
32 layer_rect);
33
35 canvas.DrawPaint({.color = Color::Black()});
36 canvas.DrawRect(Rect::MakeXYWH(100, 100, 300, 300),
37 {.color = Color::White()});
38 canvas.Restore();
39
40 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
41}
42
43TEST_P(AiksTest, BlendModeShouldCoverWholeScreen) {
44 Canvas canvas;
46
47 paint.color = Color::Red();
48 canvas.DrawPaint(paint);
49
50 paint.blend_mode = BlendMode::kSourceOver;
51 canvas.SaveLayer(paint);
52
53 paint.color = Color::White();
54 canvas.DrawRect(Rect::MakeXYWH(100, 100, 400, 400), paint);
55
56 paint.blend_mode = BlendMode::kSource;
57 canvas.SaveLayer(paint);
58
59 paint.color = Color::Blue();
60 canvas.DrawRect(Rect::MakeXYWH(200, 200, 200, 200), paint);
61
62 canvas.Restore();
63 canvas.Restore();
64
65 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
66}
67
68TEST_P(AiksTest, CanDrawPaintWithAdvancedBlend) {
69 Canvas canvas;
70 canvas.Scale(Vector2(0.2, 0.2));
71 canvas.DrawPaint({.color = Color::MediumTurquoise()});
72 canvas.DrawPaint({.color = Color::Color::OrangeRed().WithAlpha(0.5),
73 .blend_mode = BlendMode::kHue});
74 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
75}
76
77TEST_P(AiksTest, DrawPaintWithAdvancedBlendOverFilter) {
78 Paint filtered = {
79 .color = Color::Black(),
80 .mask_blur_descriptor =
83 .sigma = Sigma(60),
84 },
85 };
86
87 Canvas canvas;
88 canvas.DrawPaint({.color = Color::White()});
89 canvas.DrawCircle({300, 300}, 200, filtered);
90 canvas.DrawPaint({.color = Color::Green(), .blend_mode = BlendMode::kScreen});
91 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
92}
93
94TEST_P(AiksTest, DrawAdvancedBlendPartlyOffscreen) {
95 std::vector<Color> colors = {Color{0.9568, 0.2627, 0.2118, 1.0},
96 Color{0.1294, 0.5882, 0.9529, 1.0}};
97 std::vector<Scalar> stops = {0.0, 1.0};
98
99 Paint paint = {
100 .color_source = ColorSource::MakeLinearGradient(
101 {0, 0}, {100, 100}, std::move(colors), std::move(stops),
103 .blend_mode = BlendMode::kLighten,
104 };
105
106 Canvas canvas;
107 canvas.DrawPaint({.color = Color::Blue()});
108 canvas.Scale(Vector2(2, 2));
109 canvas.ClipRect(Rect::MakeLTRB(0, 0, 200, 200));
110 canvas.DrawCircle({100, 100}, 100, paint);
111 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
112}
113
114TEST_P(AiksTest, PaintBlendModeIsRespected) {
115 Paint paint;
116 Canvas canvas;
117 // Default is kSourceOver.
118 paint.color = Color(1, 0, 0, 0.5);
119 canvas.DrawCircle(Point(150, 200), 100, paint);
120 paint.color = Color(0, 1, 0, 0.5);
121 canvas.DrawCircle(Point(250, 200), 100, paint);
122
123 paint.blend_mode = BlendMode::kPlus;
124 paint.color = Color::Red();
125 canvas.DrawCircle(Point(450, 250), 100, paint);
126 paint.color = Color::Green();
127 canvas.DrawCircle(Point(550, 250), 100, paint);
128 paint.color = Color::Blue();
129 canvas.DrawCircle(Point(500, 150), 100, paint);
130 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
131}
132
133// Bug: https://github.com/flutter/flutter/issues/142549
134TEST_P(AiksTest, BlendModePlusAlphaWideGamut) {
135 EXPECT_EQ(GetContext()->GetCapabilities()->GetDefaultColorFormat(),
137 auto texture = CreateTextureForFixture("airplane.jpg",
138 /*enable_mipmapping=*/true);
139
140 Canvas canvas;
141 canvas.Scale(GetContentScale());
142 canvas.DrawPaint({.color = Color(0.9, 1.0, 0.9, 1.0)});
143 canvas.SaveLayer({});
144 Paint paint;
145 paint.blend_mode = BlendMode::kPlus;
146 paint.color = Color::Red();
147 canvas.DrawRect(Rect::MakeXYWH(100, 100, 400, 400), paint);
148 paint.color = Color::White();
149 canvas.DrawImageRect(
150 std::make_shared<Image>(texture), Rect::MakeSize(texture->GetSize()),
151 Rect::MakeXYWH(100, 100, 400, 400).Expand(-100, -100), paint);
152 canvas.Restore();
153 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
154}
155
156// Bug: https://github.com/flutter/flutter/issues/142549
157TEST_P(AiksTest, BlendModePlusAlphaColorFilterWideGamut) {
158 EXPECT_EQ(GetContext()->GetCapabilities()->GetDefaultColorFormat(),
160 auto texture = CreateTextureForFixture("airplane.jpg",
161 /*enable_mipmapping=*/true);
162
163 Canvas canvas;
164 canvas.Scale(GetContentScale());
165 canvas.DrawPaint({.color = Color(0.1, 0.2, 0.1, 1.0)});
166 canvas.SaveLayer({
167 .color_filter =
169 });
170 Paint paint;
171 paint.color = Color::Red();
172 canvas.DrawRect(Rect::MakeXYWH(100, 100, 400, 400), paint);
173 paint.color = Color::White();
174 canvas.DrawImageRect(
175 std::make_shared<Image>(texture), Rect::MakeSize(texture->GetSize()),
176 Rect::MakeXYWH(100, 100, 400, 400).Expand(-100, -100), paint);
177 canvas.Restore();
178 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
179}
180
181#define BLEND_MODE_TUPLE(blend_mode) {#blend_mode, BlendMode::k##blend_mode},
182
184 std::vector<const char*> blend_mode_names;
185 std::vector<BlendMode> blend_mode_values;
186};
187
189 std::vector<const char*> blend_mode_names;
190 std::vector<BlendMode> blend_mode_values;
191 {
192 const std::vector<std::tuple<const char*, BlendMode>> blends = {
194 assert(blends.size() ==
195 static_cast<size_t>(Entity::kLastAdvancedBlendMode) + 1);
196 for (const auto& [name, mode] : blends) {
197 blend_mode_names.push_back(name);
198 blend_mode_values.push_back(mode);
199 }
200 }
201
202 return {blend_mode_names, blend_mode_values};
203}
204
205TEST_P(AiksTest, ColorWheel) {
206 // Compare with https://fiddle.skia.org/c/@BlendModes
207
209
210 auto draw_color_wheel = [](Canvas& canvas) {
211 /// color_wheel_sampler: r=0 -> fuchsia, r=2pi/3 -> yellow, r=4pi/3 ->
212 /// cyan domain: r >= 0 (because modulo used is non euclidean)
213 auto color_wheel_sampler = [](Radians r) {
214 Scalar x = r.radians / k2Pi + 1;
215
216 // https://www.desmos.com/calculator/6nhjelyoaj
217 auto color_cycle = [](Scalar x) {
218 Scalar cycle = std::fmod(x, 6.0f);
219 return std::max(0.0f, std::min(1.0f, 2 - std::abs(2 - cycle)));
220 };
221 return Color(color_cycle(6 * x + 1), //
222 color_cycle(6 * x - 1), //
223 color_cycle(6 * x - 3), //
224 1);
225 };
226
227 Paint paint;
228 paint.blend_mode = BlendMode::kSourceOver;
229
230 // Draw a fancy color wheel for the backdrop.
231 // https://www.desmos.com/calculator/xw7kafthwd
232 const int max_dist = 900;
233 for (int i = 0; i <= 900; i++) {
234 Radians r(kPhi / k2Pi * i);
235 Scalar distance = r.radians / std::powf(4.12, 0.0026 * r.radians);
236 Scalar normalized_distance = static_cast<Scalar>(i) / max_dist;
237
238 paint.color =
239 color_wheel_sampler(r).WithAlpha(1.0f - normalized_distance);
240 Point position(distance * std::sin(r.radians),
241 -distance * std::cos(r.radians));
242
243 canvas.DrawCircle(position, 9 + normalized_distance * 3, paint);
244 }
245 };
246
247 std::shared_ptr<Image> color_wheel_image;
248 Matrix color_wheel_transform;
249
250 auto callback = [&](AiksContext& renderer) -> std::optional<Picture> {
251 // UI state.
252 static bool cache_the_wheel = true;
253 static int current_blend_index = 3;
254 static float dst_alpha = 1;
255 static float src_alpha = 1;
256 static Color color0 = Color::Red();
257 static Color color1 = Color::Green();
258 static Color color2 = Color::Blue();
259
260 if (AiksTest::ImGuiBegin("Controls", nullptr,
261 ImGuiWindowFlags_AlwaysAutoResize)) {
262 ImGui::Checkbox("Cache the wheel", &cache_the_wheel);
263 ImGui::ListBox("Blending mode", &current_blend_index,
264 blend_modes.blend_mode_names.data(),
265 blend_modes.blend_mode_names.size());
266 ImGui::SliderFloat("Source alpha", &src_alpha, 0, 1);
267 ImGui::ColorEdit4("Color A", reinterpret_cast<float*>(&color0));
268 ImGui::ColorEdit4("Color B", reinterpret_cast<float*>(&color1));
269 ImGui::ColorEdit4("Color C", reinterpret_cast<float*>(&color2));
270 ImGui::SliderFloat("Destination alpha", &dst_alpha, 0, 1);
271 ImGui::End();
272 }
273
274 static Point content_scale;
275 Point new_content_scale = GetContentScale();
276
277 if (!cache_the_wheel || new_content_scale != content_scale) {
278 content_scale = new_content_scale;
279
280 // Render the color wheel to an image.
281
282 Canvas canvas;
283 canvas.Scale(content_scale);
284
285 canvas.Translate(Vector2(500, 400));
286 canvas.Scale(Vector2(3, 3));
287
288 draw_color_wheel(canvas);
289 auto color_wheel_picture = canvas.EndRecordingAsPicture();
290 auto snapshot = color_wheel_picture.Snapshot(renderer);
291 if (!snapshot.has_value() || !snapshot->texture) {
292 return std::nullopt;
293 }
294 color_wheel_image = std::make_shared<Image>(snapshot->texture);
295 color_wheel_transform = snapshot->transform;
296 }
297
298 Canvas canvas;
299
300 // Blit the color wheel backdrop to the screen with managed alpha.
301 canvas.SaveLayer({.color = Color::White().WithAlpha(dst_alpha),
302 .blend_mode = BlendMode::kSource});
303 {
304 canvas.DrawPaint({.color = Color::White()});
305
306 canvas.Save();
307 canvas.Transform(color_wheel_transform);
308 canvas.DrawImage(color_wheel_image, Point(), Paint());
309 canvas.Restore();
310 }
311 canvas.Restore();
312
313 canvas.Scale(content_scale);
314 canvas.Translate(Vector2(500, 400));
315 canvas.Scale(Vector2(3, 3));
316
317 // Draw 3 circles to a subpass and blend it in.
318 canvas.SaveLayer(
319 {.color = Color::White().WithAlpha(src_alpha),
320 .blend_mode = blend_modes.blend_mode_values[current_blend_index]});
321 {
322 Paint paint;
323 paint.blend_mode = BlendMode::kPlus;
324 const Scalar x = std::sin(k2Pi / 3);
325 const Scalar y = -std::cos(k2Pi / 3);
326 paint.color = color0;
327 canvas.DrawCircle(Point(-x, y) * 45, 65, paint);
328 paint.color = color1;
329 canvas.DrawCircle(Point(0, -1) * 45, 65, paint);
330 paint.color = color2;
331 canvas.DrawCircle(Point(x, y) * 45, 65, paint);
332 }
333 canvas.Restore();
334
335 return canvas.EndRecordingAsPicture();
336 };
337
338 ASSERT_TRUE(OpenPlaygroundHere(callback));
339}
340
341TEST_P(AiksTest, ForegroundBlendSubpassCollapseOptimization) {
342 Canvas canvas;
343
344 canvas.SaveLayer({
345 .color_filter =
347 });
348
349 canvas.Translate({500, 300, 0});
350 canvas.Rotate(Radians(2 * kPi / 3));
351 canvas.DrawRect(Rect::MakeXYWH(100, 100, 200, 200), {.color = Color::Blue()});
352
353 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
354}
355
356TEST_P(AiksTest, ClearBlend) {
357 Canvas canvas;
358 Paint white;
359 white.color = Color::Blue();
360 canvas.DrawRect(Rect::MakeXYWH(0, 0, 600.0, 600.0), white);
361
362 Paint clear;
363 clear.blend_mode = BlendMode::kClear;
364
365 canvas.DrawCircle(Point::MakeXY(300.0, 300.0), 200.0, clear);
366}
367
368static Picture BlendModeTest(Vector2 content_scale,
369 BlendMode blend_mode,
370 const std::shared_ptr<Image>& src_image,
371 const std::shared_ptr<Image>& dst_image,
372 Scalar src_alpha) {
373 if (AiksTest::ImGuiBegin("Controls", nullptr,
374 ImGuiWindowFlags_AlwaysAutoResize)) {
375 ImGui::SliderFloat("Source alpha", &src_alpha, 0, 1);
376 ImGui::End();
377 }
378
379 Color destination_color = Color::CornflowerBlue().WithAlpha(0.75);
380 auto source_colors = std::vector<Color>({Color::White().WithAlpha(0.75),
382 Color::Black().WithAlpha(0.75)});
383
384 Canvas canvas;
385 canvas.DrawPaint({.color = Color::Black()});
386 // TODO(bdero): Why does this cause the left image to double scale on high DPI
387 // displays.
388 // canvas.Scale(content_scale);
389
390 //----------------------------------------------------------------------------
391 /// 1. Save layer blending (top squares).
392 ///
393
394 canvas.Save();
395 for (const auto& color : source_colors) {
396 canvas.Save();
397 {
398 canvas.ClipRect(Rect::MakeXYWH(25, 25, 100, 100));
399 // Perform the blend in a SaveLayer so that the initial backdrop color is
400 // fully transparent black. SourceOver blend the result onto the parent
401 // pass.
402 canvas.SaveLayer({});
403 {
404 canvas.DrawPaint({.color = destination_color});
405 // Draw the source color in an offscreen pass and blend it to the parent
406 // pass.
407 canvas.SaveLayer({.blend_mode = blend_mode});
408 { //
409 canvas.DrawRect(Rect::MakeXYWH(25, 25, 100, 100), {.color = color});
410 }
411 canvas.Restore();
412 }
413 canvas.Restore();
414 }
415 canvas.Restore();
416 canvas.Translate(Vector2(100, 0));
417 }
418 canvas.RestoreToCount(0);
419
420 //----------------------------------------------------------------------------
421 /// 2. CPU blend modes (bottom squares).
422 ///
423
424 canvas.Save();
425 canvas.Translate({0, 100});
426 // Perform the blend in a SaveLayer so that the initial backdrop color is
427 // fully transparent black. SourceOver blend the result onto the parent pass.
428 canvas.SaveLayer({});
429 for (const auto& color : source_colors) {
430 // Simply write the CPU blended color to the pass.
431 canvas.DrawRect(Rect::MakeXYWH(25, 25, 100, 100),
432 {.color = destination_color.Blend(color, blend_mode),
433 .blend_mode = BlendMode::kSourceOver});
434 canvas.Translate(Vector2(100, 0));
435 }
436 canvas.Restore();
437 canvas.Restore();
438
439 //----------------------------------------------------------------------------
440 /// 3. Image blending (bottom images).
441 ///
442 /// Compare these results with the images in the Flutter blend mode
443 /// documentation: https://api.flutter.dev/flutter/dart-ui/BlendMode.html
444 ///
445
446 canvas.Translate({0, 250});
447
448 // Draw grid behind the images.
449 canvas.DrawRect(Rect::MakeLTRB(0, 0, 800, 400),
450 {.color = Color::MakeRGBA8(41, 41, 41, 255)});
451 Paint square_paint = {.color = Color::MakeRGBA8(15, 15, 15, 255)};
452 for (int y = 0; y < 400 / 8; y++) {
453 for (int x = 0; x < 800 / 16; x++) {
454 canvas.DrawRect(Rect::MakeXYWH(x * 16 + (y % 2) * 8, y * 8, 8, 8),
455 square_paint);
456 }
457 }
458
459 // Uploaded image source (left image).
460 canvas.Save();
461 canvas.SaveLayer({.blend_mode = BlendMode::kSourceOver});
462 {
463 canvas.DrawImage(dst_image, {0, 0},
464 {
465 .blend_mode = BlendMode::kSourceOver,
466 });
467 canvas.DrawImage(src_image, {0, 0},
468 {
469 .color = Color::White().WithAlpha(src_alpha),
470 .blend_mode = blend_mode,
471 });
472 }
473 canvas.Restore();
474 canvas.Restore();
475
476 // Rendered image source (right image).
477 canvas.Save();
478 canvas.SaveLayer({.blend_mode = BlendMode::kSourceOver});
479 {
480 canvas.DrawImage(dst_image, {400, 0},
481 {.blend_mode = BlendMode::kSourceOver});
482 canvas.SaveLayer({.color = Color::White().WithAlpha(src_alpha),
483 .blend_mode = blend_mode});
484 {
485 canvas.DrawImage(src_image, {400, 0},
486 {.blend_mode = BlendMode::kSourceOver});
487 }
488 canvas.Restore();
489 }
490 canvas.Restore();
491 canvas.Restore();
492
493 return canvas.EndRecordingAsPicture();
494}
495
496#define BLEND_MODE_TEST(blend_mode) \
497 TEST_P(AiksTest, BlendMode##blend_mode) { \
498 auto src_image = std::make_shared<Image>( \
499 CreateTextureForFixture("blend_mode_src.png")); \
500 auto dst_image = std::make_shared<Image>( \
501 CreateTextureForFixture("blend_mode_dst.png")); \
502 auto callback = [&](AiksContext& renderer) -> std::optional<Picture> { \
503 return BlendModeTest(GetContentScale(), BlendMode::k##blend_mode, \
504 src_image, dst_image, /*src_alpha=*/1.0); \
505 }; \
506 OpenPlaygroundHere(callback); \
507 }
509
510#define BLEND_MODE_SRC_ALPHA_TEST(blend_mode) \
511 TEST_P(AiksTest, BlendModeSrcAlpha##blend_mode) { \
512 auto src_image = std::make_shared<Image>( \
513 CreateTextureForFixture("blend_mode_src.png")); \
514 auto dst_image = std::make_shared<Image>( \
515 CreateTextureForFixture("blend_mode_dst.png")); \
516 auto callback = [&](AiksContext& renderer) -> std::optional<Picture> { \
517 return BlendModeTest(GetContentScale(), BlendMode::k##blend_mode, \
518 src_image, dst_image, /*src_alpha=*/0.5); \
519 }; \
520 OpenPlaygroundHere(callback); \
521 }
523
524TEST_P(AiksTest, CanDrawPaintMultipleTimesInteractive) {
525 auto modes = GetBlendModeSelection();
526
527 auto callback = [&](AiksContext& renderer) -> std::optional<Picture> {
528 static Color background = Color::MediumTurquoise();
529 static Color foreground = Color::Color::OrangeRed().WithAlpha(0.5);
530 static int current_blend_index = 3;
531
532 if (AiksTest::ImGuiBegin("Controls", nullptr,
533 ImGuiWindowFlags_AlwaysAutoResize)) {
534 ImGui::ColorEdit4("Background", reinterpret_cast<float*>(&background));
535 ImGui::ColorEdit4("Foreground", reinterpret_cast<float*>(&foreground));
536 ImGui::ListBox("Blend mode", &current_blend_index,
537 modes.blend_mode_names.data(),
538 modes.blend_mode_names.size());
539 ImGui::End();
540 }
541
542 Canvas canvas;
543 canvas.Scale(Vector2(0.2, 0.2));
544 canvas.DrawPaint({.color = background});
545 canvas.DrawPaint(
546 {.color = foreground,
547 .blend_mode = static_cast<BlendMode>(current_blend_index)});
548 return canvas.EndRecordingAsPicture();
549 };
550 ASSERT_TRUE(OpenPlaygroundHere(callback));
551}
552
553TEST_P(AiksTest, ForegroundPipelineBlendAppliesTransformCorrectly) {
554 auto texture = CreateTextureForFixture("airplane.jpg",
555 /*enable_mipmapping=*/true);
556
557 Canvas canvas;
558 canvas.Rotate(Degrees(30));
559 canvas.DrawImage(std::make_shared<Image>(texture), {200, 200},
561 Color::Orange())});
562
563 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
564}
565
566TEST_P(AiksTest, ForegroundAdvancedBlendAppliesTransformCorrectly) {
567 auto texture = CreateTextureForFixture("airplane.jpg",
568 /*enable_mipmapping=*/true);
569
570 Canvas canvas;
571 canvas.Rotate(Degrees(30));
572 canvas.DrawImage(std::make_shared<Image>(texture), {200, 200},
573 {.color_filter = ColorFilter::MakeBlend(
575
576 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
577}
578
579TEST_P(AiksTest, FramebufferAdvancedBlendCoverage) {
580 auto texture = CreateTextureForFixture("airplane.jpg",
581 /*enable_mipmapping=*/true);
582
583 // Draw with an advanced blend that can use FramebufferBlendContents and
584 // verify that the scale transform is correctly applied to the image.
585 Canvas canvas;
586 canvas.DrawPaint({.color = Color::DarkGray()});
587 canvas.Scale(Vector2(0.4, 0.4));
588 canvas.DrawImage(std::make_shared<Image>(texture), {20, 20},
589 {.blend_mode = BlendMode::kMultiply});
590
591 ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
592}
593
594} // namespace testing
595} // namespace impeller
#define BLEND_MODE_TUPLE(blend_mode)
#define BLEND_MODE_SRC_ALPHA_TEST(blend_mode)
#define BLEND_MODE_TEST(blend_mode)
static bool ImGuiBegin(const char *name, bool *p_open, ImGuiWindowFlags flags)
static std::shared_ptr< ColorFilter > MakeBlend(BlendMode blend_mode, Color color)
Definition: color_filter.cc:23
static ColorSource MakeLinearGradient(Point start_point, Point end_point, std::vector< Color > colors, std::vector< Scalar > stops, Entity::TileMode tile_mode, Matrix effect_transform)
static constexpr BlendMode kLastAdvancedBlendMode
Definition: entity.h:23
@ kNormal
Blurred inside and outside.
#define IMPELLER_FOR_EACH_BLEND_MODE(V)
Definition: color.h:19
const Paint & paint
Definition: color_source.cc:38
DlColor color
FlKeyEvent uint64_t FlKeyResponderAsyncCallback callback
static float max(float r, float g, float b)
Definition: hsl.cpp:49
static float min(float r, float g, float b)
Definition: hsl.cpp:48
FlTexture * texture
double y
double x
SK_API GrDirectContext * GetContext(const SkImage *src)
PODArray< SkColor > colors
Definition: SkRecords.h:276
SK_API sk_sp< SkShader > Color(SkColor)
DEF_SWITCHES_START aot vmservice shared library name
Definition: switches.h:32
it will be possible to load the file into Perfetto s trace viewer disable asset Prevents usage of any non test fonts unless they were explicitly Loaded via prefetched default font Indicates whether the embedding started a prefetch of the default font manager before creating the engine run In non interactive mode
Definition: switches.h:228
static Picture BlendModeTest(Vector2 content_scale, BlendMode blend_mode, const std::shared_ptr< Image > &src_image, const std::shared_ptr< Image > &dst_image, Scalar src_alpha)
TEST_P(AiksTest, CanRenderAdvancedBlendColorFilterWithSaveLayer)
static BlendModeSelection GetBlendModeSelection()
constexpr float k2Pi
Definition: constants.h:29
Point Vector2
Definition: point.h:326
constexpr float kPi
Definition: constants.h:26
float Scalar
Definition: scalar.h:18
TPoint< Scalar > Point
Definition: point.h:322
BlendMode
Definition: color.h:59
constexpr float kPhi
Definition: constants.h:53
SIN Vec< N, float > abs(const Vec< N, float > &x)
Definition: SkVx.h:707
def filtered(names, to_skip)
Definition: zip_utils.py:20
static constexpr Color LimeGreen()
Definition: color.h:604
static constexpr Color Black()
Definition: color.h:268
static constexpr Color CornflowerBlue()
Definition: color.h:344
static constexpr Color MediumTurquoise()
Definition: color.h:648
static constexpr Color White()
Definition: color.h:266
constexpr Color WithAlpha(Scalar new_alpha) const
Definition: color.h:280
static constexpr Color Orange()
Definition: color.h:692
static constexpr Color Red()
Definition: color.h:274
static constexpr Color MakeRGBA8(uint8_t r, uint8_t g, uint8_t b, uint8_t a)
Definition: color.h:154
static constexpr Color DarkGray()
Definition: color.h:372
Color Blend(Color source, BlendMode blend_mode) const
Blends an unpremultiplied destination color into a given unpremultiplied source color to form a new u...
Definition: color.cc:234
static constexpr Color Blue()
Definition: color.h:278
static constexpr Color Green()
Definition: color.h:276
A 4x4 matrix using column-major storage.
Definition: matrix.h:37
static constexpr Matrix MakeScale(const Vector3 &s)
Definition: matrix.h:104
FilterContents::BlurStyle style
Definition: paint.h:49
Scalar radians
Definition: scalar.h:39
In filters that use Gaussian distributions, "sigma" is a size of one standard deviation in terms of t...
Definition: sigma.h:32
static constexpr TPoint< Type > MakeXY(Type x, Type y)
Definition: point.h:46
static constexpr TRect MakeXYWH(Type x, Type y, Type width, Type height)
Definition: rect.h:136
static constexpr TRect MakeSize(const TSize< U > &size)
Definition: rect.h:146
constexpr TRect< T > Expand(T left, T top, T right, T bottom) const
Returns a rectangle with expanded edges. Negative expansion results in shrinking.
Definition: rect.h:605
static constexpr TRect MakeLTRB(Type left, Type top, Type right, Type bottom)
Definition: rect.h:129
std::vector< const char * > blend_mode_names