Android 滑动按钮,滑动锁的实现

本文介绍如何实现Android平台上的滑动按钮(SlidingButton),包括其作为滑动锁的用途。该组件已进行封装,可在XML布局中直接使用,并在Activity中重写ontouch方法进行交互判断。滑动逻辑自动适配,通过SlidingButton的handleActivityEvent方法处理滑动事件,根据滑动状态返回结果。示例代码展示了SlidingButton的实现细节,强调XML布局中需要使用FrameLayout作为最外层容器。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

滑动按钮,滑动锁的实现

先上图:

device-2012-05-29-141259

大概就是这种效果,你可以用于滑动解锁,也可以当做个性化的Button来用

这个我已经进行了封装,可以直接在xml中进行编写,然后在activity中重写ontouch方法进行button的判断即可,不用你再调整任何东西,

滑动什么的都是自动适配的

 

我把这种Button命名为SlidingButton,先看一下代码吧,都是非常简单易用的:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
package com.test.slidingbutton;
  
import android.content.Context;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.view.animation.AccelerateInterpolator;
import android.view.animation.Animation;
import android.view.animation.Interpolator;
import android.view.animation.TranslateAnimation;
import android.view.animation.Animation.AnimationListener;
import android.widget.Button;
import android.widget.FrameLayout;
import android.widget.LinearLayout;
  
public class SlidingButton extends Button {
  
     public SlidingButton(Context context, AttributeSet attrs, int defStyle) {
         super (context, attrs, defStyle);
     }
  
     public SlidingButton(Context context) {
         super (context);
     }
  
     private boolean isMe = false ;
  
     public boolean isMe() {
         return isMe;
     }
  
     public void setMe( boolean isMe) {
         this .isMe = isMe;
     }
  
     public SlidingButton(Context context, AttributeSet attrs) {
         super (context, attrs);
     }
  
     @Override
     public boolean onTouchEvent(MotionEvent event) {
         if (event.getAction() == MotionEvent.ACTION_DOWN) {
             isMe = true ;
         } else if (event.getAction() == MotionEvent.ACTION_UP) {
             isMe = false ;
         }
         return false ;
     }
  
     public boolean handleActivityEvent(MotionEvent activityEvent) {
         boolean result = false ;
         if (isMe()) {
             if (activityEvent.getAction() == MotionEvent.ACTION_UP) {
//              Log.v("yupeng", "frame left" + ((FrameLayout)this.getParent().getParent()).getLeft());
//              Log.v("yupeng", "my left" + this.getLeft());
//              Log.v("yupeng", "touch " + this.getLeft());
                  
                 if ( this .getLeft() + this .getWidth()/ 2 > ((FrameLayout) this .getParent().getParent()).getWidth() - this .getWidth()){
                     //用户完成了选择动作
                     Log.v( "yupeng" , "sliding true" );
                     LinearLayout.LayoutParams lp = (LinearLayout.LayoutParams) this .getLayoutParams();
                     lp.leftMargin = 0 ;
                     this .setLayoutParams(lp);
                     this .setMe( false );
                     result = true ;
                 } else {
                     TranslateAnimation trans =
                               new TranslateAnimation(
                                       Animation.ABSOLUTE, 0
                                       Animation.ABSOLUTE,- this .getLeft(), Animation.RELATIVE_TO_SELF, 0 ,
                                       Animation.RELATIVE_TO_SELF, 0 );
                      
//                  trans.setStartOffset(0);
                     trans.setDuration( 600 );
//                  trans.setFillAfter(true);
                     trans.setInterpolator( new AccelerateInterpolator());
                     trans.setInterpolator( new Interpolator() {
                          
                         @Override
                         public float getInterpolation( float input) {
                             // TODO Auto-generated method stub
                             return 0 ;
                         }
                     });
                     trans.setAnimationListener( new SlidingAnimationListener( this ));
                     startAnimation(trans);
                 }
             } else {
                 // 还在拖动
                 LinearLayout.LayoutParams lp = (LinearLayout.LayoutParams) getLayoutParams();
//              Log.v("yupeng", "yu" + lp.leftMargin);
                 lp.leftMargin = ( int ) (activityEvent.getX() - ((FrameLayout) this .getParent().getParent()).getLeft()) - this .getWidth()/ 2 ;
                 if (lp.leftMargin > 0 && lp.leftMargin < ((FrameLayout) this .getParent().getParent()).getWidth() - this .getWidth()) {
                     setLayoutParams(lp);
                      
                 }
             }
         }
         return result;
     }
      
