H5与Native的爱恨纠缠

2019-04-30  本文已影响0人  往事不许提

随着移动互联网进入下半场,App开发也不再局限与Native开发,或多或少都要用到H5技术,完全以H5技术来构建App的框架也越来越多,比较有代表性的React Native、Flutter。
在这个发展过程中,Native与H5擦出些小火花是不可避免的,接下来就来聊聊他们之间的你来我往、爱恨纠缠!

OC调用JS

[self.webview stringByEvaluatingJavaScriptFromString:@"js代码字符串"];
JSContext *context = [webView valueForKeyPath:@"documentView.webView.mainFrame.javaScriptContext"];
NSString *jsString = @"JS中的函数名('参数1','参数2')";
[context evaluateScript:jsString];

JS调用OC

1.协议

@protocol  协议名称 <JSExport>
协议方法一
- (void)methodFirst;
协议方法二
- (void)methodSecond;
@end 

- (void)webViewDidFinishLoad:(UIWebView *)webView {
    // 获取上下文
   self.jsContext  = [webView valueForKeyPath:@"documentView.webView.mainFrame.javaScriptContext"];
   self.jsContext[@"delegate"] = self;
   self.jsContext.exceptionHandler = ^(JSContext *context, JSValue *exceptionValue){
       context.exception = exceptionValue;
       NSLog(@"异常信息:%@",exceptionValue);
   };
}

- (void)methodFirst {
   //方法实现
   ......
   // 获得想要的结果把结果传回给JS
   //获取JS中的函数
   JSValue *callBack1 = self.jsContext[@"JS中函数名"];
   //把前面获取到的结果作为参数传进JS的callBack参数中
   [callBack1 callWithArguments:@[参数1,参数2,...]];
}
- (void)methodSecond {
   //方法实现
   ......
   // 获得想要的结果把结果传回给JS
   //获取JS中的函数
   JSValue *callBack2 = self.jsContext[@"JS中函数名"];
   //把前面获取到的结果作为参数传进JS的callBack参数中
   [callBack2 callWithArguments:@[参数1,参数2,...]];
}
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
</head>
<body>
<div style="margin-top: 20px">
<h2>JS与OC交互</h2>
<input type="button" value="JS直接调用OC方法 methodFirst" onclick="delegate.methodFirst()">
</div>
<div>
<input type="button" value="JS直接调用OC方法 methodFirst" onclick="callSecondMethod()">
</div>
<script>
  var callSecondMethod  = function() {
        //参数
        var callInfo = JSON.stringify({"key":"value"});
        delegate.methodSecond();// 有参数就传参,无参数就空
  }
  
  var CallBack  = function (str) {
      alert(str);
  }
   var alertCallBack = function(str) {
       alert(str);
   }
</script>

2.block

  self.jsContext  = [webView valueForKeyPath:@"documentView.webView.mainFrame.javaScriptContext"];
  self.jsContext[@"约定函数名"] = ^(){
        // 获取到的调用“约定方法名”时传递的参数数组
        NSArry *args = [JSContext currentArguments];
        for(JSValue *jsVal in args){
              NSLog(@"%@",jsVal.toString);
        }

        __block JSContext *contextObject = context;
        dispatch_async(dispatch_get_main_queue(), ^{
             UI操作
             NSString *jsStr = @"js函数名('传递返回值')";
             [contextObjet ealuateScript:jsStr];
        });
  }

以上就是全部内容。
今天利用以上技术点写了一个H5调用系统相册的小插件,详情:【Demo】(https://github.com/UnclenamedJack/js-oc)

上一篇下一篇

猜你喜欢

热点阅读