• Android快乐贪吃蛇游戏实战项目开发教程-04虚拟方向键(三)三角形按钮效果


    该系列教程概述与目录:http://www.cnblogs.com/chengyujia/p/5787111.html

    一、知识点讲解

    当我们点击系统自带的按钮时,按钮的外观会发生变化。上篇博文中我们画了一个三角形按钮,但点击还不能变色,下面我们就来实现点击变色功能。

    从知识体系上我们需要了解以下两个知识点

    • 1.如何知道手指点击了我们的控件?

    办法是重写View中的onTouchEvent方法。当手指触摸到我们的控件时,系统会通过该方法告诉我们。该方法还有一个类型为MotionEvent的参数,通过该参数我们就能知道当前触摸事件的具体类型,比如按下、移动、抬起等。
    我们可以让按钮在正常情况下显示一个较暗的颜色,按下时显示一个较亮的颜色,抬起后再恢复到较暗的颜色。这样就实现了点击变色的效果了。

    • 2.如何变色?

    View中提供了一个叫invalidate的方法,每次调用该方法,系统都会重新调用onDraw方法来重绘本控件。我们要做的就是在onDraw中判断当前的触摸动作,如果是按下就画一个高亮的三角形,没有触摸或按下抬起后就画一个较暗的三角形。

    了解了相关的知识点,下面我们就通过代码来实现。

    二、代码实现

    以下是当前DirectionKeys类的全部代码:

    package net.chengyujia.happysnake;
    
    import android.content.Context;
    import android.graphics.Canvas;
    import android.graphics.Paint;
    import android.graphics.Path;
    import android.util.AttributeSet;
    import android.view.MotionEvent;
    import android.view.View;
    
    /**
     * Created by ChengYuJia on 2016/8/19.
     * 屏幕上的虚拟方向键
     */
    public class DirectionKeys extends View {
        //左三角形按压时的颜色(较亮)
        private int leftPressedColor = 0xFFFF0000;
        //左三角形正常显示的颜色(较暗)
        private int leftNormalColor = 0xFFAA0000;
        //手触摸屏幕的动作,初始值用一个MotionEvent中没有用到的action值,比如-10,表示还没有任何触屏动作发生。
        private int action = -10;
        //画布的宽
        private int width;
        //画布的高
        private int height;
        //画左三角形的路径
        private Path pathLeft = new Path();
        //画笔
        private Paint paint = new Paint();
        //初始化方法是否执行过,确保初始化方法只执行一次。
        private boolean initDone = false;
    
        //只有一个参数的构造方法是我们在程序中通过“new”关键字创建实例时调用。
        public DirectionKeys(Context context) {
            super(context);
        }
    
        //有两个参数的构造方法是系统在XML布局文件中创建实例时调用。
        public DirectionKeys(Context context, AttributeSet attrs) {
            super(context, attrs);
        }
    
        //初始化方法
        private void init(Canvas canvas) {
            /*获取画布的长和宽*/
            width = canvas.getWidth();
            height = canvas.getHeight();
            /*
            (小提示:在计算机中一般都是将左上角作为坐标原点的)
            画布上四个顶点和中心点的坐标如下:
            左上点 0,0
            左下点 0,height
            右上点 width,0
            右下点 width,height
            中心点 width/2,height/2
            */
    
            /*设置左三角形的路径数据*/
            //从画布左上点开始
            pathLeft.moveTo(0, 0);
            //画直线到画布中心点
            pathLeft.lineTo(width / 2, height / 2);
            //再画直线到画布左下点
            pathLeft.lineTo(0, height);
            //自动闭合图形。从最后一个点(左下点)画直线到第一个点(左上点)。
            pathLeft.close();
        }
    
        /**
         * 通过重写父类的onDraw方法来绘制我们需要的图形
         * 该方法会在控件第一次显示时被系统调用,并在之后每次调用invalidate方法后被系统调用。
         *
         * @param canvas 这里的canvas是系统提供的一块矩形画布,我们要做的就是在这块画布上画我们想要的东西。
         */
        @Override
        protected void onDraw(Canvas canvas) {
            if (!initDone) {
                init(canvas);
                //确保初始化方法只执行一次
                initDone = true;
            }
    
            if (action == MotionEvent.ACTION_DOWN) {
                //手按压时高亮显示
                paint.setColor(leftPressedColor);
            } else {
                //没有按或按下抬起后显示较暗的颜色
                paint.setColor(leftNormalColor);
            }
            //画左三角形
            canvas.drawPath(pathLeft, paint);
        }
    
        /**
         * 如果手触摸到我们的控件,系统会通过该方法告诉我们
         *
         * @param event 系统给我们传递的触摸事件参数
         * @return 如果该触摸事件被我们处理了返回true,反之返回false。
         */
        @Override
        public boolean onTouchEvent(MotionEvent event) {
            action = event.getAction();
            //ACTION_DOWN表示手按到屏幕,ACTION_UP表示手从屏幕上抬起。我们只处理这两种动作。
            if (action == MotionEvent.ACTION_DOWN || action == MotionEvent.ACTION_UP) {
                //invalidate方法是告诉系统当前控件需要重绘,系统会再次调用onDraw方法来实现重绘。
                invalidate();
                return true;
            }
            return false;
        }
    }

    上面注释比较详细,主要就3个方法onDraw(绘图)、onTouchEvent(监听触摸事件)、invalidate(让系统调用onDraw方法实现重绘)。

    另外Path对象和Paint对象只要初始化一次就可以了,没必要每次onDraw的时候重新创建,提高程序性能。

    三、运行效果

    正常时显示暗色:

    按下时显示亮色:

    测试的时候会发现,点击非三角形区域也会变色,这因为我们还没有对点击的位置做判断,这个会在后面讲解。

    先到这里,下文继续。:)

  • 相关阅读:
    hdu 1698
    ACM起步要点总结(转哈工大)
    RANSAC
    Android 颜色渲染(十) ComposeShader组合渲染
    java过滤html标签函数
    Objective-C ,ios,iphone开发基础:picker控件详解与使用,(实现省市的二级联动)
    简单的三方登录SDK示例,Android Activity之间数据的传递
    搜索引擎日志分析
    继续过中等难度的题目
    包圈圈的题目
  • 原文地址:https://www.cnblogs.com/chengyujia/p/5792542.html
Copyright © 2020-2023  润新知