【发布时间】:2016-12-30 14:42:15
【问题描述】:
我是 iOS 开发的新手,因此我们将不胜感激。
项目:我正在为 iOS 开发一个 Emoji 风格的键盘。当键盘首次加载时,它会从 Internet 下载一个带有图像 URL 的 .txt 文件(这样我就可以通过更新该 .txt 文件来添加/删除/重新排序图像)。图像 URL 被输入到一个数组中,然后图像 URL 数组用于填充集合视图。
我编写的代码可以运行,但是当我切换到键盘时,系统会等到所有内容都加载完毕(通常为 2-3 秒),然后才会弹出键盘。 我想要的是让键盘在没有图像的情况下立即弹出,然后在图像可用时加载它们 - 这样用户就可以看到键盘工作了。
如何让键盘立即加载,然后下载文本文件,然后下载图片?我找到了很多关于异步下载图片的信息,但我的问题是添加文本下载后稍微复杂一些,我不太明白。
更多信息:
我正在使用 SDWebImage 加载图像,因此它们可以很好地缓存并且应该异步加载,但是我将它包裹在键盘上的方式是等到所有内容都下载后才能显示。
我尝试将下面代码的“do { } catch { }”部分包装在内部 - dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), { //do-catch code }) - 当我这样做时,键盘会像我想要的那样立即弹出,而不是 2-3 秒来加载图像,这需要 8-10 秒,并且在显示任何图像之前仍会等待所有图像。
下面是我的代码。我通过删除按钮和其他有效的代码来简化代码。此代码有两个 .xib 文件:KeyboardView 和 ImageCollectionViewCell
import UIKit
import MobileCoreServices
import SDWebImage
class ImageCollectionViewCell:UICollectionViewCell {
@IBOutlet var imgView:UIImageView!
}
class KeyboardViewController: UIInputViewController, UICollectionViewDataSource, UICollectionViewDelegate {
@IBOutlet var collectionView: UICollectionView!
let blueMojiUrl = NSURL(string: "http://example.com/list/BlueMojiList.txt")
var blueMojiArray = NSMutableArray()
func isOpenAccessGranted() -> Bool {
// Function to test if Open Access is granted
return UIPasteboard.generalPasteboard().isKindOfClass(UIPasteboard)
}
override func viewDidLoad() {
super.viewDidLoad()
let nib = UINib(nibName: "KeyboardView", bundle: nil)
let objects = nib.instantiateWithOwner(self, options: nil)
self.view = objects[0] as! UIView;
self.collectionView.registerNib(UINib(nibName: "ImageCollectionViewCell", bundle: nil), forCellWithReuseIdentifier: "ImageCollectionViewCell")
if (isOpenAccessGranted()) == false {
// Open Access is NOT granted - display error instructions
} else {
// Open Access IS granted
do {
self.blueMojiArray = NSMutableArray(array: try NSString(contentsOfURL: self.blueMojiUrl!, usedEncoding: nil).componentsSeparatedByString("\n"));
self.collectionView.reloadData()
} catch {
// Error connecting to server - display error instructions
}
}
} // End ViewDidLoad
func collectionView(collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
return self.blueMojiArray.count
}
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
let iCell = collectionView.dequeueReusableCellWithReuseIdentifier("ImageCollectionViewCell", forIndexPath: indexPath) as! ImageCollectionViewCell
let url = NSURL(string: self.blueMojiArray.objectAtIndex(indexPath.row) as! String)
iCell.imgView.sd_setImageWithURL(url, placeholderImage: UIImage(named: "loading"))
iCell.layer.cornerRadius = 10.0
return iCell
}
}
更新:
感谢您的回答。我能够用 Alamofire 解决我的问题。我将 Alamofire pod 安装到我的项目中。我用来解决问题的具体代码:首先我在顶部添加了import Alamofire,然后我删除了上面的 do { } catch { } 代码并将其替换为
Alamofire.request(.GET, blueMojiUrl!)
.validate()
.responseString { response in
switch response.result {
case .Success:
let contents = try? NSString(contentsOfURL: self.blueMojiUrl!, usedEncoding: nil)
self.blueMojiArray = NSMutableArray(array: contents!.componentsSeparatedByString("\n"))
self.collectionView.reloadData()
case .Failure:
// Error connecting to server - display error instructions
}
}
现在键盘会立即加载,然后在 2-3 秒内加载图像。
【问题讨论】:
标签: ios swift asynchronous keyboard