<small id='hJm7n'></small> <noframes id='pOLE'>

  • <tfoot id='TeU02rIDF'></tfoot>

      <legend id='7vJeh'><style id='kORA'><dir id='T5cIlx2SbO'><q id='ezjfnmMOkA'></q></dir></style></legend>
      <i id='BHfCY'><tr id='t5GUdKnY'><dt id='0sl3Z'><q id='JSFgLAVpI5'><span id='ijte'><b id='ZgH5h'><form id='THeVL'><ins id='ifMzuC'></ins><ul id='rbNiQ'></ul><sub id='ELraBn'></sub></form><legend id='h8UIf'></legend><bdo id='G4HA8X'><pre id='PhQMRwCgI'><center id='qbR3sS'></center></pre></bdo></b><th id='1KZemoOW'></th></span></q></dt></tr></i><div id='plNT09o4si'><tfoot id='ASncV'></tfoot><dl id='YL148oP'><fieldset id='wRr40gqIv'></fieldset></dl></div>

          <bdo id='pjUO5Kr'></bdo><ul id='e1Iowri2Xd'></ul>

          1. <li id='MVSYzeF'></li>
            登陆

            h5 与原生 app 交互的原理

            admin 2019-05-16 392人围观 ,发现0个评论

            作者 | senntyou

            来历 | segmentfault.com/a/1190000016759517


            现在移动端 web 运用,许多时分都需求与原生 app 进行交互、交流(运行在 webview中),比方微信的 jssdk,经过 window.wx 目标调用一些原生 app 的功用。所以,这次就来捋一捋 h5 与原生 app 交互的原理。

            h5 与原生 app 的交互,实质上说,便是两种调用:

            1. app 调用 h5 的代码

            2. h5 调用 app 的代码

            1、 app 调用 h5 的代码

            由于 app 是宿主,能够直接拜访 h5,所以这种调用比较简略,便是在 h5 中曝露一些大局目标(包含办法),然后在原生 app 中调用这些目标。

            javascript:

            1. window.sdk = {

            2.  double = value => value * 2,

            3.  triple = value => value * 3,

            4. };

            android:

            1. webview.evaluateJavascript('window.sdk.double(10)', new ValueCallback<String>() {

            2.  @Override

            3.  public void onReceiveValue(String s) {

            4.    // 20

            5.  }

            6. });

            ios:

            1. NSString *func = @"window.sdk.double(10)";

            2. NSString *str = [webview stringByEvaluatingJavaScriptFromString:func]; // 20

            2. h5 调用 app 的代码

            由于 h5 不能直接拜访宿主 app,所以这种调用就相对杂乱一点。

            这种调用常用有两种方法:

            1. 由 app 向 h5 注入一个大局 js 目标,然后在 h5 直接拜访这个目标

            2. 由 h5 建议一个自界说协议恳求,app 阻拦这个恳求后,再由 app 调用 h5 中的回调函数

            2.1 由 app 向 h5 注入一个大局 js 目标

            这种方法交流机制简略,比较好了解,而且关于 h5 来说,没有新的东西,所以是比较引荐的一种方法。但这种方法或许存在安全隐患,具体检查 你不知道的 Android WebView 运用缝隙。

            android:

            1. webview.addJavascriptInterface(new Object() {

            2.  @JavascriptInterface

            3.  public int double(value) {

            4.    return value * 2;

            5.  }


            6.  @JavascriptInterface

            7.  h5 与原生 app 交互的原理;public int triple(value) {

            8.    return value * 3;

            9.  }

            10. }, "appSdk");

            ios:

            1. @interface AppSdk : NSObject

            2. {}

            3. - (int) double:(int)value;

            4. - (int) triple:(int)value;

            5. @end


            6. @implementation AppSdk

            7. - (int) double:(int)value {

            8.  return value * 2;

            9. }

            10. - (int) triple:(int)value {

            11.  return value * 3;

            12. }

            13. @end


            14. JSContext *context=[webview valueForKeyPath:@"documentView.webView.mainFrame.javaScriptContext"];


            15. AppSdk *appSdk = [AppSdk new];


            16. context[@"appSdk"] = appSdk;

            javascript:

            1. window.appSdk.double(10); // 20

            2.2 由 h5 建议一个自界说协议恳求

            这种方法要稍杂乱一点,由于需求自界说协议,这对许多前端开发者来说是比较新的东西。所以一般不引荐这种方法,能够作为第一种方法的弥补。

            大致需求以下几个过程:

            1. 由 app 自界说协议,比方 sdk://action?params

            2. 在 h5 界说好回调函数,比方 window.bridge={getDouble:value=>{},getTr旋转小火锅iple:value=>{}}

            3. 由 h5 建议一个自界说协议恳求,比方 location.hrh5 与原生 app 交互的原理ef='sdk://double?value=10'

            4. app 阻拦这个恳求后,进行相应的操作,获取返回值

            5. 由 app 调用 h5 中的回调函数,比方 window.bridge.getDouble(20);

            javascript:

            1. window.bridge = {

            2.  getDouble: value => {

            3.    // 20

            4.  },

            5.  getTriple: value => {

            6.    // more  

            7.  }

            8. };


            9. location.href = 'sdk://double?value=10';

            android:

            1. webview.setWebViewClient(new WebViewClient() {

            2.    @Override

            3.    public boolean shouldOverrideUrlLoading(WebView view, String url) {

            4.        // 判别假如 url 是 sdk:// 打头的就阻拦掉

            5.        // 然后从 url sdk://action?params 中取出 action 与params


            6.        Uri uri = Uri.parseh5 与原生 app 交互的原理(url);                                

            7.        if ( uri.getScheme().equals("sdk")) {


            8.            // 比方 action = double, params = value=10

            9.            webview.evaluateJavascript('window.bridge.getDouble(20)');


            10.            return true;

            11.        }

            12.        return super.shouldOverrideUrlLoading(view, url);

            13.    }

            14. });

            ios:

            1. - (BOOL)webview:(UIWebView *)webview shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigh5 与原生 app 交互的原理ationType {

            2.  // 判别假如 url 是 sdk:// 打头的就阻拦掉

            3.  // 然后从 url sdk://action?params 中取出 action 与params


            4.  NSString *urlStr = request.URL.absoluteString;


            5.  if ([urlStr hasPrefix:@"sdk://"]) {


            6. &nbsh5 与原生 app 交互的原理p;  // 比方 action = double, params = value=10

            7. &nbh5 与原生 app 交互的原理sp;  NSString *func = @"window.bridge.getDouble(20)";

            8.    [webview stringByEvaluatingJavaScriptFromString:func];


            9.    return NO;

            10.  }


            11.  return YES;

            12. }


            请关注微信公众号
            微信二维码
            不容错过
            Powered By Z-BlogPHP