You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Flutter从URL下载SVG图片遇PlatformException问题求助

SVG图片保存失败问题解决

我用代码从URL下载SVG图片转成Uint8List后,用ImageGallerySaver保存时触发如下错误:

PlatformException (PlatformException(error, decodeByteArray(image, 0, image.size) must not be null, null, java.lang.NullPointerException: decodeByteArray(image, 0, image.size) must not be null

同样的代码保存PNG格式图片完全正常,相关代码如下:

调用逻辑

String url = 'https://qodevault-staging.s3.us-east-2.amazonaws.com/qrcodes/6136f35c3a5e9824329fdd8166d01715.svg'
final bytes = await kNetworkImageToBytes(url);
kSaveImageFromBytes(imgData: bytes, name: 'qrcode');

网络图片转字节函数

///converts network image (Except for svg) to [Uint8List]
Future<Uint8List> kNetworkImageToBytes(String imageUrl) async {
  try {
    var response = await Dio().get(
      imageUrl,
      options: Options(responseType: ResponseType.bytes),
    );
    return Uint8List.fromList(response.data);
  } catch (e) {
    rethrow;
  }
}

图片保存函数

Future<void> kSaveImageFromBytes({
  required Uint8List imgData,
  required String name,
  bool appendRandomString = true,
}) async {
  final random = generateRandomString(10);
  final filename = appendRandomString ? '${name}_$random' : name;
  final bool hasPermission =
      await PermissionHandler.requestPermission(Permission.storage);
  if (!hasPermission) throw 'Permission not granted';
  final result = await ImageGallerySaver.saveImage(
    imgData,
    quality: 100,
    name: 'QV_$filename',
  );
  print(result);
  if (result is Map) {
    if (result['isSuccess'].toString() == 'false') {
      throw 'Error saving image';
    }
  }
}

问题原因与解决方案

原因

ImageGallerySaver仅支持保存PNG/JPG这类位图格式的字节数据,而SVG是矢量图格式,无法直接被它解码处理,因此抛出空指针异常。

解决步骤

需要先将SVG矢量图渲染成位图(比如PNG),再进行保存,具体实现如下:

  1. 添加SVG渲染依赖
    在pubspec.yaml中加入flutter_svg依赖(版本请根据你的Flutter版本选择兼容的最新版):
dependencies:
  flutter_svg: ^2.0.9
  1. 新增SVG转PNG的工具函数
import 'package:flutter_svg/flutter_svg.dart';
import 'package:flutter/services.dart';

Future<Uint8List> svgBytesToPngBytes(Uint8List svgBytes) async {
  // 解析SVG字节数据
  final svgDrawableRoot = await svg.fromSvgBytes(svgBytes, '');
  // 指定渲染尺寸(可根据需求调整)
  final picture = svgDrawableRoot.toPicture(size: const Size(300, 300));
  // 转换为Image对象
  final image = await picture.toImage(300, 300);
  // 导出为PNG字节数据
  final byteData = await image.toByteData(format: ImageByteFormat.png);
  return byteData!.buffer.asUint8List();
}
  1. 修改调用逻辑
String url = 'https://qodevault-staging.s3.us-east-2.amazonaws.com/qrcodes/6136f35c3a5e9824329fdd8166d01715.svg';
// 下载SVG字节
final svgBytes = await kNetworkImageToBytes(url);
// 转换为PNG字节
final pngBytes = await svgBytesToPngBytes(svgBytes);
// 保存图片
await kSaveImageFromBytes(imgData: pngBytes, name: 'qrcode');

内容的提问来源于stack exchange,提问作者Sujan Gainju

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.28 19:52:58