iOS 14 UICollectionView scrollToItem not working
If you are using UICollectionViewDiffableDataSource, based on the limited information, I'm going to assume that you are trying to call scrollToItemAtIndexPath: in the completion block of your data source update. In iOS 14, it seems like UICollectionView will not perform the first layout until the UICollectionView has entered the window. This means that if you are loading your data in viewDidLoad, then it is possible that cells won't actually have done laying out when the completion block is called.
If this is the case, you can simply call collectionView:scrollToItemAtIndexPath:animated: during viewDidAppear: since that will guarantee that the UICollectionView is already in the UIWindow.
I can't put this code into viewWillAppear because layout hasn't occurred yet.
I did end up taking this advice. But to get around the flashing, I set the alpha value of the collectionView to 0 in viewDidLoad, then in viewDidAppear I set alpha to 1. I'm not really happy with this solution, but anything else I've tried hasn't worked. I wish I had a better approach to this.
Why don't you set the animate into false?
collectionView.scrollToItem(at: centerIndexPath, at: .right, animated: false)
My working solution (hack) is to introduce an empty cell that gets returned when we are initially scrolling.
`class EmptyVideoCellBeforeScrollingCollectionCell: UICollectionViewCell { static let ID = "EmptyVideoCellBeforeScrollingCollectionCell" }
var scrollToIndex: IndexPath?
let dataSource = HashableDataSource(collectionView: collectionView) { [weak self] (collectionView, indexPath, item) -> UICollectionViewCell? in guard let self = self else { return nil } if let idx = self.scrollToIndex{ if idx != indexPath{ if let cell = collectionView.dequeueReusableCell(withReuseIdentifier: EmptyVideoCellBeforeScrollingCollectionCell.ID, for: indexPath) as? EmptyVideoCellBeforeScrollingCollectionCell { return cell } } }
override func viewWillAppear(_ animated: Bool) { super.viewWillAppear(animated) if let idx = self.scrollToIndex{ self.feedCollectionView.scrollToItem(at: idx, at: .top, animated: false) self.scrollToIndex = nil } }`
方法scrollToItemAtIndexPath
失效是由于开启了pagingEnabled
属性导致的,因此可以像下面这样处理:
_collectionView.pagingEnabled = NO;
[_collectionView scrollToItemAtIndexPath:indexPath atScrollPosition:position animated:animated];
_collectionView.pagingEnabled = YES;