Android 通过 WebView 请求下载 APK

来源:互联网 发布:java触屏当乐 编辑:程序博客网 时间:2024/06/06 04:33

很少去研究 Webview 的具体使用,之前在项目中遇到,通过点击 H5 中的按钮来进行下载 Apk 。刚收到这个需求想到的第一个想法就是调用 JS 来实现。之后实际运用前去看了看 WebView 的 API 发现了  WebView 下有一个 setDownloadListener 方法。它主要就是负责当你需要在使用 webview 时下载资源用的。具体的下载 APK 方法:

一个 Downloader 下载工具:

import android.app.DownloadManager;import android.content.BroadcastReceiver;import android.content.Context;import android.content.Intent;import android.content.IntentFilter;import android.database.Cursor;import android.net.Uri;import android.os.Build;import android.os.Environment;import android.support.v4.content.FileProvider;import android.widget.Toast;import java.io.File;/** * Created by 49829 on 2017/8/28. */public class Downloader {    //下载器    private DownloadManager downloadManager;    //上下文    private Context mContext;    //下载的ID    private long downloadId;    public Downloader(Context context) {        this.mContext = context;    }    //下载apk    public void downloadAPK(String url, String name) {        //创建下载任务        DownloadManager.Request request = new DownloadManager.Request(Uri.parse(url));        //移动网络情况下是否允许漫游        request.setAllowedOverRoaming(false);        //在通知栏中显示,默认就是显示的        request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE);        request.setTitle("雪豹外汇");        request.setDescription("正在下载...");        request.setVisibleInDownloadsUi(true);        //设置下载的路径        request.setDestinationInExternalPublicDir(Environment.getExternalStorageDirectory().getAbsolutePath(), name);        //获取DownloadManager        downloadManager = (DownloadManager) mContext.getSystemService(Context.DOWNLOAD_SERVICE);        //将下载请求加入下载队列,加入下载队列后会给该任务返回一个long型的id,通过该id可以取消任务,重启任务、获取下载的文件等等        downloadId = downloadManager.enqueue(request);        //注册广播接收者,监听下载状态        mContext.registerReceiver(receiver,                new IntentFilter(DownloadManager.ACTION_DOWNLOAD_COMPLETE));    }    //广播监听下载的各个状态    private BroadcastReceiver receiver = new BroadcastReceiver() {        @Override        public void onReceive(Context context, Intent intent) {            checkStatus();        }    };    //检查下载状态    private void checkStatus() {        DownloadManager.Query query = new DownloadManager.Query();        //通过下载的id查找        query.setFilterById(downloadId);        Cursor c = downloadManager.query(query);        if (c.moveToFirst()) {            int status = c.getInt(c.getColumnIndex(DownloadManager.COLUMN_STATUS));            switch (status) {                //下载暂停                case DownloadManager.STATUS_PAUSED:                    break;                //下载延迟                case DownloadManager.STATUS_PENDING:                    break;                //正在下载                case DownloadManager.STATUS_RUNNING:                    break;                //下载完成                case DownloadManager.STATUS_SUCCESSFUL:                    //下载完成安装APK                    installAPK();                    break;                //下载失败                case DownloadManager.STATUS_FAILED:                    Toast.makeText(mContext, "下载失败", Toast.LENGTH_SHORT).show();                    break;            }        }    }    //下载到本地后执行安装    private void installAPK() {        Intent intent = new Intent();        File apkFile = queryDownloadedApk();        Uri uri;        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {//7.0启动姿势<pre name="code" class="html">    //com.xxx.xxx.fileprovider为上述manifest中provider所配置相同;apkFile为问题1中的外部存储apk文件</pre>            uri = FileProvider.getUriForFile(mContext, "com.zz.fileprovider", apkFile);            intent.setAction(Intent.ACTION_INSTALL_PACKAGE);            intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);//7.0以后,系统要求授予临时uri读取权限,安装完毕以后,系统会自动收回权限,次过程没有用户交互        } else {//7.0以下启动姿势            uri = Uri.fromFile(apkFile);            intent.setAction(Intent.ACTION_VIEW);            intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);        }        intent.setDataAndType(uri, "application/vnd.android.package-archive");        mContext.startActivity(intent);    }    public File queryDownloadedApk() {        File targetApkFile = null;        if (downloadId != -1) {            DownloadManager.Query query = new DownloadManager.Query();            query.setFilterById(downloadId);            query.setFilterByStatus(DownloadManager.STATUS_SUCCESSFUL);            Cursor cur = downloadManager.query(query);            if (cur != null) {                if (cur.moveToFirst()) {                    String uriString = cur.getString(cur.getColumnIndex(DownloadManager.COLUMN_LOCAL_URI));                    if (!uriString.isEmpty()) {                        targetApkFile = new File(Uri.parse(uriString).getPath());                    }                }                cur.close();            }        }        return targetApkFile;    }}
直接在 WebView  的下载监听中使用:

   webView.setDownloadListener(new DownloadListener() {                            @Override                            public void onDownloadStart(final String url, String userAgent, String contentDisposition, String mimetype, long contentLength) {                                runOnUiThread(new Runnable() {                                    @Override                                    public void run() {                                        //使用前先判断是否有读取、写入内存卡权限                                        if (ContextCompat.checkSelfPermission(RechargeActivity.this, Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {                                            ActivityCompat.requestPermissions(RechargeActivity.this, new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, MY_PERMISSIONS_WRITE_EXTERNAL_STORAGE2);                                        } else {                                            downloadAPK.downloadAPK(url,"***.apk");//DownLoader 需要在oncreate 中初始化                                        }                                    }                                });                            }                        });




原创粉丝点击