zoukankan      html  css  js  c++  java
  • android控件RecyclerView中,如何显示自定义分割线以及最后一项去除分割线

    在控件RecyclerView中,分割线DividerItemDecoration类的使用经常见,如果是使用自带的分割线,只需要这样写即可

       RecyclerView mRecyclerView;
     mRecyclerView.addItemDecoration(new DividerItemDecoration(this, DividerItemDecoration.VERTICAL));

    会出现一条1pd的灰色的分割线,但是我如果想自己写自定义的分割线呢,这个时候需要我们自定义一个shape,在里面进行自定义样式然后进行引用

    代码如下:divider.xml

    <?xml version="1.0" encoding="utf-8"?>
    <shape xmlns:android="http://schemas.android.com/apk/res/android"
        android:shape="rectangle">
        <solid android:color="#CB8589" />
        <size android:height="15dp" />
    </shape>

    那我怎么在我的java里面用呢,代码如下:

            //添加自定义的分割线
          DividerItemDecoration divider = new DividerItemDecoration(this, DividerItemDecoration.VERTICAL);
         divider.setDrawable(ContextCompat.getDrawable(this, R.drawable.divider));
         mRecyclerView.addItemDecoration(divider);

    如此,我的模拟器上就出现了又粗又红的分割线

    但是这个时候又有问题,我每个子项都有,那么我如果想最后一个不要分割线呢,这个时候,我打开了DividerItemDecoration类的源码,发现了循环的地方

     我只需要把这个地方减1,那么我不就可以删去最后一个子项的分割线了吗,显然,改源码是很不合理的,于是,我新建一个GridItemDecoration的类,修改如下:

    GridItemDecoration.java
    //
    // Source code recreated from a .class file by IntelliJ IDEA
    // (powered by Fernflower decompiler)
    //
    
    package com.example.administrator.myapplication;
    
    import android.content.Context;
    import android.content.res.TypedArray;
    import android.graphics.Canvas;
    import android.graphics.Rect;
    import android.graphics.drawable.Drawable;
    import android.support.annotation.NonNull;
    import android.support.v7.widget.RecyclerView;
    import android.support.v7.widget.RecyclerView.ItemDecoration;
    import android.support.v7.widget.RecyclerView.State;
    import android.util.Log;
    import android.view.View;
    
    public class GridItemDecoration extends ItemDecoration {
        public static final int HORIZONTAL = 0;
        public static final int VERTICAL = 1;
        private static final String TAG = "DividerItem";
        private static final int[] ATTRS = new int[]{16843284};
        private Drawable mDivider;
        private int mOrientation;
        private final Rect mBounds = new Rect();
    
        public GridItemDecoration(Context context, int orientation) {
            TypedArray a = context.obtainStyledAttributes(ATTRS);
            this.mDivider = a.getDrawable(0);
            if (this.mDivider == null) {
                Log.w("DividerItem", "@android:attr/listDivider was not set in the theme used for this DividerItemDecoration. Please set that attribute all call setDrawable()");
            }
    
            a.recycle();
            this.setOrientation(orientation);
        }
    
        public void setOrientation(int orientation) {
            if (orientation != 0 && orientation != 1) {
                throw new IllegalArgumentException("Invalid orientation. It should be either HORIZONTAL or VERTICAL");
            } else {
                this.mOrientation = orientation;
            }
        }
    
        public void setDrawable(@NonNull Drawable drawable) {
            if (drawable == null) {
                throw new IllegalArgumentException("Drawable cannot be null.");
            } else {
                this.mDivider = drawable;
            }
        }
    
        public void onDraw(Canvas c, RecyclerView parent, State state) {
            if (parent.getLayoutManager() != null && this.mDivider != null) {
                if (this.mOrientation == 1) {
                    this.drawVertical(c, parent);
                } else {
                    this.drawHorizontal(c, parent);
                }
    
            }
        }
    
        private void drawVertical(Canvas canvas, RecyclerView parent) {
            canvas.save();
            int left;
            int right;
            if (parent.getClipToPadding()) {
                left = parent.getPaddingLeft();
                right = parent.getWidth() - parent.getPaddingRight();
                canvas.clipRect(left, parent.getPaddingTop(), right, parent.getHeight() - parent.getPaddingBottom());
            } else {
                left = 0;
                right = parent.getWidth();
            }
    
            int childCount = parent.getChildCount();
    
            //当最后一个子项的时候去除下划线
            for (int i = 0; i < childCount - 1; ++i) {
                View child = parent.getChildAt(i);
                parent.getDecoratedBoundsWithMargins(child, this.mBounds);
                int bottom = this.mBounds.bottom + Math.round(child.getTranslationY());
                int top = bottom - this.mDivider.getIntrinsicHeight();
                this.mDivider.setBounds(left, top, right, bottom);
                this.mDivider.draw(canvas);
            }
    
            canvas.restore();
        }
    
        private void drawHorizontal(Canvas canvas, RecyclerView parent) {
            canvas.save();
            int top;
            int bottom;
            if (parent.getClipToPadding()) {
                top = parent.getPaddingTop();
                bottom = parent.getHeight() - parent.getPaddingBottom();
                canvas.clipRect(parent.getPaddingLeft(), top, parent.getWidth() - parent.getPaddingRight(), bottom);
            } else {
                top = 0;
                bottom = parent.getHeight();
            }
    
            int childCount = parent.getChildCount();
    
            for (int i = 0; i < childCount; ++i) {
                View child = parent.getChildAt(i);
                parent.getLayoutManager().getDecoratedBoundsWithMargins(child, this.mBounds);
                int right = this.mBounds.right + Math.round(child.getTranslationX());
                int left = right - this.mDivider.getIntrinsicWidth();
                this.mDivider.setBounds(left, top, right, bottom);
                this.mDivider.draw(canvas);
            }
    
            canvas.restore();
        }
    
        public void getItemOffsets(Rect outRect, View view, RecyclerView parent, State state) {
            if (this.mDivider == null) {
                outRect.set(0, 0, 0, 0);
            } else {
                if (this.mOrientation == 1) {
                    outRect.set(0, 0, 0, this.mDivider.getIntrinsicHeight());
                } else {
                    outRect.set(0, 0, this.mDivider.getIntrinsicWidth(), 0);
                }
    
            }
        }
    }

    如此,我在activity里面把这个类引进就可以:

      //最后一个不显示分割线且自定义分割线
            GridItemDecoration gridItemDecoration = new GridItemDecoration(this, DividerItemDecoration.VERTICAL);
            gridItemDecoration.setDrawable(ContextCompat.getDrawable(this, R.drawable.divider));
            mRecyclerView.addItemDecoration(gridItemDecoration);

    完整代码如下:

    package com.example.administrator.myapplication;
    
    import android.content.ContextWrapper;
    import android.graphics.Paint;
    import android.os.Bundle;
    import android.support.v4.content.ContextCompat;
    import android.support.v7.app.AppCompatActivity;
    import android.support.v7.widget.GridLayoutManager;
    import android.support.v7.widget.LinearLayoutManager;
    import android.support.v7.widget.DividerItemDecoration;
    import android.support.v7.widget.RecyclerView;
    
    
    import java.util.List;
    import java.util.ArrayList;
    
    public class BodyActivity extends AppCompatActivity {
        RecyclerView mRecyclerView;
        public Paint paint;
    
        @Override
        protected void onCreate(Bundle saveInstanceState) {
            super.onCreate(saveInstanceState);
            setContentView(R.layout.activity_body);
            //1.获取控件
            mRecyclerView = (RecyclerView) findViewById(R.id.recycler_view);
    
            //设置布局方式
            mRecyclerView.setLayoutManager(new LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false));//线性布局
    //        mRecyclerView.setLayoutManager(new GridLayoutManager(this,2));//网格布局
            mRecyclerView.setHasFixedSize(true); //是否重新计算大小
    
            //3.准备数据
            List<News> newsList = new ArrayList<>();
            News news;
            for (int i = 1; i <= 20; i++) {
                news = new News();
                news.setNewsTitle("java是世界上最好的语言" + i);
                news.setNewsSource("新华网" + i);
                news.setPublishTime("2018-8-6");
                newsList.add(news);
            }
    
    
            //添加Android自带的分割线
    //    mRecyclerView.addItemDecoration(new DividerItemDecoration(this, DividerItemDecoration.VERTICAL));
    
    
            //添加自定义的分割线
    //        DividerItemDecoration divider = new DividerItemDecoration(this, DividerItemDecoration.VERTICAL);
    //        divider.setDrawable(ContextCompat.getDrawable(this, R.drawable.divider));
    //        mRecyclerView.addItemDecoration(divider);
    
            //最后一个不显示分割线且自定义分割线
            GridItemDecoration gridItemDecoration = new GridItemDecoration(this, DividerItemDecoration.VERTICAL);
            gridItemDecoration.setDrawable(ContextCompat.getDrawable(this, R.drawable.divider));
            mRecyclerView.addItemDecoration(gridItemDecoration);
    
    
            //4.准备适配器
            NewsAdapter newsAdapter = new NewsAdapter(newsList);
            mRecyclerView.setAdapter(newsAdapter);
    
    
        }
    }
  • 相关阅读:
    MOSS 2013研究系列动态修改WebConfig(上) 欧阳锋
    MOSS 2013研究系列MOSS 2013安装篇 欧阳锋
    GPIO
    [转]vi/vim使用进阶: 在VIM中使用GDB调试 – 使用pyclewn
    建立openwrt虚拟环境
    ebtables基本使用
    LFS小记
    Autoconf & Automake使用小记
    Packet Filter小记
    Web技术整理
  • 原文地址:https://www.cnblogs.com/mmykdbc/p/10636044.html
Copyright © 2011-2022 走看看