Android 使用ColorMatrix改变图片颜色

时间:2023-01-15 06:19:25

原文链接:http://blog.csdn.net/janice0529/article/details/49207939

ColorMatrix的颜色矩阵介绍

  • 颜色矩阵M是一个5*4的矩阵,在Android中,颜色矩阵M是以一维数组m=[a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t]的方式进行存储的。如下图1:

Android 使用ColorMatrix改变图片颜色 
图1 颜色矩阵M

他通过RGBA四个通道来直接操作对应颜色,达到修改图像的效果。

  • 第一行决定红色 R
  • 第二行决定绿色 G
  • 第三行决定蓝色 B
  • 第四行决定了透明度 A
  • 第五列是颜色的偏移量

原图的RGBA的ColorMatrix颜色矩阵数组为:

[ 1, 0, 0, 0, 0,
0, 1, 0, 0, 0,
0, 0, 1, 0, 0,
0, 0, 0, 1, 0]
  • 1
  • 2
  • 3
  • 4
  • 1
  • 2
  • 3
  • 4
  • 在一张图片中,图像的RGBA(红色、绿色、蓝色、透明度)值决定了该图片所呈现出来的颜色效果。而图像的RGBA值则存储在一个5*1的颜色分量矩阵C中,由颜色分量矩阵C可以控制图像的颜色效果。颜色分量矩阵C 如图2所示: 
    Android 使用ColorMatrix改变图片颜色 
    图2 颜色分量矩阵C

  • 要想改变一张图片的颜色效果,只需要改变图像的颜色分量矩阵即可。通过颜色矩阵可以很方便的修改图像的颜色分量矩阵。假设修改后的图像颜色分量矩阵为C1,则有如图3所示的颜色分量矩阵计算公式: 
    Android 使用ColorMatrix改变图片颜色 
    图3 颜色分量矩阵计算公式

通常,改变颜色分量时可以通过修改第5列的颜色偏移量来实现,如图4所示的颜色矩阵M1,通过计算后可以得知该颜色矩阵的作用是使图像的红色分量和绿色分量均增加100,这样的效果就是图片泛黄(因为红色与绿色混合后得到黄色)。 
Android 使用ColorMatrix改变图片颜色 
图4 颜色矩阵M1

除此之外,也可以通过直接对颜色值乘以某一系数而达到改变颜色分量的目的。如图5所示的颜色矩阵M2,将绿色分量放大了2倍,这样的效果就是图片泛绿色。 
Android 使用ColorMatrix改变图片颜色 
图5 颜色矩阵M2

————以上内容收集于网络:http://www.android100.org/html/201406/05/19490.html———-


使用ColorMatrix改变图片颜色的步骤

  • 通过Bitmap.createBitmap()方法获得一个空白的Bitmap对象。
  • 使用Bitmap对象创建画布Canvas, 然后创建画笔Paint。
  • 定义ColorMatrix,并指定RGBA矩阵。
  • 使用ColorMatrix创建一个ColorMatrixColorFilter对象, 作为画笔的滤镜 paint.setColorFilter(new ColorMatrixColorFilter(colorMatrix))。
  • 使用Canvas.drawBitmap()方法把原图使用定义的Paint画到空白的Bitmap对象上即可获得改变RGBA值后的图像。

图像颜色处理实例

  • 首先准备一张用来修改颜色的黑色原始图片 btn_pause.png 如下: 
    Android 使用ColorMatrix改变图片颜色

  • 布局文件 colormatrix_activity.xml 内容如下:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
android:orientation="vertical"> <TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="R" /> <SeekBar
android:id="@+id/sb_red"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="255"
android:progress="0" /> <TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="G" /> <SeekBar
android:id="@+id/sb_green"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="255"
android:progress="0" /> <TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="B" /> <SeekBar
android:id="@+id/sb_blue"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="255"
android:progress="0" /> <TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="A" /> <SeekBar
android:id="@+id/sb_alpha"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="255"
android:progress="255" /> <ImageView
android:id="@+id/iv_color_show"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="30dp"
android:layout_gravity="center_horizontal"
android:src="@drawable/btn_pause" /> </LinearLayout>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 界面代码 ColorMatrixActivity.java
/**
* Created by lvzhengbin on 15/10/15.
*/
public class ColorMatrixActivity extends ActionBarActivity { private SeekBar sb_red, sb_green, sb_blue, sb_alpha;
private ImageView iv_show;
private Bitmap afterBitmap;
private Paint paint;
private Canvas canvas;
private Bitmap baseBitmap; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.colormatrix_activity);
initView();
} private void initView() {
iv_show = (ImageView) findViewById(R.id.iv_color_show);
sb_red = (SeekBar) findViewById(R.id.sb_red);
sb_green = (SeekBar) findViewById(R.id.sb_green);
sb_blue = (SeekBar) findViewById(R.id.sb_blue);
sb_alpha = (SeekBar) findViewById(R.id.sb_alpha); sb_red.setOnSeekBarChangeListener(seekBarChange);
sb_green.setOnSeekBarChangeListener(seekBarChange);
sb_blue.setOnSeekBarChangeListener(seekBarChange);
sb_alpha.setOnSeekBarChangeListener(seekBarChange); baseBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.btn_pause);
// 1.获取一个与baseBitmap大小一致的可编辑的空图片
afterBitmap = Bitmap.createBitmap(baseBitmap.getWidth(),
baseBitmap.getHeight(), baseBitmap.getConfig());
// 2.使用Bitmap对象创建画布Canvas, 然后创建画笔Paint。
canvas = new Canvas(afterBitmap);
paint = new Paint();
} private SeekBar.OnSeekBarChangeListener seekBarChange = new SeekBar.OnSeekBarChangeListener() {
@Override
public void onStopTrackingTouch(SeekBar seekBar) {
if(seekBar.getId() == R.id.sb_alpha){
iv_show.getDrawable().setAlpha(sb_alpha.getProgress()); }else{
float progressR = sb_red.getProgress();
float progressG = sb_green.getProgress();
float progressB = sb_blue.getProgress();
// 根据SeekBar定义RGBA的矩阵, 通过修改矩阵第五列颜色的偏移量改变图片的颜色
float[] src = new float[]{
1, 0, 0, 0, progressR,
0, 1, 0, 0, progressG,
0, 0, 1, 0, progressB,
0, 0, 0, 1, 0}; // 3.定义ColorMatrix,并指定RGBA矩阵
ColorMatrix colorMatrix = new ColorMatrix();
colorMatrix.set(src);
// 4.使用ColorMatrix创建一个ColorMatrixColorFilter对象, 作为画笔的滤镜, 设置Paint的颜色
paint.setColorFilter(new ColorMatrixColorFilter(src));
// 5.通过指定了RGBA矩阵的Paint把原图画到空白图片上
canvas.drawBitmap(baseBitmap, new Matrix(), paint);
iv_show.setImageBitmap(afterBitmap);
}
} @Override
public void onStartTrackingTouch(SeekBar seekBar) { } @Override
public void onProgressChanged(SeekBar seekBar, int progress,boolean fromUser) {
}
};
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
    • 我们可以通过SeekBar调节RGB的值来修改图片的颜色来达到不同的效果,运行效果如下: 
      Android 使用ColorMatrix改变图片颜色