I have a Circular ProgressBar View that takes a @Binding var progress: Float
property as its progress value, what I would like to be able to do is pass the var progress: Float
value from the Task
objects respectably in the List
. I tried assigning the progress = task.progress
the value from the Task
objects to a @State property within the ContentView but of course that cannot be done inside a View (see commented code line below).
How can I pass the progress values from each Task to the ProgressBar view respectably?
Task Model:
class Task:Identifiable{
var name = ""
var progress: Float = 0.0
init(name:String, progress:Float){
self.name = name
self.progress = progress
}
}
Content View
var tasks = [Task(name: "Ketchen Floors", progress: 0.5),
Task(name: "Install Windows", progress: 0.75)]
struct ContentView: View {
@State var progress:Float = 0.15
var body: some View {
List {
ForEach(tasks) { task in
// outputs error: Type '()' cannot conform to 'View'
// progress = task.progress
HStack{
Text(task.name)
// here $progress value shoud come from task.progress
ProgressBar(progress: $progress)
}
}
}
}
}
ProgressBar View
struct ProgressBar: View {
@Binding var progress: Float
var body: some View {
ZStack {
Circle()
.stroke(lineWidth:5.0)
.opacity(0.3)
.foregroundColor(Color.orange)
Circle()
.trim(from: 0.0, to: CGFloat(min(self.progress, 1.0)))
.stroke(style: StrokeStyle(lineWidth: 5.0, lineCap: .round, lineJoin: .round))
.foregroundColor(Color.orange)
.rotationEffect(Angle(degrees: 270.0))
.animation(.linear, value: progress)
VStack{
Text(String(format: "%.0f %%", min(self.progress, 1.0)*100.0))
.font(.caption2)
}
}
}
}
Screen
As you can see, every item shows the initial 15% progress value, no surprise. Again, what I want is to be able to use the value from each Task respectably, Ketchen Floors at 50% and Install Windows at 75%.
CodePudding user response:
First, add your array inside ContentView and make it @State
After that, you can directly bind var by task.
struct ContentView: View {
@State var progress:Float = 0.15
@State var tasks = [Task(name: "Ketchen Floors", progress: 0.5),
Task(name: "Install Windows", progress: 0.75)] // <---- Here
var body: some View {
List {
ForEach($tasks) { $task in // <---- Here
// outputs error: Type '()' cannot conform to 'View'
// progress = task.progress
HStack{
Text(task.name)
// here $progress value shoud come from task.progress
ProgressBar(progress: $task.progress) // <---- Here
}
}
}
}
}