H5与安卓混合开发

1,Header和Cookie的传递。

public void loadUrl(String url){
        Map<String, String> httpsHeaders = SharedPreferencesHelper.getInstance().getHeaders();
        String cookie = SharedPreferencesHelper.getInstance().getCookie();
        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
            CookieSyncManager.createInstance(this);
        }
        CookieManager.getInstance().setCookie(CommonUtil.getHttpBaseUrl(), cookie);
        mWebView.loadUrl(url,httpsHeaders);
    }

2,debug开启

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
            WebView.setWebContentsDebuggingEnabled(BuildConfig.DEBUG);
        }

3,接受H5标题

private class ChromeClient extends WebChromeClient{
        @Override
        public void onReceivedTitle(WebView view, String title) {
            super.onReceivedTitle(view, title);
            if(CheckUtils.isEmpty(nTitle)){
                if(title!=null)setToolbarMiddleText(title);
            }
        }
    }

4,WebViewClient,这个我不怎么常用,显示进度条,捕捉H5里面的异常。但是这种东西交给H5去调好了,安卓端调太费劲。

private class WebClient extends WebViewClient {
        @Override
        public boolean shouldOverrideUrlLoading(WebView view, String url) {
            return loadingUrl(view, url);
        }

        @Override
        public void onPageStarted(WebView view, String url, Bitmap favicon) {
            showProgressDialog(CommonUtil.getString(R.string.toast_please_wait_uploading));
            super.onPageStarted(view, url, favicon);
        }

        @Override
        public void onPageFinished(WebView view, String url) {
            closeProgressDialog();
            super.onPageFinished(view, url);
        }

        @Override
        public void onReceivedError(WebView view, WebResourceRequest request, WebResourceError error) {
            super.onReceivedError(view, request, error);
        }

        @Override
        public void onReceivedHttpError(WebView view, WebResourceRequest request, WebResourceResponse errorResponse) {
            super.onReceivedHttpError(view, request, errorResponse);
        }
    }

5,WebChromeClient,这个里面有两个方法比较长用,

onReceivedTitle接受H5传递的标题。onShowFileChooser当H5调用文件选择时。

private class ChromeClient extends WebChromeClient{
        @Override
        public void onReceivedTitle(WebView view, String title) {
            super.onReceivedTitle(view, title);
            if(CheckUtils.isEmpty(nTitle)){
                if(title!=null)mToolbarMiddle.setText(title);
            }
        }
        @Override
        public boolean onShowFileChooser(WebView webView, ValueCallback<Uri[]> filePathCallback, FileChooserParams fileChooserParams) {
            mUploadCallbackAboveL = filePathCallback;
            Intent i = new Intent(Intent.ACTION_GET_CONTENT);
            i.addCategory(Intent.CATEGORY_OPENABLE);
            i.setType("*/*");
            startActivityForResult(Intent.createChooser(i, "File Browser"),FILE_CHOOSER_RESULT_CODE);
            return true;
        }
    }

6,WebSettings

WebSettings webSettings = mWebView.getSettings();
        webSettings.setJavaScriptCanOpenWindowsAutomatically(true);
        webSettings.setUseWideViewPort(true);//关键点
        webSettings.setDisplayZoomControls(false);
        webSettings.setAllowFileAccess(true); // 允许访问文件
        webSettings.setBuiltInZoomControls(true); // 设置显示缩放按钮
        webSettings.setSupportZoom(true); // 支持缩放
        webSettings.setJavaScriptEnabled(true);
        webSettings.setDomStorageEnabled(true);
        webSettings.setCacheMode(WebSettings.LOAD_NO_CACHE);
        CookieManager.getInstance().setAcceptCookie(true);

7,H5与安卓交互:JavascriptInterface

需要和后端约定,JavascriptInterface是H5调用安卓的方法。

