Androidカスタムプログレスバーの角の横のプログレスバーの例を詳しく説明します。
1.本論文では、ユーザー定義の進捗書の書き方を紹介します。比較的簡単ですが、いくつかの知識点は注意が必要です。
invalidate()方法
RectF方法の応用
オンメスア法の応用
2.原理
3層の角を丸くした長方形を描きます。下の方は黒で、2層目は灰色で、一番上の方はプログレスバーの色です。
3.効果図
円角プログレスを実現するには他にも多くの方法があります。例えば、プログレスコントロールに円角画像を充填し、写真を引き伸ばすことで予想される効果が得られます。
4.解説方法
(1)invalidate()方法
invalidate()はViewを更新するためのものであり、UIスレッドで作業しなければならない。例えば、あるviewの表示を修正する時に、invalidate()を呼び出して、再描画の画面が見えます。invalidate()の呼び出しは、以前の古いviewをメインUIスレッドの列からpopします。通常はカスタムコントロールでこの方法が使われます。
(2)RectF方法の応用
RectFは長方形を描く方法です。
RectF(left,top,right,bottom)は、4つのパラメータの意味は、それぞれ親のコントロールから矩形の左上と右下の余白の距離です。以下は図で説明します。
drawRoundRect方法は、角を丸くした長方形を描くためのもので、そのパラメータは以下の通りです。
パラメータの説明
rect:RectFオブジェクトです。
rx:x方向の円角半径。
y方向の円角半径
paint:描画時に使うブラシです。
(3)onMeasre方法
スクリーン上のカスタムコントロールのサイズを指定します。オンメスア方式の2つのパラメータは前のコントロールから入ってきたサイズで、モードとサイズが混在している数値です。Meass reSpec.getModeがモードを得るために必要です。
オンメスアのいくつかのモードはそれぞれEXACT LYで、AT_MOST、UNSPECIFFIED。
[1]Meass reSpec.EXACT LY
Meass reSpec.EXACT LYは正確なサイズです。コントロールのlayout_widthまたはlayout_heightが具体的な数値に指定されている場合は、andored:layout_width=「50 dip」またはFILL_PARDENTは、コントロールのサイズが決まっている場合で、正確なサイズです。
[2]Meass reSpec.AT_MOST
Meass reSpec.AT_MOSTは最大サイズで、コントロールのlayout_になります。widthまたはlayout_heightはWRAP_に指定されていますCONTENTの場合、コントロールのサイズは通常コントロールのサブスペースや内容によって変化します。この場合、コントロールのサイズは親コントロールが許可する最大サイズを超えない限り大丈夫です。ですから、この時のモードはAT_です。MOST,sizeは、親コントロールが許可する最大サイズを与えます。
[3]Meass reSpec.UNSPECIFIED
Meass reSpec.UNSPECIFFIEDはサイズが指定されていません。このような場合は多くなく、一般的には親コントロールがAdapterViewであり、measre方式で入ってくるモードです。
5.activitymail.xmlファイル:
invalidate()方法
RectF方法の応用
オンメスア法の応用
2.原理
3層の角を丸くした長方形を描きます。下の方は黒で、2層目は灰色で、一番上の方はプログレスバーの色です。
3.効果図
円角プログレスを実現するには他にも多くの方法があります。例えば、プログレスコントロールに円角画像を充填し、写真を引き伸ばすことで予想される効果が得られます。
4.解説方法
(1)invalidate()方法
invalidate()はViewを更新するためのものであり、UIスレッドで作業しなければならない。例えば、あるviewの表示を修正する時に、invalidate()を呼び出して、再描画の画面が見えます。invalidate()の呼び出しは、以前の古いviewをメインUIスレッドの列からpopします。通常はカスタムコントロールでこの方法が使われます。
(2)RectF方法の応用
RectFは長方形を描く方法です。
RectF(left,top,right,bottom)は、4つのパラメータの意味は、それぞれ親のコントロールから矩形の左上と右下の余白の距離です。以下は図で説明します。
drawRoundRect方法は、角を丸くした長方形を描くためのもので、そのパラメータは以下の通りです。
パラメータの説明
rect:RectFオブジェクトです。
rx:x方向の円角半径。
y方向の円角半径
paint:描画時に使うブラシです。
(3)onMeasre方法
スクリーン上のカスタムコントロールのサイズを指定します。オンメスア方式の2つのパラメータは前のコントロールから入ってきたサイズで、モードとサイズが混在している数値です。Meass reSpec.getModeがモードを得るために必要です。
オンメスアのいくつかのモードはそれぞれEXACT LYで、AT_MOST、UNSPECIFFIED。
[1]Meass reSpec.EXACT LY
Meass reSpec.EXACT LYは正確なサイズです。コントロールのlayout_widthまたはlayout_heightが具体的な数値に指定されている場合は、andored:layout_width=「50 dip」またはFILL_PARDENTは、コントロールのサイズが決まっている場合で、正確なサイズです。
[2]Meass reSpec.AT_MOST
Meass reSpec.AT_MOSTは最大サイズで、コントロールのlayout_になります。widthまたはlayout_heightはWRAP_に指定されていますCONTENTの場合、コントロールのサイズは通常コントロールのサブスペースや内容によって変化します。この場合、コントロールのサイズは親コントロールが許可する最大サイズを超えない限り大丈夫です。ですから、この時のモードはAT_です。MOST,sizeは、親コントロールが許可する最大サイズを与えます。
[3]Meass reSpec.UNSPECIFIED
Meass reSpec.UNSPECIFFIEDはサイズが指定されていません。このような場合は多くなく、一般的には親コントロールがAdapterViewであり、measre方式で入ってくるモードです。
5.activitymail.xmlファイル:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/container"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.example.progresstest.MainActivity"
tools:ignore="MergeRootFrame" >
<com.example.progresstest.ProgressViewTest
android:id="@+id/progressbar"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
</LinearLayout>
6.ProgressView Test.javaファイル
package com.example.progresstest;
import android.content.Context;
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 ProgressViewTest extends View {
/** */
private float maxCount;
/** */
private float currentCount;
/** */
private Paint mPaint;
private int mWidth,mHeight;
public ProgressViewTest(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
// TODO Auto-generated constructor stub
}
public ProgressViewTest(Context context, AttributeSet attrs) {
super(context, attrs);
// TODO Auto-generated constructor stub
}
public ProgressViewTest(Context context) {
super(context);
// TODO Auto-generated constructor stub
}
/***
*
* @param maxCount
*/
public void setMaxCount(float maxCount) {
this.maxCount = maxCount;
}
/**
*
*/
public double getMaxCount(){
return maxCount;
}
/***
*
* @param currentCount
*/
public void setCurrentCount(float currentCount) {
this.currentCount = currentCount > maxCount ? maxCount : currentCount;
/**
* invalidate() View , UI 。 view ,
* invalidate() 。invalidate() view UI
* pop 。
*/
invalidate();
}
@Override
protected void onDraw(Canvas canvas) {
// TODO Auto-generated method stub
super.onDraw(canvas);
mPaint = new Paint();
//
mPaint.setAntiAlias(true);
//
mPaint.setColor(Color.BLACK);
int round = mHeight/2;
/**
* RectF: , left,top,right,bottom
*
*/
RectF rf = new RectF(0, 0, mWidth, mHeight);
/* , */
canvas.drawRoundRect(rf, round, round, mPaint);
/* progress */
mPaint.setColor(Color.rgb(211, 211, 211));
RectF rectBlackBg = new RectF(2, 2, mWidth-2, mHeight-2);
canvas.drawRoundRect(rectBlackBg, round, round, mPaint);
//
float section = currentCount/maxCount;
RectF rectProgressBg = new RectF(3, 3, (mWidth-3)*section, mHeight-3);
if(section!=0.0f){
mPaint.setColor(Color.GREEN);
}else{
mPaint.setColor(Color.TRANSPARENT);
}
canvas.drawRoundRect(rectProgressBg, round, round, mPaint);
}
//dip * scale + 0.5f * (dip >= 0 ? 1 : -1)
private int dipToPx(int dip){
float scale = getContext().getResources().getDisplayMetrics().density;
return (int) (dip * scale + 0.5f * (dip >= 0 ? 1 : -1));// 0.5
}
/** ,onMeasure
* , , MeasureSpec.getMode(widthMeasureSpec)
* ,MeasureSpec.getSize(widthMeasureSpec)
*
*/
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
// TODO Auto-generated method stub
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
int widthSpecMode = MeasureSpec.getMode(widthMeasureSpec);
int heightSpecMode = MeasureSpec.getMode(heightMeasureSpec);
int widthSpecSize = MeasureSpec.getSize(widthMeasureSpec);
int heightSpecSize = MeasureSpec.getSize(heightMeasureSpec);
//MeasureSpec.EXACTLY,
if (widthSpecMode == MeasureSpec.EXACTLY || widthSpecMode == MeasureSpec.AT_MOST) {
mWidth = widthSpecSize;
} else {
mWidth = 0;
}
//MeasureSpec.AT_MOST, , ,MeasureSpec.UNSPECIFIED
if (heightSpecMode == MeasureSpec.AT_MOST || heightSpecMode == MeasureSpec.UNSPECIFIED) {
mHeight = dipToPx(20);
} else {
mHeight = heightSpecSize;
}
//
setMeasuredDimension(mWidth, mHeight);
}
}
MainActivity.javaファイル
package com.example.progresstest;
import android.support.v7.app.ActionBarActivity;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
public class MainActivity extends ActionBarActivity {
private ProgressViewTest progress;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
progress = (ProgressViewTest) findViewById(R.id.progressbar);
progress.setMaxCount(100);
new Thread(new Runnable() {
@Override
public void run() {
// TODO Auto-generated method stub
for (int i = 0; i <=progress.getMaxCount(); i++) {
Message msg = new Message();
msg.arg1 = i;
msg.what = 0x01;
handler.sendMessage(msg);
try {
// 0.1 1
Thread.sleep(100);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}).start();
}
Handler handler = new Handler(){
public void handleMessage(Message msg) {
if(msg.what==0x01){
progress.setCurrentCount(msg.arg1);
}
};
};
}
以上は小编が绍介したAndroidカスタムプログレスバーの丸い角横のプログレスバーの実例です。皆さんに助けてほしいです。もし何か疑问があれば、メッセージをください。小编はすぐに返事します。ここでも私たちのサイトを応援してくれてありがとうございます。