模板缓冲区的相交检测

问题描述

为了实现延迟闪电,我将光源渲染为一个具有半径的球体。

我仅将光的实际位置渲染到屏幕上。结果如下。

enter image description here

所以我想也许我可以渲染这些球体的交点,那么我就可以消除延迟着色器中每个光源的for循环。

通过在链接https://kayru.org/articles/deferred-stencil/中使用以下文档 我将光球与实际场景相交,并将其保存到下面的纹理中。

enter image description here

问题在于结果与我预期的有所不同。交叉口还包括其他球体。轻的体积不应彼此相交。如何实现合适的交集方法

return (
  <div>
    {fetchedData.map((data,i) => {
      const prevIoUs = fetchedData[i - 1];
      return (
        <>
          {prevIoUs && data.timeStampString !== prevIoUs.timeStampString && (
            <div className="divider"></div> 
          )} 
          <div>{data.foo} - {data.timeStampString}</div>
        </>
      )
    })}
  </div>
);

解决方法

我解决了这个问题。 在将几何体渲染到缓冲区后,我没有在屏幕上绘制四边形,而是在下面渲染了球体。

首先,在具有以下状态的空通道中渲染光球。

    glEnable(GL_STENCIL_TEST);
    glEnable(GL_DEPTH_TEST);
    glDisable(GL_CULL_FACE);
    glDepthFunc(GL_LESS);
    glDepthMask(GL_FALSE);
    glEnable(GL_DEPTH_TEST);
    glDisable(GL_CULL_FACE);
    glClear(GL_STENCIL_BUFFER_BIT);
    glStencilFunc(GL_ALWAYS,0);
    glStencilOpSeparate(GL_BACK,GL_KEEP,GL_INCR_WRAP,GL_KEEP);
    glStencilOpSeparate(GL_FRONT,GL_DECR_WRAP,GL_KEEP);
    glDepthMask(GL_FALSE);//disable writing to depth buffer
    glColorMask(GL_FALSE,GL_FALSE,GL_FALSE);//!! disable writing to color buffer

现在使用以下状态再次渲染光球。

    glStencilFunc(GL_NOTEQUAL,0xFF);
    glDisable(GL_DEPTH_TEST);
    glEnable(GL_BLEND);
    glBlendEquation(GL_FUNC_ADD);
    glBlendFunc(GL_ONE,GL_ONE);
    glEnable(GL_CULL_FACE);
    glCullFace(GL_FRONT);
    glDepthMask(GL_TRUE);
    glColorMask(GL_TRUE,GL_TRUE,GL_TRUE);