Recyclerview 实现流式布局

没有多余废话直接上代码

1.布局中添加recyclerview

<androidx.recyclerview.widget.RecyclerView
                android:id="@+id/feekbacktab_rv"
                android:layout_width="match_parent"
                android:layout_height="wrap_content">
            </androidx.recyclerview.widget.RecyclerView>

2.添加适配器,大体思路放出来,细节自己改

(框架不一样,适配器写法不一样)

<RelativeLayout//适配器布局
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content">
    <TextView
        android:id="@+id/itemtab"
        android:layout_marginLeft="@dimen/dp_8"
        android:layout_marginTop="@dimen/dp_10"
        android:paddingRight="@dimen/dp_14"
        android:paddingLeft="@dimen/dp_14"
        android:gravity="center"
        android:textColor="@color/color_999999"
        android:textSize="@dimen/dp_13"
        android:text="班主任服务"
        android:background="@drawable/feekbacktab_seletor"
        android:layout_width="wrap_content"
        android:layout_height="@dimen/dp_30">
    </TextView>
</RelativeLayout>
public class LabelAdapter extends BaseRecyclerViewAdapter<LabelBean> {

    public LabelAdapter(Context mContext, int mLayout) {
        super(mContext, mLayout);

    }

    @SuppressLint("ResourceAsColor")
    @Override
    public void onBindChildViewHolder(RecyclerView.ViewHolder viewHolder, int position, LabelBean mItemData) {

        TextView name=viewHolder.itemView.findViewById(R.id.itemtab);
        name.setText(mItemData.getName());
        name.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                if (iChildItemClick!=null){
                    iChildItemClick.isChildItemClick(v,position);
                }
            }
        });
        if (position == getmPosition()) {
            name.setBackgroundResource(R.drawable.bg_15r517bff_shape);
            name.setTextColor(Color.WHITE);
        }else{
            name.setTextColor(R.color.color_999999);
            name.setBackgroundResource(R.drawable.bg_15rf4f4f8_shape);
        }

    }

    private IChildItemClick iChildItemClick;

    public void setiChildItemClick(IChildItemClick iChildItemClick) {
        this.iChildItemClick = iChildItemClick;
    }

    public interface IChildItemClick {
        void isChildItemClick(View view, int position);
    }
    private  int mPosition;

    public int getmPosition() {
        return mPosition;
    }

    public void setmPosition(int mPosition) {
        this.mPosition = mPosition;
    }

适配器通过接口回调实现子条目的状态改变

3.适配器创建和绑定流式布局

提供大体思路自行修改

labelAdapter=new LabelAdapter(this,R.layout.adapter_label);
        labelAdapter.setList(list);//为适配器添加数据
        labelAdapter.notifyDataSetChanged();//刷新适配器
        AutoLineFeedLayoutManager manager=new AutoLineFeedLayoutManager();//流式布局
        label.setLayoutManager(manager);//为recyclerview绑定布局  label为recyclerview
        label.setAdapter(labelAdapter);//recyclerview绑定适配器
        labelAdapter.setiChildItemClick(new LabelAdapter.IChildItemClick() {
            @Override
            public void isChildItemClick(View view, int position) {
                labelAdapter.setmPosition(position);//接口回调查看当前点击是否和上一次点击相同,达到改变子条目状态的效果
                labelAdapter.notifyDataSetChanged();
                }
        });

附加AutoLineFeedLayoutManager代码

public class AutoLineFeedLayoutManager extends RecyclerView.LayoutManager {

    public AutoLineFeedLayoutManager() {
        setAutoMeasureEnabled(true);//layoutmanager必须调用此方法设为true才能在onMesure时自动布局
    }

    @Override
    public RecyclerView.LayoutParams generateDefaultLayoutParams() {
        return new RecyclerView.LayoutParams(
                RecyclerView.LayoutParams.WRAP_CONTENT,
                RecyclerView.LayoutParams.WRAP_CONTENT);
    }

    @Override
    public void onLayoutChildren(RecyclerView.Recycler recycler, RecyclerView.State state) {
        detachAndScrapAttachedViews(recycler);

        int curLineWidth = 0, curLineTop = 0;//curLineWidth 累加item布局时的x轴偏移curLineTop 累加item布局时的x轴偏移
        int lastLineMaxHeight = 0;
        for (int i = 0; i < getItemCount(); i++) {
            View view = recycler.getViewForPosition(i);
            //获取每个item的布局参数,计算每个item的占用位置时需要加上margin
            RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) view.getLayoutParams();

            addView(view);
            measureChildWithMargins(view, 0, 0);
            int width = getDecoratedMeasuredWidth(view) + params.leftMargin + params.rightMargin;
            int height = getDecoratedMeasuredHeight(view) + params.topMargin + params.bottomMargin;

            curLineWidth += width;//累加当前行已有item的宽度
            if (curLineWidth <= getWidth()) {//如果累加的宽度小于等于RecyclerView的宽度,不需要换行
                layoutDecorated(view, curLineWidth - width + params.leftMargin, curLineTop + params.topMargin, curLineWidth - params.rightMargin, curLineTop + height - params.bottomMargin);//布局item的真实位置
                //比较当前行多有item的最大高度,用于换行后计算item在y轴上的偏移量
                lastLineMaxHeight = Math.max(lastLineMaxHeight, height);
            } else {//换行
                curLineWidth = width;
                if (lastLineMaxHeight == 0) {
                    lastLineMaxHeight = height;
                }
                //记录当前行top
                curLineTop += lastLineMaxHeight;

                layoutDecorated(view, params.leftMargin, curLineTop + params.topMargin, width - params.rightMargin, curLineTop + height - params.bottomMargin);
                lastLineMaxHeight = height;
            }
        }
    }
}
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容