it-swarm.com.de

Laden Sie eine Datei mit Android herunter und zeigen Sie den Fortschritt in einem ProgressDialog an

Ich versuche, eine einfache Anwendung zu schreiben, die aktualisiert wird. Dafür benötige ich eine einfache Funktion, die eine Datei herunterladen und den aktuellen Fortschritt anzeigen in einem ProgressDialog. Ich weiß, wie man ProgressDialog macht, aber ich bin nicht sicher, wie man den aktuellen Fortschritt anzeigt und wie man die Datei zuerst herunterlädt.

1006
Tom Leese

Es gibt viele Möglichkeiten, Dateien herunterzuladen. Im Folgenden werde ich die gebräuchlichsten Methoden veröffentlichen. Sie müssen entscheiden, welche Methode für Ihre App besser ist.

1. Verwenden Sie AsyncTask und zeigen Sie den Download-Fortschritt in einem Dialogfeld an

Mit dieser Methode können Sie einige Hintergrundprozesse ausführen und gleichzeitig die Benutzeroberfläche aktualisieren (in diesem Fall wird eine Fortschrittsanzeige aktualisiert).

Dies ist ein Beispielcode:

// declare the dialog as a member field of your activity
ProgressDialog mProgressDialog;

// instantiate it within the onCreate method
mProgressDialog = new ProgressDialog(YourActivity.this);
mProgressDialog.setMessage("A message");
mProgressDialog.setIndeterminate(true);
mProgressDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
mProgressDialog.setCancelable(true);

// execute this when the downloader must be fired
final DownloadTask downloadTask = new DownloadTask(YourActivity.this);
downloadTask.execute("the url to the file you want to download");

mProgressDialog.setOnCancelListener(new DialogInterface.OnCancelListener() {

    @Override
    public void onCancel(DialogInterface dialog) {
        downloadTask.cancel(true); //cancel the task
    }
});

Die AsyncTask wird so aussehen:

// usually, subclasses of AsyncTask are declared inside the activity class.
// that way, you can easily modify the UI thread from here
private class DownloadTask extends AsyncTask<String, Integer, String> {

    private Context context;
    private PowerManager.WakeLock mWakeLock;

    public DownloadTask(Context context) {
        this.context = context;
    }

    @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();
            }

            // 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("/sdcard/file_name.extension");

            byte data[] = new byte[4096];
            long total = 0;
            int count;
            while ((count = input.read(data)) != -1) {
                // allow canceling with back button
                if (isCancelled()) {
                    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;
    }

Die obige Methode (doInBackground) wird immer in einem Hintergrundthread ausgeführt. Sie sollten dort keine UI-Aufgaben ausführen. Auf der anderen Seite werden onProgressUpdate und onPreExecute im UI-Thread ausgeführt, sodass Sie dort die Fortschrittsanzeige ändern können:

    @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) context.getSystemService(Context.POWER_SERVICE);
        mWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK,
             getClass().getName());
        mWakeLock.acquire();
        mProgressDialog.show();
    }

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

    @Override
    protected void onPostExecute(String result) {
        mWakeLock.release();
        mProgressDialog.dismiss();
        if (result != null)
            Toast.makeText(context,"Download error: "+result, Toast.LENGTH_LONG).show();
        else
            Toast.makeText(context,"File downloaded", Toast.LENGTH_SHORT).show();
    }

Damit dies ausgeführt werden kann, benötigen Sie die Berechtigung WAKE_LOCK.

<uses-permission Android:name="Android.permission.WAKE_LOCK" />

2. Vom Dienst herunterladen

Die große Frage hier ist: Wie aktualisiere ich meine Aktivität von einem Dienst aus? . Im nächsten Beispiel werden zwei Klassen verwendet, die Ihnen möglicherweise nicht bekannt sind: ResultReceiver und IntentService. Mit ResultReceiver können wir unseren Thread von einem Service aus aktualisieren. IntentService ist eine Unterklasse von Service, die einen Thread erzeugt, um Hintergrundarbeit von dort aus zu erledigen (Sie sollten wissen, dass ein Service tatsächlich im selben Thread Ihrer App ausgeführt wird; wenn Sie Service erweitern, müssen Sie neue Threads manuell erzeugen, um CPU-Blockierungsvorgänge auszuführen). .

Der Download-Service kann folgendermaßen aussehen:

public class DownloadService extends IntentService {
    public static final int UPDATE_PROGRESS = 8344;

