AsyncTask的定義:
public abstract class AsyncTask<Params, Progress, Result>
以上三種泛型類型分别代表“啟動任務執行的輸入參數”、“背景任務執行的進度”、“背景計算結果的類型”。在特定場合下,并不是所有類型都被使用,如果沒有被使用,可以用java.lang.Void類型代替。
異步任務執行步驟:
1、execute(Params... params):執行任務,一般在onCreate中調用這個方法,就可以開始執行任務
2、onPreExecute():調用了execute(Params... params)後就立即執行,用于在執行耗時任務前對UI進行一些操作,比如可以彈出進度對話框
3、doInBackground(Params... params):在onPreExecute()完成後立即執行,本方法是執行耗時任務的(如:擷取網絡資源),本方法内不能更新UI
4、onProgressUpdate(Progress... values):在調用了publishProgress(Progress... values)後被執行,本方法可以更新進度條,publishProgress(Progress... values)在doInBackground(Params... params)裡面調用
5、onPostExecute(Result result):背景操作結束時,執行此方法,比如關閉進度對話框。
MainActivity.java:
package com.example.demo2;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.HttpStatus;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.DefaultHttpClient;
import android.app.Activity;
import android.app.ProgressDialog;
import android.os.AsyncTask;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.ProgressBar;
import android.widget.TextView;
public class MainActivity extends Activity {
private Button execute, cancel;
private ProgressBar progress_bar;
private TextView textView;
private ProgressDialog dialog;
private MyTask mTask;
private String TAG = "MainActivity";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
execute = (Button) findViewById(R.id.execute);
cancel = (Button) findViewById(R.id.cancel);
textView = (TextView) findViewById(R.id.textView);
progress_bar = (ProgressBar) findViewById(R.id.progress_bar);
execute.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View arg0) {
// 沒次都要new一個執行個體,建立的任務隻能執行一次,否則會出現異常
mTask = new MyTask();
mTask.execute("http://www.baidu.com");
execute.setEnabled(false);
cancel.setEnabled(true);
}
});
cancel.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View arg0) {
// 取消一個正在執行的任務,onCancelled将會被調用
mTask.cancel(true);
}
});
}
private class MyTask extends AsyncTask<String, Integer, String> {
// onPreExecute用于執行背景任務前做一些UI操作
@Override
protected void onPreExecute() {
Log.i(TAG, "onPreExecute()");
textView.setText("加載中...");
dialog = ProgressDialog.show(MainActivity.this, "提示", "加載中...");
}
// doInBackground方法内部執行背景任務(就是執行網絡請求等耗時任務),不可在此方法内修改UI
@Override
protected String doInBackground(String... arg0) {
Log.i(TAG, "doInBackground(String... arg0)");
try {
HttpClient client = new DefaultHttpClient();
HttpGet get = new HttpGet(arg0[0]);
HttpResponse response = client.execute(get);
if (response.getStatusLine().getStatusCode() == HttpStatus.SC_OK) {
HttpEntity entity = response.getEntity();
InputStream is = entity.getContent();
long total = entity.getContentLength();
ByteArrayOutputStream baos = new ByteArrayOutputStream();
byte[] buf = new byte[1024];
int count = 0;
int length = -1;
while ((length = is.read(buf)) != -1) {
baos.write(buf, 0, length);
count += length;
// 調用publishProgress公布進度,然後onProgressUpdate方法将被執行
publishProgress((int) ((count / (float) total) * 100));
// 為延時進度,休眠500毫秒
Thread.sleep(500);
}
return new String(baos.toByteArray(), "utf-8");
}
} catch (ClientProtocolException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
// onProgressUpdate用于更新進度資訊
@Override
protected void onProgressUpdate(Integer... values) {
Log.i(TAG, "onProgressUpdate(Integer... values)");
progress_bar.setProgress(values[0]);
textView.setText("loading..." + values[0] + "%");
}
// onPostExecute方法用于在執行完背景任務後更新UI,顯示結果
@Override
protected void onPostExecute(String result) {
Log.i(TAG, "onPostExecute(String result)");
dialog.dismiss();
textView.setText(result);
execute.setEnabled(true);
cancel.setEnabled(false);
}
// onCancelled方法用于在取消執行中的任務時更新UI
@Override
protected void onCancelled() {
Log.i(TAG, "onCancelled() called");
textView.setText("任務取消了");
progress_bar.setProgress(0);
execute.setEnabled(true);
cancel.setEnabled(false);
}
}
}
main.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<Button
android:id="@+id/execute"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="執行" />
<Button
android:id="@+id/cancel"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="取消" />
<ProgressBar
android:id="@+id/progress_bar"
style="?android:attr/progressBarStyleHorizontal"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:max="100"
android:progress="0" />
<ScrollView
android:layout_width="match_parent"
android:layout_height="wrap_content" >
<TextView
android:id="@+id/textView"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</ScrollView>
</LinearLayout>
不要忘了添加網絡通路權限:
<uses-permission android:name="android.permission.INTERNET"/>