6

Qualcuno ha escogitato un modo per ottenere informazioni sui riciclabili, AppbarLayouts e SwipeRefreshLayout per lavorare insieme ancora il 23.2? Sto usando un metodo piuttosto standard, penso, ma lo swiperefreshlayout continua a catturare il gesto di scorrimento quando si cerca di risalire il recyclerview.Recyclerviews e SwipeRefreshLayout utilizzando la libreria di supporto 23.2.0

<android.support.design.widget.CoordinatorLayout 
    android:layout_width="match_parent" 
    android:layout_height="wrap_content"> 

    <android.support.design.widget.AppBarLayout 
     android:id="@+id/appbar" 
     android:layout_width="match_parent" 
     android:layout_height="wrap_content"> 

     <android.support.v7.widget.Toolbar 
      android:id="@+id/toolbar" 
      android:layout_width="match_parent" 
      android:layout_height="wrap_content" 
      android:theme="?attr/toolbar_theme" 
      app:layout_scrollFlags="scroll|enterAlways" 
      android:elevation="4dp" /> 
    </android.support.design.widget.AppBarLayout> 
    <FrameLayout 
     android:id="@+id/fragment_container" 
     app:layout_behavior="@string/appbar_scrolling_view_behavior" 
     android:layout_width="match_parent" 
     android:layout_height="match_parent"> 
     <!--fragment goes here --> 
    </FrameLayout> 
</android.support.design.widget.CoordinatorLayout> 

con ciò che segue

<android.support.v4.widget.SwipeRefreshLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    xmlns:app="http://schemas.android.com/apk/res-auto" 
    android:id="@+id/swipe_container" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" 
    android:background="?attr/window_background"> 
<FrameLayout 
    android:layout_width="match_parent" 
    android:layout_height="match_parent"> 
    <ProgressBar 
     android:id="@+id/progress_bar" 
     android:layout_width="match_parent" 
     android:layout_height="wrap_content" 
     style="@style/Widget.AppCompat.ProgressBar.Horizontal" 
     android:layout_marginTop="-4dp" 
     android:layout_marginBottom="-8dp" 
     android:elevation="17dp" 
     android:indeterminate="true" 
     android:visibility="invisible" /> 

    <android.support.v7.widget.RecyclerView 
     android:id="@+id/recyclerview" 
     android:layout_width="match_parent" 
     android:layout_height="match_parent" 
     android:scrollbars="vertical" /> 
</FrameLayout> 
</android.support.v4.widget.SwipeRefreshLayout> 

risposta

6

attrs.xml

<?xml version="1.0" encoding="utf-8"?> 
<resources> 
    <declare-styleable name="ImprovedSwipeLayoutAttrs"> 
     <attr name="scrollableChildId" format="reference" /> 
    </declare-styleable> 
</resources> 

layout.xml

<in.nerd_is.inactive_weibo.ui.ImprovedSwipeLayout 
    xmlns:android="http://schemas.android.com/apk/res/android" 
    xmlns:tools="http://schemas.android.com/tools" 
    xmlns:fab="http://schemas.android.com/apk/res-auto" 
    xmlns:isl="http://schemas.android.com/apk/res-auto" 
    android:id="@+id/swipe_container" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" 
    android:background="@color/md_blue_grey_50" 
    isl:scrollableChildId="@+id/list_statuses" 
    tools:context="in.nerd_is.inactive_weibo.ui.StatusesFragment" > 

    <FrameLayout 
     android:layout_width="match_parent" 
     android:layout_height="match_parent"> 

     <ListView 
      android:id="@+id/list_statuses" 
      android:minHeight="?android:attr/listPreferredItemHeight" 
      android:layout_width="match_parent" 
      android:layout_height="match_parent" 
      android:paddingTop="12dp" 
      android:paddingBottom="12dp" 
      android:paddingLeft="8dp" 
      android:paddingRight="8dp" 
      android:clipToPadding="false" 
      android:divider="@android:color/transparent" 
      android:dividerHeight="12dp"/> 

     <com.melnykov.fab.FloatingActionButton 
      android:id="@+id/button_floating_action" 
      android:layout_width="wrap_content" 
      android:layout_height="wrap_content" 
      android:layout_gravity="bottom|right" 
      android:layout_margin="16dp" 
      android:src="@drawable/ic_md_create" 
      fab:fab_colorNormal="@color/md_blue_400" 
      fab:fab_colorPressed="@color/md_blue_grey_500"/> 
    </FrameLayout> 

</in.nerd_is.inactive_weibo.ui.ImprovedSwipeLayout> 

ImprovedSwipeLayout.java

