用 firebase 数据库和存储填充表视图?
Filling a tableview with firebase database and storage?
我有一个表格视图,我想用 firebase 数据填充,还有一个我存储在存储器中的图像。
我最初的游戏计划是 运行 firebase 的观察者,对于快照中的每个项目,填充一个 firebase 数据数组并从具有相同快照名称的存储中提取数据并将其放入另一个数组中两者都会匹配,然后在我的单元格中,我会用图像数组的 indexpath.row 和数据数组中的数据填充图像,它会匹配并且很酷。
这次崩溃和烧毁是因为我猜从存储中下载图像比提取信息花费的时间更长?并且图像数组的填充速度比数据慢,所以我遇到了图像 [indexPath.row] 超出范围的崩溃。
用数据库和存储中的数据填充表视图的正确方法是什么?
编辑:
我的 firebase 数据如下:
users
02938409283049829304
Category
Cats : true
Dogs: true
这就是我想要做的:
REF_USERS.child(currentUserUID).child("Category").observeEventType(.Value) { ( snapshot: FIRDataSnapshot) in
self.categoriesArray = []
self.imagesArray = []
if let snapshots = snapshot.children.allObjects as? [FIRDataSnapshot] {
for snap in snapshots {
self.categoryArray.append(snap.key)
let pictureRef = DataService.ds.REF_BASE_STORAGE.child(self.currentUserUID).child(String(snap.key))
pictureRef.dataWithMaxSize(9809898999098098 /* no idea what to put here*/) { (data, error) -> Void in
if (error != nil) {
print(error)
} else {
let picture : UIImage! = UIImage(data: data!)
self.imagesArray.append(picture)
print(self.imagesArray.count)
}
}
self.tableView.reloadData()
所以我希望它的阅读方式是:
转到用户并查看他们的类别。我正在寻找 post 它的名称,所以我只使用密钥。键名与存入存储时的图片一模一样,所以我用那个键名从存储中抓取照片。
let pictureRef = DataService.ds.REF_BASE_STORAGE.child(self.currentUserUID).child(String(snap.key))
我将数据库中的数据添加到一个数组,将存储中的图像添加到另一个数组,然后在制作单元格时,我只需将数据设置为数据[indexPath.row]并将图像设置为图像[indexPath.row]。当我执行 images.count 和 data.count 并且我在两者中都有 3 个东西时,我的图像落后 3 个,所以我猜这就是我得到图像 [indexPath.row] 超出范围错误的地方.
我觉得你能做到这一点的最好方法是显示占位符图像,或者为你从数据库调用的每个图像加载图标。当图像进来时,您相应地更新 tableView。
您可以这样做的另一种方法是 运行 异步请求,一旦所有进程完成,您就可以一起显示所有图像。
您甚至可以显示加载屏幕并让图像在显示 tableView 之前加载。
您所要做的就是在开始将图像添加到 tableView 之前确保图像存在,并确保内存使用不会过多。
I usually load images asynchronously and I have a delegate method that fires when download is complete and will refresh the tableview when new data/image is downloaded.
Making a placeholder image and maybe with a spinning loader icon would be great to display before the images get's downloaded.
编辑:
You need to call self.tableview.reload() in the pictureRef.dataWithMaxSize method.
Since the download is async your tableview will now reload when the method REF_USERS.child is complete and not necessarily when the image is downloaded.
So either place self.tableview.reloadData in your else claus in pictureRef.dataWithMaxSize or make a delegate method in the very same spot to handle finished downloaded images.
我有一个表格视图,我想用 firebase 数据填充,还有一个我存储在存储器中的图像。
我最初的游戏计划是 运行 firebase 的观察者,对于快照中的每个项目,填充一个 firebase 数据数组并从具有相同快照名称的存储中提取数据并将其放入另一个数组中两者都会匹配,然后在我的单元格中,我会用图像数组的 indexpath.row 和数据数组中的数据填充图像,它会匹配并且很酷。
这次崩溃和烧毁是因为我猜从存储中下载图像比提取信息花费的时间更长?并且图像数组的填充速度比数据慢,所以我遇到了图像 [indexPath.row] 超出范围的崩溃。
用数据库和存储中的数据填充表视图的正确方法是什么?
编辑:
我的 firebase 数据如下:
users
02938409283049829304
Category
Cats : true
Dogs: true
这就是我想要做的:
REF_USERS.child(currentUserUID).child("Category").observeEventType(.Value) { ( snapshot: FIRDataSnapshot) in
self.categoriesArray = []
self.imagesArray = []
if let snapshots = snapshot.children.allObjects as? [FIRDataSnapshot] {
for snap in snapshots {
self.categoryArray.append(snap.key)
let pictureRef = DataService.ds.REF_BASE_STORAGE.child(self.currentUserUID).child(String(snap.key))
pictureRef.dataWithMaxSize(9809898999098098 /* no idea what to put here*/) { (data, error) -> Void in
if (error != nil) {
print(error)
} else {
let picture : UIImage! = UIImage(data: data!)
self.imagesArray.append(picture)
print(self.imagesArray.count)
}
}
self.tableView.reloadData()
所以我希望它的阅读方式是:
转到用户并查看他们的类别。我正在寻找 post 它的名称,所以我只使用密钥。键名与存入存储时的图片一模一样,所以我用那个键名从存储中抓取照片。
let pictureRef = DataService.ds.REF_BASE_STORAGE.child(self.currentUserUID).child(String(snap.key))
我将数据库中的数据添加到一个数组,将存储中的图像添加到另一个数组,然后在制作单元格时,我只需将数据设置为数据[indexPath.row]并将图像设置为图像[indexPath.row]。当我执行 images.count 和 data.count 并且我在两者中都有 3 个东西时,我的图像落后 3 个,所以我猜这就是我得到图像 [indexPath.row] 超出范围错误的地方.
我觉得你能做到这一点的最好方法是显示占位符图像,或者为你从数据库调用的每个图像加载图标。当图像进来时,您相应地更新 tableView。
您可以这样做的另一种方法是 运行 异步请求,一旦所有进程完成,您就可以一起显示所有图像。
您甚至可以显示加载屏幕并让图像在显示 tableView 之前加载。
您所要做的就是在开始将图像添加到 tableView 之前确保图像存在,并确保内存使用不会过多。
I usually load images asynchronously and I have a delegate method that fires when download is complete and will refresh the tableview when new data/image is downloaded.
Making a placeholder image and maybe with a spinning loader icon would be great to display before the images get's downloaded.
编辑:
You need to call self.tableview.reload() in the pictureRef.dataWithMaxSize method. Since the download is async your tableview will now reload when the method REF_USERS.child is complete and not necessarily when the image is downloaded. So either place self.tableview.reloadData in your else claus in pictureRef.dataWithMaxSize or make a delegate method in the very same spot to handle finished downloaded images.