SwiftUI 中按钮操作内的 ForEach 循环?

Posted

技术标签:

【中文标题】SwiftUI 中按钮操作内的 ForEach 循环?【英文标题】:ForEach loop inside a button action in SwiftUI? 【发布时间】:2020-04-12 23:41:29 【问题描述】:

我了解 ForEach 循环通常用于显示视图。当我在操作按钮中放置一个 ForEach 循环时,它几乎告诉我按钮操作不符合视图协议。那么如何使用循环让按钮执行多个动作呢?

struct SomeView: View 
    var newExercises = [NewExercise]()
    var finalExercises = [Exercise]()

    var body: some View 
        Button(action: 
            ForEach(newExercises)  newExercise in
                //.getExercise() returns an Exercise object
                finalExercises.append(newExercise.getExercise())
            

        ) 
            Text("Done")
        
    


我希望按钮为 newExercises 数组中的每个 newExercise 添加一个练习(通过调用 .getExercise())到 finalExercises 数组。

我该怎么做?

【问题讨论】:

【参考方案1】:

新的SwiftUIForEach 语句为Array 的每个Element 返回一个View。对于您的代码,您只需要运行 VoidArray<Exercise>.append(newElement: Exercise) 而不是获得多个 View,因此您可以使用 for 循环、mapArray.forEach(body: (_) throws -> Void)

如果附加newExercises 的顺序很重要,最优雅的解决方案是将finalExercises 中的每个NewExercise 映射到Exercise,并将生成的Array<Exercise> 附加到Array<Exercise>.append(contentsOf: Sequence)

struct SomeView: View 
    @State var newExercises = [NewExercise]()
    @State var finalExercises = [Exercise]()

    var body: some View 
        Button(action: 
            self.finalExercises.append(contentsOf:
                self.newExercises.map  newExercise -> Exercise in
                    newExercise.getExercise()
                
            )


        ) 
            Text("Done")
        
    

如果newExercises 的附加顺序无关紧要,您可以从newExcercises.forEach 调用Array<Exercise>.append(newElement: Exercise),这与SwiftUI ForEach 语句不同:

struct SomeView: View 
    @State var newExercises = [NewExercise]()
    @State var finalExercises = [Exercise]()

    var body: some View 
        Button(action: 
            self.newExercises.forEach  newExercise in
                self.finalExercises.append(newExercise.getExercise())
            
        ) 
            Text("Done")
        
    

用 for 循环完成你想要的东西的方法很简单,但不太优雅:

struct SomeView: View 
    @State var newExercises = [NewExercise]()
    @State var finalExercises = [Exercise]()

    var body: some View 
        Button(action: 
            for newExercise in self.newExercises 
                self.finalExercises.append(newExercise.getExercise())
            

        ) 
            Text("Done")
        
    

【讨论】:

以上是关于SwiftUI 中按钮操作内的 ForEach 循环?的主要内容,如果未能解决你的问题,请参考以下文章

在 SwiftUI 中修改 ForEach 内的视图

iOS SwiftUI 中 ForEach 内的 if 语句

SwiftUI:如何根据 Picker 的值更新 ForEach 循环的范围

按钮操作块内的 Foreach 循环抛出“Type() 不能符合视图”

SwiftUI:VStack 中 ForEach 中的 HStack 使多行文本重叠

使用简写参数名称 $0 在 ForEach 中为 SwiftUI 添加按钮