日常的开发中经常会需要用到自定义View,这次刚好有个需求,需要用到带有节点的进度条。东西很简单直接继承View就行了。

首先定义一些需要的属性
/**     * 背景画笔     */    private Paint bgPaint;    /**     * 前景画笔     */    private Paint forePaint;    /**     * 选中画笔     */    private Paint selectPaint;    /**     * 未选中画笔     */    private Paint unselectPaint;    /**     * 背景颜色     */    private int bgColor = Color.parseColor("#9C9C9C");    /**     * 前景颜色     */    private int foreColor = Color.parseColor("#8A2BE2");    /**     * 默认高度     */    private int defaultHeight;    /**     * 节点文字     */    private List nodeList;    private List mBounds;    /**     * 节点圆的半径     */    private int radius;    /**     * 文字和节点进度条的top     */    private int marginTop;    /**     * 两个节点之间的距离     */    private int dividWidth;    /**     * 选中位置     */    private int selectIndex;
然后在构造方法中初始化这些数据
private void init(Context context) {        radius = SizeUtils.dp2px(context,4);        defaultHeight = SizeUtils.dp2px(context,30);        marginTop = SizeUtils.dp2px(context,5);        bgPaint = new Paint(Paint.ANTI_ALIAS_FLAG);        bgPaint.setColor(bgColor);        bgPaint.setStyle(Paint.Style.FILL);        forePaint = new Paint(Paint.ANTI_ALIAS_FLAG);        forePaint.setColor(foreColor);        forePaint.setStyle(Paint.Style.FILL);        unselectPaint = new Paint(Paint.ANTI_ALIAS_FLAG);        unselectPaint.setColor(bgColor);        unselectPaint.setTextSize(SizeUtils.sp2px(context,10));        selectPaint = new Paint(Paint.ANTI_ALIAS_FLAG);        selectPaint.setColor(foreColor);        selectPaint.setTextSize(SizeUtils.sp2px(context,10));    }
设置节点文字
/**     * 设置数据     * @param nodeDatas     */    public void setNodeList(List nodeDatas){        if(nodeDatas != null){            nodeList = nodeDatas;        }        //测量文字所占用的空间        measureText();    }    /**     * 设置选中位置     * @param selectIndex     */    public void setSelectIndex(int selectIndex){        this.selectIndex = selectIndex;        invalidate();    }/**     * 测量文字的长宽     */    private void measureText(){        mBounds = new ArrayList<>();        for (int i = 0; i < nodeList.size(); i++) {            Rect mBound = new Rect();            unselectPaint.getTextBounds(nodeList.get(i),0,nodeList.get(i).length(),mBound);            mBounds.add(mBound);        }    }
最后重要的步骤,开始在onDraw中绘制节点进度条和绘制文字

1、绘制灰色背景线条

if(nodeList == null || nodeList.isEmpty()){            return;        }        bgPaint.setStrokeWidth(radius/2);        //绘制灰色的背景线条        canvas.drawLine(radius,radius,getWidth()-radius,radius,bgPaint);

2、绘制节点上的圆和两个节点之间的间隔线条

//画节点圆        //每个圆相隔的距离        dividWidth = (getWidth()-radius*2)/(nodeList.size() - 1);        forePaint.setStrokeWidth(radius/2);        for (int i = 0; i < nodeList.size(); i++) {            if(i == selectIndex){                for (int j = 0; j <= i; j++) {                    canvas.drawCircle(radius+ j * dividWidth, radius, radius , forePaint);                    canvas.drawLine(radius,radius,j*dividWidth,radius,forePaint);                }            }else if(i>selectIndex){                canvas.drawCircle(radius + i * dividWidth, radius, radius, bgPaint);            }        }

3、绘制节点上的文字

for (int i = 0; i < nodeList.size(); i++) {            int currentTextWidth=mBounds.get(i).width();            if (i==0){                if (i==selectIndex){                    canvas.drawText(nodeList.get(i), 0, radius*2 + marginTop + mBounds.get(i).height()/2, selectPaint);                }else if(i>selectIndex) {                    canvas.drawText(nodeList.get(i), 0, radius*2 + marginTop + mBounds.get(i).height()/2, unselectPaint);                }            }else if (i==nodeList.size()-1){                if (i==selectIndex){                    for (int j = 0; j <= i; j++) {                        if(j == 0){                            canvas.drawText(nodeList.get(j), 0, radius*2 + marginTop + mBounds.get(j).height()/2, selectPaint);                        }else if(j == i){                            canvas.drawText(nodeList.get(j), getWidth() - currentTextWidth, radius*2 + marginTop + mBounds.get(j).height()/2, selectPaint);                        }else{                            canvas.drawText(nodeList.get(j), radius + j * dividWidth - currentTextWidth / 2, radius*2 + marginTop + mBounds.get(j).height()/2, selectPaint);                        }                    }                }else if(i>selectIndex) {                    canvas.drawText(nodeList.get(i), getWidth() - currentTextWidth, radius*2 + marginTop + mBounds.get(i).height()/2, unselectPaint);                }            }else {                if (i==selectIndex){                    for (int j = 0; j <= i; j++) {                        if(j>0){                            canvas.drawText(nodeList.get(j), radius + j * dividWidth - currentTextWidth / 2, radius*2 + marginTop + mBounds.get(j).height()/2, selectPaint);                        }else{                            canvas.drawText(nodeList.get(j), 0, radius*2 + marginTop + mBounds.get(j).height()/2, selectPaint);                        }                    }                }else if(i>selectIndex) {                    canvas.drawText(nodeList.get(i), radius + i * dividWidth - currentTextWidth / 2, radius*2 + marginTop + mBounds.get(i).height()/2, unselectPaint);                }            }        }

有时候可能需要的是下面这种进度条

只需要修改onDraw中绘制节点圆和文字的方法就可以了
for (int i=0; i < nodeList.size();i++) {            if (i==selectIndex){                canvas.drawCircle(radius+ i * dividWidth, radius, radius , forePaint);            }else {                canvas.drawCircle(radius + i * dividWidth, radius, radius, bgPaint);            }        }        for (int i=0; i

点击节点进行节点切换

// 实现节点切换,把注释打开就行了@Override    public boolean onTouchEvent(MotionEvent event) {        float eventX;        float eventY;        int i = event.getAction();        if (i == MotionEvent.ACTION_DOWN) {        } else if (i == MotionEvent.ACTION_MOVE) {        } else if (i == MotionEvent.ACTION_UP) {            eventX = event.getX();            eventY = event.getY();            //计算选中的index            float select = eventX / dividWidth;            float xs = select - (int) (select);            //selectIndex = (int) select + (xs > 0.5 ? 1 : 0);        }        //invalidate();        return true;    }

更多相关文章

  1. [Android]JNI进阶--问题集
  2. android 给图片加文字、图片水印
  3. Android布局绘制常见小问题
  4. 语音识别为文字
  5. android 绘制文本居中
  6. XML的解析中的三种方法
  7. Android(安卓)Canvas绘图详解
  8. MPAndroidChart常见设置属性(一)——应用层
  9. Android(安卓)实现文字按照路径曲线显示

随机推荐

  1. Android详细教程 - 基础篇完成了
  2. android软键盘弹出,会把原来的界面挤上去
  3. Android(安卓)内核相关内容总结
  4. android webkit学习笔记1---url的load过
  5. android 多点
  6. Android实现内录
  7. Android ListView优化之getView频繁多次
  8. Android程序优化之对屏幕旋转的处理总结
  9. [置顶] Android 网络连接--Wifi/3G
  10. android软键盘弹出引起的各种不适终极解