美文网首页
简单进度条

简单进度条

作者: 淹死丶的鱼 | 来源:发表于2019-12-11 17:11 被阅读0次

import android.content.Context
import android.graphics.Canvas
import android.graphics.Paint
import android.graphics.Rect
import android.graphics.RectF
import android.util.AttributeSet
import android.util.TypedValue
import android.view.View
/**
 *created by 淹死的鱼 on 2019/12/11
 */
class ProgressBar @JvmOverloads constructor(
    context: Context,
    attSet: AttributeSet? = null,
    defStyleAttr: Int = 0
) : View(context, attSet, defStyleAttr) {
    private var proTextColor = 0
    private var selectColor = 0
    private var unSelectColor = 0
    private var borderWidth = 3f
    private var proTextSize = 15
    private var orientation = 1
    private var maxProgress = 100
    private var currentProgress = 0
    //外圈画笔
    private val unSelectPaint: Paint
    //内圈画笔
    private val selectPaint: Paint
    private val textPaint: Paint
    var text = ""

    init {
        val typedArray = context.obtainStyledAttributes(attSet, R.styleable.ProgressBar)
        proTextColor = typedArray.getColor(R.styleable.ProgressBar_proTextColor, proTextColor)
        selectColor = typedArray.getColor(R.styleable.ProgressBar_proInnerColor, selectColor)
        unSelectColor = typedArray.getColor(R.styleable.ProgressBar_proOutColor, unSelectColor)
        borderWidth = typedArray.getDimension(R.styleable.ProgressBar_proBorderWidth, dip2px(borderWidth.toInt()))
        proTextSize = typedArray.getDimensionPixelSize(R.styleable.ProgressBar_proTextSize, sp2px(proTextSize.toFloat()))
        orientation = typedArray.getInt(R.styleable.ProgressBar_proOrientation, orientation)
        maxProgress = typedArray.getInt(R.styleable.ProgressBar_maxProgress, maxProgress)
        typedArray.recycle()
        unSelectPaint = getPaint(unSelectColor)
        selectPaint = getPaint(selectColor)
        textPaint = Paint()
        textPaint.color = proTextColor
        textPaint.isAntiAlias = true
        textPaint.textSize = proTextSize.toFloat()
    }

    private fun getPaint(color: Int) = Paint().apply {
        this.color = color
        this.isAntiAlias = true
        this.isDither = true
        strokeWidth = borderWidth
        style = Paint.Style.STROKE
    }

    private fun sp2px(sp: Float): Int {//不建议用这样的方式转单位
        return TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP, sp, resources.displayMetrics).toInt()
    }

    private fun dip2px(dip: Int): Float {//不建议用这样的方式转单位
        return TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dip.toFloat(), resources.displayMetrics)
    }

    override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec)
        val width = MeasureSpec.getSize(widthMeasureSpec)
        val height = MeasureSpec.getSize(heightMeasureSpec)
        if (orientation == 2) {
            setMeasuredDimension(if (width > height) height else width, if (width > height) height else width)
        } else {
            if (MeasureSpec.getMode(heightMeasureSpec) == MeasureSpec.AT_MOST) {
                if (borderWidth <= 0) {
                    setMeasuredDimension(width, dip2px(20).toInt())
                } else {
                    setMeasuredDimension(width, borderWidth.toInt())
                }
            } else {
                unSelectPaint.strokeWidth = height.toFloat()
                selectPaint.strokeWidth = height.toFloat()
                setMeasuredDimension(width, height)
            }
        }
        val center = width / 2f
        val radius = width / 2 - borderWidth / 2
        rectF.set(center - radius, center - radius, center + radius, center + radius)
    }

    private val rect = Rect()
    private var rectF = RectF()
    override fun onDraw(canvas: Canvas) {
        textPaint.getTextBounds(text, 0, text.length, rect)
        val metricsInt = textPaint.fontMetricsInt
        val dy = (metricsInt.bottom - metricsInt.top) / 2 - metricsInt.bottom
        val baseLine = height / 2f + dy
        //1画圆
        if (orientation == 2) {
            //画外圆
            canvas.drawCircle(width / 2f, height / 2f, width / 2 - borderWidth / 2, unSelectPaint)
            //画进度
            canvas.drawArc(rectF, 90f, (currentProgress.toFloat() / maxProgress) * 360, false, selectPaint)
            //画文字
            canvas.drawText(text, width / 2 - rect.width() / 2f, baseLine, textPaint)
        } else {
            val y = height / 2f
            //画总长渡
            canvas.drawLine(0f, y, width.toFloat(), y, unSelectPaint)
            //画进度
            canvas.drawLine(0f, y, (currentProgress.toFloat() / maxProgress) * width, y, selectPaint)
            //画文字
            canvas.drawText(text, width / 2 - rect.width() / 2f, baseLine, textPaint)
        }
    }

    @Synchronized
    fun setMaxProgress(max: Int) {
        maxProgress = max
    }

    @Synchronized
    fun setProgress(current: Int) {
        if (current < 0 || current > maxProgress) return
        currentProgress = current
        invalidate()
    }
}
    <declare-styleable name="ProgressBar">
        <attr name="proBorderWidth" format="dimension" />
        <attr name="proInnerColor" format="color" />
        <attr name="proOutColor" format="color" />
        <attr name="proTextColor" format="color" />
        <attr name="proTextSize" format="dimension" />
        <attr name="proOrientation" format="enum">
            <enum name="proHorizontal" value="1" />
            <enum name="proCircle" value="2" />
        </attr>
        <attr name="maxProgress" format="integer" />
    </declare-styleable>

相关文章

网友评论

      本文标题:简单进度条

      本文链接:https://www.haomeiwen.com/subject/rycagctx.html