在这个例子里面我实现了多个view在切换时同时支持手势和点击底部的button,纯UI的东西,除了设计模式,没有什么原理可讲,上代码。
package com.isomobile.widgets; import android.app.ActivityGroup; import android.os.Bundle; import android.view.View; public class MainActivity extends ActivityGroup implements View.OnClickListener { private int mCurId = R.id.btn1; private MainViewManager mViewManager; /** Called when the activity is first created. */ @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); mViewManager = MainViewManager.getInstance(); mViewManager.setupViews(this); } @Override public void onClick(View v) { final int id = v.getId(); if (mCurId == id) { return; } mCurId = id; mViewManager.setCurBtnPos(id); mViewManager.processViews(this); mViewManager.onRotateAnimation(mViewManager.getCurBtnIndex(id)); } }
package com.isomobile.widgets; import android.app.Activity; import android.app.ActivityGroup; import android.content.Context; import android.content.Intent; import android.view.MotionEvent; import android.view.View; import android.view.View.OnClickListener; import android.view.animation.Animation; import android.widget.Button; import android.widget.RelativeLayout; public class MainViewManager { private static final int FLING_MIN_DISTANCE = 120; private static final int FLING_MIN_VELOCITY = 200; private final static int DISTENCE_X = 240, DISTENCE_Y = 0; private final static int ROTATE_ANIMATION_DURATION = 300; private final static int DEFAULT_FLING_ANGLE = 30; public final static Class<?>[] sActivityClasses = new Class[]{ Activity1.class, Activity2.class, Activity3.class, Activity4.class, Activity5.class }; public final static int[] sResIds = new int[]{ R.id.btn1, R.id.btn2, R.id.btn3, R.id.btn4, R.id.btn5 }; public final static String[] sActivityIds = new String[]{ "Activity1", "Activity2", "Activity3", "Activity4", "Activity5" }; private int mPreBtnPos = 0, mCurBtnPos = 0; private RelativeLayout mViewContainer; private View mPreView; private View[] mCurView = new View[sResIds.length]; private Button[] mBtns = new Button[sResIds.length]; private static MainViewManager mInstance = new MainViewManager(); private MainViewManager() { } public static MainViewManager getInstance() { return mInstance; } public int getCurBtnId(int index) { return sResIds[index]; } public void setCurBtnPos(int rid) { mCurBtnPos = getCurBtnIndex(rid); } public View getCurView(int index) { return mCurView[index]; } public void setupViews(Context context) { mViewContainer = (RelativeLayout) ((Activity) context).findViewById(R.id.container); final Button[] btns = mBtns; for (int i = 0; i < btns.length; i++) { btns[i] = (Button) ((Activity) context).findViewById(sResIds[i]); btns[i].setOnClickListener((OnClickListener) context); } // 第一次启动时,默认跳转到第一个activity mCurView[0] = ((ActivityGroup) context).getLocalActivityManager().startActivity( sActivityIds[0], new Intent(context, sActivityClasses[0]).addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)) .getDecorView(); mViewContainer.addView(mCurView[0]); mPreView = mCurView[0]; mPreBtnPos = 0; } public int getCurBtnIndex(int rid) { final int length = sResIds.length; for (int i = 0; i < length; i++) { if (rid == sResIds[i]) { return i; } } return 0; } public int getCurBtnResid(){ return sResIds[mCurBtnPos]; } public boolean getMotionState(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY){ return e1.getX() - e2.getX() > FLING_MIN_DISTANCE && Math.abs(velocityX) > FLING_MIN_VELOCITY && Math.abs(Math.toDegrees(Math.atan((e1.getY() - e2.getY()) / (e1.getX() - e2.getX())))) < DEFAULT_FLING_ANGLE; } public void processViews(Context context) { mViewContainer.removeAllViews(); final Intent intent = new Intent(context, sActivityClasses[mCurBtnPos]); intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); mCurView[mCurBtnPos] = ((ActivityGroup) context).getLocalActivityManager().startActivity( sActivityIds[mCurBtnPos], intent).getDecorView(); } public void onRotateAnimation(int index) { if (mPreBtnPos > mCurBtnPos) { Rotate3d.rightRotate(mPreView, mCurView[index], DISTENCE_X, DISTENCE_Y, ROTATE_ANIMATION_DURATION, new AnimListener()); } else { Rotate3d.leftRotate(mPreView, mCurView[index], DISTENCE_X, DISTENCE_Y, ROTATE_ANIMATION_DURATION, new AnimListener()); } mPreView = mCurView[index]; mViewContainer.removeAllViews(); mViewContainer.addView(mCurView[index]); mPreBtnPos = mCurBtnPos; } private final static class AnimListener implements Animation.AnimationListener { public void onAnimationEnd(Animation animation) { // 可以设置buttons的背景或者状态(是否可点击等) } public void onAnimationRepeat(Animation animation) { } public void onAnimationStart(Animation animation) { // 可以设置buttons的背景或者状态(是否可点击等) } } }
package com.isomobile.widgets; import android.app.Activity; import android.os.Bundle; import android.view.GestureDetector; import android.view.MotionEvent; import android.view.View; import android.view.GestureDetector.OnGestureListener; import android.view.View.OnTouchListener; import android.widget.LinearLayout; import android.widget.TextView; public class Activity1 extends Activity implements OnTouchListener, OnGestureListener { private GestureDetector mGestureDetector; private MainViewManager mViewManager; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity1_layout); setupViews(); } private void setupViews() { mGestureDetector = new GestureDetector(this); mViewManager = MainViewManager.getInstance(); android.util.Log.d("TAG", "aaa"); final LinearLayout layout1 = (LinearLayout) findViewById(R.id.layout1); final TextView tv1 = (TextView) layout1.findViewById(R.id.tv1); tv1.setOnTouchListener(this); } @Override public boolean onTouch(View v, MotionEvent event) { android.util.Log.d("TAG", "1111"); mGestureDetector.onTouchEvent(event); return true; } @Override public boolean onDown(MotionEvent e) { return false; } @Override public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { try { if (mViewManager.getMotionState(e1, e2, velocityX, velocityY)) { mViewManager.setCurBtnPos( mViewManager.getCurBtnId(1)); if (null == mViewManager.getCurView(1)) { mViewManager.processViews(getParent()); } mViewManager.onRotateAnimation(1); return true; } else if (mViewManager.getMotionState(e2, e1, velocityX, velocityY)) { mViewManager.setCurBtnPos( mViewManager.getCurBtnId(4)); if (null == mViewManager.getCurView(4)) { mViewManager.processViews(getParent()); } mViewManager.onRotateAnimation(4); return true; } } catch (Exception ex) { return true; } return false; } @Override public void onLongPress(MotionEvent e) { } @Override public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) { return false; } @Override public void onShowPress(MotionEvent e) { } @Override public boolean onSingleTapUp(MotionEvent e) { return false; } }
整个工程源代码:http://download.csdn.net/detail/androidzhaoxiaogang/3643473