为啥 overScrollBy() 和 onOverScrolled() 不能与 RecyclerView 一起使用

Posted

技术标签:

【中文标题】为啥 overScrollBy() 和 onOverScrolled() 不能与 RecyclerView 一起使用【英文标题】:Why doesn't overScrollBy() and onOverScrolled() work with RecyclerView为什么 overScrollBy() 和 onOverScrolled() 不能与 RecyclerView 一起使用 【发布时间】:2014-10-05 09:00:18 【问题描述】:

我希望在我的自定义 RecyclerView 中使用这些方法,但由于某种原因它不起作用,我不确定为什么......

@Override
protected boolean overScrollBy(int deltaX, int deltaY, int scrollX, int scrollY, int scrollRangeX, int scrollRangeY, int maxOverScrollX, int maxOverScrollY, boolean isTouchEvent)     
    return super.overScrollBy(deltaX, deltaY, scrollX, scrollY, scrollRangeX, scrollRangeY, mOverscrollDistance, mOverscrollDistance, isTouchEvent);


@Override
protected void onOverScrolled(int scrollX, int scrollY, boolean clampedX, boolean clampedY) 
    super.onOverScrolled(scrollX, scrollY, clampedX, clampedY);

我实际上希望做的是在列表的开头添加空白空间,这样我就可以滚动到第一个具有设定距离 mOverscrollDistance 的项目,所以如果你有更好的建议如何实现这个然后请分享!

【问题讨论】:

老实说我没试过,但你设置过滚动模式了吗? developer.android.com/reference/android/view/… @yigit 是的,我已将过度滚动模式设置为 OVER_SCROLL_ALWAYS,我知道这是默认设置,但我想确定 【参考方案1】:

在默认的android实现中,android只会在过度滚动时绘制发光:

@Override
public void draw(Canvas c) 
    super.draw(c);

    final int count = mItemDecorations.size();
    for (int i = 0; i < count; i++) 
        mItemDecorations.get(i).onDrawOver(c, this);
    

    boolean needsInvalidate = false;
    if (mLeftGlow != null && !mLeftGlow.isFinished()) 
        final int restore = c.save();
        c.rotate(270);
        c.translate(-getHeight() + getPaddingTop(), 0);
        needsInvalidate = mLeftGlow != null && mLeftGlow.draw(c);
        c.restoreToCount(restore);
    
    if (mTopGlow != null && !mTopGlow.isFinished()) 
        c.translate(getPaddingLeft(), getPaddingTop());
        needsInvalidate |= mTopGlow != null && mTopGlow.draw(c);
    
    if (mRightGlow != null && !mRightGlow.isFinished()) 
        final int restore = c.save();
        final int width = getWidth();

        c.rotate(90);
        c.translate(-getPaddingTop(), -width);
        needsInvalidate |= mRightGlow != null && mRightGlow.draw(c);
        c.restoreToCount(restore);
    
    if (mBottomGlow != null && !mBottomGlow.isFinished()) 
        final int restore = c.save();
        c.rotate(180);
        c.translate(-getWidth() + getPaddingLeft(), -getHeight()
                + getPaddingTop());
        needsInvalidate |= mBottomGlow != null && mBottomGlow.draw(c);
        c.restoreToCount(restore);
    

    if (needsInvalidate) 
        ViewCompat.postInvalidateOnAnimation(this);
    

如果你想拥有类似 iphone 的滚动效果,你必须这样做:

    为第一个孩子添加左边距,为右边孩子添加右边距。比如说,边距是mOverScrollSpace

    你需要在自己的LayoutManager中写一个方法isOverScrolled来知道剩余滚动空间是否小于mOverScrollSpace

    然后在onTouchEvent,遇到事件ACTION_MOVE,你写这样的东西

    if(isOverScrolled) 
        scrollByInternal(canScrollHorizontally ? -dx : 0,
            canScrollVertically ? -dy : 0)
    
    else 
        scrollByInternal(canScrollHorizontally ? -dx/4 : 0,
            canScrollVertically ? -dy/4 : 0)
    
    

【讨论】:

以上是关于为啥 overScrollBy() 和 onOverScrolled() 不能与 RecyclerView 一起使用的主要内容,如果未能解决你的问题,请参考以下文章

Android的ListView弹动效果

用于收集超过 1000 万条记录的 Mongo 查询优化

JAVASCRIPT的onSubmit事件的作用是

krpano怎么让文字一直显示在热点上

为啥 SQL Server GEOGRAPHY 允许 -15069° 和 +15069° 之间的经度?为啥是±15069°?

为啥 int 存在于 C 中,为啥不只是 short 和 long