什么是亮度:
简单点说一幅图像的亮度属性是图像的RGB值的大小,RGB各个值越大亮度越高RGB
分量取值范围为0~255之间。调整图像亮度。
什么是饱和度:
饱和度是是指颜色的强度,调整饱和度可以修正过度曝光或者未充分曝光的图片。使
图像看上去更加自然。
基本思想:
通常在RGB色彩空间调整亮度与饱和度不是很直观,而HSL彩色空可以很直观表示出
每个像素的饱和度与亮度。所以首先读取图像的像素RGB值然后再转换到HSL空间得
到饱和度与亮度值,调整以后再从HSL空间转换到RGB空间的RGB值,对每个像素完
成这样的调整就完成图像的亮度与饱和度调整。关于RGB与HSL色彩空间的转换
看这里:http://en.wikipedia.org/wiki/HSL_color_space
程序效果:
滤镜源代码:
- package com.gloomyfish.filter.study;
-
- import java.awt.image.BufferedImage;
-
-
-
-
-
-
- public class HSLFilter extends AbstractBufferedImageOp {
- public final static double c1o60 = 1.0 / 60.0;
- public final static double c1o255 = 1.0 / 255.0;
- private double hue;
- private double saturation;
- private double lightness;
-
- public HSLFilter() {
- System.out.println("Hue Filter");
- }
-
- public double getHue() {
- return hue;
- }
-
- public void setHue(double hue) {
- while (hue < 0.0) {
- this.hue += 360;
- }
- while (hue >= 360.0) {
- this.hue -= 360;
- }
- }
-
- public double getSaturation() {
- return saturation;
- }
-
- public void setSaturation(double saturation) {
- if((saturation >= -100.0) && (saturation <= 100.0)) {
- this.saturation = saturation;
- }
- }
-
- public double getLightness() {
- return lightness;
- }
-
- public void setLightness(double lightness) {
- if((lightness >= -100.0) && (lightness <= 100.0)) {
- this.lightness = lightness;
- }
- }
-
- @Override
- public BufferedImage filter(BufferedImage src, BufferedImage dest) {
- int width = src.getWidth();
- int height = src.getHeight();
- double sat = 127.0d * saturation / 100.0d;
- double lum = 127.0d * lightness / 100.0d;
- if ( dest == null )
- dest = createCompatibleDestImage( src, null );
-
- int[] inPixels = new int[width*height];
- int[] outPixels = new int[width*height];
- getRGB( src, 0, 0, width, height, inPixels );
- double min, max, dif, sum;
- double f1, f2;
- int index = 0;
- double h, s, l;
- double v1, v2, v3, h1;
- for(int row=0; row<height; row++) {
- int ta = 0, tr = 0, tg = 0, tb = 0;
- for(int col=0; col<width; col++) {
- index = row * width + col;
- ta = (inPixels[index] >> 24) & 0xff;
- tr = (inPixels[index] >> 16) & 0xff;
- tg = (inPixels[index] >> 8) & 0xff;
- tb = inPixels[index] & 0xff;
-
-
- min = tr;
- if (tg < min)
- min = tg;
- if (tb < min)
- min = tb;
- max = tr;
- f1 = 0.0;
- f2 = tg - tb;
- if (tg > max) {
- max = tg;
- f1 = 120.0;
- f2 = tb - tr;
- }
- if (tb > max) {
- max = tb;
- f1 = 240.0;
- f2 = tr - tg;
- }
- dif = max - min;
- sum = max + min;
- l = 0.5 * sum;
- if (dif == 0) {
- h = 0.0;
- s = 0.0;
- }
- else if(l < 127.5) {
- s = 255.0 * dif / sum;
- }
- else {
- s = 255.0 * dif / (510.0 - sum);
- }
-
- h = (f1 + 60.0 * f2 / dif);
- if (h < 0.0) {
- h += 360.0;
- }
- if (h >= 360.0) {
- h -= 360.0;
- }
-
-
- h = h + hue;
- if( h >= 360.0) {
- h = h - 360.0;
- }
- s = s + sat;
- if( s < 0.0) {
- s = 0.0;
- }
- if( s > 255.0) {
- s = 255.0;
- }
- l = l + lum;
- if( l < 0.0) {
- l = 0.0;
- }
- if( l > 255.0) {
- l = 255.0;
- }
-
-
- if (s == 0) {
- tr = (int)l;
- tg = (int)l;
- tb = (int)l;
- } else {
-
- if (l < 127.5) {
- v2 = c1o255 * l * (255 + s);
- } else {
- v2 = l + s - c1o255 * s * l;
- }
-
- v1 = 2 * l - v2;
- v3 = v2 - v1;
- h1 = h + 120.0;
- if (h1 >= 360.0)
- h1 -= 360.0;
-
- if (h1 < 60.0) {
- tr = (int)(v1 + v3 * h1 * c1o60);
- }
- else if (h1 < 180.0) {
- tr = (int)v2;
- }
- else if (h1 < 240.0) {
- tr = (int)(v1 + v3 * (4 - h1 * c1o60));
- }
- else {
- tr = (int)v1;
- }
-
- h1 = h;
- if (h1 < 60.0) {
- tg = (int)(v1 + v3 * h1 * c1o60);
- }
- else if (h1 < 180.0) {
- tg = (int)v2;
- }
- else if (h1 < 240.0) {
- tg = (int)(v1 + v3 * (4 - h1 * c1o60));
- }
- else {
- tg = (int)v1;
- }
-
- h1 = h - 120.0;
- if (h1 < 0.0) {
- h1 += 360.0;
- }
- if (h1 < 60.0) {
- tb = (int)(v1 + v3 * h1 * c1o60);
- }
- else if (h1 < 180.0) {
- tb = (int)v2;
- }
- else if (h1 < 240.0) {
- tb = (int)(v1 + v3 * (4 - h1 * c1o60));
- }
- else {
- tb = (int)v1;
- }
- }
- outPixels[index] = (ta << 24) | (tr << 16) | (tg << 8) | tb;
- }
- }
-
- setRGB( dest, 0, 0, width, height, outPixels );
- return dest;
- }
-
- }
-