美文网首页
自定义view---水波纹

自定义view---水波纹

作者: 免费的午餐 | 来源:发表于2019-06-19 12:40 被阅读0次
    Ripple2.gif
    package com.wgp.customview;
    
    
    import android.content.Context;
    import android.graphics.Canvas;
    import android.graphics.Color;
    import android.graphics.Paint;
    import android.os.Handler;
    import android.os.Message;
    import android.util.AttributeSet;
    import android.util.Log;
    import android.view.MotionEvent;
    import android.view.View;
    
    import androidx.annotation.Nullable;
    
    import java.util.ArrayList;
    import java.util.List;
    
    
    /**
     * 自定义view
     * 水波纹
     *
     * 思路:
     * 1.先可以画出一个
     * 2.把每个点定义一个进行封装,半径、圆心坐标、画笔
     * 3.定义集合,把每个点对象进行存放,for循环改变每个对象的属性值(半径、透明度等)
     * 4.改变完后,通知onDraw()方法,绘制集合里所有的信息,就是我们看到的效果了
     */
    public class RippleView extends View {
    
        private int[] colors = new int[]{Color.RED, Color.BLUE, Color.YELLOW, Color.GREEN};
    
        //存放所有在屏幕上触发的点
        private List<Ripple> rippleList = new ArrayList<>();
    
        private float DISTANCE = 10;//两个点距离要大于10个像素,防止太密集
    
    
        public RippleView(Context context, @Nullable AttributeSet attrs) {
            super(context, attrs);
        }
    
    
        //测量view的大小
        @Override
        protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
            super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        }
    
        //布局view在父类中的位置
        @Override
        protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
            super.onLayout(changed, left, top, right, bottom);
        }
    
        /**
         * 绘制内容
         *
         * @param canvas
         */
        @Override
        protected void onDraw(Canvas canvas) {
            super.onDraw(canvas);
            for (int i = 0; i < rippleList.size(); i++) {
                Ripple ripple = rippleList.get(i);
                canvas.drawCircle(ripple.cx, ripple.cy, ripple.radius, ripple.paint);
            }
    
        }
    
        @Override
        public boolean onTouchEvent(MotionEvent event) {
            switch (event.getAction()) {
                case MotionEvent.ACTION_DOWN://按下获得圆心坐标
                case MotionEvent.ACTION_MOVE:
    
                    Ripple ripple;
                    if (rippleList.size() == 0) {//第一次点击
                        ripple = new Ripple();
                        ripple.cx = event.getX();
                        ripple.cy = event.getY();
    
                        initPaint(ripple);
    
                        rippleList.add(ripple);
                        handler.sendEmptyMessage(0);
                    } else {
                        Ripple prRipple = rippleList.get(rippleList.size() - 1);
    
                        //做个判断 如果是屏幕上移动的产生的点,密度比较大,这里判断每个点距离大于10个像素的才加入集合
                        if (event.getAction() == MotionEvent.ACTION_MOVE) {
                            if (Math.abs(prRipple.cx - event.getX()) > DISTANCE || Math.abs(prRipple.cy - event.getY()) > DISTANCE) {
                                ripple = new Ripple();
                                ripple.cx = event.getX();
                                ripple.cy = event.getY();
                                initPaint(ripple);
                                rippleList.add(ripple);
                            }
                        }
                        ripple = new Ripple();
                        ripple.cx = event.getX();
                        ripple.cy = event.getY();
                        initPaint(ripple);
                        rippleList.add(ripple);
    
                    }
    
                    break;
            }
    
            return true;
        }
    
        private void initPaint(Ripple ripple) {
            ripple.paint = new Paint();
            ripple.paint.setColor(colors[(int) (Math.random() * colors.length)]);
            ripple.paint.setAntiAlias(true);
            ripple.paint.setStyle(Paint.Style.STROKE);
        }
    
    
        Handler handler = new Handler(new Handler.Callback() {
            @Override
            public boolean handleMessage(Message msg) {
                //循环所有的圆心,并改变属性值,圆的透明度为小于10的时候,移除该圆对象。
                for (int i = 0; i < rippleList.size(); i++) {
                    Ripple ripple = rippleList.get(i);
    
                    ripple.radius += 20;
                    ripple.alpha -= 10;
                    ripple.paint.setStrokeWidth(ripple.radius / 3);
                    ripple.paint.setAlpha(ripple.alpha);
    
                    if (ripple.alpha <= 10) {
                        rippleList.remove(ripple);
                    }
                }
    
                //使当前试图无效,会重新调用onDraw()绘制试图
                invalidate();
    
                if (rippleList.size() != 0) {
                    handler.sendMessageDelayed(Message.obtain(), 50);
                }
                return false;
            }
        });
    
    
    }
    
    //圆环
    class Ripple {
        float cx;//圆心x坐标
        float cy;//圆心y坐标
        float radius = 0;//半径
    
        int alpha = 255;//透明度
        Paint paint;
    }
    
    
    
    
    

    相关文章

      网友评论

          本文标题:自定义view---水波纹

          本文链接:https://www.haomeiwen.com/subject/rjwhqctx.html