mWebView.addJavascriptInterface(new JSInterface(),"NativeInterface");
private final class JSInterface{
        /**
         * 注意这里的@JavascriptInterface注解, target是4.2以上都需要添加这个注解,否则无法调用
         */
        @JavascriptInterface
        public void jsCallAndroidMethod(final String action,final String param){
            runOnUiThread(new Runnable() {
                @Override
                public void run() {
                    jsCallNative(action,param);
                }
            });
        }
    }

    protected void jsCallNative(String action, String param) {
        if ("close".equalsIgnoreCase(action)) {
            finish();
        }else if ("showRightHeaderBtn".equalsIgnoreCase(action)) {
            JSONObject jsonObject = JSON.parseObject(param);
            final String url = jsonObject.getString("url");
            mToolbarRight.setBackgroundResource(R.drawable.menu_history);
            mToolbarRight.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    loadUrl(url);
                }
            });
        } else if ("hideRightHeaderBtn".equalsIgnoreCase(action)) {
            mToolbarRight.setVisibility(View.GONE);
        }
    }

8,H5与安卓交互:evaluateJavascript

同样的需要和后端约定,evaluateJavascript是安卓调用H5的方法。

@Override
    public void onBackPressed() {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
            mWebView.evaluateJavascript("javascript:phoneBackButtonListener()", new ValueCallback<String>() {
                @Override
                public void onReceiveValue(String value) {
                    // value的值为"true"时,H5页面屏蔽手机返回键
                    // value的值为"false"或"null"时,H5页面不屏蔽手机返回键
                    // phoneBackButtonListener()未定义或没有返回任何数据,则value的值为"null"
                    if ("true".equals(value)) {
                        finish();
                    }else {
                        back();
                    }
                }
            });
        }else {
            back();
        }
    }
    private void back(){
        if (mWebView!=null&&mWebView.canGoBack()&&!TextUtils.equals(url,mWebView.getUrl())) {
            mWebView.goBack();
        } else {
            super.onBackPressed();
        }
    }

而h5这边要真样处理:


function phoneBackButtonListener() {
    // 执行H5的处理逻辑
    return true;
}

9,H5下载文件:DownloadListener

mWebView.setDownloadListener(new FileDownLoadListener());
private final class FileDownLoadListener implements DownloadListener {

        @Override
        public void onDownloadStart(String url, String userAgent, String contentDisposition, String mimetype, long contentLength) {
            showProgressDialog();
            RetrofitService.getInstance().downloadFile(url,getFileName(contentDisposition), new CallBack<File>() {
                @Override
                public void onResponse(File response) {
                    closeProgressDialog();
                    openLocalFile(response.getPath());
                }

                @Override
                public void onError(String message) {
                    closeProgressDialog();
                    super.onError(message);
                }
            });
        }
        private String getFileName(String contentDisposition) {
            if (CheckUtils.isNotEmpty(contentDisposition)) {
                String[] strValue = contentDisposition.split(";");
                for (String value : strValue) {
                    if (StringUtil.isNotBlank(value) && value.contains("filename")) {
                        String[] pair = value.split("=");
                        if (pair.length == 2) {
                            return pair[1];
                        }
                    }
                }
            }
            return String.valueOf(System.currentTimeMillis());
        }
        private void openLocalFile(String fileLocalPath) {
            Intent intent = OpenFileIntentUtil.getOpenFileIntentByLocalPath(WebViewActivity.this, fileLocalPath);
            if (intent != null) {
                try {
                    startActivity(intent);
                } catch (ActivityNotFoundException ex) {
                    ToastHelper.showToast(CommonUtil.getString(R.string.toast_file_open_failed));
                }
            }
        }
    }

10,上传文件:FileChooser

private class ChromeClient extends WebChromeClient{
        @Override
        public void onReceivedTitle(WebView view, String title) {
            super.onReceivedTitle(view, title);
            if(CheckUtils.isEmpty(nTitle)){
                if(title!=null)mToolbarMiddle.setText(title);
            }
        }
        @Override
        public boolean onShowFileChooser(WebView webView, ValueCallback<Uri[]> filePathCallback, FileChooserParams fileChooserParams) {
            mUploadCallbackAboveL = filePathCallback;
            Intent i = new Intent(Intent.ACTION_GET_CONTENT);
            i.addCategory(Intent.CATEGORY_OPENABLE);
            i.setType("*/*");
            startActivityForResult(Intent.createChooser(i, "File Browser"),FILE_CHOOSER_RESULT_CODE);
            return true;
        }
    }

 

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值