有过UI设计经验的一定对2D图形渲染中的Color Gradient 或多或少有些接触,很多编程
语言也提供了Gradient的接口,但是想知道它是怎么实现的嘛?
本文介绍三种简单的颜色梯度变化算法,就可以很容易实现常见的梯度变化算法
三种都要求提供两个参数即起始颜色RGB值, 最终颜色RGB的值。
垂直梯度颜色变化,效果如下:
水平梯度颜色变化,效果如下:
水平与垂直两个方向叠加梯度变化效果如下:
算法代码及其解释
计算起始颜色和终点颜色RGB之间差值代码如下:
float rr = startColor[0] - endColor[0];
float gg = startColor[1] - endColor[1];
float bb = startColor[2] - endColor[2];
实现垂直梯度变化的代码如下:
r = endColor[0] + (int)(rr * ((float)row/255.0f) +0.5f);
g = endColor[1] + (int)(gg * ((float)row/255.0f) +0.5f);
b = endColor[2] + (int)(bb * ((float)row/255.0f) +0.5f);
实现水平梯度变化代码如下:
// set gradient color valuefor each pixel
r = endColor[0] + (int)(rr * ((float)col/255.0f) +0.5f);
g = endColor[1] + (int)(gg * ((float)col/255.0f) + 0.5f);
b = endColor[2] + (int)(bb * ((float)col/255.0f) +0.5f);
实现水平和垂直两个方向上Gradient叠加代码如下:
r = endColor[0] + (int)(rr * (((float)col * (float)row)/size) +0.5f);
g = endColor[1] + (int)(gg * (((float)col * (float)row)/size) +0.5f);
b = endColor[2] + (int)(bb * (((float)col * (float)row)/size) +0.5f);
程序对上面三种Gradient方法分别放在三个不同的方法中,根据参数调用。
程序的完全Java源代码如下:
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.image.BufferedImage;
import javax.swing.JComponent;
import javax.swing.JFrame;
public class ColorGradientDemo extends JComponent {
/**
*
*/
private static final long serialVersionUID = -4134440495899912869L;
private BufferedImage image = null;
protected void paintComponent(Graphics g) {
Graphics2D g2 = (Graphics2D)g;
g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2.drawImage(getImage(4), 5, 5, image.getWidth(), image.getHeight(), null);
}
public BufferedImage getImage(int type) {
if(image == null) {
image = new BufferedImage(256, 256, BufferedImage.TYPE_INT_ARGB);
int[] rgbData = new int[256*256];
if(type == 1) {
generateVGradientImage(rgbData);
} else if(type == 2) {
generateHGradientImage(rgbData);
} else {
generateHVGradientImage(rgbData);
}
setRGB(image, 0, 0, 256, 256, rgbData);
}
return image;
}
private void generateVGradientImage(int[] rgbData) {
int[] startColor = getStartColor();
int[] endColor = getEndColor();
float rr = startColor[0] - endColor[0];
float gg = startColor[1] - endColor[1];
float bb = startColor[2] - endColor[2];
int a=255;
int r=0, g=0, b=0;
int index = 0;
for(int row=0; row<256; row++) {
for(int col=0; col<256; col++) {
// set random color value for each pixel
// set gradient color value for each pixel
r = endColor[0] + (int)(rr * ((float)row/255.0f) + 0.5f);
g = endColor[1] + (int)(gg * ((float)row/255.0f) + 0.5f);
b = endColor[2] + (int)(bb * ((float)row/255.0f) + 0.5f);
rgbData[index] = ((a & 0xff) << 24) |
((r & 0xff) << 16) |
((g & 0xff) << 8) |
((b & 0xff));
index++;
}
}
}
private void generateHGradientImage(int[] rgbData) {
int[] startColor = getStartColor();
int[] endColor = getEndColor();
float rr = startColor[0] - endColor[0];
float gg = startColor[1] - endColor[1];
float bb = startColor[2] - endColor[2];
int a=255;
int r=0, g=0, b=0;
int index = 0;
for(int row=0; row<256; row++) {
for(int col=0; col<256; col++) {
// set gradient color value for each pixel
r = endColor[0] + (int)(rr * ((float)col/255.0f) + 0.5f);
g = endColor[1] + (int)(gg * ((float)col/255.0f) + 0.5f);
b = endColor[2] + (int)(bb * ((float)col/255.0f) + 0.5f);
rgbData[index] = ((a & 0xff) << 24) |
((r & 0xff) << 16) |
((g & 0xff) << 8) |
((b & 0xff));
index++;
}
}
}
private void generateHVGradientImage(int[] rgbData) {
int[] startColor = getStartColor();
int[] endColor = getEndColor();
float rr = startColor[0] - endColor[0];
float gg = startColor[1] - endColor[1];
float bb = startColor[2] - endColor[2];
int a=255;
int r=0, g=0, b=0;
int index = 0;
float size = (float)Math.pow(255.0d, 2.0);
for(int row=0; row<256; row++) {
for(int col=0; col<256; col++) {
// set random color value for each pixel
r = endColor[0] + (int)(rr * (((float)col * (float)row)/size) + 0.5f);
g = endColor[1] + (int)(gg * (((float)col * (float)row)/size) + 0.5f);
b = endColor[2] + (int)(bb * (((float)col * (float)row)/size) + 0.5f);
rgbData[index] = ((a & 0xff) << 24) |
((r & 0xff) << 16) |
((g & 0xff) << 8) |
((b & 0xff));
index++;
}
}
}
public int[] getStartColor() {
return new int[]{246,53,138};
}
public int[] getEndColor() {
return new int[]{0,255,255};
}
public void setRGB( BufferedImage image, int x, int y, int width, int height, int[] pixels ) {
int type = image.getType();
if ( type == BufferedImage.TYPE_INT_ARGB || type == BufferedImage.TYPE_INT_RGB )
image.getRaster().setDataElements( x, y, width, height, pixels );
else
image.setRGB( x, y, width, height, pixels, 0, width );
}
public static void main(String[] args) {
JFrame frame = new JFrame("Gradient Color Panel");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().setLayout(new BorderLayout());
// Display the window.
frame.getContentPane().add(new ColorGradientDemo(), BorderLayout.CENTER);
frame.setPreferredSize(new Dimension(280,305));
frame.pack();
frame.setVisible(true);
}
}
分享到:
相关推荐
计算图像每个点的梯度,包括横向梯度、纵向梯度
PHD_Gradient_pyramid_pyramid_ct_matlab图像融合_matlab图像处理_梯度金字塔.zip
PHD_Gradient_pyramid_pyramid_ct_matlab图像融合_matlab图像处理_梯度金字塔_源
梯度检验Gradient Checking梯度检验Gradient Checking
梯度下降法gradientdescent.pdf
梯度算子,图像的梯度函数即为函数灰度变化的速率
对于一幅彩色图像来说,可以对于三个通道进行分别梯度,然后选取最大值组成一幅梯度图像
用户可以生成自定义线性颜色图,提供 2 种颜色和颜色图深度。 颜色作为具有 RGB 值的向量给出。... 该函数输出颜色图和简化颜色图查看过程的图像。 将其用作 colormapeditor 的替代品或在代码中生成颜色图。
神经网络___梯度下降_(Gradient_Descent_in_Neural_Nets)
图像处理(图像融合,图像加密等)的性能评价指标集包括:平均梯度,边缘强度,信息熵,灰度均值,标准差(均方差MSE),均方根误差,峰值信噪比(psnr),空间频率(sf),图像清晰度,互信息(mi),结构相似性(ssim),...
JavaScript 颜色梯度和渐变效果
本程序实现了基于梯度金字塔的图像融合算法,效果还不错,可以参考一下。
对于无约束问题,给出的共轭梯度法,内涵多个函数实例
共轭梯度法在数值分析中应用非常广泛,比最速下降法要快,这里是FR共轭梯度法,及简单的例子。
文章目录图像梯度的定义(离散)图像梯度理解 图像梯度的定义(离散) 对于一个二元函数F(x,y)F(x,y)F(x,y)来说,其偏导数的定义为: δF(x,y)δx=limϵ→0F(x+ϵ,y)−F(x,y)ϵ\frac {\delta F(x,y)}{\delta x}=\...
用于图像梯度获取,包括x y两个方向,同时用图像的形式描述梯度
可以直接运行的梯度域引导图滤波Gradient Domain Guided Image Filtering MATLAB源码
1. Re:Android系统架构 1. 机器学习-随机梯度下降 2. 前端开发之旅- 移动端HTML5实 3. android接收mjpg-streamer软