&tag(SwiftUI/CoreData);
struct ContentView: View {
@Environment(\.managedObjectContext) private var viewContext
@FetchRequest(
entity: Task.entity(),
sortDescriptors: [NSSortDescriptor(keyPath: \Task.timestamp, ascending: true)],
animation: .default)
private var tasks: FetchedResults<Task>
//タスク一覧
var body: some View {
NavigationView {
// 取得したデータリストを表示
List {
ForEach(tasks) {task in
// タスクの表示
HStack {
Image(systemName: task.checked ? "checkmark.circle.fill": "circle")
Text("\(task.name!)")
Spacer()
}
// タスクをタップでcheckedフラグを変更する
.contentShape(Rectangle())
.onTapGesture {
task.checked.toggle()
try? viewContext.save()
}
}.onDelete(perform: deleteTasks)
}
.navigationTitle("Todoリスト")
.toolbar {
ToolbarItem(placement: .navigationBarLeading) {
EditButton()
}
ToolbarItem(placement: .navigationBarTrailing) {
NavigationLink(destination: AddTaskView()) {
Image(systemName: "plus")
}
}
}
Text("Select an item")
}
}
func deleteTasks(offsets: IndexSet) {
for index in offsets {
viewContext.delete(tasks[index])
}
try? viewContext.save()
}
}
struct AddTaskView: View {
@Environment(\.managedObjectContext) private var context
@Environment(\.presentationMode) var presentationMode
@State private var task = ""
//タスク入力
var body: some View {
Form {
Section() {
TextField("タスク入力", text: $task)
}
}
.navigationTitle("タスク追加")
.toolbar {
ToolbarItem(placement: .navigationBarTrailing) {
Button("保存") {
let newTask = Task(context: context)
newTask.timestamp = Date()
newTask.checked = false
newTask.name = task
try? context.save()
presentationMode.wrappedValue.dismiss()
}
}
}
}
}
private let itemFormatter: DateFormatter = {
let formatter = DateFormatter()
formatter.dateStyle = .short
formatter.timeStyle = .medium
return formatter
}()
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView().environment(\.managedObjectContext, PersistenceController.preview.container.viewContext)
}
}
static var preview: PersistenceController = {
let result = PersistenceController(inMemory: true)
let viewContext = result.container.viewContext
/// preview用初期データ登録処理
let newTask = Task(context: viewContext)
newTask.timestamp = Date()
newTask.checked = false
newTask.name = "初期タスク"
do {
try viewContext.save()
} catch {
// Replace this implementation with code to handle the error appropriately.
// fatalError() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development.
let nsError = error as NSError
fatalError("Unresolved error \(nsError), \(nsError.userInfo)")
}
return result
}()