SlidingMenu实现
来源:互联网 发布:红米清空用户数据99 编辑:程序博客网 时间:2024/05/21 23:42
SlidingMenu
原理
SlidingMenu
无非就是一个包含三个View
的控件,左边View、中间View(默认时全屏)、右边View,默认的情况下中间View
会把两边的View
覆盖住,在手指滑动的时候,会根据手指的滑动方向以及滑动距离去移动中间的那个View
,从而能让两边View
完全可见。
在定义该View的时候,首先会想到继承RelativeLayout
,能简单的实现这种左、中、右三个View的布局。
继承RelativeLayout
- public class SlidingMenu extends RelativeLayout {
- public SlidingMenu(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- init(context);
- }
- public SlidingMenu(Context context, AttributeSet attrs) {
- super(context, attrs);
- init(context);
- }
- public SlidingMenu(Context context) {
- super(context);
- init(context);
- }
- private void init(Context context) {
- mContext = context;
- mScroller = new Scroller(context);
- mWindowWidth = getWindowWidth(context);
- }
- }
具体的三个View需要暴露给外界调用,所以我们要提供一个setView()的方法。
- public void setView(View leftView, View rightView, View centerView,
- int leftViewWidth, int rightViewWidth) {
- //添加左边View
- RelativeLayout.LayoutParams leftParams = new LayoutParams(
- (int) convertDpToPixel(leftViewWidth, mContext),
- LayoutParams.MATCH_PARENT);
- leftParams.addRule(RelativeLayout.ALIGN_PARENT_LEFT);
- addView(leftView, leftParams);
- //右边的View
- RelativeLayout.LayoutParams rightParams = new LayoutParams(
- (int) convertDpToPixel(rightViewWidth, mContext),
- LayoutParams.MATCH_PARENT);
- rightParams.addRule(RelativeLayout.ALIGN_PARENT_RIGHT);
- addView(rightView, rightParams);
- //添加中间的View
- RelativeLayout.LayoutParams centerParams = new LayoutParams(
- LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
- addView(centerView, centerParams);
- mLeftView = leftView;
- mRightView = rightView;
- mCenterView = centerView;
- }
外界使用
SlidingMenu
类的时候需要首先调用该方法去设置相应的View,一旦调用该方法后,我们就将布局设置完了,下一步就是对touch
事件进行处理,然后去移动中间的View。处理Touch事件 在手指按下的时候,我们去控制两边View的显示与隐藏
- public boolean onInterceptTouchEvent(MotionEvent ev) {
- int x = (int) ev.getRawX();
- int y = (int) ev.getRawY();
- int action = ev.getAction();
- switch (action) {
- case MotionEvent.ACTION_DOWN:
- mLastPostionX = x;
- mLastPostionY = y;
- //通过变量记录当前可以显示左边的View还是可以显示右边的View
- if (mCanLeftViewShow) {
- //如果当前,中间的View往右滑,那么这时候左边的View就要能显示了
- mLeftView.setVisibility(View.VISIBLE);
- mRightView.setVisibility(View.GONE);
- } else if (mCanRightViewShow) {
- mLeftView.setVisibility(View.GONE);
- mRightView.setVisibility(View.VISIBLE);
- }
- break;
- case MotionEvent.ACTION_MOVE:
- break;
- case MotionEvent.ACTION_UP:
- break;
- default:
- break;
- }
- return false;
- }
在onTouch()
中,我们去获取手指移动的距离
- public boolean onTouchEvent(MotionEvent event) {
- int x = (int) event.getRawX();
- int y = (int) event.getRawY();
- int action = event.getAction();
- switch (action) {
- case MotionEvent.ACTION_DOWN:
- mLastPostionX = x;
- mLastPostionY = y;
- if (!mScroller.isFinished()) {
- mScroller.abortAnimation();
- }
- break;
- case MotionEvent.ACTION_MOVE:
- int distance = x - mLastPostionX;
- int targetPositon = mCenterView.getScrollX() - distance;
- mLastPostionX = x;
- if (mCanLeftViewShow) {
- if (targetPositon > 0) {
- targetPositon = 0;
- }
- if (targetPositon < -mLeftViewWidth) {
- targetPositon = -mLeftViewWidth;
- }
- }
- if (mCanRightViewShow) {
- if (targetPositon < 0) {
- targetPositon = 0;
- }
- if (targetPositon > mRightViewWidth) {
- targetPositon = mRightViewWidth;
- }
- }
- mClicked = false;
- //让中间的View随着手指的移动而移动
- mCenterView.scrollTo(targetPositon, 0);
- break;
- case MotionEvent.ACTION_UP:
- //你手指移动后抬起的时候需要注意,如果现在左边的View已经超过一半可见了,这时候就算你抬起手指了,SlidingMenu也要滑动到右边让左边View完全可见。当然还有就是你滑动的飞快,然后突然抬起了手指,这时候就要进行速率的计算了,我们先不说速率
- int dx = 0;
- if (mCanLeftViewShow) {
- if (mCenterView.getScrollX() <= -mLeftViewWidth / 2) {
- //已经超过左边View的一般了,应该让中间View继续移动,移动到左边View完全可见
- dx = -mLeftViewWidth - mCenterView.getScrollX();
- } else {
- // 滚回原来的位置
- dx = -mCenterView.getScrollX();
- resumeLeftViewClickState();
- }
- } else if (mCanRightViewShow) {
- if (mCenterView.getScrollX() >= mRightViewWidth / 2) {
- dx = mRightViewWidth - mCenterView.getScrollX();
- } else {
- dx = -mCenterView.getScrollX();
- resumeRightViewClickState();
- }
- }
- //手指抬起后,要让中间View有过程的滑过去,所以要用到Scroller类
- smoothScrollTo(dx);
- break;
- default:
- break;
- }
- return true;
- }
Scroller
的实现
- private void smoothScrollTo(int distance) {
- mScroller.startScroll(mCenterView.getScrollX(), 0, distance, 0,
- sDuration);
- invalidate();
- }
- @Override
- public void computeScroll() {
- if (mScroller.computeScrollOffset()) {
- mCenterView.scrollTo(mScroller.getCurrX(), mScroller.getCurrY());
- postInvalidate();
- }
- }
- 到这里SlidingMenu的大体实现已经完成了剩下的就是对速率的计算,已经添加显示左边与显示右边的View的按钮。当左边View完全显示的时候,点击中间View可见部分时需要让中间View全屏。至于这些细节的东西就不再仔细说了,大家自己看源码吧。
源码:点击打开链接
0 0
- SlidingMenu实现
- 仿SlidingMenu的实现原理,例SlidingMenu
- Android SlidingMenu 的实现
- Android SlidingMenu 布局实现
- 实现简单slidingmenu
- SlidingMenu+ActionBar+Fragment实现
- slidingmenu简单实现
- SlidingMenu-布局实现
- 自定义View实现SlidingMenu
- SlidingMenu实现侧滑
- SlidingMenu实现透明状态栏
- slidingmenu实现左侧滑
- slidingmenu实现代码
- Android学习之SlidingMenu实现
- SlidingMenu动画效果的实现
- SlidingMenu 实现抽屉样式菜单
- android 滑动菜单SlidingMenu实现
- 奇葩实现SlidingMenu,不得不转
- mediainfo
- qt零碎知识点记录
- 在Ubuntu上安装Qt5.2.0
- meld--Visual diff and merge tool for the GNOME Desktop
- 拓胜第一天,下
- SlidingMenu实现
- mono touch中处理json字符串
- 电阻电容
- 在.Net框架中 C# 实现多线程的同步方法详解
- oc学习之旅:NSArray分割,排序,Block
- C#连接Sqlite
- JNI学习积累之三 - 操作JNI函数以及复杂对象传递
- jQuery.post()函数
- mongoDB非正常关闭后无法启动问题