冥想与阶段有一对多的关系,我已经根据顺序属性对冥想进行了排序,当我点击编辑时,通过移动它们来改变冥想,这是可行的。现在,我也想对冥想的各个阶段做同样的事情。
我尝试为FetchRequest做一个新的DetailView,这样我就可以使用与冥想相同的方法,但是我不能将它具体地用于特定的冥想(如果我认为新的FetchRequest是可以避免的,那么这可能不是最好的方法)。
我还尝试使用.sorted对列表项进行排序,但是当在编辑模式下更改顺序时,它没有立即更新,您必须来回查看更改。
有办法让这些方法之一起作用吗?当然,我也愿意考虑其他解决办法。
这就是冥想的观点:
import SwiftUI
import CoreData
struct ContentView: View {
@Environment(\.managedObjectContext) private var viewContext
@FetchRequest(sortDescriptors: [NSSortDescriptor(keyPath: \Meditation.order, ascending: true)])
private var meditations:FetchedResults<Meditation>
@State private var add = false
var body: some View {
NavigationView {
List {
ForEach(meditations){meditation in
NavigationLink(destination: {
DetailView(meditation: meditation)
}, label: {
Text(meditation.title ?? "")
Text("\(meditation.order)")
})
}
.onDelete(perform: deleteMeditation)
.onMove(perform: moveItem)
}
.navigationTitle("Meditations")
.sheet(isPresented: $add){
AddView()
}
.toolbar {
ToolbarItem(placement:.navigationBarTrailing){
EditButton()
}
ToolbarItem(placement:.navigationBarTrailing){
Button(action: {
add.toggle()
}, label: {
Label("Add Meditation",systemImage: "plus")
})
}
}
}
}
private func deleteMeditation(at offset:IndexSet){
withAnimation {
for index in offset{
let meditationToDelete = meditations[index]
do{
viewContext.delete(meditationToDelete)
try viewContext.save()
}catch{
print("Error while deleting Meditation \(error.localizedDescription)")
}
}
}
}
private func moveItem(at sets:IndexSet,destination:Int) {
let itemToMove = sets.first!
print (itemToMove)
print (destination)
if itemToMove < destination {
var startIndex = itemToMove + 1
let endIndex = destination - 1
print (startIndex)
print (endIndex)
var startOrder = meditations[itemToMove].order
while startIndex <= endIndex {
meditations[startIndex].order = startOrder
startOrder = startOrder + 1
startIndex = startIndex + 1
}
meditations[itemToMove].order = startOrder
} else if destination < itemToMove {
var startIndex = destination
let endIndex = itemToMove - 1
var startOrder = meditations[destination].order + 1
let newOrder = meditations[destination].order
while startIndex <= endIndex {
meditations[startIndex].order = startOrder
startOrder = startOrder + 1
startIndex = startIndex + 1
}
meditations[itemToMove].order = newOrder
}
do {
try viewContext.save()
}
catch {
print(error.localizedDescription)
}
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}
这是显示阶段的详细视图:
import SwiftUI
struct DetailView: View {
let meditation : Meditation
@Environment(\.managedObjectContext) var viewContext
@Environment(\.dismiss) var dismiss
@State private var addStage = false
@State private var showingDeleteAlert = false
@State private var isPresented = false
var body: some View {
VStack {
Text(meditation.wrappedDetails)
List{
ForEach(meditation.meditationStage){meditationStage in
MeditationStageDetailCell(meditationStage: meditationStage)
}
.onMove(perform: moveStage)
.onDelete(perform: deleteStage)
}
Spacer()
Button ("Begin"){
isPresented.toggle()
}
.fullScreenCover(isPresented: $isPresented) {
MeditatingView(meditation: meditation)
}
Spacer()
}
.navigationTitle(meditation.wrappedTitle)
.navigationBarTitleDisplayMode(.inline)
.alert("Delete Meditation?", isPresented: $showingDeleteAlert) {
Button ("Delete", role: .destructive, action: deleteMeditation)
Button ("Cancel", role: .cancel) {}
} message: {
Text("This action can't be undone")
}
.toolbar{
ToolbarItem(placement:.navigationBarTrailing){
Button {
showingDeleteAlert = true
} label: {
Label ("Delete this Stage", systemImage: "trash")
}
}
ToolbarItem(placement:.navigationBarTrailing){
EditButton()
}
ToolbarItem(placement:.navigationBarTrailing){
Button(action: {
addStage.toggle()
}, label: {
Label("Add Stage",systemImage: "plus")
})
}
}
.sheet(isPresented: $addStage){
AddMeditationStageView(meditation: meditation)
}
}
private func deleteMeditation() {
viewContext.delete(meditation)
try? viewContext.save()
dismiss()
}
private func deleteStage(at offset:IndexSet){
for index in offset{
let stageToDelete = meditation.meditationStage[index]
do{
viewContext.delete(stageToDelete)
meditation.stages -= 1
try viewContext.save()
} catch {
print("Error while deleting Meditation \(error.localizedDescription)")
}
}
}
private func moveStage(at sets:IndexSet,destination:Int) {
let itemToMove = sets.first!
print (itemToMove)
print (destination)
if itemToMove < destination {
var startIndex = itemToMove + 1
let endIndex = destination - 1
print (startIndex)
print (endIndex)
var startOrder = meditation.meditationStage[itemToMove].order
print(startOrder)
while startIndex <= endIndex {
meditation.meditationStage[startIndex].order = startOrder
startOrder = startOrder + 1
startIndex = startIndex + 1
}
meditation.meditationStage[itemToMove].order = startOrder
} else if destination < itemToMove {
var startIndex = destination
let endIndex = itemToMove - 1
var startOrder = meditation.meditationStage[destination].order + 1
let newOrder = meditation.meditationStage[destination].order
while startIndex <= endIndex {
meditation.meditationStage[startIndex].order = startOrder
startOrder = startOrder + 1
startIndex = startIndex + 1
}
meditation.meditationStage[itemToMove].order = newOrder
}
do {
try viewContext.save()
}
catch {
print(error.localizedDescription)
}
}
}
发布于 2022-11-06 20:16:37
@FetchRequest
private var stages: FetchedResults<MeditationStage>
init(meditation: Meditation) {
let sortDescriptors = [SortDescriptor(\MeditationStage.timestamp]
_stages = FetchRequest(sortDescriptors: sortDescriptors, predicate: NSPredicate(format: "meditation = %@", meditation), animation: .default)
}
https://stackoverflow.com/questions/74334491
复制相似问题