侧滑菜单的两种实现

  1. 使用DrawerLayout,灵活度比较高。
  2. 使用DrawerLayout+NavigationView,这是谷歌对Material Design的一种标准化。

使用DrawerLayout实现侧滑

首先,我们需要一个布局:

<?xml version="1.0" encoding="utf-8"?>                                                                                            


这个布局侧滑菜单包括了菜单部分以及内容部分,用DrawerLayout来包裹起来。其中,菜单部分的根布局需要添加android:layout_gravity="start",如果是右滑的话,改为end即可。这样就可以完成了一个基本的侧滑效果。

DrawerLayout的实现其实是通过ViewDragHelper来实现的,DrawerLayout构造函数的相关代码如下:

public DrawerLayout(Context context, AttributeSet attrs, int defStyle) {    super(context, attrs, defStyle);    mLeftCallback = new ViewDragCallback(Gravity.LEFT);    mRightCallback = new ViewDragCallback(Gravity.RIGHT);    mLeftDragger = ViewDragHelper.create(this, TOUCH_SLOP_SENSITIVITY, mLeftCallback);    mLeftDragger.setEdgeTrackingEnabled(ViewDragHelper.EDGE_LEFT);    mLeftDragger.setMinVelocity(minVel);    mLeftCallback.setDragger(mLeftDragger);}

利用DrawerLayout的监听实现一些效果

例如,我们可以实现侧滑的时候,Toolbar左上角的按钮实时变化,我们可以添加一个监听ActionBarDrawerToggle:

toolbar = (Toolbar) findViewById(R.id.toolbar);drawer = (DrawerLayout) findViewById(R.id.drawer);ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(this, drawer, toolbar, R.string.drawer_open, R.string.drawer_close);toggle.syncState();drawer.addDrawerListener(toggle);

下面我们分析一下实现原理:

其中,ActionBarDrawerToggle实现了DrawerLayout.DrawerListener。并且在滑动的过程中不断 刷新左上角的Drawerable:

@Overridepublic void onDrawerSlide(View drawerView, float slideOffset) {    setPosition(Math.min(1f, Math.max(0, slideOffset)));}
setPosition的实现如下:

private void setPosition(float position) {    if (position == 1f) {        mSlider.setVerticalMirror(true);    } else if (position == 0f) {        mSlider.setVerticalMirror(false);    }    mSlider.setProgress(position);}

其实就是在滑动的过程中不断改变mSlider(一个自定义Drawerable对象)的Progress,从而不断刷新状态。

因此,我们可以做一些自定义的特效,例如侧滑的时候缩放、平移:

drawer.addDrawerListener(new DrawerLayout.DrawerListener() {    @Override    public void onDrawerStateChanged(int newState) {        // 状态发生改变    }    @Override    public void onDrawerSlide(View drawerView, float slideOffset) {        // 滑动的过程当中不断地回调 slideOffset:0~1        View content = drawer.getChildAt(0);        float scale = 1 - slideOffset;//1~0        float leftScale = (float) (1 - 0.3 * scale);        float rightScale = (float) (0.7f + 0.3 * scale);//0.7~1        drawerView.setScaleX(leftScale);//1~0.7        drawerView.setScaleY(leftScale);//1~0.7        content.setScaleX(rightScale);        content.setScaleY(rightScale);        content.setTranslationX(drawerView.getMeasuredWidth() * (1 - scale));//0~width    }    @Override    public void onDrawerOpened(View drawerView) {        // 打开    }    @Override    public void onDrawerClosed(View drawerView) {        // 关闭    }});

使用DrawerLayout+NavigationView实现侧滑

同样道理,我们需要一个布局,同样的,用DrawerLayout进行包裹内容以及菜单,其中菜单是一个NavigationView,可以指定头部以及菜单部分,并且提供一些属性的设置。(可以看出来,使用NavigationView的灵活度比较差,如果项目是直接使用这种模板的话,可以直接使用,不然的话我们还是使用一般的方式去实现)

                

这里我们指定了头部如下:

<?xml version="1.0" encoding="utf-8"?>        

菜单部分如下(menu文件夹下建立),其中菜单可以嵌套:

<?xml version="1.0" encoding="utf-8"?>                                                            

到现在为止,就可以实现侧滑了,最后我们添加上对应的点击事件,然后关闭菜单:

nav_view = (NavigationView) findViewById(R.id.nav_view);drawer = (DrawerLayout) findViewById(R.id.drawer);nav_view.setNavigationItemSelectedListener(new NavigationView.OnNavigationItemSelectedListener() {    @Override    public boolean onNavigationItemSelected(@NonNull MenuItem item) {        Toast.makeText(NavigationViewActivity.this, item.getTitle(), Toast.LENGTH_SHORT).show();        drawer.closeDrawer(nav_view);        return false;    }});nav_view.getHeaderView(0).findViewById(R.id.iv_icon).setOnClickListener(new View.OnClickListener() {    @Override    public void onClick(View v) {        Toast.makeText(NavigationViewActivity.this, "点击了头部的图标", Toast.LENGTH_SHORT).show();        drawer.closeDrawer(nav_view);    }});


更多相关文章

  1. android EditText长按屏蔽ActionMode context菜单但保留选择工具
  2. android横竖屏切换和布局的问题
  3. Android UI开发篇之 ViewPager+九宫格布局 实现左右滑动
  4. Android 布局方式学习
  5. android线性布局布局的layout_weight
  6. Android顶部菜单栏,返回按钮、标题布局、右上角菜单

随机推荐

  1. Android React Native使用原生模块
  2. Android连载之:第三章第二节:Android用户界
  3. Android高仿QQ下拉刷新
  4. android关于第3方包的问题
  5. 源码解析Android中View的layout布局过程
  6. ubuntu下整合eclipse和javah生成jni头文
  7. Android释放内存
  8. Android(安卓)使WebView支持HTML5 Video(
  9. Android 开发 UI 规则
  10. Android之自定义五子棋View