【问题标题】:OpenGL HSV additive blendingOpenGL HSV 附加混合
【发布时间】:2013-02-25 11:06:37
【问题描述】:

我想用 OpenGL 实现这种效果: http://www.escapemotions.com/experiments/flame/#top

有一种添加混合似乎可以增加亮度值:添加红色会产生白色。

(255,0,0) + (200,0,0) -> (255,100,100)

我可以使用 GLSL 实现这一点(将两种颜色转换为 HSV 空间,添加值,然后返回),但我想知道是否有更好的方法。

火焰画家是用Processing制作的(我用openframeworks不太了解),Processing中效果是如何计算的?

【问题讨论】:

    标签: opengl glsl processing


    【解决方案1】:

    Peter,这里的 Flame Painter 程序员。

    Flame Painter 中的变亮模式类似于 Photoshop ADD 混合模式, 我正在向所有 RGB 通道添加少量颜色。

    示例(伪代码):

    color: C = (50, 20, 10) // RGB channels = 50, 20, 10
    lighter color: C = C + C // RGB channels = 100, 40, 20
    lighter color: C = C + C // RGB channels = 150, 60, 30
    ...
    

    添加颜色直到颜色 C 变为白色。 (255, 255, 255)

    如果颜色是纯红色、蓝色、绿色、紫色、黄色或洋红色,则此方法不起作用。 红色示例:

    color: C = (50, 0, 0) // RGB channels = 50, 0, 0
    lighter color: C = C + C // RGB channels = 100, 0, 0
    lighter color: C = C + C // RGB channels = 150, 0, 0
    ...
    

    最亮的颜色是红色。 (255, 0, 0)

    这就是为什么我在默认颜色为 0 的通道中添加少量(1 种颜料)。 示例:

    color: C = (50, 1, 1) // RGB channels = 50, 1, 1
    lighter color: C = C + C // RGB channels = 100, 2, 2
    lighter color: C = C + C // RGB channels = 150, 3, 3
    ...
    

    最亮的颜色将再次变为白色。 (255, 255, 255)

    【讨论】:

      【解决方案2】:

      混合模式作为处理 API 的一部分实现: http://processing.org/reference/blendMode_.html

      在内部,如果渲染器是 GL 渲染器 (glBlendFunc(GL_SRC_ALPHA, GL_ONE)),则使用 GL,否则使用 GL 使用的相同数学:

      private static int blend_add_pin(int a, int b) {
          int f = (b & ALPHA_MASK) >>> 24;
      
          return (low(((a & ALPHA_MASK) >>> 24) + f, 0xff) << 24 |
              low(((a & RED_MASK) + ((b & RED_MASK) >> 8) * f), RED_MASK) & RED_MASK |
              low(((a & GREEN_MASK) + ((b & GREEN_MASK) >> 8) * f), GREEN_MASK) & GREEN_MASK |
              low((a & BLUE_MASK) + (((b & BLUE_MASK) * f) >> 8), BLUE_MASK));
      }
      

      (来自PImage.java)

      至于“如果有更好的方法”,使用 GL 的好处是它发生在 GPU 而不是 CPU 上。因此,如上所示自己进行数学运算将比让显卡支持的 GL 混合模式发挥作用要慢。

      【讨论】:

      • 当我用 glBlendFunc(GL_SRC_ALPHA, GL_ONE) 添加两种红色 (255,0,0) 时,我得到一个红色:andersriggelsen.dk/glblendfunc.php 我想得到一个更浅的红色,就像这里@ 987654324@当我选择纯红色时。也许它不仅是纯粹的 openGL 混合,而且火焰的中心最终是白色的,与它下面的颜色无关。
      • 颜色 escapemotions.com/experiments/flame 可能取决于粒子的位置。似乎它们离光标越近,它就越白。无需任何特殊混合即可解释这种效果。
      猜你喜欢
      • 2011-11-14
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-12-14
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-12-02
      相关资源
      最近更新 更多