【移动应用开发技术】怎么在Android中自定义一个圆环倒计时控件_第1页
【移动应用开发技术】怎么在Android中自定义一个圆环倒计时控件_第2页
【移动应用开发技术】怎么在Android中自定义一个圆环倒计时控件_第3页
【移动应用开发技术】怎么在Android中自定义一个圆环倒计时控件_第4页
【移动应用开发技术】怎么在Android中自定义一个圆环倒计时控件_第5页
已阅读5页,还剩9页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

【移动应用开发技术】怎么在Android中自定义一个圆环倒计时控件

怎么在Android中自定义一个圆环倒计时控件?很多新手对此不是很清楚,为了帮助大家解决这个难题,下面在下将为大家详细讲解,有这方面需求的人可以来学习下,希望你能有所收获。自定义属性:<declare-styleable

name="CountDownProgressBar">

<attr

name="countDown_circleWidth"

format="dimension"

/>

<attr

name="countDown_centerTextSize"

format="dimension"

/>

<attr

name="countDown_betaAngle"

format="integer"

/>

<attr

name="countDown_firstColor"

format="color"

/>

<attr

name="countDown_secondColor"

format="color"

/>

<attr

name="countDown_centerTextColor"

format="color"

/>

<attr

name="countDown_isShowGradient"

format="boolean"

/>

</declare-styleable>主要代码:import

android.animation.ValueAnimator;

import

android.content.Context;

import

android.content.res.Resources;

import

android.content.res.TypedArray;

import

android.graphics.Canvas;

import

android.graphics.Color;

import

android.graphics.LinearGradient;

import

android.graphics.Paint;

import

android.graphics.Paint.FontMetricsInt;

import

android.graphics.Rect;

import

android.graphics.RectF;

import

android.graphics.Shader;

import

android.util.AttributeSet;

import

android.util.TypedValue;

import

android.view.View;

import

android.view.animation.LinearInterpolator;

import

com.daodaojk.myapplication.R;

public

class

CountDownProgressBar

extends

View

