【问题标题】:SwiftUI selectable lists where selection variable is ordered排序选择变量的 SwiftUI 可选列表
【发布时间】:2021-05-16 19:34:22
【问题描述】:

我会保持简单,我有一个带有 UUID 标识项目的列表。此列表是可选择的,当输入 EditMode() 时,用户可以点击项目,这些项目会被添加到选择变量中:

而选择变量是:

@State var selection = Set<UUID?>()

但是,问题是我关心选择项目的顺序。在选择数组中,项目不会以 FIFO 或 LIFO 方式更新,它们似乎是随机的,或者可能取决于 UUID 的值,但关键是它不保留添加它们的顺序。

我考虑使用堆栈来跟踪添加的内容,但 SwiftUI 中的 List + 选择组合似乎没有内置方法来通知新增内容,例如已添加 UUID 1234。我可以用“不干净”的方式让它工作,就像每次selection.count 更改时迭代整个选择集并将“新项目”添加到堆栈中,但我不想归结为这一点。

【问题讨论】:

  • Set 根据定义是无序的。 Swift 不提供原生有序集合(带有支持数组的集合),但您可能会找到 here 的内容。顺便说一句,为什么 UUID 是可选的?
  • 无缘无故,当我创建实体并给它一个 UUID 字段时,它默认为 UUID?当我创建 NSManaged 子类时,如果有问题可能会更改它
  • 我会尝试使用 OrderedSets 看看是否有任何运气,谢谢!没有经常使用 Set,忘记了它们在定义上是无序的

标签: ios swift xcode swiftui


【解决方案1】:

所以经过一些研究,在 .editMode 中启用选择的 List 构造函数确实指定了 selection 变量必须是一个 Set 并且只能是一个 Set:

public init(selection: Binding<Set<SelectionValue>>?, @ViewBuilder content: () -> Content)

所以我决定实现我自己的数组来跟踪选择顺序。我将展示它如何帮助任何人,但它非常初级:

     @State var selectedItemsArray=[UUID]()
     ...
     List(selection: $selection) {
     ...
     }
     .onChange(of: selection) { newValue in
        if newValue.count>selectedItemsArray.count {
          for uuid in newValue {
            if !selectedItemsArray.contains(uuid) {
                selectedItemsArray.append(uuid)
                break
            }
          }
        }
        if newValue.count<selectedItemsArray.count {
          for uuid in selectedItemsArray {
            if !newValue.contains(uuid) {
                selectedItemsArray.remove(at:  selectedItemsArray.firstIndex(of: uuid)!)
                 break
              }
           }
        }
     }

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-05-13
    • 1970-01-01
    • 1970-01-01
    • 2015-06-21
    • 2021-09-19
    • 1970-01-01
    • 2022-01-14
    相关资源
    最近更新 更多