【问题标题】:How to pass a View() as part of a list in SwiftUI?如何在 SwiftUI 中将 View() 作为列表的一部分传递?
【发布时间】:2021-03-08 22:25:51
【问题描述】:

我已经定义了几个(最多很多)不同的 SwiftUI 视图:

ViewA()、ViewB()、ViewC() ..ViewN()

每个视图都包含我想要根据用户做出的选择呈现的特定信息..

我创建了一个可散列的、可识别的项目列表,我想将每个项目链接到一个特定的视图。但我似乎无法克服这些错误..

这是我正在尝试做的具体示例:

//Country Definitions:

import Foundation
import Combine
import SwiftUI

let Countries = [
    CountryModel(countryID: "US", countryName: "United States", countryView: USAView() )
    CountryModel(countryID: "UK", countryName: "United Kingdom", countryView: UKView() )
]

struct CountryModel: Identifiable, Hashable {
    
    let id:UUID
    let countryID:String
    let countryName:String
    let countryView:View   //I have tried AnyView here, different issues, still no go...
    
    init(countryID:String, countryName:String, countryView:View) {
        self.id = UUID();
        self.countryID = countryID
        self.countryName = countryName
        self.countryView = countryView
    }
}

理论上计划如何在 NavigationView / NavigationLink 中使用它:


struct ContentView: View {
    
    var body: some View {
        
        NavigationView {
            
            ForEach(Countries) { thisCoutry in
                
                NavigationLink(destination: thisCoutry.countryView) { //Also tried forcing as! View, no good
                    MyItemCell(itemName: thisCoutry.countryName, itemDesc: thisCoutry.countryID)
                    
                }
            }
        }
    }
}

(MyItemCell 只是一个用于格式化项目名称和 ID 的视图)..

到目前为止,尝试使用“视图”时出现错误:

Protocol 'View' 只能用作通用约束,因为它 有 Self 或关联的类型要求

还有一些关于不符合 Equatable 的内容。当我添加 Equatable 并让它添加带有 return true 的存根时,没有帮助...

struct CountryModel: Hashable, Identifiable, Equatable {
    static func == (lhs: CountryModel, rhs: CountryModel) -> Bool {
        return true
    }

我也收到一个错误,声称这不符合 Hashable,所以我尝试将其删除,但仍然不行..

非常感谢任何想法。试图避免一长串导航链接,因为 SwiftUI 似乎在 10 左右/左右/之后变得时髦,我必须开始分组,或者更有创意......

struct ContentView: View {
    
    var body: some View {
        
        VStack{
            NavigationView {
                
                NavigationLink(destination: ViewA()) {
                    MyItemCell(itemName: "United States", itemDesc: "USA")
                    
                }
                
                NavigationLink(destination: ViewB()) {
                    MyItemCell(itemName: "United Kingdom", itemDesc: "UK")
                    
                }
            }
        }
    }
}

【问题讨论】:

    标签: ios swift swiftui


    【解决方案1】:

    您可以使用AnyView 类型擦除包装器(但它不仅应该在模型中声明,而且应该在创建时显式使用 - 转换在这里不起作用,我认为这是错误的根源):

    let Countries = [
        CountryModel(countryID: "US", countryName: "United States", 
           countryView: AnyView(USAView()) )    // << here !!
        CountryModel(countryID: "UK", countryName: "United Kingdom", 
           countryView: AnyView(UKView()) )
    ]
    
    struct CountryModel: Identifiable, Hashable {
        
        let id:UUID
        let countryID:String
        let countryName:String
        let countryView:AnyView
        
        init(countryID:String, countryName:String, countryView:View) {
            self.id = UUID();
            self.countryID = countryID
            self.countryName = countryName
            self.countryView = countryView
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-07-19
      • 1970-01-01
      相关资源
      最近更新 更多