{

/**

*

进度条最大值

*/

private

int

maxValue

=

200;

/**

*

当前进度值

*/

private

int

currentValue

;

/**

*

每次扫过的角度,用来设置进度条圆弧所对应的圆心角,alphaAngle=(currentValue/maxValue)*360

*/

private

float

alphaAngle;

/**

*

底部圆弧的颜色,默认为Color.LTGRAY

*/

private

int

firstColor;

/**

*

进度条圆弧块的颜色

*/

private

int

secondColor;

/**

*

中间文字颜色(默认蓝色)

*/

private

int

centerTextColor

=

Color.BLUE;

/**

*

中间文字的字体大小(默认40dp)

*/

private

int

centerTextSize;

/**

*

圆环的宽度

*/

private

int

circleWidth;

/**

*

画圆弧的画笔

*/

private

Paint

circlePaint;

/**

*

画文字的画笔

*/

private

Paint

textPaint;

/**

*

是否使用渐变色

*/

private

boolean

isShowGradient

=

false;

/**

*

渐变圆周颜色数组

*/

private

int[]

colorArray

=

new

int[]{Color.parseColor("#2773FF"),

Color.parseColor("#27C0D2"),

Color.parseColor("#40C66E")};

private

int

duration;

private

OnFinishListener

listener;

private

ValueAnimator

animator;

public

CountDownProgressBar(Context

context)

{

this(context,

null);

}

public

CountDownProgressBar(Context

context,

AttributeSet

attrs)

{

this(context,

attrs,

0);

}

public

CountDownProgressBar(Context

context,

AttributeSet

attrs,

int

defStyleAttr)

{

super(context,

attrs,

defStyleAttr);

TypedArray

ta

=

context.getTheme().obtainStyledAttributes(attrs,

R.styleable.CountDownProgressBar,

defStyleAttr,

0);

int

n

=

ta.getIndexCount();

for

(int

i

=

0;

i

<

n;

i++)

{

int

attr

=

ta.getIndex(i);

switch

(attr)

{

case

R.styleable.CountDownProgressBar_countDown_firstColor:

firstColor

=

ta.getColor(attr,

Color.LTGRAY);

//

默认底色为亮灰色

break;

case

R.styleable.CountDownProgressBar_countDown_secondColor:

secondColor

=

ta.getColor(attr,

Color.BLUE);

//

默认进度条颜色为蓝色

break;

case

R.styleable.CountDownProgressBar_countDown_centerTextSize:

centerTextSize

=

ta.getDimensionPixelSize(attr,

(int)

dip2px(40));

//

默认中间文字字体大小为40dp

break;

case

R.styleable.CountDownProgressBar_countDown_circleWidth:

circleWidth

=

ta.getDimensionPixelSize(attr,

(int)

dip2px(6f));

//

默认圆弧宽度为6dp

break;

case

R.styleable.CountDownProgressBar_countDown_centerTextColor:

centerTextColor

=

ta.getColor(attr,

Color.BLUE);

//

默认中间文字颜色为蓝色

break;

case

R.styleable.CountDownProgressBar_countDown_isShowGradient:

isShowGradient

=

ta.getBoolean(attr,

false);

//

默认不适用渐变色

break;

default:

break;

}

}

ta.recycle();

circlePaint

=

new

Paint();

circlePaint.setAntiAlias(true);

//

抗锯齿

circlePaint.setDither(true);

//

防抖动

circlePaint.setStrokeWidth(circleWidth);//画笔宽度

textPaint

=

new

Paint();

textPaint.setAntiAlias(true);

textPaint.setDither(true);

}

@Override

protected

void

onMeasure(int

widthMeasureSpec,

int

heightMeasureSpec)

{

//

分别获取期望的宽度和高度,并取其中较小的尺寸作为该控件的宽和高,并且不超过屏幕宽高

int

widthPixels

=

this.getResources().getDisplayMetrics().widthPixels;//获取屏幕宽

int

heightPixels

=

this.getResources().getDisplayMetrics().heightPixels;//获取屏幕高

int

width

=

MeasureSpec.getSize(widthMeasureSpec);

int

hedight

=

MeasureSpec.getSize(heightMeasureSpec);

int

minWidth

=

Math.min(widthPixels,

width);

int

minHedight

=

Math.min(heightPixels,

hedight);

setMeasuredDimension(Math.min(minWidth,

minHedight),

Math.min(minWidth,

minHedight));

}

@Override

protected

void

onDraw(Canvas

canvas)

{

int

center

=

this.getWidth()

/

2;

int

radius

=

center

-

circleWidth

/

2;

drawCircle(canvas,

center,

radius);

//

绘制进度圆弧

drawText(canvas,

center);

}

/**

*

绘制进度圆弧

*

*

@param

canvas

画布对象

*

@param

center

圆心的x和y坐标

*

@param

radius

圆的半径

*/

private

void

drawCircle(Canvas

canvas,

int

center,

int

radius)

{

circlePaint.setShader(null);

//

清除上一次的shader

circlePaint.setColor(firstColor);

//

设置底部圆环的颜色,这里使用第一种颜色

circlePaint.setStyle(Paint.Style.STROKE);

//

设置绘制的圆为空心

canvas.drawCircle(center,

center,

radius,

circlePaint);

//

画底部的空心圆

RectF

oval

=

new

RectF(center

-

radius,

center

-

radius,

center

+

radius,

center

+

radius);

//

圆的外接正方形

if

(isShowGradient)

{

//

绘制颜色渐变圆环

//

shader类是Android在图形变换中非常重要的一个类。Shader在三维软件中我们称之为着色器,其作用是来给图像着色。

LinearGradient

linearGradient

=

new

LinearGradient(circleWidth,

circleWidth,

getMeasuredWidth()

-

circleWidth,

getMeasuredHeight()

-

circleWidth,

colorArray,

null,

Shader.TileMode.MIRROR);

circlePaint.setShader(linearGradient);

}

circlePaint.setShadowLayer(10,

10,

10,

Color.BLUE);

circlePaint.setColor(secondColor);

//

设置圆弧的颜色

circlePaint.setStrokeCap(Paint.Cap.ROUND);

//

把每段圆弧改成圆角的

alphaAngle

=

currentValue

*

360.0f

/

maxValue

*

1.0f;

//

计算每次画圆弧时扫过的角度,这里计算要注意分母要转为float类型,否则alphaAngle永远为0

canvas.drawArc(oval,

-90,

alphaAngle,

false,

circlePaint);

}

/**

*

绘制文字

*

*

@param

canvas

画布对象

*

@param

center

圆心的x和y坐标

*/

private

void

drawText(Canvas

canvas,

int

center)

{

int

result

=

((maxValue

-

currentValue)

*

(duration

/

1000)

/

maxValue);

//

计算进度

String

percent;

if

(maxValue

==

currentValue)

{

percent

=

"完成";

textPaint.setTextSize(centerTextSize);

//

设置要绘制的文字大小

}

else

{

percent

=

(result

/

60

<

10

?

"0"

+

result

/

60

:

result

/

60)

+

":"

+

(result

%

60

<

10

?

"0"

+

result

%

60

:

result

%

60);

//

percent

=

result+"秒";

textPaint.setTextSize(centerTextSize+centerTextSize/3);

//

设置要绘制的文字大小

}

textPaint.setTextAlign(Paint.Align.CENTER);

//

设置文字居中,文字的x坐标要注意

textPaint.setColor(centerTextColor);

//

设置文字颜色

textPaint.setStrokeWidth(0);

//

注意此处一定要重新设置宽度为0,否则绘制的文字会重叠

Rect

bounds

=

new

Rect();

//

文字边框

textPaint.getTextBounds(percent,

0,

percent.length(),

bounds);

//

获得绘制文字的边界矩形

FontMetricsInt

fontMetrics

=

textPaint.getFontMetricsInt();

//

获取绘制Text时的四条线

int

baseline

=

center

+

(fontMetrics.bottom

-

fontMetrics.top)

/

2

-

fontMetrics.bottom;

//

计算文字的基线

canvas.drawText(percent,

center,

baseline,

textPaint);

//

绘制表示进度的文字

}

/**

*

设置圆环的宽度

*

*

@param

width

*/

public

void

setCircleWidth(int

width)

{

this.circleWidth

=

(int)

TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,

width,

getResources()

.getDisplayMetrics());

circlePaint.setStrokeWidth(circleWidth);

//一般只是希望在View发生改变时对UI进行重绘。invalidate()方法系统会自动调用

View的onDraw()方法。

invalidate();

}