    public DownloadService() {
        super("DownloadService");
    }
    @Override
    protected void onHandleIntent(Intent intent) {

        String urlToDownload = intent.getStringExtra("url");
        ResultReceiver receiver = (ResultReceiver) intent.getParcelableExtra("receiver");
        try {

            //create url and connect
            URL url = new URL(urlToDownload);
            URLConnection connection = url.openConnection();
            connection.connect();

            // this will be useful so that you can show a typical 0-100% progress bar
            int fileLength = connection.getContentLength();

            // download the file
            InputStream input = new BufferedInputStream(connection.getInputStream());

            String path = "/sdcard/BarcodeScanner-debug.apk" ;
            OutputStream output = new FileOutputStream(path);

            byte data[] = new byte[1024];
            long total = 0;
            int count;
            while ((count = input.read(data)) != -1) {
                total += count;

                // publishing the progress....
                Bundle resultData = new Bundle();
                resultData.putInt("progress" ,(int) (total * 100 / fileLength));
                receiver.send(UPDATE_PROGRESS, resultData);
                output.write(data, 0, count);
            }

            // close streams 
            output.flush();
            output.close();
            input.close();

        } catch (IOException e) {
            e.printStackTrace();
        }

        Bundle resultData = new Bundle();
        resultData.putInt("progress" ,100);

        receiver.send(UPDATE_PROGRESS, resultData);
    }
}

Fügen Sie den Service Ihrem Manifest hinzu:

<service Android:name=".DownloadService"/>

Und die Aktivität wird so aussehen:

// initialize the progress dialog like in the first example

// this is how you fire the downloader
mProgressDialog.show();
Intent intent = new Intent(this, DownloadService.class);
intent.putExtra("url", "url of the file to download");
intent.putExtra("receiver", new DownloadReceiver(new Handler()));
startService(intent);

Hier kommt ResultReceiver ins Spiel:

private class DownloadReceiver extends ResultReceiver{

    public DownloadReceiver(Handler handler) {
        super(handler);
    }

    @Override
    protected void onReceiveResult(int resultCode, Bundle resultData) {

        super.onReceiveResult(resultCode, resultData);

        if (resultCode == DownloadService.UPDATE_PROGRESS) {

            int progress = resultData.getInt("progress"); //get the progress
            dialog.setProgress(progress);

            if (progress == 100) {
                dialog.dismiss();
            }
        }
    }
}

2.1 Verwenden Sie die Groundy-Bibliothek

Groundy ist eine Bibliothek, mit der Sie im Grunde Teile des Codes in einem Hintergrunddienst ausführen können. Sie basiert auf dem Konzept ResultReceiver oben gezeigt. Diese Bibliothek ist im Moment veraltet . So würde der ganze Code aussehen:

Die Aktivität, in der Sie den Dialog anzeigen ...

public class MainActivity extends Activity {

    private ProgressDialog mProgressDialog;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        findViewById(R.id.btn_download).setOnClickListener(new View.OnClickListener() {
            public void onClick(View view) {
                String url = ((EditText) findViewById(R.id.edit_url)).getText().toString().trim();
                Bundle extras = new Bundler().add(DownloadTask.PARAM_URL, url).build();
                Groundy.create(DownloadExample.this, DownloadTask.class)
                        .receiver(mReceiver)
                        .params(extras)
                        .queue();

                mProgressDialog = new ProgressDialog(MainActivity.this);
                mProgressDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
                mProgressDialog.setCancelable(false);
                mProgressDialog.show();
            }
        });
    }

    private ResultReceiver mReceiver = new ResultReceiver(new Handler()) {
        @Override
        protected void onReceiveResult(int resultCode, Bundle resultData) {
            super.onReceiveResult(resultCode, resultData);
            switch (resultCode) {
                case Groundy.STATUS_PROGRESS:
                    mProgressDialog.setProgress(resultData.getInt(Groundy.KEY_PROGRESS));
                    break;
                case Groundy.STATUS_FINISHED:
                    Toast.makeText(DownloadExample.this, R.string.file_downloaded, Toast.LENGTH_LONG);
                    mProgressDialog.dismiss();
                    break;
                case Groundy.STATUS_ERROR:
                    Toast.makeText(DownloadExample.this, resultData.getString(Groundy.KEY_ERROR), Toast.LENGTH_LONG).show();
                    mProgressDialog.dismiss();
                    break;
            }
        }
    };
}

Eine GroundyTask-Implementierung, die von Groundy verwendet wird, um die Datei herunterzuladen und den Fortschritt anzuzeigen:

public class DownloadTask extends GroundyTask {    
    public static final String PARAM_URL = "com.groundy.sample.param.url";

