专栏首页Open软件开发小组一秒钟学会实现不规则图形响应点击事件

一秒钟学会实现不规则图形响应点击事件

背景

在日常的开发过程中,有时候会碰到形状不规则的图片(其实是看起来不规则),比如一个卡通人物、特殊的符号或者拟物化的一个东西,如下图这样。当然这些图片也是矩形的,只是人眼看不到的区域是透明的而已。

实现步骤

  • 1、自定义一个view,在view的onTouchEvent(MotionEvent event)方法中获取到手指触摸的点的坐标;
  • 2、获取这个view的bitmap,然后把触摸点对应的bitmap上的颜色值获取到;
  • 3、判断该点的颜色值是否为透明,如果透明,则让onTouchEvent返回false,view就不会响应此次触摸事件。

说白了就是让透明区域不响应触摸事件,所以只要在view的触摸事件里做处理就行了。我们知道,view里的onTouchEvent ( MotionEvent event ) 方法,该方法返回false时,表示当前view不消费此次触摸事件,会把消息传递给它的父控件。(view的消息分发机制:http://www.cnblogs.com/linjzong/p/4191891.html)。

具体代码

1、自定义控件的代码

public class IrregularView extends View {
   private Bitmap bitmap;   public IrregularView(Context context) {
       super(context);
   }   public IrregularView(Context context, AttributeSet attrs) {
       super(context, attrs);
   }   public IrregularView(Context context, AttributeSet attrs, int defStyle) {
       super(context, attrs, defStyle);
   }   @Override
   public boolean onTouchEvent(MotionEvent event) {
       // 点击了透明区域,则返回false
       return !isPointTransparent(event) && super.onTouchEvent(event);
   }   /**
    * 该点的颜色值是否为透明
    * @param event event
    * @return boolean
    */
   private boolean isPointTransparent(MotionEvent event) {
       int x = (int) event.getX();
       int y = (int) event.getY();       return getPointColor(x, y) == 0;
   }   /**
    * 获取bitmap上某点的颜色值
    */
   private int getPointColor(int x, int y) {
       if(bitmap == null) {
           bitmap = getBitmap();
       }       try {
           return bitmap.getPixel(x, y);
       } catch (Exception e) {
           return -1;
       }
   }   private Bitmap getBitmap() {
       setDrawingCacheEnabled(true);// View对象必须做如下设置后,才能获取其中的图像
       Bitmap bitmap = Bitmap.createBitmap(getDrawingCache());// 获取View中的图像
       setDrawingCacheEnabled(false);// 从View对象中获取图像后,调用setDrawingCacheEnabled(false)清空画图缓       return bitmap;
   }
}

2、XML布局文件 2、XML布局

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
   android:layout_width="match_parent"
   android:layout_height="match_parent"
   android:background="#C7EDCC">   <com.jiazy.irregularviewdemo.view.IrregularView
       android:id="@+id/view1"
       android:layout_width="200dp"
       android:layout_height="200dp"
       android:onClick="onClick"
       android:background="@drawable/img_1_selector" />   <com.jiazy.irregularviewdemo.view.IrregularView
       android:id="@+id/view2"
       android:layout_width="200dp"
       android:layout_height="200dp"
       android:layout_alignParentEnd="true"
       android:onClick="onClick"
       android:background="@drawable/img_2_selector" />   <com.jiazy.irregularviewdemo.view.IrregularView
       android:id="@+id/view3"
       android:layout_width="200dp"
       android:layout_height="200dp"
       android:layout_alignParentBottom="true"
       android:layout_centerHorizontal="true"
       android:onClick="onClick"
       android:background="@drawable/img_1_selector" />   <com.jiazy.irregularviewdemo.view.IrregularView
       android:id="@+id/view4"
       android:layout_width="200dp"
       android:layout_height="200dp"
       android:layout_alignParentBottom="true"
       android:layout_centerHorizontal="true"
       android:onClick="onClick"
       android:background="@drawable/img_2_selector" />
</RelativeLayout>

效果演示

拓展

上面我们用到了透明的颜色值:0,其实也可以用其他颜色来判断是否需要处理触摸事件。之前有一个需求,是做一个选择地区的图形控件,点击某个地区进行选择,这个时候我们就可以通过这种方法来实现。 图中每个地区是一种颜色值,把地区的颜色值和地区信息对应起来,就可以实现以下效果。

本文分享自微信公众号 - Open软件开发小组(open_dev),作者:安口Jar

原文出处及转载信息见文内详细说明,如有侵权,请联系 yunjia_community@tencent.com 删除。

原始发表时间:2019-05-24

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • Android程序猿怎么学H5

    本文适合有一定android基础想初步了解学习web前端开发的朋友。以下均为个人理解,很多可能不是百分百就是完全能类比过去,只是比较相似,希望能...

    open
  • [Android技术专题]应用开发进阶必经之路之性能优化(上)

    性能优化在一款产品的迭代过程中非常重要;程序实现了功能、还原产品原型只能保证程序能用,但如果要让用户更愿意使用,产品得好用。试想一下如果你开发的产品启动慢、页...

    open
  • 聊聊Android应用Preference组件那点事

    本文主要给大家讲述下本人使用Preference的经验和体会。为了使短信项目和系统之间的耦合度更低,使用简单,达到代码可读性更好,又要达到策划的需求,根据以上...

    open
  • Android开发之ListFragment结合LoaderManager加载数据

    之前实现过Android开发之ContentProvider结合LoaderManager加载数据,现在来实现用ListFragment加载 先看main....

    刘晓杰
  • 4-AIII--Service跨进程通信:aidl

    张风捷特烈
  • Android语音录制,语音发送

    这是一个录音的例子,可用于IM的语音发送,OA的语音留言等。 首先我们需要引入权限:

    饮水思源为名
  • android上拉下拉加载更多数据

    最近项目中用到了ListView的下拉刷新的功能,总结了一下前辈们的代码,单独抽取出来写了一个demo作为示例。 效果图 下拉刷新: ? 加载更多: ? Cu...

    xiangzhihong
  • 项目需求讨论-标题栏上的搜索功能

    今天讲的就是一个很简单的具体开始时候遇到的需求,在标题栏中实现搜索功能,而且美工要求需要实现下面GIF图的效果,我就实现了下,可能不是最好的,有哪里可以更方便请...

    青蛙要fly
  • 浅谈PopupWindow弹出菜单

    听着music睡
  • TimePicker控件、帧动画、补间动画

    1.TimePicker控件 最近感觉每个开发平台的控件基本都差不多,在Android中控件的事件和.net控件直接写事件有一定的区别,net事件可以直接界面进...

    水击三千

扫码关注云+社区

领取腾讯云代金券