Skip to content

Commit

Permalink
remove single-view assumption from paintImage (#118721)
Browse files Browse the repository at this point in the history
* remove single-view assumption from paintImage

* dpr

* fix test for web
  • Loading branch information
goderbauer committed Jan 18, 2023
1 parent 374f09e commit ae1cc18
Show file tree
Hide file tree
Showing 2 changed files with 17 additions and 6 deletions.
21 changes: 16 additions & 5 deletions packages/flutter/lib/src/painting/decoration_image.dart
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@
// found in the LICENSE file.

import 'dart:developer' as developer;
import 'dart:ui' as ui show Image;
import 'dart:math' as math;
import 'dart:ui' as ui show FlutterView, Image;

import 'package:flutter/foundation.dart';
import 'package:flutter/scheduler.dart';
Expand Down Expand Up @@ -558,13 +559,22 @@ void paintImage({
bool invertedCanvas = false;
// Output size and destination rect are fully calculated.
if (!kReleaseMode) {
// We can use the devicePixelRatio of the views directly here (instead of
// going through a MediaQuery) because if it changes, whatever is aware of
// the MediaQuery will be repainting the image anyways.
// Furthermore, for the memory check below we just assume that all images
// are decoded for the view with the highest device pixel ratio and use that
// as an upper bound for the display size of the image.
final double maxDevicePixelRatio = PaintingBinding.instance.platformDispatcher.views.fold(
0.0,
(double previousValue, ui.FlutterView view) => math.max(previousValue, view.devicePixelRatio),
);

final ImageSizeInfo sizeInfo = ImageSizeInfo(
// Some ImageProvider implementations may not have given this.
source: debugImageLabel ?? '<Unknown Image(${image.width}×${image.height})>',
imageSize: Size(image.width.toDouble(), image.height.toDouble()),
// It's ok to use this instead of a MediaQuery because if this changes,
// whatever is aware of the MediaQuery will be repainting the image anyway.
displaySize: outputSize * PaintingBinding.instance.window.devicePixelRatio,
displaySize: outputSize * maxDevicePixelRatio,
);
assert(() {
if (debugInvertOversizedImages &&
Expand All @@ -576,7 +586,8 @@ void paintImage({
exception: 'Image $debugImageLabel has a display size of '
'$outputWidth×$outputHeight but a decode size of '
'${image.width}×${image.height}, which uses an additional '
'${overheadInKilobytes}KB.\n\n'
'${overheadInKilobytes}KB (assuming a device pixel ratio of '
'$maxDevicePixelRatio).\n\n'
'Consider resizing the asset ahead of time, supplying a cacheWidth '
'parameter of $outputWidth, a cacheHeight parameter of '
'$outputHeight, or using a ResizeImage.',
Expand Down
2 changes: 1 addition & 1 deletion packages/flutter/test/painting/paint_image_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ void main() {

expect(
messages.single,
'Image TestImage has a display size of 300×150 but a decode size of 300×300, which uses an additional 234KB.\n\n'
'Image TestImage has a display size of 300×150 but a decode size of 300×300, which uses an additional 234KB (assuming a device pixel ratio of ${3.0}).\n\n'
'Consider resizing the asset ahead of time, supplying a cacheWidth parameter of 300, a cacheHeight parameter of 150, or using a ResizeImage.',
);

Expand Down

0 comments on commit ae1cc18

Please sign in to comment.