SwiftUI中数据项更改时更新列表

我有一个采用ObservableObject协议的activity类,并具有一个items数组属性,该属性存储也采用ObservableObjectactivity对象。

class activity: ObservableObject,Codable,Identifiable {
    let id = UUID()
    @Published var title: String
    @Published var description: String
    @Published var numberOfTimesCompleted: Int = 0

    func encode(to encoder: Encoder) throws {
        var container = encoder.container(keyedBy: CodingKeys.self)

        try container.encode(title,forKey: .title)
        try container.encode(description,forKey: .description)
        try container.encode(numberOfTimesCompleted,forKey: .numberOfTimesCompleted)
    }

    init(title: String,description: String) {
        self.title = title
        self.description = description
        numberOfTimesCompleted = 0
    }

    required init(from decoder: Decoder) throws {
        let container = try decoder.container(keyedBy: CodingKeys.self)

        title = try container.decode(String.self,forKey: .title)
        description = try container.decode(String.self,forKey: .description)
        numberOfTimesCompleted = try container.decode(Int.self,forKey: .numberOfTimesCompleted)
    }
}

class activities: ObservableObject {
    @Published var items: [activity] {
        didSet {
            let encoder = JSONEncoder()
            if let encoded = try? encoder.encode(items) {
                UserDefaults.standard.set(encoded,forKey: "items")
            }
        }
    }

    init() {
        if let items = UserDefaults.standard.data(forKey: "items") {
            let decoder = JSONDecoder()
            if let decoded = try? decoder.decode([activity].self,from: items) {
                self.items = decoded
                return
            }
        }

        self.items = []
    }
}

我正在使用List这样动态显示我的数组

List {
  ForEach(activities.items) { activity in
    NavigationLink(destination: activityView(activity: activity)) {
      HStack {
        Text("\(activity.numberOfTimesCompleted)")
        VStack(alignment: .leading) {
          Text(activity.title)
          Text(activity.description)
        }
      }
    }
  }
}

当我将“活动”传递到另一个视图(在NavigationLink中)并编辑numberOfTimesCompleted属性时,当我导航回到列表时,更改不会反映出来。如果将新的activity实例添加到列表中,列表将更新,并且新的numberOfTimesCompleted值会反映在我之前编辑的activity中。我有一种接近的感觉,但是我正在学习Swift和ObservableObject,因此缺少一些东西。

ppliang69 回答:SwiftUI中数据项更改时更新列表

这里的问题是列表视图具有一系列活动:var items: [Activity],而子级则具有来自该阵列的单个Activity。您已经创建了活动Identifiable,并且id是常量,因此发生的事情是您从数组中传递了活动并对其进行了修改,但是就数组而言,什么都没有改变:所有对象数组中的ID完全相同,因此不会重新加载任何内容。您需要触发活动的重新加载。您可能要考虑使用一个环境对象或传递一个更改闭包,该更改闭包实际上对数组执行突变,以便重建列表视图。仅当它可以检测到已发布的数组与上一个值不同时,它才会自我重建。

本文链接:https://www.f2er.com/3105919.html

大家都在问