2014-2-14ProgressBar及其子类

1.进度条(ProgressBar)的功能与用法

       ProgressBar组件本身代表了进度条组件,它还派生了两个常用组件:SeekBar和RatingBar.

       进度条通常用于向用户显示某个耗时操作完成的百分比,通过style属性可以为ProgressBar指定风格(水平进度条、环形进度条等)

       Xml属性中,android:progressDrawable用于指定进度条的轨道的绘制形式,该属性可指定一个LayoutDrawable对象(该对象可通过在Xml文件中用<layer-list>元素进行配置)

实例:

界面布局文件:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    >
    <LinearLayout
        android:orientation="horizontal"
        android:layout_width="match_parent"
        android:layout_height="wrap_content">
        <!-- 定义一个大环形进度条 -->
        <ProgressBar
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            style="@android:style/Widget.ProgressBar.Large"/>
        <!-- 定义一个中等大小的环形进度条 -->
        <ProgressBar
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"/>
        <!-- 定义一个小环形进度条 -->
        <ProgressBar
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            style="@android:style/Widget.ProgressBar.Small"/>
    </LinearLayout>
    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="任务完成的进度"/>
    <!-- 定义一个水平进度条 -->
    <ProgressBar
        android:id="@+id/bar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:max="100"
        style="@android:style/Widget.ProgressBar.Horizontal"/>
    <!-- 定义一个水平进度条,并改变轨道外观 -->
    <ProgressBar
        android:id="@+id/bar2"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:max="100"
        android:progressDrawable="@drawable/my_bar"
        style="@android:style/Widget.ProgressBar.Horizontal"/>
</LinearLayout>

       Ps:上面定义了三个环形进度条,这些进度条无法显示进度,只显示一个不断旋转的图片。布局文件定义两个水平进度条的最大值为100,第二个外观被定义为@drawable/my_bar  代码为:

<?xml version="1.0"encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
    <!-- 定义轨道的背景 -->
    <item android:id="@android:id/background"
        android:drawable="@drawable/no"></item>
    <!-- 定义轨道上已完成部分的样式 -->
    <item android:id="@android:id/progress"
        android:drawable="@drawable/ok"/>
</layer-list>

Activity代码清单,用一个填充数组的任务模拟了耗时操作,并以进度条来标识任务的完成百分比:

public class ProgressBarT extends Activity {
 
    //该程序模拟填充长度为100的数据
    private int[] data = new int[100];
    int hasDate = 0;
    //记录ProgressBar的完成进度
    int status = 0;
    ProgressBar bar, bar2;
    //创建一个负责更新的进度的Handler
    Handler mHandler = new Handler()
    {
       public voidhandleMessage(Message msg)
       {
           //表明信息是由该程序发送的
           if (msg.what == 0x111)
           {
              bar.setProgress(status);
              bar2.setProgress(status);
           }
       }
    };
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.progress_bar_t);
        bar = (ProgressBar) findViewById(R.id.bar);
        bar2 = (ProgressBar) findViewById(R.id.bar2);
        //启动线程来执行任务
        new Thread()
        {
            public void run()
            {
               while (status < 100)
               {
                   //获取耗时操作的完成百分比
                   status = doWork();
                   //发送消息
                   mHandler.sendEmptyMessage(0x111);
               }
            }
        }.start();
    }
    //模拟一个耗时操作
    public int doWork()
    {
        //为数组元素赋值
        data[hasDate++] = (int) (Math.random()*100);
        try
        {
           Thread.sleep(100);
        }
        catch (InterruptedException e)
        {
           e.printStackTrace();
        }
        return hasDate;
    }
}

效果:

实例2:显示在标题上的进度条

       这种进度条直接由Activity的方法启用为在窗口上显示进度条,需经如下两部:

1.       调用Activity的requestWindowFeature()方法,该方法根据传入的参数可启用特定的窗口特征。

2.       调用Activity的setProgressBarIndeterminateVisibility(boolean)或

setProgressBarVisibility(boolean)方法即可控制进度条的显示和隐藏。

Activity代码清单

public class TitleProgressBarT extends Activity {
 
