无需SherlockActionbar的SlidingMenu使用详解(一)——通过SlidingMenu设置容器并解决滑动卡顿的问题
想必很多人都听过这个开源框架,一年前真的是风靡一时。只是它的配置较为繁琐,还需要sherlockActionbar的支持,我这里下载了最新的开源库,并且在实际用套用了AppCompat的官方库,这样就完全不用sherlockActionbar的支持啦~
SlidingMenu官方下载地址:https://github.com/jfeinstein10/SlidingMenu
先大概讲解下配置:
下载库library,然后倒入到编译器中,并且添加依赖。这里可能会出现v4包不同的问题,总之换为最新的即可!
本篇讲解的是这个项目的简单配置,为以后做准备。咱们先来看看怎么来初步使用这个控件。
一、思路
1. 建立一个主界面的布局和菜单界面的布局
1.1 主界面
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/content_frame_id"
android:layout_width="match_parent"
android:layout_height="match_parent" />
1.2 菜单界面
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/menu_frame_id"
android:layout_width="match_parent"
android:layout_height="match_parent" />
可以看出都是超级简单的布局,这两个就是为以后放fragment做准备的容器。
二、在Actiivity或者主布局文件中设置SlidingMenu控件
这里我不推荐在xml文件中定义,原因是有bug。
2.1 在activity中初始化slidingmenu
private SlidingMenu menu;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// 设置正文容器
setContentView(R.layout.content_frame);
// 用代码来设置抽屉菜单
setSlidingMenu(); }
/**
* slidingMenu属性详解
*/
protected void setSlidingMenu() {
// configure the SlidingMenu
menu = new SlidingMenu(this);
menu.setMode(SlidingMenu.LEFT);
menu.setTouchModeAbove(SlidingMenu.TOUCHMODE_FULLSCREEN);
// 设置边缘阴影的宽度,通过dimens资源文件中的ID设置
menu.setShadowWidthRes(R.dimen.slidingmenu_shadow_width);
// 设置阴影的图片
menu.setShadowDrawable(R.drawable.shadow);
// 设置偏移量。说明:设置menu全部打开后,主界面剩余部分与屏幕边界的距离,值写在dimens里面:60dp
menu.setBehindOffsetRes(R.dimen.slidingmenu_offset);
// 设置是否淡入淡出
menu.setFadeEnabled(true);
// 设置淡入淡出的值,只在setFadeEnabled设置为true时有效
menu.setFadeDegree(0.5f);
// 全屏:TOUCHMODE_FULLSCREEN ;边缘:TOUCHMODE_MARGIN ;不打开:TOUCHMODE_NONE
menu.setTouchModeAbove(SlidingMenu.TOUCHMODE_FULLSCREEN);
// 设置滑动时actionbar是否跟着移动,SLIDING_WINDOW=跟着移动;SLIDING_CONTENT=不跟着移动
menu.attachToActivity(this, SlidingMenu.SLIDING_WINDOW);
// 设置滑动方向
menu.setMode(SlidingMenu.LEFT);
// 设置menu的背景
// menu.setBackgroundColor(getResources().getColor(android.R.color.background_dark));
// 设置菜单容器,注意这里只是容器,而不是菜单的界面
menu.setMenu(R.layout.menu_frame);
} public SlidingMenu getMySlidingMenu() {
return menu;
}
附上官网的example:
public class SlidingExample extends Activity { @Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setTitle(R.string.attach);
// set the content view
setContentView(R.layout.content);
// configure the SlidingMenu
SlidingMenu menu = new SlidingMenu(this);
menu.setMode(SlidingMenu.LEFT);
menu.setTouchModeAbove(SlidingMenu.TOUCHMODE_FULLSCREEN);
menu.setShadowWidthRes(R.dimen.shadow_width);
menu.setShadowDrawable(R.drawable.shadow);
menu.setBehindOffsetRes(R.dimen.slidingmenu_offset);
menu.setFadeDegree(0.35f);
menu.attachToActivity(this, SlidingMenu.SLIDING_CONTENT);
menu.setMenu(R.layout.menu);
} }
这里initSlidingMenu做的事情就是在主布局文件中建立一个SlidingMenu控件,并且这个控件通过setMenu方法扩展了一个Menu的容器。
这样你的布局文件中其实是有两个布局了,一个是通过setContentView(R.layout.content_frame);正常设置的布局,一个是通过slidingMenu.setMenu(R.layout.menu_frame);设置的菜单布局。这里的两个布局就是我们上面定义的布局。OK,现在我们拥有了两个布局容器,就可以往里面放Fragment了。
2.2 通过xml文件设置,虽然有bug,但我还是注释下。
官网:
If you decide to use SlidingMenu as a view, you can define it in your xml layouts like this:
<com.jeremyfeinstein.slidingmenu.lib.SlidingMenu
xmlns:sliding="http://schemas.android.com/apk/res-auto"
android:id="@+id/slidingmenulayout"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
sliding:viewAbove="@layout/YOUR_ABOVE_VIEW"
sliding:viewBehind="@layout/YOUR_BEHIND_BEHIND"
sliding:touchModeAbove="margin|fullscreen"
sliding:behindOffset="@dimen/YOUR_OFFSET"
sliding:behindWidth="@dimen/YOUR_WIDTH"
sliding:behindScrollScale="@dimen/YOUR_SCALE"
sliding:shadowDrawable="@drawable/YOUR_SHADOW"
sliding:shadowWidth="@dimen/YOUR_SHADOW_WIDTH"
sliding:fadeEnabled="true|false"
sliding:fadeDegree="float"
sliding:selectorEnabled="true|false"
sliding:selectorDrawable="@drawable/YOUR_SELECTOR"/>
NOTE : you cannot use both behindOffset and behindWidth. You will get an exception if you try.
viewAbove
- a reference to the layout that you want to use as the above view of the SlidingMenuviewBehind
- a reference to the layout that you want to use as the behind view of the SlidingMenutouchModeAbove
- an enum that designates what part of the screen is touchable when the above view is showing. Margin means only the left margin. Fullscreen means the entire screen. Default is margin.behindOffset
- a dimension representing the number of pixels that you want the above view to show when the behind view is showing. Default is 0.behindWidth
- a dimension representing the width of the behind view. Default is the width of the screen (equivalent to behindOffset = 0).behindScrollScale
- a float representing the relationship between the above view scrolling and the behind behind view scrolling. If set to 0.5f, the behind view will scroll 1px for every 2px that the above view scrolls. If set to 1.0f, the behind view will scroll 1px for every 1px that the above view scrolls. And if set to 0.0f, the behind view will never scroll; it will be static. This one is fun to play around with. Default is 0.25f.shadowDrawable
- a reference to a drawable to be used as a drop shadow from the above view onto the below view. Default is no shadow for now.shadowWidth
- a dimension representing the width of the shadow drawable. Default is 0.fadeEnabled
- a boolean representing whether or not the behind view should fade when the SlidingMenu is closing and "un-fade" when openingfadeDegree
- a float representing the "amount" of fade.1.0f
would mean fade all the way to black when the SlidingMenu is closed.0.0f
would mean do not fade at all.selectorEnabled
- a boolean representing whether or not a selector should be drawn on the left side of the above view showing a selected view on the behind view.selectorDrawable
- a reference to a drawable to be used as the selector NOTE : in order to have the selector drawn, you must call SlidingMenu.setSelectedView(View v) with the selected view. Note that this will most likely not work with items in a ListView because of the way that Android recycles item views.
我自己的注释:
activity_main.xml
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="${relativePackage}.${activityClass}" > <!--
mode:设置抽屉的打开方向,可以设置左右或同时left|right
behindOffset:设置打开抽屉后主界面距离屏幕的距离
fadeEnabled:允许淡入淡出
fadeDegree:淡入淡出的度数,这个在fadeEnable = true时有效
shadowDrawable:阴影的图片
shadowWidth:阴影宽度,这里要在dimen中设置
touchModeAbove:滑动打开抽屉的范围,可以选择:"fullscreen"=全屏,"margin"=边缘打开
viewAbove:在主页面上方的图片
viewBehind:在抽屉界面上方显示的图片。example:sliding:viewBehind="@layout/above_layout"
-->
<com.jeremyfeinstein.slidingmenu.lib.SlidingMenu
xmlns:sliding="http://schemas.android.com/apk/res-auto"
android:id="@+id/slidingmenulayout"
android:layout_width="match_parent"
android:layout_height="match_parent"
sliding:viewBehind="@layout/menu_frame"
sliding:viewAbove="@layout/content_frame"
sliding:mode="left"
sliding:behindOffset="@dimen/slidingmenu_offset"
sliding:fadeEnabled="true"
sliding:fadeDegree="0.5"
sliding:shadowDrawable="@drawable/shadow"
sliding:shadowWidth="@dimen/slidingmenu_shadow_width"
sliding:touchModeAbove="fullscreen"/> </RelativeLayout>
这里可以明确的看到在xml文件中有这个布局,并且这个布局通过viewBehind、viewAbove设置两个布局。其实就是一个主布局,主布局中include了两个其他的布局文件。
在Activity中获取到控件,就可以使用啦。注意:这里setContentView设置的布局是有slidingmenu的main_activity.xml
setContentView(R.layout.activity_main);
//在主界面的布局文件中设置slidingMenu
initSlidingMenu();
private void initSlidingMenu() {
menu = (SlidingMenu) findViewById(R.id.slidingmenulayout);
}
三、加载Fragment
现在我们可以往里面加载Fragment了,这里有用到个小技巧来存放当前的fragment对象
//通过数字来标识当前是哪个fragment,这样用于加载顶部的menu
public static int NOW_FRAGMENT_NO = 0; private Fragment nowFragment;
private SlidingMenu menu; @Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// 设置正文容器
setContentView(R.layout.content_frame);
// 设置左上角的按钮可以点击
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
getSupportActionBar().setBackgroundDrawable(getResources().getDrawable(R.drawable.bar_color));
// 用代码来设置抽屉菜单
setSlidingMenu();
/*setContentView(R.layout.activity_main);
//在主界面的布局文件中设置slidingMenu
initSlidingMenu();*/ if (savedInstanceState != null) {
nowFragment = getSupportFragmentManager().getFragment(
savedInstanceState, "mContent");
}
// 默认载入的fragment
else {
nowFragment = new FirstFragment();
}
initFragment();
}
@Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
getSupportFragmentManager().putFragment(outState, "mContent", nowFragment);
}
/**
* 填入主界面和菜单的Fragment
*/
private void initFragment() {
// 设置正文容器
getSupportFragmentManager().beginTransaction()
.replace(R.id.content_frame_id, nowFragment).commit(); // 设置菜单容器,这里用到了AppMenuFragment()
getSupportFragmentManager().beginTransaction()
.replace(R.id.menu_frame_id, new MenuFragment()).commit();
}
四、切换Fragment的方法
因为我们通常是随着menu菜单的点击来切换fragment的,所以切换的方法需要写到activity才能对slidingmenu进行完全的控制。此外,我们一般对Menu界面是不需要进行切换的,主要是切换正文的fragment。
/**
* 切换正文fragment
*
* @param fragment
*/
public void switchContent(Fragment fragment) {
// 切换回默认样式
getSupportActionBar().setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
// 切换界面前清空tab
getSupportActionBar().removeAllTabs();
// 切换回默认的触控范围(全屏滑动有效)
getMySlidingMenu().setTouchModeAbove(SlidingMenu.TOUCHMODE_FULLSCREEN); nowFragment = fragment;
getSupportFragmentManager().beginTransaction()
.replace(R.id.content_frame_id, fragment).commit();
/**
* 优化的代码,通过handler来避免滑动卡顿的情况。方法:延迟加载抽屉
* 如果不优化也可以运行,就是将下面的代码改为:menu.showContent();
*/
Handler h = new Handler();
h.postDelayed(new Runnable() {
public void run() {
menu.showContent();
}
}, 50);
}
下篇:http://www.cnblogs.com/tianzhijiexian/p/3994329.html
无需SherlockActionbar的SlidingMenu使用详解(一)——通过SlidingMenu设置容器并解决滑动卡顿的问题的更多相关文章
- 百度地图API详解之事件机制,function“闭包”解决for循环和监听器冲突的问题:
原文:百度地图API详解之事件机制,function"闭包"解决for循环和监听器冲突的问题: 百度地图API详解之事件机制 2011年07月26日 星期二 下午 04:06 和D ...
- 详解Mac睡眠模式设置
详解Mac睡眠模式设置 原文链接:http://www.insanelymac.com/forum/index.php?showtopic=281945 需要说明的是,首先这篇文章是针对已经能够成功睡 ...
- 详解Docker 端口映射与容器互联
详解Docker 端口映射与容器互联 1.端口映射实现访问容器 1.从外部访问容器应用 在启动容器的时候,如果不指定对应的参数,在容器外部是无法通过网络来访问容器内部的网络应用和服务的. 当容器中运行 ...
- 无需SherlockActionbar的SlidingMenu使用详解(二)——向Fragment中添加ViewPager和Tab
之前我们对大体框架有了一定的认识,现在我们来做Fragment界面,其实这里面和这个框架的关系就不大了,但因为有些同学对于在SlidingMenu中切换fragment还是有问题,所以我就在本篇进行详 ...
- 【Android】SlidingMenu属性详解(转)
原文:http://my.eoe.cn/1169143/archive/21892.html SlidingMenu简介:SlidingMenu的是一种比较新的设置界面或配置界面效果,在主界面左滑或者 ...
- 【Android】SlidingMenu属性详解
SlidingMenu 常用属性介绍: menu.setMode(SlidingMenu.LEFT);//设置左滑菜单menu.setTouchModeAbove(SlidingMenu.TOUCHM ...
- ViewPager 详解(五)-----使用Fragment实现ViewPager滑动
前言:前几篇文章讲解了ViewPager的普通实现方法,但Android官方最推荐的一种实现方法却是使用fragment,下面我们使用fragment来重新实现一下第一篇<ViewPager 详 ...
- V4L2 API详解 <二> Camera详细设置【转】
转自:http://blog.sina.com.cn/s/blog_602f87700101bf36.html 作者: Sam (甄峰) sam_code@hotmail.com Camera的 ...
- Android SlidingMenu 使用详解
转载请标明出处:http://blog.csdn.net/lmj623565791/article/details/36677279 很多APP都有侧滑菜单的功能,部分APP左右都是侧滑菜单~Slid ...
随机推荐
- spring-cloud-sleuth+zipkin追踪服务实现(四)
1.前言 在上一篇spring-cloud-sleuth+zipkin追踪服务实现(三)的处理实现后,很多朋友告诉我,在zipkin server的管理页面无法看到项目依赖关系. 当时也没有多想,以为 ...
- 为什么要做A.prototype.constructor=A这样的修正?
问题 虽然看过这篇博文JavaScript prototype之后对原型理解不再那么模糊了,但是依然还有很多理解不甚透彻的地方.比如,今天看到一个原型式继承的例子,又有些困惑,于是找了些帖子看看,有了 ...
- 【PAT】1051 Pop Sequence (25)(25 分)
Given a stack which can keep M numbers at most. Push N numbers in the order of 1, 2, 3, ..., N and p ...
- JS易错知识点
JAVASCRIPT易错知识点整理 前言 本文是学习JavaScript过程中收集与整理的一些易错知识点,将分别从变量作用域,类型比较,this指向,函数参数,闭包问题及对象拷贝与赋值这6个方面进行由 ...
- Codeforces 405E Graph Cutting
Graph Cutting 不会写.. dfs的过程中把回边丢到它的祖先中去, 回溯的时候两两配对.感觉好神奇啊. #include<bits/stdc++.h> #define LL l ...
- Divide by Zero 2018 and Codeforces Round #474 (Div. 1 + Div. 2, combined)
思路:把边看成点,然后每条边只能从下面的边转移过来,我们将边按照u为第一关键字,w为第二关键字排序,这样就能用线段树维护啦. #include<bits/stdc++.h> #define ...
- Python异常处理回顾与总结
1 引言 在我们调试程序时,经常不可避免地出现意料之外的情况,导致程序不得不停止运行,然后提示大堆提示信息,大多是这种情况都是由异常引起的.异常的出现一方面是因为写代码时粗心导致的语法错误,这种错误在 ...
- java中的二进制运算简单理解
package test9; public class StreamTest { public static void main(String[] args) { int a = 15;// 0b11 ...
- eclipse launching workspace太慢的解决方法
这几天eclipse调试Android项目的时候反应超慢,右下显示launching workspace就不怎么动了,今天终于卡的受不了了,在网上搜了写方法,设置了下总算好点了,现在把方法贴出来,跟大 ...
- 苹果Mac OS 显示隐藏文件
苹果Mac OS 操作系统下,隐藏文件默认为隐藏状态,隐藏文件是否显示有多种方法可以设置. 方法一: 打开终端,输入命令行 显示Mac隐藏文件的命令: defaults write com.apple ...