Android Paint、Path详解
生活随笔
收集整理的這篇文章主要介紹了
Android Paint、Path详解
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
都是自己隨手練習時寫的一些小demo
Paint類:
package com.gyz;import android.content.Context; import android.graphics.Bitmap; import android.graphics.Bitmap.Config; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.LinearGradient; import android.graphics.Paint; import android.graphics.Path; import android.graphics.RectF; import android.graphics.Shader; import android.util.AttributeSet; import android.view.MotionEvent; import android.view.View;/*** Paint類介紹* * Paint即畫筆,在繪圖過程中起到了極其重要的作用,畫筆主要保存了顏色, 樣式等繪制信息,指定了如何繪制文本和圖形,畫筆對象有很多設置方法,* 大體上可以分為兩類,一類與圖形繪制相關,一類與文本繪制相關。* * 1.圖形繪制 setARGB(int a,int r,int g,int b); 設置繪制的顏色,a代表透明度,r,g,b代表顏色值。* * setAlpha(int a); 設置繪制圖形的透明度。* * setColor(int color); 設置繪制的顏色,使用顏色值來表示,該顏色值包括透明度和RGB顏色。* * setAntiAlias(boolean aa); 設置是否使用抗鋸齒功能,會消耗較大資源,繪制圖形速度會變慢。* * setDither(boolean dither); 設定是否使用圖像抖動處理,會使繪制出來的圖片顏色更加平滑和飽滿,圖像更加清晰* * setFilterBitmap(boolean filter); 如果該項設置為true,則圖像在動畫進行中會濾掉對Bitmap圖像的優化操作,加快顯示* 速度,本設置項依賴于dither和xfermode的設置* * setMaskFilter(MaskFilter maskfilter);* 設置MaskFilter,可以用不同的MaskFilter實現濾鏡的效果,如濾化,立體等 * setColorFilter(ColorFilter* colorfilter); 設置顏色過濾器,可以在繪制顏色時實現不用顏色的變換效果* * setPathEffect(PathEffect effect); 設置繪制路徑的效果,如點畫線等* * setShader(Shader shader); 設置圖像效果,使用Shader可以繪制出各種漸變效果* * setShadowLayer(float radius ,float dx,float dy,int color);* 在圖形下面設置陰影層,產生陰影效果,radius為陰影的角度,dx和dy為陰影在x軸和y軸上的距離,color為陰影的顏色* * setStyle(Paint.Style style); 設置畫筆的樣式,為FILL,FILL_OR_STROKE,或STROKE* * setStrokeCap(Paint.Cap cap); 當畫筆樣式為STROKE或FILL_OR_STROKE時,設置筆刷的圖形樣式,如圓形樣式* Cap.ROUND,或方形樣式Cap.SQUARE* * setSrokeJoin(Paint.Join join); 設置繪制時各圖形的結合方式,如平滑效果等* * setStrokeWidth(float width); 當畫筆樣式為STROKE或FILL_OR_STROKE時,設置筆刷的粗細度* * setXfermode(Xfermode xfermode); 設置圖形重疊時的處理方式,如合并,取交集或并集,經常用來制作橡皮的擦除效果,圖片圓角也可以* * 2.文本繪制 setFakeBoldText(boolean fakeBoldText); 模擬實現粗體文字,設置在小字體上效果會非常差* * setSubpixelText(boolean subpixelText); 設置該項為true,將有助于文本在LCD屏幕上的顯示效果* * setTextAlign(Paint.Align align); 設置繪制文字的對齊方向* * setTextScaleX(float scaleX); 設置繪制文字x軸的縮放比例,可以實現文字的拉伸的效果* * setTextSize(float textSize); 設置繪制文字的字號大小* * setTextSkewX(float skewX); 設置斜體文字,skewX為傾斜弧度* * setTypeface(Typeface typeface); 設置Typeface對象,即字體風格,包括粗體,斜體以及襯線體,非襯線體等* * setUnderlineText(boolean underlineText); 設置帶有下劃線的文字效果* * setStrikeThruText(boolean strikeThruText); 設置帶有刪除線的效果** @author gyzboy*/ public class MyCanvasTest extends View {public Paint mPaint;private Path mPath;// 定義一個內存中的圖片,該圖片將作為緩沖區private Bitmap cacheBitmap = null;// 定義cacheBitmap上的Canvas對象private Canvas cacheCanvas = null;float preX = 0;float preY = 0;/*** 為了實現保存用戶之前繪制的內容使用雙緩沖技術,程序先不繪制在view上,先繪制在一個內存中的bitmap上,* 當繪制完成后將bitmap繪制在view上* * @param context* @param attrs*/public MyCanvasTest(Context context, AttributeSet attrs) {super(context, attrs);// 父類構造器必須放到最前面mPaint = new Paint();mPath = new Path();cacheBitmap = Bitmap.createBitmap(320, 480, Config.ARGB_8888);cacheCanvas = new Canvas();cacheCanvas.setBitmap(cacheBitmap);// 將圖片畫到緩存中mPaint = new Paint(Paint.DITHER_FLAG);mPaint.setColor(Color.RED);mPaint.setStyle(Paint.Style.STROKE);mPaint.setStrokeWidth(5);mPaint.setAntiAlias(true);// 反鋸齒mPaint.setDither(true);// 與DITHER_FLAG對應,相當于開關}// @Override// protected void onDraw(Canvas canvas) {//// // 將整個桌布繪制成白色 canvas還有rotate旋轉、scale縮放、skew傾斜、translate平移屬性// canvas.drawColor(Color.WHITE);//// Paint paint = new Paint();// paint.setAntiAlias(true);// 去鋸齒// paint.setColor(Color.BLUE);// paint.setStyle(Paint.Style.STROKE);// 設置為空心// paint.setStrokeWidth(5);//// /**// * 參數依次為x,y坐標,半徑// */// canvas.drawCircle(40, 40, 30, paint);// 畫圓// /**// * 同Rect// */// canvas.drawRect(40, 40, 140, 180, paint);// 繪制矩形// canvas.drawRect(10, 50, 60, 100, paint);// 正方形// /**// * 矩形左邊的X坐標 150 矩形頂部的Y坐標 75 矩形右邊的X坐標 260 矩形底部的Y坐標 120// * 說白了就是左上角的坐標是(150,75),右下角的坐標是(260,120)// */// RectF rf1 = new RectF(150, 20, 200, 120);// rect為整型,rectF為浮點數// /**// * x,y方向的圓化角度// */// canvas.drawRoundRect(rf1, 15, 50, paint);// RectF re11 = new RectF(10, 240, 70, 270);// // 繪制橢圓// canvas.drawOval(re11, paint);// /*// * 最重要的就是movtTo和close,如果是Style.FILL的話,不設置close,也沒有區別,可是如果是STROKE模式,// * 如果不設置close,圖形不封閉。// *// * 當然,你也可以不設置close,再添加一條線,效果一樣。// */// Path path1 = new Path();// path1.moveTo(10, 340); // 路徑繪制的開始點// path1.lineTo(70, 340);// path1.lineTo(40, 290);// path1.close();// 繪制完成,形成封閉圖形,相當于畫了一條連接到開頭的直線// canvas.drawPath(path1, paint);//// /**// * 參數一為漸變起初點坐標x位置,參數二為y軸位置,參數三和四分辨對應漸變終點 其中參數new int[]{startColor,// * midleColor,endColor}是參與漸變效果的顏色集合, 其中參數new float[]{0 , 0.5f,// * 1.0f}是定義每個顏色處于的漸變相對位置, 這個參數可以為null,如果為null表示所有的顏色按順序均勻的分布// */// // 為Paint設置漸變器// Shader mShader = new LinearGradient(0, 0, 40, 60, new int[] {// Color.RED, Color.GREEN, Color.BLUE, Color.YELLOW }, null,// Shader.TileMode.REPEAT);// // Shader.TileMode三種模式// // REPEAT:沿著漸變方向循環重復// // CLAMP:如果在預先定義的范圍外畫的話,就重復邊界的顏色// // MIRROR:與REPEAT一樣都是循環重復,但這個會對稱重復// paint.setShader(mShader);// // 設置陰影// paint.setShadowLayer(45, 10, 10, Color.GRAY);// paint.setStyle(Paint.Style.FILL);// 設置為實心// // 繪制圓形// canvas.drawCircle(200, 40, 30, paint);// // 繪制字體// paint.setTextSize(40);// paint.setShader(mShader);// canvas.drawText("Circle", 100, 200, paint);//// super.onDraw(canvas);// }@Overridepublic boolean onTouchEvent(MotionEvent event) {float x = event.getX();float y = event.getY();switch (event.getAction()) {case MotionEvent.ACTION_DOWN:mPath.moveTo(x, y);preX = x;preY = y;break;case MotionEvent.ACTION_MOVE:mPath.quadTo(preX, preY, x, y);// 繪制曲線preX = x;preY = y;break;case MotionEvent.ACTION_UP:cacheCanvas.drawPath(mPath, mPaint);// 繪制// mPath.reset();//清空路徑break;}invalidate();// 返回true表明處理方法已經處理該事件,否則會繼續傳遞return true;}@Overrideprotected void onDraw(Canvas canvas) {super.onDraw(canvas);Paint bitmapPaint = new Paint();bitmapPaint.setColor(Color.BLACK);// 將cacheBitmap繪制到該View組件上canvas.drawBitmap(cacheBitmap, 50, 50, bitmapPaint);// 沿著path繪制canvas.drawPath(mPath, mPaint);} }Path類:
package com.gyz;import android.app.Activity; import android.content.Context; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.ComposePathEffect; import android.graphics.CornerPathEffect; import android.graphics.DashPathEffect; import android.graphics.DiscretePathEffect; import android.graphics.Paint; import android.graphics.Path; import android.graphics.PathDashPathEffect; import android.graphics.PathEffect; import android.graphics.RectF; import android.graphics.SumPathEffect; import android.os.Bundle; import android.view.View;/*** @author gyzboy*/ public class MyPathTest extends Activity {@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState); // setContentView(new MyView(this));setContentView(new MyTextView(this));}class MyView extends View {float phase;Path path;PathEffect[] effects;Paint paint;int[] colors;public MyView(Context context) {super(context);effects = new PathEffect[7];// 路徑效果path = new Path();colors = new int[] {};paint = new Paint();paint.setColor(Color.BLUE);paint.setAntiAlias(true);paint.setStyle(Paint.Style.STROKE);paint.setStrokeWidth(5);path.moveTo(0, 0);for (int i = 0; i < 15; i++) {// 生成15個點,隨機生成它們的Y座標。并將它們連成一條Pathpath.lineTo(i * 20, (float) Math.random() * 60);}// 初始化7個顏色colors = new int[] { Color.BLACK, Color.BLUE, Color.CYAN,Color.GREEN, Color.MAGENTA, Color.RED, Color.YELLOW };// -----------下面開始初始化7中路徑效果----------// 不使用路徑效果。effects[0] = null;// 使用CornerPathEffect路徑效果effects[1] = new CornerPathEffect(10);// 初始化DiscretePathEffecteffects[2] = new DiscretePathEffect(3.0f, 5.0f);}@Overrideprotected void onDraw(Canvas canvas) {super.onDraw(canvas);// 將背景填充成白色canvas.drawColor(Color.WHITE);// 初始化DashPathEffect,DashPathEffect有動畫效果effects[3] = new DashPathEffect(new float[] { 20, 10, 5, 10 },phase);// 初始化PathDashPathEffect,PathDashPathEffect有動畫效果Path p = new Path();p.addRect(0, 0, 8, 8, Path.Direction.CCW);effects[4] = new PathDashPathEffect(p, 12, phase,PathDashPathEffect.Style.ROTATE);// 初始化PathDashPathEffecteffects[5] = new ComposePathEffect(effects[2], effects[4]);effects[6] = new SumPathEffect(effects[4], effects[3]);// 對Canvas執行坐標變換:將畫布“整體位移”到8、8處開始繪制canvas.translate(8, 8);// 依次使用7中不同路徑效果、7種不同的顏色來繪制路徑for (int i = 0; i < effects.length; i++) {paint.setPathEffect(effects[i]);paint.setColor(colors[i]);canvas.drawPath(path, paint);canvas.translate(0, 60);// 移動畫布為了顯示出不同的路徑效果}// 改變phase值,形成動畫效果,變化速度phase += 1;invalidate();}}class MyTextView extends View {final String DRAW_STR = "來一個測試";Path[] paths = new Path[3];Paint paint;public MyTextView(Context context) {super(context);paths[0] = new Path();paths[0].moveTo(0, 0);for (int i = 1; i <= 7; i++) {// 生成7個點,隨機生成它們的Y座標。并將它們連成一條Pathpaths[0].lineTo(i * 30, (float) Math.random() * 30);}paths[1] = new Path();RectF rectF = new RectF(0, 0, 200, 120);paths[1].addOval(rectF, Path.Direction.CCW);//逆時針paths[2] = new Path();paths[2].addArc(rectF, 60, 180);// 初始化畫筆paint = new Paint();paint.setAntiAlias(true);paint.setColor(Color.CYAN);paint.setStrokeWidth(1);}@Overrideprotected void onDraw(Canvas canvas) {canvas.drawColor(Color.WHITE);canvas.translate(40, 40);// 設置從右邊開始繪制(右對齊)paint.setTextAlign(Paint.Align.RIGHT);paint.setTextSize(20);// 繪制路徑paint.setStyle(Paint.Style.STROKE);canvas.drawPath(paths[0], paint);// 沿著路徑繪制一段文本。paint.setStyle(Paint.Style.FILL);canvas.drawTextOnPath(DRAW_STR, paths[0], -8, 20, paint);// 對Canvas進行坐標變換:畫布下移120canvas.translate(0, 60);// 繪制路徑paint.setStyle(Paint.Style.STROKE);canvas.drawPath(paths[1], paint);// 沿著路徑繪制一段文本。paint.setStyle(Paint.Style.FILL);canvas.drawTextOnPath(DRAW_STR, paths[1], -20, 20, paint);// 對Canvas進行坐標變換: 畫布下移120canvas.translate(0, 120);// 繪制路徑paint.setStyle(Paint.Style.STROKE);canvas.drawPath(paths[2], paint);// 沿著路徑繪制一段文本。paint.setStyle(Paint.Style.FILL);canvas.drawTextOnPath(DRAW_STR, paths[2], -10, 20, paint);}} }
轉載于:https://www.cnblogs.com/gyzboy/p/4626751.html
與50位技術專家面對面20年技術見證,附贈技術全景圖總結
以上是生活随笔為你收集整理的Android Paint、Path详解的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: PHP的反射机制
- 下一篇: MeteoInfoLab脚本示例:TRM