欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Android自定義View之漸變色折線圖的實(shí)現(xiàn)

 更新時(shí)間:2022年04月26日 11:41:42   作者:ChenYhong  
折線圖的實(shí)現(xiàn)方法在github上有很多開源的程序,但是對(duì)于初學(xué)者來講,簡單一點(diǎn)的教程可能更容易入門,下面這篇文章主要給大家介紹了關(guān)于Android自定義View之漸變色折線圖的相關(guān)資料,需要的朋友可以參考下

前言

在之前的項(xiàng)目中,有做過一個(gè)需求,需要實(shí)現(xiàn)一個(gè)顏色漸變的折線圖。當(dāng)時(shí)項(xiàng)目中使用的圖表庫是MPAndroidChart,但是該庫沒有提供合適的方法來實(shí)現(xiàn)想要的效果,因此只能通過自定義view來實(shí)現(xiàn)。

通過這篇文章記錄一下,便于之后需要實(shí)現(xiàn)類似的效果時(shí)查找使用。

如何實(shí)現(xiàn)

通過創(chuàng)建LinearGradient來實(shí)現(xiàn)顏色漸變,并將之設(shè)置到畫筆Paint的著色器Shader,繪制想要的路徑即可實(shí)現(xiàn)該效果。

實(shí)現(xiàn)代碼如下:

class GradientLineChart : View {
    private var viewWidth: Int = 0
    private var viewHeight: Int = 0

    private var chartWidth: Int = 0
    private var chartHeight: Int = 0

    /**
     * 折線寬度
     */
    private var lineWidth: Float = 0f

    /**
     * 網(wǎng)格線寬度
     */
    private var gridLineWidth: Float = 0f

    /**
     * 網(wǎng)格線顏色
     */
    private var gridLineColor: Int = 0

    /**
     * 背景顏色
     */
    private var backgroundColorRes: Int = 0

    private var linePaint: Paint? = null
    private var gridLinePaint: Paint? = null
    private var gradientColor: IntArray? = null

    private val rectF = RectF()
    private val linePath = Path()

    private val lineValueList = ArrayList<LineEntity>()

    constructor(context: Context?) : this(context, null)

    constructor(context: Context?, attrs: AttributeSet?) : this(context, attrs, 0)

    constructor(context: Context?, attrs: AttributeSet?, defStyleAttr: Int) : super(context, attrs, defStyleAttr) {
        lineValueList.add(LineEntity(3f, 28f))
        lineValueList.add(LineEntity(7f, 2f))
        lineValueList.add(LineEntity(14f, 18f))
        lineValueList.add(LineEntity(17f, 12f))
        lineValueList.add(LineEntity(22f, 21f))

        context?.let {
            gradientColor = intArrayOf(
                ContextCompat.getColor(it, R.color.color_FFD200),
                ContextCompat.getColor(it, R.color.color_FF2600),
                ContextCompat.getColor(it, R.color.color_49E284),
                ContextCompat.getColor(it, R.color.color_00A5FF)
            )
        }

        initAttr(attrs, defStyleAttr)
        initPaint()
    }

    private fun initAttr(attrs: AttributeSet?, defStyleAttr: Int) {
        val typeArray =
            context.theme.obtainStyledAttributes(attrs, R.styleable.GradientLineChart, defStyleAttr, 0)

        lineWidth = typeArray.getDimension(
            R.styleable.GradientLineChart_tc_lineWidth,
            DensityUtil.dp2Px(2).toFloat()
        )
        gridLineWidth = typeArray.getDimension(
            R.styleable.GradientLineChart_tc_grid_line_width,
            DensityUtil.dp2Px(1).toFloat()
        )
        gridLineColor = typeArray.getColor(
            R.styleable.GradientLineChart_tc_grid_line_color,
            ContextCompat.getColor(context, R.color.color_1Affffff)
        )
        backgroundColorRes = typeArray.getColor(
            R.styleable.GradientLineChart_tc_background_color,
            ContextCompat.getColor(context, R.color.color_23242a)
        )

        typeArray.recycle()
    }

