mirror of
https://github.com/servo/servo.git
synced 2025-08-05 21:50:18 +01:00
WebVR API Implementation, r=larsbergstrom
This commit is contained in:
parent
13826970c4
commit
c5705bff50
70 changed files with 13044 additions and 20 deletions
210
tests/html/webvr/js/vr-cube-island.js
Normal file
210
tests/html/webvr/js/vr-cube-island.js
Normal file
|
@ -0,0 +1,210 @@
|
|||
// Copyright 2016 The Chromium Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
/* global mat4, WGLUProgram */
|
||||
|
||||
/*
|
||||
Like CubeSea, but designed around a users physical space. One central platform
|
||||
that maps to the users play area and several floating cubes that sit just
|
||||
those boundries (just to add visual interest)
|
||||
*/
|
||||
window.VRCubeIsland = (function () {
|
||||
"use strict";
|
||||
|
||||
var cubeIslandVS = [
|
||||
"uniform mat4 projectionMat;",
|
||||
"uniform mat4 modelViewMat;",
|
||||
"attribute vec3 position;",
|
||||
"attribute vec2 texCoord;",
|
||||
"varying vec2 vTexCoord;",
|
||||
|
||||
"void main() {",
|
||||
" vTexCoord = texCoord;",
|
||||
" gl_Position = projectionMat * modelViewMat * vec4( position, 1.0 );",
|
||||
"}",
|
||||
].join("\n");
|
||||
|
||||
var cubeIslandFS = [
|
||||
"precision mediump float;",
|
||||
"uniform sampler2D diffuse;",
|
||||
"varying vec2 vTexCoord;",
|
||||
|
||||
"void main() {",
|
||||
" gl_FragColor = texture2D(diffuse, vTexCoord);",
|
||||
"}",
|
||||
].join("\n");
|
||||
|
||||
var CubeIsland = function (gl, texture, width, depth) {
|
||||
this.gl = gl;
|
||||
|
||||
this.statsMat = mat4.create();
|
||||
|
||||
this.texture = texture;
|
||||
|
||||
this.program = new WGLUProgram(gl);
|
||||
this.program.attachShaderSource(cubeIslandVS, gl.VERTEX_SHADER);
|
||||
this.program.attachShaderSource(cubeIslandFS, gl.FRAGMENT_SHADER);
|
||||
this.program.bindAttribLocation({
|
||||
position: 0,
|
||||
texCoord: 1
|
||||
});
|
||||
this.program.link();
|
||||
|
||||
this.vertBuffer = gl.createBuffer();
|
||||
this.indexBuffer = gl.createBuffer();
|
||||
|
||||
this.resize(width, depth);
|
||||
};
|
||||
|
||||
CubeIsland.prototype.resize = function (width, depth) {
|
||||
var gl = this.gl;
|
||||
|
||||
this.width = width;
|
||||
this.depth = depth;
|
||||
|
||||
var cubeVerts = [];
|
||||
var cubeIndices = [];
|
||||
|
||||
// Build a single box.
|
||||
function appendBox (left, bottom, back, right, top, front) {
|
||||
// Bottom
|
||||
var idx = cubeVerts.length / 5.0;
|
||||
cubeIndices.push(idx, idx + 1, idx + 2);
|
||||
cubeIndices.push(idx, idx + 2, idx + 3);
|
||||
|
||||
cubeVerts.push(left, bottom, back, 0.0, 1.0);
|
||||
cubeVerts.push(right, bottom, back, 1.0, 1.0);
|
||||
cubeVerts.push(right, bottom, front, 1.0, 0.0);
|
||||
cubeVerts.push(left, bottom, front, 0.0, 0.0);
|
||||
|
||||
// Top
|
||||
idx = cubeVerts.length / 5.0;
|
||||
cubeIndices.push(idx, idx + 2, idx + 1);
|
||||
cubeIndices.push(idx, idx + 3, idx + 2);
|
||||
|
||||
cubeVerts.push(left, top, back, 0.0, 0.0);
|
||||
cubeVerts.push(right, top, back, 1.0, 0.0);
|
||||
cubeVerts.push(right, top, front, 1.0, 1.0);
|
||||
cubeVerts.push(left, top, front, 0.0, 1.0);
|
||||
|
||||
// Left
|
||||
idx = cubeVerts.length / 5.0;
|
||||
cubeIndices.push(idx, idx + 2, idx + 1);
|
||||
cubeIndices.push(idx, idx + 3, idx + 2);
|
||||
|
||||
cubeVerts.push(left, bottom, back, 0.0, 1.0);
|
||||
cubeVerts.push(left, top, back, 0.0, 0.0);
|
||||
cubeVerts.push(left, top, front, 1.0, 0.0);
|
||||
cubeVerts.push(left, bottom, front, 1.0, 1.0);
|
||||
|
||||
// Right
|
||||
idx = cubeVerts.length / 5.0;
|
||||
cubeIndices.push(idx, idx + 1, idx + 2);
|
||||
cubeIndices.push(idx, idx + 2, idx + 3);
|
||||
|
||||
cubeVerts.push(right, bottom, back, 1.0, 1.0);
|
||||
cubeVerts.push(right, top, back, 1.0, 0.0);
|
||||
cubeVerts.push(right, top, front, 0.0, 0.0);
|
||||
cubeVerts.push(right, bottom, front, 0.0, 1.0);
|
||||
|
||||
// Back
|
||||
idx = cubeVerts.length / 5.0;
|
||||
cubeIndices.push(idx, idx + 2, idx + 1);
|
||||
cubeIndices.push(idx, idx + 3, idx + 2);
|
||||
|
||||
cubeVerts.push(left, bottom, back, 1.0, 1.0);
|
||||
cubeVerts.push(right, bottom, back, 0.0, 1.0);
|
||||
cubeVerts.push(right, top, back, 0.0, 0.0);
|
||||
cubeVerts.push(left, top, back, 1.0, 0.0);
|
||||
|
||||
// Front
|
||||
idx = cubeVerts.length / 5.0;
|
||||
cubeIndices.push(idx, idx + 1, idx + 2);
|
||||
cubeIndices.push(idx, idx + 2, idx + 3);
|
||||
|
||||
cubeVerts.push(left, bottom, front, 0.0, 1.0);
|
||||
cubeVerts.push(right, bottom, front, 1.0, 1.0);
|
||||
cubeVerts.push(right, top, front, 1.0, 0.0);
|
||||
cubeVerts.push(left, top, front, 0.0, 0.0);
|
||||
}
|
||||
|
||||
// Appends a cube with the given centerpoint and size.
|
||||
function appendCube (x, y, z, size) {
|
||||
var halfSize = size * 0.5;
|
||||
appendBox(x - halfSize, y - halfSize, z - halfSize,
|
||||
x + halfSize, y + halfSize, z + halfSize);
|
||||
}
|
||||
|
||||
// Main "island", covers where the user can safely stand. Top of the cube
|
||||
// (the ground the user stands on) should be at Y=0 to align with users
|
||||
// floor. X=0 and Z=0 should be at the center of the users play space.
|
||||
appendBox(-width * 0.5, -width, -depth * 0.5, width * 0.5, 0, depth * 0.5);
|
||||
|
||||
// A sprinkling of other cubes to make things more visually interesting.
|
||||
appendCube(1.1, 0.3, (-depth * 0.5) - 0.8, 0.5);
|
||||
appendCube(-0.5, 1.0, (-depth * 0.5) - 0.9, 0.75);
|
||||
appendCube(0.6, 1.5, (-depth * 0.5) - 0.6, 0.4);
|
||||
appendCube(-1.0, 0.5, (-depth * 0.5) - 0.5, 0.2);
|
||||
|
||||
appendCube((-width * 0.5) - 0.8, 0.3, -1.1, 0.5);
|
||||
appendCube((-width * 0.5) - 0.9, 1.0, 0.5, 0.75);
|
||||
appendCube((-width * 0.5) - 0.6, 1.5, -0.6, 0.4);
|
||||
appendCube((-width * 0.5) - 0.5, 0.5, 1.0, 0.2);
|
||||
|
||||
appendCube((width * 0.5) + 0.8, 0.3, 1.1, 0.5);
|
||||
appendCube((width * 0.5) + 0.9, 1.0, -0.5, 0.75);
|
||||
appendCube((width * 0.5) + 0.6, 1.5, 0.6, 0.4);
|
||||
appendCube((width * 0.5) + 0.5, 0.5, -1.0, 0.2);
|
||||
|
||||
appendCube(1.1, 1.4, (depth * 0.5) + 0.8, 0.5);
|
||||
appendCube(-0.5, 1.0, (depth * 0.5) + 0.9, 0.75);
|
||||
appendCube(0.6, 0.4, (depth * 0.5) + 0.6, 0.4);
|
||||
|
||||
|
||||
gl.bindBuffer(gl.ARRAY_BUFFER, this.vertBuffer);
|
||||
gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(cubeVerts), gl.STATIC_DRAW);
|
||||
|
||||
gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, this.indexBuffer);
|
||||
gl.bufferData(gl.ELEMENT_ARRAY_BUFFER, new Uint16Array(cubeIndices), gl.STATIC_DRAW);
|
||||
|
||||
this.indexCount = cubeIndices.length;
|
||||
};
|
||||
|
||||
CubeIsland.prototype.render = function (projectionMat, modelViewMat, stats) {
|
||||
var gl = this.gl;
|
||||
var program = this.program;
|
||||
|
||||
program.use();
|
||||
|
||||
gl.uniformMatrix4fv(program.uniform.projectionMat, false, projectionMat);
|
||||
gl.uniformMatrix4fv(program.uniform.modelViewMat, false, modelViewMat);
|
||||
|
||||
gl.bindBuffer(gl.ARRAY_BUFFER, this.vertBuffer);
|
||||
gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, this.indexBuffer);
|
||||
|
||||
gl.enableVertexAttribArray(program.attrib.position);
|
||||
gl.enableVertexAttribArray(program.attrib.texCoord);
|
||||
|
||||
gl.vertexAttribPointer(program.attrib.position, 3, gl.FLOAT, false, 20, 0);
|
||||
gl.vertexAttribPointer(program.attrib.texCoord, 2, gl.FLOAT, false, 20, 12);
|
||||
|
||||
gl.activeTexture(gl.TEXTURE0);
|
||||
gl.uniform1i(this.program.uniform.diffuse, 0);
|
||||
gl.bindTexture(gl.TEXTURE_2D, this.texture);
|
||||
|
||||
gl.drawElements(gl.TRIANGLES, this.indexCount, gl.UNSIGNED_SHORT, 0);
|
||||
|
||||
if (stats) {
|
||||
// To ensure that the FPS counter is visible in VR mode we have to
|
||||
// render it as part of the scene.
|
||||
mat4.fromTranslation(this.statsMat, [0, 1.5, -this.depth * 0.5]);
|
||||
mat4.scale(this.statsMat, this.statsMat, [0.5, 0.5, 0.5]);
|
||||
mat4.rotateX(this.statsMat, this.statsMat, -0.75);
|
||||
mat4.multiply(this.statsMat, modelViewMat, this.statsMat);
|
||||
stats.render(projectionMat, this.statsMat);
|
||||
}
|
||||
};
|
||||
|
||||
return CubeIsland;
|
||||
})();
|
Loading…
Add table
Add a link
Reference in a new issue