blob: ddbfca8bb323598dc165367970c7a0aff21dd193 [file] [log] [blame]
/*
* Copyright 2015-2016 IBM Corporation
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import UIKit
/*
Convenience UI element that allows you to invoke whisk actions. You can use like a normal UIButton and handle all the press events yourself, or you can have the button "self-contained". If you set listenForPressEvents = true it will listen for its own press events and invoke the the configured action.
*/
@objc(WhiskButton) public class WhiskButton: UIButton {
var whisk: Whisk?
var urlSession: NSURLSession?
var actionParameters: Dictionary<String,AnyObject>?
var actionHasResult: Bool = false
var actionName: String?
var actionPackage: String?
var actionNamespace: String?
var isListeningToSelf: Bool?
public required init?(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
}
public override init(frame: CGRect) {
super.init(frame: frame)
}
public var listenForPressEvents: Bool? {
get {
return isListeningToSelf
}
set {
if newValue == true {
self.addTarget(self, action: #selector(WhiskButton.buttonPressed), forControlEvents: .TouchUpInside)
} else {
self.removeTarget(self, action: #selector(WhiskButton.buttonPressed), forControlEvents: .TouchUpInside)
}
isListeningToSelf = newValue
}
}
public var actionButtonCallback: ((reply: Dictionary<String,AnyObject>?, error: WhiskError?) -> Void)?
func buttonPressed() {
invokeAction(parameters: nil, actionCallback: actionButtonCallback)
}
public func setupWhiskAction(qualifiedName qName:String, credentials: WhiskCredentials, hasResult: Bool = false,parameters: Dictionary<String, AnyObject>? = nil, urlSession: NSURLSession? = nil, baseUrl: String? = nil) throws {
let pathParts = try Whisk.processQualifiedName(qName)
setupWhiskAction(pathParts.name, package: pathParts.package, namespace: pathParts.namespace, credentials: credentials, hasResult: hasResult, parameters: parameters, urlSession: urlSession, baseUrl: baseUrl)
}
public func setupWhiskAction(name: String, package: String? = nil, namespace: String = "_", credentials: WhiskCredentials, hasResult: Bool = false,parameters: Dictionary<String, AnyObject>? = nil, urlSession: NSURLSession? = nil, baseUrl: String? = nil) {
whisk = Whisk(credentials: credentials)
if let session = urlSession {
whisk?.urlSession = session
}
if let baseUrl = baseUrl {
whisk?.baseURL = baseUrl
}
actionParameters = parameters
actionName = name
actionPackage = package
actionNamespace = namespace
actionHasResult = hasResult
}
public func invokeAction(parameters parameters: [String:AnyObject]? = nil, actionCallback: ((reply: Dictionary<String,AnyObject>?, error: WhiskError?) -> Void)?) {
if let whisk = whisk, actionName = actionName, actionNamespace = actionNamespace {
dispatch_async(dispatch_get_global_queue(QOS_CLASS_USER_INITIATED, 0)) {
do {
var params:[String:AnyObject]?
if let parameters = parameters {
params = parameters
} else {
params = self.actionParameters
}
try whisk.invokeAction(name: actionName, package: self.actionPackage, namespace: actionNamespace, parameters: params, hasResult: self.actionHasResult, callback: {(reply, error) in
// note callback is in main queue already we should be on the UI thread
if let actionCallback = actionCallback {
actionCallback(reply:reply, error: error)
}
})
} catch {
print("Error invoking action: \(error)")
}
}
} else {
print("WhiskButton action not initialized")
}
}
}