iOS and JS Interactive Combat chapter (OBJC version)

Source: Internet
Author: User

Preface Objectivec and JS Interaction is a common demand, can be novice or so-called master, in fact, is not so simple and clear. Only the JavaScriptCore framework that comes out of iOS7.0 is introduced here. About JavaScriptCore the several types involved in this tutorial: Jscontext, Jscontext is the execution environment representing JS, through the-evaluatescript: Method can execute a JS code jsvalue, Jsvalue encapsulated JS and OBJC in the corresponding type, and invoke the JS API, such as Jsexport, Jsexport is a protocol, adhere to this protocol, you can define our own protocol, the Protocol declared in the API will be exposed in JS, To call OBJC and JS Interactive way through Jscontext, we have two methods of invoking JS code: 1, directly call JS Code 2, in OBJC through the Jscontext injection model, and then call the model method directly call JS code//A Jscontext object, Just like the window in JS,//Just create once. Self.jscontext = [[Jscontext alloc] init]; Jscontext can execute the JS code directly. [Self.jscontext evaluatescript:@ "var num = 10"]; [Self.jscontext evaluatescript:@ "var squarefunc = function (value) {return value * 2}"]; Calculate the area of the square jsvalue *square = [Self.jscontext evaluatescript:@ "Squarefunc (num)"]; can also be obtained by means of subscript jsvalue *squarefunc = self.jscontext[@ "Squarefunc"]; Jsvalue *value = [Squarefunc callwitharguments:@[@ "20"]]; NSLog (@ "%@", Square.tonumber); NSLog (@ "%@", value.tonumber); This method is not injected into the JS model. This method is not suitable for use, usually in JS there are a lot of global functions, in order to prevent the name of names, the way to use the model is best. By the name of the model we negotiated, in JSThe APIs that are exposed by the model that we define in OBJC are invoked directly through the model. Interaction by injecting the model first, we need to define a protocol, and this Protocol must abide by the Jsexport protocol. @protocol javascriptobjectivecdelegate JS calls this method to call OC's system album Method-(void) callsystemcamera;//when called in JS, the function name should be showalertmsg (arg1, arg2)//Here is only two parameters. -(void) Showalert: (NSString *) title msg: (NSString *) msg;//pass through JSON-(void) Callwithdict: (Nsdictionary *) params;// JS call OC, and then in OC by invoking the JS method to pass the value to JS. -(void) Jscallobjcandobjccalljswithdict: (Nsdictionary *) params; @end Next, we need to define a model://This model is used to inject the JS model so that the method can be called through the model. @interface Hybjsobjcmodel:nsobject @property (nonatomic, weak) Jscontext *jscontext; @property (nonatomic, weak) UIWebView *webview;@ End implementation of this model: @implementation hybjsobjcmodel-(void) Callwithdict: (Nsdictionary *) params {NSLog (@ "JS called the OC method, the parameter is:%@", params);} JS called callsystemcamera-(void) Callsystemcamera {NSLog (@ "JS called oc Method, the System album");//JS call after OC, and by OC Call JS, but this is not the parameters of the Jsvalue *jsfunc = self.jscontext[@ "Jsfunc"]; [Jsfunc Callwitharguments:nil];} -(void) Jscallobjcandobjccalljswithdict: (Nsdictionary *) params {NSLog (@ "Jscallobjcandobjccalljswithdict was called, Params is%@ ", params); The method of invoking JS Jsvalue *jsparamfunc = self.jscontext[@ "Jsparamfunc"]; [Jsparamfunc callwitharguments:@[@{@ "age": @10, @ "name": @ "Lili", @ "height": @158}]];} -(void) Showalert: (NSString *) title msg: (NSString *) msg {dispatch_async (Dispatch_get_main_queue (), ^{uialertview *a = [ [Uialertview alloc] initwithtitle:title message:msg delegate:nil cancelbuttontitle:@ "OK" otherbuttontitles:nil, nil]; [A show]; });} @end Next, we are in the controller in the WebView loading completed agent, to JSInjection model. #pragma mark-uiwebviewdelegate-(void) Webviewdidfinishload: (UIWebView *) WebView {self.jscontext = [WebView valueforkeypath:@ "DocumentView.webView.mainFrame.javaScriptContext"]; This is a better way to invoke the method through the model. Hybjsobjcmodel *model = [[Hybjsobjcmodel alloc] init]; self.jscontext[@ "Ocmodel"] = model; Model.jscontext = Self.jscontext; Model.webview = Self.webview; Self.jsContext.exceptionHandler = ^ (Jscontext *context, Jsvalue *exceptionvalue) {context.exception = Exceptionvalue; NSLog (@ "Exception information:%@", exceptionvalue); };} We obtained it through the valueforkeypath of WebView, whose path is DocumentView.webView.mainFrame.javaScriptContext. This allows you to get to the context of JS and then inject our model object into this context. We first write two JS method: var jsfunc = function () {alert (' Objective-c call JS to show alert '), var jsparamfunc = function (argument) { document.getElementById (' Jsparamfuncspan '). InnerHTML = argument[' name ']; Here we define two JS methods, one is Jsfunc, without parameters. The other is Jsparamfunc, with one parameter. Next, we add the following code in the body of the HTML: Test How to use objective-c call JS Now it's time to test the code. When we click on the first button: Call OBJC system camera, through Ocmodel.callsystemcamera (), you can invoke the OC method in HTML via JS. In the OC code, our Callsystemcamera method body, add the following two lines of code, is to get the HTML defined in the JS to go to Jsfunc, and then call it. Jsvalue *jsfunc = self.jscontext[@ "Jsfunc"]; [Jsfunc Callwitharguments:nil]; This allows OC feedback to JS when the OC method is called. Look at the following dictionary parameters:-(void) Jscallobjcandobjccalljswithdict: (Nsdictionary *) params {NSLog (@ "jscallobjcandobjccalljswithdict was called, the params is%@ ", params); The method of invoking JS Jsvalue *jsparamfunc = self.jscontext[@ "Jsparamfunc"]; [Jsparamfunc callwitharguments:@[@{@ "age": @10, @ "name": @ "Lili", @ "height": @158}]];} Get the Jsparamfunc method that we defined in HTML, and then call it and pass a dictionary as a parameter.

iOS and JS Interactive Combat chapter (OBJC version)

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.