Saving text from a UITextView using core data Swift

时间:2015-07-28 22:40:32

标签: ios swift core-data

Completely new to iOS Development and Swift so I hope you'll bear with me. I'm creating a simple note app based off the apple Notes app.

I am also completely new to core data. What I'm trying to do is save the text from the UITextView. Strangely enough this works but only after I remove this piece of code,

if let detail: Note = self.detailItem {

                if let textView = self.textView {
                    textView.text = detail.noteText
                }

create a new note, then reintroduce the code...

func configureView() {
        // Update the user interface for the detail item.
        if let detail: Note = self.detailItem {
            if let label = self.detailDescriptionLabel {
                label.text = detail.timeStamp.description
            }

        if let detail: Note = self.detailItem {

            if let textView = self.textView {
                textView.text = detail.noteText
            }

        }
    }

For a note that has already been created, this code is able to save the text in the textView. If I try to create a new note and then open it, the code above will crash the app.

This error comes up: Thread 1: EXC_BAD_ACCESS(code=1, address=0x0)

I think I have made a silly mistake like not initializing my model "Note.swift" class.

I'm using the boilerplate code for a master detail app with core data. I also have two "insertNewObject" functions. One is in the MasterViewController and the other is in the DetailViewController.

DetailViewController.swift

 func insertNewObject(sender: AnyObject) {
        let context = self.fetchedResultsController.managedObjectContext
        let entity = self.fetchedResultsController.fetchRequest.entity!
        let newManagedObject = NSEntityDescription.insertNewObjectForEntityForName(entity.name!, inManagedObjectContext: context) as! NSManagedObject

Here's the full code including the fetchedResultsController.

  func insertNewObject(sender: AnyObject) {
        let context = self.fetchedResultsController.managedObjectContext
        let entity = self.fetchedResultsController.fetchRequest.entity!
        let newManagedObject = NSEntityDescription.insertNewObjectForEntityForName(entity.name!, inManagedObjectContext: context) as! NSManagedObject

        // If appropriate, configure the new managed object.
        // Normally you should use accessor methods, but using KVC here avoids the need to add a custom class to the template.
        newManagedObject.setValue(self.textView.text, forKey: "noteText")
        newManagedObject.setValue("I changed", forKey: "noteTitle")

        // Save the context.
        var error: NSError? = nil
        if !context.save(&error) {
            // Replace this implementation with code to handle the error appropriately.
            // abort() 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.
            //println("Unresolved error \(error), \(error.userInfo)")
            abort()
        }
    }

    // MARK: - Fetched results controller

    var fetchedResultsController: NSFetchedResultsController {
        if _fetchedResultsController != nil {
            return _fetchedResultsController!
        }

        let fetchRequest = NSFetchRequest()
        // Edit the entity name as appropriate.
        let entity = NSEntityDescription.entityForName("Note", inManagedObjectContext: self.managedObjectContext!)
        fetchRequest.entity = entity

        // Set the batch size to a suitable number.
        fetchRequest.fetchBatchSize = 20

        // Edit the sort key as appropriate.
        let sortDescriptor = NSSortDescriptor(key: "timeStamp", ascending: false)
        let sortDescriptors = [sortDescriptor]

        fetchRequest.sortDescriptors = [sortDescriptor]

        // Edit the section name key path and cache name if appropriate.
        // nil for section name key path means "no sections".
        let aFetchedResultsController = NSFetchedResultsController(fetchRequest: fetchRequest, managedObjectContext: self.managedObjectContext!, sectionNameKeyPath: nil, cacheName: "Master")
        aFetchedResultsController.delegate = self
        _fetchedResultsController = aFetchedResultsController

        var error: NSError? = nil
        if !_fetchedResultsController!.performFetch(&error) {
            // Replace this implementation with code to handle the error appropriately.
            // abort() 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.
            //println("Unresolved error \(error), \(error.userInfo)")
            abort()
        }

        return _fetchedResultsController!
    }    

    var _fetchedResultsController: NSFetchedResultsController? = nil

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }

    override func viewWillDisappear(animated: Bool) {
        detailItem!.noteText = self.textView.text
        detailItem!.noteTitle = "I changed"

        var error: NSError? = nil
        if !self.managedObjectContext!.save(&error) {
            abort()
        }
    }

1 个答案:

答案 0 :(得分:0)

我能够弄清楚。问题是我第一次调用func insertNewObject(sender: AnyObject)时没有为“noteText”设置值。这导致nil设置为textView.text,从而导致应用程序崩溃。感谢您的帮助@BaseZen!