    private fun initPaint() {
        linePaint = Paint()
        linePaint?.isAntiAlias = true
        linePaint?.style = Paint.Style.STROKE
        linePaint?.strokeWidth = lineWidth

        gridLinePaint = Paint()
        gridLinePaint?.isAntiAlias = true
        gridLinePaint?.style = Paint.Style.FILL
        gridLinePaint?.color = gridLineColor
    }

    override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
        viewWidth = MeasureSpec.getSize(widthMeasureSpec)
        viewHeight = MeasureSpec.getSize(heightMeasureSpec)
        //MUST CALL THIS
        setMeasuredDimension(viewWidth, viewHeight)

        chartWidth = viewWidth - paddingStart - paddingEnd
        chartHeight = viewHeight - paddingTop - paddingBottom
    }

    override fun onDraw(canvas: Canvas?) {
        super.onDraw(canvas)
        //設(shè)置畫布背景色
        canvas?.drawColor(backgroundColorRes)
        //繪制網(wǎng)格線
        drawGradLine(canvas)
        //繪制折線
        drawLine(canvas)
    }

    /**
     * 繪制網(wǎng)格線
     */
    private fun drawGradLine(canvas: Canvas?) {
        gridLinePaint?.let {
            val yGridValues = 7
            val xGridValues = 6

            //Y軸網(wǎng)格線間距
            val yGridDistance = (chartHeight - yGridValues * gridLineWidth) / (yGridValues - 1)
            for (index in 0 until yGridValues) {
                val left = paddingStart.toFloat()
                val top = paddingTop.toFloat() + index * yGridDistance + index * gridLineWidth
                val right = left + chartWidth
                val bottom = top + gridLineWidth
                rectF.set(left, top, right, bottom)
                canvas?.drawRect(rectF, it)
            }

            //X軸網(wǎng)格線間距
            val xGridDistance = (chartWidth - xGridValues * gridLineWidth) / (xGridValues - 1)
            for (index in 0 until xGridValues) {
                val left = paddingStart + xGridDistance * index + gridLineWidth * index
                val top = paddingTop.toFloat()
                val right = left + gridLineWidth
                val bottom = top + chartHeight
                rectF.set(left, top, right, bottom)
                canvas?.drawRect(rectF, gridLinePaint!!)
            }
        }
    }

    /**
     * 繪制折線
     */
    private fun drawLine(canvas: Canvas?) {
        val yGridValues = 7
        val xGridValues = 6
        val yGridDistance = (chartHeight - yGridValues * gridLineWidth) / (yGridValues - 1)
        val xGridDistance = (chartWidth - xGridValues * gridLineWidth) / (xGridValues - 1)

        for ((index, linePoint) in lineValueList.withIndex()) {
            val pointX =
                ((linePoint.xValue - 5 * index) / 5) * xGridDistance + (xGridDistance * index)
            val pointY =
                chartHeight - (linePoint.yValue / 30 * (yGridDistance * 6))
            if (index == 0) {
                linePath.moveTo(pointX, pointY)
            } else {
                linePath.lineTo(pointX, pointY)
            }
        }

        linePaint?.shader = createLineGradient(gradientColor!!)
        canvas?.drawPath(linePath, linePaint!!)
    }

    private fun createLineGradient(gradientColor: IntArray): LinearGradient {
        return LinearGradient(
            0f,
            0f,
            0f,
            viewHeight.toFloat(),
            gradientColor,
            null,
            Shader.TileMode.CLAMP
        )
    }
}

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <declare-styleable name="GradientLineChart">
        <!--線寬度-->
        <attr name="tc_lineWidth" format="dimension" />
        <!--網(wǎng)格線寬度-->
        <attr name="tc_grid_line_width" format="dimension" />
        <!--網(wǎng)格線顏色-->
        <attr name="tc_grid_line_color" format="color" />
        <!--等級(jí)顏色指示器寬度-->
        <attr name="tc_level_indicator_width" format="dimension" />
        <!--背景顏色-->
        <attr name="tc_background_color" format="color" />
    </declare-styleable>
