The Setup
I have a 3D garage door with transparent windows.
I then enable a plane behind the door with a brick wall texture on it (tinted red here for visibility) and take a screenshot of the door through an orthographic camera.
The render texture has the following config:
this.renderTarget = new pc.RenderTarget({
colorBuffer: colorBuffer,
depth: true,
flipY: true,
samples: pc.app.graphicsDevice.maxSamples
});
and the color buffer has the following config:
{
width: 0, // dynamic
height: 0, // dynamic
format: pc.PIXELFORMAT_R8_G8_B8,
autoMipmap: true,
mipmaps: true,
minFilter: pc.FILTER_LINEAR_MIPMAP_NEAREST,
anisotropy: pc.app.graphicsDevice.maxAnisotropy
}
I then place that texture on a material, place that material on a quad, and place manipulate the corners of the quad to match a house.
Note that in order to get the perspective effect, I’m using a custom shader. That shader looks like this:
varying vec2 vUv0;
uniform vec4 _Color;
uniform mat4 _Matrix0;
uniform sampler2D _MainTex;
uniform int textureExists;
void main(void)
{
vec4 persp = _Matrix0 * vec4(vUv0, 1, 1);
vec2 uv_persp = vec2(persp.x / persp.z, persp.y / persp.z);
vec4 c = _Color;
if (textureExists == 1) {
c = texture2D(_MainTex, uv_persp.xy);
}
gl_FragColor = c;
}
Essentially all it does is calculate new UV coordinates from a precalculated matrix. As you can see it does nothing to the pixel color whatsoever.
The Problem
In the house image above, the windows are red when the actual texture clearly shows them to be black. And when I stretch it out to fill the screen, it transitions to black.
When the polygon is stretched, we can see it fade smoothly from black in big parts, to red in smaller parts.
The Clues
When I turn antialiasing off on the render texture (samples: 1), the problem goes away completely.
When I reenable antialiasing on the render texture and change the pixel format on the color buffer to include an alpha channel (PIXELFORMAT_R8_G8_B8_A8), we can now see straight through the black windows. The red windows are opaque and show the red brick wall, as intended.
The Question
As far as I can tell, this has to do with the way transparent pixels are handled during hardware antialiasing. Is this due to something I’m doing wrong? Or is this an engine bug?