Android自定义组件——四个方向滑动的菜单实现

今天无意中实现了一个四个方向滑动的菜单,感觉挺好玩,滑动起来很顺手,既然已经做出来了就贴出来让大家也玩弄一下。

一、效果演示

(说明:目前没有安装Android模拟器,制作的动态图片太卡了,就贴一下静态图片吧,实际效果可以下载源代码查看)

(向上滑动)

(向下滑动)

(向左滑动)

(向右滑动)

二、实现过程介绍

1、放置5个View (分别是上下左右中)

 

  1. @Override  
  2. protected void onLayout(boolean changed, int l, int t, int r, int b) {  
  3.     mTopView.layout(0, -mViewHeight, mViewWidth, 0);  
  4.     mBottomView.layout(0, mViewHeight, mViewWidth, 2 * mViewHeight);  
  5.     mCenterView.layout(0, 0, mViewWidth, mViewHeight);  
  6.     mLeftView.layout(-mViewWidth, 0, 0, mViewHeight);  
  7.     mRightView.layout(mViewWidth, 0, 2 * mViewWidth, mViewHeight);  
  8. }  

 

转载请说明出处:http://blog.csdn.net/dawanganban

2、通过onTouchEvent事件来判断移动方向

 

  1. private float mDownY;  
  2. private float mDownX;  
  3. @Override  
  4. public boolean onTouchEvent(MotionEvent event) {  
  5.     int disY;  
  6.     int disX;  
  7.     float eventY = event.getY();  
  8.     float eventX = event.getX();  
  9.     switch (event.getAction()) {  
  10.     case MotionEvent.ACTION_DOWN:  
  11.         mDownY = eventY;      
  12.         mDownX = eventX;  
  13.         break;  
  14.     case MotionEvent.ACTION_UP:  
  15.         disY = (int)(eventY - mDownY);  
  16.         disX = (int)(eventX - mDownX);  
  17.         if(Math.abs(disY) > Math.abs(disX)){  
  18.             if(Math.abs(disY) > MIN_VIEW_HEIGHT / 2){  
  19.                 if(disY > 0){ //向下滑动  
  20.                     Log.d(TAG, "TO_BOTTOM");  
  21.                     changeToBottom();  
  22.                 }else{        //向上滑动  
  23.                     Log.d(TAG, "TO_TOP");  
  24.                     changeToTop();  
  25.                 }  
  26.             }  
  27.         }else{  
  28.             if(Math.abs(disX) > MIN_VIEW_WIDTH / 2){  
  29.                 if(disX > 0){ //向右滑动  
  30.                     Log.d(TAG, "TO_RIGHT");  
  31.                     changeToRight();  
  32.                 }else{        //向左滑动  
  33.                     Log.d(TAG, "TO_LEFT");  
  34.                     changeToLeft();  
  35.                 }  
  36.             }  
  37.         }  
  38.         break;  
  39.   
  40.     default:  
  41.         break;  
  42.     }  
  43.     return true;  
  44. }  

3、通过computerScroll()方法实现平滑移动

 

 

  1. @Override  
  2. public void computeScroll() {  
  3.     super.computeScroll();  
  4.     if(mScroller.computeScrollOffset()){  
  5.         scrollTo(mScroller.getCurrX(), mScroller.getCurrY());  
  6.         postInvalidate();  
  7.     }  
  8. }  

4、判断临界条件(否则会一直向一个方向滑动)

 

 

  1. int[] location = new int[2];  
  2. mCenterView.getLocationOnScreen(location);  
  3. if(location[1] >= mViewHeight - MIN_VIEW_HEIGHT * 2) return;  

例如上面代码就是判断向下滑动的临界条件,location[1]代表中间View的y坐标(相对于屏幕)。

 

 

