我正在构建一个跟踪包裹的应用程序。UICollectionView中的每个单元格都包含包裹的名称和包裹的交付状态。我的集合视图的数据源是一个项目数组。
Item类看起来像这样。
class Item {
var name: String
var carrier: String
var trackingNumber: String
var status: String //obtained via API get request at some point after initialization
}
我想实现两个功能:添加一个项目(并随后触发所有项目的更新)和只触发所有项目的更新。这就是我的ViewController的基本样子。
class PackagesController: UICollectionViewController, UICollectionViewDelegateFlowLayout {
var items: [Item]?
override func viewDidLoad() {super.viewDidLoad()}
override func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
return items.count
}
override func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
//return an item cell
//Is this where I should make the API request?
}
}
我的问题是:
我应该在哪里发出API请求(为了达到最高效率)?
我怎样才能在用户请求时更新所有项目的信息(不知道循环浏览项目数组是否会导致集合视图重载)?
我的代码目前的结构是否有一些内在的问题,或者有什么更好的方法来组织我的代码以达到预期的目的?
到目前为止,你写的代码看起来基本没问题。
我建议做一些修改。
Item
应该是一个结构,而不是一个类,而且它的成员应该是常数 (let
),除非你有非常好的具体理由。String?
)我应该在这里进行API请求吗?
不要在这里做网络请求或任何复杂的事情。cellForItemAt
. 只需从你的数据源(即你的项目数组)中获取相应的记录,然后将其填充到单元格中即可。
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
// get a cell
let cell = collectionView.dequeueResuableCell(withIdentifier: "yourCellIdentifier", indexPath: indexPath) as! YourCellClass
// get the data
let item = self.items[indexPath.row]
// populate the cell with the data
cell.setup(with: data) // you need to implement this in your cell
return cell
}
如何根据用户的要求更新所有项目的信息?
进行相应的网络请求计算或任何必要的计算,得到结果后,覆盖你的 items
数组和调用 reloadData()
的方法中。把这个放在你可以调用的方法中,例如作为按钮点击的动作,当然也可以在你的集合视图最初显示时调用。