1. 程式人生 > >我的自定義View學習筆記(二)—— Paint 使用

我的自定義View學習筆記(二)—— Paint 使用

  • 這個一個系列,本系列講的都是本人自定義 View 的學習筆記。目的是加深影響,便於在以後工作中遇到相關問題的時候,能夠有個印象知道到哪裡去尋找答案。
  • 這是我學習扔物線大神的自定義 View 教程,自己記錄的筆記。連結在這裡HenCoder,強烈推薦大家去原地址學習,畢竟我寫的筆記只是針對我個人的口味而言的,用詞和對概念的理解不一定有扔物線大神準確。

對 Paint 中的方法進行記錄

  • Paint 的方法主要分為四類
    • 顏色
    • 效果
    • drawText()
    • 初始化

一、顏色

image

canvas 中有多種繪製顏色的方式。最後一種就涉及到本文章主要說的 Paint 的使用

  • drawColor/RGB/ARGB() 直接傳入顏色
  • drawBitmap() 傳入的是 bitmap 的顏色(並沒覺得繪製圖片和顏色有關係
  • drawCircle()、drawPath()、drawText() 等多種繪製方法,使用 paint 中的顏色

Paint中使用顏色

1、直接設定顏色

  • setColor(int color)
    • 直接傳入 Color.parse("#000000") 括號內就是顏色的程式碼
  • setARGB(int a, int r, int g, int b)
    • 顏色的三原色傳入

2、設定 Shader(著色器) 傳入顏色

        Paint paint = new Paint();
        paint.setStyle(Paint.Style.FILL);
        paint.setAntiAlias(true);
        Shader linerGradient0 = new LinearGradient(0, 100, 200, 100,
                Color.parseColor("#E91E63"), Color.parseColor("#2196F3"),
                Shader.TileMode.CLAMP);
        paint.setShader(linerGradient0);
        canvas.drawCircle(100, 100, 100, paint);
  • 顏色漸變 Gradient
    • 線性漸變 LinearGradient
      • 定義兩個點,從兩點之間漸變
        Shader linerGradient0 = new LinearGradient(0, 100, 200, 100,
                Color.parseColor("#E91E63"), Color.parseColor("#2196F3"),
                Shader.TileMode.CLAMP);
- 輻射漸變 RadialGradient
    - 從中間向外,輻射型漸變
        Shader radialGradient0 = new RadialGradient(100, 350, 100,
                Color.parseColor("#E91E63"), Color.parseColor("#2196F3"),
                Shader.TileMode.CLAMP);
- 掃描漸變 SweepGradient
    - 扇面掃描型別的漸變
        Shader sweepGradient = new SweepGradient(300, 300, Color.parseColor("#E91E63"),
                Color.parseColor("#2196F3"));
        paint.setShader(sweepGradient);
- 其中線性線性漸變和輻射漸變有一個 TileMode 屬性,CLAMP、MIRROR、REPEAT 三種樣式 載入、映象、重複模式
  • BitmapShader 對圖片進行處理
Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.batman);  
Shader shader = new BitmapShader(bitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);  
paint.setShader(shader);
- 其中第二、三個引數,是決定水平和豎直方向上的圖片顯示模式同上
  • ComposeShader 混合著色器
    • 兩種格式疊加使用,根據不同的 mode 格式,實現不同的疊加效果

3、顏色過濾

  • setColorFilter(ColorFilter colorFilter);
    • LightingColorFilter 模擬光照。通過計算之後,過濾某一顏色,使得在顯示的時候是過濾之後的顏色
    • PorterDuffColorFilter、ColorMatrixColorFilter 同上,也是根據不用的計算方式顯示不同的過濾顏色的方式
    • 該方法能實現多種圖片顏色處理方式,例如各種常見的濾鏡效果,用的時候再詳細學習吧

4、顏色圖形轉化方式

  • 具體使用沒看太懂。主要用途是圖片疊加顯示時的問題

二、效果

1、抗鋸齒 setAntiAlias(boolean aa)

2、填充效果 setStyle(Paint.Style style)

  • 充滿 Paint.Style.FILL
  • 劃線 Paint.Style.StROKE
  • 填充加劃線 Paint.Style.FILL_AND_STROKE

3、線條形狀

  • setStrokeWidth(float width) 設定線條寬度

  • setStrokeCap(Paint.Cap cap) 設定線頭的形狀 image

    • 平頭 BUTT
    • 方頭 ROUND
    • 圓頭 SQUARE
  • setStrokeJoin(Paint.Join join) 設定拐角的形狀 image

    • Paint.Join.ROUND 圓角
    • Paint.Join.MITER 尖角
    • Paint.Join.BEVEL 平角
  • setStrokeMiter(float miter)

    • 對於拐角形狀的補充

4、色彩優化

(1) setDither(boolean dither)
  • 抖動,優化色彩深度降低時的繪製效果。沒什麼卵用
(2)setFilterBitmap(boolean filter)
  • 雙線性過濾。是圖片繪製更平滑,減輕馬賽克效果

5、setPathEffect(PathEffect effect)

  • 使用 PathEffect 來給圖形的輪廓設定效果。
(1) CornerPathEffect
  • 把拐角設定成圓角
