H5 唤起 APP的解决方案

 H5 页面唤起APP或跳转到下载APP的某个链接地址。总结如下:

在 IOS 中, 系统版本在 8 以下时,可以监听页面的 pagehide / visibilitychange 事件。 系统版本大于 8 以后,可以使用 universal Link 或 URL scheme 进行跳转。

// IOS 的唤起
function  vForIOS(urlScheme, storeURL, fallback, universalLink) {
     var  tid = deferFallback(TIMEOUT_IOS, storeURL, fallback);
     if  (parseInt(os.version, 10) < 8) {
         bindPagehideEvent(tid);
     else  {
         bindVisibilityChangeEvent(tid);
     }
     if  (parseInt(os.version, 10) > 8 && os.name ==  'iOS' ) {
         // 通过universalLink
         if  (universalLink === undefined) {
             universalLink = urlScheme;
         else  {
             clearTimeout(tid);
         }
         vLocation(universalLink);
     else  {
         vIframe(urlScheme);
     }
}

在安卓中, 安卓版本 4.4.4 以上机型的安卓自带浏览器、chrome 浏览器,需要通过 intent 跳转 【详情请见 https://developer.chrome.com/multidevice/android/intents】,其他浏览器大多数可通过 url scheme 唤起。但由于唤起APP后浏览器并无回调事件,我们很难判断是否已成功拉起APP,比较通用的解决办法是判断计时器是否变慢,若APP启动浏览器最小化入后台将会导致计时器变慢,即为实际事件间隔大于理想时间间隔。若未变慢则判断为未成功拉起APP,则跳转至下载地址。此判断代码如下:

function  deferFallback(timeout, storeURL, fallback) {
         var  clickedAt =  new  Date().getTime();
         return  setTimeout( function  () {
             var  now =  new  Date().getTime();
             if  (isPageVisible() && now - clickedAt < timeout + INTERVAL) {
                 fallback(storeURL);
             }
         }, timeout);
     }

安卓系统中,不同浏览器对唤起APP有严重的兼容性问题,主要处理方案有以下几种:

  1. 通过改变 window.location.href 
  2. 通过创建 iframe 并为其 src 赋值
  3. 通过 intent 
  4. 通过制造不可见 a 链接,并触发点击时间
// 打开页面的方式可能
     // 1. 通过改变location
     function  vLocation(urlScheme) {
         window.location.href = urlScheme;
     }
     // 2. 通过ifreame
     function  vIframe(urlScheme) {
         setTimeout( function  () {
             var  iframe = createHiddenIframe( 'appLauncher' );
             iframe.src = urlScheme;
         }, 100);
     }
     // 3. 通过intent
     function  vIntent(launchURI) {
         if  (browser.name ==  'Chrome' ) {
             move();
         else  {
             setTimeout(move, 100);
         }
 
         function  move() {
             // window.top.location.href = launchURI;
             window.location.href = launchURI
         }
     }
     // 3. 通过添加出发alink
     function  vAlink(launchURI) {
         var  aLink = document.createElement( "a" );
         aLink.setAttribute( "href" , launchURI);
         aLink.style.display =  "none" ;
         document.body.appendChild(aLink);
         var  event = document.createEvent( "HTMLEvents" );
         event.initEvent( "click" , !1, !1);
         aLink.dispatchEvent(event)
     }
  
     // IOS 中的 可见性事件
     function  bindPagehideEvent(tid) {
         window.addEventListener( 'pagehide' function  clear() {
             if  (isPageVisible()) {
                 clearTimeout(tid);
                 window.removeEventListener( 'pagehide' , clear);
             }
         });
     }
 
     function  bindVisibilityChangeEvent(tid) {
         document.addEventListener( 'visibilitychange' function  clear() {
             if  (isPageVisible()) {
                 clearTimeout(tid);
                 document.removeEventListener( 'visibilitychange' , clear);
             }
         });
     }
 
     function  isPageVisible() {
         var  attrNames = [ 'hidden' 'webkitHidden' ];
         for  ( var  i = 0, len = attrNames.length; i < len; i++) {
             if  ( typeof  document[attrNames[i]] !==  'undefined' ) {
                 return  !document[attrNames[i]];
             }
         }
         return  true ;
     }

已知的浏览器兼容问题:

  1.  上述 chrome 和 Android Browser 可以使用 intent 的方式拉起 app
  2.  QQ 浏览器 无法正确判断计时器是否变慢
  3.  微信浏览器 和 百度浏览器 无法唤起 app 除非加入其白名单
  4.  安卓4.4.4以前的 UC浏览器无法正确识别为 【安卓系统】需要单独设置判断条件


另: 研究京东唤起APP的代码时,其对百度浏览器做了如下操作,但我们对此的尝试并为成功,如下为其代码, 希望对后续研究此项的同学有帮助 :

function  ai(aA) {
     var  aD = ay(aA,  true );
     var  aB = aA.universalLinksUrl +  "/ul/ul.action?"  + aD;
     if  (navigator.userAgent.indexOf( "baidubrowser" ) >= 0) {
         window.location.href = aB
     else  {
         var  az = document.createElement( "a" );
         az.setAttribute( "href" , aB);
         az.style.display =  "none" ;
         document.body.appendChild(az);
         var  aC = document.createEvent( "HTMLEvents" );
         aC.initEvent( "click" , !1, !1);
         az.dispatchEvent(aC)
     }
}

转载于:https://www.cnblogs.com/yzhihao/p/8989195.html

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值