Android ColorMatrix类图像颜色处理-黑白老照片、泛黄旧照片、高对比度等效果
在Android中,对图像进行颜色方面的处理,如黑白老照片、泛黄旧照片、高对比度、低饱和度等效果,都可以通过使用颜色矩阵(ColorMatrix)来实现。
1.颜色矩阵(ColorMatrix)介绍
颜色矩阵M是一个5*4的矩阵,如图1所示。在Android中,颜色矩阵M是以一维数组m=[a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t]的方式进行存储的。
图1 颜色矩阵M
在一张图片中,图像的RGBA(红色、绿色、蓝色、透明度)值决定了该图片所呈现出来的颜色效果。而图像的RGBA值则存储在一个5*1的颜色分量矩阵C中,由颜色分量矩阵C可以控制图像的颜色效果。颜色分量矩阵C如图2所示。
图2 颜色分量矩阵C
要想改变一张图片的颜色效果,只需要改变图像的颜色分量矩阵即可。通过颜色矩阵可以很方便的修改图像的颜色分量矩阵。假设修改后的图像颜色分量矩阵为C1,则有如图3所示的颜色分量矩阵计算公式。
图3 颜色分量矩阵计算公式
由此可见,通过颜色矩阵修改了原图像的RGBA值,从而达到了改变图片颜色效果的目的。并且,通过如图3所示的运算可知,颜色矩阵M的第一行参数abcde决定了图像的红色成分,第二行参数fghij决定了图像的绿色成分,第三行参数klmno决定了图像的蓝色成分,第四行参数pqrst决定了图像的透明度,第五列参数ejot是颜色的偏移量。
通常,改变颜色分量时可以通过修改第5列的颜色偏移量来实现,如图4所示的颜色矩阵M1,通过计算后可以得知该颜色矩阵的作用是使图像的红色分量和绿色分量均增加100,这样的效果就是图片泛黄(因为红色与绿色混合后得到黄色)。
图4 颜色矩阵M1
除此之外,也可以通过直接对颜色值乘以某一系数而达到改变颜色分量的目的。如图5所示的颜色矩阵M2,将绿色分量放大了2倍,这样的效果就是图片泛绿色。
图5 颜色矩阵M2
2.图像颜色处理实例
了解了颜色矩阵的工作原理之后,我们就可以使用颜色矩阵对图片进行处理了。
布局代码:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
2 xmlns:tools="http://schemas.android.com/tools"
3 android:layout_width="match_parent"
4 android:layout_height="match_parent"
5 android:orientation="vertical"
6 android:paddingBottom="@dimen/activity_vertical_margin"
7 android:paddingLeft="@dimen/activity_horizontal_margin"
8 android:paddingRight="@dimen/activity_horizontal_margin"
9 android:paddingTop="@dimen/activity_vertical_margin"
10 tools:context=".MainActivity" >
11
12 <TextView
13 android:layout_width="wrap_content"
14 android:layout_height="wrap_content"
15 android:text="R" />
16
17 <SeekBar
18 android:id="@+id/sb_red"
19 android:layout_width="match_parent"
20 android:layout_height="wrap_content"
21 android:max="255"
22 android:progress="128" />
23
24 <TextView
25 android:layout_width="wrap_content"
26 android:layout_height="wrap_content"
27 android:text="G" />
28
29 <SeekBar
30 android:id="@+id/sb_green"
31 android:layout_width="match_parent"
32 android:layout_height="wrap_content"
33 android:max="255"
34 android:progress="128" />
35
36 <TextView
37 android:layout_width="wrap_content"
38 android:layout_height="wrap_content"
39 android:text="B" />
40
41 <SeekBar
42 android:id="@+id/sb_blue"
43 android:layout_width="match_parent"
44 android:layout_height="wrap_content"
45 android:max="255"
46 android:progress="128" />
47
48 <TextView
49 android:layout_width="wrap_content"
50 android:layout_height="wrap_content"
51 android:text="A" />
52
53 <SeekBar
54 android:id="@+id/sb_alpha"
55 android:layout_width="match_parent"
56 android:layout_height="wrap_content"
57 android:max="255"
58 android:progress="128" />
59
60 <ImageView
61 android:id="@+id/iv_show"
62 android:layout_width="wrap_content"
63 android:layout_height="wrap_content"
64 android:src="@drawable/painter" />
65
66 </LinearLayout>
复制代码
实现代码:
1 package cn.bgxt.colormatrixdemo;
2
3 import android.os.Bundle;
4 import android.util.Log;
5 import android.widget.ImageView;
6 import android.widget.SeekBar;
7 import android.widget.SeekBar.OnSeekBarChangeListener;
8 import android.app.Activity;
9 import android.graphics.Bitmap;
10 import android.graphics.BitmapFactory;
11 import android.graphics.Canvas;
12 import android.graphics.ColorMatrix;
13 import android.graphics.ColorMatrixColorFilter;
14 import android.graphics.Matrix;
15 import android.graphics.Paint;
16
17 public class MainActivity extends Activity {
18 private SeekBar sb_red, sb_green, sb_blue,sb_alpha;
19 private ImageView iv_show;
20 private Bitmap afterBitmap;
21 private Paint paint;
22 private Canvas canvas;
23 private Bitmap baseBitmap;
24
25 @Override
26 protected void onCreate(Bundle savedInstanceState) {
27 super.onCreate(savedInstanceState);
28 setContentView(R.layout.activity_main);
29
30 iv_show = (ImageView) findViewById(R.id.iv_show);
31 sb_red = (SeekBar) findViewById(R.id.sb_red);
32 sb_green = (SeekBar) findViewById(R.id.sb_green);
33 sb_blue = (SeekBar) findViewById(R.id.sb_blue);
34 sb_alpha = (SeekBar) findViewById(R.id.sb_alpha);
35
36 sb_red.setOnSeekBarChangeListener(seekBarChange);
37 sb_green.setOnSeekBarChangeListener(seekBarChange);
38 sb_blue.setOnSeekBarChangeListener(seekBarChange);
39 sb_alpha.setOnSeekBarChangeListener(seekBarChange);
40
41 // 从资源文件中获取图片
42 baseBitmap = BitmapFactory.decodeResource(getResources(),
43 R.drawable.painter);
44 // 获取一个与baseBitmap大小一致的可编辑的空图片
45 afterBitmap = Bitmap.createBitmap(baseBitmap.getWidth(),
46 baseBitmap.getHeight(), baseBitmap.getConfig());
47 canvas = new Canvas(afterBitmap);
48 paint = new Paint();
49 }
50
51 private SeekBar.OnSeekBarChangeListener seekBarChange = new OnSeekBarChangeListener() {
52
53 @Override
54 public void onStopTrackingTouch(SeekBar seekBar) {
55 // 获取每个SeekBar当前的值
56 float progressR = sb_red.getProgress()/128f;
57 float progressG = sb_green.getProgress()/128f;
58 float progressB = sb_blue.getProgress()/128f;
59 float progressA=sb_alpha.getProgress()/128f;
60 Log.i("main", "R:G:B="+progressR+":"+progressG+":"+progressB);
61 // 根据SeekBar定义RGBA的矩阵
62 float[] src = new float[]{
63 progressR, 0, 0, 0, 0,
64 0, progressG, 0, 0, 0,
65 0, 0, progressB, 0, 0,
66 0, 0, 0, progressA, 0};
67 // 定义ColorMatrix,并指定RGBA矩阵
68 ColorMatrix colorMatrix = new ColorMatrix();
69 colorMatrix.set(src);
70 // 设置Paint的颜色
71 paint.setColorFilter(new ColorMatrixColorFilter(src));
72 // 通过指定了RGBA矩阵的Paint把原图画到空白图片上
73 canvas.drawBitmap(baseBitmap, new Matrix(), paint);
74 iv_show.setImageBitmap(afterBitmap);
75 }
76
77 @Override
78 public void onStartTrackingTouch(SeekBar seekBar) {
79 }
80
81 @Override
82 public void onProgressChanged(SeekBar seekBar, int progress,
83 boolean fromUser) {
84 }
85 };
86 }
效果图:
android把彩色图像变成灰度图(黑白)
代码:
public class MainActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
ImageView iv = new ImageView(this);
setContentView(iv);
Bitmap originImg = BitmapFactory.decodeResource(getResources(), R.drawable.painter);
Bitmap grayImg = Bitmap.createBitmap(originImg.getWidth(), originImg.getHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(grayImg);
Paint paint = new Paint();
ColorMatrix colorMatrix = new ColorMatrix();
colorMatrix.setSaturation(0);
ColorMatrixColorFilter colorMatrixFilter = new ColorMatrixColorFilter(colorMatrix);
paint.setColorFilter(colorMatrixFilter);
canvas.drawBitmap(originImg, 0, 0, paint);
iv.setImageBitmap(grayImg);
}
}
主要是 colorMatrix.setSaturation(0);这一行代码的作用。
效果图,还是刚才的彩色图处理后的结果:
黑白老照片、泛黄旧照片、高对比度、低饱和度等效果
泛红效果
高对比度、高饱和度、色相变换等图片处理效果
Android ColorMatrix类图像颜色处理-黑白老照片、泛黄旧照片、高对比度等效果的更多相关文章
- Android学习笔记之图像颜色处理(ColorMatrix)
对图像进行颜色方面的处理,通过使用颜色矩阵(ColorMatrix)来实现.从而可以达到很多特效如黑白老照片.泛黄旧照片等等. 1.颜色矩阵(ColorMatrix) 这里有详细的介绍:http:// ...
- Android图像格式类及图像转换方法
Android图像格式类及图像转换方法介绍 一款软件的开发和图像密切相关,特别是移动应用程序,在视觉效果等方面是至关重要的,因为这直接关系到用户的体验效果.在Android程序开发的过程中,了解存在哪 ...
- Android 使用ColorMatrix改变图片颜色
原文链接:http://blog.csdn.net/janice0529/article/details/49207939 ColorMatrix的颜色矩阵介绍 颜色矩阵M是一个5*4的矩阵,在And ...
- Android Matrix类以及ColorMatri
引自:http://www.chinabaike.com/t/37396/2014/0624/2556217.html Android Matrix类以及ColorMatrix类详解 最近在系统学习了 ...
- Android资源之图像资源(图层图像资源)
曾经看别人的程序的drawable目录里有xml资源,说实话第一次见到这种xml图像资源时,我真心不知道是干什么的.抽出时间学习了一下图像资源.才了解了这类图像资源的妙用. 以下我来分享一下这部分知识 ...
- android Activity类中的finish()、onDestory()和System.exit(0) 三者的区别
android Activity类中的finish().onDestory()和System.exit(0) 三者的区别 Activity.finish() Call this when your a ...
- Codrops 实验:使用 Vibrant.js 提取图像颜色
Codrops 分享了一个有趣的颜色提取实验.这个想法是创建图像的调色板,既有图像本身的潜移默化的影响,也有一些花哨的颜色延伸.通过使用 Vibrant.js 来提取图像中的颜色,并通过 CSS 过滤 ...
- Android中解决图像解码导致的OOM问题
Android中解决图像解码导致的OOM问题 原文链接:http://blog.csdn.net/zjl5211314/article/details/7042017
- Android 服务类Service 的详细学习
http://blog.csdn.net/vipzjyno1/article/details/26004831 Android服务类Service学习四大组建 目录(?)[+] 什么是服务 服务有 ...
随机推荐
- 【luogu P4007 清华集训2017】小Y和恐怖奴隶主
题目背景 “A fight? Count me in!” 要打架了,算我一个. “Everyone, get in here!” 所有人,都过来! 题目描述 小 Y 是一个喜欢玩游戏的 OIer.一天 ...
- ●洛谷 P3616 富金森林公园
题链: https://www.luogu.org/problemnew/show/3616 题解: 树状数组,,, 本题思路挺巧妙. 考虑这种暴力算法:(设H[i]为i位置的高度,水面的高度为B) ...
- poj 3525 凸多边形多大内切圆
Most Distant Point from the Sea Time Limit: 5000MS Memory Limit: 65536K Total Submissions: 4758 ...
- 【Toll!Revisited(uva 10537)】
题目来源:蓝皮书P331 ·这道题使得我们更加深刻的去理解Dijkstra! 在做惯了if(dis[u]+w<dis[v])的普通最短路后,这道选择路径方案不是简单的比大小的题横在了 ...
- Java连接FTP成功,但是上传是失败,报错:Connected time out
Java代码在本机上传文件到FTP服务器的时候成功,但是部署到测试服务器的时候出现,连接FTP成功但是上传失败,并且报Connected time out错误: 测试服务器和FTP服务都在阿里云上:( ...
- Mysql索引介绍及常见索引的区别
关于MySQL索引的好处,如果正确合理设计并且使用索引的MySQL是一辆兰博基尼的话,那么没有设计和使用索引的MySQL就是一个人力三轮车.对于没有索引的表,单表查询可能几十万数据就是瓶颈,而通常大型 ...
- 基于PHP的地址清洗调用案例-快宝开放平台
快宝地址清洗,纠正错误地址.识别不完整地址.地址补全,并输出结构化地址数据的通用解决方案.广泛应用于快递行业,电商行业,ERP应用等. 快宝开放平台-地址清洗对接API:http://open.kua ...
- Lucene——Field.Store(存储域选项)及Field.Index(索引选项)
Field.Store.YES或者NO(存储域选项) 设置为YES表示或把这个域中的内容完全存储到文件中,方便进行文本的还原 设置为NO表示把这个域的内容不存储到文件中,但是可以被索引,此时内容无法完 ...
- JavaScript基础知识必知!!!
JavaScript一种直译式脚本语言,是一种动态类型.弱类型.基于原型的语言,内置支持类型. JS作用:表单验证,减轻服务端的压力:添加页面动画效果:动态更改页面内容:Ajax网络请求. 下面简单介 ...
- Device Mapper 代码分析
Device Mapper(DM)是Linux 2.6全面引入的块设备新构架,通过DM可以灵活地管理系统中所有的真实或虚拟的块设备. DM以块设备的形式注册到Linux内核中,凡是挂载(或者说&quo ...