使用AsyncTask模拟进度条
AsyncTask的简介
AsyncTask可以用来处理一些后台较耗时的任务,查看源码发现其内部就是一个Handler和线程池的封装,可以帮助我们处理耗时任务的同时去更新UI
AsyncTask三个参数
AsyncTask<Params, Progress, Result>
Params 启动任务执行的输入参数,比如下载URL
Progress 后台任务执行的百分比,比如下载进度
Result 后台执行任务最终返回的结果,比如下载结果
AsyncTask的几个函数
-
onPreExecute():(运行在UI线程中) (非必须方法,可以不用实现)
在任务没被线程池执行之前调用,通常用来做一些准备操作,比如下载文件任务执行前,在这个方法中显示一个进度条。 -
doInBackground(Params… params):(运行在子线程中)(此函数是抽象函数必须实现)
在任务被线程池执行时调用 ,可以在此方法中处理比较耗时的操作,比如下载文件等等。 -
onProgressUpdate(Progress… values) (运行在UI线程中) (非必须方法,可以不用实现)
此函数是任务在线程池中执行处于Running状态,回调给UI主线程的进度,比如上传或者下载进度。 -
onPostExecute(Result result)(运行在UI线程中) (非必须方法,可以不用实现)
此函数代表任务在线程池中执行结束了,回调给UI主线程的结果。比如下载结果。 -
onCancelled(Result result)onCancelled()任务关闭的函数
例子的实现
自定义AsyncTask
/**
* 输入、进度、以及输出
* 输入对应的是:async.execute()
* 进度对应的是:onProgressUpdate(Integer... values)
* 输出对应的是:protected String doInBackground 返回值是String
*/
class myAsync extends AsyncTask<Integer, Integer, String> {
private Context context;
private ProgressBar progressBar;
public myAsync(Context context, ProgressBar progressBar) {
this.context = context;
this.progressBar = progressBar;
}
//在这里模拟进度条的增长
//该方法不运行在UI线程中,主要用于异步操作,通过调用publishProgress()方法
//触发onProgressUpdate对UI进行操作
@Override
protected String doInBackground(Integer... integers) {
int i = 0;
publishProgress(i);
for (i = 0;i<=100;i+=10){
try {
//是线程休眠,表示在加载
Thread.sleep(500);
} catch (InterruptedException e) {
e.printStackTrace();
}
publishProgress(i);
}
return i+integers[0].intValue()+"";
}
@Override
protected void onProgressUpdate(Integer... values) {
super.onProgressUpdate(values);
int value = values[0];
if (value==0){
Toast.makeText(context,"开始",Toast.LENGTH_SHORT).show();
}
if (value==100){
Toast.makeText(context,"结束",Toast.LENGTH_SHORT).show();
}
progressBar.setProgress(value);
}
}
Activity
Activity的xml文件
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".AsyncTask.AsyncTaskTestActivity">
<Button
android:id="@+id/sp"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentStart="true"
android:layout_alignParentTop="true"
android:layout_marginStart="142dp"
android:layout_marginTop="61dp"
android:text="点击开始" />
<ProgressBar
android:id="@+id/pb"
style="?android:attr/progressBarStyleHorizontal"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_alignParentStart="true"
android:layout_alignParentTop="true"
android:layout_marginStart="15dp"
android:layout_marginTop="33dp" />
</RelativeLayout>
Activity本体文件
import androidx.appcompat.app.AppCompatActivity;
import android.content.Context;
import android.os.AsyncTask;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.ProgressBar;
import android.widget.Toast;
import com.example.androidtest.R;
public class AsyncTaskTestActivity extends AppCompatActivity {
private ProgressBar progressBar;
private Button button;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_async_task_test);
progressBar = findViewById(R.id.pb);
button = findViewById(R.id.sp);
}
}