Search code examples
swiftcore-dataios8xcode7

Swift - Retrieving Image from Core Data


I've searched over the internet (mostly here) about my issue and I've tried them but I still can't get this to work. I'm trying to retrieve the image from the core data and then display it on a table view. So basically, a table view with a thumbnail image along with a name and a switch. I have the following swift files below. Can anyone lead me what to do? Aside from the image retrieving, I'm planning to add a switch that when turned on/off it asks for a password so that it can be switched on/off. How can I start this? Hoping for your kind responses. Thank you!

I have this snippet of code for saving a record including an image to core data.

let mOC =
(UIApplication.sharedApplication().delegate
    as! AppDelegate).managedObjectContext

@IBOutlet weak var firstName: UITextField!
@IBOutlet weak var lastName: UITextField!
@IBOutlet weak var status: UILabel!

@IBAction func saveRecord(sender: AnyObject) {
    let entityDescription =
    NSEntityDescription.entityForName("Faculty",
        inManagedObjectContext: mOC)

    let faculty = Faculty(entity: entityDescription!,
        insertIntoManagedObjectContext: mOC)

    faculty.firstname = firstName.text
    faculty.lastname = lastName.text

    let pickedImage = UIImageJPEGRepresentation(imageView.image!, 1.0)

    faculty.image = pickedImage

    do {
        try mOC.save()
        firstName.text = ""
        lastName.text = ""

        status.text = "New record saved."
        NSNotificationCenter.defaultCenter().postNotificationName("load", object: nil)
        self.dismissViewControllerAnimated(true, completion: nil)
    } catch {
        status.text = "Record not saved."
    }

}

@IBOutlet weak var imageView: UIImageView!
var newMedia : Bool?
@IBAction func choosePhoto(sender: AnyObject) {
    if UIImagePickerController.isSourceTypeAvailable(
        UIImagePickerControllerSourceType.SavedPhotosAlbum) {
            let imagePicker = UIImagePickerController()

            imagePicker.delegate = self
            imagePicker.sourceType =
                UIImagePickerControllerSourceType.PhotoLibrary
            imagePicker.mediaTypes = [kUTTypeImage as String]
            imagePicker.allowsEditing = false
            self.presentViewController(imagePicker, animated: true,
                completion: nil)
            newMedia = false

    }

}

This is the TableViewController which displays the records on the table view and supposedly with the image, the one I'm trying to figure out.

let managedObjectContext =
(UIApplication.sharedApplication().delegate
    as! AppDelegate).managedObjectContext

var fetchedLastName = [String]()
var fetchedFirstName = [String]()

override func viewDidLoad() {
    super.viewDidLoad()

    NSNotificationCenter.defaultCenter().addObserver(self, selector: "reloadData:",name:"load", object: nil)

    let entityDescription =
    NSEntityDescription.entityForName("Faculty",
        inManagedObjectContext: managedObjectContext)

    let request = NSFetchRequest()
    request.entity = entityDescription

    do{
        let objects = try managedObjectContext.executeFetchRequest(request)

        let results = objects

        if results.count > 0 {
            for var i = 0; i < results.count; i += 1{
                let match = results[i] as! NSManagedObject

                fetchedLastName.append((match.valueForKey("lastname") as? String)!)
                fetchedFirstName.append((match.valueForKey("firstname") as? String)!)

            }
        } else {

        }
    }
    catch{}
}

func reloadData(notification: NSNotification){
    fetchedLastName.removeAll()
    fetchedFirstName.removeAll()

    let entityDescription =
    NSEntityDescription.entityForName("Faculty",
        inManagedObjectContext: managedObjectContext)

    let request = NSFetchRequest()
    request.entity = entityDescription

    do{
        let objects = try managedObjectContext.executeFetchRequest(request)

        let results = objects

        if results.count > 0 {
            for var i = 0; i < results.count; i += 1{
                let match = results[i] as! NSManagedObject

                fetchedLastName.append((match.valueForKey("lastname") as? String)!)
                fetchedFirstName.append((match.valueForKey("firstname") as? String)!)
            }
        } else {

        }
    }
    catch{}

    self.tableView.reloadData()
}

Am I right to think that it is somewhere here that I should write the code to retrieve the image from the core data and display it on the table view?

