更新版本,上传数据到服务端,都是需要进度显示的,Android进度显示两种方式 ProgressDialog 和 ProgressBar。
新版本中ProgressDialog不被推荐使用,所以项目采用ProgressBar。
另有替代方案,采用AlertDialog去提示用户上传和下载的结束,不提供进度界面
Progress分为三种实现方式:
1、MainActivity直接加载,调用xml资源显示
2、Service加载,还是调用MainActivity的bar资源显示,
3、动态加载
如果需要在非主线程显示,可以采用Handler进行数据转发到主线程去显示
代码下载:https://download.csdn.net/download/zishuiyi/10689155
升级版代码(包含上一个连接的内容): https://download.csdn.net/download/zishuiyi/10691073
新增:主线程使用ProgressDialog进行显示;启动Service,然后创建AlertDialog.build创建,确认后跳转到Activity,再动态生成ProgressBar
note:
Service 要配置到xml文件
AlertDialog.build 注册成系统的弹窗就好了,在xml配置设置可以
AlertDialog ad = builder.create();
ad.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ALERT);
跳转采用intent即可
示例代码如下:
public class MainActivity extends AppCompatActivity {
private ProgressBar mProgress;
private int mProgressStatus = 0;
public static ProgressBar progressBar;
private static int PROGRESS = 0;
private Intent intent;
private ProgressBar pb = null;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mProgress = (ProgressBar) findViewById(R.id.progress_bar);
progressBar = (ProgressBar) findViewById(R.id.progress_bar);
intent = new Intent(this, MyServices.class);
}
Handler mHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
mProgress.setProgress(mProgressStatus);
}
};
/**
* TODO: 方式一:显示默认UI上面的进度条
*/
public void useProgressByMainThread(View view) {
Toast.makeText(getApplicationContext(), "useProgressByMainThread", Toast.LENGTH_LONG).show();
// 把进度条复原
mProgressStatus = 0;
new Thread(new Runnable() {
public void run() {
mHandler.sendEmptyMessage(0);
}
}).start();
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(new Runnable() {
public void run() {
String tag = MainActivity.class.getSimpleName();
while (mProgressStatus < 100) {
mProgressStatus = doWork();
mHandler.sendEmptyMessage(0);
Log.d(tag, (System.currentTimeMillis()) / 1000 + "" + mProgressStatus);
}
}
}).start();
}
public int doWork() {
try {
PROGRESS += 1;
Thread.currentThread();
Thread.sleep(200);
} catch (InterruptedException e) {
e.printStackTrace();
}
return PROGRESS;
}
/**
* TODO: 方式二:在Service控制进度条,还是回到MainActivity进行显示
*/
public void useProgressByService(View view) {
Toast.makeText(getApplicationContext(), "useProgressByService", Toast.LENGTH_LONG).show();
// 把进度条复原
mProgressStatus = 0;
new Thread(new Runnable() {
public void run() {
mHandler.sendEmptyMessage(0); // 用线程才能刷新进度条,否则无效
}
}).start();
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
}
// 开启服务进行进度条控制
startService(intent);
}
/**
* TODO: 方式三:动态创建进度条
* https://blog.csdn.net/chdjj/article/details/19825145
*/
public void useProgressByDynamic(View view) {
pb = this.createProgressBar(this);
pb.setVisibility(View.VISIBLE);
}
public ProgressBar createProgressBar(Activity a) {
// 1.找到activity根部的ViewGroup,类型都为FrameLayout。
FrameLayout rootContainer = (FrameLayout) a.findViewById(android.R.id.content);//固定写法,返回根视图
// 2.初始化控件显示的位置
FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.MATCH_PARENT);
lp.gravity = Gravity.CENTER;
// 3.设置控件显示位置
ProgressBar pb = new ProgressBar(a);
pb.setLayoutParams(lp);
pb.setVisibility(View.GONE);//默认不显示
// 4.将控件加到根节点下
rootContainer.addView(pb);
return pb;
}
}
public class MyServices extends Service {
@Nullable
@Override
public IBinder onBind(Intent intent) {
return null;
}
@Override
public void onCreate() {
super.onCreate();
Log.i("test","onCreate");
}
@Override
public int onStartCommand(Intent intent,int flags, int startId) {
new MyThread(intent,startId).start();
Log.i("test","onStartCommand");
return Service.START_STICKY;
}
class MyThread extends Thread{
private int startId;
private Intent intent;
public MyThread(Intent intent,int startId){
this.startId=startId;
this.intent=intent;
}
Handler handler=new Handler(){
@Override
public void handleMessage(Message msg) {
int i=msg.what;
MainActivity.progressBar.setProgress(i);
}
};
@Override
public void run() {
for (int i =1; i <=100 ; i++) {
handler.sendEmptyMessage(i);
SystemClock.sleep(200);
Log.i("test"," "+i);
}
//服务执行完毕后自动调用onDestroy方法
stopSelf(startId);
}
}
@Override
public void onDestroy() {
super.onDestroy();
Log.i("test","onDestroy");
}
}
xml配置
layout
参考:
ProgressDialog 和 ProgressBar对比: https://www.jb51.net/article/38532.htm
直接加载:https://blog.csdn.net/u012587005/article/details/78203882
Service加载: https://blog.csdn.net/Li_Driver/article/details/75140398
动态加载:https://blog.csdn.net/chdjj/article/details/19825145
参考: https://www.cnblogs.com/tianzhijiexian/p/3867731.html
public void progressDialog(String title, String msg) {
final ProgressDialog dialog = new ProgressDialog(this);
dialog.setTitle(title);
dialog.setMessage(msg);
dialog.setCancelable(false);// 设置点击空白处也不能关闭该对话框
dialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
// dialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);//设置采用圆形进度条
dialog.setMax(100);
// dialog.setIndeterminate(true);//设置不显示明确的进度
dialog.setIndeterminate(false);// 设置显示明确的进度
dialog.setButton(ProgressDialog.BUTTON_POSITIVE, "确定",
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int whichButton) {
// 这里添加点击后的逻辑
}
});
dialog.setButton(ProgressDialog.BUTTON_NEUTRAL, "中立",
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int whichButton) {
// 这里添加点击后的逻辑
}
});
dialog.setButton(ProgressDialog.BUTTON_NEGATIVE, "取消",
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int whichButton) {
// 这里添加点击后的逻辑
}
});
dialog.show();
//启动线程,模拟一个耗时的操作
new Thread(new Runnable() {
@Override
public void run() {
int Progress = 0;
while (Progress < 100) {
try {
Thread.sleep(100);
Progress++;
// dialog.setProgress(Progress);
dialog.incrementProgressBy(1);// 进度条一次加10
} catch (InterruptedException e) {
e.printStackTrace();
}
}
dialog.dismiss();// 完成后消失
}
}).start();
}
public void testAlertDialog() {
///new AlertDialog.Builder(xxx, AlertDialog.THEME_HOLO_LIGHT);// 可以设置主题,更换外观
AlertDialog.Builder builder = new AlertDialog.Builder(getApplicationContext());
builder.setMessage("测试");
builder.setPositiveButton("Cancel", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
});
builder.setNegativeButton("Confirm",
new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
turnToNewActivty(); // 跳转到别的界面,然后又可以调用进度条
}
});
AlertDialog ad = builder.create();
// TODO:重点,设置为系统弹窗
ad.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ALERT);
ad.setCanceledOnTouchOutside(false); //点击外面区域不会让dialog消失
ad.show();
}
public void turnToNewActivty() {
Intent intent = new Intent(getApplicationContext(), DemoActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
getApplicationContext().startActivity(intent);
}