【问题标题】:Circle masking for pool balls using shaders使用着色器对台球进行圆形遮罩
【发布时间】:2015-06-09 04:19:22
【问题描述】:

在使用 OpenGL ES 2.0 的 2D 台球游戏中,当“白色”和“数字”纹理围绕球的边缘旋转时,我需要对其进行遮罩。我目前正在使用模板,但有两个问题:

  1. 模板测试中没有抗锯齿,产生锯齿状边缘。
  2. 每个球都被单独屏蔽(相邻的球可能会相互渗透),而且每帧多次清除和重新创建模板缓冲区太慢了。

我很确定最好的解决方案将涉及着色器代码,但我是着色器编程的新手(对 OpenGL 本身也很陌生),我在研究中发现的大量结果让我不确定如何最好地继续。

这个似乎接近我需要的: https://gamedev.stackexchange.com/questions/98573/how-do-i-draw-a-circular-portion-of-a-texture-within-libgdx-using-an-opengl-es-s

特别是第一个回答“Alpha 蒙版纹理”的方法,使用灰度图像作为最终gl_FragColor 的alpha 值。但是我找不到任何关于如何设置这样的着色器程序的示例。 (常见的例子有 3 张图片,分别是背景、前景和蒙版,并使用 mix() 将它们混合)。

例如,蒙版是整个球的大小和形状,但是像数字这样的纹理是在球的一部分上绘制的(并且对于透视图使用不同的变换矩阵),所以纹理坐标是图像和蒙版完全不同。我找不到类似的东西。

第二种可能更容易的选择是仅对距中心一定距离^2 以外的像素使用“丢弃”。甚至可以羽化阿尔法。我发现了这种方法: https://gist.github.com/tgfrerer/6009069

...但是它使用了 ES 2.0 中没有的功能。如果有人可以提供一个功能相似但适用于 ES 的示例,那也将受到欢迎。就像对比两种方法的优点一样。

【问题讨论】:

    标签: opengl-es opengl-es-2.0 mask


    【解决方案1】:

    也许这篇论文可以提供帮助:https://www.valvesoftware.com/publications/2007/SIGGRAPH2007_AlphaTestedMagnification.pdf 我认为这正是您所需要的——并且在 ES2 中应该可以正常工作。

    【讨论】:

    • 感谢您提供链接,但我不明白“矢量纹理的放大”过程与蒙版场景有何关联或有助于解决蒙版场景。
    【解决方案2】:

    我现在使用第二种“距离”方法有一个可行的解决方案。而且由于它的边缘也很光滑,所以我应该很高兴。请注意,中心和内部/外部边缘的制服都需要在“窗口坐标”中。 distance() 中的每像素 sqrt 有点困扰我,但我尝试将其展开到 distance^2 测试中,并且分析速度更慢。

    precision mediump float;
    varying vec2 v_texCoord;
    uniform vec2 center;
    uniform float innerEdge;
    uniform float outerEdge;
    uniform float alpha;
    uniform sampler2D s_texture;
    void main() {
      float dist = distance(gl_FragCoord.xy, center);
      if (dist >= innerEdge)
        gl_FragColor = alpha * (1. - smoothstep(innerEdge, outerEdge, dist)) * texture2D(s_texture, v_texCoord);
      else
        gl_FragColor = alpha * texture2D(s_texture, v_texCoord);
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-05-18
      • 2014-11-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-05-25
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多