首页 > 解决方案 > 如何从 firestore 数据库渲染图像

问题描述

我正在做一个项目,最终在从 firestore 渲染图像时出错,但仍然不明白到底是什么问题。我对 Flutter 很陌生。这是我上传的方式

RoundedButton(
  buttonName: 'Add Event',
  onPressed: () async{
    if(kIsWeb){
      await uploadFileWeb().then((value) => showToast(
        message: "Events Added Successfully",
        color: Colors.green,
      ));
      Navigator.pop(context);
    }
    else{
      await uploadFile().then((value) => showToast(
        message: "Events Added Successfully",
        color: Colors.green,
      ));
      Navigator.pop(context);
    }
  },
  color: Colors.green,
),

和功能

Future selectFile() async{
    final result = await FilePicker.platform.pickFiles(
      type: FileType.custom,
        allowMultiple: false,
        allowedExtensions: ['jpg']
    );
    if(result == null) return;
    final path = result.files.single.path!;
    setState(() {
      file = File(path);
    });
  }

  Future uploadFile() async{
    if(file == null) return;
    final fileName = basename(file!.path);
    final destination = 'events/$fileName';
    task = await FirebaseApi.uploadFile(destination, file!)!.then((_) async{
      DateTime time = DateTime.now();
      await FirebaseFirestore.instance.collection('activities').doc().set({
        'Name' : name,
        'Location': location,
        'Description' : description,
        'Price' : price,
        'Date' : date,
        'PhotoUrl': destination,
        'Type' : selectedType,
        'ts' : time,
      });
    });
  }

  void selectWebImage(){
    res.FileUploadInputElement uploadInput = res.FileUploadInputElement()..accept = 'image/*';
    uploadInput.click();

    uploadInput.onChange.listen((event) {
      webFile = uploadInput.files!.first;
      final reader = res.FileReader();
      reader.readAsDataUrl(webFile!);
      reader.onLoadEnd.listen((event) {

      });
    });
  }

  Future<void> uploadFileWeb()async {
    final dateTime = DateTime.now();
    final path = 'events/$dateTime';
    await FirebaseStorage.instance.refFromURL('gs://tembea-4d3c6.appspot.com')
        .child(path)
        .putBlob(webFile).then((_) async{
      DateTime time = DateTime.now();
      await FirebaseFirestore.instance.collection('activities').doc().set({
        'Name' : name,
        'Location': location,
        'Description' : description,
        'Price' : price,
        'Date' : date,
        'PhotoUrl': path,
        'Type' : selectedType,
        'ts' : time,
      });
    });
  }
}

这就是我尝试检索数据的方式

    final Stream<QuerySnapshot> activities = FirebaseFirestore
        .instance.collection('activities').orderBy('ts', descending: true).snapshots();
StreamBuilder<QuerySnapshot>(
  stream: activities,
    builder: (BuildContext context, AsyncSnapshot<QuerySnapshot> snapshot){
      if(snapshot.connectionState == ConnectionState.waiting){
        return const Center(
          child: CircularProgressIndicator(),
        );
      }
      final data = snapshot.requireData;
      return ListView.builder(
          scrollDirection: Axis.vertical,
          shrinkWrap: true,
        itemCount: data.size,
          itemBuilder: (context, index){
            if(data.docs[index]['Type'] == 'Event'){
              return Column(
                children: [
                  Row(
                    mainAxisAlignment: MainAxisAlignment.spaceBetween,
                    children: [
                      CircleAvatar(
                        backgroundColor: Colors.transparent,
                        radius: 40,
                        backgroundImage: NetworkImage(data.docs[index]['PhotoUrl']),
                      ),
                      Text( data.docs[index]['Name'], style:const TextStyle(
                          color: Colors.white,
                          fontSize: 20,
                          fontWeight: FontWeight.bold),

                      ),
                      Responsive.isWeb(context) ? ButtonBlue(
                        addLabel: 'Edit Event',
                        color: Colors.green,
                        onPressed: (){},
                        icon: const Icon(IconData(61161, fontFamily: 'MaterialIcons')),
                      ) : InkWell(
                        onTap: (){},
                        child: const Icon(IconData(61161, fontFamily: 'MaterialIcons')),
                      ),
                      Responsive.isWeb(context) ? ButtonBlue(
                        addLabel: 'Delete Event',
                        color: Colors.red,
                        onPressed: (){},
                        icon: const Icon(Icons.delete_outline,),
                      ): InkWell(
                        onTap: (){},
                        child:  const Icon(Icons.delete_outline,),
                      ),
                    ],
                  ),
                  const Divider(
                    color: Colors.white70,
                    height:40.0,
                  ),
                ],
              );
            }
            return Container();
          });
    },
)

它一直给我带来这个错误,我不知道该怎么办

Invalid argument(s): No host specified in URI file:///events/2021-11-16%2002:59:15.764

我整天都在做这个,似乎不明白。谁可以帮我这个事?

标签: flutter

解决方案


final path = 'events/$dateTime';在 Firestore 上,您使用as保存文档PhotoUrl,检索它时您正在读取字符串events/$dateTime并尝试将其用作NetworkImage.

NetworkImage然后尝试从该字符串创建一个 URI,这会导致本地文件 uri 并且无法从网络下载它。

基本上,在我看来,你实际上并没有上传图片,但没有完整的代码流很难说。


推荐阅读