如何从 UICollectionView.CellRegistration 访问更新的数据源
Posted
技术标签:
【中文标题】如何从 UICollectionView.CellRegistration 访问更新的数据源【英文标题】:How to access the updated datasource from the UICollectionView.CellRegistration 【发布时间】:2022-01-04 08:32:09 【问题描述】:我想知道为什么数据源的值会更新,但是当我从单元格注册访问单个值时,值没有改变。 下面的代码就是我的意思。
我有一个名为 Event 的结构体,它接受三个值,id、name 和 streamState
struct Event: Codable, Hashable
let id: String
let name: String
let streamState: String
struct Events: Codable
let streams: [Event]
在我的 EventDataSource 类中,我有一个事件数组和用于从后端获取事件数据的 fetchEvent 函数,为了简单起见,我只添加了 1 个数据(1 个事件),所以我知道事件数组只有现在有一个数据。
class EventDataSource
var events = [Event]()
func fetchEvents(completion: @escaping () -> Void)
AF.request(myEndpoint)
.validate()
.responseJSON response in
guard let data = response.data else return
let decoder: JSONDecoder = JSONDecoder()
var result: Events?
do
result = try decoder.decode(Events.self, from: data)
catch
print("error with fetch events: \(error)")
guard let final = result else return
self.events = final.streams
if events.count > 0
print("fetched first item: \(self.events[0].streamState), \(events[0].name)") // -> get the updated streamState with correct name
DispatchQueue.main.async
completion()
在上面的代码中,我添加了 if 语句 (events.count > 0
) 以确保更新事件的 streamState。 (更具体地说,事件的streamState从init
开始,但几秒钟后,它变成ready
,我得到ready
被打印出来,所以我想我可以说streamState在后端。)
我使用 CollectionViewListCell 显示事件数据,每当我使用 EventDataSource 中的 fetchEvents 函数更新事件数据时,我都会调用 displayEvents 函数来更新 collectionViewListCell。然后由于重新创建了单元格,因此也调用了 cellRegistration 部分。我打印了 event.streamState
中的内容,但它给了我原始值 (init
),即使 fetchEvents
函数中获取的数据清楚地给了我更新后的值 (ready
)。
class ListViewController: UIViewController, UICollectionViewDelegate
private var collectionViewDataSource: UICollectionViewDiffableDataSource<Section, Event>?
private var snapshot: NSDiffableDataSourceSnapshot<Section, Event>!
private var eventDataSource = EventDataSource()
override func viewDidLoad()
displayEvents()
configureDataSource()
func displayEvents()
snapshot = NSDiffableDataSourceSnapshot<Section, Event>()
snapshot.appendSections([.list])
snapshot.appendItems(eventDataSource.Events)
collectionViewDataSource?.apply(snapshot, animatingDifferences: false)
collectionView.reloadData()
func configureDataSource()
let cellRegistration = UICollectionView.CellRegistration<CustomListCell, Event> cell, indexPath, event in
print(event.streamState) // -> this value is not changed, only gives me the original value
cell.event = event
collectionViewDataSource = UICollectionViewDiffableDataSource<Section, Event (collectionView: collectionView) (collectionView, indexPath, event) -> UICollectionViewCell? in
let cell = collectionView.dequeueConfiguredReusableCell(using: cellRegistration, for: indexPath, item: event)
return cell
我查了一些其他文章并用谷歌搜索,但我仍然不知道为什么会打印更新的值。我现在感觉卡住了,这就是我发布这个问题的原因。如果有人能指出我正确的方向,请告诉我...
【问题讨论】:
【参考方案1】:在您的viewDidLoad()
实现中颠倒对configureDataSource()
和displayEvents()
的调用顺序,否则您将快照应用到nil
数据源。
另外,您将collectionViewDataSource
设置在configureDataSource()
的范围之外
【讨论】:
以上是关于如何从 UICollectionView.CellRegistration 访问更新的数据源的主要内容,如果未能解决你的问题,请参考以下文章
UICollectionView Cell Spacing 基于设备屏幕大小
ios . -- UICollectionView --cell 自适应