Пример #1
0
  @Override
  public void computeScroll() {
    super.computeScroll();
    if (mScroller.computeScrollOffset()) {
      int lastScrollY = mHolder.mOffsetY;
      int currentY = mScroller.getCurrY();
      int offsetY = currentY - lastScrollY;
      lastScrollY = currentY;
      moveView(offsetY);

      LogUtils.d("currentY=" + currentY + ";mHolder.mOffsetY=" + mHolder.mOffsetY);
    } else {
      LogUtils.d("scroll end mOffsetY=" + mHolder.mOffsetY);
      if (mHolder.mOffsetY == 0) mHasScrollBack = false;
    }
  }
Пример #2
0
 @Override
 protected void onLayout(boolean changed, int l, int t, int r, int b) {
   super.onLayout(changed, l, t, r, b);
   LogUtils.d("onLayout mHolder.mOffsetY=" + mHolder.mOffsetY);
   mFootHeight = ((IFooterCallBack) mFooterView).getFooterHeight();
   int childCount = getChildCount();
   int top = getPaddingTop() + mHolder.mOffsetY;
   int adHeight = 0;
   for (int i = 0; i < childCount; i++) {
     View child = getChildAt(i);
     if (child.getVisibility() == View.VISIBLE) {
       if (i == 0) {
         adHeight = child.getMeasuredHeight() - mHeaderViewHeight;
         // 通过把headerview向上移动一个headerview高度的距离来达到隐藏headerview的效果
         child.layout(0, top - mHeaderViewHeight, child.getMeasuredWidth(), top + adHeight);
         top += adHeight;
       } else if (i == 1) {
         int childHeight = child.getMeasuredHeight() - adHeight;
         child.layout(0, top, child.getMeasuredWidth(), childHeight + top);
         top += childHeight;
       } else {
         child.layout(0, top, child.getMeasuredWidth(), child.getMeasuredHeight() + top);
         top += child.getMeasuredHeight();
       }
     }
   }
 }
Пример #3
0
 /**
  * 设置自定义headerView
  *
  * @param headerView headerView必须要实现 IHeaderCallBack接口
  */
 public void setCustomHeaderView(View headerView) {
   LogUtils.i("setCustomHeaderView");
   if (headerView instanceof IHeaderCallBack) {
     mHeaderView = headerView;
   } else {
     throw new RuntimeException("headerView must be implementes IHeaderCallBack!");
   }
 }
Пример #4
0
 /** reset header view's height. */
 private void resetHeaderHeight() {
   float height = mHolder.mOffsetY;
   if (height == 0) // not visible.
   return;
   // refreshing and header isn't shown fully. do nothing.
   if (mPullRefreshing && height <= mHeaderViewHeight) {
     return;
   }
   int offsetY = 0;
   if (mPullRefreshing) {
     offsetY = mHeaderViewHeight - mHolder.mOffsetY;
     startScroll(offsetY, SCROLL_DURATION);
   } else {
     offsetY = 0 - mHolder.mOffsetY;
     startScroll(offsetY, SCROLL_DURATION);
   }
   LogUtils.d("resetHeaderHeight offsetY=" + offsetY);
 }
Пример #5
0
 private void sendCancelEvent() {
   LogUtils.d("sendCancelEvent");
   if (!mHasSendCancelEvent) {
     setRefreshTime();
     mHasSendCancelEvent = true;
     mHasSendDownEvent = false;
     MotionEvent last = mLastMoveEvent;
     MotionEvent e =
         MotionEvent.obtain(
             last.getDownTime(),
             last.getEventTime() + ViewConfiguration.getLongPressTimeout(),
             MotionEvent.ACTION_CANCEL,
             last.getX(),
             last.getY(),
             last.getMetaState());
     dispatchTouchEventSupper(e);
   }
 }
Пример #6
0
 private void addFooterView(OnGlobalLayoutListener listener) {
   mHeaderViewHeight = ((IHeaderCallBack) mHeaderView).getHeaderHeight();
   LogUtils.d("onGlobalLayout mHeaderViewHeight=" + mHeaderViewHeight);
   mContentView.setHolder(mHolder);
   mContentView.setScrollListener();
   if (mEnablePullLoad && needAddFooterView()) {
     Log.i("CustomView", "add footView" + ";mHeaderViewHeight=" + mHeaderViewHeight);
     addView(mFooterView);
   }
   // 移除视图树监听器
   removeViewTreeObserver(listener);
   if (autoRefresh) {
     startRefresh();
   }
   if (mHeadMoveDistence == 0) {
     mHeadMoveDistence = getHeight() / 3;
   }
 }
