implement radial gradient in canvaskit backend (flutter/engine#13796)

This commit is contained in:
Yegor 2019-11-12 10:56:07 -08:00 committed by GitHub
parent f3b15f82c9
commit 0aec3787c7
2 changed files with 50 additions and 19 deletions

View File

@ -193,6 +193,28 @@ js.JsArray<double> makeSkMatrix(Float64List matrix4) {
return skMatrix;
}
/// Color stops used when the framework specifies `null`.
final js.JsArray<double> _kDefaultColorStops = () {
final js.JsArray<double> jsColorStops = js.JsArray<double>();
jsColorStops.length = 2;
jsColorStops[0] = 0;
jsColorStops[1] = 1;
return jsColorStops;
}();
/// Converts a list of color stops into a Skia-compatible JS array or color stops.
///
/// In Flutter `null` means two color stops `[0, 1]` that in Skia must be specified explicitly.
js.JsArray<double> makeSkiaColorStops(List<double> colorStops) {
if (colorStops == null) {
return _kDefaultColorStops;
}
final js.JsArray<double> jsColorStops = js.JsArray<double>.from(colorStops);
jsColorStops.length = colorStops.length;
return jsColorStops;
}
// These must be kept in sync with `flow/layers/physical_shape_layer.cc`.
const double kLightHeight = 600.0;
const double kLightRadius = 800.0;

View File

@ -142,21 +142,11 @@ class GradientLinear extends EngineGradient {
jsColors[i] = colors[i].value;
}
js.JsArray<double> jsColorStops;
if (colorStops == null) {
jsColorStops = js.JsArray<double>();
jsColorStops.length = 2;
jsColorStops[0] = 0;
jsColorStops[1] = 1;
} else {
jsColorStops = js.JsArray<double>.from(colorStops);
jsColorStops.length = colorStops.length;
}
return canvasKit.callMethod('MakeLinearGradientShader', <dynamic>[
makeSkPoint(from),
makeSkPoint(to),
jsColors,
jsColorStops,
makeSkiaColorStops(colorStops),
tileMode.index,
]);
}
@ -178,13 +168,16 @@ class GradientRadial extends EngineGradient {
@override
Object createPaintStyle(html.CanvasRenderingContext2D ctx) {
if (matrix4 != null && !Matrix4.fromFloat64List(matrix4).isIdentity()) {
throw UnimplementedError(
'matrix4 not supported in GradientRadial shader');
}
if (tileMode != ui.TileMode.clamp) {
throw UnimplementedError(
'TileMode not supported in GradientRadial shader');
if (!experimentalUseSkia) {
// The DOM backend does not (yet) support all parameters.
if (matrix4 != null && !Matrix4.fromFloat64List(matrix4).isIdentity()) {
throw UnimplementedError(
'matrix4 not supported in GradientRadial shader');
}
if (tileMode != ui.TileMode.clamp) {
throw UnimplementedError(
'TileMode not supported in GradientRadial shader');
}
}
final html.CanvasGradient gradient = ctx.createRadialGradient(
center.dx, center.dy, 0, center.dx, center.dy, radius);
@ -203,7 +196,23 @@ class GradientRadial extends EngineGradient {
@override
js.JsObject createSkiaShader() {
throw UnimplementedError();
assert(experimentalUseSkia);
final js.JsArray<num> jsColors = js.JsArray<num>();
jsColors.length = colors.length;
for (int i = 0; i < colors.length; i++) {
jsColors[i] = colors[i].value;
}
return canvasKit.callMethod('MakeRadialGradientShader', <dynamic>[
makeSkPoint(center),
radius,
jsColors,
makeSkiaColorStops(colorStops),
tileMode.index,
matrix4 != null ? makeSkMatrix(matrix4) : null,
0,
]);
}
}