Flutter Engine
 
Loading...
Searching...
No Matches
dl_sk_conversions.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
6
11#include "third_party/skia/include/core/SkColorFilter.h"
12#include "third_party/skia/include/effects/SkGradientShader.h"
13#include "third_party/skia/include/effects/SkImageFilters.h"
14#include "third_party/skia/include/effects/SkRuntimeEffect.h"
15
16namespace flutter {
17
18// clang-format off
19constexpr float kInvertColorMatrix[20] = {
20 -1.0, 0, 0, 1.0, 0,
21 0, -1.0, 0, 1.0, 0,
22 0, 0, -1.0, 1.0, 0,
23 1.0, 1.0, 1.0, 1.0, 0
24};
25// clang-format on
26
27SkPaint ToSk(const DlPaint& paint) {
28 SkPaint sk_paint;
29
30 sk_paint.setAntiAlias(paint.isAntiAlias());
31 sk_paint.setColor(ToSkColor4f(paint.getColor()));
32 sk_paint.setBlendMode(ToSk(paint.getBlendMode()));
33 sk_paint.setStyle(ToSk(paint.getDrawStyle()));
34 sk_paint.setStrokeWidth(paint.getStrokeWidth());
35 sk_paint.setStrokeMiter(paint.getStrokeMiter());
36 sk_paint.setStrokeCap(ToSk(paint.getStrokeCap()));
37 sk_paint.setStrokeJoin(ToSk(paint.getStrokeJoin()));
38 sk_paint.setImageFilter(ToSk(paint.getImageFilterPtr()));
39 auto color_filter = ToSk(paint.getColorFilterPtr());
40 if (paint.isInvertColors()) {
41 auto invert_filter = SkColorFilters::Matrix(kInvertColorMatrix);
42 if (color_filter) {
43 invert_filter = invert_filter->makeComposed(color_filter);
44 }
45 color_filter = invert_filter;
46 }
47 sk_paint.setColorFilter(color_filter);
48
49 auto color_source = paint.getColorSourcePtr();
50 if (color_source) {
51 // Unconditionally set dither to true for gradient shaders.
52 sk_paint.setDither(color_source->isGradient());
53 sk_paint.setShader(ToSk(color_source));
54 }
55
56 sk_paint.setMaskFilter(ToSk(paint.getMaskFilterPtr()));
57
58 return sk_paint;
59}
60
61SkPaint ToStrokedSk(const DlPaint& paint) {
62 DlPaint stroked_paint = paint;
64 return ToSk(stroked_paint);
65}
66
67SkPaint ToNonShaderSk(const DlPaint& paint) {
68 DlPaint non_shader_paint = paint;
69 non_shader_paint.setColorSource(nullptr);
70 return ToSk(non_shader_paint);
71}
72
73sk_sp<SkShader> ToSk(const DlColorSource* source) {
74 if (!source) {
75 return nullptr;
76 }
77 SkMatrix scratch;
78 static auto ToSkColors =
79 [](const DlGradientColorSourceBase* gradient) -> std::vector<SkColor> {
80 std::vector<SkColor> sk_colors;
81 sk_colors.reserve(gradient->stop_count());
82 for (int i = 0; i < gradient->stop_count(); ++i) {
83 sk_colors.push_back(gradient->colors()[i].argb());
84 }
85 return sk_colors;
86 };
87 switch (source->type()) {
89 const DlImageColorSource* image_source = source->asImage();
90 FML_DCHECK(image_source != nullptr);
91 auto image = image_source->image();
92 if (!image || !image->skia_image()) {
93 return nullptr;
94 }
95 return image->skia_image()->makeShader(
96 ToSk(image_source->horizontal_tile_mode()),
97 ToSk(image_source->vertical_tile_mode()),
98 ToSk(image_source->sampling()),
99 ToSk(image_source->matrix_ptr(), scratch));
100 }
102 const DlLinearGradientColorSource* linear_source =
103 source->asLinearGradient();
104 FML_DCHECK(linear_source != nullptr);
105 SkPoint pts[] = {ToSkPoint(linear_source->start_point()),
106 ToSkPoint(linear_source->end_point())};
107 std::vector<SkColor> skcolors = ToSkColors(linear_source);
108 return SkGradientShader::MakeLinear(
109 pts, skcolors.data(), linear_source->stops(),
110 linear_source->stop_count(), ToSk(linear_source->tile_mode()), 0,
111 ToSk(linear_source->matrix_ptr(), scratch));
112 }
114 const DlRadialGradientColorSource* radial_source =
115 source->asRadialGradient();
116 FML_DCHECK(radial_source != nullptr);
117 return SkGradientShader::MakeRadial(
118 ToSkPoint(radial_source->center()), radial_source->radius(),
119 ToSkColors(radial_source).data(), radial_source->stops(),
120 radial_source->stop_count(), ToSk(radial_source->tile_mode()), 0,
121 ToSk(radial_source->matrix_ptr(), scratch));
122 }
124 const DlConicalGradientColorSource* conical_source =
125 source->asConicalGradient();
126 FML_DCHECK(conical_source != nullptr);
127 return SkGradientShader::MakeTwoPointConical(
128 ToSkPoint(conical_source->start_center()),
129 conical_source->start_radius(),
130 ToSkPoint(conical_source->end_center()), conical_source->end_radius(),
131 ToSkColors(conical_source).data(), conical_source->stops(),
132 conical_source->stop_count(), ToSk(conical_source->tile_mode()), 0,
133 ToSk(conical_source->matrix_ptr(), scratch));
134 }
136 const DlSweepGradientColorSource* sweep_source =
137 source->asSweepGradient();
138 FML_DCHECK(sweep_source != nullptr);
139 return SkGradientShader::MakeSweep(
140 sweep_source->center().x, sweep_source->center().y,
141 ToSkColors(sweep_source).data(), sweep_source->stops(),
142 sweep_source->stop_count(), ToSk(sweep_source->tile_mode()),
143 sweep_source->start(), sweep_source->end(), 0,
144 ToSk(sweep_source->matrix_ptr(), scratch));
145 }
147 const DlRuntimeEffectColorSource* runtime_source =
148 source->asRuntimeEffect();
149 FML_DCHECK(runtime_source != nullptr);
150 auto runtime_effect = runtime_source->runtime_effect();
151 if (!runtime_effect || !runtime_effect->skia_runtime_effect()) {
152 return nullptr;
153 }
154
155 auto samplers = runtime_source->samplers();
156 std::vector<sk_sp<SkShader>> sk_samplers(samplers.size());
157 for (size_t i = 0; i < samplers.size(); i++) {
158 const auto& sampler = samplers[i];
159 if (sampler == nullptr) {
160 return nullptr;
161 }
162 sk_samplers[i] = ToSk(sampler);
163 }
164
165 auto uniform_data = runtime_source->uniform_data();
166 auto ref = new std::shared_ptr<std::vector<uint8_t>>(uniform_data);
167 auto sk_uniform_data = SkData::MakeWithProc(
168 uniform_data->data(), uniform_data->size(),
169 [](const void* ptr, void* context) {
170 delete reinterpret_cast<std::shared_ptr<std::vector<uint8_t>>*>(
171 context);
172 },
173 ref);
174
175 return runtime_effect->skia_runtime_effect()->makeShader(
176 sk_uniform_data, sk_samplers.data(), sk_samplers.size());
177 }
178 }
179}
180
181sk_sp<SkImageFilter> ToSk(const DlImageFilter* filter) {
182 if (!filter) {
183 return nullptr;
184 }
185 switch (filter->type()) {
187 const DlBlurImageFilter* blur_filter = filter->asBlur();
188 FML_DCHECK(blur_filter != nullptr);
189 return SkImageFilters::Blur(blur_filter->sigma_x(),
190 blur_filter->sigma_y(),
191 ToSk(blur_filter->tile_mode()), nullptr);
192 }
194 const DlDilateImageFilter* dilate_filter = filter->asDilate();
195 FML_DCHECK(dilate_filter != nullptr);
196 return SkImageFilters::Dilate(dilate_filter->radius_x(),
197 dilate_filter->radius_y(), nullptr);
198 }
200 const DlErodeImageFilter* erode_filter = filter->asErode();
201 FML_DCHECK(erode_filter != nullptr);
202 return SkImageFilters::Erode(erode_filter->radius_x(),
203 erode_filter->radius_y(), nullptr);
204 }
206 const DlMatrixImageFilter* matrix_filter = filter->asMatrix();
207 FML_DCHECK(matrix_filter != nullptr);
208 return SkImageFilters::MatrixTransform(
209 ToSkMatrix(matrix_filter->matrix()), ToSk(matrix_filter->sampling()),
210 nullptr);
211 }
213 const DlComposeImageFilter* compose_filter = filter->asCompose();
214 FML_DCHECK(compose_filter != nullptr);
215 return SkImageFilters::Compose(ToSk(compose_filter->outer()),
216 ToSk(compose_filter->inner()));
217 }
219 const DlColorFilterImageFilter* cf_filter = filter->asColorFilter();
220 FML_DCHECK(cf_filter != nullptr);
221 return SkImageFilters::ColorFilter(ToSk(cf_filter->color_filter()),
222 nullptr);
223 }
225 const DlLocalMatrixImageFilter* lm_filter = filter->asLocalMatrix();
226 FML_DCHECK(lm_filter != nullptr);
227 sk_sp<SkImageFilter> skia_filter = ToSk(lm_filter->image_filter());
228 // The image_filter property itself might have been null, or the
229 // construction of the SkImageFilter might be optimized to null
230 // for any number of reasons. In any case, if the filter is null
231 // or optimizaed away, let's then optimize away this local matrix
232 // case by returning null.
233 if (!skia_filter) {
234 return nullptr;
235 }
236 return skia_filter->makeWithLocalMatrix(ToSkMatrix(lm_filter->matrix()));
237 }
239 // UNSUPPORTED.
240 return nullptr;
241 }
242}
243
244sk_sp<SkColorFilter> ToSk(const DlColorFilter* filter) {
245 if (!filter) {
246 return nullptr;
247 }
248 switch (filter->type()) {
250 const DlBlendColorFilter* blend_filter = filter->asBlend();
251 FML_DCHECK(blend_filter != nullptr);
252 return SkColorFilters::Blend(ToSkColor4f(blend_filter->color()), nullptr,
253 ToSk(blend_filter->mode()));
254 }
256 const DlMatrixColorFilter* matrix_filter = filter->asMatrix();
257 FML_DCHECK(matrix_filter != nullptr);
258 float matrix[20];
259 matrix_filter->get_matrix(matrix);
260 return SkColorFilters::Matrix(matrix);
261 }
263 return SkColorFilters::SRGBToLinearGamma();
264 }
266 return SkColorFilters::LinearToSRGBGamma();
267 }
268 }
269}
270
271sk_sp<SkMaskFilter> ToSk(const DlMaskFilter* filter) {
272 if (!filter) {
273 return nullptr;
274 }
275 switch (filter->type()) {
277 const DlBlurMaskFilter* blur_filter = filter->asBlur();
278 FML_DCHECK(blur_filter != nullptr);
279 return SkMaskFilter::MakeBlur(ToSk(blur_filter->style()),
280 blur_filter->sigma(),
281 blur_filter->respectCTM());
282 }
283 }
284}
285
286sk_sp<SkVertices> ToSk(const std::shared_ptr<DlVertices>& vertices) {
287 std::vector<SkColor> sk_colors;
288 const SkColor* sk_colors_ptr = nullptr;
289 if (vertices->colors()) {
290 sk_colors.reserve(vertices->vertex_count());
291 for (int i = 0; i < vertices->vertex_count(); ++i) {
292 sk_colors.push_back(vertices->colors()[i].argb());
293 }
294 sk_colors_ptr = sk_colors.data();
295 }
296 return SkVertices::MakeCopy(ToSk(vertices->mode()), vertices->vertex_count(),
297 ToSkPoints(vertices->vertex_data()),
298 ToSkPoints(vertices->texture_coordinate_data()),
299 sk_colors_ptr, vertices->index_count(),
300 vertices->indices());
301}
302
303} // namespace flutter
virtual T type() const =0
DlBlurStyle style() const
virtual const DlBlendColorFilter * asBlend() const
virtual const DlMatrixColorFilter * asMatrix() const
const std::shared_ptr< const DlColorFilter > color_filter() const
virtual const DlRuntimeEffectColorSource * asRuntimeEffect() const
virtual const DlRadialGradientColorSource * asRadialGradient() const
virtual const DlLinearGradientColorSource * asLinearGradient() const
virtual const DlImageColorSource * asImage() const
virtual const DlSweepGradientColorSource * asSweepGradient() const
virtual const DlConicalGradientColorSource * asConicalGradient() const
std::shared_ptr< DlImageFilter > inner() const
std::shared_ptr< DlImageFilter > outer() const
DlImageSampling sampling() const
DlTileMode horizontal_tile_mode() const
sk_sp< const DlImage > image() const
virtual const DlLocalMatrixImageFilter * asLocalMatrix() const
virtual const DlColorFilterImageFilter * asColorFilter() const
virtual const DlMatrixImageFilter * asMatrix() const
virtual const DlComposeImageFilter * asCompose() const
virtual const DlBlurImageFilter * asBlur() const
virtual const DlDilateImageFilter * asDilate() const
virtual const DlErodeImageFilter * asErode() const
const std::shared_ptr< DlImageFilter > image_filter() const
virtual const DlBlurMaskFilter * asBlur() const
void get_matrix(float matrix[20]) const
const DlMatrix & matrix() const
bool isAntiAlias() const
Definition dl_paint.h:57
DlStrokeCap getStrokeCap() const
Definition dl_paint.h:98
DlColor getColor() const
Definition dl_paint.h:69
DlBlendMode getBlendMode() const
Definition dl_paint.h:82
float getStrokeMiter() const
Definition dl_paint.h:120
DlStrokeJoin getStrokeJoin() const
Definition dl_paint.h:106
const DlColorSource * getColorSourcePtr() const
Definition dl_paint.h:129
const DlMaskFilter * getMaskFilterPtr() const
Definition dl_paint.h:183
const DlColorFilter * getColorFilterPtr() const
Definition dl_paint.h:147
const DlImageFilter * getImageFilterPtr() const
Definition dl_paint.h:165
DlDrawStyle getDrawStyle() const
Definition dl_paint.h:90
float getStrokeWidth() const
Definition dl_paint.h:114
DlPaint & setDrawStyle(DlDrawStyle style)
Definition dl_paint.h:93
DlPaint & setColorSource(std::nullptr_t source)
Definition dl_paint.h:131
bool isInvertColors() const
Definition dl_paint.h:63
const std::shared_ptr< std::vector< uint8_t > > uniform_data() const
const sk_sp< DlRuntimeEffect > runtime_effect() const
const std::vector< std::shared_ptr< DlColorSource > > samplers() const
FlutterVulkanImage * image
#define FML_DCHECK(condition)
Definition logging.h:122
SkPaint ToSk(const DlPaint &paint)
const SkPoint & ToSkPoint(const DlPoint &point)
SkPaint ToStrokedSk(const DlPaint &paint)
SkColor4f ToSkColor4f(DlColor color)
SkPaint ToNonShaderSk(const DlPaint &paint)
@ kStroke
strokes boundary of shapes
constexpr float kInvertColorMatrix[20]
SkMatrix ToSkMatrix(const DlMatrix &matrix)
DEF_SWITCHES_START aot vmservice shared library Name of the *so containing AOT compiled Dart assets for launching the service isolate vm snapshot data
Definition switch_defs.h:36
const SkPoint * ToSkPoints(const DlPoint *points)