Reputation: 85
I'm quite new to Swift and coding in general so apologies if this is a super simple question.
I'm trying to add a button either side of a Picker to allow the user to move up/down the selections within the Picker (my Picker is populated from an Array) - I'm using this selection in another part of my App.
The code below works but only updates the example Text, but it does not update the selection: within the pickerto update correctly.
Any ideas what I'm doing wrong?
import SwiftUI
struct ContentView: View {
let myArray = ["Period 1", "Period 2", "Period 3", "Period 4", "Period 5", "Period 6", "Period 7", "Period 8", "Period 9", "Period 10", "Period 11", "Period 12", "Period 13"]
@State var currentIndex = 0
var body: some View {
VStack(spacing: 20) {
HStack {
Button(action: {
if currentIndex == 0 {
} else {
currentIndex -= 1
}
}) {
Image(systemName: "chevron.left.circle")
.imageScale(.large)
}
.padding(2)
.frame(maxWidth: .infinity, alignment: .leading)
Picker(selection: $currentIndex, label: Text("Picker")) {
ForEach(myArray, id: \.self) {
Text($0)
}
}
Button(action: {
if currentIndex == 12 {
} else {
currentIndex += 1
}
}) {
Image(systemName: "chevron.right.circle")
.imageScale(.large)
}
.padding(2)
.frame(maxWidth: .infinity, alignment: .trailing)
}
.padding()
Text("\(myArray[currentIndex])")
}
}
}
'''
Upvotes: 7
Views: 3536
Reputation: 52013
The problem here is that you are programmatically updating your State variable currentIndex
but you are not modifying the array selection. To make this work you need to iterate the array over the indices and not the elements so change the Picker
code to this
Picker(selection: $currentIndex, label: Text("Picker")) {
ForEach(myArray.indices) { index in
Text(myArray[index])
}
}
Here each item in the picker automatically gets the id
of the raw value of index
which matches with currentIndex
which makes this work.
To work directly with the elements of the array here is an alternative solution where a new State variable is added to hold the selected string.
@State var currentSelection = ""
@State var currentIndex = 0 {
didSet {
currentSelection = myArray[currentIndex]
}
}
The picker code gets changed to
Picker(selection: $currentSelection, label: Text("Picker")) {
ForEach(myArray, id: \.self) { period in
Text(period)
}
}
but the rest of the code is the same since the buttons are still using currentIndex
Upvotes: 9