三、整个View的源码

  1. package com.example.testmx4update;  
  2.   
  3. import android.content.Context;  
  4. import android.graphics.Color;  
  5. import android.util.AttributeSet;  
  6. import android.util.Log;  
  7. import android.view.MotionEvent;  
  8. import android.view.View;  
  9. import android.view.ViewGroup;  
  10. import android.widget.Scroller;  
  11.   
  12. /** 
  13.  * 自定义可以拖动的View 
  14.  * @author 阳光小强  http://blog.csdn.net/dawanganban 
  15.  * 
  16.  */  
  17. public class MyCanPullView extends ViewGroup{  
  18.       
  19.     private static final int MIN_VIEW_HEIGHT = 200;  
  20.     private static final int MIN_VIEW_WIDTH = 400;  
  21.   
  22.   
  23.     private static final String TAG = "TEST";  
  24.       
  25.       
  26.     private int mViewHeight;  
  27.     private int mViewWidth;  
  28.       
  29.     private View mTopView;  
  30.     private View mBottomView;  
  31.     private View mCenterView;  
  32.     private View mLeftView;  
  33.     private View mRightView;  
  34.       
  35.       
  36.       
  37.     private Scroller mScroller;  
  38.   
  39.     public MyCanPullView(Context context, AttributeSet attrs) {  
  40.         super(context, attrs);  
  41.           
  42.         initView(context);  
  43.           
  44.         mScroller = new Scroller(context);  
  45.     }  
  46.   
  47.     private void initView(Context context) {  
  48.         setTopView(context);  
  49.         setBottomView(context);  
  50.         setCenterView(context);  
  51.         setLeftView(context);  
  52.         setRightView(context);  
  53.     }  
  54.       
  55.       
  56.     private float mDownY;  
  57.     private float mDownX;  
  58.     @Override  
  59.     public boolean onTouchEvent(MotionEvent event) {  
  60.         int disY;  
  61.         int disX;  
  62.         float eventY = event.getY();  
  63.         float eventX = event.getX();  
  64.         switch (event.getAction()) {  
  65.         case MotionEvent.ACTION_DOWN:  
  66.             mDownY = eventY;      
  67.             mDownX = eventX;  
  68.             break;  
  69.         case MotionEvent.ACTION_UP:  
  70.             disY = (int)(eventY - mDownY);  
  71.             disX = (int)(eventX - mDownX);  
  72.             if(Math.abs(disY) > Math.abs(disX)){  
  73.                 if(Math.abs(disY) > MIN_VIEW_HEIGHT / 2){  
  74.                     if(disY > 0){ //向下滑动  
  75.                         Log.d(TAG, "TO_BOTTOM");  
  76.                         changeToBottom();  
  77.                     }else{        //向上滑动  
  78.                         Log.d(TAG, "TO_TOP");  
  79.                         changeToTop();  
  80.                     }  
  81.                 }  
  82.             }else{  
  83.                 if(Math.abs(disX) > MIN_VIEW_WIDTH / 2){  
  84.                     if(disX > 0){ //向右滑动  
  85.                         Log.d(TAG, "TO_RIGHT");  
  86.                         changeToRight();  
  87.                     }else{        //向左滑动  
  88.                         Log.d(TAG, "TO_LEFT");  
  89.                         changeToLeft();  
  90.                     }  
  91.                 }  
  92.             }  
  93.             break;  
  94.   
  95.         default:  
  96.             break;  
  97.         }  
  98.         return true;  
  99.     }  
  100.       
  101.     private void changeToBottom(){  
  102.         int[] location = new int[2];  
  103.         mCenterView.getLocationOnScreen(location);  
  104.         if(location[1] >= mViewHeight - MIN_VIEW_HEIGHT * 2) return;  
  105.         int dy = (int)(mViewHeight - MIN_VIEW_HEIGHT);  
  106.         mScroller.startScroll(0, getScrollY(), 0, -dy, 500);  
  107.         invalidate();  
  108.     }  
  109.       
  110.     private void changeToTop(){  
  111.         int[] location = new int[2];  
  112.         mTopView.getLocationOnScreen(location);  
  113.         if(location[1] <= -mViewHeight - MIN_VIEW_HEIGHT / 2) return;  
  114.         int dy = (int)(mViewHeight - MIN_VIEW_HEIGHT);  
  115.         mScroller.startScroll(0, getScrollY(), 0, dy, 500);  
  116.         invalidate();  
  117.     }  
  118.       
  119.     private void changeToRight(){  
  120.         int[] location = new int[2];  
  121.         mCenterView.getLocationOnScreen(location);  
  122.         if(location[0] >= mViewWidth - MIN_VIEW_WIDTH * 2) return;  
  123.         int dx = (int)(mViewWidth - MIN_VIEW_WIDTH);  
  124.         mScroller.startScroll(getScrollX(), 0, -dx, 0, 500);  
  125.         invalidate();  
  126.     }  
  127.       
  128.     private void changeToLeft(){  
  129.         Log.d(TAG, "TO_LEFT");  
  130.         int[] location = new int[2];  
  131.         mLeftView.getLocationOnScreen(location);  
  132.         if(location[0] <= -mViewWidth - MIN_VIEW_WIDTH / 2) return;  
  133.         int dx = (int)(mViewWidth - MIN_VIEW_WIDTH);  
  134.         mScroller.startScroll(getScrollX(), 0, dx, 0, 500);  
  135.         invalidate();  
  136.     }  
  137.       
  138.     @Override  
  139.     public void computeScroll() {  
  140.         super.computeScroll();  
  141.         if(mScroller.computeScrollOffset()){  
  142.             scrollTo(mScroller.getCurrX(), mScroller.getCurrY());  
  143.             postInvalidate();  
  144.         }  
  145.     }  
  146.   
  147.     @Override  
  148.     protected void onLayout(boolean changed, int l, int t, int r, int b) {  
  149.         mTopView.layout(0, -mViewHeight, mViewWidth, 0);  
  150.         mBottomView.layout(0, mViewHeight, mViewWidth, 2 * mViewHeight);  
  151.         mCenterView.layout(0, 0, mViewWidth, mViewHeight);  
  152.         mLeftView.layout(-mViewWidth, 0, 0, mViewHeight);  
  153.         mRightView.layout(mViewWidth, 0, 2 * mViewWidth, mViewHeight);  
  154.     }  
  155.   
  156.     @Override  
  157.     protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {  
  158.         super.onMeasure(widthMeasureSpec, heightMeasureSpec);  
  159.         //获取整个View的宽高  
  160.         mViewWidth = MeasureSpec.getSize(widthMeasureSpec);  
  161.         mViewHeight = MeasureSpec.getSize(heightMeasureSpec);  
  162.     }  
  163.       
  164.     private void setTopView(Context context){  
  165.         View topButton = new View(context);  
  166.         topButton.setBackgroundColor(Color.RED);  
  167.         mTopView = topButton;  
  168.         this.addView(mTopView);  
  169.     }  
  170.       
  171.     private void setBottomView(Context context){  
  172.         View bottomButton = new View(context);  
  173.         bottomButton.setBackgroundColor(Color.GREEN);  
  174.         mBottomView = bottomButton;  
  175.         this.addView(mBottomView);  
  176.     }  
  177.       
  178.     private void setCenterView(Context context){  
  179.         View centerButton = new View(context);  
  180.         centerButton.setBackgroundColor(Color.WHITE);  
  181.         mCenterView = centerButton;  
  182.         this.addView(mCenterView);  
  183.     }  
  184.       
  185.     private void setLeftView(Context context){  
  186.         View leftButton = new View(context);  
  187.         leftButton.setBackgroundColor(Color.BLUE);  
  188.         mLeftView = leftButton;  
  189.         this.addView(mLeftView);  
  190.     }  
  191.       
  192.     private void setRightView(Context context){  
  193.         View rightButton = new View(context);  
  194.         rightButton.setBackgroundColor(Color.YELLOW);  
  195.         mRightView = rightButton;  
  196.         this.addView(mRightView);  
  197.     }  
  198. }  

获取全部源代码,请加群在群共享中获取(142979499)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值