欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Android自定義View實(shí)現(xiàn)簡單的圓形Progress效果

 更新時間:2016年09月03日 08:51:57   作者:Rabbit丶  
這篇文章主要介紹了Android自定義View實(shí)現(xiàn)簡單的圓形Progress效果的相關(guān)資料,非常不錯,具有參考借鑒價值,需要的朋友可以參考下

先給大家展示下效果圖,如果感覺不錯,請參考實(shí)現(xiàn)思路:

我們要實(shí)現(xiàn)一個自定義的再一個圓形中繪制一個弧形的自定義View,思路是這樣的:

  先要創(chuàng)建一個類ProgressView,繼承自View類,然后重寫其中的兩個構(gòu)造方法,一個是一個參數(shù)的,一個是兩個參數(shù)的,因?yàn)槲覀円趚ml文件中使用該自定義控件,所以必須要定義這個兩個參數(shù)的構(gòu)造函數(shù)。創(chuàng)建完了這個類后,我們先不去管它,先考慮我們實(shí)現(xiàn)的這個自定義View,我們想讓它的哪些部分可以由使用者自己指定,比如說這個Demo中我們讓他的外面圓的外邊框顏色和寬度,還有扇形部分的顏色,扇形增長的速度等等屬性,這時候我們要在項(xiàng)目工程目錄的res/values目錄下創(chuàng)建一個資源文件命名為attrs(注意,名字隨意,只是大多數(shù)情況下都這么叫而已),然后我們在這個資源文件中添加我們想要的屬性,如下:

<?xml version="1.0" encoding="utf-8"?>
<resources>
<declare-styleable name="ProgressView">
<!--circleColor 設(shè)置圓形邊框的顏色 sweepColor設(shè)置扇形變換的顏色
startAngle 設(shè)置起始角度 sweepStep 設(shè)置變換的步長-->
<attr name="circleColor" format="color|reference"></attr>
<attr name="sweepColor" format="color|reference"></attr>
<attr name="startAngle" format="integer"></attr>
<attr name="sweepStep" format="integer"></attr>
<attr name="padding" format="integer"></attr>
</declare-styleable>
</resources>

可以看到,<declare-styleable>標(biāo)簽中的name屬性是為了方便我們獲取AttributeSet時候使用,而<attr>標(biāo)簽中name,則是我們希望控件可以自定義的屬性部分,類似于xml文件中的android:name=""等標(biāo)簽的使用。format屬性是設(shè)置該屬性可以接受什么類型的參數(shù)。

定義好了自定義資源類,我們開始寫ProgressView中的主要代碼:

