recyclerView.setHasFixedSize方法什么时间设置为true 什么时间设置为false呢?
可以看下源码中关于这个方法的表明:
/** * RecyclerView can perform several optimizations if it can know in advance that RecyclerView's * size is not affected by the adapter contents. RecyclerView can still change its size based * on other factors (e.g. its parent's size) but this size calculation cannot depend on the * size of its children or contents of its adapter (except the number of items in the adapter). * <p> * If your use of RecyclerView falls into this category, set this to {@code true}. It will allow * RecyclerView to avoid invalidating the whole layout when its adapter contents change. * * @param hasFixedSize true if adapter changes cannot affect the size of the RecyclerView. */ public void setHasFixedSize(boolean hasFixedSize) { mHasFixedSize = hasFixedSize; }看上面的英文解释可以知道:
如果可以提前知道RecyclerView的巨细不受adapter内容的影响,那么可以做一些优化。RecyclerView可以由于一些其他的因素(好比它父结构的巨细)改变它自身的巨细,但是不依赖于它的子结构大概adapter内容的巨细。
如果利用RecyclerView属于上面所属的种别,那么可以设置为true。这将会答应RecyclerView当adapter内容改变时克制革新整个结构。
在从前的RecycleView的源码中是如许的:
void onItemsInsertedOrRemoved() { if (hasFixedSize) layoutChildren(); else requestLayout();}现在RecyclerView的源码中是如许的:
@Override protected void onMeasure(int widthSpec, int heightSpec) { if (mLayout == null) { defaultOnMeasure(widthSpec, heightSpec); return; } if (mLayout.isAutoMeasureEnabled()) { ....... 省略部门代码 } else { if (mHasFixedSize) { mLayout.onMeasure(mRecycler, mState, widthSpec, heightSpec); return; } // custom onMeasure ...... 省略部门代码 setMeasuredDimension(getMeasuredWidth(), getMeasuredHeight()); return; } if (mAdapter != null) { mState.mItemCount = mAdapter.getItemCount(); } else { mState.mItemCount = 0; } startInterceptRequestLayout(); mLayout.onMeasure(mRecycler, mState, widthSpec, heightSpec); stopInterceptRequestLayout(false); mState.mInPreLayout = false; // clear } }由上面内容可知:
setHasFixedSize 为 true,是为了更改 adapter的内容不会改变 它的View的高度和宽度,那么就可以设置为 true来克制不须要的 requestLayout
简单的说:
(1)如果我们利用固定的宽度/高度:
<android.support.v7.widget.RecyclerView android:id="@+id/my_recycler_view" android:layout_width="match_parent" android:layout_height="match_parent"/>可以用setHasFixedSize(true)
(2)如果我们不利用固定的宽度/高度:
<android.support.v7.widget.RecyclerView android:id="@+id/my_recycler_view" android:layout_width="match_parent" android:layout_height="wrap_content"/>应该利用setHasFixedSize(false),由于宽度或高度可以改变我们的巨细。
总之,当结构文件高度或宽度设置为固定值大概 match_parent时 ,可以设置 setHasFixedSize =true。 |