如何让 SwiftUI 列表删除按钮工作? (或消失)
Posted
技术标签:
【中文标题】如何让 SwiftUI 列表删除按钮工作? (或消失)【英文标题】:How can I get SwiftUI List delete buttons to work? (or disappear) 【发布时间】:2021-10-29 01:59:14 【问题描述】:我有一个允许删除和移动的列表。并且有一个与 List 关联的 EditButton :
struct IDLine: Identifiable, Codable
let id: Int
let line: String
// IDLine
struct ContentView: View
...
@AppStorage("savedConversions") var conversions: [IDLine] = []
...
var body: some View
...
List
ForEach(conversions) Text($0.line) // List of conversions
.onDelete(perform: deleteConversion)
.onMove(perform: moveConversion)
...
func deleteConversion(at offsets: IndexSet) conversions.remove(atOffsets: offsets)
func moveConversion(from source: IndexSet, to dest: Int) conversions.move(fromOffsets: source, toOffset: dest)
// ContentView
当我向左滑动列表的某一行时,该行的右边缘会出现一个红色矩形删除按钮。点击它什么都不做。如果我单击 EditButton,每一行都会在左侧得到一个圆形的“-”按钮,然后再次单击它什么也不做。 这并不全是坏事。如果在一行上向左滑动足够远,则调用 deleteConversion。当按下 EditButton 时,每行右侧会出现一个 3 行小把手,允许用户重新排序列表。
编辑:我添加了更多代码,希望它更易于解释。
【问题讨论】:
向我们展示一个完整的示例,它可以重现您的问题,包括deleteConversion
。
从conversions
删除项目后,听起来视图没有更新,或者根本没有删除它。
为了诊断为什么删除按钮不起作用,我们至少需要查看您的deleteConversion
函数。关于让他们“消失”的问题 - 只需删除您的 onDelete
修饰符即可。
我认为这是 SwiftUI 中的一个错误。我的旧 UIKit 版本中的逻辑等效代码有效。出现的删除按钮应该只是调用 deleteConversion 函数的替代路径,但似乎只有其中一个被正确连接。
【参考方案1】:
我已经找出了问题所在。我在声明 List 的 VStack 上有一个 onTapGesture 修饰符。它用于隐藏键盘。当我删除该修饰符时,删除按钮再次开始工作。 这是一个有问题的最小应用程序:
import SwiftUI
struct IDLine: Identifiable, Codable // To allow SwiftUI List to correctly edit with repeated strings
let id: Int
let value: String
// IDLine
struct ContentView: View
@State private var value: String = ""
@State private var lines: [IDLine] = []
@FocusState private var entryFocused: Bool
var body: some View
VStack
Text("Enter value")
TextField("value", text: $value).padding()
.focused($entryFocused)
HStack
Button("Add", action: addLine).disabled(value.count == 0)
Button("Clear", action: clearLines).disabled(lines.count == 0)
EditButton().disabled(lines.count == 0)
.padding(20)
List
ForEach(lines)
Text($0.value)
.onDelete(perform: deleteLine)
.onMove(perform: moveLine)
// VStack
.onTapGesture entryFocused = false
// body
func nextLine() -> IDLine
let id = 1 + lines.reduce(0) Swift.max($0, $1.id)
return IDLine(id: id, value: value)
func addLine() lines.append(nextLine())
func clearLines() lines = []
func deleteLine(at offsets: IndexSet) lines.remove(atOffsets: offsets)
func moveLine(from source: IndexSet, to dest: Int) lines.move(fromOffsets: source, toOffset: dest)
【讨论】:
以上是关于如何让 SwiftUI 列表删除按钮工作? (或消失)的主要内容,如果未能解决你的问题,请参考以下文章