如何在父视图中更改子视图的状态时从父视图读取子视图的State属性并更新父视图-SwiftUI

时间:2020-06-08 07:24:01

标签: ios swift view swiftui state

我试图在其子级属性之一更改时更新其父级视图。 我尝试使用Binding,但是该值从未在父视图中更新-它仅在子视图中更新。

这是一些示例代码,可简化我遇到的问题:

struct ArrayDisplayWithPageNumber: View {
    var arrayDisplay: ArrayDisplay
    @Binding var index: Int  // This should update when 'index' changes in 'arrayDisplay'.

    init() {
        self.arrayDisplay = ArrayDisplay()
        self._index = self.arrayDisplay.$index
    }

    var body: some View {
        VStack {
            arrayDisplay
                .padding()
            Text("Page number: \(index + 1)")  // Stays at "Page number: 1".
        }
    }
}
struct ArrayDisplay: View {
    var greetings: [String] = ["Hello", "Hola", "Bonjour"]
    @State var index: Int = 0  // This is the property I want to read in the parent view.

    var body: some View {
        VStack {
            Button("Next greeting") {
                if self.index + 1 == self.greetings.count {
                    self.index = 0  // Simple check to prevent array out of bounds error.
                } else {
                    self.index += 1  // Increments index if it's not at it's highest index value.
                }
            }
            Text(greetings[index])
                .font(.title)
        }
    }
}

我不想合并两个我创建的View,所以有什么方法可以读取index中的ArrayDisplay属性,并在更改时ArrayDisplayWithPageNumber进行更新吗? / p>

如果您可以提供解决我的问题的代码并解释为什么我的代码不起作用,那将非常有帮助。

谢谢!

2 个答案:

答案 0 :(得分:0)

您混淆了源和目标的所有权,即依赖方向。这是固定的变体。使用Xcode 11.4 / iOS 13.4进行了测试

struct ArrayDisplayWithPageNumber: View {
    @State var index: Int = 0    // << here !!

    var body: some View {
        VStack {
            ArrayDisplay(index: $index)   // << here !!
                .padding()
            Text("Page number: \(index + 1)")
        }
    }
}

struct ArrayDisplay: View {
    var greetings: [String] = ["Hello", "Hola", "Bonjour"]
    @Binding var index: Int  // << and here !!

    var body: some View {
        VStack {
            Button("Next greeting") {
                if self.index + 1 == self.greetings.count {
                    self.index = 0 
                } else {
                    self.index += 1
                }
            }
            Text(greetings[index])
                .font(.title)
        }
    }
}

这些链接会有所帮助:

Data Flow Through SwiftUI

State and Data Flow

答案 1 :(得分:0)

使用EnvironmentObject How to use environment object共享数据并更新UI