问题描述
我想删除列表的行。
我已经按照 Apple 的官方 SwiftUI 教程构建了我的应用程序的这一部分。如果您愿意,您可以从 https://developer.apple.com/tutorials/swiftui/handling-user-input 下载 SwiftUI Essentials - 处理用户输入。
我正在使用 onDelete
修饰符删除行。
ForEach(filteredLandmarks) { landmark in
NavigationLink(destination: LandmarkDetail(landmark: landmark)) {
LandmarkRow(landmark: landmark)
}
}
.onDelete(perform: { indexSet in
for index in indexSet {
self.modelData.landmarks.remove(at: index)
}
})
只要您不导航到 LandmarkDetail
视图,它就可以工作。如果您这样做,应用程序会因 Thread 1: Fatal error: Unexpectedly found nil while unwrapping an Optional value
而崩溃。这是因为正如您在以下代码中看到的那样,firstIndex
被强制解包。
struct LandmarkDetail: View {
@EnvironmentObject var modelData: ModelData
var landmark: Landmark
var landmarkIndex: Int {
modelData.landmarks.firstIndex(where: { $0.id == landmark.id })!
}
var body: some View {
FavoriteButton(isSet: $modelData.landmarks[landmarkIndex].isFavorite)
}
}
我不知道如何允许在 Landmark
中编辑 LandmarkDetail
以及如何删除它。
信息
为了测试,点击一行以导航到 LandmarkDetail
,然后导航回 LandmarkList
。然后删除您刚刚点击的行。
解决方法
问题是您正在从 modelData
中删除索引,但是您正在将 landmark
对象从 filteredLandmarks
变量发送到 LandmarkDetail
视图(该对象在 filteredLandmarks
中仍然可用) {1}})。因此,在 LandmarkDetail 视图中,“modelData”不包含您提供的“landmark”变量。
在 LandmarkDetail
视图中:
var landmarkIndex: Int {
guard let index = modelData.landmarks.firstIndex(where: { return $0.id == landmark.id }) else {
return 0
}
return index
}
或,
您可以尝试找出从 filteredLandmarks
变量中删除确切行索引的解决方案。