Simultaneously scrolling ScrollViews with SwiftUI support

Overview

SimultaneouslyScrollView

Simultaneously scrolling ScrollViews with SwiftUI support


Build SwiftLint

Installation

Using Swift Package Manager

Swift Package Manager is a tool for managing the distribution of Swift frameworks. It integrates with the Swift build system to automate the process of downloading, compiling, and linking dependencies.

Using Xcode

To integrate using Xcode 13, open your Project file and specify it in Project > Package Dependencies using the following URL:

https://github.com/stonko1994/SimultaneouslyScrollView.git

Usage

import SimultaneouslyScrollView

Synchronize multiple UIScrollViews

  1. Create an SimultaneouslyScrollViewHandler instance by using the factory method and the create function:
    let simultaneouslyScrollViewHandler = SimultaneouslyScrollViewHandlerFactory.create()
  2. Register UIScrollViews that should be synchronized:
    simultaneouslyScrollViewHandler.register(scrollView: scrollView)

SwiftUI support

To enable simultaneously scrolling in SwiftUI we need to utilize another library that allows access to the underlying UIScrollView for a SwiftUI.ScrollView.

SwiftUI-Introspect 🚀

Synchronize multiple ScrollViews

  1. Follow the installataion steps from SwiftUI-Introspect

  2. Import Introspect in addition to SimultaneouslyScrollView

    import SimultaneouslyScrollView
    import Introspect
  3. Access the UIScrollView from your ScrollView and register it to the SimultaneouslyScrollViewHandler.

    ScrollView {
        ...
    }
    .introspectScrollView { simultaneouslyScrollViewHandler.register(scrollView: $0) }
  4. That's it 🥳 🎉

    I recommend storing the simultaneouslyScrollViewHandler inside some view-model. E.g. an @ObservedObject or a @StateObject.

How it works

SwiftUI doesn't provide any API to specify the contentOffset for ScrollViews. Therefore we need to access the underlying UIKit element and set the contentOffset there. This is where SwiftUI-Introspect comes in handy by providing access to the UIKit elements.

As every redraw of the View creates a new ScrollView and a new UIScrollView instance, it is important not to store strong references of the registered UIScrollViews. The SimultaneouslyScrollViewHandler manages this using a custom implementation using the WeakObjectStore.

When a ScrollView is scrolled by the user, the SimultaneouslyScrollViewHandler gets notified about this via the UIScrollViewDelegate. When this happens, the contentOffset of every other registered UIScrollView will be adapted to the new contentOffset of the currently scrolled UIScrollView.

Example

I use this package in one of my own Apps that is currently in the Appstore. So there shouldn't be any issues using this in any production code except the possibility that new SwiftUI versions could break SwiftUI-Introspect.

Please note that this introspection method might break in future SwiftUI releases. Future implementations might not use the same hierarchy, or might not use UIKit elements that are being looked for. Though the library is unlikely to crash, the .introspect() method will not be called in those cases.

Download Scoretastic 🥳


Buy Me A Coffee

You might also like...
SwiftUI, peek scrolling animation and card tapped animation, using GeometryReader
SwiftUI, peek scrolling animation and card tapped animation, using GeometryReader

SwiftUI, peek scrolling animation and card tapped animation, using GeometryReader, follow the livestream tutorial by MengTo.

A small project written with SwiftUI achieves a scrolling effect similar to Apple Music lyrics.
A small project written with SwiftUI achieves a scrolling effect similar to Apple Music lyrics.

Music Lyrics scrolling animation effect Since the iOS/iPadOS 13 update, Apple has brought a new scrolling lyrics feature to Apple Music. The album im

Horizontal and Vertical collection view for infinite scrolling that was designed to be used in SwiftUI
Horizontal and Vertical collection view for infinite scrolling that was designed to be used in SwiftUI

