如何在webView URL上处理intent://?

Ped*_*ito 17 android webview

我正在开发一个带有的Android应用程序webView.在某些urls我需要使用这个shouldOverrideUrlLoading方法,这是非常直接的:

if(url.startsWith("something")){
//do something
return true;
}
Run Code Online (Sandbox Code Playgroud)

我的问题:

URLS例如,谷歌搜索中的一些有以下URL方案:

intent://en.m.wikipedia.org/wiki/Test_cricket#Intent;scheme=http;package=org.wikipedia;S.browser_fallback_url=https%3A%2F%2Fwww.google.pt%2Fsearchurl%2Fr.html%23app%3Dorg.wikipedia%26pingbase%3Dhttps%3A%2F%2Fwww.google.pt%2F%26url%3Dhttps%3A%2F%2Fen.m.wikipedia.org%2Fwiki%2FTest_cricket;S.android.intent.extra.REFERRER_NAME=https%3A%2F%2Fwww.google.pt;launchFlags=0x8080000;end
Run Code Online (Sandbox Code Playgroud)

我尝试过使用:

Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
startActivity(browserIntent);
Run Code Online (Sandbox Code Playgroud)

但是我收到了一个错误:

10-15 15:18:15.546: W/System.err(29086): android.content.ActivityNotFoundException: No Activity found to handle Intent { act=android.intent.action.VIEW dat=intent://en.m.wikipedia.org/wiki/Test_cricket }
Run Code Online (Sandbox Code Playgroud)

我该如何处理这种URL方案?


更新:

在@CommonsWare评论之后,我尝试使用parseUri()on Intent来创建一个Intent objectfrom URL然后尝试startActivity(),例如:

Intent myIntent = new Intent().parseUri(url, Intent.URI_INTENT_SCHEME);
startActivity(myIntent);
Run Code Online (Sandbox Code Playgroud)

但我仍然得到:

android.content.ActivityNotFoundException: No Activity found to handle Intent { act=android.intent.action.VIEW dat=http://en.m.wikipedia.org/wiki/Test_cricket flg=0x8080000 pkg=org.wikipedia (has extras) }
Run Code Online (Sandbox Code Playgroud)

我可能有错误的指令或者我根本无法构造intent指定的@CommonsWare.关于如何构建的任何提示Intent

com*_*ade 39

此意图URL的结构在此处描述https://developer.chrome.com/multidevice/android/intents.

所以我们可以在内部WebView中处理它,如下所示:

@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
    if (url.startsWith("intent://")) {
        try {
            Context context = view.getContext();
            Intent intent = Intent.parseUri(url, Intent.URI_INTENT_SCHEME);

            if (intent != null) {
                view.stopLoading();

                PackageManager packageManager = context.getPackageManager();
                ResolveInfo info = packageManager.resolveActivity(intent, PackageManager.MATCH_DEFAULT_ONLY);
                if (info != null) {
                    context.startActivity(intent);
                } else {
                    String fallbackUrl = intent.getStringExtra("browser_fallback_url");
                    view.loadUrl(fallbackUrl);

                    // or call external broswer
//                    Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(fallbackUrl));
//                    context.startActivity(browserIntent);
                }

                return true;
            }
        } catch (URISyntaxException e) {
            if (GeneralData.DEBUG) {
                Log.e(TAG, "Can't resolve intent://", e);
            }
        }
    }

    return false;
}
Run Code Online (Sandbox Code Playgroud)

  • 完善!终于解决了 (2认同)
  • 注意:不需要`view.stopLoading();`,因为只有在此函数返回URL并通过返回true来使用URL时,URL才开始加载。 (2认同)

Ped*_*ito 5

同志的回答是要使用的.


我设法解决这个问题的方式并不优雅,但它确实有效.

首先,我们检查,如果网址 startsWithintent://和包含scheme=http,如果是这样,我们之后获得的价值意图://everything until#并把它传递给Intent.ACTION_VIEW,如果没有,我们return false(忽略点击).
我已经使用谷歌手机搜索的几个结果测试了这个解决方案,例如, 推特,脸书,谷歌地图维基百科,它完美无缺.

@Override
public boolean shouldOverrideUrlLoading( WebView view, String url) {
    if(url.startsWith("intent://") && url.contains("scheme=http")){
        url = Uri.decode(url);
        String bkpUrl = null;
        Pattern regexBkp = Pattern.compile("intent://(.*?)#");
        Matcher regexMatcherBkp = regexBkp.matcher(url);
        if (regexMatcherBkp.find()) {
            bkpUrl = regexMatcherBkp.group(1);
            Intent myIntent = new Intent(Intent.ACTION_VIEW, Uri.parse("http://"+bkpUrl));
            startActivity(myIntent);
            return true;
        }else{
            return false;
        }
   }
return false;
}
Run Code Online (Sandbox Code Playgroud)

如果你有更好的解决方案,我想听听.
谢谢大家的支持,特别是CommonsWare.