編輯:關於Android編程
最近做項目,有個一個需求,就是圓角進度條。效果圖如下。
當時項目時間很緊,沒多去想怎麼實現最佳,就直接把美工給的圓角進度條裁剪成了四份。來做 Canvas 剪切繪制。這樣雖然也能達到效果,但是服用性很差。最近網上搜索了很長時間,發現Paint畫筆,有遮擋層的功能。android.graphics.Paint.setXfermode(Xfermode xfermode) 。其中一個參數就是
Mode.DST_OUT 顯示底圖與上層圖非交集的底圖圖像。於是就有個思路,先繪制圓角矩形進度條,然後設置畫筆遮擋屬性,再繪制扇形,來遮罩圓角矩形。這樣就可以實現圓角矩形進度條的功能了。
import android.content.Context; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.graphics.PorterDuff.Mode; import android.graphics.PorterDuffXfermode; import android.graphics.RectF; import android.util.AttributeSet; import android.view.SurfaceHolder; import android.view.SurfaceView; public class MySurfaceView extends SurfaceView implements SurfaceHolder.Callback{ SurfaceHolder mSurfaceHolder; boolean isRun; /** 進度條背景**/ Bitmap bmpDes; /** 移動角度**/ float m = 0; /** 包圍進度條背景的圓半徑**/ float r; /** 移動速度**/ float speed; public MySurfaceView(Context context, AttributeSet attrs) { super(context, attrs); // TODO Auto-generated constructor stub mSurfaceHolder = this.getHolder(); mSurfaceHolder.addCallback(this); /** 加載進度條**/ bmpDes = BitmapFactory.decodeResource(getResources(), R.drawable.d1).copy(Bitmap.Config.ARGB_8888, true); /** 計算半徑**/ r = (float) Math.sqrt(Math.pow(bmpDes.getWidth()/2, 2) + Math.pow(bmpDes.getHeight()/2, 2)); /** 根據25s,計算移動速度**/ speed = (float) (360 / (25000 / 33.0)); } @Override public void surfaceChanged(SurfaceHolder arg0, int arg1, int arg2, int arg3) { // TODO Auto-generated method stub } @Override public void surfaceCreated(SurfaceHolder arg0) { // TODO Auto-generated method stub isRun = true; new Thread(){ public void run(){ while(isRun){ long start = System.currentTimeMillis(); Canvas canvas = null; synchronized (mSurfaceHolder) { canvas = mSurfaceHolder.lockCanvas(); if(canvas != null ){ onGameDraw(canvas); if(canvas != null && mSurfaceHolder != null){ mSurfaceHolder.unlockCanvasAndPost(canvas); } m += speed; if(m >= 360) m = 0; } } long end = System.currentTimeMillis() - start; if(end < 33){ try { Thread.sleep(end); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } } }.start(); } @Override public void surfaceDestroyed(SurfaceHolder arg0) { // TODO Auto-generated method stub isRun = false; } private void onGameDraw(Canvas canvas){ /* canvas.drawColor(Color.BLACK); c = new Canvas(bmpDes); Paint paint = new Paint(); paint.setAntiAlias(true); paint.setXfermode(new PorterDuffXfermode(Mode.DST_OUT)); int sc = c.saveLayer(0, 0, bmpDes.getWidth(), bmpDes.getHeight(), null, LAYER_FLAGS); c.drawArc(new RectF(-(r - bmpDes.getWidth()/2), -(r - bmpDes.getHeight()/2), r*2, r*2), 0, m, true, paint); c.restoreToCount(sc); canvas.drawBitmap(bmpDes, 0, 0, null);*/ canvas.drawColor(Color.BLACK); Paint paint = new Paint(); paint.setFilterBitmap(false); // 繪制第二層 int sc = canvas.saveLayer(0, 0, 0 + bmpDes.getWidth(), 0 + bmpDes.getHeight(), null, Canvas.MATRIX_SAVE_FLAG | Canvas.CLIP_SAVE_FLAG | Canvas.HAS_ALPHA_LAYER_SAVE_FLAG | Canvas.FULL_COLOR_LAYER_SAVE_FLAG | Canvas.CLIP_TO_LAYER_SAVE_FLAG); // 繪制進度條背景 canvas.drawBitmap(bmpDes, 0, 0, paint); // 設置遮擋屬性 paint.setXfermode(new PorterDuffXfermode(Mode.DST_OUT)); // 繪制遮擋扇形 canvas.drawArc(new RectF(-(r - bmpDes.getWidth()/2), -(r - bmpDes.getHeight()/2), r*2, r*2), 0, m, true, paint); // 將第二層反饋給畫布 canvas.restoreToCount(sc); } }
動態加載、插件化開發很重要當今360手機助手(DroidPlugin),個人開源(VirtualApp)、百度DL、攜程DynamicAPK都用到了該技術本例的大概思路是
為什麼要使用多線程下載呢?究其原因就一個字:"快",使用多線程下載的速度遠比單線程的下載速度要快,說到下載速度,決定下載速度的因素一般有兩個:一個是客
ListView是Android軟件開發中十分常用也十分重要的一個UI控件。ListView的每一個子項可以是一個簡單的字符串,也可以是一組View的組合,開發者完全可以
一、什麼是多媒體多媒體(duō méi tǐ) 的英文單詞是Multimedia,它由media和multi兩部分組成。一般理解為多種媒體的綜合多媒體是計算