Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Load image from URL on WatchKit

Is there a more elegant solution to load an external image on the watch than the following ?

let image_url:String = "http://placehold.it/350x150"

dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)) {
    let url:NSURL = NSURL(string:image_url)!
    var data:NSData = NSData(contentsOfURL: url)!
    var placeholder = UIImage(data: data)!

    // update ui
    dispatch_async(dispatch_get_main_queue()) {
        self.imageView.setImage(placeholder)
    }
}
like image 922
fabian Avatar asked Apr 05 '15 15:04

fabian


4 Answers

Just had the same task, the answers here helped me, but I needed to do some modifications. So I wanted to share the updated version (without any forced unwraps) of the common answers here (should work with Swift 4.2):

public extension WKInterfaceImage {

public func setBackgroundImage(url: String) {
    let asyncQueue = DispatchQueue(label: "backgroundImage")
    asyncQueue.async {
        do {
            if let url = URL(string: url) {
                let data = try Data(contentsOf: url)
                if let placeholder = UIImage(data: data) {
                    self.setImage(placeholder)
                }
            }
        } catch let error {
            print("Could not set backgroundImage for WKInterfaceImage: \(error.localizedDescription)")
        }
    }
}

}

like image 180
Yasin Mantas Avatar answered Sep 22 '22 16:09

Yasin Mantas


NSURL is meant to be used for local files. Instead use NSURLSession. It's also useful to set the scale for the remote image.

import WatchKit

public extension WKInterfaceImage {

    public func setImageWithUrl(url:String, scale: CGFloat = 1.0) -> WKInterfaceImage? {

        NSURLSession.sharedSession().dataTaskWithURL(NSURL(string: url)!) { data, response, error in
            if (data != nil && error == nil) {
                let image = UIImage(data: data!, scale: scale)

                dispatch_async(dispatch_get_main_queue()) {
                    self.setImage(image)
                }
            }
        }.resume()

        return self
    }
}

Use it like this

self.imageView.setImageWithUrl(image_url, scale: 2.0)
like image 29
Fokke Zandbergen Avatar answered Sep 21 '22 16:09

Fokke Zandbergen


public extension WKInterfaceImage {
    public func setImageWithUrl(url:String, scale: CGFloat = 1.0) -> WKInterfaceImage? {
        URLSession.shared.dataTask(with: NSURL(string: url)! as URL) { data, response, error in
            if (data != nil && error == nil) {
                let image = UIImage(data: data!, scale: scale)

                DispatchQueue.main.async() {
                   self.setImage(image)
                }
            }
        }.resume()

        return self
    }
}
like image 26
unixb0y Avatar answered Sep 20 '22 16:09

unixb0y


Here is the category

import WatchKit

public extension WKInterfaceImage {

    public func setImageWithUrl(url:String) -> WKInterfaceImage? {

        dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)) {
            let url:NSURL = NSURL(string:url)!
            var data:NSData = NSData(contentsOfURL: url)!
            var placeholder = UIImage(data: data)!

            dispatch_async(dispatch_get_main_queue()) {
                self.setImage(placeholder)
            }
        }

        return self
    }

}

Use it like this

 self.imageView.setImageWithUrl(image_url)
like image 40
fabian Avatar answered Sep 21 '22 16:09

fabian