     private static class SlidingAnimationListener implements AnimationListener {
  
         private SlidingButton but;
  
         public SlidingAnimationListener(SlidingButton button) {
             this .but = button;
         }
  
         @Override
         public void onAnimationEnd(Animation animation) {
             rePosition();
             but.setMe( false );
             but.clearAnimation();
         }
  
         private void rePosition() {
             LinearLayout.LayoutParams lp = (LinearLayout.LayoutParams) but
                     .getLayoutParams();
             lp.leftMargin = 0 ;
             but.setLayoutParams(lp);
              
         }
  
         @Override
         public void onAnimationRepeat(Animation animation) {
             // TODO Auto-generated method stub
  
         }
  
         @Override
         public void onAnimationStart(Animation animation) {
             // TODO Auto-generated method stub
  
         }
  
     }
      
}

SlidingButton是集成了Button,重写onTouchEvent方法,但是这里的ontouchEvent里只是判断是否touch了自己,如果是

则把自己的boolean isMe这个变量置为true,然后在activity中执行SlidingButton的handleActivityEvent方法,handleActivityEvent方法

来判断是否滑动,以及是否滑动到了进度条的末端,如果是则返回Boolean告诉调用者结果,如果没有,则触发动画滑回去

?
1
2
3
4
5
lp.leftMargin = ( int ) (activityEvent.getX() - ((FrameLayout) this .getParent().getParent()).getLeft()) - this .getWidth()/ 2 ;
             if (lp.leftMargin > 0 && lp.leftMargin < ((FrameLayout) this .getParent().getParent()).getWidth() - this .getWidth()) {
                 setLayoutParams(lp);
                  
             }

 

再看Activity的代码:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
package com.test.slidingbutton;
  
import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.FrameLayout;
import android.widget.LinearLayout;
import android.widget.Toast;
  
public class SlidingButtonActivity extends Activity {
      
     private SlidingButton mSlidingButton;
      
     @Override
     public void onCreate(Bundle savedInstanceState) {
         super .onCreate(savedInstanceState);
         setContentView(R.layout.main);
          
         mSlidingButton = (SlidingButton) this .findViewById(R.id.mainview_answer_1_button);
          
     }
      
     @Override
     public boolean onTouchEvent(MotionEvent event) {
         if (mSlidingButton.handleActivityEvent(event)) {
             Toast.makeText(SlidingButtonActivity. this , "touch" , 1 ).show();
         }
          
         return super .onTouchEvent(event);
     }
      
}

这就不用解释了吧?要是看不懂你就放弃吧…

需要注意的是xml文件:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
<FrameLayout
         android:layout_width= "250dip"
         android:layout_height= "60dip"
         android:layout_gravity= "center"
          >
          
         <TextView
             android:id= "@+id/mainview_answer_1"
             android:layout_width= "fill_parent"
             android:layout_height= "fill_parent"
             android:background= "@drawable/w_bg1"
             android:gravity= "center"
             android:paddingLeft= "35dip"
             android:text= "滑动按钮测试"
             android:textColor= "#FFFFFF"
             android:textSize= "18sp" />
         <!-- 此处,滑动按钮的父亲组件不能为FrameLayout -->
  
         <LinearLayout
             android:layout_width= "fill_parent"
             android:layout_height= "fill_parent" >
  
             <com.test.slidingbutton.SlidingButton
                 android:id= "@+id/mainview_answer_1_button"
                 android:layout_width= "wrap_content"
                 android:layout_height= "fill_parent"
                 android:background= "@drawable/bn_jt1"
                 android:gravity= "center" />
         </LinearLayout>
     </FrameLayout>

最外层一定要用FrameLayout,因为在SlidingButton中我一路找到它的父类并把它强转为了FrameLayout,你自己如果

愿意改也可以。

 

ok,就这样简单。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值