firebase - 更改 Firebase Firestore 上的数据后更新 Flutter UI
问题描述
我有一个带有用户名、电子邮件和个人资料图片的个人资料页面的应用程序。
我想要做的是,用户单击一个按钮来更改个人资料图片,打开一个带有简单圆形头像小部件和一个按钮的新页面,该页面会将图像上传到 Firebase 存储和 Firebase Firestore,添加到 Firestore该特定当前用户 uid 的集合。
一切正常,我可以看到 Firebase 存储上的更改,由 uid + 当前用户集合上的 URL 添加的图像。
这是edit_user_image_screen的代码:
import 'dart:io';
import 'package:cloud_firestore/cloud_firestore.dart';
import 'package:firebase_auth/firebase_auth.dart';
import 'package:firebase_storage/firebase_storage.dart';
import 'package:flutter/material.dart';
import 'package:image_picker/image_picker.dart';
import 'package:tradie_app/scr/providers/authService.dart';
import 'package:tradie_app/scr/widgets/loading.dart';
class EditCompanyImageScreen extends StatefulWidget {
@override
_EditCompanyImageScreenState createState() => _EditCompanyImageScreenState();
}
class _EditCompanyImageScreenState extends State<EditCompanyImageScreen> {
// Keep track of the form for validation
final _formKey = GlobalKey<FormState>();
// Loading Icon
bool loading = false;
final AuthService _authService = AuthService();
final FirebaseAuth _firebaseAuth = FirebaseAuth.instance;
final FirebaseFirestore _firebaseFirestore = FirebaseFirestore.instance;
File _image;
Future getImage(bool gallery) async {
ImagePicker picker = ImagePicker();
PickedFile pickedFile;
// Let user select photo from gallery
if (gallery) {
pickedFile = await picker.getImage(
source: ImageSource.gallery,
);
}
setState(() {
if (pickedFile != null) {
_image = File(pickedFile.path);
uploadFile(_image); // Use if you only need a single picture
} else {
print('No image selected.');
}
});
}
Future<String> uploadFile(File image) async {
String downloadURL;
Reference ref = FirebaseStorage.instance
.ref()
.child("images/${_firebaseAuth.currentUser.uid}");
await ref.putFile(image);
downloadURL = await ref.getDownloadURL();
return downloadURL;
}
Future uploadToFirebase() async {
final CollectionReference users =
_firebaseFirestore.collection("Companies");
final String uid = _firebaseAuth.currentUser.uid;
String url = await uploadFile(
_image); // this will upload the file and store url in the variable 'url'
await users.doc(uid).update({'url': url});
final result = await users.doc(uid).get();
return result.data()["url"];
}
@override
Widget build(BuildContext context) {
return loading
? Loading()
: Scaffold(
appBar: AppBar(
title: Text("Update Profile Image"),
),
body: Form(
key: _formKey,
child: Column(
children: [
Container(
child: Stack(
children: <Widget>[
Align(
alignment: Alignment.center,
child: IconButton(
icon: Icon(Icons.camera_alt),
onPressed: () async {
getImage(true);
},
),
),
Container(
child: _image != null
? Container(
height: 200,
width: 200,
decoration: BoxDecoration(
image: DecorationImage(
image: FileImage(
_image,
),
fit: BoxFit.contain),
),
)
: Container(
decoration: BoxDecoration(
color: Colors.grey[200],
borderRadius: BorderRadius.circular(50),
),
width: 100,
height: 100,
child: Icon(
Icons.camera_alt,
color: Colors.grey[800],
),
),
),
],
),
),
Row(
children: [
ElevatedButton(
style: ElevatedButton.styleFrom(
primary: Colors.black,
),
child: Text(
"Submit",
style: TextStyle(color: Colors.white),
),
onPressed: () async {
uploadToFirebase();
Navigator.pop(context);
},
),
],
),
],
),
),
);
}
}
在 company_profile_screen 上,我有这段代码:
Stream getCompanyImageData() async* {
final CollectionReference users =
_firebaseFirestore.collection("Companies");
final String uid = _firebaseAuth.currentUser.uid;
final result = await users.doc(uid).get();
yield result.data()["url"];
}
我的问题:
当我从 edit_user_image_screen 回到 company_screen 时,App UI 没有更新,我可以在 Firebase 上看到更改,如果我重新加载 Android Studio,我可以在 UI 上看到更改,但不是自动的。
这是我在 company_screen 上显示图像的代码:
Column(
children: [
StreamBuilder(
stream: getCompanyImageData(),
builder: (BuildContext context,
AsyncSnapshot snapshot) {
if (snapshot.connectionState ==
ConnectionState.waiting) {
return Center(
child: CircularProgressIndicator(),
);
}
return Image.network(
snapshot.data.toString(),
width: 100,
height: 100,
);
},
),
],
),
解决方案
这将取决于您的状态管理,
CollectionRef.users.doc(ViewModelUser.user.value.mobile).snapshots().listen((event) {
ViewModelUser.setUser(UserModel.fromJson(event.data()));
});
这是我的代码,我在其中监听我的个人资料中的更改,当有更改时,firebase 向我发送更新的数据并且我更新了我的 userData,我的状态管理完成了更新 UI 的其余部分。
推荐阅读
- python - 在我的代码中寻找漏洞(拆分方法)
- sql - 计算一列可以取的 3 个不同的值
- sql-server - 想要捕获特定负载的负载详细信息(而不是按天)
- r - R- 转换为 TS
- windows - 在 Windows 10 中使用 ssh 的 Git 远程存储库 - 有没有办法让它完美运行?
- firebase - Firebase 云消息传递 cURL POST 显示错误 403
- node.js - 如何销毁存储在 MongoDB(NodeJS)中的会话
- azure - Azure 函数的 ARM 模板忽略 preWarmedInstanceCount 设置
- javascript - 为什么 allSettled 不会拒绝一个嘲笑的笑话承诺?
- python - yolov4 自定义对象检测在训练期间出错