У меня есть следующий код:
import SwiftUI
let names = ["John", "Betty", "Fred", "May", "Judy"]
struct ContentView: View {
@State var selection = 0
var body: some View {
VStack(spacing: 20) {
Picker("Name", selection: self.$selection.animation(.linear(duration: 0.3))) {
ForEach(names.indices, id: \.self) { i in
Text(names[i]).tag(i)
}
}.pickerStyle(SegmentedPickerStyle())
Text(names[self.selection])
.font(.title)
.fixedSize()
.modifier(MyShake(animatableData: CGFloat(self.selection)))
}
.padding()
}
}
struct MyShake: GeometryEffect {
var animatableData: CGFloat
func modifier(_ x: CGFloat) -> CGFloat {
10 * sin(x * .pi * 2)
}
func effectValue(size: CGSize) -> ProjectionTransform {
let transform1 = ProjectionTransform(CGAffineTransform(translationX: 10 + modifier(animatableData), y: 0))
return transform1
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
.previewDevice("iPhone SE")
}
}
Если вы переключитесь с Джона на Бетти (то есть выберите сегмент рядом с текущим), анимация запустится один раз, и это именно то, что я хочу. Однако если вы переключитесь с Джона на Фреда, анимация будет выполняться несколько раз, потому что выделение фактически не перемещается от 0 до 2, а интерполирует каждый шаг между ними.
Как можно ограничить анимацию так, чтобы он запускается только один раз?