    Button bn1, bn2;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        //设置窗口特征:启动显示进度的进度条
        requestWindowFeature(Window.FEATURE_PROGRESS);
        //设置窗口特征:启用不显示进度的进度条
        requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS);
        setContentView(R.layout.title_progress_bar_t);
        bn1 = (Button) findViewById(R.id.bn1);
        bn2 = (Button) findViewById(R.id.bn2);
        bn1.setOnClickListener(new OnClickListener()
        {
 
           @Override
           public void onClick(View v) {
              //显示不带进度的进度条
              setProgressBarIndeterminateVisibility(true);
              //显示带进度的进度条
              setProgressBarVisibility(true);
              //设置进度条的进度
              setProgress(4500);
           }
        });
        bn2.setOnClickListener(new OnClickListener()
        {
 
           @Override
           public void onClick(View v) {
              //显示不带进度的进度条
              setProgressBarIndeterminateVisibility(false);
              //显示带进度的进度条
              setProgressBarVisibility(false);
           }
        });
    }
}

效果:

2.拖动条(SeekBar)的功能和用法

       拖动条与进度条非常相似,只是拖动条通过滑块位置来表示数值—而且拖动条允许用户拖动滑块来改变值。

       改变滑块外观可通过如下属性android:thumb:指定一个Drawable对象,该对象将作为自定义滑块。

       为了让程序响应拖动条滑块位置变化,程序可以考虑为它绑定一个OnSeekBarChangeListener监听器。

       实例:

线性布局一个图片组件、一个拖动条

<ImageView
        android:id="@+id/image"
        android:layout_width="match_parent"
        android:layout_height="240px"
        android:src="@drawable/p1"/>
    <!-- 定义一个拖动条,并改变它的滑块外观 -->
    <SeekBar
        android:id="@+id/seekbar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:max="255"
        android:progress="255"
        android:thumb="@drawable/ic_launcher"/>

PS:该拖动条的最大值、当前值都是255,android:thumb属性是改变拖动条滑块的外观。

Activity中绑定一个监听器,动态改变图片透明度:

seekBar.setOnSeekBarChangeListener(new OnSeekBarChangeListener()
        {
 
            //当滑动条的滑块位置发生改变时触发该方法
           @Override
           public void onProgressChanged(SeekBar arg0, int progress,
                  boolean fromUser) {
              //动态改变图片的透明度
              image.setAlpha(progress);
           }
 
           @Override
           public void onStartTrackingTouch(SeekBar arg0) {
             
           }
 
           @Override
           public void onStopTrackingTouch(SeekBar arg0) { 
          
}
        });

效果:

3.星级评分条(RatingBar)功能用法

       星级条与拖动条有相同父类AbsSeekBar,很相近。

       为让程序响应星级评分条的改变,程序可以考虑为它绑定一个onRatingChanged监听器。

    实例:

界面布局RatingBar代码段

   

 <RatingBar
        android:id="@+id/rating"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:numStars="5"
        android:max="255"
        android:progress="255"
        android:stepSize="0.5"
        />

主程序为RatingBar绑定事件监听器

rating.setOnRatingBarChangeListener(new OnRatingBarChangeListener()
        {
 
           @Override
           public void onRatingChanged(RatingBarratingBar, float rating,
                  boolean fromUser) {
              // 动态改变图片透明度,其中255是星级评分条最大值
              //5个星星就是代表最大值255
              image.setAlpha((int) (rating * 255) / 5);
           }
           
        });

效果:

PS:程序报错“不能引用另一方法中定义的内部类中非终态变量 image”