package com.yztc.customprogressview;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.RectF;
import android.util.AttributeSet;
import android.view.View;
/**
* 自定義的
*/
public class ProgressView extends View {
private int sweepStep = 10;//扇形變換的步長(就是角度)
private int padding = 40;//外邊框距離扇形的距離 填充
private int circleColor = Color.GRAY;//邊框的顏色
private int sweepColor = Color.BLUE;//扇形顏色
private int startAngle = 90;//起始角度
//設(shè)置外邊框圓的邊框粗細(xì)
private int storke = 20;
private int sweepAngle = 0;//掃過的角度
private static final int DEFAULT_WIDTH = 200;
private static final int DEFAULT_HEIGHT = 200;
public ProgressView(Context context) {
super(context);
}
//如果要在xml文件中使用該自定義控件,則必須重寫兩個參數(shù)的構(gòu)造函數(shù)
//因?yàn)槲覀兪褂米远x的屬性的時候,會默認(rèn)傳遞過來一個AttributeSet集合
public ProgressView(Context context, AttributeSet attrs) {
super(context, attrs);
TypedArray array = context.obtainStyledAttributes(attrs, R.styleable.ProgressView);
if (array != null) {
//獲取我們在xml中設(shè)置的各個自定義屬性
sweepStep = array.getInteger(R.styleable.ProgressView_sweepStep, sweepStep);
padding = array.getInteger(R.styleable.ProgressView_padding, padding);
circleColor = array.getColor(R.styleable.ProgressView_circleColor, circleColor);
sweepColor = array.getColor(R.styleable.ProgressView_sweepColor, sweepColor);
startAngle = array.getInteger(R.styleable.ProgressView_startAngle, startAngle);
//回收TypeArray資源
array.recycle();
}
}
/**
* 先繪制外邊框 --內(nèi)部扇形
*
* @param canvas
*/
@Override
protected void onDraw(Canvas canvas) {
Paint mPaint = new Paint();
mPaint.setAntiAlias(true); //設(shè)置抗鋸齒
//繪制外層的圓框
mPaint.setColor(circleColor);
mPaint.setStrokeWidth(storke);
mPaint.setStyle(Paint.Style.STROKE);//設(shè)置圓形為空心的圓
//這里我們得到控件的Height和Width,根據(jù)Heigh和Width來確定圓心的位置,來繪制外層圓
canvas.drawCircle(getWidth() / 2, getWidth() / 2, getWidth() / 2 - storke / 2, mPaint);
// Log.d("tag", "onDraw: "+getWidth());
invalidate();//請求重新繪制view
//繪制內(nèi)部的扇形
mPaint.setStyle(Paint.Style.FILL_AND_STROKE);
mPaint.setColor(sweepColor);
/*
drawArc(RectF oval, float startAngle, float sweepAngle, boolean useCenter,Paint paint)
RectF oval 指定扇形的矩形容器對象 指定圓弧的外輪廓的矩形
float startAngle 表示圓弧的起始角度
float sweepAngle 表示圓弧走過掃過的角度 順時針方向
boolean useCenter 如果設(shè)置為true 在繪制圓弧時將圓心包括在內(nèi),是指以一個固定的圓心來繪制弧形(扇形),
如果指定為false,則不規(guī)則繪制扇形
Paint paint 畫筆 顏色 填充
public RectF(float left, float top, float right, float bottom)
float left 矩形的左邊點(diǎn)(左切點(diǎn))的x坐標(biāo)
float top 矩形上邊點(diǎn)(上切點(diǎn))的y軸坐標(biāo)
float right, 矩形的右邊點(diǎn)(右切點(diǎn))的x坐標(biāo)
float bottom 矩形的下邊點(diǎn)(下切點(diǎn))的y坐標(biāo)
*/
//RectF中的四個參數(shù),分別對應(yīng)其內(nèi)切圓的四個切點(diǎn)的坐標(biāo)
RectF rectF = new RectF(padding + storke, padding + storke, getWidth() - padding - storke, getWidth() - padding - storke);
canvas.drawArc(rectF, startAngle, sweepAngle, true, mPaint);
sweepAngle += sweepStep;//根據(jù)步長更新掃過的角度
sweepAngle = sweepAngle > 360 ? 0 : sweepAngle;
invalidate();//重繪view
}
//因?yàn)槲覀兪抢^承的View來自定義的View,所以onMeasure()方法要重寫
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
int wMode = MeasureSpec.getMode(widthMeasureSpec);
int hMode = MeasureSpec.getMode(heightMeasureSpec);
int wSize = MeasureSpec.getSize(widthMeasureSpec);
int hSize = MeasureSpec.getSize(heightMeasureSpec);
//因?yàn)槔L制的是圓,所以判斷一下高度或者寬度中的一個就可以。
switch (wMode) {
case MeasureSpec.AT_MOST://android:layout_width="warp_content"
//獲取屏幕像素
float density = getResources().getDisplayMetrics().density;
wSize = (int) (DEFAULT_WIDTH * density);
hSize = (int) (DEFAULT_HEIGHT * density);
break;
//當(dāng)在xml中指定控件的寬高為match_parent或者指定數(shù)值的寬高時,回調(diào)以下代碼
case MeasureSpec.EXACTLY://android:layout_width="match_parent" android:layout_width="40dp"
wSize = hSize = Math.min(wSize, hSize);
break;
}
//只要重寫onMeasure()方法,一定要調(diào)用以下方法,不然會報錯
setMeasuredDimension(wSize, hSize);
}
}

我們先畫一個外部的圓,也就是都用drawCircle()方法,這里我們調(diào)用getWidth(),getHeight()表示得到布局中設(shè)置的控件的尺寸,因?yàn)槭菆A,所以可以使用getWidth()/2來表示圓心位置。而畫內(nèi)部弧形的時候,確定其圓心位置,左部點(diǎn)的坐標(biāo)是外面圓的邊框加上弧形與原的間距padding來確定,右側(cè)點(diǎn)的x坐標(biāo)則是getWidth()得到總長度,減去邊框?qū)挾龋贉p去padding得到,上邊距和下邊距同樣,不明白的畫一個圖立馬明白。大部分不好理解的地方都有注釋,只要認(rèn)真看不會看不明白的~

