只使用一种颜色生成渐变

4
我有一个颜色,比如0xFF0000。我想只使用这个颜色作为起点信息来创建简单的渐变。第二个点将是比第一个颜色更浅的颜色。
例如,如果我有一个值为0xFF0000,我想从中得到0xCC0000。然后我可以绘制简单的渐变。
因此,第二种颜色应该比第一种颜色轻10或20%。
硬编码的值是不可接受的。用户将从调色板中选择颜色,应用程序应自动生成第二个颜色来绘制简单的渐变。
是否有任何算法或方法来实现这个问题?可能算法会计算哪个更高:R还是G还是B,然后平行减少其他组件,或者什么...我不确定这是如何工作的。
附言:我正在使用android SDK。

为了更快地获得帮助,请发布一个SSCCE,它是一个简短的、可运行的、可编译的示例,仅涉及Gradient。 - mKorbel
基本上,您想要的是从起始颜色到...白色之间的渐变? - mb14
不,只有2种颜色:红色/蓝色/绿色/橙色/紫色/其他 和 浅红色/浅蓝色/浅绿色/浅橙色/浅紫色/浅其他。 - pleerock
我为另一个问题所写的这个答案解释了RGB和HSV颜色空间之间的关系。它可能会有所帮助。 - John Schmidt
3个回答

4

我认为最好的方法是从RGB颜色空间转换到HSV颜色空间

public int enlight(int color, float amount) {
  float[] hsv = new float[3];
  Color.colorToHSV(color, hsv);
  hsv[2] = Math.min(1.0f, amount * hsv[2]);
  return Color.HSVToColor(hsv);
}

如果要简单地增加颜色的亮度,只需增加v(value)属性,然后使用同样的Android API Color将其转换回RGB格式(如有需要)。


看起来不错... 我们需要同时增加v的三个值吗? - pleerock
不,一个单一的颜色,比如说绿色可以用RGB和HSV形式表示。一个比绿色亮20%的绿色具有相同的H和S分量,但V增加了20%(V在0.0-1.0范围内)。请参阅链接的维基百科文章:页面底部有一个漂亮的表格。 - Raffaele
我改变了饱和度(hsv [1]),它给了我我想要的效果。渐变不是那么动态,但同时也很美,正是我想要的。 - pleerock
这与我的答案完全相同,但需要进行两次额外的颜色到HSV和反向转换。与我的答案相比,我并没有看到它的好处。 - htz
@htz 你没有使用 Android API,而且 结果是不同的 - Raffaele

0

看起来像是这样的:

int red     = Color.red(color);
int green   = Color.green(color);
int blue    = Color.blue(color);

int secondColor = 0;
int lighting    = 51; // from 0 to 255. The larger the number is the brighter second color

if (red > green && red > blue)
    secondColor = Color.rgb(red, green - lighting, blue - lighting);
else if (green > red && green > blue)
    secondColor = Color.rgb(red - lighting, green, blue - lighting);
else if (blue > red && blue > green)
    secondColor = Color.rgb(red - lighting, green - lighting, blue);

我应该为所有颜色进行测试...


更新:

它能正常工作,但你需要加入其他条件来检查绿色和蓝色是否相等或者红色和蓝色是否相等等。请参考@Raffaele的回答。


0
我制作了一个简单的示例,展示了一种可能的方法,该方法利用了Color类的getRGBColorComponents()方法。
import java.awt.Color;
import java.awt.FlowLayout;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.image.BufferedImage;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;

public class Test extends JFrame {

public Test(Color c1, Color c2) {
    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    setSize(200, 200);
    setVisible(true);
    JPanel panel = new JPanel(new FlowLayout(FlowLayout.CENTER));
    panel.add(new JLabel(createColorIcon(c1)));
    panel.add(new JLabel(createColorIcon(c2)));
    add(panel);
}

public ImageIcon createColorIcon(Color c) {
    int w = 44, h = 20;
    BufferedImage bi = new BufferedImage(w, h, BufferedImage.TYPE_INT_ARGB);
    Graphics2D g = bi.createGraphics();
    if (c != null) {
        g.setColor(c);
        g.fillRect(0, 0, w, h);
    } else {
        g.setColor(Color.GRAY);
        g.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
        g.drawLine(1, 1, w - 2, h - 2);
        g.drawLine(1, h - 2, w - 2, 1);
    }
    g.setColor(Color.GRAY);
    g.drawRect(0, 0, w - 1, h - 1);
    g.dispose();
    return new ImageIcon(bi);
}

public static void main(String[] args) {

    Color c1 = Color.decode("0xFF0000");
    float[] f = c1.getRGBColorComponents(null);
    System.out.println(f.length);
    for (int i = 0; i < f.length; i++) {
        System.out.println(f[i]);
    }
    f[0] = f[0] * 0.8f;
    Color c2 = new Color(f[0],f[1],f[2]);
    new Test(c1,c2);

}

}

你只需调用getRGBColorComponents()方法,就可以获得一个包含红、绿和蓝色值的数组,以浮点值表示,范围从0.0到1.0,其中255(或0xFF)的整数值对应于1.0的浮点值。你只需将其乘以你选择的因子,就像我在示例的结尾处所做的那样。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接