我找到了一些被问过的地方,但我还没有找到一个好的答案.
问题:我想要渲染到纹理,然后我想将渲染的纹理绘制到屏幕IDENTICALLY,如果我跳过渲染到纹理步骤并且只是直接渲染到屏幕,它将如何显示.我目前正在使用混合模式glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA).我也有glBlendFuncSeparate来玩.
我希望能够将部分透明的重叠项呈现给此纹理.我知道混合功能目前正在弄乱基于Alpha的RGB值.我已经看到一些模糊的建议使用"预乘alpha",但描述的含义很差.我在photoshop中制作png文件,我知道它们有一个半透明的位,你不能像TGA一样独立编辑alpha通道.如果需要,我可以切换到TGA,虽然PNG更方便.
现在,为了这个问题,我们假设我们没有使用图像,而是使用带有alpha的全彩色四边形.
一旦我将场景渲染到纹理,我需要将该纹理渲染到另一个场景,并且我需要将纹理再次呈现为部分透明度.事情就是崩溃的地方.在之前的混合步骤中,我明确地改变了基于Alpha的RGB值,如果Alpha为0或1,则再次执行它,但如果它在中间,则结果是那些部分半透明像素进一步变暗.
玩混合模式我运气很少.我能做的最好就是渲染纹理:
glBlendFuncSeparate(GL_ONE,GL_ONE_MINUS_SRC_ALPHA,GL_ONE,GL_ONE);
我发现使用glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA)多次渲染将近似正确的颜色(除非事情重叠).但这并不完美(正如您在下图中看到的那样,绿色/红色/蓝色框重叠的部分会变暗或累积alpha.(编辑:如果我在渲染中进行多次绘制以筛选部分而且仅渲染一次纹理,alpha累积问题消失,它确实有效,但为什么?!我不想为屏幕呈现相同的纹理数百次,以使其正确累积)
以下是一些详细说明问题的图像(多个渲染过程使用基本混合(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA),并且它们在纹理渲染步骤中多次渲染.右边的3个框渲染为100%红色,绿色或蓝色(0-255)但蓝色的阿尔法值为50%,红色的阿尔法值为25%,绿色的阿尔法值为75%:

那么,我想知道的细分:
期望的行为是,在该步骤结束时,最终的像素结果与我刚刚执行此操作相同:
而且,为了完整性,这里有一些我的原始天真尝试的代码(只是定期混合):
//RENDER TO TEXTURE.
void Clipped::refreshTexture(bool a_forceRefresh) {
if(a_forceRefresh || dirtyTexture){
auto pointAABB = basicAABB();
auto textureSize = castSize<int>(pointAABB.size());
clippedTexture = DynamicTextureDefinition::make("", textureSize, {0.0f, 0.0f, 0.0f, 0.0f});
dirtyTexture = false;
texture(clippedTexture->makeHandle(Point<int>(), textureSize));
framebuffer = renderer->makeFramebuffer(castPoint<int>(pointAABB.minPoint), textureSize, clippedTexture->textureId());
{
renderer->setBlendFunction(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
SCOPE_EXIT{renderer->defaultBlendFunction(); };
renderer->modelviewMatrix().push();
SCOPE_EXIT{renderer->modelviewMatrix().pop(); };
renderer->modelviewMatrix().top().makeIdentity();
framebuffer->start();
SCOPE_EXIT{framebuffer->stop(); };
const size_t renderPasses = 1; //Not …Run Code Online (Sandbox Code Playgroud)