原因:因为内部类本身是方法内的临时变量,只存在于方法内。

       所以需将image改为“final image”或在方法外定义。

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
实现圆弧进度条的自定义ProgressBar,可以使用Canvas和Paint来绘制。 首先,创建一个自定义的ProgressBar类,继承自ProgressBar类,并实现构造方法和onDraw方法: ``` public class CircleProgressBar extends ProgressBar { private Paint paint; // 画笔 private int roundColor; // 圆环颜色 private int progressColor; // 进度条颜色 private int textColor; // 文字颜色 private float textSize; // 文字大小 private float roundWidth; // 圆环宽度 private int max; // 最大进度 private boolean textIsDisplayable; // 是否显示进度文字 private int style; // 进度条样式 public static final int STROKE = 0; public static final int FILL = 1; public CircleProgressBar(Context context) { this(context, null); } public CircleProgressBar(Context context, AttributeSet attrs) { this(context, attrs, 0); } public CircleProgressBar(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); // 获取自定义属性的值 TypedArray mTypedArray = context.obtainStyledAttributes(attrs, R.styleable.CircleProgressBar); roundColor = mTypedArray.getColor(R.styleable.CircleProgressBar_roundColor, Color.RED); progressColor = mTypedArray.getColor(R.styleable.CircleProgressBar_progressColor, Color.GREEN); textColor = mTypedArray.getColor(R.styleable.CircleProgressBar_textColor, Color.GREEN); textSize = mTypedArray.getDimension(R.styleable.CircleProgressBar_textSize, 15); roundWidth = mTypedArray.getDimension(R.styleable.CircleProgressBar_roundWidth, 5); max = mTypedArray.getInteger(R.styleable.CircleProgressBar_max, 100); textIsDisplayable = mTypedArray.getBoolean(R.styleable.CircleProgressBar_textIsDisplayable, true); style = mTypedArray.getInt(R.styleable.CircleProgressBar_style, 0); mTypedArray.recycle(); // 初始化画笔 paint = new Paint(); } @Override protected synchronized void onDraw(Canvas canvas) { super.onDraw(canvas); // 获取圆心坐标和半径 int centerX = getWidth() / 2; int centerY = getHeight() / 2; int radius = (int) (centerX - roundWidth / 2); // 绘制圆环 paint.setColor(roundColor); paint.setStyle(Paint.Style.STROKE); paint.setStrokeWidth(roundWidth); paint.setAntiAlias(true); canvas.drawCircle(centerX, centerY, radius, paint); // 绘制进度条 paint.setStrokeWidth(roundWidth); paint.setColor(progressColor); RectF oval = new RectF(centerX - radius, centerY - radius, centerX + radius, centerY + radius); switch (style) { case STROKE: paint.setStyle(Paint.Style.STROKE); canvas.drawArc(oval, 0, 360 * getProgress() / getMax(), false, paint); break; case FILL: paint.setStyle(Paint.Style.FILL_AND_STROKE); if (getProgress() != 0) canvas.drawArc(oval, 0, 360 * getProgress() / getMax(), true, paint); break; } // 绘制文字 paint.setStrokeWidth(0); paint.setColor(textColor); paint.setTextSize(textSize); paint.setTypeface(Typeface.DEFAULT_BOLD); int percent = (int) (((float) getProgress() / (float) getMax()) * 100); if (textIsDisplayable && percent >= 0) { String text = percent + "%"; float textWidth = paint.measureText(text); canvas.drawText(text, centerX - textWidth / 2, centerY + textSize / 2, paint); } } } ``` 在这个类中,我们定义了几个自定义属性,包括圆环颜色、进度条颜色、文字颜色、文字大小、圆环宽度、最大进度、是否显示进度文字、进度条样式等。在构造方法中,我们获取了这些属性的值,并初始化了画笔。在onDraw方法中,我们首先获取了圆心坐标和半径,然后使用画笔绘制了圆环和进度条,最后绘制了进度文字。 接下来,在布局文件中使用这个自定义ProgressBar: ``` <com.example.circleprogressbar.CircleProgressBar android:id="@+id/circle_progressbar" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerInParent="true" app:roundColor="#cccccc" app:roundWidth="5dp" app:progressColor="#FF4081" app:textColor="#FF4081" app:textSize="20sp" app:textIsDisplayable="true" app:style="STROKE" /> ``` 最后,在Java代码中设置进度值即可: ``` CircleProgressBar circleProgressBar = findViewById(R.id.circle_progressbar); circleProgressBar.setProgress(50); // 设置进度为50% ``` 这样就完成了自定义的圆弧进度条的实现。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值