swift - SwiftUI 分段选择器的问题

标签 swift swiftui swift5

我是 SwiftUI 的新手,正在尝试开发我的第一个应用程序。我正在尝试使用分段选择器为用户提供在 DayView 和 Week View 之间切换的选项。在这些 View 中的每一个中,都会有特定的用户数据显示为图表。我遇到的问题是加载数据。我在下面发布了代码,但据我所知,问题归结为以下几点:

当加载 View 时,它首先加载 dayView,因为 selectedTimeInterval = 0。这很好,但是当用户按下分段选择器中的“周”时,数据不显示。这是由于在分段选择器运行的 .onChange() 函数之前加载其余 View 。由于 .onChange 将调用放入 viewModel 以加载新数据,因此没有数据。如果您运行下面的代码,您可以在打印语句中看到这一点。

我本以为 View 加载顺序会是

加载分段选择器 如果值更改,则运行 .onChange 加载 View 的其余部分 但实际订单是

加载分段选择器, 加载 View 的其余部分(图表加载此处没有数据!!!!!!) 如果值已更改,则运行 .onChange。 我很迷茫,所以任何帮助都会很棒!非常感谢!

import SwiftUI 
import OrderedCollections

class ViewModel: ObservableObject{ 
    @Published var testDictionary: OrderedDictionary<String, Int> = ["":0]

    public func daySelected() {
        testDictionary = ["Day View Data": 100]
    }

    public func weekSelected() {
        testDictionary = ["Week View Data": 200]
    }
}


struct ContentView: View {
    @State private var selectedTimeInterval = 0
    @StateObject private var vm = ViewModel()
    
    var body: some View {
        VStack {
            Picker("Selected Date", selection: $selectedTimeInterval) {
                Text("Day").tag(0)
                Text("Week").tag(1)
            }
            .pickerStyle(SegmentedPickerStyle())
            .onChange(of: selectedTimeInterval) { _ in
                let _ = print("In on change")
                //Logic to handle different presses of the selector
                switch selectedTimeInterval {
                case 0:
                    vm.daySelected()
                case 1:
                    vm.weekSelected()
                default:
                    print("Unknown Selected Case")
                }
            }
            switch selectedTimeInterval {
            case 0:
                let _ = print("In view change")
                Day_View()
            case 1:
                let _ = print("In view change")
                Week_View(inputDictionary: vm.testDictionary)
            default:
                Text("Whoops")
            }
        }
    }
}

struct Day_View: View {
    
    var body: some View {
        Text("Day View!")
    }
}

struct Week_View: View {
    @State private var inputDictionary: OrderedDictionary<String,Int>
    
    init(inputDictionary: OrderedDictionary<String,Int>) {
        self.inputDictionary = inputDictionary
    }
    
    var body: some View {
        
        let keys = Array(inputDictionary.keys)
        let values = Array(inputDictionary.values)
        VStack {
            Text(keys[0])
            Text(String(values[0]))
        }
    }
}


struct ContentView_Previews: PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}

最佳答案

在您的 WeekView 中,更改

@State private var inputDictionary: OrderedDictionary<String,Int>

private let inputDictionary: OrderedDictionary<String,Int>

@State 用于 View 的本地状态。这个想法是你用初始状态初始化它,从那时起 View 本身将改变它并导致重新渲染。重新渲染 WeekView 时,SwiftUI 会忽略您传递给 init 的参数,并从之前的 WeekView 复制它以保持状态。

但是,您希望继续从 ContentView 传入字典并导致从父 View 重新呈现。

关于swift - SwiftUI 分段选择器的问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/73839152/

相关文章:

swift - __NSCFString nsli_lowerAttribute :intoExpression:withCoefficient:forConstraint: this occur in ios 10 only

Swift prepareForSegue 初始化空数组

ios - 如何在 SwiftUI 中从后代 View 更改 NavigationViewStyle?

swift - 为什么 AVCaptureDevice.default 在 swiftui 中返回 nil ?

Swift: 'Hashable.hashValue' 作为协议(protocol)要求已被弃用;

swift - 在尝试使用 Timer.scheduledTimer 的 SwiftUI 代码中获取未解析的标识符 'self'

ios - CoreStore 创建对象并成功返回

xcode - 使用 NSuserdefaults 在 swift 中设置图像

ios - 从解析中删除对象的问题

swift - 计时器 onReceive 在 NavigationView 中不起作用