-
-
Notifications
You must be signed in to change notification settings - Fork 421
Description
I'm having an issue with the depth test not working with WebGL. It works as expected with C++ OpenGL.
Also, this is my first post, so let me know if this is not the appropriate way to present an issue.
C++ OpenGL compiles to the following correct result:

JS WebGL compiles to the following, which is incorrect. Simply notice the triangles are switched:

At the bottom is the entirety of the code I am using to test. I am using the latest versions of Haxe and Lime.
Mostly note the GL calls to force the depth test, and the vertices I am passing to the program. If you switch the order the triangles are positioned in the array, the JavaScript WebGL triangles will swap depths, but the C++ triangles will not. This tells me the depth test is not working for the WebGL context.
In the meantime, is there a workaround for this issue? I've tried everything I could think of so far, but I could be missing something obvious.
Thanks!
package;
import lime.app.Application;
import lime.graphics.opengl.*;
import lime.graphics.RenderContext;
import lime.graphics.Renderer;
import lime.math.Matrix4;
import lime.utils.Float32Array;
class Main extends Application {
public function new() {
super();
}
var _firstFrame:Bool = true;
var _vertices:Float32Array;
public override function render(render:Renderer):Void {
if (_firstFrame) {
// Do everything here only on the first frame
GL.clearColor(.08, .09, .10, 1);
GL.clearDepthf(1);
GL.depthFunc(GL.LEQUAL);
GL.enable(GL.DEPTH_TEST);
GL.depthMask(true);
var aspect:Float = window.width / window.height;
var FOV:Float = Math.tan(45*Math.PI/360.0);
var near:Float = .1;
var far:Float = 2;
var _projectionMatrix:Matrix4 = new Float32Array([
1 / (FOV * aspect), 0, 0, 0,
0, 1 / FOV, 0, 0,
0, 0, (near + far) / (near - far), -1,
0, 0, 2 * near * far / (near - far), 0
]);
var _vertexShaderCode =
#if web
"precision mediump float;" +
#end
"
attribute vec3 _vertexPosition;
varying vec3 _vertexColor;
uniform mat4 _projectionMatrix;
void main () {
_vertexColor = vec3(cos(_vertexPosition.x * 12.0 + _vertexPosition.y * 8.0), sin(_vertexPosition.x * 10.0 + _vertexPosition.y * 14.0), 1.0);
gl_Position = _projectionMatrix * vec4(_vertexPosition, 1.0);
}
";
var _vertexShader:GLShader = createShader(_vertexShaderCode, GL.VERTEX_SHADER);
var _fragmentShaderCode =
#if web
"precision mediump float;" +
#end
"
varying vec3 _vertexColor;
void main () {
gl_FragColor = vec4(_vertexColor, 1.0);
}
";
var _fragmentShader:GLShader = createShader(_fragmentShaderCode, GL.FRAGMENT_SHADER);
var _shaderProgram:GLProgram = GL.createProgram();
GL.attachShader(_shaderProgram, _vertexShader);
GL.attachShader(_shaderProgram, _fragmentShader);
GL.linkProgram(_shaderProgram);
GL.useProgram(_shaderProgram);
// Swapping the top and bottom triangle code does not affect the image in C++
// But in JavaScript (webGL) the triangles will swap position. This is because it is not performing the depth test.
_vertices = new Float32Array([
// Top triangle (closer to camera)
0, .1, -1.0,
-.2, -.1, -1.0,
.2, -.1, -1.0,
// Bottom triangle (further from camera)
0, 0, -1.1,
-.2, -.2, -1.1,
.2, -.2, -1.1
]);
var _vbo:GLBuffer = GL.createBuffer();
GL.bindBuffer(GL.ARRAY_BUFFER, _vbo);
GL.bufferData(GL.ARRAY_BUFFER, Math.floor(_vertices.length * Float32Array.BYTES_PER_ELEMENT), _vertices.toBytes(), GL.STATIC_DRAW);
var _vertexPosition = GL.getAttribLocation(_shaderProgram, "_vertexPosition");
GL.vertexAttribPointer(_vertexPosition, 3, GL.FLOAT, false, 0, 0);
GL.enableVertexAttribArray(_vertexPosition);
var _projectionMatrix_location = GL.getUniformLocation(_shaderProgram, "_projectionMatrix");
GL.uniformMatrix4fv(_projectionMatrix_location, 1, false, new Float32Array(_projectionMatrix));
GL.viewport(0, 0, window.width, window.height);
_firstFrame = false;
}
// Every frame (otherwise it flickers in the C++ version)
GL.clear(GL.COLOR_BUFFER_BIT | GL.DEPTH_BUFFER_BIT);
GL.drawArrays(GL.TRIANGLES, 0, Math.floor(_vertices.length / 3));
}
private function createShader(_source:String, _type:Int):GLShader {
var _shader = GL.createShader(_type);
GL.shaderSource (_shader, _source);
GL.compileShader (_shader);
return _shader;
}
}