Пример #7
0
  /** stop refresh, reset header view. */
  public void stopRefresh() {
    LogUtils.i("stopRefresh mPullRefreshing=" + mPullRefreshing);
    if (mPullRefreshing == true) {
      mPullRefreshing = false;
      mHeaderCallBack.onStateFinish();
      mState = XRefreshViewState.STATE_COMPLETE;
      mHasScrollBack = true;
      mHandler.postDelayed(
          new Runnable() {

            @Override
            public void run() {
              resetHeaderHeight();
              lastRefreshTime = Calendar.getInstance().getTimeInMillis();
            }
          },
          mPinnedTime);
    }
  }
Пример #8
0
 private void sendDownEvent() {
   if (!mHasSendDownEvent) {
     LogUtils.d("sendDownEvent");
     mHasSendCancelEvent = false;
     mHasSendDownEvent = true;
     isIntercepted = false;
     final MotionEvent last = mLastMoveEvent;
     if (last == null) return;
     MotionEvent e =
         MotionEvent.obtain(
             last.getDownTime(),
             last.getEventTime(),
             MotionEvent.ACTION_DOWN,
             last.getX(),
             last.getY(),
             last.getMetaState());
     dispatchTouchEventSupper(e);
   }
 }
Пример #9
0
  @Override
  public void computeScroll() {
    super.computeScroll();
    if (mScroller.computeScrollOffset()) {
      int lastScrollY = mHolder.mOffsetY;
      int currentY = mScroller.getCurrY();
      int offsetY = currentY - lastScrollY;
      lastScrollY = currentY;
      moveView(offsetY);

      LogUtils.d("currentY=" + currentY + ";mHolder.mOffsetY=" + mHolder.mOffsetY);
    } else {
      int currentY = mScroller.getCurrY();
      if (mHolder.mOffsetY == 0) {
        mStopingRefresh = false;
      } else {
        // 有时scroller已经停止了,但是却没有回到应该在的位置,执行下面的方法恢复
        if (mStopingRefresh && !mPullLoading && !mPullRefreshing) {
          startScroll(-currentY, SCROLL_DURATION);
        }
      }
    }
  }
Пример #10
0
 @Override
 protected void onLayout(boolean changed, int l, int t2, int r, int b) {
   super.onLayout(changed, l, t2, r, b);
   //        if(mHolder.mOffsetY!=0)return;
   LogUtils.d("onLayout mHolder.mOffsetY=" + mHolder.mOffsetY);
   mFootHeight = ((IFooterCallBack) mFooterView).getFooterHeight();
   int childCount = getChildCount();
   int top = getPaddingTop() + mHolder.mOffsetY;
   int adHeight = 0;
   for (int i = 0; i < childCount; i++) {
     View child = getChildAt(i);
     LayoutParams margins = (LayoutParams) child.getLayoutParams();
     int topMargin = margins.topMargin;
     int bottomMargin = margins.bottomMargin;
     int leftMargin = margins.leftMargin;
     int rightMargin = margins.rightMargin;
     l = leftMargin;
     top += topMargin;
     r -= rightMargin;
     if (child.getVisibility() != View.GONE) {
       if (i == 0) {
         adHeight = child.getMeasuredHeight() - mHeaderViewHeight;
         // 通过把headerview向上移动一个headerview高度的距离来达到隐藏headerview的效果
         child.layout(l, top - mHeaderViewHeight, r, top + adHeight);
         top += adHeight;
       } else if (i == 1) {
         int childHeight = child.getMeasuredHeight() - adHeight;
         child.layout(l, top, r, childHeight + top);
         top += childHeight;
       } else {
         child.layout(l, top, r, child.getMeasuredHeight() + top);
         top += child.getMeasuredHeight();
       }
     }
   }
 }
Пример #11
0
 /**
  * enable or disable pull up load more feature.
  *
  * @param enable
  */
 public void setPullLoadEnable(boolean enable) {
   LogUtils.d("setPullLoadEnable");
   mEnablePullLoad = enable;
 }
