转载请注明出处 —— http://blog.csdn.net/jjwwmlp456。QQ交流群:473876194
效果图
使用SweepGradient作为paint的shader,用于绘制
paint的color也会影响shader
利用handler不断发送消息,不断改变canvas.drawArc()
中的起始角度kotlin中认为类似”0xffffffff”这样,0x后面跟8位数的是long值,在用于颜色时,必须转为Int
在声明Handler成员属性时,不要声明成handler,因为View中有个方法为public Handler getHander();
所以kotlin会认为你重写定义了一个属性
package com.stone.stoneviews.widget import android.content.Context import android.graphics.* import android.os.Handler import android.os.Message import android.util.AttributeSet import android.view.MotionEvent import android.view.View /** * desc : * author : stone * email : aa86799@163.com * time : 22/07/2017 11 37 */ class RadarView: View { private var mRadius = 0f private var mPaint = Paint() private var mShader: SweepGradient? = null private var mRx = 0f private var mRy = 0f private val mRingCount = 4 private var mRect: RectF = RectF() private var mSweepStartAngle = 0f private var mSweepAngle = 120f private var mSweepAngleSpeed = 10f private var mIsStartSweep = false private val STATE_START = 1 private val STATE_STOP = 2 private val mHandler = object : Handler() { override fun handleMessage(msg: Message) { val what = msg.what when (what) { STATE_START -> { mSweepStartAngle += mSweepAngleSpeed invalidate() sendMessageDelayed(Message.obtain(this, STATE_START), 50) } STATE_STOP -> { removeCallbacksAndMessages(null) } } } } constructor(context: Context) : super(context) { initParams(context, null, 0) } constructor(context: Context, attrs: AttributeSet) : super(context, attrs) { initParams(context, attrs, 0) } constructor(context: Context, attrs: AttributeSet, defStyleAttr: Int) : super(context, attrs, defStyleAttr) { initParams(context, attrs, defStyleAttr) } fun initParams(context: Context, attrs: AttributeSet?, defStyleAttr: Int) { val w = resources.displayMetrics.widthPixels val h = resources.displayMetrics.heightPixels val min = Math.min(w, h) mRadius = (min / 2 - 50).toFloat() mRx = (w / 2).toFloat() mRy = (h / 2).toFloat() mPaint.isAntiAlias = true mRect = RectF(mRx - mRadius, mRy - mRadius, mRx + mRadius, mRy + mRadius) } override fun onDraw(canvas: Canvas) { super.onDraw(canvas) mPaint.style = Paint.Style.FILL_AND_STROKE mPaint.color = Color.BLUE mPaint.shader = null canvas.drawCircle(mRx, mRy, mRadius, mPaint) mPaint.color = Color.parseColor("#abc07f") mPaint.style = Paint.Style.STROKE canvas.drawLine(mRx - mRadius, mRy, mRadius + mRx, mRy, mPaint) canvas.drawLine(mRx, mRy - mRadius, mRx, mRy + mRadius, mPaint) val eachRingUnit = mRadius / mRingCount var curRingRadius: Float = 0f (1 until mRingCount).forEach { curRingRadius += eachRingUnit canvas.drawCircle(mRx, mRy, curRingRadius, mPaint) } // mShader = SweepGradient(mRx, mRy, 0xddff00f0.toInt(), 0xffabc777.toInt()) mShader = SweepGradient(mRx, mRy, intArrayOf(0xee191970.toInt(), 0xddff000f.toInt(), 0xddff00f0.toInt(), 0xaaff0000.toInt()), floatArrayOf(0.0f, 0.1f, 0.6f, 0.98f)) mPaint.shader = mShader mPaint.style = Paint.Style.FILL_AND_STROKE mPaint.color = Color.parseColor("#ccffffff") canvas.drawArc(mRect, mSweepStartAngle, mSweepAngle, true, mPaint) } override fun onTouchEvent(event: MotionEvent): Boolean { when (event.action) { MotionEvent.ACTION_DOWN -> { mIsStartSweep = !mIsStartSweep if (mIsStartSweep) { Message.obtain(mHandler, STATE_START).sendToTarget() } else { Message.obtain(mHandler, STATE_STOP).sendToTarget() } return true } } return super.onTouchEvent(event) } }