自定义控件探究

来源:互联网 发布:黑色四叶草 知乎 编辑:程序博客网 时间:2024/05/27 01:10

从今天开始每天会分享一些自定义控件编程相关内容。

自定义控件研发算是Android研发中的一颗明珠。每每Android推出漂亮功能的时候,都是某位代码工匠精心雕琢的硕果。研究他们的实现原理,相关技巧,有助于我们开发更好Android功能。常言道:熟读唐诗三百首,不会作诗也会吟。

好,今天我们先研究一个比较经典的,经常会碰到,但是又觉得实现起来有一定难度的“水波纹”效果。

核心类继承至View类

public class WaterBubbleView extends View {    /**     * 初始半径     */    private final int RADIUS = 40;    /**     * 初始透明度     */    private final int ALPHA = 255;    private Canvas canvas;    private Paint paint;    /**     * 颜色数组     */    private final int colors[] = new int[]{Color.RED, Color.BLUE,            Color.GREEN, Color.YELLOW, Color.BLACK, Color.CYAN, Color.GRAY,            Color.GRAY, Color.MAGENTA};    /**     * 圆心X坐标     */    private int cx;    /**     * 圆心Y坐标     */    private int cy;    /**     * 圆的半径     */    private int radius = RADIUS;    /**     * 运行状态     */    private boolean isRunning = false;    /**     * 透明度     */    private int alpha = ALPHA;    /**     * 实现动画效果     */    private Handler handler = new Handler(new Callback() {        @Override        public boolean handleMessage(Message msg) {            alpha -= 4;            paint.setAlpha(alpha);            radius += 15;            if (alpha <= 10) {                isRunning = false;                radius = RADIUS;                alpha = ALPHA;            }            invalidate();            return true;        }    });    public WaterBubbleView(Context context, AttributeSet attrs) {        super(context, attrs);        init();    }    private void init() {        canvas = new Canvas();        paint = new Paint();        paint.setAntiAlias(true);    }
    //这是第三步,在屏幕上画出视图,在此之前还有个第二步onLayout方法,用来决定视图绘制在屏幕的哪个部位,一般认为决定视图左上角和右下角的两个位置。    @Override    protected void onDraw(Canvas canvas) {        if (isRunning) {            System.out.println("isRun, draw");            canvas.drawCircle(cx, cy, radius, paint);            handler.sendEmptyMessageDelayed(0, 20);        } else {            System.out.println("noRun, change");            paint.setColor(colors[(int) (Math.random() * colors.length)]);        }    }
    //用来测量视图绘制在屏幕上的大小尺度,这是继承View的第一步    @Override    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {        super.onMeasure(widthMeasureSpec, heightMeasureSpec);    }    @Override    public boolean onTouchEvent(MotionEvent event) {        switch (event.getAction()) {            case MotionEvent.ACTION_DOWN:                //保证每次按下时绘图颜色重置                radius=40;                alpha=255;                if (!isRunning) {                    isRunning = true;                }                cx = (int) event.getX();                cy = (int) event.getY();                handler.sendEmptyMessage(0);                break;            case MotionEvent.ACTION_HOVER_MOVE:                isRunning = true;                break;            case MotionEvent.ACTION_UP:                isRunning = true;                break;        }        return super.onTouchEvent(event);    }}

引用方式:

<com.voyage.waterbubble.WaterBubbleView    android:layout_width="fill_parent"    android:layout_height="fill_parent" />
layout_height可以指定为固定高度,波纹会在视图中绘画。

特别说明:当alpha 的值为0时将停止循环绘制。

实现原理:init()  中初始化画布和画笔,

在onDraw()中首次画默认圆,发送handler消息,更新半径和透明图参数,启动   invalidate()  方法,再次绘画,如此循环。直到alpha值为o,停止绘画。 


效果图:

——————


0 0
原创粉丝点击