Reconfigure visible updates when refreshing

Closes #300
This commit is contained in:
Shadowfacts 2023-09-26 09:42:39 -04:00
parent 1b42cd7816
commit 3ba1a00257
4 changed files with 49 additions and 0 deletions

View File

@ -25,6 +25,8 @@ class NotificationsCollectionViewController: UIViewController, TimelineLikeColle
private(set) var collectionView: UICollectionView! private(set) var collectionView: UICollectionView!
private(set) var dataSource: UICollectionViewDiffableDataSource<Section, Item>! private(set) var dataSource: UICollectionViewDiffableDataSource<Section, Item>!
var reconfigureVisibleItemsOnEndDecelerating: Bool = false
private var newer: RequestRange? private var newer: RequestRange?
private var older: RequestRange? private var older: RequestRange?
@ -662,6 +664,13 @@ extension NotificationsCollectionViewController: UICollectionViewDelegate {
func collectionView(_ collectionView: UICollectionView, willPerformPreviewActionForMenuWith configuration: UIContextMenuConfiguration, animator: UIContextMenuInteractionCommitAnimating) { func collectionView(_ collectionView: UICollectionView, willPerformPreviewActionForMenuWith configuration: UIContextMenuConfiguration, animator: UIContextMenuInteractionCommitAnimating) {
MenuPreviewHelper.willPerformPreviewAction(animator: animator, presenter: self) MenuPreviewHelper.willPerformPreviewAction(animator: animator, presenter: self)
} }
func scrollViewDidEndDecelerating(_ scrollView: UIScrollView) {
if reconfigureVisibleItemsOnEndDecelerating {
reconfigureVisibleItemsOnEndDecelerating = false
reconfigureVisibleCells()
}
}
} }
extension NotificationsCollectionViewController: UICollectionViewDragDelegate { extension NotificationsCollectionViewController: UICollectionViewDragDelegate {

View File

@ -32,6 +32,8 @@ class ProfileStatusesViewController: UIViewController, TimelineLikeCollectionVie
private(set) var dataSource: UICollectionViewDiffableDataSource<Section, Item>! private(set) var dataSource: UICollectionViewDiffableDataSource<Section, Item>!
private(set) var headerCell: ProfileHeaderCollectionViewCell? private(set) var headerCell: ProfileHeaderCollectionViewCell?
var reconfigureVisibleItemsOnEndDecelerating: Bool = false
private(set) var state: State = .unloaded private(set) var state: State = .unloaded
init(accountID: String?, kind: Kind, owner: ProfileViewController) { init(accountID: String?, kind: Kind, owner: ProfileViewController) {
@ -627,6 +629,13 @@ extension ProfileStatusesViewController: UICollectionViewDelegate {
return true return true
} }
} }
func scrollViewDidEndDecelerating(_ scrollView: UIScrollView) {
if reconfigureVisibleItemsOnEndDecelerating {
reconfigureVisibleItemsOnEndDecelerating = false
reconfigureVisibleCells()
}
}
} }
extension ProfileStatusesViewController: UICollectionViewDragDelegate { extension ProfileStatusesViewController: UICollectionViewDragDelegate {

View File

@ -42,6 +42,8 @@ class TimelineViewController: UIViewController, TimelineLikeCollectionViewContro
private(set) var collectionView: UICollectionView! private(set) var collectionView: UICollectionView!
private(set) var dataSource: UICollectionViewDiffableDataSource<Section, Item>! private(set) var dataSource: UICollectionViewDiffableDataSource<Section, Item>!
var reconfigureVisibleItemsOnEndDecelerating: Bool = false
private var cancellables = Set<AnyCancellable>() private var cancellables = Set<AnyCancellable>()
private var userActivityNeedsUpdate = PassthroughSubject<Void, Never>() private var userActivityNeedsUpdate = PassthroughSubject<Void, Never>()
// the last time this VC disappeared or the scene was backgrounded while it was active, used to decide if we want to check for present when reappearing // the last time this VC disappeared or the scene was backgrounded while it was active, used to decide if we want to check for present when reappearing
@ -1317,6 +1319,11 @@ extension TimelineViewController: UICollectionViewDelegate {
func scrollViewDidEndDecelerating(_ scrollView: UIScrollView) { func scrollViewDidEndDecelerating(_ scrollView: UIScrollView) {
userActivityNeedsUpdate.send() userActivityNeedsUpdate.send()
if reconfigureVisibleItemsOnEndDecelerating {
reconfigureVisibleItemsOnEndDecelerating = false
reconfigureVisibleCells()
}
} }
func scrollViewDidScroll(_ scrollView: UIScrollView) { func scrollViewDidScroll(_ scrollView: UIScrollView) {

View File

@ -21,6 +21,8 @@ protocol TimelineLikeCollectionViewController: UIViewController, TimelineLikeCon
var collectionView: UICollectionView! { get } var collectionView: UICollectionView! { get }
var dataSource: UICollectionViewDiffableDataSource<Section, Item>! { get } var dataSource: UICollectionViewDiffableDataSource<Section, Item>! { get }
var reconfigureVisibleItemsOnEndDecelerating: Bool { get set }
} }
protocol TimelineLikeCollectionViewSection: Hashable, Sendable { protocol TimelineLikeCollectionViewSection: Hashable, Sendable {
@ -125,6 +127,18 @@ extension TimelineLikeCollectionViewController {
var config: ToastConfiguration var config: ToastConfiguration
if let error = error as? Self.Error, if let error = error as? Self.Error,
error == .allCaughtUp { error == .allCaughtUp {
// Reconfigure visible items to update timestamps.
#if targetEnvironment(macCatalyst)
let isRefreshing = false
#else
let isRefreshing = collectionView.refreshControl?.isRefreshing ?? false
#endif
if isRefreshing {
reconfigureVisibleItemsOnEndDecelerating = true
} else {
reconfigureVisibleCells()
}
config = ToastConfiguration(title: "You're all caught up") config = ToastConfiguration(title: "You're all caught up")
config.edge = .top config.edge = .top
config.dismissAutomaticallyAfter = 2 config.dismissAutomaticallyAfter = 2
@ -204,6 +218,16 @@ extension TimelineLikeCollectionViewController {
await task.value await task.value
} }
@MainActor
func reconfigureVisibleCells() {
let items = collectionView.indexPathsForVisibleItems.compactMap { dataSource.itemIdentifier(for: $0) }
if !items.isEmpty {
var snapshot = dataSource.snapshot()
snapshot.reconfigureItems(items)
dataSource.apply(snapshot, animatingDifferences: false)
}
}
func registerTimelineLikeCells() { func registerTimelineLikeCells() {
collectionView.register(LoadingCollectionViewCell.self, forCellWithReuseIdentifier: "loadingIndicator") collectionView.register(LoadingCollectionViewCell.self, forCellWithReuseIdentifier: "loadingIndicator")
collectionView.register(ConfirmLoadMoreCollectionViewCell.self, forCellWithReuseIdentifier: "confirmLoadMore") collectionView.register(ConfirmLoadMoreCollectionViewCell.self, forCellWithReuseIdentifier: "confirmLoadMore")