Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> 關於Android編程 >> Android編程滑動效果之Gallery仿圖像集浏覽實現方法

Android編程滑動效果之Gallery仿圖像集浏覽實現方法

編輯:關於Android編程

本文實例講述了Android編程滑動效果之Gallery仿圖像集浏覽實現方法。分享給大家供大家參考,具體如下:

Android系統自帶一個Gallery浏覽圖片的應用,通過手指拖動時能夠非常流暢的顯示圖片,用戶交互和體驗都很好。

本示例就是通過Gallery和自定義的View,模仿實現一個仿Gallery圖像集的圖片浏覽效果。效果圖如下:

1、基本原理

在 Activity 中實現 OnGestureListener 的接口 onFling() 手勢事件,通過自定義的 View 繪制draw() 圖片

2、Activity

Activity中,通過onTouchEvent() 注冊 myGesture.onTouchEvent(event)

@Override
public boolean onTouchEvent(MotionEvent event) {
  switch (event.getAction()) {
  case MotionEvent.ACTION_UP:
    flingView.onFling(0); // 手指抬起後,重置滑動距離offsetX = 0
    break;
  }
  return myGesture.onTouchEvent(event);
}

接著實現接口OnGestureListener 的 onScroll()方法,給繼承自View的 FlingView 的handleScroll()成員方法傳遞滑動參數,獲取滑動的x軸距離

@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
  flingView.handleScroll(-1 * (int) distanceX);
  return true;
}

接著實現接口OnGestureListener 的 OnFling()方法,給繼承自View的 FlingView 的onFling()成員方法傳遞滑動參數,獲取手勢的速度

@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
  flingView.onFling((int) - velocityX);
  return true;
}

3、FlingView

FlingView中,獲取來自Activity中的手勢速度

public void onFling(int paramFloat1) {
  if (offsetX > GalleryDemoActivity.deviceScreenWidth / 5) {
    if (fBitmap != null) {
      isFling = true;
      isFlingRight = true;
    }
  } else if (offsetX < -GalleryDemoActivity.deviceScreenWidth / 5) {
    if (nBitmap != null) {
      isFling = true;
      isFlingLeft = true;
    }
  }
  // 開始動畫效果
  startAnimation(new MyAnimation());
}

在滑動過程中,通過實現View的Draw()方法繪制圖片,注意:此時需要同時繪制當前圖片(獲取焦點)和下一張圖片(即將獲取焦點)共兩張圖片

@Override
public void draw(Canvas canvas) {
  Paint paint = new Paint();
  Rect rect = new Rect();
  canvas.drawColor(Color.BLACK);
  // 繪制當前圖片
  if (bitmap != null) {
    int left = offsetX;
    int top = offsetY;
    int right = offsetX + GalleryDemoActivity.deviceScreenWidth;
    int bottom = offsetY + GalleryDemoActivity.deviceScreenHeight;
    rect.set(left, top, right, bottom);
    canvas.drawBitmap(bitmap, null, rect, paint);
  }
  // 繪制下一張圖片
  if (offsetX < 0) { // 向左滑動
    if (nBitmap != null) {
      int left = GalleryDemoActivity.deviceScreenWidth + 15 + offsetX;
      int top = 0;
      int right = left + GalleryDemoActivity.deviceScreenWidth;
      int bottom = GalleryDemoActivity.deviceScreenHeight;
      rect.set(left, top, right, bottom);
      canvas.drawBitmap(nBitmap, null, rect, paint);
    }
  } else if (offsetX > 0) { // 向右滑動
    if (fBitmap != null) {
      int left = -GalleryDemoActivity.deviceScreenWidth - 15 + offsetX;
      int top = 0;
      int right = left + GalleryDemoActivity.deviceScreenWidth;
      int bottom = GalleryDemoActivity.deviceScreenHeight;
      rect.set(left, top, right, bottom);
      canvas.drawBitmap(fBitmap, null, rect, paint);
    }
  }
}

在滑動圖片結束後,需要做滑動動畫後的處理,重新設置當前圖片和當前圖片的上一張和下一張的狀態,為下次滑動做准備

@Override
protected void onAnimationEnd() {
  if (isFlingRight) { // 向右滑動,position減1
    nBitmap = bitmap;
    bitmap = fBitmap;
    fBitmap = null;
    postion = postion - 1;
  } else if (isFlingLeft) { // 向左滑動,position加1
    fBitmap = bitmap;
    bitmap = nBitmap;
    nBitmap = null;
    postion = postion + 1;
  }
  isFlingRight = false;
  isFlingLeft = false;
  isFling = false;
  offsetX = 0;
  if (fBitmap == null && offsetX == 0) { // 如果前一張圖片為空(向右滑),則重置前一張圖片(position - 1)
    if (postion > 0) {
      fBitmap = getBitmap(postion - 1);
    }
  } else if (nBitmap == null && offsetX == 0) { // 如果後一張圖片為空(向左滑),則重置後一張圖片(position + 1)
    if (postion < bitmaps.length - 1) {
      nBitmap = getBitmap(postion + 1);
    }
  }
  clearAnimation();
}

4、手勢坐標介紹

本示例中,用到了OnGestureListener接口的onScroll()和OnFling()方法,涉及到了Android系統坐標及觸摸MotionEvent e1和e2、速度velocityX、velocityY等值
Android屏幕坐標系如下圖(左)

(1)MotionEvent中 e1是手指第一次按上屏幕的起點,e2是抬起手指離開屏幕的終點,根據上圖Android屏幕坐標系可知:
手指向右滑動,終點(e2)在起點(e1)的右側,有e2.getX() - e1.getX() 大於0
手指向左滑動,終點(e2)在起點(e1)的左側,有e2.getX() - e1.getX() 小於0
手指向下滑動,終點(e2)在起點(e1)的下側,有e2.getY() - e1.getY() 大於0
手指向上滑動,終點(e2)在起點(e1)的上側,有e2.getY() - e1.getY() 小於0

(2)onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY)
distanceX,是前後兩次call的X距離,不是e2與e1的水平距離
distanceX,是前後兩次call的Y距離,不是e2與e1的垂直距離
具體數值的方向,請詳見上圖(中)

(3)onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY)
velocityX,是X軸的每秒速度
velocityY,是Y軸的每秒速度
具體數值的方向,請詳見上圖(右)
仔細觀察可以發現:velocityX、velocityY的方向與distanceX、distanceY方向正好相反

更多OnGestureListener接口函數介紹

更多關於Android相關內容感興趣的讀者可查看本站專題:《Android開發動畫技巧匯總》、《Android開發入門與進階教程》及《Android控件用法總結》。

希望本文所述對大家Android程序設計有所幫助。

  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved