由浅入深学习自定义控件(6)- 超简捷的slidemenu实现

借鉴了鸿洋哥的博文中利用HorizontalScrollView实现的slidemenu滑动菜单,本文利用fragment做了进一步简化。

说下具体步骤:
1.首先是在onMeasre方法中量出每个子控件的宽度,并设置主页面的宽度为全屏。
2. 重写onTouchEvent方法,利用SrollView的方法很容易的控制视图的滑动。
3. 写出一个公共的SlideMenuActivity,负责设置菜单项对应的Fragment.
4. 在自己的Activity中直接继承SlideMenuActivity,并去设置具体Fragment。
5.专注于每个Frament的实现。
代码很简介,,直接贴出来。

public class MySlideMenu extends HorizontalScrollView {
 private LinearLayout llContainer;
 private ViewGroup leftMenu;
 private ViewGroup rightMenu;
 private ViewGroup content;
 private int mLeftMenuWidth;
 private int mRightMenuWidth;
 private int mScreenWidth;
 private boolean isLeft = false;
 private boolean isRight = false;
 public MySlideMenu(Context context) {
  super(context);
 }
 public MySlideMenu(Context context, AttributeSet attrs) {
  super(context, attrs);
  this.setHorizontalScrollBarEnabled(false); // 隐藏滚动条
  WindowManager wm = (WindowManager) getContext().getSystemService(
    Context.WINDOW_SERVICE);
  mScreenWidth = wm.getDefaultDisplay().getWidth();
 }
 @Override
 protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
  super.onMeasure(widthMeasureSpec, heightMeasureSpec);
  llContainer = (LinearLayout) this.getChildAt(0);
  leftMenu = (ViewGroup) llContainer.getChildAt(0);
  content = (ViewGroup) llContainer.getChildAt(1);
  rightMenu = (ViewGroup) llContainer.getChildAt(2);
  // 测量子控件的宽搞
  measureChildren(widthMeasureSpec, heightMeasureSpec);
  mLeftMenuWidth = leftMenu.getWidth();
  mRightMenuWidth = rightMenu.getWidth();
  content.getLayoutParams().width = mScreenWidth;
 }
 @Override
 protected void onLayout(boolean changed, int l, int t, int r, int b) {
  super.onLayout(changed, l, t, r, b);
  if (changed) {
   this.scrollTo(leftMenu.getWidth(), 0);
  }
 }
 @Override
 public boolean onTouchEvent(MotionEvent ev) {
  switch (ev.getAction()) {
  case MotionEvent.ACTION_UP:
   int scrollX = getScrollX();
   if (scrollX > mLeftMenuWidth + mRightMenuWidth / 2) {
    this.smoothScrollTo(mLeftMenuWidth + mRightMenuWidth, 0);
   } else if (scrollX > mLeftMenuWidth / 2) {
    this.smoothScrollTo(mLeftMenuWidth, 0);
   } else {
    this.smoothScrollTo(0, 0);
   }
   return true;
  }
  return super.onTouchEvent(ev);
 }
 public void openLeft() {
  if (isLeft) {
   return;
  }
  this.smoothScrollTo(0, 0);
  isLeft = true;
 }
 public void openRight() {
  if (isRight) {
   return;
  }
  this.smoothScrollTo(mLeftMenuWidth + mRightMenuWidth, 0);
  isRight = true;
 }
 public void resume() {
  this.smoothScrollTo(mLeftMenuWidth, 0);
  isLeft = false;
  isRight = false;

 下面是布局文件。-----

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:jw="http://schemas.android.com/apk/res/wei.jiang.selfview"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context="${relativePackage}.${activityClass}" >

    <wei.jiang.selfview.view.MySlideMenu
        android:id="@+id/mySlideMenu"
        android:layout_width="match_parent"
        android:layout_height="match_parent" >

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:orientation="horizontal" >

            <FrameLayout
                android:id="@+id/leftFrame"
                android:layout_width="wrap_content"
                android:layout_height="match_parent" >
            </FrameLayout>

            <FrameLayout
                android:id="@+id/contentFrame"
                android:layout_width="match_parent"
                android:layout_height="match_parent" >
            </FrameLayout>

            <FrameLayout
                android:id="@+id/rightFrame"
                android:layout_width="wrap_content"
                android:layout_height="match_parent" >
            </FrameLayout>
        </LinearLayout>
    </wei.jiang.selfview.view.MySlideMenu>

</RelativeLayout>


公用的MenuActivity ,
public abstract class MenuActivity extends FragmentActivity {
 private FragmentManager fm;
 private Fragment leftFragment;
 private Fragment rightFragment;
 private Fragment contentFragment;
 private MySlideMenu mySlideMenu;
 private boolean hasLeftMenu = false;
 private boolean hasRightMenu = false;
 @Override
 protected void onCreate(Bundle arg0) {
  super.onCreate(arg0);
  setContentView(R.layout.activity_slidemenu);
  mySlideMenu = (MySlideMenu) findViewById(R.id.mySlideMenu);
  // 子类设置菜单的回调
  initFragment();
  fm = getSupportFragmentManager();
  FragmentTransaction ft = fm.beginTransaction();
  if (leftFragment != null)
   ft.replace(R.id.leftFrame, leftFragment);
  if (contentFragment != null)
   ft.replace(R.id.contentFrame, contentFragment);
  if (rightFragment != null)
   ft.replace(R.id.rightFrame, rightFragment);
  ft.commit();
 }
 public void setLeftFragment(Fragment leftFragment) {
  this.leftFragment = leftFragment;
  hasLeftMenu = true;
 }
 public void setContentFragment(Fragment contentFragment) {
  this.contentFragment = contentFragment;
 };
 public void setRightFragment(Fragment rightFragment) {
  this.rightFragment = rightFragment;
  hasRightMenu = true;
 }
 public void openLeft() {
  if (hasLeftMenu)
   mySlideMenu.openLeft();
 }
 public void openRight() {
  if (hasRightMenu)
   mySlideMenu.openRight();
 }
 public void resume() {
  mySlideMenu.resume();
 }
 public abstract void initFragment();
}


自己的Activity只用去设置具体的Fragment
public class MenuTestActivity extends MenuActivity{
 @Override
 public void initFragment() {
  //设置菜单,其中ContentFragment为主菜单,必须设置
  //setLeftFragment(new LeftFragment());
  setRightFragment(new RightFragment());
  setContentFragment(new ContentFragment());
 }
}

你可能感兴趣的:(自定义控件,SlideMenu)