I moved the on appear to the h stack but the table rows portion of the table still ran before the on appear resulting in an index out of range error. So I added the suggested state variable and if statement. The view now works perfectly. Thank you again for providing great advice. Below is the updated code.
struct DataTable: View {
@ObservedObject var vm: ButtonsViewModel = ButtonsViewModel.shared
var closingValues: [TradingDayClose]
var heading: String = ""
@State private var hasAppeared = false
init(fundName: String, closingValues: [TradingDayClose]) {
self.heading = fundName
self.closingValues = closingValues
}
var body: some View {
HStack {
Spacer()
.frame(width: 150)
GroupBox(heading) {
if hasAppeared {
Table (of: TradingDayClose.self) {
TableColumn("") { closingValue in
Text(dateToStringFormatter.string(from: closingValue.timeStamp!))
.id(closingValue.timeStamp!)
.textFormatting(fontSize: 14)
.frame(width: 100, alignment: .center)
} // end table column
TableColumn("") { closingValue in
Text(String(format: "$ %.2f", closingValue.close))
.textFormatting(fontSize: 14)
.frame(width: 100, alignment: .center)
} // end table column
} rows: {
ForEach((closingValues.indices), id: \.self) { index in
if vm.showData[index] == true {
TableRow(closingValues[index])
}
}
}
.frame(width: 250)
.overlay {
let tempValue1: String = "Date"
let tempValue2: String = "Closing Value"
Text(tempValue1).position(x: 63, y: 15)
.textFormatting(fontSize: 16)
Text(tempValue2).position(x: 180, y: 15)
.textFormatting(fontSize: 16)
}
} // end has appeared
} // end group box
.groupBoxStyle(Table2GroupBoxStyle())
Spacer()
.frame(width: 50)
VStack {
Spacer()
.frame(height: 100)
ButtonUp25(closingValuesCount: closingValues.count)
ButtonUp200(closingValuesCount: closingValues.count)
Spacer()
.frame(height: 20)
ButtonDown25(closingValuesCount: closingValues.count)
ButtonDown200(closingValuesCount: closingValues.count)
Spacer()
.frame(height: 100)
} // end v stack
Spacer()
.frame(width: 50)
} // end h stack
.onAppear {
vm.showData = []
vm.showData = Array(repeating: false, count: closingValues.count)
vm.InitializeIndexes()
vm.InitializeButtons()
for i in vm.startIndex...vm.endIndex {
DispatchQueue.main.asyncAfter(deadline: .now() + vm.renderRate * Double(i)) {
vm.showData[i] = true
} // end dispatch queue main async
}
hasAppeared = true
}
} // end body
} // end struct
Topic:
UI Frameworks
SubTopic:
SwiftUI
Tags: