WebView shouldOverrideUrlLoading()未调用无效链接

dar*_*ord 20 android android-webview

HTML文件中有两种类型的链接:

(1) A normal link like http://www.bbb.com/q?type=normal
(2) A short link like /q?type=short.
Run Code Online (Sandbox Code Playgroud)

对于第一种,只需加载网址.对于第二种,我应该在加载URL之前使用固定地址(如http://www.abc.com).

我试图通过覆盖WebViewClient中的shouldOverrideUrlLoading()函数来做到这一点.但是,不会为第二种类型的链接调用此函数.我尝试将" http://www.abc.com " 添加到HTML文件中的第二种类型的链接.然后当我点击第二种链接时,会调用该函数.

我认为发生的事情是WebView将首先检查链接是否是有效的URL.只有它有效才会调用该函数.我对吗?我怎么解决这个问题?提前致谢.

        contentWebView = new WebView(context);

        webViewClient = new WebViewClient() {
            @Override
            public void onPageStarted(WebView view, String url, Bitmap favicon) {
                super.onPageStarted(view, url, favicon);
            }

            @Override
            public boolean shouldOverrideUrlLoading(WebView view, String url) {
                // String not in Logger.
                Log.d(TAG, "Here!");
                Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
                context.startActivity(intent);
                return true;
            }

            @Override
            public void onPageFinished(WebView view, String url) {
                super.onPageFinished(view, url);
                if (hosted) {
                    contentWebView.setVisibility(VISIBLE);
                } else {
                    summaryTextView.setVisibility(VISIBLE);
                    articleLinkButton.setVisibility(VISIBLE);
                }

                progressBar.setVisibility(View.GONE);
            }
        };

        contentWebView.setWebViewClient(webViewClient);
        contentWebView.getSettings().setJavaScriptEnabled(true);
        contentWebView.loadData(fullString, "text/html", "utf-8");
        contentWebView.setVisibility(GONE);
Run Code Online (Sandbox Code Playgroud)

更多关于此:

我试过改变

contentWebView.loadData(fullString, "text/html", "utf-8");
Run Code Online (Sandbox Code Playgroud)

contentWebView.loadDataWithBaseURL("http://www.abc.com", fullString, "text/html", "utf-8", null);
Run Code Online (Sandbox Code Playgroud)

然后调用该函数.

如果我手动将短链接更改为html字符串中的完整链接.然后该函数也被调用.

所以我认为这可能是发生的事情:WebView检查链接URL是否有效.只有当URL有效时才会调用shouldOverrideUrlLoading().

mar*_*iba 12

您可能正在使用KitKat WebView.这是一个已知问题(我认为它在迁移指南中有所概述),其中无法根据基本URL解析的URL被丢弃在地板上(您不会获得任何回调,无论是overOverrideUrlLoading还是onPageStarted).

问题是你的基本URL是一个数据网址,所以你试图解决'/ q?type = short'对'data:text/html,...'这没有多大意义,所以整个尝试导航到URL会被忽略.

对于使用KURL而不是GURL进行URL处理的pre-KK WebView,这是不同的.GURL通常比KURL更严格(更安全),这是两个WebView版本之间某些不兼容的原因.


mic*_*zuk 8

也许尝试使用onPageStarted方法


Ste*_*tes 6

对我有用的解决方案是使用loadDataWithBaseURL和无效的baseUrl并检测并删除它并在setWebViewClient期间替换为"http://"

public class MyActivity
    extends Activity
{
    private static final String badurl = "http://myappname.invalid/";

    @Override
    public void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        ...
        WebView wv = ((WebView)findViewById(R.id.webview));
        WebSettings settings = wv.getSettings();
        settings.setJavaScriptEnabled(false);
        settings.setSupportMultipleWindows(true);
        wv.setWebChromeClient(new WebChromeClient() {
            @Override
            public boolean onCreateWindow(WebView view, boolean isDialog, boolean isUserGesture, Message resultMsg)
            {
                handleUrlview.getHitTestResult().getExtra());
                return true;
            }
        });
        wv.setWebViewClient(new WebViewClient() {
            @Override
            public boolean shouldOverrideUrlLoading(WebView view, String url) 
            {
                handleUrl(url);
                return true;
            }
        });
        wv.loadDataWithBaseURL(badurl,text,"text/html","utf-8",null);
    }

    private void handleUrl(String url)
    {
        if (url.startsWith(badurl))
            url = "http://"+url.substring(badurl.length());
        try {
            startActivity(new Intent(Intent.ACTION_VIEW, Uri.parse(url)));
        } catch (ActivityNotFoundException e) { }
    }
}
Run Code Online (Sandbox Code Playgroud)