OC and JS Hybrid development

Source: Internet
Author: User

As the cost of iOS development increases, more and more companies are starting to use HTML5 hybrid development software, because the cost of using native development costs and time is very large, and the use of HTML5 to build the interface is much more convenient, the efficiency is relatively improved. Although the interaction effect achieved with UIWebView is still much less than the native effect, such interfaces often have no complex interaction, so most mainstream applications now use hybrid development.    Spent a few days, the basis of the JS read all over, and study the Book of Ingenious God, wrote a iOS7 before the JS and OC Mixed development of the demo. Since it is the layout of the HTML5 page, then there must be a HTML5 page, so first we have to write a HTML5 page. Since we are doing the app, so we are targeting the mobile page, we need to add a viewport for the mobile page optimization, and then add a button in the body, binding a click event, in JS to implement this method, through location.href = ""; method to jump Web page, the address is self-defined, and then in OC inside parsing.
<HTML>    <Head>        <MetaCharSet= "UTF-8">        <Metaname= "Viewport"content= "Width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, User-scalable=no, target-densitydpi=device-dpi "/>        <title>Test Web page</title>        <script type= "Text/javascript">            functionsum () {location.href= 'jsoc://call_?100'; //written by yourselfJump URL            }                    functionoccalljsnoparamsfunction () {alert ("the non-parametric method in OC call JS"); }                    functionoccalljshasparamsfunction (name, food) {alert (name+"like to eat:"+URL); }        </Script>    </Head>    <Body>        <Buttonstyle= "backgroud:red; width:100px; height:30px; "onclick= "click ();"> Give me a try.</Button>        <BR>        <ahref= "Http://www.baidu.com">Baidu a bit, you will know</a>    </Body></HTML>
After writing a simple HTML5 page, the next step is to write JS call oc and OC call JS. First, use storyboard to build the layout, and of course you have to drag constraints. Then set the refreshed item to refresh.

Drag the WebView as a property, drag the Refresh method, and refresh the webview when you click on the button.
-(Ibaction) Refresh: (ID) sender{    [Self.webview Reload]; }

Next, you can set the properties of the WebView.   Load the Web page with WebView, can load the network, can also load the local, if you need to load the page above, then you need to add a configuration in the Info.plist. Loading the local, you just need to get the local HTML5 page path, you can show on the webview above.
    // The system can automatically detect phone, link, address, calendar, mailbox    Self.webView.dataDetectorTypes = Uidatadetectortypeall;    Self.webview. delegate = self ;    ///based on the resource name, the extension gets the URL corresponding to the resource  *htmlurl = [[NSBundle mainbundle] Urlforresource:@ "info.html"  withextension: NIL];    [Self.webview loadrequest:[nsurlrequest Requestwithurl:htmlurl];
Set up the WebView, now run up, you should be able to see the effect as shown in.

First of all, a OC call JS method, through-(nullable nsstring *) stringbyevaluatingjavascriptfromstring: (nsstring *) script; method, we can call JS inside we write a good method.    Here, I put the calling method in-(void) Webviewdidfinishload: (UIWebView *) WebView; When WebView loaded the page after the call JS inside the method. Implement OC Invoke JS. I wrote two methods, the first is not with any parameters, so the direct call method can be, and the second is with parameters, so the second method of writing will be different, Stringbyevaluatingjavascriptfromstring can only carry strings, so you need to first pass through stringWithFormat: Stitch the string, and then pass the string in.
-(void ) Webviewdidfinishload: (UIWebView *    ) webview{ //     NSString *js = [WebView stringbyevaluatingjavascriptfromstring:@ "occalljsnoparamsfunction ();"];  NSString *js = [nsstring stringwithformat:@ "  ,  " , @ "Apple   "     //  WebView call JS code, When WebView loads the HTML interface, the   [WebView stringbyevaluatingjavascriptfromstring:js];} 
OC Call JS Code is very simple, but JS call OC is a bit difficult, because this is iOS7 before, that time did not out javascriptcore, so it is difficult to develop. Let's talk about how JS calls OC code. JS call OC, and there is no ready-made API, you can use the "curve to salvation" method, indirectly reached. All network requests initiated within the UIWebView can be notified via the delegate function in the native interface. Therefore, in the HTML5 page to launch a special network request, the content of the requested URL is usually not the actual address, OC in the judgment of this special network request to achieve different functions.
/** * This method is called every time WebView sends a request (JS calls OC)*/-(BOOL) WebView: (UIWebView *) WebView shouldstartloadwithrequest: (Nsurlrequest *Request Navigationtype: (uiwebviewnavigationtype) navigationtype{//get URL full pathNSString *url =request.    url.absolutestring; NSString*protocol =@"jsoc://"; //determine if the URL starts with protocol    if([url hasprefix:protocol]) {//gets the path following the agreement, Substringfromindex: Indicates that the string is truncated from the specified position to the last, and the location that you are capturing contains the specified positionNSString *path =[url substringFromIndex:protocol.length]; //using placeholders for cuttingNsarray *subpaths =[path componentsseparatedbystring:@"?"]; //Get method name JSOC://call_?100NSString *methodname = [[subpaths firstobject] stringbyreplacingoccurrencesofstring:@"_"Withstring:@":"];Nsarray*params=Nil; if(Subpaths.count = =2) {            params= [[subpaths lastobject] componentsseparatedbystring:@"&"]; }                //Calling MethodsSel sel =sel_registername ([MethodName utf8string]); [Self Jsoc_performselector:sel withobjects:params]; returnNO; }        returnYES; }
Sel_registername ([xxx utf8string]); and jsoc_performselector:withobjects: Using the runtime, so also need to have some knowledge of the runtime, SEL is just a pointer to the method, a hash of the method name of the key value, can only represent a method, It exists only to speed up the query of the method. The method that is found through the SEL is then called by its own jsoc_performselector:withobjects: Here we use the custom performselector, because the system gives only one or two parameters, if I want to take more than one parameter, it can only be customized. The SEL points to a method, so we have to implement this method, and here I will simply implement it.
-(void) Call: (NSString *) number{    NSLog (@ " parameter:%@", number);    NSLog (@ " called OC's%s method ", __func__);}
Let's talk about how the custom Performselector is implemented. Add a category to NSObject, and then put jsoc_performselecor:withobjects: Implement the following. Here we will use Nsmethodsignature and nsinvocation, not much nonsense to say, directly on the code.
- (ID) Jsoc_performselector: (SEL) aselector withobjects: (Nsarray *) objects{//nsinvocation Use a Nsinvocation object to wrap a method call (method caller, method name, method parameter, method return value)//obtaining method signatures from selectorsNsmethodsignature *signature = [selfclass] Instancemethodsignatureforselector:aselector]; if(Signature = =Nil) {NSString*reason = [NSString stringWithFormat:@"* * The method[%@] is not find * *", Nsstringfromselector (Aselector)]; @throw[NSException exceptionwithname:@"Error!"Reason:reason Userinfo:nil]; }    //There are two types of messages that can be called directly to an object in iOS, one of which is nsinvocation (for >2 parameters or for processing with a return value) another Performselector:withobjectNsinvocation *invocation =[Nsinvocation invocationwithmethodsignature:signature]; Invocation.target=Self ; Invocation.selector=Aselector; Nsinteger Paras= Signature.numberofarguments-2; Paras=MIN (paras, objects.count);  for(Nsinteger i=0; i<paras;i++){        ID Object=Objects[i]; if([ObjectIskindofclass:[nsnullclass]])Continue; //index starting from 2, the reason is: 0 12 parameters have been occupied by target and selector[Invocation setargument:&Objectatindex:i+2]; }    //Calling Methods[invocation invoke]; IDReturnValue =Nil; if(signature.methodreturnlength) {[Invocation getreturnvalue:&ReturnValue]; }    returnreturnvalue;}
Nsmethodsignature is a method signature, which is officially defined to encapsulate the parameters of a method, return a similar package, and implement message forwarding in a cooperative nsinvocation.

OC and JS Hybrid development

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.