android自定義控制元件
阿新 • • 發佈:2022-04-29
Android為開發者提供了大量的控制元件,這些控制元件只能滿足一般性的需求,有時候需要開發者重新定製控制元件。控制元件的定製有三種形式:對原有控制元件的重寫;對原有控制元件進行組合;自定義新的控制元件。Android中所有控制元件類都是View的子類。
本例主要是講一個自定義時鐘控制元件,該控制元件直接繼承View類。
1.控制元件類
首先需要編寫控制元件類,該類繼承View類,並實現介面Runnable。時鐘控制元件主要包含的引數:clockimageresourceid,scale,handcenterwidthscale,handcenterheightscale,minutehandsize,hourhandsize。
1 public class HandClock extends View implements Runnable { 2 3 private int clockImageResourceId;//影象資源id 4 private Bitmap bitmap;//影象資源 5 private float scale;//影象顯示的比例 6 private float handCenterWidthScale;//橫座標顯示比例 7 private float handCenterHeightScale;//縱座標顯示比例 8 private int minuteHandSize;//分鐘長度 9 private int hourHandSize;//時針長度 10 private Handler hanlder=new Handler(); 11 public HandClock(Context context, AttributeSet attrs) { 12 super(context, attrs); 13 // TODO Auto-generated constructor stub 14 //讀取屬性值 15 clockImageResourceId=attrs.getAttributeResourceValue(null, "clockImageSrc", 0); 16 if(clockImageResourceId>0) 17 { 18 bitmap=BitmapFactory.decodeResource(getResources(), clockImageResourceId); 19 } 20 scale=attrs.getAttributeFloatValue(null, "scale", 1); 21 handCenterWidthScale=attrs.getAttributeFloatValue(null, "handCenterWidthScale", bitmap.getWidth()/2); 22 handCenterHeightScale=attrs.getAttributeFloatValue(null, "handCenterHeightScale", bitmap.getHeight()/2); 23 minuteHandSize=(int)(attrs.getAttributeIntValue(null, "minuteHandSize",0)*scale); 24 hourHandSize=(int)(attrs.getAttributeIntValue(null, "hourHandSize", 0)*scale); 25 int curentSecond=Calendar.getInstance().get(Calendar.SECOND); 26 hanlder.postDelayed(this, (60-curentSecond)*1000); 27 } 28 29 protected void onDetachedFromWindow() 30 { 31 super.onDetachedFromWindow(); 32 hanlder.removeCallbacks(this); 33 } 34 @Override 35 public void run() { 36 // TODO Auto-generated method stub 37 invalidate(); 38 hanlder.postDelayed(this,60*1000); 39 } 40 protected void onMeasure(int widthMeasurespc,int heightMeasurespe) 41 { 42 super.onMeasure(widthMeasurespc, heightMeasurespe); 43 setMeasuredDimension((int)(bitmap.getWidth()*scale),(int)(bitmap.getHeight()*scale)); 44 45 } 46 protected void onDraw(Canvas canvas) 47 { 48 super.onDraw(canvas); 49 Paint paint=new Paint(); 50 Rect src=new Rect(); 51 Rect target=new Rect(); 52 src.left=0; 53 src.top=0; 54 src.right=bitmap.getWidth(); 55 src.bottom=bitmap.getHeight(); 56 target.left=0; 57 target.top=0; 58 target.bottom=(int)(src.bottom*scale); 59 target.right=(int)(src.right*scale); 60 //畫表盤影象 61 canvas.drawBitmap(bitmap, src, target,paint); 62 //計算錶盤中心點的橫座標 63 float centerX=bitmap.getWidth()*scale*handCenterWidthScale; 64 //計算錶盤中心店的縱座標 65 float centerY=bitmap.getHeight()*scale*handCenterHeightScale; 66 67 canvas.drawCircle(centerX, centerY, 5, paint); 68 paint.setStrokeWidth(3); 69 Calendar calendar=Calendar.getInstance(); 70 int currentMin=calendar.get(Calendar.MINUTE); 71 int currentHour=calendar.get(Calendar.HOUR); 72 //計算時針和分針角度 73 double minuteRadian=Math.toRadians((360-((currentMin*6)-90))%360); 74 double hourRadian=Math.toRadians((360-((currentHour*30)-90))%360-(30*currentMin/60)); 75 //畫分針 76 canvas.drawLine(centerX, centerY,(int)(centerX+minuteHandSize*Math.cos(minuteRadian)),(int)(centerY-minuteHandSize*Math.sin(minuteRadian)),paint); 77 paint.setStrokeWidth(4); 78 //畫時針 79 canvas.drawLine(centerX, centerY,(int)(centerX+hourHandSize*Math.cos(hourRadian)),(int)(centerY-hourHandSize*Math.sin(hourRadian)),paint); 80 } 81 82 }
這裡面有很多重點,比如說時針與分針角度的計算,重繪的時間等。Runnable介面是軟定時器類,這裡定義一分鐘重繪一次。
2.handclok.xml
在一個xml頁面引用剛剛自定義的控制元件。
1 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 2 android:layout_width="match_parent" 3 android:layout_height="match_parent" 4 android:orientation="vertical" > 5 6 <com.example.myandroiddemp.HandClock 7 android:layout_width="wrap_content" 8 android:layout_height="wrap_content" 9 clockImageSrc="@drawable/clock1" 10 scale="0.7" 11 handCenterWidthScale="0.5" 12 handCenterHeightScale="0.5" 13 minuteHandSize="54" 14 hourHandSize="40"/> 15 16 </LinearLayout>