下面是他的網址
http://www.curious-creature.org/2012/12/13/android-recipe-2-fun-with-shaders/
他的做法其實是利用 canvas draw bitmap 以及 paint來完成,
首先他將背景設置到 paint,
接著將mask 轉成 alpha 接著在canvas上繪製就完成了。
知道大概要怎麼做之後,我們來看code
- 將背景設置到 paint
private void createShader() { View target = getRootView().findViewById(mTargetId); mTargetBitmap = createBitmap(target); Shader targetShader = createShader(mTargetBitmap); mPaint.setShader(targetShader); } private static Shader createShader(Bitmap b) { return new BitmapShader(b, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP); } private static Bitmap createBitmap(View target) { Bitmap b = Bitmap.createBitmap(target.getWidth(), target.getHeight(), Bitmap.Config.ARGB_8888); Canvas c = new Canvas(b); target.draw(c); return b; }
- 接著將mask圖轉成alpha
mMask = convertToAlphaMask(BitmapFactory.decodeResource(getResources(), maskId)); private static Bitmap convertToAlphaMask(Bitmap b) { Bitmap a = Bitmap.createBitmap(b.getWidth(), b.getHeight(), Bitmap.Config.ALPHA_8); Canvas c = new Canvas(a); c.drawBitmap(b, 0.0f, 0.0f, null); return a; }
- 接著在canvas上繪製
canvas.drawBitmap(mMask, 0.0f, 0.0f, mPaint);
基本的功能這樣就完成了,如下圖
接著該如何讓spotlight移動以及放大是另一個問題,
假設我們希望將剛剛的spotlight放大3倍,並且移至較中間的位置 100,100 我們應該怎麼做呢?
mShaderMatrix.setScale(1.0f / 3, 1.0f / 3); mShaderMatrix.preTranslate(-100, -100); mPaint.getShader().setLocalMatrix(mShaderMatrix); canvas.translate(100, 100); canvas.scale(3, 3); canvas.drawBitmap(mMask, 0.0f, 0.0f, mPaint);
可以發現,作者的做法是
- 先將背景先縮小並反向位移
- 接著再將整個畫布放大並位移
也就是原先看到的mask 被放大的並位移到較中間的位置,而背景的縮放以及位移被抵銷掉
結果的圖如下
由於作者的範例包含太多動畫,所以我寫了一個更簡單的sample,由兩個按鈕來控制
postion以及 scale ,讓大家比較容易trace,附上 sample code
沒有留言:
張貼留言