SwitchButton可以点击的时候切换状态,类似CheckBox
在拖动的时候,也可以根据拖动的距离判断是否切换状态,类似ToggleButton
因此要区别出单击事件和拖动事件
实现效果如图所示:
自定义的SwitchButton如下:
public class SwitchButton extends View implements View.OnTouchListener { private Bitmap bg_on, bg_off, slipper_btn; /** * 按下时的x和当前的x */ private float downX, nowX; /** * 记录用户是否在滑动 */ private boolean onSlip = false; /** * 当前的状态 */ private boolean nowStatus = false; /** * 监听接口 */ private OnChangedListener listener; /** * 一个滑动的距离临界值,判断是滑动还是点击 * getScaledTouchSlop(): * Distance in pixels a touch can wander before we think the user is scrolling * */ private int mTouchSlop=new ViewConfiguration().getScaledTouchSlop(); public SwitchButton(Context context) { super(context); init(); } public SwitchButton(Context context, AttributeSet attrs) { super(context, attrs); init(); } public void init(){ //载入图片资源 bg_on = BitmapFactory.decodeResource(getResources(), R.mipmap.switch_on_on); bg_off = BitmapFactory.decodeResource(getResources(), R.mipmap.switch_off_off); slipper_btn = BitmapFactory.decodeResource(getResources(), R.mipmap.switch_ball_ball); setOnTouchListener(this); } protected void onDraw(Canvas canvas) { super.onDraw(canvas); Matrix matrix = new Matrix(); Paint paint = new Paint(); float x = 0; //根据nowX设置背景,开或者关状态 if (nowX < (bg_on.getWidth()/2)){ canvas.drawBitmap(bg_off, matrix, paint);//画出关闭时的背景 }else{ canvas.drawBitmap(bg_on, matrix, paint);//画出打开时的背景 } if (onSlip) {//是否是在滑动状态, if(nowX >= bg_on.getWidth())//是否划出指定范围,不能让滑块跑到外头,必须做这个判断 x = bg_on.getWidth() - slipper_btn.getWidth()/2;//减去滑块1/2的长度 else x = nowX - slipper_btn.getWidth()/2; }else { if(nowStatus){//根据当前的状态设置滑块的x值 x = bg_on.getWidth() - slipper_btn.getWidth(); }else{ x = 0; } } //对滑块滑动进行异常处理,不能让滑块出界 if (x < 0 ){ x = 0; } else if(x > bg_on.getWidth() - slipper_btn.getWidth()){ x = bg_on.getWidth() - slipper_btn.getWidth(); } //画出滑块 canvas.drawBitmap(slipper_btn, x, 0, paint); } @Override public boolean onTouch(View v, MotionEvent event) { switch(event.getAction()){ case MotionEvent.ACTION_DOWN:{ if (event.getX() > bg_off.getWidth() || event.getY() > bg_off.getHeight()){ return false; }else{ onSlip = true; downX = event.getX(); nowX = downX; } break; } case MotionEvent.ACTION_MOVE:{ nowX = event.getX(); break; } case MotionEvent.ACTION_UP:{ DebugLog.e("mTouchSlop:"+mTouchSlop); onSlip = false; nowX = event.getX(); float float_distance=nowX - downX; int int_disatnce=(int)float_distance; DebugLog.e("int_disatnce:"+int_disatnce); /** * 滑动距离太短,认定是点击事件 */ if(Math.abs(int_disatnce)<mTouchSlop){ if(this.isChecked()){ this.setChecked(false); nowX = 0; }else{ this.setChecked(true); nowX = bg_on.getWidth() - slipper_btn.getWidth(); } }else{ /** * 滑动距离足够,认为是滑动事件 */ if(event.getX() >= (bg_on.getWidth()/2)){ nowStatus = true; nowX = bg_on.getWidth() - slipper_btn.getWidth(); }else{ nowStatus = false; nowX = 0; } } if(listener != null){ listener.OnChanged(SwitchButton.this, nowStatus); } break; } } //刷新界面 invalidate(); return true; } /** * 为WiperSwitch设置一个监听,供外部调用的方法 * @param listener */ public void setOnChangedListener(OnChangedListener listener){ this.listener = listener; } /** * 设置滑动开关的初始状态,供外部调用 * @param checked */ public void setChecked(boolean checked){ if(checked){ nowX = bg_off.getWidth(); }else{ nowX = 0; } nowStatus = checked; } public boolean isChecked() { return nowStatus; } /** * 回调接口 * */ public interface OnChangedListener { public void OnChanged(SwitchButton wiperSwitch, boolean checkState); } }
布局文件中使用:
<com.uestcneon.chuji.changjianglife.share.SwitchButton android:id="@+id/user_privacy_state" android:layout_width="wrap_content" android:layout_height="20dp" android:layout_marginLeft="30dp" />
控件用到的3个资源图片:
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持小牛知识库。
本文向大家介绍Android仿IOS自定义AlertDialog提示框,包括了Android仿IOS自定义AlertDialog提示框的使用技巧和注意事项,需要的朋友参考一下 本文介绍的仿IOS对话框的实现,先来看一下效果图 具体代码如下: 布局文件view_alertdialog.xml alertdialog_left_selector.xml alertdialog_right_select
我想自定义滑块显示的数据。例如,与其显示一个数字,不如说是“前缀”数字“后缀”,而且这个值应该始终可见。 在类VSlider我找到了方法。我怀疑这是配置滑块显示的值的地方。我尝试用相同的包结构在我自己的项目中复制这个类,我还重新编译了小部件集,但是视图中没有显示这些更改。我刚开始为Vaadin创建客户端代码,所以可能有一些我不理解的地方。 问题: 你对我如何实现我的目标有什么建议吗? 您知道为什么
本文向大家介绍Android自定义view仿IOS开关效果,包括了Android自定义view仿IOS开关效果的使用技巧和注意事项,需要的朋友参考一下 本文主要讲解如何在 Android 下实现高仿 iOS 的开关按钮,并非是在 Android 自带的 ToggleButton 上修改,而是使用 API 提供的 onDraw、onMeasure、Canvas 方法,纯手工绘制。基本原理就是在 Ca
Tabris.js控件由JavaScript API和原生平台的实现组成。本文档介绍Android平台上的自定义控件的原生实现。 为了实现自定义控件你需要本地构建。 在Cordova基础上构建 为了创建Tabris.js自定义控件,我们使用Cordova的构建系统。因此,我们创建一个与Tabris.js特定的API相关联的Cordova插件。Tabris.js自定义控件不需要接触任何Cordova
本文向大家介绍Android自定义星星可滑动评分控件,包括了Android自定义星星可滑动评分控件的使用技巧和注意事项,需要的朋友参考一下 本文实例为大家分享了Android自定义星星可滑动评分控件的具体方法,供大家参考,具体内容如下 此控件通过线性布局结合ImageView来实现。 具有展示分数,滑动评分功能,可设置0-10分,自行设置星星图片,是否可点击与滑动,星星间距。 效果如下: 需准备好
本文向大家介绍Android自定义控件之自定义组合控件(三),包括了Android自定义控件之自定义组合控件(三)的使用技巧和注意事项,需要的朋友参考一下 前言: 前两篇介绍了自定义控件的基础原理Android自定义控件基本原理详解(一)、Android自定义控件之自定义属性(二)。今天重点介绍一下如何通过自定义组合控件来提高布局的复用,降低开发成本,以及维护成本。 使用自定义组合控件的好处? 我