    @Override
    protected boolean doInBackground() {
        try {
            String url = getParameters().getString(PARAM_URL);
            File dest = new File(getContext().getFilesDir(), new File(url).getName());
            DownloadUtils.downloadFile(getContext(), url, dest, DownloadUtils.getDownloadListenerForTask(this));
            return true;
        } catch (Exception pokemon) {
            return false;
        }
    }
}

Und füge dies einfach zum Manifest hinzu:

<service Android:name="com.codeslap.groundy.GroundyService"/>

Es könnte nicht einfacher sein, denke ich. Nimm einfach das neueste Glas von Github und du bist bereit zu gehen. Beachten Sie, dass Groundy hauptsächlich dazu dient, externe REST -APIs in einem Hintergrunddienst aufzurufen und Ergebnisse an die zu senden Benutzeroberfläche mit leicht. Wenn Sie so etwas in Ihrer App tun, kann es sehr nützlich sein.

2.2 Verwenden Sie https://github.com/koush/ion

3. Verwenden Sie die Klasse DownloadManager (nur Gingerbread und neuer)

Gingerbread brachte eine neue Funktion, DownloadManager, mit der Sie Dateien einfach herunterladen und die harte Arbeit beim Umgang mit Threads, Streams usw. an das System delegieren können.

Lassen Sie uns zuerst eine Dienstprogrammmethode sehen:

/**
 * @param context used to check the device version and DownloadManager information
 * @return true if the download manager is available
 */
public static boolean isDownloadManagerAvailable(Context context) {

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Gingerbread) {
        return true;
    }
    return false;
}

Der Name der Methode erklärt alles. Sobald Sie sicher sind, dass DownloadManager verfügbar ist, können Sie Folgendes tun:

String url = "url you want to download";
DownloadManager.Request request = new DownloadManager.Request(Uri.parse(url));
request.setDescription("Some descrition");
request.setTitle("Some title");
// in order for this if to run, you must use the Android 3.2 to compile your app
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) {
    request.allowScanningByMediaScanner();
    request.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED);
}
request.setDestinationInExternalPublicDir(Environment.DIRECTORY_DOWNLOADS, "name-of-the-file.ext");

// get download service and enqueue file
DownloadManager manager = (DownloadManager) getSystemService(Context.DOWNLOAD_SERVICE);
manager.enqueue(request);

Der Download-Fortschritt wird in der Benachrichtigungsleiste angezeigt.

Abschließende Gedanken

Erste und zweite Methode sind nur die Spitze des Eisbergs. Es gibt viele Dinge, die Sie beachten müssen, wenn Sie möchten, dass Ihre App robust ist. Hier ist eine kurze Liste:

  • Sie müssen prüfen, ob der Benutzer über eine Internetverbindung verfügt
  • Stellen Sie sicher, dass Sie die richtigen Berechtigungen haben (INTERNET und WRITE_EXTERNAL_STORAGE); auch ACCESS_NETWORK_STATE, wenn Sie die Internetverfügbarkeit überprüfen möchten.
  • Stellen Sie sicher, dass das Verzeichnis, in das Sie Dateien herunterladen möchten, vorhanden ist und über Schreibberechtigungen verfügt.
  • Wenn der Download zu groß ist, möchten Sie möglicherweise eine Möglichkeit implementieren, den Download fortzusetzen, wenn vorherige Versuche fehlgeschlagen sind.
  • Benutzer sind dankbar, wenn Sie ihnen erlauben, den Download zu unterbrechen.

Wenn Sie keine detaillierte Kontrolle über den Downloadprozess benötigen, sollten Sie DownloadManager (3) verwenden, da die meisten der oben aufgeführten Elemente bereits verarbeitet werden.

Bedenken Sie aber auch, dass sich Ihre Bedürfnisse ändern können. Zum Beispiel DownloadManagerführt keine Antwortzwischenspeicherung durch . Die gleiche große Datei wird mehrmals blind heruntergeladen. Es gibt keine einfache Möglichkeit, das Problem nachträglich zu beheben. Wenn Sie mit einem einfachen HttpURLConnection (1, 2) beginnen, müssen Sie lediglich ein HttpResponseCache hinzufügen. Der erste Versuch, die grundlegenden Standardwerkzeuge zu erlernen, kann daher eine gute Investition sein.

Diese Klasse wurde in API-Ebene 26 als veraltet eingestuft. ProgressDialog ist ein modaler Dialog, der den Benutzer daran hindert, mit der App zu interagieren. Anstatt diese Klasse zu verwenden, sollten Sie eine Fortschrittsanzeige wie ProgressBar verwenden, die in die Benutzeroberfläche Ihrer App eingebettet werden kann. Alternativ können Sie eine Benachrichtigung verwenden, um den Benutzer über den Fortschritt der Aufgabe zu informieren. Für weitere Details Link