/**

*

设置圆环的底色,默认为亮灰色LTGRAY

*

*

@param

color

*/

public

void

setFirstColor(int

color)

{

this.firstColor

=

color;

circlePaint.setColor(firstColor);

//一般只是希望在View发生改变时对UI进行重绘。invalidate()方法系统会自动调用

View的onDraw()方法。

invalidate();

}

/**

*

设置进度条的颜色,默认为蓝色<br>

*

*

@param

color

*/

public

void

setSecondColor(int

color)

{

this.secondColor

=

color;

circlePaint.setColor(secondColor);

//一般只是希望在View发生改变时对UI进行重绘。invalidate()方法系统会自动调用

View的onDraw()方法。

invalidate();

}

/**

*

设置进度条渐变色颜色数组

*

*

@param

colors

颜色数组,类型为int[]

*/

public

void

setColorArray(int[]

colors)

{

this.colorArray

=

colors;

//一般只是希望在View发生改变时对UI进行重绘。invalidate()方法系统会自动调用

View的onDraw()方法。

invalidate();

}

/**

*

按进度显示百分比,可选择是否启用数字动画

*

*

@param

duration

动画时长

*/

public

void

setDuration(int

duration,

OnFinishListener

listener)

{

this.listener

=

listener;

this.duration

=

duration

+

1000;

if

(animator

!=

null)

{

animator.cancel();

}

else

{

animator

=

ValueAnimator.ofInt(0,

maxValue);

animator.addUpdateListener(new

ValueAnimator.AnimatorUpdateListener()

{

@Override

public

void

onAnimationUpdate(ValueAnimator

animation)

{

currentValue

=

(int)

animation.getAnimatedValue();

//一般只是希望在View发生改变时对UI进行重绘。invalidate()方法系统会自动调用

View的onDraw()方法。

invalidate();

if

(maxValue

==

currentValue

&&

CountDownProgressBar.this.listener

!=

null)

{

CountDownProgressBar.this.listener.onFinish();

}

}

});

animator.setInterpolator(new

LinearInterpolator());

}

animator.setDuration(duration);

animator.start();

}

public

interface

OnFinishListener

{

void

onFinish();

}

public

void

setOnFinishListener(OnFinishListener

listener)

{

this.listener

=

listener;

}

public

static

int

px2dip(int

pxValue)

{

final

float

scale

=

Resources.getSystem().getDisplayMetrics().density;

return

(int)

(pxValue

/

scale

+

0.5f);

}

public

static

float

dip2px(float

dipValue)

{

final

float

scale

=

Resources.getSystem().getDisplayMetrics().density;

return

(dipValue

*

scale

+

0.5f);

}

}xml布局:<?xml

version="1.0"

encoding="utf-8"?>

<LinearLayout

xmlns:android="/apk/res/android"

android:layout_width="match_parent"

android:layout_height="match_parent"

xmlns:app="/apk/res-auto"

android:orientation="vertical">

<Button

android:layout_width="match_parent"

android:text="开始"

android:id="@+id/btn_start"

android:layout_height="wrap_content"

/>

<com.daodaojk.myapplication.view.CountDownProgressBar

android:id="@+id/cpb_countdown"

android:layout_width="200dp"

android:layout_marginTop="100dp"

android:layout_gravity="center_horizontal"

app:countDown_centerTextSize="25dp"

app:countDown_circleWidth="4dp"

app:countDown_firstColor="@color/text_gray_ccc"

app:countDown_secondColor="@color/text_blue"

app:countDown_isShowGradient=

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论