在 swift 中附加数组后,如何使 table 查看来自 Firebase Firestore 的加载数据
How to make table view load data from Firebase Firestore after array is appended in swift
我遇到过这种情况,我从 Firebase 获取数据,将其放入数组中,然后将其填充到我的 Table View
中。
但是 Table View
在函数完成将数据追加到数组之前加载数据。
因此,我总是得到 Index out of range
错误。
如果你们对我的情况有任何其他解决方案,请随时更正我的代码。
但是现在,我只能想办法让函数在 Table View
加载数据之前将数据追加到数组中。
希望你们明白我的意思。
代码如下:
import UIKit
import FirebaseFirestore
var arrayCurrentProduct = [currentProduct]()
var arrayRetrievedData: [String:Any] = [:]
var arrayConvertedPrice: [String] = []
override func viewDidLoad() {
super.viewDidLoad()
}
func initProduct(selectedProduct: String) {
arrayCurrentProduct = referProduct(productName: selectedProduct)
}
private func referProduct(productName: String) -> [currentProduct] {
switch productName {
case Product.Microsoft.rawValue:
getPrices(document: "Msft") { (_) in
self.convertPrice(Type: "std")
self.convertPrice(Type: "dc")
self.tableView.reloadData()
self.dismiss(animated: true, completion: nil)
DispatchQueue.main.async {
self.tableView.reloadData()
}
}
default:
break
}
return arrayCurrentProduct
}
private func getPrices(document: String, completion: @escaping (_ String:Any?) -> Void) {
retrievePrice(document: document) { [weak self] (data) in
guard let self = self else {return}
self.arrayRetrievedData = data
completion(self.arrayRetrievedData)
}
}
private func convertPrice(Type: String) {
formatterCode(formatter: formatter)
var priceFormatted = ""
guard let price = arrayRetrievedData[Type] else {return}
if let formattedPrice = formatter.string(from: price as! NSNumber) {
priceFormatted = formattedPrice
}
arrayConvertedPrice.append(priceFormatted)
}
func numberOfSections(in tableView: UITableView) -> Int {
return 2
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 4
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cellShowing = tableView.dequeueReusableCell(withIdentifier: ShowingTVCell.cellIdentifier, for: indexPath) as! ShowingTVCell
let cellInput = tableView.dequeueReusableCell(withIdentifier: InputTVCell.cellIdentifier, for: indexPath) as! InputTVCell
switch indexPath.section {
case 0:
cellShowing.labelName.text = microsoft[indexPath.row]
cellShowing.labelPrice.text = arrayConvertedPrice[indexPath.row] // Error index out of range
return cellShowing
case 1:
cellInput.labelSpec.text = microsoft[indexPath.row]
return cellInput
default:
return cellShowing
}
}
这里有一些流程:
我 select 一个产品,initProduct()
调用 --> referProduct()
调用 --> 从 Firebase 获取价格 --> 将价格转换为货币,附加到数组 -->由 Table View
加载
我也试过在某些地方放 reloadData()
但没用。
任何帮助将不胜感激。
提前谢谢你。
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 4
}
您在获取数据之前写了一个幻数 (4)。 tableView 尝试在没有数据的情况下为每个部分创建 4 行。您应该在获取数据后更新您的 numbersOfRowsInSection return 值。
我遇到过这种情况,我从 Firebase 获取数据,将其放入数组中,然后将其填充到我的 Table View
中。
但是 Table View
在函数完成将数据追加到数组之前加载数据。
因此,我总是得到 Index out of range
错误。
如果你们对我的情况有任何其他解决方案,请随时更正我的代码。
但是现在,我只能想办法让函数在 Table View
加载数据之前将数据追加到数组中。
希望你们明白我的意思。
代码如下:
import UIKit
import FirebaseFirestore
var arrayCurrentProduct = [currentProduct]()
var arrayRetrievedData: [String:Any] = [:]
var arrayConvertedPrice: [String] = []
override func viewDidLoad() {
super.viewDidLoad()
}
func initProduct(selectedProduct: String) {
arrayCurrentProduct = referProduct(productName: selectedProduct)
}
private func referProduct(productName: String) -> [currentProduct] {
switch productName {
case Product.Microsoft.rawValue:
getPrices(document: "Msft") { (_) in
self.convertPrice(Type: "std")
self.convertPrice(Type: "dc")
self.tableView.reloadData()
self.dismiss(animated: true, completion: nil)
DispatchQueue.main.async {
self.tableView.reloadData()
}
}
default:
break
}
return arrayCurrentProduct
}
private func getPrices(document: String, completion: @escaping (_ String:Any?) -> Void) {
retrievePrice(document: document) { [weak self] (data) in
guard let self = self else {return}
self.arrayRetrievedData = data
completion(self.arrayRetrievedData)
}
}
private func convertPrice(Type: String) {
formatterCode(formatter: formatter)
var priceFormatted = ""
guard let price = arrayRetrievedData[Type] else {return}
if let formattedPrice = formatter.string(from: price as! NSNumber) {
priceFormatted = formattedPrice
}
arrayConvertedPrice.append(priceFormatted)
}
func numberOfSections(in tableView: UITableView) -> Int {
return 2
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 4
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cellShowing = tableView.dequeueReusableCell(withIdentifier: ShowingTVCell.cellIdentifier, for: indexPath) as! ShowingTVCell
let cellInput = tableView.dequeueReusableCell(withIdentifier: InputTVCell.cellIdentifier, for: indexPath) as! InputTVCell
switch indexPath.section {
case 0:
cellShowing.labelName.text = microsoft[indexPath.row]
cellShowing.labelPrice.text = arrayConvertedPrice[indexPath.row] // Error index out of range
return cellShowing
case 1:
cellInput.labelSpec.text = microsoft[indexPath.row]
return cellInput
default:
return cellShowing
}
}
这里有一些流程:
我 select 一个产品,initProduct()
调用 --> referProduct()
调用 --> 从 Firebase 获取价格 --> 将价格转换为货币,附加到数组 -->由 Table View
我也试过在某些地方放 reloadData()
但没用。
任何帮助将不胜感激。
提前谢谢你。
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 4
}
您在获取数据之前写了一个幻数 (4)。 tableView 尝试在没有数据的情况下为每个部分创建 4 行。您应该在获取数据后更新您的 numbersOfRowsInSection return 值。