InfiniteScroller Example struct ContentView: View { @State var selected: Int = 1 var body: some View { InfiniteScroller(direction: .ve

SwiftUI stack views with paged scrolling behaviour.

SwiftUI PageView SwiftUI stack views with paged scrolling behaviour. HPageView A view that arranges its children in a horizontal line, and provides pa

Scrollable UINavigationBar that follows the scrolling of a UIScrollView
Scrollable UINavigationBar that follows the scrolling of a UIScrollView

A custom UINavigationController that enables the scrolling of the navigation bar alongside the scrolling of an observed content view Versioning notes

A container view that responds to scrolling of UIScrollView
A container view that responds to scrolling of UIScrollView

FlexibleHeader A container view that responds to scrolling of UIScrollView. normal threshold FlexibleHeaderExecutantType Getting Started Progressive I

Infinite paging controller, scrolling through contents and title bar scrolls with a delay
Infinite paging controller, scrolling through contents and title bar scrolls with a delay

PageController PageController is infinite paging controller, scrolling through contents and title bar scrolls with a delay. Then it provide user inter

List a collection of items in a horizontally scrolling view. A scaling factor controls the size of the items relative to the center.
List a collection of items in a horizontally scrolling view. A scaling factor controls the size of the items relative to the center.

CAROUSEL List a collection of items in a horizontally scrolling view. A scaling factor controls the size of the items relative to the center. We speci

Optimizing UITableViewCell For Fast Scrolling
Optimizing UITableViewCell For Fast Scrolling

DWURecyclingAlert Your code usually has less than ten milliseconds to run before it causes a frame drop.1 Visualize Bad Drawings On The Fly Injects 4

Give pull-to-refresh & infinite scrolling to any UIScrollView with 1 line of code.

SVPullToRefresh + SVInfiniteScrolling These UIScrollView categories makes it super easy to add pull-to-refresh and infinite scrolling fonctionalities

ESPullToRefresh is an easy-to-use component that give pull-to-refresh and infinite-scrolling implemention for developers.
ESPullToRefresh is an easy-to-use component that give pull-to-refresh and infinite-scrolling implemention for developers.

ESPullToRefresh is an easy-to-use component that give pull-to-refresh and infinite-scrolling implemention for developers.

Scrolling the image as a background in Swift
Scrolling the image as a background in Swift

Scrolling the image as a background!

Flix is an app the uses the the movies database to get upcoming movies, with infinite scrolling
Flix is an app the uses the the movies database to get upcoming movies, with infinite scrolling

Flix Flix is an app the uses the the movies database to get upcoming movies, with infinite scrolling Libraries Flix uses Swift Package Manager (SPM),

A custom image view that implements device motion scrolling
A custom image view that implements device motion scrolling

YXTMotionView A custom image view that implements device motion scrolling Installation CocoaPods Add the dependency to your Podfile: platform :ios pod

iOS library for quickly displaying images while scrolling

Fast Image Cache is an efficient, persistent, and—above all—fast way to store and retrieve images in your iOS application. Part of any good iOS applic

Swift image slideshow with circular scrolling, timer and full screen viewer
Swift image slideshow with circular scrolling, timer and full screen viewer

🖼 ImageSlideshow Customizable Swift image slideshow with circular scrolling, timer and full screen viewer 📱 Example To run the example project, clon

Infinite paging controller, scrolling through contents and title bar scrolls with a delay
Infinite paging controller, scrolling through contents and title bar scrolls with a delay

PageController PageController is infinite paging controller, scrolling through contents and title bar scrolls with a delay. Then it provide user inter

iOS 7+ Calendar (Date Picker) with Infinite Scrolling.
iOS 7+ Calendar (Date Picker) with Infinite Scrolling.

RSDayFlow iOS 7 Calendar with Infinite Scrolling. Only need 4 lines of code to set up. RSDayFlow is a slim fork of DayFlow with updates and extensions

Scrollable UINavigationBar that follows the scrolling of a UIScrollView
Scrollable UINavigationBar that follows the scrolling of a UIScrollView

A custom UINavigationController that enables the scrolling of the navigation bar alongside the scrolling of an observed content view Versioning notes

Comments
  • Fast scrolling does not match up with each other

    Fast scrolling does not match up with each other

    Hi,

    So I have two horizontal scrollViews. I want them to scroll simultaneously. It works as expected when I scroll in nominal speed, but if I scroll really fast it does not catch up to each other. Any idea how I can fix this?

    var body: some View {
            return GeometryReader { geo in
                ZStack {
                    // bars
                    ScrollView(.horizontal, showsIndicators: false) {
                        LazyHStack(alignment: .bottom, spacing: spaceBetweenMarks) {
                            ForEach(0 ..< durationInSeconds, id: \.self) { i in
                                getBarsViewForIndex(i, geo: geo)
                            }
                        }
                    }
                    .introspectScrollView { simultaneouslyScrollViewHandler.register(scrollView: $0) }
                    // numbers
                    ScrollView(.horizontal, showsIndicators: false) {
                        LazyHStack(alignment: .top, spacing: spaceBetweenMarks) {
                            ForEach(0 ..< durationInSeconds, id: \.self) { i in
                                getNumbersViewForIndex(i, geo: geo)
                            }
                        }
                        .introspectScrollView { simultaneouslyScrollViewHandler.register(scrollView: $0) }
                    }
                }
            }
        }
    
    opened by AnnieNinaJoyceV 3
  • Delegate is overridden on `register(scrollView:)`

    Delegate is overridden on `register(scrollView:)`

    Current behaviour

    When passing a UIScrollView to the SimultaneouslyScrollViewHandler using the register(scrollView:) method, a potentially already set delegate will be overridden.

    Expected behaviour

    An already set delegate should not be overridden when registering a UIScrollView.

    enhancement 
    opened by stonko1994 0
Releases(1.0.0)
Owner
David Steinacher
David Steinacher
SwiftUI, peek scrolling animation and card tapped animation, using GeometryReader

SwiftUI, peek scrolling animation and card tapped animation, using GeometryReader, follow the livestream tutorial by MengTo.

Terry Kuo 4 Jun 10, 2022
ScrollingFollowView is a simple view which follows UIScrollView scrolling.

ScrollingFollowView ScrollingFollowView is a simple view which follows UIScrollView scrolling. ScrollingFollowView Sample Images SearchBarSample : Sea

Tanaka Kenji 186 Dec 21, 2022
CrownControl is a tiny accessory that makes scrolling through scrollable content possible without lifting your thumb.

CrownControl Overview Features Example Project Requirements Installation Usage Quick Usage Crown Attributes Scroll Axis Anchor Position Spin Direction

Daniel Huri 96 Dec 27, 2022
Multi-tier UIScrollView nested scrolling solution. 😋😋😋

Multi-tier UIScrollView nested scrolling solution. Snapshots Requirements iOS 9.0+ Xcode 10.0+ Swift 4.2+ Installation CocoaPods CocoaPods is a depend

Jiar 1.2k Dec 30, 2022
SwiftUI ScrollView with custom pull to refresh & scroll to load-more implementations

PaginatedScrollView SwiftUI ScrollView with custom "pull to refresh" & "scroll to load-more" implementations. example usage PaginatedScrollView {

Aung Ko Min 7 Sep 20, 2022
SwiftUI OpenScrollView

A non gesture blocking, non clipping by default custom scroll view implementation with example code.

Marco Boerner 10 Dec 6, 2022
Add snapping behaviour to a SwiftUI ScrollView

SwiftUI Snapping ScrollView Add snapping behaviour to a SwiftUI ScrollView. SnappingScrollView A scrollable view that supports snapping. Usage Snappin

Ciaran O'Brien 21 Dec 27, 2022
A scroll view with a sticky header which shrinks as you scroll. Written with SwiftUI.

Scaling Header Scroll View A scroll view with a sticky header which shrinks as you scroll. Written with SwiftUI. We are a development agency building

Exyte 395 Dec 31, 2022
🔥 🔥 🔥Support for ORM operation,Customize the PQL syntax for quick queries,Support dynamic query,Secure thread protection mechanism,Support native operation,Support for XML configuration operations,Support compression, backup, porting MySQL, SQL Server operation,Support transaction operations.

?? ?? ??Support for ORM operation,Customize the PQL syntax for quick queries,Support dynamic query,Secure thread protection mechanism,Support native operation,Support for XML configuration operations,Support compression, backup, porting MySQL, SQL Server operation,Support transaction operations.

null 60 Dec 12, 2022
A SwiftUI ScrollView Designed to imitate the App Store and Apple Music ScrollViews (with or without a Parallax Header)

FancyScrollView I spent a lot of time looking for a way to recreate the UI of the ScrollViews in Stock Apple Apps (i.e. App Store and Apple Music) ins

Mathias Quintero 696 Dec 30, 2022