轉自:http://droidwolf.iteye.com/blog/1356416
在android的xml佈局中,幾百上千行的xml文件是常事。佈局文件的增大一定程度上增加了視圖編寫的複雜度,而且如果視圖的嵌套越深android在加載視圖時的性能也會越差,甚至會出現一些低端設備內存不足而崩潰等奇異情況。
對性能要求比較高或適配終端機型廣泛的應用,通過編寫自定視圖控件來優化應用是常用的方式。今天我實現一個類似appstore的更新應用個數提醒的實例,來探討自畫視圖的應用場合。
或許很多人一看到上圖就會想到用FrameLayout來實現,但一個複雜的視圖想添加這種功能往往會非常複雜或有很多的顧慮,而且framelayout的過多使用又會陷入優化的陷阱。所以我用一個折中而且比較保險的方法,最小的修改視圖佈局結合自繪方式來實現這種功能。下面是最終截圖
5個底部tab通過RadioGroup結合RadioButton來實現,如果您不清楚怎麼實現該視圖請參閱《RadioGroup&RadioButton小技巧 》。紅圓和數字"8"通過繼承RadioGroup的類MyRadioGroup
重載dispatchDraw方法繪製,再用MyRadioGroup 替換佈局裏的RadioGroup。爲什麼重載的不是onDraw而是dispatchDraw呢?下面先來看看dispatchDraw的描述
在onDraw繪製您畫的元素在原佈局元素的下面,而我們是想把自己畫的元素覆蓋在原佈局元素的上面,所以得用dispatchDraw。好了一些思路講完了上代碼
- import android.content.Context;
- import android.graphics.Canvas;
- import android.graphics.Color;
- import android.graphics.Paint;
- import android.graphics.Rect;
- import android.graphics.drawable.Drawable;
- import android.util.AttributeSet;
- import android.widget.RadioGroup;
- /**
- * 轉載請註明 http://hemowolf.iteye.com
- */
- public class MyRadioGroup extends RadioGroup {
- Drawable mBg;
- Paint mPaintText;
- @Override
- protected void dispatchDraw(Canvas canvas) {
- super.dispatchDraw(canvas);
- if (mBg == null) mBg = getResources().getDrawable(R.drawable.tab_unread_bg);
- if(mPaintText==null){
- mPaintText=new Paint();
- mPaintText.setTextSize(18f);
- mPaintText.setColor(Color.WHITE);
- mPaintText.setFakeBoldText(true);
- }
- //獲取字體所佔寬度和高度
- String text="8";
- Rect rect= new Rect();
- mPaintText.getTextBounds(text, 0, text.length(), rect);
- int textWidth = rect.width(), textHeight = rect.height();
- int bgWidth = textWidth+30 > mBg.getIntrinsicWidth() ? textWidth +30: mBg.getIntrinsicWidth()
- , bgHeight = textHeight > mBg.getIntrinsicHeight() ? textHeight : mBg.getIntrinsicHeight();
- int bgX = this.getWidth() + this.getPaddingLeft() - bgWidth
- ,bgY = this.getPaddingTop();
- mBg.setBounds(bgX, bgY, bgX + bgWidth, bgY + bgHeight);
- mBg.draw(canvas);
- int x = bgX + (bgWidth - textWidth) / 2 - rect.left, y = bgY + (bgHeight - textHeight) / 2 - rect.top;
- canvas.drawText(text, x, y, mPaintText);
- }
- public MyRadioGroup(Context context) {
- super(context);
- }
- public MyRadioGroup(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
- }