ProgressBar是Android中很常用的一个控件,也就是进度条,但是系统的进度条实在是...哎,大家懂的,本人处女座,这么丑陋的东西怎么能活在我的世界中?
这里以圆形的进度条为例讲一下自定义ProgressBar的过程:
1.找一个好看的圆形进度条图片,当然自己画也行,压力比较大
2.给这个圆形进度条图片设置View动画,就是代码中的RotateAnimation
<?xml version="1.0" encoding="utf-8"?> <rotate xmlns:android="http://schemas.android.com/apk/res/android" android:drawable="@drawable/bg_progress_bar" android:fromDegrees="0" android:pivotX="50%" android:pivotY="50%" android:toDegrees="360"> </rotate>
3.style.xml中给进度条设置样式,核心属性是android:indeterminateDrawable,这个属性是用来替换ProgressBar的图片资源的。
<style name="style_progressbar_custom"> <item name="android:indeterminateDrawable">@drawable/bg_progress_bar_all</item> <item name="android:minWidth">25dp</item> <item name="android:minHeight">25dp</item> <item name="android:maxWidth">45dp</item> <item name="android:maxHeight">45dp</item> </style>
4.然后是设置ProgressBar所在的布局的背景的样式:
<?xml version="1.0" encoding="utf-8"?> <shape xmlns:android="http://schemas.android.com/apk/res/android" android:shape="rectangle"> <solid android:color="#80000000" /> <corners android:radius="6dp" /> <stroke android:width="0.5dp" android:color="#BFFFFFFF" /> <padding android:bottom="8dp" android:left="8dp" android:right="8dp" android:top="8dp" /> </shape>
5.最后就是画ProgressBar的布局:
<?xml version="1.0" encoding="utf-8"?> <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent"> <LinearLayout android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:background="@drawable/bg_linearlayout_no_outside_progress_dialog" android:gravity="center" android:orientation="horizontal"> <FrameLayout android:layout_width="wrap_content" android:layout_height="wrap_content"> <ProgressBar android:id="@+id/progressbar_no_outside_progress_dialog" style="@style/style_progressbar_custom" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:max="100" android:progress="0" /> <TextView android:id="@+id/textview_progress_no_outside_progress_dialog" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_gravity="center" android:textColor="@android:color/white" android:textSize="12dp" /> </FrameLayout> <TextView android:id="@+id/textview_description_no_outside_progress_dialog" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textColor="@android:color/white" android:textSize="15dp" /> </LinearLayout> </FrameLayout>
6.重点来啦,自定义ProgressBar,继承FrameLayout,showProgressDialog()显示,dismissProgressDialog隐藏,setProgress()来设置进度,onTouchEvent()是用来拦截触摸事件的,当ProgressBar显示时,用户不能点击ProgressBar以外的区域,防止出现奇怪的现象。
/** * 自定义的ProgressDialog * 显示时拦截触摸事件,进度条外面不能点击 * * @author yuzhentao */ public class NoOutsideProgressDialog extends FrameLayout {
private ProgressBar pb; private TextView tvProgress, tvDescription; public NoOutsideProgressDialog(Context context) {
this(context, null); }
public NoOutsideProgressDialog(Context context, AttributeSet attrs) {
super(context, attrs); init(context); }
@Override public boolean onTouchEvent(MotionEvent event) {
if (getVisibility() == VISIBLE) {
return true; }
return false; }
private void init(Context context) {
LayoutInflater.from(context).inflate(R.layout.no_outside_progress_dialog, this); pb = (ProgressBar) this.findViewById(R.id.progressbar_no_outside_progress_dialog); tvProgress = (TextView) this.findViewById(R.id.textview_progress_no_outside_progress_dialog); tvDescription = (TextView) this.findViewById(R.id.textview_description_no_outside_progress_dialog); tvProgress.setText("0%"); setVisibility(GONE); }
public void setProgress(int progress) {
pb.setProgress(progress); String percent = progress + "%"; tvProgress.setText(percent); }
public void setDescription(String description) {
tvDescription.setText(description); }
public void showProgressDialog() {
setVisibility(VISIBLE); }
public void dismissProgressDialog() {
setVisibility(GONE); }
}
7.主布局中使用我们自定义的ProgressBar来作为控件:
<?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:gravity="center" android:orientation="vertical"> <yuzhentao.customprogressdialogdemo.NoOutsideProgressDialog android:id="@+id/nooutsideprogressdialog_activity_main" android:layout_width="match_parent" android:layout_height="wrap_content" /> <Button android:id="@+id/button_show_activity_main" android:layout_width="match_parent" android:layout_height="wrap_content" android:background="@android:color/white" android:text="显示" android:textSize="16dp" /> </LinearLayout>
8.最后就是主界面中去使用这个自定义的ProgressBar,这里用一个异步任务来模拟进度,关于AsyncTask怎么使用大家可以看我另外一篇关于AsyncTask的文章:
/** * 主界面 * * @author yuzhentao */ public class MainActivity extends Activity implements View.OnClickListener {
private NoOutsideProgressDialog nopd; @Override protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); initView(); }
@Override public void onClick(View v) {
int viewId = v.getId(); switch (viewId) {
case R.id.button_show_activity_main:
new ProgressDialogAsyncTask().execute(); break; }
}
private void initView() {
nopd = (NoOutsideProgressDialog) findViewById(R.id.nooutsideprogressdialog_activity_main); findViewById(R.id.button_show_activity_main).setOnClickListener(this); nopd.setDescription("正在..."); }
private class ProgressDialogAsyncTask extends AsyncTask<Void, Integer, Void> {
@Override protected void onPreExecute() {
super.onPreExecute(); nopd.showProgressDialog(); }
@Override protected Void doInBackground(Void... params) {
for (int i = 1; i < 100; i++) {
try {
Thread.sleep(50); } catch (InterruptedException e) {
e.printStackTrace(); }
publishProgress(i); }
return null; }
@Override protected void onProgressUpdate(Integer... values) {
super.onProgressUpdate(values); nopd.setProgress(values[0]); }
@Override protected void onPostExecute(Void aVoid) {
super.onPostExecute(aVoid); nopd.dismissProgressDialog(); }
}
}
效果图:
是不是很酷炫啊?呵呵...
Demo地址:http://download.csdn.net/detail/qq_23940659/9469160