android webview下載以及斷點續(xù)傳

game.gif

Android部分代碼

所有下載線程的信息會存儲再hashmap中,但是這個是線程不安全的。不過我們只是用來存一些數(shù)據(jù)用來返回給前端進度。

 /**
     * 當前下載對象
     * {
     * key: name 線程名
     * value : {
     * key:filelength 文件總大小
     * key:state 文件狀態(tài)
     * key:haveDownloaded 當前下載量
     * }
     * }
     */
    public Map<String, Plan> planMap = new HashMap<>();

每次請求會創(chuàng)建一個線程進行下載,代碼每次寫入會有一定的性能損失,可以先緩存部分然后再一次性寫入。


/**
     * 下載文件
     *
     * @param uri 下載地址
     * @throws Exception
     */
    @JavascriptInterface
    public void downLoad(String uri) throws Exception {
        Plan verify = planMap.get(getFileName(uri));
        if (verify == null || (!verify.state && verify.haveDownloaded < verify.filelength)) {
            new Thread() {//子線程
                public void run() {
                    try {
                        //獲取服務器上文件的大小
                        HttpClient client = new DefaultHttpClient();
                        HttpHead request = new HttpHead(uri);
                        HttpResponse response = client.execute(request);
                        //response  只有響應頭  沒有響應體
                        if (response.getStatusLine().getStatusCode() == 200) {
                            Header[] headers = response.getHeaders("Content-Length");
                            String value = headers[0].getValue();
                            //文件大小
                            Long filelength = Long.parseLong(value);
                            Log.i("下載文件", "filelength:" + filelength);
                            //在sdcard創(chuàng)建和服務器大小一樣的文件
                            String name = getFileName(uri);
                            File file = new File("/data/data/" + mContext.getPackageName() + "/files", name + ".downLoad");
                            if ((file.exists() && file.length() < filelength) || !file.exists()) {
                                //隨機訪問文件
                                RandomAccessFile raf = new RandomAccessFile(file, "rwd");
                                //修改下載的開始位置   重新下載
                                Long start = file.length();
                                HttpGet httpget = new HttpGet(uri);
                                httpget.addHeader("Range", "bytes=" + start + "-");//添加請求頭
                                response = client.execute(httpget);
                                InputStream inputStream = response.getEntity().getContent();
                                //跳轉(zhuǎn)到起始位置
                                raf.seek(start);
                                //把流寫入到文件
                                byte[] buffer = new byte[65536];
                                int len = 0;
                                Plan plan = planMap.get(getFileName(uri));
                                if (plan == null)
                                    plan = new Plan();
                                plan.filelength = filelength;
                                plan.haveDownloaded = start;
                                plan.state = true;
                                planMap.put(name, plan);//當前線程數(shù)據(jù)更新
                                /*更新下載文件列表*/
                                updateFiles();
                                while ((len = inputStream.read(buffer, 0, buffer.length)) != -1 && plan.state) {
                                    //寫數(shù)據(jù)
                                    raf.write(buffer, 0, len);
                                    plan.haveDownloaded += len;//當前下載數(shù)
                                    //模擬  看到進度條動的效果
//                                    SystemClock.sleep(50);
                                }
                                httpget.releaseConnection(); 
                                inputStream.close();
                                //關(guān)閉
                                raf.close();
                                if (file.length() == filelength) {
                                    file.renameTo(new File("/data/data/" + mContext.getPackageName() + "/files", name));
                                    /*更新下載文件列表*/
                                    updateFiles();
                                }
                                Log.i("下載", name + "下載結(jié)束");
                            }
                        }
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }

                ;
            }.start();
        }
    }

一個用到的實體類,用來傳給前端當前下載的信息


class Plan {
    /**
     * 總大小
     */
    Long filelength;
    /**
     * 代表當前線程狀態(tài) true進行中 false 暫停
     */
    Boolean state;
    /**
     * 當前已下載的數(shù)據(jù)量
     */
    long haveDownloaded;
}

updateFiles這個方法是用來讀取當前目錄下的文件用的,有g(shù)etFiles的方法給前端調(diào)用,
作用是 重啟APP后獲取下載記錄。
代碼就不貼上來了。
所有代碼只提供參考思路,拒絕縫合怪

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容