android 自定义ViewGroup和对view进行切图动画实现滑动菜单SlidingMenu

示意图就不展示了,和上一节的一样,滑动菜单SlidingMenu效果如何大家都比较熟悉,在这里我简单说明一下用自定义ViewGroup来实现.

实现方法:我们自定义一个ViewGroup实现左右滑动,第一屏隐藏,第二屏显示.

代码如下:

package com.jj.sliding_6;

import android.content.Context;
import android.util.AttributeSet;
import android.util.Log;
import android.view.View;
import android.view.ViewGroup;
import android.view.ViewTreeObserver;
import android.view.View.MeasureSpec;
import android.view.ViewTreeObserver.OnGlobalLayoutListener;
import android.widget.AbsoluteLayout;
import android.widget.LinearLayout;
import android.widget.ListView;
import android.widget.RelativeLayout;
import android.widget.Scroller;

/***
 * 自定义view
 * 
 * @author zhangjia
 * 
 */
public class MyViewGroup extends ViewGroup {
	private Scroller scroller;// 滑动
	private int distance;// 滑动距离

	private View menu_view, content_view;
	private int duration = 500;

	private ViewTreeObserver viewTreeObserver;
	private Context context;
	private CloseAnimation closeAnimation;

	public static boolean isMenuOpned = false;// 菜单是否打开

	public MyViewGroup(Context context) {
		super(context, null);
	}

	public void setCloseAnimation(CloseAnimation closeAnimation) {
		this.closeAnimation = closeAnimation;
	}

	public MyViewGroup(Context context, AttributeSet attrs) {
		super(context, attrs);
		this.context = context;
		scroller = new Scroller(context);
	}

	public void setDistance(int distance) {
		this.distance = distance;
	}

	@Override
	protected void onLayout(boolean changed, int l, int t, int r, int b) {
		if (changed) {
			menu_view = getChildAt(0);// 获取滑动菜单的view
			content_view = getChildAt(1);// 获得主页view

			// 相当于fill_parent
			content_view.measure(0, 0);
			content_view.layout(0, 0, getWidth(), getHeight());
		}
	}

	@Override
	public void computeScroll() {
		Log.e("jj", "isMenuOpned=" + isMenuOpned);
		if (scroller.computeScrollOffset()) {
			scrollTo(scroller.getCurrX(), scroller.getCurrY());
			postInvalidate();// 刷新
			if (closeAnimation != null)
				closeAnimation.closeMenuAnimation();

		}else{
			MainActivity.isScrolling=false;
		}
	}

	void showMenu() {
		Log.e("jj", "shoeMenu");
		isMenuOpned = true;
		scroller.startScroll(getScrollX(), 0, -distance, 0, duration);
		invalidate();// 刷新
	}

	// 关闭菜单(执行自定义动画)
	void closeMenu() {
		Log.e("jj", "closeMenu");
		isMenuOpned = false;
		scroller.startScroll(getScrollX(), 0, distance, 0, duration);

		invalidate();// 刷新
	}

	// 关闭菜单(执行自定义动画)
	void closeMenu_1() {
		isMenuOpned = false;
		scroller.startScroll(getScrollX(), 0, distance - getWidth(), 0,
				duration);
		invalidate();// 刷新
	}

	// 关闭菜单(执行自定义动画)
	void closeMenu_2() {
		isMenuOpned = false;
		scroller.startScroll(getScrollX(), 0, getWidth(), 0, duration);
		invalidate();// 刷新
	}

	/***
	 * Menu startScroll(startX, startY, dx, dy)
	 * 
	 * dx=e1的减去e2的x,所以右移为负,左移动为正 dx为移动的距离,如果为正,则标识向左移动|dx|,如果为负,则标识向右移动|dx|
	 */
	void slidingMenu() {
		Log.e("jj", "slidingMenu");
		// 没有超过半屏
		if (getScrollX() > -getWidth() / 2) {
			scroller.startScroll(getScrollX(), 0, -getScrollX(), 0, duration);
			isMenuOpned = false;
		}
		// 超过半屏
		else if (getScrollX() <= -getWidth() / 2) {
			scroller.startScroll(getScrollX(), 0, -(distance + getScrollX()),
					0, duration);
			isMenuOpned = true;
		}

		invalidate();// 刷新
		Log.v("jj", "getScrollX()=" + getScrollX());
	}
}

  abstract class CloseAnimation {
	// 点击list item 关闭menu动画
	public void closeMenuAnimation() {

	};
}

上诉大部分我都加以注释,想必不用我解释太多,大家仔细看都应该可以看懂.

之后我们只需要在MainActivity中把要显示的view添加进去就可以了。

运行效果:


我把源码上传网上,大家可以下载运行,如有不足请留言.

说明一点:listview上下左右滑动冲突没有解决,不过我运行看过很多应用,要么listview不能左右滑动,要么能左右滑动但是listview不到一屏.


源码下载


下面我介绍另外一种方法,这种方法比较简单,但是有点不实用.不过对SlidingMenu滑动菜单要求不高的应用完全可以了,如:云中书城等,没有用到手势时时滑动.

实现方法:我们在点击或者滑动的时候获取当前view的切图bitmap,然后将这个bitmap传递到打开后的activity,在这个activity中布局具体如下:

<?xml version="1.0" encoding="utf-8"?>
<AbsoluteLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/layout"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent" >

    <FrameLayout
        android:id="@+id/slideout_placeholder"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:background="#777777" >

        <ListView
            android:id="@+id/list"
            android:layout_width="fill_parent"
            android:layout_height="fill_parent"
            android:cacheColorHint="#00000000" />
    </FrameLayout>

    <ImageView
        android:id="@+id/slidedout_cover"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:scaleType="fitXY" />

</AbsoluteLayout>
这种布局目的就是让用户觉得我们操作的是一个view.

具体实现:我将代码上传网上,大家自行下载运行,有不足之处,自行调整.

效果图;



源码下载


这篇讲解比较少,不过大部分都加以注释,相信大家都看得明白.


我看了有的朋友是对HorizontalScrollView进行的自定义,实现方法比较多,因人而异,总之只要实现效果就行.


写到这里,不足的地方请之处,thanks for you .








版权声明:本文为iteye_17686原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/iteye_17686/article/details/82437169