2015-03-13 3 views
21

Woher wissen wir, ob der Benutzer in RecyclerView nach unten oder oben scrollte?RecyclerView scrollte UP/DOWN Listener

Ich versuchte mit RecyclerView#OnScrollListener, gibt es die Menge der vertikalen Scroll und der Scroll-Zustand. Wie erhalten wir die letzte Scroll-Position, wenn Sie im Scroll-Status im Leerlauf gestartet werden, ziehen und scrollen.

Vielen Dank.

Antwort

15

Versuchen Sie, diese Art und Weise:

private static int firstVisibleInListview; 

firstVisibleInListview = yourLayoutManager.findFirstVisibleItemPosition(); 

In Ihrem Scroll-Hörer:

public void onScrolled(RecyclerView recyclerView, int dx, int dy) 
{ 
    super.onScrolled(recyclerView, dx, dy); 

    int currentFirstVisible = yourLayoutManager.findFirstVisibleItemPosition(); 

    if(currentFirstVisible > firstVisibleInListview) 
     Log.i("RecyclerView scrolled: ", "scroll up!"); 
    else 
     Log.i("RecyclerView scrolled: ", "scroll down!"); 

    firstVisibleInListview = currentFirstVisible; 

} 
+1

Dank. Es funktionierte. Aber ich handle diese Logik im 'onScrollStateChanged'' RecyclerView.SCROLL_STATE_DRAGGING'-Zustand. – Libin

+56

'if (dy> 0) {// Scrollen nach oben} else {// Scrollen nach unten}' ist nicht genug? –

+0

die Methode, die ich in scrollup einfügen wird nie aufgerufen ... aber in logcat zeigt sowohl nach oben und unten –

37

Die akzeptierte Antwort funktioniert gut, aber @MaciejPigulski gab mehr klare und saubere Lösung in dem unten stehenden Kommentar. Ich stelle es nur als Antwort hier auf. Hier ist mein Arbeitscode.

mRecyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() { 

    @Override 
    public void onScrolled(RecyclerView recyclerView, int dx, int dy) { 
     super.onScrolled(recyclerView, dx, dy); 
     if (dy > 0) { 
      // Scrolling up 
     } else { 
      // Scrolling down 
     } 
    } 

    @Override 
    public void onScrollStateChanged(RecyclerView recyclerView, int newState) { 
     super.onScrollStateChanged(recyclerView, newState); 

     if (newState == AbsListView.OnScrollListener.SCROLL_STATE_FLING) { 
      // Do something 
     } else if (newState == AbsListView.OnScrollListener.SCROLL_STATE_TOUCH_SCROLL) { 
      // Do something 
     } else { 
      // Do something 
     } 
    } 
}); 
+0

diese deprazierte –

+7

anstelle von 'setOnScrollListener (...)' können Sie 'addOnScrollListener (...)' – Juancho

+0

Verwenden Sie 'switch (newState) {...} 'Konstruktion – Destiner

6

Ich wollte ein Layout ausblenden, wenn die Recycleransicht gescrollt wird und dann sichtbar machen, wenn die Recycleransicht nach oben gescrollt wird. Ich habe nachgedacht und diese Logik entwickelt. Variable y ist ein globaler statischer int. Vergessen Sie nicht, zu erklären, y als static int y;

Ich hoffe, es hilft jemand :)

mRecyclerView.addOnScrollListener(new EndlessRecyclerOnScrollListener(lLayout) { 
      @Override 
      public void onScrolled(RecyclerView recyclerView, int dx, int dy) { 
      // super.onScrolled(recyclerView, dx, dy); 
       y=dy; 
      } 

      @Override 
      public void onScrollStateChanged(RecyclerView recyclerView, int newState) { 
       super.onScrollStateChanged(recyclerView, newState); 
       if(mRecyclerView.SCROLL_STATE_DRAGGING==newState){ 
        //fragProductLl.setVisibility(View.GONE); 
       } 
       if(mRecyclerView.SCROLL_STATE_IDLE==newState){ 
        // fragProductLl.setVisibility(View.VISIBLE); 
        if(y<=0){ 
         fragProductLl.setVisibility(View.VISIBLE); 
        } 
        else{ 
         y=0; 
         fragProductLl.setVisibility(View.GONE); 
        } 
       } 
      } 
     }); 
