2 Copyright (c) 2019 The Khronos Group Inc.
3 Use of this source code is governed by an MIT-style license that can be
4 found in the LICENSE.txt file.
10 <meta charset=
"utf-8">
11 <title>WebGL Uniform Buffers Conformance Tests
</title>
12 <link rel=
"stylesheet" href=
"../../resources/js-test-style.css"/>
13 <script src=
"../../js/js-test-pre.js"></script>
14 <script src=
"../../js/webgl-test-utils.js"></script>
15 <script id='vshader' type='x-shader/x-vertex'
>#version
300 es
16 layout(location=
0) in vec3 p;
19 gl_Position = vec4(p.xyz,
1.0);
22 <script id='fbadshader' type='x-shader/x-fragment'
>#version
300 es
23 precision mediump float;
24 layout(location=
0) out vec4 oColor;
40 oColor = vec4(UBORed * Red, UBOGreen * UBOGreen, UBOBlue * Blue,
1.0);
43 <script id='fshader' type='x-shader/x-fragment'
>#version
300 es
44 precision mediump float;
45 layout(location=
0) out vec4 oColor;
61 oColor = vec4(UBORed * UBOR, UBOGreen * UBOG, UBOBlue * UBOB,
1.0);
64 <script id='fshadernamed' type='x-shader/x-fragment'
>#version
300 es
65 precision mediump float;
66 layout(location=
0) out vec4 oColor;
76 oColor = vec4(UBOA.Red, UBOA.Green, UBOA.Blue,
1.0);
79 <script id='fshadernamedarray' type='x-shader/x-fragment'
>#version
300 es
80 precision mediump float;
81 layout(location=
0) out vec4 oColor;
91 oColor = vec4((UBOA[
0].Red + UBOA[
1].Red) /
2.0,
92 (UBOA[
0].Green + UBOA[
1].Green) /
2.0,
93 (UBOA[
0].Blue + UBOA[
1].Blue) /
2.0,
1.0);
96 <script id='fshadernestedstruct' type='x-shader/x-fragment'
>#version
300 es
97 precision mediump float;
98 layout(location=
0) out vec4 oColor;
114 // This is intended to reproduce a specific ANGLE bug that triggers when the wrapper struct is passed to a function.
115 // https://bugs.chromium.org/p/angleproject/issues/detail?id=
2084
116 void processColor(wrapper_t wrapper) {
117 oColor = vec4(wrapper.color.red, wrapper.color.green, wrapper.color.blue,
1.0);
122 processColor(UBOStruct);
125 <script id='fshaderarrayofstructs' type='x-shader/x-fragment'
>#version
300 es
126 precision mediump float;
127 layout(location=
0) out vec4 oColor;
136 color_t UBOColors[
2];
139 // This is intended to reproduce a specific ANGLE bug that triggers when a struct from an array of structs in an interface block is passed to a function.
140 // https://bugs.chromium.org/p/angleproject/issues/detail?id=
2084
141 vec3 processColor(color_t color) {
142 return vec3(color.red, color.green, color.blue);
147 oColor = vec4(processColor(UBOColors[
0]) + processColor(UBOColors[
1]),
1.0);
152 <div id=
"description"></div>
153 <canvas id=
"canvas" style=
"width: 50px; height: 50px;"> </canvas>
154 <div id=
"console"></div>
157 description("This test verifies the functionality of the Uniform Buffer objects");
161 var wtu
= WebGLTestUtils
;
162 var canvas
= document
.getElementById("canvas");
163 var gl
= wtu
.create3DContext(canvas
, null, 2);
168 testFailed("WebGL context does not exist");
170 testPassed("WebGL context exists");
172 wtu
.setupUnitQuad(gl
);
176 runUniformBufferOffsetAlignmentTest();
179 runNamedArrayDrawTest();
180 runNestedStructsDrawTest();
181 runArrayOfStructsDrawTest();
184 function runBindingTest() {
186 debug("Testing uniform buffer binding behavior");
187 shouldBeNull("gl.getParameter(gl.UNIFORM_BUFFER_BINDING)");
188 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "UNIFORM_BUFFER_BINDING query should succeed");
190 debug("Testing basic uniform buffer binding and unbinding");
191 b1
= gl
.createBuffer();
192 b2
= gl
.createBuffer();
193 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "createBuffer should not set an error");
194 shouldBeNonNull("b1");
195 shouldBeNonNull("b2");
196 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, b1
);
197 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to bind uniform buffer");
198 shouldBe("gl.getParameter(gl.UNIFORM_BUFFER_BINDING)", "b1");
199 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, b2
);
200 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to update uniform buffer binding");
201 shouldBe("gl.getParameter(gl.UNIFORM_BUFFER_BINDING)", "b2");
202 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, null);
203 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to unbind uniform buffer");
205 debug("Testing deleting uniform buffers");
208 shouldBeNull("gl.getParameter(gl.UNIFORM_BUFFER_BINDING)");
210 // Shouldn't be able to bind a deleted buffer.
211 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, b2
);
212 wtu
.glErrorShouldBe(gl
, gl
.INVALID_OPERATION
, "binding a deleted buffer should generate INVALID_OPERATION");
213 shouldBeNull("gl.getParameter(gl.UNIFORM_BUFFER_BINDING)");
216 function runBadShaderTest() {
218 var testProgram
= wtu
.setupProgram(gl
, ['vshader', 'fbadshader']);
220 testFailed("To define the same uniform in two uniform blocks should fail");
222 testPassed("To define the same uniform in two uniform blocks should fail");
226 function runUniformBufferOffsetAlignmentTest() {
228 var offsetAlignment
= gl
.getParameter(gl
.UNIFORM_BUFFER_OFFSET_ALIGNMENT
);
230 if (offsetAlignment
% 4 != 0) {
231 testFailed("Unexpected UNIFORM_BUFFER_OFFSET_ALIGNMENT - should be aligned on a 4-byte boundary");
233 testPassed("UNIFORM_BUFFER_OFFSET_ALIGNMENT is divisible by four");
237 function setRGBValuesToFloat32Array(floatView
, red
, green
, blue
) {
239 floatView
[1] = green
;
243 function checkFloat32UniformOffsetsInStd140Layout(uniformOffsets
, expectedInitialOffset
) {
244 if (expectedInitialOffset
=== undefined)
246 expectedInitialOffset
= 0;
248 // Verify that the uniform offsets are set according to the std140 layout, which WebGL enforces.
249 // This function checks this for 32-bit float values, which are expected to be tightly packed.
250 for (var i
= 0; i
< uniformOffsets
.length
; ++i
)
252 if (uniformOffsets
[i
] != expectedInitialOffset
+ i
* Float32Array
.BYTES_PER_ELEMENT
)
254 testFailed("Uniform offsets are not according to std140 layout");
261 function runDrawTest() {
263 debug("Testing drawing with uniform buffers");
265 var program
= wtu
.setupProgram(gl
, ['vshader', 'fshader']);
267 testFailed("Could not compile shader with uniform blocks without error");
271 var blockIndex_1
= gl
.getUniformBlockIndex(program
, "UBOData");
272 var blockSize_1
= gl
.getActiveUniformBlockParameter(program
, blockIndex_1
, gl
.UNIFORM_BLOCK_DATA_SIZE
);
273 var uniformIndices_1
= gl
.getUniformIndices(program
, ["UBORed", "UBOGreen", "UBOBlue"]);
274 var uniformOffsets_1
= gl
.getActiveUniforms(program
, uniformIndices_1
, gl
.UNIFORM_OFFSET
);
275 var blockIndex_2
= gl
.getUniformBlockIndex(program
, "UBOD");
276 var blockSize_2
= gl
.getActiveUniformBlockParameter(program
, blockIndex_2
, gl
.UNIFORM_BLOCK_DATA_SIZE
);
277 var uniformIndices_2
= gl
.getUniformIndices(program
, ["UBOR", "UBOG", "UBOB"]);
278 var uniformOffsets_2
= gl
.getActiveUniforms(program
, uniformIndices_2
, gl
.UNIFORM_OFFSET
);
279 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to query uniform block information without error");
281 if (uniformOffsets_1
.length
< 3 || uniformOffsets_2
.length
< 3) {
282 testFailed("Could not query uniform offsets");
286 if (!checkFloat32UniformOffsetsInStd140Layout(uniformOffsets_1
) || !checkFloat32UniformOffsetsInStd140Layout(uniformOffsets_2
))
291 var uboArray_1
= new ArrayBuffer(blockSize_1
);
292 var uboFloatView_1
= new Float32Array(uboArray_1
);
293 setRGBValuesToFloat32Array(uboFloatView_1
, 1.0, 0.0, 0.0); // UBORed, UBOGreen, UBOBlue
294 var uboArray_2
= new ArrayBuffer(blockSize_2
);
295 var uboFloatView_2
= new Float32Array(uboArray_2
);
296 setRGBValuesToFloat32Array(uboFloatView_2
, 1.0, 1.0, 1.0); // UBOR, UBOG, UBOB
298 var b_1
= gl
.createBuffer();
299 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, b_1
);
300 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboFloatView_1
, gl
.DYNAMIC_DRAW
);
301 var b_2
= gl
.createBuffer();
302 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, b_2
);
303 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboFloatView_2
, gl
.DYNAMIC_DRAW
);
304 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to set UBO data with no errors");
306 var bindings
= [1, 2];
307 gl
.uniformBlockBinding(program
, blockIndex_1
, bindings
[0]);
308 gl
.bindBufferBase(gl
.UNIFORM_BUFFER
, bindings
[0], b_1
);
309 gl
.uniformBlockBinding(program
, blockIndex_2
, bindings
[1]);
310 gl
.bindBufferBase(gl
.UNIFORM_BUFFER
, bindings
[1], b_2
);
311 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to call bindBufferBase without errors");
313 wtu
.clearAndDrawUnitQuad(gl
);
314 wtu
.checkCanvas(gl
, [255, 0, 0, 255], "draw call should set canvas to red", 2);
316 debug("Changing the data in the uniform buffer should automatically update the uniforms exposed to the draw call");
317 setRGBValuesToFloat32Array(uboFloatView_1
, 0.0, 0.0, 1.0); // UBORed, UBOGreen, UBOBlue
318 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, b_1
);
319 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboFloatView_1
, gl
.DYNAMIC_DRAW
);
321 wtu
.clearAndDrawUnitQuad(gl
);
322 wtu
.checkCanvas(gl
, [0, 0, 255, 255], "draw call should set canvas to blue", 2);
323 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "there should be no errors");
326 function runNamedDrawTest() {
328 debug("Testing drawing with named uniform buffers");
330 var program
= wtu
.setupProgram(gl
, ['vshader', 'fshadernamed']);
332 testFailed("Could not compile shader with named uniform blocks without error");
336 var blockIndex
= gl
.getUniformBlockIndex(program
, "UBOData");
337 var blockSize
= gl
.getActiveUniformBlockParameter(program
, blockIndex
, gl
.UNIFORM_BLOCK_DATA_SIZE
);
338 var uniformIndices
= gl
.getUniformIndices(program
, ["UBOData.Red", "UBOData.Green", "UBOData.Blue"]);
339 var uniformOffsets
= gl
.getActiveUniforms(program
, uniformIndices
, gl
.UNIFORM_OFFSET
);
340 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to query uniform block information without error");
342 if (uniformOffsets
.length
< 3) {
343 testFailed("Could not query uniform offsets");
347 if (!checkFloat32UniformOffsetsInStd140Layout(uniformOffsets
))
352 var uboArray
= new ArrayBuffer(blockSize
);
353 var uboFloatView
= new Float32Array(uboArray
);
354 setRGBValuesToFloat32Array(uboFloatView
, 1.0, 0.0, 0.0);
356 b1
= gl
.createBuffer();
357 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, b1
);
358 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboArray
, gl
.DYNAMIC_DRAW
);
359 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to set UBO data with no errors");
362 gl
.uniformBlockBinding(program
, blockIndex
, binding
);
363 gl
.bindBufferBase(gl
.UNIFORM_BUFFER
, binding
, b1
);
364 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to call bindBufferBase without errors");
366 wtu
.clearAndDrawUnitQuad(gl
);
367 wtu
.checkCanvas(gl
, [255, 0, 0, 255], "draw call should set canvas to red", 2);
369 debug("Changing the data in the uniform buffer should automatically update the uniforms exposed to the draw call");
370 setRGBValuesToFloat32Array(uboFloatView
, 0.0, 0.0, 1.0);
371 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboArray
, gl
.DYNAMIC_DRAW
);
373 wtu
.clearAndDrawUnitQuad(gl
);
374 wtu
.checkCanvas(gl
, [0, 0, 255, 255], "draw call should set canvas to blue", 2);
375 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "there should be no errors");
378 function runNamedArrayDrawTest() {
380 debug("Testing drawing with named uniform buffer arrays");
382 var program
= wtu
.setupProgram(gl
, ['vshader', 'fshadernamedarray']);
384 testFailed("could not compile shader with named uniform block arrays without error");
388 var blockIndex
= [gl
.getUniformBlockIndex(program
, "UBOData[0]"),
389 gl
.getUniformBlockIndex(program
, "UBOData[1]")];
390 if (blockIndex
[0] == gl
.INVALID_INDEX
||
391 blockIndex
[1] == gl
.INVALID_INDEX
) {
392 testFailed("Could not query uniform block index");
395 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to query uniform block indices without error");
396 var blockSize
= [gl
.getActiveUniformBlockParameter(program
, blockIndex
[0], gl
.UNIFORM_BLOCK_DATA_SIZE
),
397 gl
.getActiveUniformBlockParameter(program
, blockIndex
[1], gl
.UNIFORM_BLOCK_DATA_SIZE
)];
398 if (blockSize
[0] != blockSize
[1]) {
399 testFailed("uniform block instance array with different block sizes");
401 var uniformIndices
= gl
.getUniformIndices(program
, ["UBOData.Red", "UBOData.Green", "UBOData.Blue"]);
402 if (uniformIndices
< 3 ||
403 uniformIndices
[0] == gl
.INVALID_INDEX
||
404 uniformIndices
[1] == gl
.INVALID_INDEX
||
405 uniformIndices
[2] == gl
.INVALID_INDEX
) {
406 testFailed("Could not query uniform indices");
409 var uniformOffsets
= gl
.getActiveUniforms(program
, uniformIndices
, gl
.UNIFORM_OFFSET
);
410 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to query uniform block information without error");
411 if (uniformOffsets
.length
< 3) {
412 testFailed("Could not query uniform offsets");
416 if (!checkFloat32UniformOffsetsInStd140Layout(uniformOffsets
))
421 var offsetAlignment
= gl
.getParameter(gl
.UNIFORM_BUFFER_OFFSET_ALIGNMENT
);
422 var offset
= Math
.ceil(blockSize
[0] / offsetAlignment
) * offsetAlignment
;
424 var bufferSize
= offset
+ blockSize
[1];
425 var uboArray
= new ArrayBuffer(bufferSize
);
426 var uboFloatView
= new Float32Array(uboArray
);
427 setRGBValuesToFloat32Array(uboFloatView
, 1.0, 0.0, 0.0);
428 var uboFloatView2
= new Float32Array(uboArray
, offset
);
429 setRGBValuesToFloat32Array(uboFloatView2
, 0.0, 0.0, 1.0);
431 b1
= gl
.createBuffer();
432 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, b1
);
433 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboArray
, gl
.DYNAMIC_DRAW
);
434 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to set UBO data with no errors");
436 var bindings
= [4, 5];
437 gl
.uniformBlockBinding(program
, blockIndex
[0], bindings
[0]);
438 gl
.bindBufferRange(gl
.UNIFORM_BUFFER
, bindings
[0], b1
, 0, blockSize
[0]);
439 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to call bindBufferRange without errors");
440 gl
.uniformBlockBinding(program
, blockIndex
[1], bindings
[1]);
441 gl
.bindBufferRange(gl
.UNIFORM_BUFFER
, bindings
[1], b1
, offset
, blockSize
[1]);
442 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to call bindBufferRange without errors");
444 wtu
.clearAndDrawUnitQuad(gl
);
445 wtu
.checkCanvas(gl
, [127, 0, 127, 255], "draw call should set canvas to (0.5, 0, 0.5)", 2);
447 debug("Changing the data in the uniform buffer should automatically update the uniforms exposed to the draw call");
448 setRGBValuesToFloat32Array(uboFloatView
, 0.0, 1.0, 1.0);
449 setRGBValuesToFloat32Array(uboFloatView2
, 0.0, 0.0, 1.0);
450 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboArray
, gl
.DYNAMIC_DRAW
);
452 wtu
.clearAndDrawUnitQuad(gl
);
453 wtu
.checkCanvas(gl
, [0, 127, 255, 255], "draw call should set canvas to (0, 0.5, 1)", 2);
454 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "there should be no errors");
457 function runNestedStructsDrawTest() {
459 debug("Testing drawing with nested struct inside uniform block. The wrapper struct is passed to a function.");
461 var program
= wtu
.setupProgram(gl
, ['vshader', 'fshadernestedstruct'], undefined, undefined, true);
463 testFailed("Could not compile shader with nested structs without error");
467 var blockIndex
= gl
.getUniformBlockIndex(program
, "UBOData");
468 var blockSize
= gl
.getActiveUniformBlockParameter(program
, blockIndex
, gl
.UNIFORM_BLOCK_DATA_SIZE
);
469 var uniformIndices
= gl
.getUniformIndices(program
, ["UBOStruct.color.red", "UBOStruct.color.green", "UBOStruct.color.blue"]);
470 var uniformOffsets
= gl
.getActiveUniforms(program
, uniformIndices
, gl
.UNIFORM_OFFSET
);
471 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to query uniform block information without error");
473 if (uniformOffsets
.length
< 3) {
474 testFailed("Could not query uniform offsets");
478 if (!checkFloat32UniformOffsetsInStd140Layout(uniformOffsets
))
483 var uboArray
= new ArrayBuffer(blockSize
);
484 var uboFloatView
= new Float32Array(uboArray
);
485 setRGBValuesToFloat32Array(uboFloatView
, 0.0, 1.0, 0.0);
487 b1
= gl
.createBuffer();
488 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, b1
);
489 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboArray
, gl
.DYNAMIC_DRAW
);
490 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to set UBO data with no errors");
493 gl
.uniformBlockBinding(program
, blockIndex
, binding
);
494 gl
.bindBufferBase(gl
.UNIFORM_BUFFER
, binding
, b1
);
495 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to call bindBufferBase without errors");
497 wtu
.clearAndDrawUnitQuad(gl
);
498 wtu
.checkCanvas(gl
, [0, 255, 0, 255], "draw call should set canvas to green", 2);
500 debug("Changing the data in the uniform buffer should automatically update the uniforms exposed to the draw call");
501 setRGBValuesToFloat32Array(uboFloatView
, 0.0, 0.0, 1.0);
502 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboArray
, gl
.DYNAMIC_DRAW
);
504 wtu
.clearAndDrawUnitQuad(gl
);
505 wtu
.checkCanvas(gl
, [0, 0, 255, 255], "draw call should set canvas to blue", 2);
506 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "there should be no errors");
509 function runArrayOfStructsDrawTest() {
511 debug("Testing drawing with array of structs inside uniform block. A struct in the block is passed to a function.");
513 var program
= wtu
.setupProgram(gl
, ['vshader', 'fshaderarrayofstructs'], undefined, undefined, true);
515 testFailed("Could not compile shader with an array of structs in an interface block without error");
519 var blockIndex
= gl
.getUniformBlockIndex(program
, "UBOData");
520 var blockSize
= gl
.getActiveUniformBlockParameter(program
, blockIndex
, gl
.UNIFORM_BLOCK_DATA_SIZE
);
521 var uniformIndices
= gl
.getUniformIndices(program
, ["UBOColors[0].red", "UBOColors[0].green", "UBOColors[0].blue"]);
522 var uniformOffsets
= gl
.getActiveUniforms(program
, uniformIndices
, gl
.UNIFORM_OFFSET
);
523 var uniformIndices_2
= gl
.getUniformIndices(program
, ["UBOColors[1].red", "UBOColors[1].green", "UBOColors[1].blue"]);
524 var uniformOffsets_2
= gl
.getActiveUniforms(program
, uniformIndices_2
, gl
.UNIFORM_OFFSET
);
525 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to query uniform block information without error");
527 if (uniformOffsets
.length
< 3) {
528 testFailed("Could not query uniform offsets");
532 if (!checkFloat32UniformOffsetsInStd140Layout(uniformOffsets
))
536 if (!checkFloat32UniformOffsetsInStd140Layout(uniformOffsets_2
, uniformOffsets_2
[0]))
541 var uboArray
= new ArrayBuffer(blockSize
);
542 var uboFloatView
= new Float32Array(uboArray
);
543 setRGBValuesToFloat32Array(uboFloatView
, 0.0, 0.5, 0.0);
544 var uboFloatView2
= new Float32Array(uboArray
, uniformOffsets_2
[0]);
545 setRGBValuesToFloat32Array(uboFloatView2
, 0.0, 0.5, 0.0);
547 b1
= gl
.createBuffer();
548 gl
.bindBuffer(gl
.UNIFORM_BUFFER
, b1
);
549 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboArray
, gl
.DYNAMIC_DRAW
);
550 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to set UBO data with no errors");
553 gl
.uniformBlockBinding(program
, blockIndex
, binding
);
554 gl
.bindBufferBase(gl
.UNIFORM_BUFFER
, binding
, b1
);
555 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "should be able to call bindBufferBase without errors");
557 wtu
.clearAndDrawUnitQuad(gl
);
558 wtu
.checkCanvas(gl
, [0, 255, 0, 255], "draw call should set canvas to green", 2);
560 debug("Changing the data in the uniform buffer should automatically update the uniforms exposed to the draw call");
561 setRGBValuesToFloat32Array(uboFloatView
, 1.0, 0.0, 0.0);
562 setRGBValuesToFloat32Array(uboFloatView2
, 0.0, 0.0, 1.0);
563 gl
.bufferData(gl
.UNIFORM_BUFFER
, uboArray
, gl
.DYNAMIC_DRAW
);
565 wtu
.clearAndDrawUnitQuad(gl
);
566 wtu
.checkCanvas(gl
, [255, 0, 255, 255], "draw call should set canvas to purple", 2);
567 wtu
.glErrorShouldBe(gl
, gl
.NO_ERROR
, "there should be no errors");
571 var successfullyParsed
= true;
573 <script src=
"../../js/js-test-post.js"></script>