1823
Cristian

Vergessen Sie nicht, Ihrer Manifestdatei Berechtigungen hinzuzufügen, wenn Sie Inhalte aus dem Internet herunterladen möchten!

<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>
105
Mnightmare

Ja, der obige Code funktioniert. Wenn Sie jedoch Ihr progressbar in onProgressUpdate von Asynctask aktualisieren und die Zurück-Taste drücken oder Ihre Aktivität beenden AsyncTask verliert den Track mit Ihrer Benutzeroberfläche Und wenn Sie zu Ihrer Aktivität zurückkehren, wird in der Fortschrittsanzeige kein Update angezeigt, auch wenn der Download im Hintergrund ausgeführt wird. Versuchen Sie also bei OnResume(), einen Thread wie runOnUIThread mit einer Timer-Task auszuführen, die Ihr progressbar mit Werten aktualisiert, die aus dem AsyncTask laufenden Hintergrund aktualisiert werden.

private void updateProgressBar(){
    Runnable runnable = new updateProgress();
    background = new Thread(runnable);
    background.start();
}

public class updateProgress implements Runnable {
    public void run() {
        while(Thread.currentThread()==background)
            //while (!Thread.currentThread().isInterrupted()) {
            try {
                Thread.sleep(1000); 
                Message msg = new Message();
                progress = getProgressPercentage();        
                handler.sendMessage(msg);
            } catch (InterruptedException e) {
                Thread.currentThread().interrupt();
            } catch (Exception e) {
        }
    }
}

private Handler handler = new Handler(){
    @Override
    public void handleMessage(Message msg) {
        progress.setProgress(msg.what);
    }
};

Vergessen Sie nicht, Destroy den Thread, wenn Ihre Aktivität nicht sichtbar ist.

private void destroyRunningThreads() {
    if (background != null) {
        background.interrupt();
        background=null;
    }
}
31
sheetal

Ich würde empfehlen, mein Projekt zu verwenden Netroid , Es basiert auf Volley . Ich habe einige Funktionen hinzugefügt, wie z. B. Multi-Event-Rückruf, Dateidownload-Verwaltung. Dies könnte hilfreich sein.

17
VinceStyling

Ich habe die Klasse AsyncTask geändert, um die Erstellung von progressDialog im selben Kontext zu handhaben. Ich denke, der folgende Code ist wiederverwendbarer. (Es kann von jeder Aktivität aufgerufen werden, nur Kontext, Zieldatei, Dialognachricht übergeben.)

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();
    }
}
14
The Syrian

Ich fand this Blog-Post sehr hilfreich, die Verwendung von loopJ zum Herunterladen von Dateien, es hat nur eine einfache Funktion, wird einigen neuen Android Leuten hilfreich sein.

8
chintan adatiya

Vergessen Sie nicht, "/ sdcard ..." durch neue Datei ("/ mnt/sdcard/... ") sonst erhalten Sie eine FileNotFoundException

8
ENSATE

Als ich anfing, Android Entwicklung zu lernen, hatte ich gelernt, dass ProgressDialog der richtige Weg ist. Es gibt die setProgress Methode von ProgressDialog, die aufgerufen werden kann, um die Fortschrittsstufe zu aktualisieren, wenn die Datei heruntergeladen wird.

Das Beste, was ich in vielen Apps gesehen habe, ist, dass sie die Attribute dieses Fortschrittsdialogs anpassen, um dem Fortschrittsdialog ein besseres Erscheinungsbild zu verleihen als der Standardversion. Gut, um den Benutzer mit Animationen wie Frosch, Elefant oder süßen Katzen/Welpen zu beschäftigen. Jede Animation im Fortschrittsdialog zieht Benutzer an und sie haben nicht das Gefühl, lange warten zu müssen.

6
Sandeep

Mein persönlicher Rat ist, Fortschrittsdialog zu verwenden und vor der Ausführung aufzubauen oder um OnPreExecute() zu initiieren, den Fortschritt häufig zu veröffentlichen, wenn Sie die horizontale Fortschrittsanzeige des Fortschrittsdialogs verwenden. Der verbleibende Teil ist die Optimierung des Algorithmus von doInBackground.

5
Raju yourPepe

Verwenden Sie Android Abfragebibliothek, in der Tat sehr cool. Sie können es ändern, um ProgressDialog zu verwenden. Wie Sie in anderen Beispielen sehen, wird diese Fortschrittsanzeige in Ihrem Layout angezeigt und nach Abschluss ausgeblendet.

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  
        } 
    }
});
5
Renetik