</resources>

效果如下圖:

總結(jié)

到此這篇關(guān)于Android自定義View之漸變色折線圖的文章就介紹到這了,更多相關(guān)Android漸變色折線圖內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Android自動(dòng)提示控件AutoCompleteTextView

    Android自動(dòng)提示控件AutoCompleteTextView

    這篇文章主要介紹了Android自動(dòng)提示控件AutoCompleteTextView的相關(guān)資料,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2016-12-12
  • Android如何自定義升級(jí)對(duì)話框示例詳解

    Android如何自定義升級(jí)對(duì)話框示例詳解

    對(duì)話框是我們?cè)谄綍r(shí)經(jīng)常會(huì)遇到的一個(gè)功能,但自帶的對(duì)話框不夠美觀,大家一般都會(huì)自定義,下面這篇文章主要給大家介紹了關(guān)于Android如何自定義升級(jí)對(duì)話框的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),需要的朋友可以參考借鑒,下面來一起看看吧。
    2017-08-08
  • Android獲取SD卡中選中圖片的路徑(URL)示例

    Android獲取SD卡中選中圖片的路徑(URL)示例

    一個(gè)圖片上傳功能需要提供上傳圖片在SD卡中的路徑,總結(jié)了網(wǎng)上的一些列子,修改了一下,代碼很簡單,感興趣的朋友可以參考下哈,希望對(duì)大家有所幫助
    2013-07-07
  • 淺談Android studio 生成apk文件時(shí)的 key store path 的問題

    淺談Android studio 生成apk文件時(shí)的 key store path 的問題

    這篇文章主要介紹了淺談Android studio 生成apk文件時(shí)的 key store path 的問題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧
    2020-03-03
  • Android控制文本輸入框最多輸入10個(gè)字符長度

    Android控制文本輸入框最多輸入10個(gè)字符長度

    這篇文章主要為大家詳細(xì)介紹了Android控制文本輸入框最多輸入10個(gè)字符長度,即最多輸入5個(gè)漢字,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2017-10-10
  • Android中js和原生交互的示例代碼

    Android中js和原生交互的示例代碼

    本篇文章主要介紹了Android中js和原生交互的示例代碼,小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧
    2017-08-08
  • 使用RecyclerView添加Header和Footer的方法

    使用RecyclerView添加Header和Footer的方法

    RecyclerView雖然作為ListView的替代者有著較好的性能提升,但是ListView的一些常用功能卻沒有提供,比如我們平時(shí)會(huì)經(jīng)常用到的addHeaderView,addFooterView,既然RecyclerView沒有提供這個(gè)方法,我們應(yīng)該如何為列表添加頭部和底部呢,接下來通過本文給大家介紹
    2016-03-03
  • Android開發(fā)自定義實(shí)時(shí)圖表控件實(shí)現(xiàn)示例

    Android開發(fā)自定義實(shí)時(shí)圖表控件實(shí)現(xiàn)示例

    這篇文章主要為大家介紹了Android自定義實(shí)時(shí)圖表控件實(shí)現(xiàn)示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-06-06
  • android ListView和GridView拖拽移位實(shí)現(xiàn)代碼

    android ListView和GridView拖拽移位實(shí)現(xiàn)代碼

    有些朋友對(duì)android中ListView和GridView拖拽移位功能的實(shí)現(xiàn)不是很了解,接下來將詳細(xì)介紹,需要了解的朋友可以參考下
    2012-12-12
  • android實(shí)現(xiàn)直播點(diǎn)贊飄心動(dòng)畫效果

    android實(shí)現(xiàn)直播點(diǎn)贊飄心動(dòng)畫效果

    這篇文章主要為大家詳細(xì)介紹了android實(shí)現(xiàn)直播點(diǎn)贊飄心動(dòng)畫效果,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2018-03-03

最新評(píng)論