From 432a9dcaba2dfadb3990f02fb0778aab7214c035 Mon Sep 17 00:00:00 2001 From: Ian Luo Date: Fri, 12 Mar 2021 11:36:38 -0800 Subject: [PATCH 1/2] Fix `scrollToItem` appearing underneath sticky header When a `top` scroll position is used, the item will appear underneath the sticky section header. Now, we adjust the frame and use a manual content offset when sticky headers are enabled. When sticky headers are disabled or scrolling to a different position, we call the existing `scrollToItem` function on UICollectionView. --- ListableUI/Sources/ListView/ListView.swift | 35 ++++++++++++++++------ 1 file changed, 26 insertions(+), 9 deletions(-) diff --git a/ListableUI/Sources/ListView/ListView.swift b/ListableUI/Sources/ListView/ListView.swift index b14d8b5ea..564dc740c 100644 --- a/ListableUI/Sources/ListView/ListView.swift +++ b/ListableUI/Sources/ListView/ListView.swift @@ -424,27 +424,44 @@ public final class ListView : UIView, KeyboardObserverDelegate } return self.preparePresentationStateForScroll(to: toIndexPath) { - - let isAlreadyVisible: Bool = { - let frame = self.collectionViewLayout.frameForItem(at: toIndexPath) + let itemFrame = self.collectionViewLayout.frameForItem(at: toIndexPath) - return self.collectionView.contentFrame.contains(frame) - }() + let isAlreadyVisible = self.collectionView.contentFrame.contains(itemFrame) // If the item is already visible and that's good enough, return. if isAlreadyVisible && position.ifAlreadyVisible == .doNothing { return } - - animation.perform( - animations: { + + let scroll: () -> Void = { + let sectionHeader = self.collectionViewLayout.layout.content.sections[toIndexPath.section].header + + // Prevent the item from appearing underneath a sticky section header. + + if sectionHeader.isPopulated, + self.collectionViewLayout.layout.stickySectionHeaders, + position.position == .top { + + let itemFrameAdjustedForStickyHeaders = CGRect( + x: itemFrame.minX, + y: itemFrame.minY - sectionHeader.size.height, + width: itemFrame.width, + height: itemFrame.height + ) + self.performScroll(to: itemFrameAdjustedForStickyHeaders, scrollPosition: position) + + } else { self.collectionView.scrollToItem( at: toIndexPath, at: position.position.UICollectionViewScrollPosition, animated: false ) - }, + } + } + + animation.perform( + animations: scroll, completion: completion ) } From 3c5bb7a587393008dce9ebb1af71ce8d704e5aa1 Mon Sep 17 00:00:00 2001 From: Ian Luo Date: Fri, 12 Mar 2021 12:55:05 -0800 Subject: [PATCH 2/2] Add changelog message --- CHANGELOG.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 710b54271..97105ee85 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,8 @@ ### Fixed +- When calling `scrollToItem` with a `.top` scroll position, [the item no longer appears underneath sticky section headers](https://github.com/kyleve/Listable/pull/279). + ### Added - [Adds `scrollToSection`](https://github.com/kyleve/Listable/pull/277) to `ListActions` and `ListView`. To support this functionality, `Section` can now be queried with an `Identifier`. Also added `SectionPosition` to specify the top or bottom within a `Section`.