//
// ContentView.swift
// CDBootCamp
//
// on 2021/8/13.
//参考自Nick Sarno
import SwiftUI
import CoreData//引入模块
class CoreDataViewModel: ObservableObject {
//申明一个容器
let container : NSPersistentContainer
//建立一个可监听的水果实体数组
@Published var savedEntities:[FruitEntity] = []
//初始化容器
init(){
//用自己在Xcode建立的coredata文件初始化容器,注意名字必须与你建立的文件
//一致FruitsContainer.xcdatamodeld。不包括xcdatamodeld这个部分
container = NSPersistentContainer(name: "FruitsContainer")
//加载持久存储并完成核心数据堆栈的创建
container.loadPersistentStores { description, error in
if let error = error {
print("Loading core data wrong :\(error) ")
}
}
fetchFruits()//调用此方法,初始化entity数组
}
//申明请求 ---- 尝试请求
func fetchFruits(){
//声明一个取回请求,类型是FruitEntity,名字是FruitEntity
let request = NSFetchRequest<FruitEntity>(entityName: "FruitEntity")
do {
//调用viewContext的fetch方法尝试取回包含FruitEntity的数组
savedEntities = try container.viewContext.fetch(request)
} catch let error {
//失败则报错
print(" Error Fetching \( error )")
}
}
func addFruits(text:String){
//实例化一个FruitEntity在view context里
let newFruit = FruitEntity(context: container.viewContext)
//进行更新操作
newFruit.name = text
//记得同步保存一下
saveData()
}
func deleteFruits(indexSet:IndexSet){
//获取索引
guard let index = indexSet.first else{return}
//获取索引对应的实体数据,这些水果数据都在数组里
let entity = savedEntities[index]
//删除这个实体
container.viewContext.delete(entity)
//记得同步保存一下
saveData()
}
func updateFruit(entity:FruitEntity){
//传入实体,直接更新,保存
let currentName = entity.name ?? "no name"
let newName = currentName + "🍉"
entity.name = newName
saveData()
}
func saveData(){
//fetchFruits可能会更新被监听的数组,从而刷新界面
fetchFruits()
do {
try container.viewContext.save()
} catch let error {
print("Saving Failure:\(error) ")
}
}
}
struct ContentView: View {
@StateObject var vm = CoreDataViewModel()
@State var textFieldText:String = ""
var body: some View {
NavigationView{
VStack(spacing:20){
TextField("Add fruits here ...", text: $textFieldText)
.font(.headline)
.frame(height:55)
.padding(.leading,10)
.background(Color(#colorLiteral(red: 0.921431005, green: 0.9214526415, blue: 0.9214410186, alpha: 1)))
.cornerRadius(10)
.padding(.horizontal,10)
Button(action: {
guard !textFieldText.isEmpty else{return}
vm.addFruits(text: textFieldText)
textFieldText = ""
}, label: {
Text("保存")
.font(.title)
.foregroundColor(.white)
.frame(height:55)
.frame(maxWidth:.infinity)
.background(Color(#colorLiteral(red: 0.8549019694, green: 0.250980407, blue: 0.4784313738, alpha: 1)))//背景色上色放最后
.cornerRadius(10)
.padding(.horizontal,10)
})
List{
ForEach(vm.savedEntities) { fruite in
Text(fruite.name ?? "no data")
.onTapGesture {
vm.updateFruit(entity: fruite)
}
}
.onDelete(perform: vm.deleteFruits)
}
}
.navigationTitle(Text("水果🍉"))
}
}
}
网友评论