欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

Android控件View打造完美的自定义侧滑菜单

程序员文章站 2023-12-17 12:26:34
一、概述   在app中,经常会出现侧滑菜单,侧滑滑出view等效果,虽然说android有很多第三方开源库,但是实际上咱们可以自己也写一个自定义的侧滑view控件,其实...

一、概述

  在app中,经常会出现侧滑菜单,侧滑滑出view等效果,虽然说android有很多第三方开源库,但是实际上咱们可以自己也写一个自定义的侧滑view控件,其实不难,主要涉及到以下几个要点:

1.对android中window类中的decorview有所了解

2.对scroller类实现平滑移动效果

3.自定义viewgroup的实现

首先来看看效果图吧:

Android控件View打造完美的自定义侧滑菜单

Android控件View打造完美的自定义侧滑菜单   Android控件View打造完美的自定义侧滑菜单  

  下面现在就来说说这里咱们实现侧滑view的基本思路吧,这里我采用的是自定义一个继承于relativelayout的控件叫做xcslideview类吧。

首先从布局文件中inflater出来一个menuview,然后通过addview的方法,将该侧滑view添加到自定义的控件view中怎么让xcslideview 这个侧滑view 隐藏到屏幕之外呢?很简单通过scrollto方法,移动一个屏幕宽度的距离即可,这里以左侧滑出为例吧,只需要这样 xcslideview.this.scrollto(mscreenwidth, 0);mscreenwidth是屏幕宽度。下面还要处理的就是底下的半透明黑色的蒙层效果,这个其实就是一个view,然后设置半透明效果。这个当然简单了,关键是咱们让他显示在咱们的自定义侧滑view的下面呢,这里咱们先给出decorview的简单分析,方便下面介绍添加半透明view蒙层下:

Android控件View打造完美的自定义侧滑菜单

下面是对上面这张图的解释:

1、decorview为整个window界面的最顶层view。

2、decorview只有一个子元素为linearlayout。代表整个window界面,包含通知栏,标题栏,内容显示栏三块区域。

3、linearlayout里有两个framelayout子元素。

  (20)为标题栏显示界面。只有一个textview显示应用的名称。也可以自定义标题栏,载入后的自定义标题栏view将加入framelayout中。

  (21)为内容栏显示界面。就是setcontentview()方法载入的布局界面,加入其中。 

有了上面的decorview知识背景,现在就来说说 怎么添加蒙层view和将自定义侧滑view添加到activity的decorview中,首先把蒙层view添加到

(31)customview中去,然后将自定义侧滑view添加到 (21)framelayout中去,至于为什么要这样,是因为考虑到自定义侧滑view不一定是宽度为屏幕宽度,所以才这么做,而且也方面处理有无标题栏,有无采用沉浸式状态栏设计等情况。

二、自定义侧滑view的实现

根据上面的概述,大家应该知道大概的思路了,下面我就给出自定义侧滑view类的核心代码:

1、自定义侧滑view用到的变量:

//侧滑方向-从哪侧滑出
 public static enum positon {
 left, right
 }
 private context mcontext;
 private activity mactivity;
 private scroller mscroller = null;
 //侧滑菜单布局view
 private view mmenuview;
 //底部蒙层view
 private view mmaskview;
 private int mmenuwidth = 0;
 //屏幕宽度
 private int mscreenwidth = 0;
 //是否在滑动中
 private boolean mismoving = false;
 //显示登录界面与否
 private boolean mshow = false;
 //滑动动画时间
 private int mduration = 600;
 //缺省侧滑方向为左
 private positon mpositon = positon.left;

2、初始化创建自定义侧滑view:

**
 * 创建侧滑菜单view
 */
 public static xcslideview create(activity activity) {
 xcslideview view = new xcslideview(activity);
 return view;
 }
 /**
 * 创建侧滑菜单view
 */
 public static xcslideview create(activity activity, positon positon) {
 xcslideview view = new xcslideview(activity);
 view.mpositon = positon;
 return view;
 }

3、创建半透明蒙层view,并添加到contentview中去

/**
 * 创建 蒙层view并添加到contentview中
 */
 private void attachtocontentview(activity activity, positon positon) {
 mpositon = positon;
 viewgroup contentframelayout = (viewgroup) activity.findviewbyid(android.r.id.content);
 viewgroup contentview = ((viewgroup) contentframelayout.getchildat(0));
 mmaskview = new view(activity);
 mmaskview.setbackgroundcolor(mcontext.getresources().getcolor(r.color.mask_color));
 contentview.addview(mmaskview, contentview.getlayoutparams());
 mmaskview.setvisibility(view.gone);
 mmaskview.setclickable(true);
 mmaskview.setonclicklistener(new onclicklistener() {
 @override
 public void onclick(view view) {
 if (isshow()) {
  dismiss();
 }
 }
 });
 }

4、设置侧滑菜单view,并添加到dectorview->linearlayout->内容显示区域view(framelayout)中

