【UI交互效果】android UI效果三: 滚动切换屏幕
效果如下:
主要有3个类1个layout:
Activity: ScrollViewTestActivity, 两个自定义View, 1个 ScrollView用来控制滑动效果, 1个PageControlView,用来控制下方显示的处在第几屏.
1个mian.xml
Activity:
import android.app.Activity; import android.os.Bundle; import android.view.View; import android.widget.ImageView; public class ScrollViewTestActivity extends Activity { /** Called when the activity is first created. */ @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); ScrollView sv = (ScrollView)findViewById(R.id.scroll); ImageView iv = new ImageView(this); iv.setImageDrawable(this.getResources().getDrawable(R.drawable.a1)); sv.addView(iv); sv.addView(View.inflate(this, R.layout.layout_0, null)); ImageView iv2 = new ImageView(this); iv2.setImageDrawable(getResources().getDrawable(R.drawable.a2)); sv.addView(iv2); PageControlView pageControl = (PageControlView)findViewById(R.id.pageControl); sv.setOnScreenChangeListener(pageControl); sv.initPageControlView(); } }
ScrollView:
import android.content.Context; import android.util.AttributeSet; import android.view.GestureDetector; import android.view.GestureDetector.SimpleOnGestureListener; import android.view.MotionEvent; import android.view.View; import android.view.ViewConfiguration; import android.view.ViewGroup; import android.widget.Scroller; public class ScrollView extends ViewGroup{ private GestureDetector gesture; private Context context; private boolean fling; private Scroller scroller; private OnScreenChangeListener onScreenChangeListener; public ScrollView(Context context) { super(context); this.context = context; gesture = new GestureDetector(context,new GestureListener()); scroller = new Scroller(context); } public ScrollView(Context context,AttributeSet att){ super(context,att); this.context = context; gesture = new GestureDetector(context,new GestureListener()); scroller = new Scroller(context); } @Override protected void onLayout(boolean changed, int l, int t, int r, int b) { for(int i=0;i<getChildCount();i++){ View child = (View)getChildAt(i); child.measure(r-l, b-t); child.layout(getWidth()*i, 0, getWidth()*(i+1), getHeight()); } } @Override public boolean onTouchEvent(MotionEvent ev){ gesture.onTouchEvent(ev); switch(ev.getAction()){ case MotionEvent.ACTION_MOVE: break; case MotionEvent.ACTION_UP: System.out.println("action_up..."); if(!fling){ scrollToScreen(); } fling = false; break; } return true; } /** * 用来计算拖动一段距离后,要显示哪个界面 */ private void scrollToScreen(){ int leftWidth = getScrollX(); int tabs = leftWidth/getWidth(); int len = leftWidth - tabs*getWidth(); if(len<getWidth()/2){ // scrollTo(tabs*getWidth(),0); scroller.startScroll(leftWidth, 0, -len, 0, len*2); }else{ // scrollTo((tabs+1)*getWidth(),0); scroller.startScroll(leftWidth, 0, getWidth()-len, 0, len*2); tabs = tabs + 1; } if(onScreenChangeListener!=null){ onScreenChangeListener.screenChange(tabs, getChildCount()); } invalidate(); } @Override public void computeScroll() { if (scroller.computeScrollOffset()) { scrollTo(scroller.getCurrX(), 0); postInvalidate(); } } class GestureListener extends SimpleOnGestureListener{ @Override public boolean onDoubleTap(MotionEvent e){ return super.onDoubleTap(e); } @Override public boolean onDown(MotionEvent e){ return super.onDown(e); } @Override public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,float velocityY){ if(Math.abs(velocityX)>ViewConfiguration.get(context).getScaledMinimumFlingVelocity()){ scrollToScreen(); fling = true; } return true; } @Override public void onShowPress(MotionEvent e){ super.onShowPress(e); } @Override public void onLongPress(MotionEvent e){ super.onLongPress(e); } @Override public boolean onScroll(MotionEvent e1, MotionEvent e2,float distanceX, float distanceY){ if(distanceX>0&&getScrollX()<(getChildCount()-1)*getWidth()|| distanceX<0&&getScrollX()>0){ scrollBy((int)distanceX,0); } return true; } @Override public boolean onSingleTapUp(MotionEvent e){ return super.onSingleTapUp(e); } } public interface OnScreenChangeListener { void screenChange(int currentTab,int totalTab); } public void setOnScreenChangeListener(OnScreenChangeListener onScreenChangeListener){ this.onScreenChangeListener = onScreenChangeListener; } public void initPageControlView(){ if(onScreenChangeListener!=null){ onScreenChangeListener.screenChange(0, getChildCount()); } } }
PageControlView:
import com.yang.testscroll.ScrollView.OnScreenChangeListener; import android.content.Context; import android.util.AttributeSet; import android.widget.ImageView; import android.widget.LinearLayout; public class PageControlView extends LinearLayout implements OnScreenChangeListener{ private Context context; public PageControlView(Context context) { super(context); this.context = context; } public PageControlView(Context context,AttributeSet attr){ super(context,attr); this.context = context; } @Override public void screenChange(int currentTab, int totalTab) { this.removeAllViews(); for(int i=0;i<totalTab;i++){ ImageView iv = new ImageView(context); if(i==currentTab){ iv.setImageResource(R.drawable.page_indicator_focused); }else{ iv.setImageResource(R.drawable.page_indicator); } this.addView(iv); } } }
main.xml:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical" >
<com.yang.testscroll.ScrollView
android:id="@+id/scroll"
android:layout_width="fill_parent"
android:layout_height="fill_parent" />
<com.yang.testscroll.PageControlView
android:id="@+id/pageControl"
android:layout_width="fill_parent"
android:layout_height="40dp"
android:layout_alignParentBottom="true"
android:background="#8f00000f"
android:gravity="center"/>
</RelativeLayout>