Swiftui如何将一个带有参数的视图传递给另一个视图,该视图将在调用视图时设置参数

Swiftui How to pass a view that takes a parameter to another view that will set the parameter when calling the view

这是一个简单的示例,但我不知道如何将 test 的值传递到传入的目标视图中。网络上的所有示例在传入时都会形成“完全”视图。

(我正在考虑使用一个函数,我将值传回父级并让它返回形成的视图,但这是倒退的。)

这是为了支持 swift 包,其中一个视图由使用该包的应用程序提供。 (然后我提出的解决方案会让应用程序支持 GetView 函数。我更希望应用程序只传入一个采用已定义参数的视图。

import SwiftUI

struct DestinationLinkView: View {
    let title: String
    var body: some View {
        Text(title)
    }
}


struct ContentView2<LinkView: View>: View {
    let linkView: LinkView
    let testList = ["Test1", "Test2", "Test3"]
    var body: some View {
        HStack {
            NavigationView {
                List {
                    ForEach(testList, id: \.self) { test in
                                                  /*====*/
                        /* *******
                        I want to pass test into self.linkView
                        but cannot figure out how.
                        */
                    NavigationLink(destination: self.linkView) {Text(test)}
// Something like
//                  NavigationLink(destination: self.linkView(title: test)) {Text(test)}
// but that does not work.
                }
            }
        }
    }
}

init(@ViewBuilder linkView: ()->LinkView) {
        self.linkView = linkView()
    }
}

struct ContentView1: View { 
    var body: some View {
        ContentView2() {
            // I want title to be set in ContentView2 when it
            // calls the desitnation
            DestinationLinkView(title: "LINK")
        }
   }
}       
struct ContentView: View {
    var body: some View {
        ContentView1() // calling here so that I don't have to change @main in another file
    }
}

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

您可以将参数作为视图生成器参数传递。

这是可能的方法(使用 Xcode 12.1 / iOS 14.1 测试)

struct ContentView2<LinkView: View>: View {
    let linkView: (String)->LinkView
    let testList = ["Test1", "Test2", "Test3"]
    var body: some View {
        HStack {
            NavigationView {
                List {
                    ForEach(testList, id: \.self) { test in
                        NavigationLink(destination: self.linkView(test)) {Text(test)}
                    }
                }
            }
        }
    }
    
    init(@ViewBuilder linkView: @escaping (String)->LinkView) {
        self.linkView = linkView
    }
}

struct ContentView1: View {
    var body: some View {
        ContentView2() { value in
            DestinationLinkView(title: value)
        }
   }
}