Berechtigungen

  <uses-permission Android:name="Android.permission.INTERNET" />
  <uses-permission 
   Android:name="Android.permission.WRITE_EXTERNAL_STORAGE" />

Mit HttpURLConnection

import Java.io.File;
import Java.io.FileOutputStream;
import Java.io.IOException;
import Java.io.InputStream;
import Java.net.HttpURLConnection;
import Java.net.MalformedURLException;
import Java.net.URL;

import Android.app.Activity;
import Android.app.Dialog;
import Android.os.Bundle;
import Android.os.Environment;
import Android.view.View;
import Android.view.Window;
import Android.view.View.OnClickListener;
import Android.widget.Button;
import Android.widget.ProgressBar;
import Android.widget.TextView;
import Android.widget.Toast;

public class DownloadFileUseHttpURLConnection extends Activity {

ProgressBar pb;
Dialog dialog;
int downloadedSize = 0;
int totalSize = 0;
TextView cur_val;
String dwnload_file_path =  
"http://coderzheaven.com/sample_folder/sample_file.png";
@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);

    Button b = (Button) findViewById(R.id.b1);
    b.setOnClickListener(new OnClickListener() {
        @Override
        public void onClick(View v) {
             showProgress(dwnload_file_path);

                new Thread(new Runnable() {
                    public void run() {
                         downloadFile();
                    }
                  }).start();
        }
    });
}

void downloadFile(){

    try {
        URL url = new URL(dwnload_file_path);
        HttpURLConnection urlConnection = (HttpURLConnection)   
 url.openConnection();

        urlConnection.setRequestMethod("GET");
        urlConnection.setDoOutput(true);

        //connect
        urlConnection.connect();

        //set the path where we want to save the file           
        File SDCardRoot = Environment.getExternalStorageDirectory(); 
        //create a new file, to save the downloaded file 
        File file = new File(SDCardRoot,"downloaded_file.png");

        FileOutputStream fileOutput = new FileOutputStream(file);

        //Stream used for reading the data from the internet
        InputStream inputStream = urlConnection.getInputStream();

        //this is the total size of the file which we are downloading
        totalSize = urlConnection.getContentLength();

        runOnUiThread(new Runnable() {
            public void run() {
                pb.setMax(totalSize);
            }               
        });

        //create a buffer...
        byte[] buffer = new byte[1024];
        int bufferLength = 0;

        while ( (bufferLength = inputStream.read(buffer)) > 0 ) {
            fileOutput.write(buffer, 0, bufferLength);
            downloadedSize += bufferLength;
            // update the progressbar //
            runOnUiThread(new Runnable() {
                public void run() {
                    pb.setProgress(downloadedSize);
                    float per = ((float)downloadedSize/totalSize) *     
                    100;
                    cur_val.setText("Downloaded " + downloadedSize +  

                    "KB / " + totalSize + "KB (" + (int)per + "%)" );
                }
            });
        }
        //close the output stream when complete //
        fileOutput.close();
        runOnUiThread(new Runnable() {
            public void run() {
                // pb.dismiss(); // if you want close it..
            }
        });         

    } catch (final MalformedURLException e) {
        showError("Error : MalformedURLException " + e);        
        e.printStackTrace();
    } catch (final IOException e) {
        showError("Error : IOException " + e);          
        e.printStackTrace();
    }
    catch (final Exception e) {
        showError("Error : Please check your internet connection " +  
e);
    }       
}

void showError(final String err){
    runOnUiThread(new Runnable() {
        public void run() {
            Toast.makeText(DownloadFileDemo1.this, err,  
      Toast.LENGTH_LONG).show();
        }
    });
}

void showProgress(String file_path){
    dialog = new Dialog(DownloadFileDemo1.this);
    dialog.requestWindowFeature(Window.FEATURE_NO_TITLE);
    dialog.setContentView(R.layout.myprogressdialog);
    dialog.setTitle("Download Progress");

    TextView text = (TextView) dialog.findViewById(R.id.tv1);
    text.setText("Downloading file from ... " + file_path);
    cur_val = (TextView) dialog.findViewById(R.id.cur_pg_tv);
    cur_val.setText("Starting download...");
    dialog.show();

     pb = (ProgressBar)dialog.findViewById(R.id.progress_bar);
     pb.setProgress(0);
            pb.setProgressDrawable(
      getResources().getDrawable(R.drawable.green_progress));  
  }
}
2
vishnuc156

Ich füge eine weitere Antwort für eine andere Lösung hinzu, die ich derzeit verwende, weil Android die Abfrage so umfangreich und nicht gepflegt ist, um gesund zu bleiben. Also bin ich hierher gezogen 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) {
            ...
        }
    });
2
Renetik