PathEffect pathEffect = new CornerPathEffect(20);  
paint.setPathEffect(pathEffect);
(2) DiscretePathEffect
  • 線條進行隨機偏離,讓輪廓變的亂七八糟
PathEffect pathEffect = new DiscretePathEffect(20, 5);  
paint.setPathEffect(pathEffect);
(3) DashPathEffect
  • 虛線線條,輪廓變成虛線
PathEffect pathEffect = new DashPathEffect(new float[]{20, 10, 5, 10}, 0);  
paint.setPathEffect(pathEffect);
  • 第一個引數 intervals是一個數組,它指定了虛線的格式:陣列中元素必須為偶數(最少是 2 個),按照「畫線長度、空白長度、畫線長度、空白長度」……的順序排列,例如上面程式碼中的 20, 5, 10, 5 就表示虛線是按照「畫 20 畫素、空 5 畫素、畫 10 畫素、空 5 畫素」的模式來繪製;第二個引數 phase 是虛線的偏移量。
(4) PathDashPathEffect
  • 自定義虛線的圖形
        Path dashPath = new Path();
        dashPath.moveTo(0, 0);
        dashPath.lineTo(10, 0);
        dashPath.lineTo(5, 10);
        dashPath.close();
        PathEffect pathDashPathEffect = new PathDashPathEffect(dashPath, 40, 0,
                PathDashPathEffect.Style.ROTATE);
        paint.setPathEffect(pathDashPathEffect);
  • 第一個引數是虛線的圖形、第二個引數是虛線之間的間距、第三個是偏移量
  • 第四個引數是虛線圖形的拐彎時的樣式
    • TRANSLATE:位移
    • ROTATE:旋轉
    • MORPH:變體 image
(5) SumPathEffect
  • 組合效果,將兩種效果直接疊加到一起
        PathEffect sumPathEffect = new SumPathEffect(discretePathEffect, dashPathEffect);
        paint.setPathEffect(sumPathEffect);
(6) ComposePathEffect
  • 組合效果。是先對 View 進行第一次效果,然後再進行第二次效果
  • 效果的先後順序也會影響最後的效果
        PathEffect composePathEffect = new ComposePathEffect(discretePathEffect, dashPathEffect);
        paint.setPathEffect(composePathEffect);
(7) 注意
  • PathEffect 在有些情況下不支援硬體加速,需要關閉硬體加速才能正常使用

6、setShadowLayer 繪製陰影

paint.setShadowLayer(20, 10, 10, Color.RED);
  • 第一個引數是陰影的模糊範圍,第二、三個引數是陰影 x、y 方向偏移量,第四個引數是陰影顏色
  • 清除陰影使用 clearShadowLayer()
  • 在硬體加速開啟的情況下,setShadowLayer()只支援文字的繪製,文字之外的繪製必須關閉硬體加速才能正常繪製陰影。
  • 如果 shadowColor 是半透明的,陰影的透明度就使用 shadowColor 自己的透明度;而如果 shadowColor 是不透明的,陰影的透明度就使用 paint 的透明度。

7、setMaskFilter(MaskFilter maskfilter) 繪製遮罩

  • setMaskFilter(MaskFilter maskfilter) 方法和 setShadowLayer() 方法正相反,是在 View 上層新增效果,相當於遮罩層
(1) BlurMaskFilter
MaskFilter blurMaskFilter = new BlurMaskFilter(50, BlurMaskFilter.Blur.OUTER);
  • 模糊效果
  • 第一個引數是模糊的範圍
  • 第二個引數是模糊型別
    • NORMAL: 內外都模糊繪製
    • SOLID: 內部正常繪製,外部模糊
    • INNER: 內部模糊,外部不繪製
    • OUTER: 內部不繪製,外部模糊(什麼鬼?) image
(2) EmbossMaskFilter
new EmbossMaskFilter(new float[]{0, 1, 1}, 0.2f, 8, 10)
  • 浮雕效果,具體的用到再說吧
此效果使用時,需要關閉硬體加速效果(基本也用不上吧)

8、獲取繪製的 Path

  • 獲取 Path 的繪製路徑,我理解為複製源 Path 的樣式
(1) Paint.getFillPath(Path src, Path dst)
  • 獲取圖形的路徑輪廓,src 為源 Path,dst 為目標 Path
  • 在源 Path 的 Paint 為 STROKE 時
(2) getTextPath(String text, int start, int end, float x, float y, Path path) / getTextPath(char[] text, int index, int count, float x, float y, Path path)
  • 獲取文字路徑
  • 多用於對於文字的修飾效果

三、drawText() 相關

  • 對文字進行設定,間距、大小、字型、效果等功能。下一節

四、初始化類

  • 用來初始化 Paint 物件,或者批量設定 Paint 的多個屬性方法

1、reset()

  • 相當於 new 一個 Paint

2、set(Paint src)

  • 把 src 的屬性全部複製過來

3、setFlags(int flags)

  • 批量設定 Paint 的屬性
paint.setFlags(Paint.ANTI_ALIAS_FLAG | Paint.DITHER_FLAG);
等同於
paint.setAntiAlias(true);  
paint.setDither(true);