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