Пример #12
0
  @Override
  public boolean dispatchTouchEvent(MotionEvent ev) {
    final int action = ev.getAction();
    int deltaY = 0;
    int deltaX = 0;
    switch (action) {
      case MotionEvent.ACTION_DOWN:
        mHasSendCancelEvent = false;
        mHasSendDownEvent = false;
        mLastY = (int) ev.getRawY();
        mLastX = (int) ev.getRawX();
        mInitialMotionY = mLastY;

        // if (!mScroller.isFinished() && !mPullRefreshing && !mPullLoading)
        // {
        // mScroller.forceFinished(true);
        // }
        break;
      case MotionEvent.ACTION_MOVE:
        mLastMoveEvent = ev;
        if (mPullLoading
            || mPullRefreshing
            || !isEnabled()
            || mIsIntercept
            || mHasScrollBack
            || mContentView.isLoading()) {
          if (mIsPinnedContentWhenRefreshing) {
            return super.dispatchTouchEvent(ev);
          } else {
            sendCancelEvent();
            return true;
          }
        }
        int currentY = (int) ev.getRawY();
        int currentX = (int) ev.getRawX();
        deltaY = currentY - mLastY;
        deltaX = currentX - mLastX;
        mLastY = currentY;
        mLastX = currentX;
        // intercept the MotionEvent only when user is not scrolling
        if (!isIntercepted && (Math.abs(deltaY) < mTouchSlop)) {
          isIntercepted = true;
          return super.dispatchTouchEvent(ev);
        }
        if (isForHorizontalMove
            && !mMoveForHorizontal
            && Math.abs(deltaX) > mTouchSlop
            && Math.abs(deltaX) > Math.abs(deltaY)) {
          if (mHolder.mOffsetY == 0) {
            mMoveForHorizontal = true;
          }
        }
        if (mMoveForHorizontal) {
          return super.dispatchTouchEvent(ev);
        }
        LogUtils.d("isTop=" + mContentView.isTop() + ";isBottom=" + mContentView.isBottom());
        if (deltaY > 0 && mHolder.mOffsetY <= mHeadMoveDistence || deltaY < 0) {
          deltaY = (int) (deltaY / OFFSET_RADIO);
        } else {
          deltaY = 0;
        }
        if (mContentView.isTop() && (deltaY > 0 || (deltaY < 0 && mHolder.hasHeaderPullDown()))) {
          sendCancelEvent();
          updateHeaderHeight(currentY, deltaY);
        } else if (needAddFooterView()
            && mContentView.isBottom()
            && (deltaY < 0 || deltaY > 0 && mHolder.hasFooterPullUp())) {
          sendCancelEvent();
          updateFooterHeight(deltaY);
        } else if (mContentView.isTop() && !mHolder.hasHeaderPullDown()
            || mContentView.isBottom() && !mHolder.hasFooterPullUp()) {
          if (Math.abs(deltaY) > 0) sendDownEvent();
        }
        break;
      case MotionEvent.ACTION_CANCEL:
      case MotionEvent.ACTION_UP:
        // if (mHolder.mOffsetY != 0 && mRefreshViewListener != null
        // && !mPullRefreshing && !mPullLoading) {
        // mRefreshViewListener.onRelease(mHolder.mOffsetY);
        // }
        if (mHolder.hasHeaderPullDown() && !mHasScrollBack) {
          // invoke refresh
          if (mEnablePullRefresh && mHolder.mOffsetY > mHeaderViewHeight) {
            mPullRefreshing = true;
            mHeaderCallBack.onStateRefreshing();
            mState = XRefreshViewState.STATE_REFRESHING;
            if (mRefreshViewListener != null) {
              mRefreshViewListener.onRefresh();
            }
          }
          resetHeaderHeight();
        } else if (mHolder.hasFooterPullUp()) {
          if (mEnablePullLoad && needAddFooterView() && !mHasLoadComplete) {
            invoketLoadMore();
          } else {
            int offset = 0 - mHolder.mOffsetY;
            startScroll(offset, SCROLL_DURATION);
          }
        }
        mLastY = -1; // reset
        mInitialMotionY = 0;
        isIntercepted = true;
        mMoveForHorizontal = false;
        mIsIntercept = false;
        break;
    }
    return super.dispatchTouchEvent(ev);
  }