+0

Was ist der Inhalt der EndlessRecyclerOnScrollListener-Klasse? – ACAkgul

+0

@ AhmetCanAkgül Der Inhalt ist ein Adapter, der eine Liste von Bildansichten und Textansichten enthält. –

0

Eine weitere einfache Lösung, die Scroll-Richtung mit Hilfe des Adapters erkennen kann:

class MyRecyclerViewAdapter extends RecyclerView.Adapter<MyViewHolder> { 
    int lastItemPosition = -1; 

    @Override 
    public void onBindViewHolder(MyViewHolder holder, int position) { 
     if (position > lastItemPosition) { 
      // Scrolled Down 
     } 
     else { 
      // Scrolled Up 
     } 
     lastItemPosition = position; 
    } 
} 

^Hilfreiche wenn Sie beim Scrollen Objekt-Animationen machen.

PS: Dies wird Ihnen Anweisungen diskontinuierlich bis zu weiteren onBindViewHolder Anrufe nennen.

0

Es ist meine Implementierung von CustomRecyclerView mit allen Arten von Scroll-Hörer

public class CustomRecyclerView extends RecyclerView 
{ 
private boolean mIsScrolling; 
private boolean mIsTouching; 
private OnScrollListener mOnScrollListener; 
private Runnable mScrollingRunnable; 
private int y = 0; 

public abstract static class OnScrollListener 
{ 
    void onScrollChanged(CustomRecyclerView RvView, int x, int y, int oldX, int oldY) 
    { 
     //if you need just override this method 
    } 

    void onEndScroll(CustomRecyclerView RvView) 
    { 
     //if you need just override this method 
    } 

    protected abstract void onGoUp(); 