0.123,51641 milioni
public class ImprovedSwipeLayout extends SwipeRefreshLayout { 

    private static final String TAG = ImprovedSwipeLayout.class.getCanonicalName(); 
    private int mScrollableChildId; 
    private View mScrollableChild; 

    public ImprovedSwipeLayout(Context context) { 
     this(context, null); 
    } 

    public ImprovedSwipeLayout(Context context, AttributeSet attrs) { 
     super(context, attrs); 

     TypedArray a = context.obtainStyledAttributes(
       attrs, R.styleable.ImprovedSwipeLayoutAttrs); 
     mScrollableChildId = a.getResourceId(R.styleable.ImprovedSwipeLayoutAttrs_scrollableChildId, 0); 
     mScrollableChild = findViewById(mScrollableChildId); 
     a.recycle(); 
    } 

    @Override 
    public boolean canChildScrollUp() { 
     ensureScrollableChild(); 

     if (android.os.Build.VERSION.SDK_INT < 14) { 
      if (mScrollableChild instanceof AbsListView) { 
       final AbsListView absListView = (AbsListView) mScrollableChild; 
       return absListView.getChildCount() > 0 
         && (absListView.getFirstVisiblePosition() > 0 || absListView.getChildAt(0) 
         .getTop() < absListView.getPaddingTop()); 
      } else { 
       return mScrollableChild.getScrollY() > 0; 
      } 
     } else { 
      return ViewCompat.canScrollVertically(mScrollableChild, -1); 
     } 
    } 

    private void ensureScrollableChild() { 
     if (mScrollableChild == null) { 
      mScrollableChild = findViewById(mScrollableChildId); 
     } 
    } 

} 

E 'da http://nerd-is.in/2014-09/add-multi-child-view-in-swiperefreshlayout/

Crea una vista estendere SwipeRefreshLayout e canChildScrollUp personalizzato.

2

Di fronte allo stesso issue dopo l'aggiornamento a 23.2.0. È un bug vecchio-nuovo che è stato corretto in 23.1.1 e viene nuovamente visualizzato in 23.2.0.

Nel mio caso, effettuo il downgrade a 23.1.1 e everithing è di nuovo OK. Quindi dovremmo aspettare una nuova versione di libs o usare workarounds ignorando SwipeRefreshLayout.


Ecco link per google bugtracker: RecyclerView v23.2.0 - doesn't play nicely with SwipeRefreshLayout

5

Se si mette una visualizzazione che non implementa ScrollingView o non è un AbsListView in SwipeRefreshLayout, SwipeRefreshLayout#canChildScrollUp() restituisce sempre false.

Quindi, utilizzando un FrameLayout all'interno di SwipeRefreshLayout si hanno due problemi:

  1. SwipeRefreshLayout non accetti le operazioni di scorrimento nidificato di vista discendente (vedi SwipeRefreshLayout#onStartNestedScroll(View, View, int)). Ciò causa i problemi con CoordinatorLayout/AppBarLayout.

  2. Il SwipeRefreshLayout gestisce tocco si eventi a patto che il suo bambino non può scorrere verso l'alto o non c'è scorrimento nidificato in corso (vedi SwipeRefreshLayout#onInterceptTouchEvent(MotionEvent) e SwipeRefreshLayout#onTouchEvent(MotionEvent)). Ciò significa che lo spinner viene visualizzato quando "tocca verso il basso".

È possibile risolvere questo problema utilizzando il proprio SwipeRefreshLayout, che sovrascrive SwipeRefreshLayout#onStartNestedScroll(View, View, int). In questo modo i nidificato pergamene sono accettate anche se la vista diretta bambino non può scorrere verso l'alto:

public class SwipeRefreshLayout extends android.support.v4.widget.SwipeRefreshLayout { 

    public SwipeRefreshLayout(Context context) { 
     super(context); 
    } 

    public SwipeRefreshLayout(Context context, AttributeSet attrs) { 
     super(context, attrs); 
    } 

    @Override 
    public boolean onStartNestedScroll(View child, View target, int nestedScrollAxes) { 
     return isEnabled() 
       && !isRefreshing() 
       && (nestedScrollAxes & ViewCompat.SCROLL_AXIS_VERTICAL) != 0; 
    } 
} 

BTW se si guarda al codice SwipeRefreshLayout s' in 23.1.1 si vedrà, che il controllo canChildScrollUp() è stato rimosso ma è stato aggiunto di nuovo in 23.2.0.Ho anche rimosso il controllo per !mReturningToStart, perché è sempre false.

+0

Non è più necessario applicare questa soluzione alternativa, poiché ciò è corretto in 23.3.0. – segoh

Problemi correlati