然后就是在布局中引入我們的自定義View了:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.yztc.customprogressview.MainActivity">
<com.yztc.customprogressview.ProgressView
android:id="@+id/pv"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#0000ff"
app:padding="20"
app:circleColor="#aa0000"
app:sweepColor="#00aa00"
app:sweepStep="1"
app:startAngle="180"
/>
</RelativeLayout>

需要注意的是我們需要在布局的跟標(biāo)簽下面加上這么一段代碼:xmlns:app="http://schemas.android.com/apk/res-auto"

用來指定我們可以使用自己再attrs中自定義的屬性啦~,使用的形式就是app:你定義的屬性。當(dāng)然,這個app也不是固定的寫法,只要跟上面你加的那段代碼的xmlns后面的字段一致就可以了~

還有需要注意的是:

默認(rèn)使用Canvas類的drawCircle()方法來畫圓的時候,圓的半徑是你指定的半徑,再加上一半的邊長,比如你的邊框size=10,radius=50,則實(shí)際空心部分的半徑為55.注意這點(diǎn),否則畫出來的圓的四個切點(diǎn)位置會與其他位置有些不一樣,類似出現(xiàn)鋸齒的效果。具體請看drawCircle()的Rect邊框問題。

以上所述是小編給大家介紹的Android自定義View實(shí)現(xiàn)簡單的圓形Progress效果,希望對大家有所幫助,如果大家有任何疑問歡迎給我留言,小編會及時回復(fù)大家的!

相關(guān)文章

  • Android中文件讀寫(輸入流和輸出流)操作小結(jié)

    Android中文件讀寫(輸入流和輸出流)操作小結(jié)

    這篇文章主要介紹了Android中文件讀寫(輸入流和輸出流)操作小結(jié),本文總結(jié)了Android中文件讀寫的原理、字節(jié)流和字符流的區(qū)別、文件讀寫的步驟、輸入流和輸出流以及代碼實(shí)例等內(nèi)容,需要的朋友可以參考下
    2015-06-06
  • Android實(shí)現(xiàn)沉浸式狀態(tài)欄

    Android實(shí)現(xiàn)沉浸式狀態(tài)欄

    這篇文章主要為大家詳細(xì)介紹了Android沉浸式狀態(tài)欄的實(shí)現(xiàn)代碼,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2016-11-11
  • 深入分析Android構(gòu)建過程

    深入分析Android構(gòu)建過程

    本篇內(nèi)容主要講了Android 構(gòu)建的過程需要的步驟以及從編譯到生成等原理,一起來學(xué)習(xí)下。
    2017-11-11
  • Android 截圖功能源碼的分析

    Android 截圖功能源碼的分析

    這篇文章主要介紹了Android 截圖功能源碼的分析的相關(guān)資料,希望通過本文能幫助到大家,需要的朋友可以參考下
    2017-09-09
  • Android中Home鍵的監(jiān)聽和攔截示例

    Android中Home鍵的監(jiān)聽和攔截示例

    本篇文章主要介紹了Android中Home鍵的監(jiān)聽和攔截示例,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2017-02-02
  • Android App開發(fā)中Gradle構(gòu)建過程的配置方法

    Android App開發(fā)中Gradle構(gòu)建過程的配置方法

    這篇文章主要介紹了Android App開發(fā)中Gradle構(gòu)建過程的配置方法,包括在Gradle中配置manifest的方法,需要的朋友可以參考下
    2016-06-06
  • Android5.0新控件實(shí)例詳解

    Android5.0新控件實(shí)例詳解

    谷歌在推出Android5.0的同時推出了一些新控件,Android5.0中最常用的新控件有下面5種。具體哪五種大家通過本文學(xué)習(xí)下
    2018-02-02
  • Opengl?ES之紋理貼圖使用示例

    Opengl?ES之紋理貼圖使用示例

    這篇文章主要為大家介紹了Opengl?ES之紋理貼圖使用示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-09-09
  • Android事件傳遞機(jī)制

    Android事件傳遞機(jī)制

    這篇文章主要介紹了Android事件傳遞機(jī)制的相關(guān)資料,需要的朋友可以參考下
    2016-02-02
  • Android ndk獲取手機(jī)內(nèi)部存儲卡的根目錄方法

    Android ndk獲取手機(jī)內(nèi)部存儲卡的根目錄方法

    今天小編就為大家分享一篇Android ndk獲取手機(jī)內(nèi)部存儲卡的根目錄方法,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2018-08-08

最新評論