Hello,
I have also been experiencing the same issue when trying to implement a section index for a List in SwiftUI.
Please see below for a simple example from a test project (created with the default Xcode 16 build settings, no other changes) that reproduces the same issue outlined by the OP.
| import SwiftUI |
| |
| struct ContentView: View { |
| |
| let sections: [String] = ["#", "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z"] |
| |
| var body: some View { |
| ScrollViewReader { proxy in |
| ZStack { |
| List { |
| ForEach(sections, id: \.self) { section in |
| Section(section) { |
| ForEach(0...25, id: \.self) { _ in |
| Text("Hello, \(section)!") |
| } |
| } |
| } |
| } |
| .listStyle(.plain) |
| .padding(.trailing) |
| HStack { |
| Spacer() |
| SectionIndexTitles(proxy: proxy, titles: sections) |
| } |
| } |
| } |
| .scrollIndicators(.never) |
| } |
| } |
| |
| struct SectionIndexTitles: View { |
| let proxy: ScrollViewProxy |
| let titles: [String] |
| @GestureState private var dragLocation: CGPoint = .zero |
| |
| var body: some View { |
| VStack { |
| ForEach(titles, id: \.self) { title in |
| Text(title) |
| .font(.footnote) |
| .fontWeight(.semibold) |
| .background(dragObserver(title: title)) |
| } |
| } |
| .padding(.horizontal, 2.5) |
| .gesture(DragGesture(minimumDistance: 0, coordinateSpace: .global).updating($dragLocation, body: { value, state, _ in |
| state = value.location |
| })) |
| } |
| |
| func dragObserver(title: String) -> some View { |
| GeometryReader { geometry in |
| dragObserver(geometry: geometry, title: title) |
| } |
| } |
| |
| func dragObserver(geometry: GeometryProxy, title: String) -> some View { |
| if geometry.frame(in: .global).contains(dragLocation) { |
| DispatchQueue.main.async { |
| proxy.scrollTo(title, anchor: .top) |
| } |
| } |
| return Rectangle().fill(Color.clear) |
| } |
| } |
Thank you,
Alex