-
Notifications
You must be signed in to change notification settings - Fork 37
/
ScrollView.swift
80 lines (75 loc) · 2.61 KB
/
ScrollView.swift
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
//
// ScrollView.swift
// LiveViewNative
//
// Created by Shadowfacts on 2/9/22.
//
import SwiftUI
/// A view that lets it contents be scrolled if larger than the available space.
///
/// ```html
/// <ScrollView>
/// <VStack>
/// <%= for color <- @colors %>
/// <Rectangle id={color} fill-color={color} modifiers={frame(height: 100)} />
/// <% end %>
/// </VStack>
/// </ScrollView>
/// ```
///
/// ## Attributes
/// - ``axes``
/// - ``showsIndicators``
/// - ``scrollPosition``
/// - ``scrollPositionAnchor``
#if swift(>=5.8)
@_documentation(visibility: public)
#endif
struct ScrollView<R: RootRegistry>: View {
@ObservedElement private var element: ElementNode
@LiveContext<R> private var context
/// Which axes this view is scrollable along (defaults to vertical).
#if swift(>=5.8)
@_documentation(visibility: public)
#endif
@Attribute("axes") private var axes: Axis.Set = .vertical
/// Whether the scroll indicators are shown (defaults to true).
#if swift(>=5.8)
@_documentation(visibility: public)
#endif
@Attribute("shows-indicators") private var showsIndicators: Bool = true
/// When the scroll view appears, and whenever this attribute changes, it will scroll to the view with the corresponding `id` attribute.
///
/// The ``scrollPositionAnchor`` attribute governs where in the scroll view the target will be positioned.
#if swift(>=5.8)
@_documentation(visibility: public)
#endif
@Attribute("scroll-position") private var scrollPosition: String?
/// Where in the scroll view the view that is being scrolled to is positioned.
///
/// For example, specifying `top` will scroll the target to be at the top of the scroll view.
///
/// See ``LiveViewNative/SwiftUI/UnitPoint`` for how values can be specified.
#if swift(>=5.8)
@_documentation(visibility: public)
#endif
@Attribute("scroll-position-anchor") private var scrollPositionAnchor: UnitPoint?
public var body: some View {
SwiftUI.ScrollViewReader { proxy in
SwiftUI.ScrollView(
axes,
showsIndicators: showsIndicators
) {
context.buildChildren(of: element)
}
.onAppear {
guard let scrollPosition else { return }
proxy.scrollTo(scrollPosition, anchor: scrollPositionAnchor)
}
.onChange(of: scrollPosition) { newValue in
guard let newValue else { return }
proxy.scrollTo(newValue, anchor: scrollPositionAnchor)
}
}
}
}