1. 程式人生 > >自定義view,繪製階段進度progressBar,階段與圖片和文字對齊

自定義view,繪製階段進度progressBar,階段與圖片和文字對齊

 

沒用seekbar或者progressbar原生控制元件,通過繪製實現。只講下有用的思想,無關屬性不解釋,也不用看。

主要看onDraw方法程式碼:

繪製背景線,canvas.drawRect線繪製了第一條線,因為需要漸變,可以看到canvas.drawPath是從第一條線之後開始算left的,ringht包含整個進度條的長度。

 // 背景線
        if (mNodeIndex != mNodeNum - 1) {

            LinearGradient gradient = new LinearGradient(0, 0, mGap,
                    0, Color.WHITE, mContext.getResources().getColor(R.color.color_E5E5E5), Shader.TileMode.CLAMP);
            Paint paint = new Paint();
            paint.setShader(gradient);
            canvas.drawRect(paddingLeft, (getHeight() - mLineWidth) / 2, mStartX + mGap, (getHeight() + mLineWidth) / 2, paint);

            mNormalPath.addRect(mStartX + mGap, (getHeight() - mLineWidth) / 2, endX - mGap, (getHeight() + mLineWidth) / 2, Path.Direction.CCW);
            canvas.drawPath(mNormalPath, mNormalPaint);
        }

然後迴圈繪製圓球蓋在對應的位置

// 背景節點
        for (int i = 0; i < mNodeNum; i++) {
            if (i <= mNodeIndex) {
                continue;
            }
            if (i != 0 && i != mNodeNum - 1) {
                canvas.drawCircle(mStartX + (mGap * i), getHeight() / 2, mNormalNodeRadius, mNormalCirclePaint);
            }
        }

再繪製進度的線,也是第一條線的長度漸變

 // 選中線
        if (mNodeIndex > 0 && mNodeIndex != mNodeNum - 1) {

            LinearGradient gradient = new LinearGradient(0, 0, mGap,
                    0, Color.WHITE, mContext.getResources().getColor(R.color.color_FD5344),         Shader.TileMode.CLAMP);
            Paint paint = new Paint();
            paint.setShader(gradient);
            canvas.drawRect(paddingLeft, (getHeight() - mLineWidth) / 2, mStartX + mGap, (getHeight() + mLineWidth) / 2, paint);
            mSelectedPath.addRect(mStartX + mGap, (getHeight() - mLineWidth) / 2, mStartX + mGap * mNodeIndex, (getHeight() + mLineWidth) / 2, Path.Direction.CCW);
        }

 最後繪製選中的,也就是進度顏色的圓圈。

 // 選中節點
        for (int i = 0; i <= mNodeIndex; i++) {
            if (i != 0 && i != mNodeNum - 1)
                mSelectedPath.addCircle(mStartX + mGap * i, getHeight() / 2, mSelectedNodeRadius, Path.Direction.CCW);
        }
canvas.drawPath(mSelectedPath, mSelectedPaint);

 

 

然後是怎麼讓上下的圖片和文字與對應階段的圓圈居中對齊:


    public void alignmentPosition(View view, int width, int height, int i) {
        RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(width, height);
        params.leftMargin = mStartX + mGap * i - view.getMeasuredWidth() / 2;
        params.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM, RelativeLayout.TRUE);
        view.setLayoutParams(params);
    }

    public void alignmentPositionTextView(View view, int i) {
        RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        params.leftMargin = mStartX + mGap * i - view.getMeasuredWidth() / 2;
        view.setLayoutParams(params);
    }

圖片是通過第一個方法,textview通過的第二個方法。將view傳進來,然後按照繪製時候的addCirle計算left的方式,對view設定LayoutParams指定marginleft減去view本身寬度的一半即可居中對齊進度條中的圓圈。

 

沒啥可說的,似乎都是基礎,希望對你有可以借鑑的地方。