Premultiplied Alpha = false
by Gregg Tavares
HTML
<script src="http://greggman.github.com/webgl-fundamentals/webgl/resources/webgl-utils.js"></script>
<script id="vshader" type="whatever">
attribute vec4 a_position;
varying vec2 v_texcoord;
void main() {
gl_Position = a_position;
// assuming a unit quad for position we
// can just use that for texcoords. Flip Y though so we get the top at 0
v_texcoord = a_position.xy * vec2(0.5, -0.5) + 0.5;
}
</script>
<script id="fshader" type="whatever">
precision mediump float;
uniform bool u_premultiply;
varying vec2 v_texcoord;
#define PI 3.14159
void main() {
float alpha = sin(v_texcoord.x * PI) * sin(v_texcoord.y * PI);
vec4 color = vec4(1, 0, 0, alpha);
if (u_premultiply) {
color = vec4(color.rgb * color.a, color.a);
}
gl_FragColor = color;
}
</script>
<table>
<tr>
<td>canvas: premultipliedAlpha: true<br/>
data: not premultiplied</td>
<td>canvas: premultipliedAlpha: false<br/>
data: not premultiplied</td></tr>
<tr>
<td><canvas id="1" width="256" height="256"></canvas></td>
<td><canvas id="2" width="256" height="256"></canvas></td>
</tr>
<tr>
<td>canvas: premultipliedAlpha: true<br/>
data: premultiplied</td>
<td>canvas: premultipliedAlpha: false<br/>
data: premultiplied</td></tr>
<tr>
<td><canvas id="3" width="256" height="256"></canvas></td>
<td><canvas id="4" width="256" height="256"></canvas></td>
</tr>
</table>
CSS
body { background-color: green; }
canvas { border: 1px solid black; }
JavaScript
render(document.getElementById("1"));
render(document.getElementById("2"), { premultipliedAlpha: false });
render(document.getElementById("3"), undefined, true);
render(document.getElementById("4"), { premultipliedAlpha: false }, true);
function render(canvas, opt_attribs, premultiplyInShader) {
var gl = getWebGLContext(canvas, opt_attribs);
if (!gl) {
alert("no WebGL");
return;
}
// Note: createProgramFromScripts will call bindAttribLocation
// based on the index of the attibute names we pass to it.
var program = createProgramFromScripts(
gl,
["vshader", "fshader"],
["a_position"]);
gl.useProgram(program);
if (premultiplyInShader) {
var loc = gl.getUniformLocation(program, "u_premultiply");
gl.uniform1i(loc, 1);
}
// Setup a unit quad
var positions = [
1, 1,
-1, 1,
-1, -1,
1, 1,
-1, -1,
1, -1,
];
var vertBuffer = gl.createBuffer();
gl.bindBuffer(gl.ARRAY_BUFFER, vertBuffer);
gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(positions), gl.STATIC_DRAW);
gl.enableVertexAttribArray(0);
gl.vertexAttribPointer(0, 2, gl.FLOAT, false, 0, 0);
gl.drawArrays(gl.TRIANGLES, 0, positions.length / 2);
}