override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCellWithIdentifier("TEACH", forIndexPath: indexPath) as! TEACHTableViewCell

    let row = indexPath.row

    cell.facultyName.text = fetchedLastName[row] + ", " + fetchedFirstName[row]

    return cell
}

Solution

  • Ok here is the fixed code:

    TeachTableViewController:

    //
    //  TEACHTableViewController.swift
    //  TEACH
    //
    //  Created by ICST340.N1 on 9/29/15.
    //  Copyright © 2015 IyoTugs. All rights reserved.
    //
    
    import UIKit
    import CoreData
    
    class TEACHTableViewController: UITableViewController {
    let managedObjectContext =
    (UIApplication.sharedApplication().delegate
        as! AppDelegate).managedObjectContext
    
    var fetchedLastName = [String]()
    var fetchedFirstName = [String]()
    var fetchedImage = [UIImage]()
    
    override func viewDidLoad() {
        super.viewDidLoad()
    
        NSNotificationCenter.defaultCenter().addObserver(self, selector: "reloadData:",name:"load", object: nil)
    
        let entityDescription =
        NSEntityDescription.entityForName("Faculty",
            inManagedObjectContext: managedObjectContext)
    
        let request = NSFetchRequest()
        request.entity = entityDescription
    
        do{
            let objects = try managedObjectContext.executeFetchRequest(request)
    
            let results = objects
    
            if results.count > 0 {
                for var i = 0; i < results.count; i += 1{
                    let match = results[i] as! NSManagedObject
    
                    fetchedLastName.append((match.valueForKey("lastname") as? String)!)
                    fetchedFirstName.append((match.valueForKey("firstname") as? String)!)
                    //added this is convert the image
                    let image = match.valueForKey("image") as! NSData
                    fetchedImage.append(UIImage(data: image)!)
    
                }
            } else {
    
            }
        }
        catch{}
        // Uncomment the following line to preserve selection between presentations
        // self.clearsSelectionOnViewWillAppear = false
    
        // Uncommented this
        // Uncomment the following line to display an Edit button in the          navigation bar for this view controller.
        //        self.navigationItem.rightBarButtonItem = self.editButtonItem()
    }
    
    func reloadData(notification: NSNotification){
        fetchedLastName.removeAll()
        fetchedFirstName.removeAll()
        //Added this to remove all images
        fetchedImage.removeAll()
    
        let entityDescription =
        NSEntityDescription.entityForName("Faculty",
            inManagedObjectContext: managedObjectContext)
    
        let request = NSFetchRequest()
        request.entity = entityDescription
    
        do{
            let objects = try managedObjectContext.executeFetchRequest(request)
    
            let results = objects
    
            if results.count > 0 {
                for var i = 0; i < results.count; i += 1{
                    let match = results[i] as! NSManagedObject
    
                    fetchedLastName.append((match.valueForKey("lastname") as? String)!)
                    fetchedFirstName.append((match.valueForKey("firstname") as? String)!)
                    //added this is convert the image
                    let image = match.valueForKey("image") as! NSData
                    fetchedImage.append(UIImage(data: image)!)
    
                }
            } else {
    
            }
        }
        catch{}
    
        self.tableView.reloadData()
    }
    
    
    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }
    
    // MARK: - Table view data source
    
    override func numberOfSectionsInTableView(tableView: UITableView) -> Int {
        // #warning Incomplete implementation, return the number of sections
        return 1
    }
    
    override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        // #warning Incomplete implementation, return the number of rows
        return fetchedLastName.count
    }
    
    
    override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCellWithIdentifier("TEACH", forIndexPath: indexPath) as! TEACHTableViewCell
    
        let row = indexPath.row
    
        print(fetchedFirstName)
    
        cell.facultyName.text = fetchedLastName[row] + ", " + fetchedFirstName[row]
        cell.facultyImage.image = fetchedImage[row]
    
        return cell
    }
    
    }
    

    I marked each spot that I fixed, but there were only four spots. Two of them had to do with taking the NSData and turning it into an Image(in viewDidLoad and reloadData, same spots). One of them add to do with commenting out the line that made the right navbar button an edit button. And the last one fetchedImage.removeAll() on the top of reloadData to take out all of the images.