[java] Android로 파일을 다운로드하고 ProgressDialog에서 진행 상황을 표시합니다.


5 Answers

인터넷에서 물건을 다운로드하려는 경우 매니페스트 파일에 권한을 추가하는 것을 잊지 마십시오!

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.example.helloandroid"
    android:versionCode="1"
    android:versionName="1.0">

        <uses-sdk android:minSdkVersion="10" />

        <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"></uses-permission>
        <uses-permission android:name="android.permission.INTERNET"></uses-permission>
        <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"></uses-permission>
        <uses-permission android:name="android.permission.READ_PHONE_STATE"></uses-permission>

        <application 
            android:icon="@drawable/icon" 
            android:label="@string/app_name" 
            android:debuggable="true">

        </application>

</manifest>
Question

업데이트 된 간단한 응용 프로그램을 작성하려고합니다. 이를 위해 파일을 다운로드하고 ProgressDialog 에서 현재 진행률표시 할 수있는 간단한 함수가 필요합니다. ProgressDialog 하는 방법을 알고 있지만 현재 진행률을 표시하는 방법 및 처음에 파일을 다운로드하는 방법을 잘 모르겠습니다.




동일한 문맥에서 progressDialog 생성을 처리하도록 AsyncTask 클래스를 수정했습니다. 다음 코드가 더 재사용 가능할 것이라고 생각합니다. (모든 활동에서 호출 할 수 있습니다. 컨텍스트, 대상 파일, 대화 메시지 전달)

public static class DownloadTask extends AsyncTask<String, Integer, String> {
    private ProgressDialog mPDialog;
    private Context mContext;
    private PowerManager.WakeLock mWakeLock;
    private File mTargetFile;
    //Constructor parameters :
    // @context (current Activity)
    // @targetFile (File object to write,it will be overwritten if exist)
    // @dialogMessage (message of the ProgresDialog)
    public DownloadTask(Context context,File targetFile,String dialogMessage) {
        this.mContext = context;
        this.mTargetFile = targetFile;
        mPDialog = new ProgressDialog(context);

        mPDialog.setMessage(dialogMessage);
        mPDialog.setIndeterminate(true);
        mPDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
        mPDialog.setCancelable(true);
        // reference to instance to use inside listener
        final DownloadTask me = this;
        mPDialog.setOnCancelListener(new DialogInterface.OnCancelListener() {
            @Override
            public void onCancel(DialogInterface dialog) {
                me.cancel(true);
            }
        });
        Log.i("DownloadTask","Constructor done");
    }

    @Override
    protected String doInBackground(String... sUrl) {
        InputStream input = null;
        OutputStream output = null;
        HttpURLConnection connection = null;
        try {
            URL url = new URL(sUrl[0]);
            connection = (HttpURLConnection) url.openConnection();
            connection.connect();

            // expect HTTP 200 OK, so we don't mistakenly save error report
            // instead of the file
            if (connection.getResponseCode() != HttpURLConnection.HTTP_OK) {
                return "Server returned HTTP " + connection.getResponseCode()
                        + " " + connection.getResponseMessage();
            }
            Log.i("DownloadTask","Response " + connection.getResponseCode());

            // this will be useful to display download percentage
            // might be -1: server did not report the length
            int fileLength = connection.getContentLength();

            // download the file
            input = connection.getInputStream();
            output = new FileOutputStream(mTargetFile,false);

            byte data[] = new byte[4096];
            long total = 0;
            int count;
            while ((count = input.read(data)) != -1) {
                // allow canceling with back button
                if (isCancelled()) {
                    Log.i("DownloadTask","Cancelled");
                    input.close();
                    return null;
                }
                total += count;
                // publishing the progress....
                if (fileLength > 0) // only if total length is known
                    publishProgress((int) (total * 100 / fileLength));
                output.write(data, 0, count);
            }
        } catch (Exception e) {
            return e.toString();
        } finally {
            try {
                if (output != null)
                    output.close();
                if (input != null)
                    input.close();
            } catch (IOException ignored) {
            }

            if (connection != null)
                connection.disconnect();
        }
        return null;
    }
    @Override
    protected void onPreExecute() {
        super.onPreExecute();
        // take CPU lock to prevent CPU from going off if the user
        // presses the power button during download
        PowerManager pm = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE);
        mWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK,
                getClass().getName());
        mWakeLock.acquire();

        mPDialog.show();

    }

    @Override
    protected void onProgressUpdate(Integer... progress) {
        super.onProgressUpdate(progress);
        // if we get here, length is known, now set indeterminate to false
        mPDialog.setIndeterminate(false);
        mPDialog.setMax(100);
        mPDialog.setProgress(progress[0]);

    }

    @Override
    protected void onPostExecute(String result) {
        Log.i("DownloadTask", "Work Done! PostExecute");
        mWakeLock.release();
        mPDialog.dismiss();
        if (result != null)
            Toast.makeText(mContext,"Download error: "+result, Toast.LENGTH_LONG).show();
        else
            Toast.makeText(mContext,"File Downloaded", Toast.LENGTH_SHORT).show();
    }
}



나는 안드로이드 쿼리가 너무 커서 건강에 좋지 않기 때문에 지금 사용하고있는 다른 솔루션에 대한 다른 대답을 추가하고 있습니다. 그래서 나는이 https://github.com/amitshekhariitbhu/Fast-Android-Networking 으로 옮겼다.

    AndroidNetworking.download(url,dirPath,fileName).build()
      .setDownloadProgressListener(new DownloadProgressListener() {
        public void onProgress(long bytesDownloaded, long totalBytes) {
            bar.setMax((int) totalBytes);
            bar.setProgress((int) bytesDownloaded);
        }
    }).startDownload(new DownloadListener() {
        public void onDownloadComplete() {
            ...
        }

        public void onError(ANError error) {
            ...
        }
    });



"/ sdcard ..."를 새 파일 ( "/ mnt / sdcard / ...")로 바꾸는 것을 잊지 마십시오. 그렇지 않으면 FileNotFoundException이 발생합니다




Android Query 라이브러리를 사용하십시오. 실제로는 매우 멋지 네요. 다른 예제에서 볼 수있는 것처럼 ProgressDialog 를 사용하도록 변경할 수 있습니다. 레이아웃에서 진행보기를 표시하고 완료 후에 숨길 수 있습니다.

File target = new File(new File(Environment.getExternalStorageDirectory(), "ApplicationName"), "tmp.pdf");
new AQuery(this).progress(R.id.progress_view).download(_competition.qualificationScoreCardsPdf(), target, new AjaxCallback<File>() {
    public void callback(String url, File file, AjaxStatus status) {
        if (file != null) {
            // do something with file  
        } 
    }
});



나는 안드로이드 개발을 배우기 시작하면서, ProgressDialog 가 갈 길이라는 것을 배웠습니다. ProgressDialogsetProgress 메소드는 파일이 다운로드 될 때 진행 수준을 업데이트하기 위해 호출 할 수 있습니다.

많은 앱에서 내가 본 것 중에 가장 좋은 점은이 진행 대화 상자의 속성을 사용자 정의하여 진행률 대화 상자에 더 나은 모양과 느낌을주는 것입니다. 사용자가 개구리, 코끼리 또는 귀여운 고양이 / 강아지와 같은 애니메이션을 사용하는 것이 좋습니다. 진행 대화 상자에있는 모든 애니메이션은 사용자를 끌어 들이고 오랫동안 기다리지 않는 느낌을줍니다.

ProgressDialog 블로그 게시물을 작성하고 곧 공유하겠습니다.

편집 : android에서 파일을 다운로드 할 때 진행률 표시 줄 표시



Related