Android自定义View实现仿QQ实现运动步数效果

欠伸展肢体,吟咏心自愉。这篇文章主要讲述Android自定义View实现仿QQ实现运动步数效果相关的知识,希望能为你提供帮助。
效果图:
 

Android自定义View实现仿QQ实现运动步数效果

文章图片

1、attrs.xml中
< declare-styleable name="QQStepView"> < attr name="outerColor" format="color"/> < attr name="innerColor" format="color"/> < attr name="borderWidth" format="dimension"/> < attr name="stepViewTextSize" format="dimension"/> < attr name="stepViewTextColor" format="color"/> < /declare-styleable>

2、QQStepView
public class QQStepView extends View { private int mOuterColor = Color.GRAY; private int mInnerColor = Color.RED; private float mBorderWidth = 20.0f; //20代表的20px private float mStepViewTextSize = 12.0f; private int mStepViewTextColor = Color.BLACK; private Paint mOutPaint; private int mStepMax; //最大的数值 private int mCurrentStep; //当前的数值 private Paint mInnerPaint; private Paint mTextPaint; public QQStepView(Context context) { this(context, null); }public QQStepView(Context context, AttributeSet attrs) { this(context, attrs, 0); }public QQStepView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); //1分析效果 //2确定自定义属性,编写attr.xml //3在布局中使用 //4在自定义View中获取自定义属性 //5onMeasure //6onDraw TypedArray array = context.obtainStyledAttributes(attrs, R.styleable.QQStepView); mOuterColor = array.getColor(R.styleable.QQStepView_outerColor, mOuterColor); mInnerColor = array.getColor(R.styleable.QQStepView_innerColor, mInnerColor); mBorderWidth = array.getDimension(R.styleable.QQStepView_borderWidth, mBorderWidth); mStepViewTextColor = array.getColor(R.styleable.QQStepView_stepViewTextColor, mStepViewTextColor); mStepViewTextSize = array.getDimension(R.styleable.QQStepView_stepViewTextSize, mStepViewTextSize); array.recycle(); //外层圆弧画笔 mOutPaint = new Paint(); mOutPaint.setAntiAlias(true); mOutPaint.setStrokeWidth(mBorderWidth); mOutPaint.setColor(mOuterColor); mOutPaint.setStrokeCap(Paint.Cap.ROUND); //两端变圆弧 //mOutPaint.setStyle(Paint.Style.FILL); mOutPaint.setStyle(Paint.Style.STROKE); //内层圆弧画笔 mInnerPaint = new Paint(); mInnerPaint.setAntiAlias(true); mInnerPaint.setStrokeWidth(mBorderWidth); mInnerPaint.setColor(mInnerColor); mInnerPaint.setStrokeCap(Paint.Cap.ROUND); //两端变圆弧 //mOutPaint.setStyle(Paint.Style.FILL); mInnerPaint.setStyle(Paint.Style.STROKE); //文字画笔 mTextPaint = new Paint(); mInnerPaint.setAntiAlias(true); mInnerPaint.setColor(mStepViewTextColor); mTextPaint.setTextSize(mStepViewTextSize); }@Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); //在布局文件中,可能wrap_content,可能高宽不一致 //获取模式 AT_MOST //宽度高度不一致时取最小值,保持是个正方形 int width = MeasureSpec.getSize(widthMeasureSpec); int height = MeasureSpec.getSize(heightMeasureSpec); setMeasuredDimension(width > height ? height : width, width > height ? height : width); }@Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); //画外圆弧: //int center = getWidth() / 2; //int radius= (int) (getWidth()/2-mBorderWidth/2); //RectF rectF = new RectF(center-radius, center-radius, center+radius, center+radius); //int radius = (int) (getWidth() / 2 - mBorderWidth / 2); RectF rectF = new RectF(mBorderWidth / 2, mBorderWidth / 2, getWidth() - mBorderWidth / 2, getWidth() - mBorderWidth / 2); canvas.drawArc(rectF, 135, 270, false, mOutPaint); //画内圆弧:百分比,由用户设置的 if (mStepMax == 0) { return; //防止第一次进入时为0,引起错误 } float sweepAngle = (float) mCurrentStep / mStepMax; canvas.drawArc(rectF, 135, sweepAngle * 270, false, mInnerPaint); //画文字 String stepText = mCurrentStep + ""; Rect textBounds = new Rect(); mTextPaint.getTextBounds(stepText, 0, stepText.length(), textBounds); int dx = getWidth() / 2 - textBounds.width() / 2; //文字的起始位置 //基线 Paint.FontMetricsInt fontMetricsInt = mTextPaint.getFontMetricsInt(); int dy = (fontMetricsInt.bottom = fontMetricsInt.top) - fontMetricsInt.bottom; int baseLine = getHeight() / 2 + dy; canvas.drawText(stepText, dx, baseLine, mTextPaint); }//其他,动画效果等 public synchronized void setStepMax(int stepMax) { this.mStepMax = stepMax; }//synchronized,防止多线程操作出错 public synchronized void setCurrentStep(int currentStep) { this.mCurrentStep = currentStep; //不断绘制 invalidate(); } }

 
3、在Activity布局中
< com.siberiadante.view.QQStepView android:id="@+id/step_view" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_centerInParent="true" app:borderWidth="10dp" app:innerColor="@color/blue" app:outerColor="@color/colorAccent" app:stepViewTextColor="@color/blue" app:stepViewTextSize="28sp" />

4、在Activity中
mTvStart = (TextView) findViewById(R.id.tv_start); stepView = (QQStepView) findViewById(R.id.step_view); stepView.setStepMax(10000); //stepView.setCurrentStep(5000); //属性动画 final ValueAnimator valueAnimator = ObjectAnimator.ofFloat(0, 9000); valueAnimator.setDuration(3000); valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { @Override public void onAnimationUpdate(ValueAnimator valueAnimator) { float value = https://www.songbingjia.com/android/(float) valueAnimator.getAnimatedValue(); stepView.setCurrentStep((int)value); } }); mTvStart.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { valueAnimator.start(); } }); }

 
我的微信公众号:tstongxiao
Android自定义View实现仿QQ实现运动步数效果

文章图片

github地址:https://github.com/SiberiaDante/SiberiaDanteLib/blob/master/siberiadante/src/main/java/com/siberiadante/view/QQStepView.java
 
参考文章:http://www.jianshu.com/p/4e0eb9bb09ab
【Android自定义View实现仿QQ实现运动步数效果】 

    推荐阅读