CachedNetwork 图像 - URI 中未指定主机

Amx*_*ela 5 flutter flutter-layout

我正在使用缓存的网络图像从 firebase 加载图像,如果图像的 URL 为空,则会加载一个带有图标的圆形头像。

\n

它在模拟器中工作正常,但当图像 url 为空时,它总是发布错误\n:

\n
I/flutter ( 6907): CacheManager: Failed to download file from  with error:\nI/flutter ( 6907): Invalid argument(s): No host specified in URI \n
Run Code Online (Sandbox Code Playgroud)\n

当图片url不为空时:

\n
I/flutter ( 6907): CacheManager: Failed to download file from  with error:\nI/flutter ( 6907): Invalid argument(s): No host specified in URI \n\n\xe2\x95\x90\xe2\x95\x90\xe2\x95\xa1 EXCEPTION CAUGHT BY IMAGE RESOURCE SERVICE \xe2\x95\x9e\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\nThe following ArgumentError was thrown resolving an image codec:\nInvalid argument(s): No host specified in URI\n\nWhen the exception was thrown, this was the stack:\n#0      _HttpClient._openUrl (dart:_http/http_impl.dart:2662:9)\n#1      _HttpClient.openUrl (dart:_http/http_impl.dart:2568:7)\n#2      IOClient.send (package:http/src/io_client.dart:35:38)\n#3      HttpFileService.get (package:flutter_cache_manager/src/web/file_service.dart:35:44)\n#4      WebHelper._download (package:flutter_cache_manager/src/web/web_helper.dart:117:24)\n#5      WebHelper._updateFile (package:flutter_cache_manager/src/web/web_helper.dart:99:28)\n<asynchronous suspension>\n#6      WebHelper._downloadOrAddToQueue (package:flutter_cache_manager/src/web/web_helper.dart:67:7)\n<asynchronous suspension>\n\nImage provider: CachedNetworkImageProvider("", scale: 1.0)\n Image key: CachedNetworkImageProvider("", scale: 1.0):\n  CachedNetworkImageProvider("", scale: 1.0)\n\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\xe2\x95\x90\n
Run Code Online (Sandbox Code Playgroud)\n

UI 准确地显示了它的预期内容。\n图片 URL 不为空\n图片网址为空

\n

我该如何解决此显示错误?

\n

这是代码:

\n
class ProfilePicture extends GetView<UserController> {\n  const ProfilePicture({\n    Key? key,\n    this.enabled = false,\n  }) : super(key: key);\n\n  final bool enabled;\n\n  double get radius => enabled ? 40.0 : 30.0;\n\n  @override\n  Widget build(BuildContext context) {\n    return Obx(\n      () {\n        return Hero(\n          tag: \'profile_hero\',\n          child: GestureDetector(\n            child: CachedNetworkImage(\n              imageUrl: controller.user?.photoURL ?? \'\',\n              placeholder: (context, url) => Container(),\n              errorWidget: (context, url, error) {\n                return Stack(\n                  children: [\n                    CircleAvatar(\n                      radius: radius,\n                      backgroundColor: Get.theme.brightness == Brightness.dark\n                          ? Colors.transparent\n                          : Get.theme.scaffoldBackgroundColor,\n                      child: Icon(Icons.person_outline_rounded,\n                          size: radius * 1.5,\n                          color: Get.theme.brightness == Brightness.dark\n                              ? Colors.white\n                              : primaryColor),\n                    ),\n                    Obx(\n                      () => Visibility(\n                        visible: controller.loading.value,\n                        child: SizedBox(\n                          height: radius * 2,\n                          width: radius * 2,\n                          child: const CircularProgressIndicator(),\n                        ),\n                      ),\n                    ),\n                  ],\n                );\n              },\n              imageBuilder: (_, imageProvider) {\n                return Stack(\n                  children: [\n                    CircleAvatar(\n                      radius: radius,\n                      backgroundImage: imageProvider,\n                    ),\n                    Obx(() {\n                      return Visibility(\n                        visible: controller.loading.value,\n                        child: SizedBox(\n                          height: radius * 2,\n                          width: radius * 2,\n                          child: const CircularProgressIndicator(\n                            strokeWidth: 5,\n                          ),\n                        ),\n                      );\n                    }),\n                  ],\n                );\n              },\n            ),\n            onTap: () {\n              if (enabled) {\n                showModalBottomSheet(\n                  context: context,\n                  shape: RoundedRectangleBorder(\n                    borderRadius: BorderRadius.circular(12.0),\n                  ),\n                  builder: (_) => const ImagePickerBottomModal(),\n                );\n              } else {\n                Get.to(\n                  const ProfileScreen(),\n                  routeName: AppRoutes.routeProfile,\n                  curve: Curves.fastOutSlowIn,\n                  transition: Transition.downToUp,\n                );\n              }\n            },\n          ),\n        );\n      },\n    );\n  }\n}\n
Run Code Online (Sandbox Code Playgroud)\n

jam*_*lin 6

CachedNetworkImage如果您没有要加载的图像,则根本不应该创建一个。

一种方法是:

  @override
  Widget build(BuildContext context) {
    var photoURL = controller.user?.photoURL;
    var fallback = Stack(
      children: [
        CircleAvatar(...)
      ],
    );

    return Obx(
      () {
        return Hero(
          tag: 'profile_hero',
          child: GestureDetector(
            child: (photoURL == null)
              ? fallback
              : CachedNetworkImage(
                  imageUrl: photoURL,
                  placeholder: (context, url) => Container(),
                  errorWidget: (context, url, error) => fallback,
                  ...
Run Code Online (Sandbox Code Playgroud)

一个 hacky 的替代方案是只提供一个不可路由的 URL,这肯定会失败(例如https://0.0.0.0/)。


Joh*_*Joe 1

也许你可以做这样的事情。CacheNetworkImage根据您的网址创建两个。一个是 null,另一个是 not null。

child: (controller.user?.photoURL == null) ?
 CacheNetworkImage ( // with CircleAvatar ) : CacheNetworkImage(// with image path)
Run Code Online (Sandbox Code Playgroud)