/**
 * 设置侧滑菜单view,并添加到dectorview->linearlayout->内容显示区域view中
 */
 public void setmenuview(activity activity, view view) {
 mactivity = activity;
 mmenuview = view;
 layoutparams params = new layoutparams(layoutparams.match_parent, layoutparams.match_parent);
 addview(mmenuview, params);
 mmenuview.post(new runnable() {
 @override
 public void run() {
 // todo auto-generated method stub
 mmenuwidth = mmenuview.getwidth();
 switch (mpositon) {
  case left:
  xcslideview.this.scrollto(mscreenwidth, 0);
  break;
  case right:
  xcslideview.this.scrollto(-mscreenwidth, 0);
  break;
 }

 }
 });
 viewgroup contentframelayout = (viewgroup) activity.findviewbyid(android.r.id.content);
 viewgroup contentview = contentframelayout;
 contentview.addview(this);
 framelayout.layoutparams layoutparams = (framelayout.layoutparams) this.getlayoutparams();
 switch (mpositon) {
 case left:
 layoutparams.gravity = gravity.left;
 layoutparams.leftmargin = 0;
 break;
 case right:
 layoutparams.gravity = gravity.right;
 layoutparams.rightmargin = 0;
 break;
 }
 textview titleframelayout = (textview) activity.findviewbyid(android.r.id.title);
 if( titleframelayout != null){
 layoutparams.topmargin = densityutil.getstatusbarheight(mcontext);
 }
 int flags = mactivity.getwindow().getattributes().flags;
 int flag = (flags & windowmanager.layoutparams.flag_translucent_status);
 if(flag == windowmanager.layoutparams.flag_translucent_status){
 //说明状态栏使用沉浸式
 layoutparams.topmargin = densityutil.getstatusbarheight(mcontext);
 }
 this.setlayoutparams(layoutparams);
 }

5、处理自定义侧滑view的侧滑滑动和隐藏效果:

/**
 * 显示侧滑菜单view
 */
 public void show(){
 if(isshow() && !mismoving)
 return;
 switch (mpositon) {
 case left:
 startscroll(mmenuwidth, -mmenuwidth, mduration);
 break;
 case right:
 startscroll(-mmenuwidth, mmenuwidth, mduration);
 break;
 }
 switchmaskview(true);
 mshow = true;
 }
 /**
 * 蒙层显示开关
 */
 private void switchmaskview(boolean bshow){
 if(bshow){
 mmaskview.setvisibility(view.visible);
 animation animation = new alphaanimation(0.0f, 1.0f);
 animation.setduration(mduration);
 mmaskview.startanimation(animation);
 }else{
 mmaskview.setvisibility(view.gone);
 }
 }
 /**
 * 关闭侧滑菜单view
 */
 public void dismiss() {
 // todo auto-generated method stub
 if(!isshow() && !mismoving)
 return;
 switch (mpositon) {
 case left:
 startscroll(xcslideview.this.getscrollx(), mmenuwidth, mduration);
 break;
 case right:
 startscroll(xcslideview.this.getscrollx(), -mmenuwidth, mduration);
 break;
 }
 switchmaskview(false);
 mshow = false;
 }
 public boolean isshow(){
 return mshow;
 }
 @override
 public void computescroll() {
 // todo auto-generated method stub
 if (mscroller.computescrolloffset()) {
 scrollto(mscroller.getcurrx(), mscroller.getcurry());
 // 更新界面
 postinvalidate();
 mismoving = true; 
 } else {
 mismoving = false;
 }
 super.computescroll();
 }
 /**
 * 拖动移动
 */
 public void startscroll(int startx, int dx,int duration){
 mismoving = true;
 mscroller.startscroll(startx,0,dx,0,duration);
 invalidate();
 }


三、如何使用该自定义侧滑view控件

使用起来,比较简单,通过create方法创建一个侧滑view,然后通过setmenuview方法设置一个侧滑view进去,有需要设置宽度的话, 通过setmenuwidth方法来设置即可,最后用show()方法滑出来就可以啦,使用起来是不是很方便?

private xcslideview mslideviewleft;
//屏幕宽度
private int mscreenwidth = 0;
view menuviewleft = layoutinflater.from(mcontext).inflate(r.layout.layout_slideview,null);
mslideviewleft = xcslideview.create(this, xcslideview.positon.left);
mslideviewleft.setmenuview(mainactivity.this, menuviewleft);
mslideviewleft.setmenuwidth(mscreenwidth * 7 / 9);
button left = (button)findviewbyid(r.id.btn_left);
 left.setonclicklistener(new view.onclicklistener() {

 @override
 public void onclick(view v) {
 // todo auto-generated method stub
 if (!mslideviewleft.isshow())
  mslideviewleft.show();
 }
 });

四、源码下载

下载:侧滑菜单

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。

上一篇:

下一篇: