Commit 53727866 authored by TruongSinh Tran-Nguyen's avatar TruongSinh Tran-Nguyen Committed by xster

fix #25143 Successive calls to `precacheImage()` throw an exception (#25159)

parent 85ded441
...@@ -32,3 +32,4 @@ Chema Molins <chemamolins@gmail.com> ...@@ -32,3 +32,4 @@ Chema Molins <chemamolins@gmail.com>
Stefan Mitev <mr.mitew@gmail.com> Stefan Mitev <mr.mitew@gmail.com>
Jasper van Riet <jaspervanriet@gmail.com> Jasper van Riet <jaspervanriet@gmail.com>
Mattijs Fuijkschot <mattijs.fuijkschot@gmail.com> Mattijs Fuijkschot <mattijs.fuijkschot@gmail.com>
TruongSinh Tran-Nguyen <i@truongsinh.pro>
...@@ -83,9 +83,11 @@ Future<void> precacheImage( ...@@ -83,9 +83,11 @@ Future<void> precacheImage(
final ImageStream stream = provider.resolve(config); final ImageStream stream = provider.resolve(config);
void listener(ImageInfo image, bool sync) { void listener(ImageInfo image, bool sync) {
completer.complete(); completer.complete();
stream.removeListener(listener);
} }
void errorListener(dynamic exception, StackTrace stackTrace) { void errorListener(dynamic exception, StackTrace stackTrace) {
completer.complete(); completer.complete();
stream.removeListener(listener);
if (onError != null) { if (onError != null) {
onError(exception, stackTrace); onError(exception, stackTrace);
} else { } else {
...@@ -99,7 +101,6 @@ Future<void> precacheImage( ...@@ -99,7 +101,6 @@ Future<void> precacheImage(
} }
} }
stream.addListener(listener, onError: errorListener); stream.addListener(listener, onError: errorListener);
completer.future.then<void>((void value) { stream.removeListener(listener); });
return completer.future; return completer.future;
} }
......
...@@ -621,6 +621,28 @@ void main() { ...@@ -621,6 +621,28 @@ void main() {
expect(isSync, isTrue); expect(isSync, isTrue);
}); });
testWidgets('Precache remove listeners immediately after future completes, does not crash on successive calls #25143', (WidgetTester tester) async {
final TestImageStreamCompleter imageStreamCompleter = TestImageStreamCompleter();
final TestImageProvider provider = TestImageProvider(streamCompleter: imageStreamCompleter);
await tester.pumpWidget(
Builder(
builder: (BuildContext context) {
precacheImage(provider, context);
return Container();
}
)
);
expect(imageStreamCompleter.listeners.length, 2);
imageStreamCompleter.listeners.keys.toList()[1](null, null);
expect(imageStreamCompleter.listeners.length, 1);
imageStreamCompleter.listeners.keys.toList()[0](null, null);
expect(imageStreamCompleter.listeners.length, 0);
});
testWidgets('Precache completes with onError on error', (WidgetTester tester) async { testWidgets('Precache completes with onError on error', (WidgetTester tester) async {
dynamic capturedException; dynamic capturedException;
StackTrace capturedStackTrace; StackTrace capturedStackTrace;
......
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