安卓日记————自定义View(1)

来源:互联网 发布:程序员好学吗 编辑:程序博客网 时间:2024/06/16 04:05

以下大部分分内容出自http://blog.csdn.net/lmj623565791/article/details/24500107
有一些是自己修改的,代码后面也有一些自己理解的注释,希望可以帮助到大家。
跟着鸿洋大大的博客做了一个会动的圆环,发现还是蛮简单的,顺便还可以把绘图所需的东西巩固了一下,效果如下
这里写图片描述
还是我们自定View的那几个步骤:
1、自定义View的属性
2、在View的构造方法中获得我们自定义的属性
[ 3、重写onMesure ]

4、重写onDraw

1、自定义属性(在values包下新建一个attr.xml):

<?xml version="1.0" encoding="utf-8"?>  <resources>      <attr name="firstColor" format="color" />      <attr name="secondColor" format="color" />      <attr name="circleWidth" format="dimension" />      <attr name="speed" format="integer" />      <declare-styleable name="CustomProgressBar">          <attr name="firstColor" />          <attr name="secondColor" />          <attr name="circleWidth" />          <attr name="speed" />      </declare-styleable>  </resources>  

2、新建一个类继承自View,分别重写要1,2,3个参数的构造方法,通常是前三个,前两个通常是固定写法,第三个才是重点,写定义一些等一下要用的属性

/**     * 第一圈的颜色     */    private int mFirstColor;    /**     * 第二圈的颜色     */    private int mSecondColor;    /**     * 圈的宽度     */    private int mCircleWidth;    /**     * 画笔属性     */    private Paint mPaint;    /**     * 当前进度     */    private int mProgress;    /**     * 速度     */    private int mSpeed;    /**     * 是否应该开始下一圈,调换颜色     */    private boolean isNext = false;    //下面是前两个构造方法    public CustomProgressBar(Context context) {        this(context,null);    }    public CustomProgressBar(Context context, AttributeSet attrs) {        this(context,attrs,0);    }

3、在View的第三个构造方法中获得我们自定义的属性

/**     * 必要的初始化,获得一些自定义的值     *     * @param context     * @param attrs     * @param defStyle     */    public CustomProgressBar(Context context, AttributeSet attrs, int defStyle)    {        super(context, attrs, defStyle);        TypedArray a = context.getTheme().obtainStyledAttributes(attrs, R.styleable.CustomProgressBar, defStyle, 0);//将获取的属性转化为我们最先设好的属性        int n = a.getIndexCount();        for (int i = 0; i < n; i++)        {            int attr = a.getIndex(i);            switch (attr)            {                case R.styleable.CustomProgressBar_firstColor:                    mFirstColor = a.getColor(attr, Color.GREEN);//默认绿色                    break;                case R.styleable.CustomProgressBar_secondColor:                    mSecondColor = a.getColor(attr, Color.RED);//默认红色                    break;                case R.styleable.CustomProgressBar_circleWidth:                    mCircleWidth = a.getDimensionPixelSize(attr, (int) TypedValue.applyDimension(                            TypedValue.COMPLEX_UNIT_PX, 20, getResources().getDisplayMetrics()));//默认为20                    break;                case R.styleable.CustomProgressBar_speed:                    mSpeed = a.getInt(attr, 20);// 默认20                    break;            }        }        a.recycle();        mPaint = new Paint();        // 绘图线程        new Thread()        {            public void run()            {                while (true)                {                    mProgress++;                    //每到一圈归0,firstcolor和secondcolor调换                    if (mProgress == 360)                    {                        mProgress = 0;                        if (!isNext)                            isNext = true;                        else                            isNext = false;                    }                    postInvalidate();//界面刷新,重新执行ondraw                    try                    {                        Thread.sleep(mSpeed);                    } catch (InterruptedException e)                    {                        e.printStackTrace();                    }                }            };        }.start();    }

4、直接重写onDraw,这不需要重写onMeasure

 @Override    protected void onDraw(Canvas canvas) {        int center=getWidth()/2;//获取中心点到左边的距离        int radius=center-mCircleWidth/2;//半径是指圆环带中点到中心距离        mPaint.setStrokeWidth(mCircleWidth);//圆环宽度        mPaint.setAntiAlias(true);//消除锯齿        mPaint.setStyle(Paint.Style.STROKE);//空心        RectF oval=new RectF(center-radius,center-radius,center+radius,center+radius);//分别传入左上右下距离左边和上边的距离(左右距离左边,上下距离上边)        if (!isNext){            mPaint.setColor(mFirstColor);            canvas.drawCircle(center,center,radius,mPaint);//画那个不动圆环            mPaint.setColor(mSecondColor);            canvas.drawArc(oval,-90,mProgress,false,mPaint);//-90使每次都在正上方开始,Arc指那段会动的弧形        }else {            mPaint.setColor(mSecondColor);            canvas.drawCircle(center,center,radius,mPaint);            mPaint.setColor(mFirstColor);            canvas.drawArc(oval,-90,mProgress,false,mPaint);        }    }

5、在layout里使用

<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    xmlns:tools="http://schemas.android.com/tools"    android:layout_width="match_parent"    android:layout_height="match_parent"    android:orientation="vertical"    xmlns:app="http://schemas.android.com/apk/res-auto"    android:paddingBottom="@dimen/activity_vertical_margin"    android:paddingLeft="@dimen/activity_horizontal_margin"    android:paddingRight="@dimen/activity_horizontal_margin"    android:paddingTop="@dimen/activity_vertical_margin"    tools:context="com.jkgeekjack.customview3.MainActivity">    <com.jkgeekjack.customview3.CustomProgressBar        android:layout_width="100dp"        android:layout_height="100dp"        app:firstColor="#D4F668"        app:secondColor="#2F9DD2"        app:circleWidth="15dp"        app:speed="20"/>    <com.jkgeekjack.customview3.CustomProgressBar        android:layout_width="100dp"        android:layout_height="100dp"        app:firstColor="#16A3FA"        app:secondColor="#D20F02"        app:circleWidth="24dp"        app:speed="10"/></LinearLayout>

layout的代码不能完全照搬,因为有些命名与你的不同,请根据自己的情况,自己重写写那个自定义控件,然后属性的话,设好基本的witdth和heigth之后呢,输入firstcolor编译器就会提示你导入,你导入完就可以为该控件设置属性了

就这么简单就把一个自定义view写好了,是不是很简单呢
源码地址源码点击下载
这是鸿洋大大写的,注释会有所不同,如有不明白,请对照本博客

0 0