I'm runnning Xcode 12.4 & am using Core Data and when I launch a device simulator they only show a black screen.
ApDelegate.swift
import UIKit
import CoreData
@UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
internal func application( application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
return true
}
func applicationWillTerminate( application: UIApplication) {
self.saveContext()
}
// MARK: UISceneSession Lifecycle
func application( application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration {
return UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role)
}
func application( application: UIApplication, didDiscardSceneSessions sceneSessions: Set<UISceneSession>) {
}
// MARK: - Core Data stack
lazy var persistentContainer: NSPersistentContainer = {
let container = NSPersistentContainer(name: "DataModel")
container.loadPersistentStores(completionHandler: { (storeDescription, error) in
if let error = error as NSError? {
fatalError("Unresolved error \(error), \(error.userInfo)")
}
})
return container
}()
// MARK: - Core Data Saving support
func saveContext () {
let context = persistentContainer.viewContext
if context.hasChanges {
do {
try context.save()
} catch {
let nserror = error as NSError
fatalError("Unresolved error \(nserror), \(nserror.userInfo)")
}
}
}
}
ViewController
import UIKit
import CoreData
class TodoListViewController: UITableViewController {
var itemArray = [Item]()
let dataFilePath = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first?.appendingPathComponent("Items.plist")
let context = (UIApplication.shared.delegate as! AppDelegate).persistentContainer.viewContext
override func viewDidLoad() {
super.viewDidLoad()
// loadItems()
}
// MARK: - Tableview Datasource Methods
override func tableView( tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return itemArray.count
}
override func tableView( tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "ToDoItemCell", for: indexPath)
let item = itemArray[indexPath.row]
cell.textLabel?.text = item.title
// Ternary Operater ==>
cell.accessoryType = item.done ? .checkmark : .none
return cell
}
// MARK: - Tableview Delegate Methods
override func tableView( tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
itemArray[indexPath.row].done = !itemArray[indexPath.row].done
saveItems()
tableView.reloadData()
tableView.deselectRow(at: indexPath, animated: true)
}
//MARK: - Add New Items
@IBAction func addButtonPressed( sender: UIBarButtonItem) {
var textField = UITextField()
let alert = UIAlertController(title: "Add New Todoey Item", message: "", preferredStyle: .alert)
let action = UIAlertAction(title: "Add Item", style: .default) { (action) in
let newItem = Item(context: self.context)
newItem.title = textField.text!
newItem.done = false
self.itemArray.append(newItem)
self.saveItems()
self.tableView.reloadData()
}
alert.addTextField { (alertTextField) in
alertTextField.placeholder = "Create new item"
textField = alertTextField
}
alert.addAction(action)
present(alert, animated: true, completion: nil)
}
//MARK: - Model Manupulation Methods
func saveItems(){
do {
try context.save()
} catch {
print("Error while saving the context \(error)")
}
}
// func loadItems() {
// if let data = try? Data(contentsOf: dataFilePath!) {
// let decoder = PropertyListDecoder()
// do {
// itemArray = try decoder.decode([Item].self, from: data)
// } catch {
// print("Error decoding Item Array \(error)")
// }
// }
//
// }
}
ApDelegate.swift
import UIKit
import CoreData
@UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
internal func application( application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
return true
}
func applicationWillTerminate( application: UIApplication) {
self.saveContext()
}
// MARK: UISceneSession Lifecycle
func application( application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration {
return UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role)
}
func application( application: UIApplication, didDiscardSceneSessions sceneSessions: Set<UISceneSession>) {
}
// MARK: - Core Data stack
lazy var persistentContainer: NSPersistentContainer = {
let container = NSPersistentContainer(name: "DataModel")
container.loadPersistentStores(completionHandler: { (storeDescription, error) in
if let error = error as NSError? {
fatalError("Unresolved error \(error), \(error.userInfo)")
}
})
return container
}()
// MARK: - Core Data Saving support
func saveContext () {
let context = persistentContainer.viewContext
if context.hasChanges {
do {
try context.save()
} catch {
let nserror = error as NSError
fatalError("Unresolved error \(nserror), \(nserror.userInfo)")
}
}
}
}
ViewController
import UIKit
import CoreData
class TodoListViewController: UITableViewController {
var itemArray = [Item]()
let dataFilePath = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first?.appendingPathComponent("Items.plist")
let context = (UIApplication.shared.delegate as! AppDelegate).persistentContainer.viewContext
override func viewDidLoad() {
super.viewDidLoad()
// loadItems()
}
// MARK: - Tableview Datasource Methods
override func tableView( tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return itemArray.count
}
override func tableView( tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "ToDoItemCell", for: indexPath)
let item = itemArray[indexPath.row]
cell.textLabel?.text = item.title
// Ternary Operater ==>
cell.accessoryType = item.done ? .checkmark : .none
return cell
}
// MARK: - Tableview Delegate Methods
override func tableView( tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
itemArray[indexPath.row].done = !itemArray[indexPath.row].done
saveItems()
tableView.reloadData()
tableView.deselectRow(at: indexPath, animated: true)
}
//MARK: - Add New Items
@IBAction func addButtonPressed( sender: UIBarButtonItem) {
var textField = UITextField()
let alert = UIAlertController(title: "Add New Todoey Item", message: "", preferredStyle: .alert)
let action = UIAlertAction(title: "Add Item", style: .default) { (action) in
let newItem = Item(context: self.context)
newItem.title = textField.text!
newItem.done = false
self.itemArray.append(newItem)
self.saveItems()
self.tableView.reloadData()
}
alert.addTextField { (alertTextField) in
alertTextField.placeholder = "Create new item"
textField = alertTextField
}
alert.addAction(action)
present(alert, animated: true, completion: nil)
}
//MARK: - Model Manupulation Methods
func saveItems(){
do {
try context.save()
} catch {
print("Error while saving the context \(error)")
}
}
// func loadItems() {
// if let data = try? Data(contentsOf: dataFilePath!) {
// let decoder = PropertyListDecoder()
// do {
// itemArray = try decoder.decode([Item].self, from: data)
// } catch {
// print("Error decoding Item Array \(error)")
// }
// }
//
// }
}