Snappable
A set of SwiftUI custom modifiers to make the ScrollView snappable.
The goal of this library is to provide an easy way to implement Views such as carousels and slideshows.
Demo
Requirements
- iOS 14.0+
 - Swift 5.3+
 
Note
Snappable depends on Introspect for SwiftUI due to detect the behavior of scrolling from UIScrollView, so this is fragile on iOS or SwiftUI upates.
Installation
Swift Package Manager
.package(
  url: "https://github.com/hugehoge/Snappable.git",
  .upToNextMinor(from: "0.2.0")
)
Usage
Basic
struct ContentView: View {
  @State private var items: [Item]
  var body: some View {
    ScrollView(.horiaontal) {
      LazyHStack {
        ForEach(items, id: \.self) { item in
          ItemView(item)
            .snapID(item)  // Step 1
        }
      }
    }
    .snappable()  // Step 2
  }
}
- Added 
.snapID(_:)modifier to items in ScrollViewsnapIDapplies .id(_:) modifier internally
 - Added 
.snappable(_:mode:)modifier to ScrollView 
Options
Alignment
The snap anchor point can be set as an option.
.snappable(alignment: .leading)
Available alignment parameters are below:
.top.leading.center.trailing.bottom
SnapMode
You can determine the snap timing after the end of the drag with following parameters.
.afterScrolling.immediately
Both parameters are set together with scrolling deceleration rate.
.snappable(alignment: .center, mode: .afterScolling(decelerationRate: .fast))
.snappable(alignment: .center, mode: .immediately(decelerationRate: .normal, withFlick: false))

