Fix timeline state restoration not returning to correct scroll position in certain circumstances

All of the work done by the restoreInitial callback needs to be async,
so that when the TimelineLikeController signals that the loading
indicator should be removed, the collection view is in the right place.

Closes #439
This commit is contained in:
Shadowfacts 2023-12-14 18:28:22 -05:00
parent e09935125f
commit eb61043867
1 changed files with 10 additions and 11 deletions

View File

@ -420,7 +420,7 @@ class TimelineViewController: UIViewController, TimelineLikeCollectionViewContro
}
let hasStatusesToRestore = await loadStatusesToRestore(position: position)
if hasStatusesToRestore {
applyItemsToRestore(position: position)
await applyItemsToRestore(position: position)
loaded = true
}
case .mastodon:
@ -443,7 +443,7 @@ class TimelineViewController: UIViewController, TimelineLikeCollectionViewContro
position.centerStatusID = centerStatusID
let hasStatusesToRestore = await loadStatusesToRestore(position: position)
if hasStatusesToRestore {
applyItemsToRestore(position: position)
await applyItemsToRestore(position: position)
}
mastodonController.persistentContainer.viewContext.delete(position)
}
@ -532,7 +532,7 @@ class TimelineViewController: UIViewController, TimelineLikeCollectionViewContro
}
@MainActor
private func applyItemsToRestore(position: TimelinePosition) {
private func applyItemsToRestore(position: TimelinePosition) async {
var snapshot = NSDiffableDataSourceSnapshot<Section, Item>()
snapshot.appendSections([.statuses])
let statusIDs = position.statusIDs
@ -545,14 +545,13 @@ class TimelineViewController: UIViewController, TimelineLikeCollectionViewContro
"statusIDs": position.statusIDs
]
SentrySDK.addBreadcrumb(crumb)
dataSource.apply(snapshot, animatingDifferences: false) {
if let centerStatusID,
let index = statusIDs.firstIndex(of: centerStatusID) {
self.scrollToItem(item: items[index])
stateRestorationLogger.info("TimelineViewController: restored statuses with center ID \(centerStatusID)")
} else {
stateRestorationLogger.fault("TimelineViewController: restored statuses, but couldn't find center ID")
}
await apply(snapshot, animatingDifferences: false)
if let centerStatusID,
let index = statusIDs.firstIndex(of: centerStatusID) {
self.scrollToItem(item: items[index])
stateRestorationLogger.info("TimelineViewController: restored statuses with center ID \(centerStatusID)")
} else {
stateRestorationLogger.fault("TimelineViewController: restored statuses, but couldn't find center ID")
}
}