Android 사용자 정의 View 원호 진행 효과 구현
기술 실현
1.ArcView 계승
2.Canvas(캔버스)
3.Paint(화필)
효과 도:QQ 와 유사 한 스텝 효과
1.뷰 계승
(1)3 개의 구조 방법 을 다시 쓴다(새로운 API 의 구조 방법 은 4 개)
public ArcView(Context context) {
this(context,null);
}
public ArcView(Context context, @Nullable AttributeSet attrs) {
this(context, attrs,0);
}
public ArcView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
//init();
}
(2)View 의 OnDraw 를 다시 쓰 는 방법
@SuppressLint("DrawAllocation")
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
centerX=getWidth()/2;
centerY=getHeight()/2;
// paint
initPaint();
//
drawArc(canvas);
//
drawText(canvas);
}
주:여기 paint 초기 화 는 onDraw 방법 에 넣 었 습 니 다.물론 세 개의 매개 변수 가 있 는 구조 방법 에서 초기 화 할 수 있 습 니 다.2.Paint 초기 화
(1)원호 의 붓 mArcPaint
// paint
mArcPaint=new Paint(Paint.ANTI_ALIAS_FLAG);
//
mArcPaint.setAntiAlias(true);
mArcPaint.setColor(Color.parseColor("#666666"));
// ( 0-255)
mArcPaint.setAlpha(100);
//
mArcPaint.setStrokeJoin(Paint.Join.ROUND);
mArcPaint.setStrokeCap(Paint.Cap.ROUND);
//
mArcPaint.setStyle(Paint.Style.STROKE);
mArcPaint.setStrokeWidth(dp2px(mStrokeWith));
(2)글자 의 화필 mTextPaint
// paint
mTextPaint=new Paint();
mTextPaint.setAntiAlias(true);
mTextPaint.setColor(Color.parseColor("#FF4A40"));
//
mTextPaint.setTextAlign(Paint.Align.CENTER);
//mTextPaint.setTextSize(getResources().getDimensionPixelSize(R.dimen.dp_12));
mTextPaint.setTextSize(dp2px(25));
3.Canvas 그리 기(1)원호 의 그리 기
/**
*
* @param canvas
*/
private void drawArc(Canvas canvas) {
//
RectF mRectF=new RectF(mStrokeWith+dp2px(5),mStrokeWith+dp2px(5),getWidth()-mStrokeWith-dp2px(5),getHeight()-mStrokeWith);
canvas.drawArc(mRectF,startAngle,mAngle,false,mArcPaint);
//
mArcPaint.setColor(Color.parseColor("#FF4A40"));
//
canvas.drawArc(mRectF,startAngle,mIncludedAngle,false,mArcPaint);
}
(2)텍스트 그리 기
/**
*
* @param canvas
*/
private void drawText(Canvas canvas) {
Rect mRect=new Rect();
String mValue=String.valueOf(mAnimatorValue);
//
mTextPaint.getTextBounds(mValue,0,mValue.length(),mRect);
canvas.drawText(String.valueOf(mAnimatorValue),centerX,centerY+mRect.height(),mTextPaint);
//
mTextPaint.setColor(Color.parseColor("#999999"));
mTextPaint.setTextSize(dp2px(12));
mTextPaint.getTextBounds(mDes,0,mDes.length(),mRect);
canvas.drawText(mDes,centerX,centerY+2*mRect.height()+dp2px(10),mTextPaint);
//
String minValue=String.valueOf(mMinValue);
String maxValue=String.valueOf(mMaxValue);
mTextPaint.setTextSize(dp2px(18));
mTextPaint.getTextBounds(minValue,0,minValue.length(),mRect);
canvas.drawText(minValue, (float) (centerX-0.6*centerX-dp2px(5)), (float) (centerY+0.75*centerY+mRect.height()+dp2px(5)),mTextPaint);
//
mTextPaint.getTextBounds(maxValue,0,maxValue.length(),mRect);
canvas.drawText(maxValue, (float) (centerX+0.6*centerX+dp2px(5)), (float) (centerY+0.75*centerY+mRect.height()+dp2px(5)),mTextPaint);
}
4.애니메이션 효과 및 데이터 추가(1)애니메이션 효과
/**
*
*
* @param startAngle
* @param currentAngle
* @param currentValue
* @param time
*/
private void setAnimation(float startAngle, float currentAngle,int currentValue, int time) {
//
ValueAnimator progressAnimator = ValueAnimator.ofFloat(startAngle, currentAngle);
progressAnimator.setDuration(time);
progressAnimator.setTarget(mIncludedAngle);
progressAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
mIncludedAngle = (float) animation.getAnimatedValue();
// ,
postInvalidate();
}
});
//
progressAnimator.start();
//
ValueAnimator valueAnimator = ValueAnimator.ofInt(mAnimatorValue, currentValue);
valueAnimator.setDuration(2500);
valueAnimator.setInterpolator(new LinearInterpolator());
valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator valueAnimator) {
mAnimatorValue = (int) valueAnimator.getAnimatedValue();
postInvalidate();
}
});
valueAnimator.start();
}
(2)데이터 추가
/**
*
* @param minValue
* @param maxValue
* @param currentValue
* @param des
*/
public void setValues(int minValue,int maxValue, int currentValue,String des) {
mDes=des;
mMaxValue=maxValue;
mMinValue=minValue;
//
if (currentValue > maxValue) {
currentValue = maxValue;
}
//
float scale = (float) currentValue / maxValue;
//
float currentAngle = scale * mAngle;
//
setAnimation(0, currentAngle, currentValue,2500);
전체 코드:
/**
* Created by ruancw on 2018/6/13.
* view
*/
public class ArcView extends View {
// Paint
private Paint mArcPaint;
// paint
private Paint mTextPaint;
//
private float startAngle=135;
//
private float endAngle=45;
//
private float mAngle=270;
//
private float mIncludedAngle=0;
//
private float mStrokeWith=10;
//
private String mDes="";
// /
private int mAnimatorValue,mMinValue,mMaxValue;
// XY
private float centerX,centerY;
public ArcView(Context context) {
this(context,null);
}
public ArcView(Context context, @Nullable AttributeSet attrs) {
this(context, attrs,0);
}
public ArcView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
//init();
}
private void initPaint() {
// paint
mArcPaint=new Paint(Paint.ANTI_ALIAS_FLAG);
//
mArcPaint.setAntiAlias(true);
mArcPaint.setColor(Color.parseColor("#666666"));
// ( 0-255)
mArcPaint.setAlpha(100);
//
mArcPaint.setStrokeJoin(Paint.Join.ROUND);
mArcPaint.setStrokeCap(Paint.Cap.ROUND);
//
mArcPaint.setStyle(Paint.Style.STROKE);
mArcPaint.setStrokeWidth(dp2px(mStrokeWith));
// paint
mTextPaint=new Paint();
mTextPaint.setAntiAlias(true);
mTextPaint.setColor(Color.parseColor("#FF4A40"));
//
mTextPaint.setTextAlign(Paint.Align.CENTER);
//mTextPaint.setTextSize(getResources().getDimensionPixelSize(R.dimen.dp_12));
mTextPaint.setTextSize(dp2px(25));
}
@SuppressLint("DrawAllocation")
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
centerX=getWidth()/2;
centerY=getHeight()/2;
// paint
initPaint();
//
drawArc(canvas);
//
drawText(canvas);
}
/**
*
* @param canvas
*/
private void drawText(Canvas canvas) {
Rect mRect=new Rect();
String mValue=String.valueOf(mAnimatorValue);
//
mTextPaint.getTextBounds(mValue,0,mValue.length(),mRect);
canvas.drawText(String.valueOf(mAnimatorValue),centerX,centerY+mRect.height(),mTextPaint);
//
mTextPaint.setColor(Color.parseColor("#999999"));
mTextPaint.setTextSize(dp2px(12));
mTextPaint.getTextBounds(mDes,0,mDes.length(),mRect);
canvas.drawText(mDes,centerX,centerY+2*mRect.height()+dp2px(10),mTextPaint);
//
String minValue=String.valueOf(mMinValue);
String maxValue=String.valueOf(mMaxValue);
mTextPaint.setTextSize(dp2px(18));
mTextPaint.getTextBounds(minValue,0,minValue.length(),mRect);
canvas.drawText(minValue, (float) (centerX-0.6*centerX-dp2px(5)), (float) (centerY+0.75*centerY+mRect.height()+dp2px(5)),mTextPaint);
//
mTextPaint.getTextBounds(maxValue,0,maxValue.length(),mRect);
canvas.drawText(maxValue, (float) (centerX+0.6*centerX+dp2px(5)), (float) (centerY+0.75*centerY+mRect.height()+dp2px(5)),mTextPaint);
}
/**
*
* @param canvas
*/
private void drawArc(Canvas canvas) {
//
RectF mRectF=new RectF(mStrokeWith+dp2px(5),mStrokeWith+dp2px(5),getWidth()-mStrokeWith-dp2px(5),getHeight()-mStrokeWith);
canvas.drawArc(mRectF,startAngle,mAngle,false,mArcPaint);
//
mArcPaint.setColor(Color.parseColor("#FF4A40"));
//
canvas.drawArc(mRectF,startAngle,mIncludedAngle,false,mArcPaint);
}
/**
*
*
* @param startAngle
* @param currentAngle
* @param currentValue
* @param time
*/
private void setAnimation(float startAngle, float currentAngle,int currentValue, int time) {
//
ValueAnimator progressAnimator = ValueAnimator.ofFloat(startAngle, currentAngle);
progressAnimator.setDuration(time);
progressAnimator.setTarget(mIncludedAngle);
progressAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
mIncludedAngle = (float) animation.getAnimatedValue();
// ,
postInvalidate();
}
});
//
progressAnimator.start();
//
ValueAnimator valueAnimator = ValueAnimator.ofInt(mAnimatorValue, currentValue);
valueAnimator.setDuration(2500);
valueAnimator.setInterpolator(new LinearInterpolator());
valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator valueAnimator) {
mAnimatorValue = (int) valueAnimator.getAnimatedValue();
postInvalidate();
}
});
valueAnimator.start();
}
/**
*
* @param minValue
* @param maxValue
* @param currentValue
* @param des
*/
public void setValues(int minValue,int maxValue, int currentValue,String des) {
mDes=des;
mMaxValue=maxValue;
mMinValue=minValue;
//
if (currentValue > maxValue) {
currentValue = maxValue;
}
//
float scale = (float) currentValue / maxValue;
//
float currentAngle = scale * mAngle;
//
setAnimation(0, currentAngle, currentValue,2500);
}
public float dp2px(float dp) {
DisplayMetrics metrics = Resources.getSystem().getDisplayMetrics();
return dp * metrics.density;
}
}
요약:Paint 의 붓 모양(Cap 과 Join 은 원호 형 으로 설정)을 설정 합 니 다.Canvas 의 drawArc 방법 으로 원호 와 drawText 로 텍스트 정 보 를 그립 니 다.ValueAnimator 는 데이터 와 현재 원호 진도 의 애니메이션 효 과 를 설정 합 니 다.이상 이 바로 본 고의 모든 내용 입 니 다.여러분 의 학습 에 도움 이 되 고 저 희 를 많이 응원 해 주 셨 으 면 좋 겠 습 니 다.
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
Bitrise에서 배포 어플리케이션 설정 테스트하기이 글은 Bitrise 광고 달력의 23일째 글입니다. 자체 또는 당사 등에서 Bitrise 구축 서비스를 사용합니다. 그나저나 며칠 전 Bitrise User Group Meetup #3에서 아래 슬라이드를 발표했...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.