开源侧滑菜单控件SlidingMenu浅析
引子
最近一直在思考Acitity、Fragment、layouts在开发时到底如何抉择?
自然,Activity+layouts对于一个andorid App是不可缺少的,然而为何google又要提出碎片呢?
貌似用Activity+layouts已然能开发所有的应用了吧,API指出Fragment可以将多个Activity合并,然而我们用layouts难道不能做到吗?
将多个Activity视为多个layouts不也可实现吗?然而,我现在的所理解的Fragment更像一个Activity与Layouts的中间层、一个框架,它有自己的生命周期,可能使用起来比自己写的layouts要更完善,但是本人依旧无法体会到引入Fragment带来哪些实际的好处,所以开发中并未太多的使用他,最直接的理解是Fragment是因Pad而引入的可能是为Pad更易开发UI而新增的框架或组件吧。
正文
貌似引子和正文没多大的联系,但由于看SlidingMenu的同时一直在思考这个问题,姑且记在这里吧。
放个某个example的效果图:
下载地址:https://github.com/jfeinstein10/SlidingMenu
写到此处其实我的博客已经写完了99%了,下面就是本人的赘述了:
1、我理解的SlidingMenu:它是一个包含CustomViewAbove和CustomViewBehind的一个layouts,最突出的特点是,它是通过scrollTo来定位
这两个子布局的。当然这样的描述有些片面,其里面的逻辑真心看起来挺死脑细胞的~~。
2、浅析运用SlidingMenu:
主要指com.slidingmenu.lib.app.SlidingFragmentActivity:
此类中主要是使用com.slidingmenu.lib.app.SlidingActivityHelper来实现对SlidingMenu的呈现。
依次在onCreate()中实例化SlidingMenu、setBehindContentView()、setContentView(),貌似这一句挺废话的,但是我也没法描述了
主要实现逻辑是SlidingFragmentActivity类中的onPostCreate()的此段代码:
/**
* Further SlidingMenu initialization. Should be called within the activitiy's onPostCreate()
*
* @param savedInstanceState the saved instance state (unused)
*/
public void onPostCreate(Bundle savedInstanceState) {
if (mViewBehind == null || mViewAbove == null) {
throw new IllegalStateException("Both setBehindContentView must be called " +
"in onCreate in addition to setContentView.");
}
mOnPostCreateCalled = true;
// get the window background
TypedArray a = mActivity.getTheme().obtainStyledAttributes(new int\[\] {android.R.attr.windowBackground});
int background = a.getResourceId(0, 0);
a.recycle();
if (mEnableSlide) {
// move everything into the SlidingMenu
ViewGroup decor = (ViewGroup) mActivity.getWindow().getDecorView();
ViewGroup decorChild = (ViewGroup) decor.getChildAt(0);
// save ActionBar themes that have transparent assets
decorChild.setBackgroundResource(background);
decor.removeView(decorChild);
mSlidingMenu.setContent(decorChild);
decor.addView(mSlidingMenu);
} else {
// take the above view out of
ViewGroup parent = (ViewGroup) mViewAbove.getParent();
if (parent != null) {
parent.removeView(mViewAbove);
}
// save people from having transparent backgrounds
if (mViewAbove.getBackground() == null) {
mViewAbove.setBackgroundResource(background);
}
mSlidingMenu.setContent(mViewAbove);
parent.addView(mSlidingMenu, new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));
}
this.showContent();
}
明显看出不论mEnableSlide是false,还是true,最终都将SlidingMenu的实例充当为了仅此于DecorView的存在,属于最大的外层View了,这中布局的思路和上面提到的scrollTo来定位布局真心膜拜了。
将SlidingMenu视为最外层View后,就不难理解CustomViewAbove和CustomViewBehind的onInterceptTouchEvent和onTouchEvent的一些逻辑了