使用CloudKit在后台加载图像?

时间:2015-05-27 23:41:32

标签: ios swift cloudkit

我正在开发一个使用UITableViewController的应用程序,它使用固定行高200的UITableViewController。我在CloudKit上存储的JPG图像的原始分辨率为320 x 200.它们的范围从大约25k到45k。< / p>

我遇到的问题是当表填充时,它会在屏幕上加载图像和文本的2-3个单元格。我希望其余的单元格在后台加载,因为总共只有12个条目。将来可能会有多达25-30个。

由于它现在正在工作,当我开始滚动时,正确的文本加载到单元格中,但图像滞后一点并加载到先前显示图像的顶部。

从做一些阅读,这是可重复使用的细胞的结果吗?有没有办法在后台加载所有单元格,因此只有在我滚动后才会加载图像?

这是我得到的代码:

    override func numberOfSectionsInTableView(tableView: UITableView) -> Int {
    // Return the number of sections.
    return 1
}

override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    // Return the number of rows in the section.
    return traders.count
}



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

    if traders.isEmpty {
        // come back here later
        return cell
    }

    let trader = traders[indexPath.row]

    if let traderDate = trader.objectForKey("modificationDate") as? NSDate {

    //format date

    var dateFormatter = NSDateFormatter()
    dateFormatter.dateFormat = "EEE MMM dd hh:mm a"
    var dateString = dateFormatter.stringFromDate(traderDate)
    cell.dateLabel?.text = dateString
    }

    cell.nameLabel?.text = trader.objectForKey("StringAttribute") as? String
    cell.placeLabel?.text = trader.objectForKey("Place") as? String
    println(cell.placeLabel.text)

    // Can we can get the image from cache?

    if let imageFileURL = imageCache.objectForKey(trader.recordID) as? NSURL {
        println("Got image from cache")
        cell.traderImageView?.image = UIImage(data: NSData(contentsOfURL: imageFileURL)!)
    } else {

        // OK then, fetch the image from CloudKit in the background
        let publicDatabase = CKContainer.defaultContainer().publicCloudDatabase
        let fetchRecordsImageOperation = CKFetchRecordsOperation(recordIDs: [trader.recordID])
        fetchRecordsImageOperation.desiredKeys = ["image", "detailImage"]
        fetchRecordsImageOperation.queuePriority = .VeryHigh
        fetchRecordsImageOperation.perRecordCompletionBlock = {(record:CKRecord!, recordID:CKRecordID!, error:NSError!) -> Void in
            if (error != nil) {
                println("Failed to get image: \(error.localizedDescription)")
            } else {
                if let traderRecord = record {
                    dispatch_async(dispatch_get_main_queue(), {
                        if let imageAsset = traderRecord.objectForKey("image") as? CKAsset {
                            cell.traderImageView?.image = UIImage(data: NSData(contentsOfURL: imageAsset.fileURL)!)
                            self.imageCache.setObject(imageAsset.fileURL, forKey: trader.recordID)
                        }

                    })
                }
            }
        }

        println("add operation")
        publicDatabase.addOperation(fetchRecordsImageOperation)
    }
    println("return cell")
    return cell
}

我假设必须有一种方法来完成我所追求的目标,并预先加载所有细胞和图像。我已经考虑将图像作为资产存储在代码本身中(我假设它会加载更快),但我真的希望通过CloudKit仪表板访问更改图像,而无需每次我想要更改图像时重新提交新的应用程序

1 个答案:

答案 0 :(得分:0)

您应该查看缓存库,例如SDWebImageFastImageCache。由于几个原因出现滞后 - jpg解码,从磁盘加载,当图像未在内存中对齐时,Core Animation会出现一些内存问题。

我更喜欢使用FastImageCache,因为它非常棒,可以极大地提升图像加载速度。 This基准测试显示了一点点优势,以防图像已经下载并保留在磁盘上。