项目中用到手势解锁,然而没有在GitHub上找到想要的样式= =,只好自己来定义了,下面来看代码~~
基本上很多应用的手势解锁全都是九宫格的,内部内就是九个小圈圈而已。那么我们就先来自定义这个小圈圈吧~
圈圈的颜色选择状态有大致有三种状态,所以我定义了一个枚举来区分
package com.juzisang.com.library;/** * Created by 橘子桑 on 2016/3/27. */public enum LockState {SELECT_STATE,//选中ERRER_STATE, //错误DEFAULT_COLOR //默认}圈圈分为边框,内部填充色,还有内部圆。所以我定义了三个画笔来区分。
package com.juzisang.com.library;import android.content.Context;import android.content.res.TypedArray;import android.graphics.Canvas;import android.graphics.Color;import android.graphics.Paint;import android.util.AttributeSet;import android.view.View;/** * Created by 橘子桑 on 2016/3/27. */public class MarkerView extends View {//是否显示内部的圈圈private boolean mInsideNodeShow;//宽度protected int mContentWidth;//宽度protected int mContentRadius;//选中状态protected LockState mCurrentState = LockState.DEFAULT_COLOR;//画边框画圆的的画笔private Paint mNodeFramePaint;private Paint mNodeCirclePaint;private Paint mNodeFullPaint;//默认的颜色private int mDefaultColor = Color.parseColor("#757575");private int mDefailtFullColor = Color.parseColor("#64757575");private int mNodeDefaultColor = Color.parseColor("#757575");//选中的颜色private int mSelectColor = Color.parseColor("#7ECEF4");private int mFrameSelectFullColor = Color.parseColor("#647ECEF4");private int mNodeSelectColor = Color.parseColor("#7ECEF4");//错误时候的颜色private int mErrerColor = Color.parseColor("#EC6941");private int mErrerFullColor = Color.parseColor("#64EC6941");private int mErrerNodeColor = Color.parseColor("#EC6941");//边框的宽度private int mFrameLineWidth;private int mNodeRadius;//每个圈圈的内边距private int mNodePadding;//触摸有效的范围private float mTouchRatio;//当前标记的位置private int mNum;public MarkerView(Context context, AttributeSet attrs) {super(context, attrs);initView(context, attrs, 0);}public MarkerView(Context context, AttributeSet attrs, int defStyleAttr) {super(context, attrs, defStyleAttr);initView(context, attrs, defStyleAttr);}//以后外部布局传来的参数public MarkerView(Context context, int mDefaultColor, int mDefailtFullColor, int mNodeDefaultColor, int mSelectColor, int mFrameSelectFullColor, int mNodeSelectColor, int mErrerColor, int mErrerFullColor, int mErrerNodeColor, int mFrameLineWidth, int mNodeRadius, int mNodePadding, boolean insideNodeShow) {super(context);this.mInsideNodeShow = insideNodeShow;this.mDefaultColor = mDefaultColor;this.mDefailtFullColor = mDefailtFullColor;this.mNodeDefaultColor = mNodeDefaultColor;this.mSelectColor = mSelectColor;this.mFrameSelectFullColor = mFrameSelectFullColor;this.mNodeSelectColor = mNodeSelectColor;this.mErrerColor = mErrerColor;this.mErrerFullColor = mErrerFullColor;this.mErrerNodeColor = mErrerNodeColor;this.mFrameLineWidth = mFrameLineWidth;this.mNodeRadius = mNodeRadius;this.mNodePadding = mNodePadding;//内边距setPadding(mNodePadding, mNodePadding, mNodePadding, mNodePadding);//外部圆mNodeFramePaint = new Paint();mNodeFramePaint.setColor(mDefaultColor);mNodeFramePaint.setAntiAlias(true);mNodeFramePaint.setStrokeWidth(mFrameLineWidth);mNodeFramePaint.setStyle(Paint.Style.STROKE);//只画出边框//内部填充色mNodeFullPaint = new Paint();mNodeFullPaint.setColor(mDefailtFullColor);mNodeFullPaint.setStyle(Paint.Style.FILL);mNodeFullPaint.setAntiAlias(true);//内部圆mNodeCirclePaint = new Paint();mNodeCirclePaint.setColor(mNodeDefaultColor);mNodeCirclePaint.setStyle(Paint.Style.FILL);//填充mNodeCirclePaint.setAntiAlias(true);}//取当前透明度的百分比public int getFullAlpha(int color, float ratio) {return Color.argb((int) (Color.alpha(color) * ratio), Color.red(color), Color.green(color), Color.blue(color));}@Overrideprotected void onSizeChanged(int w, int h, int oldw, int oldh) {super.onSizeChanged(w, h, oldw, oldh);mContentWidth = getWidth();mContentRadius = mContentWidth / 2 - Math.abs(getPaddingLeft()) - mFrameLineWidth / 2;}@Overrideprotected void onDraw(Canvas canvas) {super.onDraw(canvas);switch (mCurrentState) {case DEFAULT_COLOR: //默认mNodeFramePaint.setColor(mDefaultColor);mNodeFullPaint.setColor(mDefailtFullColor);mNodeCirclePaint.setColor(mNodeDefaultColor);//外圆canvas.drawCircle(mContentWidth / 2, mContentWidth / 2, mContentRadius, mNodeFramePaint);//填充色canvas.drawCircle(mContentWidth / 2, mContentWidth / 2, mContentRadius - mFrameLineWidth / 2, mNodeFullPaint);//中心圆if (mInsideNodeShow)canvas.drawCircle(mContentWidth / 2, mContentWidth / 2, mNodeRadius, mNodeCirclePaint);break;case ERRER_STATE://错误mNodeFramePaint.setColor(mErrerColor);mNodeFullPaint.setColor(mErrerFullColor);mNodeCirclePaint.setColor(mErrerNodeColor);//外圆canvas.drawCircle(mContentWidth / 2, mContentWidth / 2, mContentRadius, mNodeFramePaint);//填充色canvas.drawCircle(mContentWidth / 2, mContentWidth / 2, mContentRadius - mFrameLineWidth / 2, mNodeFullPaint);//中心圆canvas.drawCircle(mContentWidth / 2, mContentWidth / 2, mNodeRadius, mNodeCirclePaint);break;case SELECT_STATE://选中mNodeFramePaint.setColor(mSelectColor);mNodeFullPaint.setColor(mFrameSelectFullColor);mNodeCirclePaint.setColor(mNodeSelectColor);//外圆canvas.drawCircle(mContentWidth / 2, mContentWidth / 2, mContentRadius, mNodeFramePaint);//填充色canvas.drawCircle(mContentWidth / 2, mContentWidth / 2, mContentRadius - mFrameLineWidth / 2, mNodeFullPaint);//中心圆canvas.drawCircle(mContentWidth / 2, mContentWidth / 2, mNodeRadius, mNodeCirclePaint);break;}}//设置状态,并且重绘public void setState(LockState CurrentState) {mCurrentState = CurrentState;invalidate();}//是否选中public boolean isHighLighted() {if (mCurrentState == LockState.SELECT_STATE || mCurrentState == LockState.ERRER_STATE) {return true;}return false;}//中心点Xpublic int getCenterX() {return (getLeft() + getRight()) / 2;}//中心点Ypublic int getCenterY() {return (getTop() + getBottom()) / 2;}//设置圈圈在手势锁当中的位置protected void setNum(int num) {mNum = num;}protected int getNum() {return mNum;}}以上就是一个简单的圆了
那么,自定义View当然会有自定义属性,所以有这么多T0T,不要问我为什么这么多属性,任性= =(其实我还想写