我明白外恕,很多讀者看到標(biāo)題后肯定都感到不屑,谷歌的兼容3.0以下的LinearLayoutCompat学少,以及3.0以上的LinearLayout不都已經(jīng)實(shí)現(xiàn)了帶有divider的功能了嗎星澳?但是當(dāng)你們真正用到的時(shí)候,你們發(fā)現(xiàn)真的如期望的那么好用嗎旱易?谷歌的倆控件禁偎,在你往線性布局里添加控件,或者隱藏某些控件等等的時(shí)候阀坏,后邊幾個(gè)divider的繪制的位置并不是期望的位置如暖。具體原因請(qǐng)參見這篇帖子:LinearLayout坑爹的showDividers屬性
好了,該控件的核心思想就是在控件dispatchDraw的過程中繪制分割線忌堂。支持是否畫divider盒至,以及是否畫頂部,中間以及底部divider。該控件支持代碼控制divider顯示方式枷遂,也支持xml控制divider顯示的方式樱衷。具體實(shí)現(xiàn)如下:
public class DividerLinearLayout extends LinearLayout {
private Paint paint;
private AttributeSet attrs;
private boolean drawDivider;
private boolean drawTop = true;
private boolean drawMiddle;
private boolean drawBottom = true;
private int dividerLeftMargin;
private int dividerRightMargin;
public DividerLinearLayout(Context context, @Nullable AttributeSet attrs) {
super(context, attrs);
this.attrs = attrs;
initPaint();
initView();
}
protected void initView() {
TypedArray ta = null;
try {
ta = getContext().obtainStyledAttributes(attrs, R.styleable.DividerView);
drawDivider = ta.getBoolean(R.styleable.DividerView_drawDivider, false);
drawaTop = ta.getBoolean(R.styleable.DividerView_drawTop, true);
drawMiddle = ta.getBoolean(R.styleable.DividerView_drawMiddle, false);
drawaBottom = ta.getBoolean(R.styleable.DividerView_drawBottom, true);
dividerLeftMargin = ta.getDimensionPixelSize(R.styleable.DividerView_dividerLeftMargin, 0);
dividerRightMargin = ta.getDimensionPixelSize(R.styleable.DividerView_dividerRightMargin, 0);
} finally {
if (null != ta) {
ta.recycle();
}
}
}
@SuppressWarnings("deprecation")
private void initPaint() {
paint = new Paint(Paint.ANTI_ALIAS_FLAG);
paint.setColor(getResources().getColor(R.color.color_dddddd));
paint.setStrokeWidth(1);
}
@Override
protected void dispatchDraw(Canvas canvas) {
super.dispatchDraw(canvas);
if (!drawDivider) return;
if (drawTop) {
canvas.drawLine(0, 0, getWidth(), 0, paint);
}
if (drawBottom) {
canvas.drawLine(0, getHeight() - 1, getWidth(), getHeight() - 1, paint);
}
if (drawMiddle) {
int height = 0;
for (int i = 0; i < getChildCount() - 1; i++) {
View child = getChildAt(i);
if (child.getVisibility() == GONE) continue;
if (child.getHeight() == 0) continue;
height += child.getHeight();
canvas.drawLine(dividerLeftMargin, height - 1, getWidth() - dividerRightMargin, height - 1, paint);
}
}
}
protected void setDrawDivider(boolean drawDivider) {
this.drawDivider = drawDivider;
}
public void setDrawTop(boolean drawTop) {
this.drawTop = drawTop;
}
public void setDrawMiddle(boolean drawMiddle) {
this.drawMiddle = drawMiddle;
}
public void setDrawBottom(boolean drawBottom) {
this.drawBottom = drawBottom;
}
public void setDividerLeftMargin(int dividerLeftMargin) {
this.dividerLeftMargin = dividerLeftMargin;
}
public void setDividerRightMargin(int dividerRightMargin) {
this.dividerRightMargin = dividerRightMargin;
}
}
整個(gè)代碼思想很簡(jiǎn)單。需要注意的是該控件的divider線的只是默認(rèn)的1像素#dddddd顏色的分割線酒唉,沒有做額外定制矩桂,有需要的可以做下額外定制。