    protected abstract void onGoDown(); 
} 

public CustomRecyclerView(final Context context) 
{ 
    super(context); 
} 

public CustomRecyclerView(final Context context, @Nullable final AttributeSet attrs) 
{ 
    super(context, attrs); 
} 

public CustomRecyclerView(final Context context, @Nullable final AttributeSet attrs, final int defStyle) 
{ 
    super(context, attrs, defStyle); 
} 

@Override 
public boolean dispatchTouchEvent(MotionEvent iEv) 
{ 
    if (isEnabled()) 
    { 
     processEvent(iEv); 
     super.dispatchTouchEvent(iEv); 
     return true; //to keep receive event that follow down event 
    } 

    return super.dispatchTouchEvent(iEv); 
} 

private void processEvent(final MotionEvent iEv) 
{ 
    switch (iEv.getAction()) 
    { 
     case MotionEvent.ACTION_DOWN: 
      y = (int) iEv.getY(); 
      break; 

     case MotionEvent.ACTION_UP: 
      y = (int) iEv.getY(); 

      if (mIsTouching && !mIsScrolling && mOnScrollListener != null) 
      { 
       mOnScrollListener.onEndScroll(this); 
      } 

      mIsTouching = false; 
      break; 
     case MotionEvent.ACTION_MOVE: 
      mIsTouching = true; 
      mIsScrolling = true; 

      int newY = (int) iEv.getY(); 
      int difY = y - newY; 

      int MAX_VALUE = 200; 
      int MIN_VALUE = -200; 
      if (difY > MAX_VALUE) 
      { 
       if (mOnScrollListener != null) 
       { 
        mOnScrollListener.onGoDown(); 
       } 
       y = newY; 
      } 
      else if (difY < MIN_VALUE) 
      { 
       if (mOnScrollListener != null) 
       { 
        mOnScrollListener.onGoUp(); 
       } 
       y = newY; 
      } 

      break; 
    } 
} 

@Override 
protected void onScrollChanged(int iX, int iY, int iOldX, int iOldY) 
{ 
    super.onScrollChanged(iX, iY, iOldX, iOldY); 

    if (Math.abs(iOldX - iX) > 0) 
    { 
     if (mScrollingRunnable != null) 
     { 
      removeCallbacks(mScrollingRunnable); 
     } 

     mScrollingRunnable =() -> 
     { 
      if (mIsScrolling && !mIsTouching && mOnScrollListener != null) 
      { 
       mOnScrollListener.onEndScroll(CustomRecyclerView.this); 
      } 

      mIsScrolling = false; 
      mScrollingRunnable = null; 
     }; 

     postDelayed(mScrollingRunnable, 200); 
    } 

    if (mOnScrollListener != null) 
    { 
     mOnScrollListener.onScrollChanged(this, iX, iY, iOldX, iOldY); 
    } 
} 

public void scrollToView(final View iV) 
{ 
    // Get deepChild Offset 
    Point childOffset = new Point(); 
    getDeepChildOffset(CustomRecyclerView.this, iV.getParent(), iV, childOffset); 
    // Scroll to child. 

    CustomRecyclerView.this.scrollToY(childOffset.y); 
} 

private void getDeepChil`enter code here`dOffset(final ViewGroup mainParent, final ViewParent parent, final View child, final Point accumulatedOffset) 
{ 
    ViewGroup parentGroup = (ViewGroup) parent; 
    accumulatedOffset.x += child.getLeft(); 
    accumulatedOffset.y += child.getTop(); 
    if (parentGroup.equals(mainParent)) 
    { 
     return; 
    } 
    getDeepChildOffset(mainParent, parentGroup.getParent(), parentGroup, accumulatedOffset); 
} 

public void scrollToY(final int iY) 
{ 
    CustomRecyclerView.this.postDelayed(() -> 
    { 
     int x = 0; 
     int y = iY; 
     ObjectAnimator xTranslate = ObjectAnimator.ofInt(CustomRecyclerView.this, "scrollX", x); 
     ObjectAnimator yTranslate = ObjectAnimator.ofInt(CustomRecyclerView.this, "scrollY", y); 

     AnimatorSet animators = new AnimatorSet(); 
     animators.setDuration(500L); 
     animators.playTogether(xTranslate, yTranslate); 
     animators.addListener(new Animator.AnimatorListener() 
     { 

      @Override 
      public void onAnimationStart(Animator arg0) 
      { 
       // noting 
      } 

      @Override 
      public void onAnimationRepeat(Animator arg0) 
      { 
       // noting 
      } 

      @Override 
      public void onAnimationEnd(Animator arg0) 
      { 
       // noting 
      } 

      @Override 
      public void onAnimationCancel(Animator arg0) 
      { 
       // noting 
      } 
     }); 
     animators.start(); 
    }, 300); 
} 

public void scrollToTop() 
{ 
    scrollToY(0); 
} 

public void setOnRvScrollListener(OnScrollListener mOnEndScrollListener) 
{ 
    this.mOnScrollListener = mOnEndScrollListener; 
} 
} 

Und es gibt Probe Nutzungs

private void setRecyclerViewSettings() 
{ 
    mRv.setLayoutManager(new LinearLayoutManager(getActivity())); 
    mRv.setOnRvScrollListener(mScrollListener); 
} 

private CustomRecyclerView.OnScrollListener mScrollListener = new CustomRecyclerView.OnScrollListener() 
{ 
    @Override 
    protected void onGoUp() 
    { 
     AppUtils.hideKeyboard(getContext(), mRvDynamicFormQuestions.getFocusedChild()); 
    } 

    @Override 
    protected void onGoDown() 
    { 
     AppUtils.hideKeyboard(getContext(), mRvDynamicFormQuestions.getFocusedChild()); 
    } 
}; 
1
public void ScrollUp(View view) { 
    GridLayoutManager layoutManager = (GridLayoutManager) recyclerView.getLayoutManager(); 

    RecyclerView.SmoothScroller smoothScroller = new LinearSmoothScroller(getBaseContext()){ 
     @Override protected int getVerticalSnapPreference() { 
      return LinearSmoothScroller.SNAP_TO_START; 
     } 
    }; 
    smoothScroller.setTargetPosition(0); 
    layoutManager.startSmoothScroll(smoothScroller); 
}