Unverified Commit 8863296d authored by nt4f04uNd's avatar nt4f04uNd Committed by GitHub

Add missing parameters to DecorationImage (#88453)

* Add missing parameters to DecorationImage

* tune docs

* fix test
parent 162d914d
......@@ -53,6 +53,10 @@ class DecorationImage {
this.repeat = ImageRepeat.noRepeat,
this.matchTextDirection = false,
this.scale = 1.0,
this.opacity = 1.0,
this.filterQuality = FilterQuality.low,
this.invertColors = false,
this.isAntiAlias = false,
}) : assert(image != null),
assert(alignment != null),
assert(repeat != null),
......@@ -142,6 +146,36 @@ class DecorationImage {
/// calculated by multiplying [scale] with `scale` of the given [ImageProvider].
final double scale;
/// If non-null, the value is multiplied with the opacity of each image
/// pixel before painting onto the canvas.
///
/// This is more efficient than using [Opacity] or [FadeTransition] to
/// change the opacity of an image.
final double opacity;
/// Used to set the filterQuality of the image.
///
/// Use the "low" quality setting to scale the image, which corresponds to
/// bilinear interpolation, rather than the default "none" which corresponds
/// to nearest-neighbor.
final FilterQuality filterQuality;
/// Whether the colors of the image are inverted when drawn.
///
/// Inverting the colors of an image applies a new color filter to the paint.
/// If there is another specified color filter, the invert will be applied
/// after it. This is primarily used for implementing smart invert on iOS.
///
/// See also:
///
/// * [Paint.invertColors], for the dart:ui implementation.
final bool invertColors;
/// Whether to paint the image with anti-aliasing.
///
/// Anti-aliasing alleviates the sawtooth artifact when the image is rotated.
final bool isAntiAlias;
/// Creates a [DecorationImagePainter] for this [DecorationImage].
///
/// The `onChanged` argument must not be null. It will be called whenever the
......@@ -166,11 +200,28 @@ class DecorationImage {
&& other.centerSlice == centerSlice
&& other.repeat == repeat
&& other.matchTextDirection == matchTextDirection
&& other.scale == scale;
&& other.scale == scale
&& other.opacity == opacity
&& other.filterQuality == filterQuality
&& other.invertColors == invertColors
&& other.isAntiAlias == isAntiAlias;
}
@override
int get hashCode => hashValues(image, colorFilter, fit, alignment, centerSlice, repeat, matchTextDirection, scale);
int get hashCode => hashValues(
image,
colorFilter,
fit,
alignment,
centerSlice,
repeat,
matchTextDirection,
scale,
opacity,
filterQuality,
invertColors,
isAntiAlias,
);
@override
String toString() {
......@@ -189,7 +240,13 @@ class DecorationImage {
'$repeat',
if (matchTextDirection)
'match text direction',
'scale: $scale',
'scale $scale',
'opacity $opacity',
'$filterQuality',
if (invertColors)
'invert colors',
if (isAntiAlias)
'use anti-aliasing',
];
return '${objectRuntimeType(this, 'DecorationImage')}(${properties.join(", ")})';
}
......@@ -286,7 +343,10 @@ class DecorationImagePainter {
centerSlice: _details.centerSlice,
repeat: _details.repeat,
flipHorizontally: flipHorizontally,
filterQuality: FilterQuality.low,
opacity: _details.opacity,
filterQuality: _details.filterQuality,
invertColors: _details.invertColors,
isAntiAlias: _details.isAntiAlias,
);
if (clipPath != null)
......
......@@ -182,7 +182,8 @@ class RenderImage extends RenderBox {
value?.addListener(markNeedsPaint);
}
/// Used to set the filterQuality of the image
/// Used to set the filterQuality of the image.
///
/// Use the [FilterQuality.low] quality setting to scale the image, which corresponds to
/// bilinear interpolation, rather than the default [FilterQuality.none] which corresponds
/// to nearest-neighbor.
......@@ -271,7 +272,7 @@ class RenderImage extends RenderBox {
/// Whether to invert the colors of the image.
///
/// inverting the colors of an image applies a new color filter to the paint.
/// Inverting the colors of an image applies a new color filter to the paint.
/// If there is another specified color filter, the invert will be applied
/// after it. This is primarily used for implementing smart invert on iOS.
bool get invertColors => _invertColors;
......
......@@ -5685,7 +5685,8 @@ class RawImage extends LeafRenderObjectWidget {
/// of an image.
final Animation<double>? opacity;
/// Used to set the filterQuality of the image
/// Used to set the filterQuality of the image.
///
/// Use the "low" quality setting to scale the image, which corresponds to
/// bilinear interpolation, rather than the default "none" which corresponds
/// to nearest-neighbor.
......@@ -5765,7 +5766,7 @@ class RawImage extends LeafRenderObjectWidget {
/// Whether the colors of the image are inverted when drawn.
///
/// inverting the colors of an image applies a new color filter to the paint.
/// Inverting the colors of an image applies a new color filter to the paint.
/// If there is another specified color filter, the invert will be applied
/// after it. This is primarily used for implementing smart invert on iOS.
///
......
......@@ -302,6 +302,10 @@ void main() {
alignment: Alignment.bottomLeft,
centerSlice: const Rect.fromLTWH(10.0, 20.0, 30.0, 40.0),
repeat: ImageRepeat.repeatY,
opacity: 0.5,
filterQuality: FilterQuality.high,
invertColors: true,
isAntiAlias: true,
);
final BoxDecoration boxDecoration = BoxDecoration(image: backgroundImage);
......@@ -316,19 +320,31 @@ void main() {
expect(call.positionalArguments[1], const Rect.fromLTRB(10.0, 20.0, 40.0, 60.0));
expect(call.positionalArguments[2], const Rect.fromLTRB(0.0, 0.0, 100.0, 100.0));
expect(call.positionalArguments[3], isA<Paint>());
// ignore: avoid_dynamic_calls
expect(call.positionalArguments[3].isAntiAlias, false);
// ignore: avoid_dynamic_calls
expect(call.positionalArguments[3].colorFilter, colorFilter);
// ignore: avoid_dynamic_calls
expect(call.positionalArguments[3].filterQuality, FilterQuality.low);
final Paint paint = call.positionalArguments[3] as Paint;
expect(paint.colorFilter, colorFilter);
expect(paint.color, const Color(0x7F000000)); // 0.5 opacity
expect(paint.filterQuality, FilterQuality.high);
expect(paint.isAntiAlias, true);
// TODO(craiglabenz): change to true when https://github.com/flutter/flutter/issues/88909 is fixed
expect(paint.invertColors, !kIsWeb);
});
test('DecorationImage with null textDirection configuration should throw Error', () async {
const ColorFilter colorFilter = ui.ColorFilter.mode(Color(0xFF00FF00), BlendMode.src);
final ui.Image image = await createTestImage(width: 100, height: 100);
final DecorationImage backgroundImage = DecorationImage(
image: SynchronousTestImageProvider(image),
colorFilter: colorFilter,
fit: BoxFit.contain,
alignment: Alignment.center,
centerSlice: const Rect.fromLTWH(10.0, 20.0, 30.0, 40.0),
repeat: ImageRepeat.repeatY,
matchTextDirection: true,
scale: 0.5,
opacity: 0.5,
filterQuality: FilterQuality.low,
invertColors: true,
isAntiAlias: true,
);
final BoxDecoration boxDecoration = BoxDecoration(image: backgroundImage);
final BoxPainter boxPainter = boxDecoration.createBoxPainter(() {
......@@ -356,7 +372,11 @@ void main() {
' direction provided in the ImageConfiguration object to match.\n'
' The DecorationImage was:\n'
' DecorationImage(SynchronousTestImageProvider(),\n'
' Alignment.center, match text direction, scale: 1.0)\n'
' ColorFilter.mode(Color(0xff00ff00), BlendMode.src),\n'
' BoxFit.contain, Alignment.center, centerSlice:\n'
' Rect.fromLTRB(10.0, 20.0, 40.0, 60.0), ImageRepeat.repeatY,\n'
' match text direction, scale 0.5, opacity 0.5,\n'
' FilterQuality.low, invert colors, use anti-aliasing)\n'
' The ImageConfiguration was:\n'
' ImageConfiguration(size: Size(100.0, 100.0))\n',
);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment