populate image array with parse in swift

2019-09-16 03:09发布

问题:

Hi I'm new with swift and parse.com, I'm trying do populate my array with already saved images in parse, try to use the dispatch_async but don't know how this works, heres the code:

//imageArray declaration in table:
var imageArray: Array<UIImage> = []


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

    var query = PFQuery(className: "ParseClass")

    query.findObjectsInBackgroundWithBlock { ( objects: [AnyObject]?, error: NSError?) -> Void in

        if(error == nil) {

            let imageObjects = objects as! [PFObject]

            for object in objects! {

                let thumbNail = object["columnInParse"] as! PFFile

                thumbNail.getDataInBackgroundWithBlock ({ (imageData: NSData?, error: NSError?) -> Void in

                    if (error == nil) {

                        if let image = UIImage(data:imageData!) {

 //here where the error appears: Cannot invoke 'dispatch_async' with an argument list of type '(dispatch_queue_t!, () -> _)' 
                           dispatch_async(dispatch_get_main_queue()) {                                     
                                cell.image.image = self.imageArray.append( image )
                            }

                        }

                    }
                })
            }
        }
        else{

            println("Error in retrieving \(error)")

        }
    }

    return cell
}

Hope you people understand that code.

回答1:

The proper way to use that dispatch block is like so:

dispatch_async(dispatch_get_main_queue(), { () -> Void in
                //perform your work here
                self.imageArray.append(image)
                cell.image.image = imageArray[indexPath.row]
            })

Another reason that the compiler is giving this warning is because you're trying to append images to an array and set that as the cells image. What you should be doing is shown above.

Finally, I would recommend moving your queries out of cellForRowAtIndexPath: and into seperate methods as this is bad code design.

Edit: Rewrote method to provide examples of good code design...

var imageArray = [UIImage]()

func performLookupQuery() {
    var query = PFQuery(className: "ParseClass")
    query.findObjectsInBackgroundWithBlock {(objects: [AnyObject]?, error: NSError?)
        if error == nil {
            let imageObjects = objects as! [PFObject]
            for object in imageObjects {
                let thumbnail = object["columnInParse"] as! PFFile
                thumbnail.getDataInBackgroundWithBlock{(imageData: NSData?, error: NSError?)
                    if error == nil {
                        if let image = UIImage(data: imageData!) {
                            imageArray.append(image)
                            //now your imageArray has all the images in it that you're trying to display
                            //you may need to reload the TableView after this to get it to display the images

                        }
                    }
                }
            }
        }
        self.tableView.reloadData()
    }
}

override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCellWithIdentifier("cell", forIndexPath: indexPath)
    cell.image.image = nil
    cell.image.image = imageArray[indexPath.row]
    return cell
}

I didn't add all the error checking in the query method like you should, I was just writing it to show what you would do. Now that you have this query method, you can call it in viewDidLoad and then the results will be available when you try to load your table.

override func viewDidLoad(animated: Bool) {
    super.viewDidLoad(animated)
    self.performLookupQuery()
}