-
Notifications
You must be signed in to change notification settings - Fork 454
Open
Description
If you provide a bundle argument to SvgPicture.asset and use Image.asset(...), then in profile and release modes the following exception will be thrown and svg won't be displayed:
Exception
[ERROR:flutter/runtime/dart_vm_initializer.cc(41)] Unhandled Exception: Invalid argument(s): Illegal argument in isolate message: object is unsendable - Library:'dart:async' Class: _Future@4048458 (see restrictions listed at `SendPort.send()` documentation for more information)
<- _List len:8 (from dart:core)
<- _Map len:1 (from dart:collection)
<- Instance of 'PlatformAssetBundle' (from package:flutter/src/services/asset_bundle.dart)
<- Instance of 'SvgAssetLoader' (from package:flutter_svg/src/loaders.dart)
<- Context num_variables: 2 <- SvgLoader._load.<anonymous closure>.<anonymous closure> (from package:flutter_svg/src/loaders.dart)
<- Context num_variables: 2 <- compute.<anonymous closure> (from package:flutter/src/foundation/_isolates_io.dart)
<- resultPort in Instance of '_RemoteRunner<ByteData>' (from dart:isolate)
#0 Isolate._spawnFunction (dart:isolate-patch/isolate_patch.dart:398)
#1 Isolate.spawn (dart:isolate-patch/isolate_patch.dart:378)
#2 Isolate.run (dart:isolate:285)
#3 compute (package:flutter/src/foundation/_isolates_io.dart:18)
#4 compute (package:flutter/src/foundation/isolates.dart:82)
#5 SvgLoader._load.<anonymous closure> (package:flutter_svg/src/loaders.dart:154)
<asynchronous suspension>
#6 _VectorGraphicWidgetState._loadPicture.<anonymous closure> (package:vector_graphics/src/vector_graphics.dart:355)
<asynchronous suspension>
#7 _VectorGraphicWidgetState._loadPicture.<anonymous closure> (package:vector_graphics/src/vector_graphics.dart:369)
<asynchronous suspension>
#8 _VectorGraphicWidgetState._loadAssetBytes.<anonymous closure> (package:vector_graphics/src/vector_graphics.dart:402)
<asynchronous suspension>
That's because CachingAssetBundle stores futures in its fields, SvgAssetLoader stores bundle (if you provided one) and SvgLoader somehow sends it to other isolate in compute.
Debug build doesn't have this problem because it doesn't use other isolate.
Reproducible with Flutter 3.24.1 and flutter_svg: 2.0.10+1.
Sample app
assets/any_svg.svg and assets/any_png.png are literally any svg and png files respectively.
import 'package:flutter/material.dart';
import 'package:flutter_svg/flutter_svg.dart';
void main() {
runApp(
const MaterialApp(
home: Screen(),
),
);
}
class Screen extends StatelessWidget {
const Screen({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
body: Row(
children: [
SvgPicture.asset(
'assets/any_svg.svg',
bundle: DefaultAssetBundle.of(context),
),
Image.asset(
'assets/any_png.png',
width: 100.0,
height: 100.0,
),
],
),
);
}
}
Problem can be fixed with the following change, but I don't sure how adequate it is.
Change that fixes problem
Future<ByteData> _load(BuildContext? context) {
final SvgTheme theme = getTheme(context);
return prepareMessage(context).then((T? message) {
return _compute<T>(
message: message,
xml: provideSvg(message),
theme: theme,
colorMapper: colorMapper,
);
});
}
static Future<ByteData> _compute<T>({
required T? message,
required String xml,
required SvgTheme theme,
required ColorMapper? colorMapper,
}) {
return compute((T? message) {
return vg
.encodeSvg(
xml: xml,
theme: theme.toVgTheme(),
colorMapper: colorMapper == null
? null
: _DelegateVgColorMapper(colorMapper),
debugName: 'Svg loader',
enableClippingOptimizer: false,
enableMaskingOptimizer: false,
enableOverdrawOptimizer: false,
)
.buffer
.asByteData();
}, message, debugLabel: 'Load Bytes');
}Metadata
Metadata
Assignees
Labels
No labels