Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

Draws quads instead of point sprites for platforms other than the Pla…

…yBook.
  • Loading branch information...
commit 76e31464110bc32de80076241b7fb510c94d26a4 1 parent 1cd14ee
Andrei Kopytov authored
Showing with 189 additions and 23 deletions.
  1. +119 −23 tunneltilt/geometry.js
  2. +70 −0 tunneltilt/shaders.html
View
142 tunneltilt/geometry.js
@@ -18,6 +18,12 @@
var RAD2DEG = 180 / Math.PI;
/**
+ * If we are running this game in a desktop browser, we will use quads instead of point sprites
+ * for drawing the ball and explosion effect
+ */
+var playbook = navigator.userAgent.indexOf("PlayBook") > -1 ? true : false;
+
+/**
* Utility function to linearly interpolate between values a and b, according
* to the parameter t, which varies between 0 and 1.
*/
@@ -34,6 +40,12 @@ Particles = function() {
// Arrays of particle velocities and sizes.
this.velocityData = [];
this.sizeData = [];
+ if (!playbook) {
+ var positions = [-1, 1, 0, 1, 1, 0, -1, -1, 0, 1, -1, 0, -1, -1, 0, 1, 1, 0];
+ var texCoords = [0, 1, 1, 1, 0, 0, 1, 0, 0, 0, 1, 1];
+ this.positionData = [];
+ this.texCoordData = [];
+ }
// Initial time, this varies from 0 to 1.
this.time = 0;
@@ -43,15 +55,35 @@ Particles = function() {
var speed = 10.0 + Math.random() * 15.0;
var angle = Math.random() * 2 * Math.PI;
var angle2 = Math.random() * 2 * Math.PI;
- this.velocityData[i*3] = speed * Math.cos(angle) * Math.sin(angle2);
- this.velocityData[i*3+1] = speed * Math.sin(angle) * Math.sin(angle2);
- this.velocityData[i*3+2] = speed * Math.cos(angle2);
- this.sizeData[i] = Math.random() * 100;
+ if (playbook) {
+ this.velocityData[i*3] = speed * Math.cos(angle) * Math.sin(angle2);
+ this.velocityData[i*3+1] = speed * Math.sin(angle) * Math.sin(angle2);
+ this.velocityData[i*3+2] = speed * Math.cos(angle2);
+ this.sizeData[i] = Math.random() * 100;
+ } else {
+ // Append quad size (6-verts per quad)
+ var tempSize = Math.random() * 100;
+ var concatSize = [tempSize, tempSize, tempSize, tempSize, tempSize, tempSize];
+ this.sizeData = this.sizeData.concat(concatSize);
+
+ // Append quad velocity (6-verts per quad)
+ var tempVelocity = [speed * Math.cos(angle) * Math.sin(angle2), speed * Math.sin(angle) * Math.sin(angle2), speed * Math.cos(angle2)];
+ var concatVelocity = [tempVelocity,tempVelocity, tempVelocity, tempVelocity, tempVelocity, tempVelocity];
+ this.velocityData = this.velocityData.concat(concatVelocity);
+
+ // Append position and texture coordinates (6-verts per quad)
+ this.positionData = this.positionData.concat(positions);
+ this.texCoordData = this.texCoordData.concat(texCoords);
+ }
}
// Create and fill the buffers with data
this.velocityBuffer = createArrayBuffer(this.velocityData, 3);
this.sizeBuffer = createArrayBuffer(this.sizeData, 1);
+ if (!playbook) {
+ this.positionBuffer = createArrayBuffer(this.positionData, 3);
+ this.texCoordBuffer = createArrayBuffer(this.texCoordData, 2);
+ }
}
/**
@@ -59,9 +91,14 @@ Particles = function() {
* doesn't change.
*/
Particles.prototype.initShader = function(perspective) {
- var attributes = ["aVelocity", "aSize"];
var uniforms = ["uPMatrix", "uSampler", "uTime"];
- this.shader = loadShader("particle-vs", "particle-fs", attributes, uniforms);
+ if (playbook) {
+ var attributes = ["aVelocity", "aSize"];
+ this.shader = loadShader("particle-vs", "particle-fs", attributes, uniforms);
+ } else {
+ var attributes = ["aPosition", "aTextureCoord", "aVelocity", "aSize"];
+ this.shader = loadShader("particle-quad-vs", "particle-quad-fs", attributes, uniforms);
+ }
gl.uniformMatrix4fv(this.shader.uniform["uPMatrix"], false, perspective);
}
@@ -93,11 +130,17 @@ Particles.prototype.draw = function (ball_matrix, elapsedTime) {
// Send the parameters to the shader
gl.uniform1f(this.shader.uniform["uTime"], this.time);
- setVertexAttribs(this.shader, [this.velocityBuffer, this.sizeBuffer]);
+ if (playbook)
+ setVertexAttribs(this.shader, [this.velocityBuffer, this.sizeBuffer]);
+ else
+ setVertexAttribs(this.shader, [this.positionBuffer, this.texCoordBuffer, this.velocityBuffer, this.sizeBuffer]);
- // Draw the points. We don't actually draw all of them at all times,
+ // Draw the points / quads. We don't actually draw all of them at all times,
// to give a shimmering effect as particles appear and disappear.
- gl.drawArrays(gl.POINTS, 0, this.sizeData.length - Math.abs(Math.sin(this.time*Math.PI*2)*150));
+ if (playbook)
+ gl.drawArrays(gl.POINTS, 0, this.sizeData.length - Math.abs(Math.sin(this.time*Math.PI*2)*150));
+ else
+ gl.drawArrays(gl.TRIANGLES, 0, this.positionBuffer.numItems - Math.floor(Math.abs(Math.sin(this.time*Math.PI*2)*150))*6);
// Re-enable depth testing
gl.enable(gl.DEPTH_TEST);
@@ -447,12 +490,28 @@ Ball = function (tunnelRadius) {
this.ballZ = -30;
// Position data for the two parts of the ball.
- var positionData = [0, -tunnelRadius + 7, this.ballZ , 1];
- var positionData2 = [0, -tunnelRadius + 7, this.ballZ + 0.05, 1];
+ if (playbook) {
+ var positionData = [0, -tunnelRadius + 7, this.ballZ , 1];
+ var positionData2 = [0, -tunnelRadius + 7, this.ballZ + 0.05, 1];
+ } else {
+ // Set up the coordinates of our quad and the texture coords that will be mapped to that quad
+ var positionData = [-1, 1, 0, 1, 1, 0, -1, -1, 0, 1, -1, 0];
+ var texCoordData = [0, 1, 1, 1, 0, 0, 1, 0];
+ var texCoordData2 = [0, 0, 1, 0, 0, 1, 1, 1];
+
+ // Ball glow effect
+ this.ballGlow = 0;
+ }
// Create and fill buffer data.
- this.positionBuffer = createArrayBuffer(positionData, 4);
- this.positionBuffer2 = createArrayBuffer(positionData2, 4);
+ if (playbook) {
+ this.positionBuffer = createArrayBuffer(positionData, 4);
+ this.positionBuffer2 = createArrayBuffer(positionData2, 4);
+ } else {
+ this.positionBuffer = createArrayBuffer(positionData, 3);
+ this.texCoordBuffer = createArrayBuffer(texCoordData, 2);
+ this.texCoordBuffer2 = createArrayBuffer(texCoordData2, 2);
+ }
// Degrees per second rotation speed
this.rotationSpeed = 0;
@@ -473,7 +532,20 @@ Ball = function (tunnelRadius) {
Math.abs(this.glowOffset/2),
0]);
}
-
+
+ if (!playbook) {
+ if (this.ballGlow < 0.3)
+ this.ballGlow += 0.0075;
+ else
+ this.ballGlow = -this.ballGlow;
+ mat4.translate(mvMatrix, [0, -13, this.ballZ]);
+ mat4.rotate(mvMatrix, 0.1, [0, 1, 0]);
+ if (glow)
+ mat4.scale(mvMatrix, [5.0+Math.abs(this.ballGlow), 5.0+Math.abs(this.ballGlow), 5.0]);
+ else
+ mat4.scale(mvMatrix, [5.0, 5.0, 5.0]);
+ }
+
// Store the modelview matrix, so the explosion
// can find the ball later.
this.mvMatrix = mvMatrix;
@@ -486,9 +558,15 @@ Ball = function (tunnelRadius) {
* transform, since it doesn't change.
*/
Ball.prototype.initShader = function(perspective) {
- var attributes = ["aPosition"];
- var uniforms = ["uPMatrix", "uMVMatrix", "uSizeMult", "uSampler", "uAmbient", "uTransparency"];
- this.shader = loadShader("ball-vs", "ball-fs", attributes, uniforms);
+ if (playbook) {
+ var attributes = ["aPosition"];
+ var uniforms = ["uPMatrix", "uMVMatrix", "uSizeMult", "uSampler", "uAmbient", "uTransparency"];
+ this.shader = loadShader("ball-vs", "ball-fs", attributes, uniforms);
+ } else {
+ var attributes = ["aPosition", "aTextureCoord"];
+ var uniforms = ["uPMatrix", "uMVMatrix", "uSampler", "uAmbient", "uTransparency"];
+ this.shader = loadShader("ball-quad-vs", "ball-quad-fs", attributes, uniforms);
+ }
gl.uniformMatrix4fv(this.shader.uniform["uPMatrix"], false, perspective);
}
@@ -522,22 +600,40 @@ Ball.prototype.draw = function (gameInfo, currentTime) {
gl.blendFunc(gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA);
// Set up buffer data.
- setVertexAttribs(this.shader, [this.positionBuffer]);
+ if (playbook) {
+ setVertexAttribs(this.shader, [this.positionBuffer]);
+ } else {
+ setVertexAttribs(this.shader, [this.positionBuffer, this.texCoordBuffer]);
+ gl.disable(gl.DEPTH_TEST);
+ }
// Draw the glow.
- gl.uniform1f(this.shader.uniform["uSizeMult"], 1.025 + 0.025 * Math.sin(currentTime/100));
+ if (playbook)
+ gl.uniform1f(this.shader.uniform["uSizeMult"], 1.025 + 0.025 * Math.sin(currentTime/100));
gl.uniform1f(this.shader.uniform["uTransparency"], 1.0);
this.setMatrixUniforms(this.shader, true);
this.glowTexture.bind();
- gl.drawArrays(gl.POINTS, 0, 1);
+ if (playbook)
+ gl.drawArrays(gl.POINTS, 0, 1);
+ else
+ gl.drawArrays(gl.TRIANGLE_STRIP, 0, 4);
// Draw the ball.
gl.uniform1f(this.shader.uniform["uTransparency"], 1.0 - ball_ambient/40.0);
- setVertexAttribs(this.shader, [this.positionBuffer2]);
- gl.uniform1f(this.shader.uniform["uSizeMult"], 1.0);
+ if (playbook) {
+ setVertexAttribs(this.shader, [this.positionBuffer2]);
+ gl.uniform1f(this.shader.uniform["uSizeMult"], 1.0);
+ } else {
+ setVertexAttribs(this.shader, [this.positionBuffer, this.texCoordBuffer2]);
+ }
this.setMatrixUniforms(this.shader, false);
this.texture.bind();
- gl.drawArrays(gl.POINTS, 0, 1);
+ if (playbook) {
+ gl.drawArrays(gl.POINTS, 0, 1);
+ } else {
+ gl.drawArrays(gl.TRIANGLE_STRIP, 0, 4);
+ gl.enable(gl.DEPTH_TEST);
+ }
// Disable blending again - it's expensive.
gl.disable(gl.BLEND);
View
70 tunneltilt/shaders.html
@@ -49,6 +49,39 @@
}
</script>
+<script id="ball-quad-vs" type="x-shader/x-vertex">
+attribute vec3 aPosition;
+attribute vec2 aTextureCoord;
+
+uniform mat4 uPMatrix;
+uniform mat4 uMVMatrix;
+
+varying vec2 vTextureCoord;
+
+void main() {
+ vec4 position = uMVMatrix * vec4(aPosition, 1.0);
+ gl_Position = uPMatrix * position;
+ vTextureCoord = aTextureCoord;
+}
+</script>
+
+<script id="ball-quad-fs" type="x-shader/x-fragment">
+#ifdef GL_ES
+precision highp float;
+precision highp sampler2D;
+#endif
+
+varying vec2 vTextureCoord;
+uniform sampler2D uSampler;
+uniform float uAmbient;
+uniform float uTransparency;
+
+void main() {
+ vec4 tex = texture2D(uSampler, vTextureCoord);
+ gl_FragColor = vec4(uAmbient * (vec3(0.01, 0.01, 0.01) + tex.rgb), tex.a * uTransparency);
+}
+</script>
+
<script id="tunnel-vs" type="x-shader/x-vertex">
attribute vec3 aVertexPosition;
attribute vec2 aTextureCoord;
@@ -156,6 +189,43 @@
}
</script>
+<script id="particle-quad-vs" type="x-shader/x-vertex">
+attribute vec3 aPosition;
+attribute vec2 aTextureCoord;
+attribute vec3 aVelocity;
+attribute float aSize;
+
+varying vec2 vTextureCoord;
+uniform mat4 uPMatrix;
+uniform float uTime;
+
+void main() {
+ float rSize = max(0.0, 1.0 - uTime);
+ float size = (aSize / 23.0 * rSize);
+ if (size < 1.1)
+ size = 0.0;
+ vec4 offset = vec4(aVelocity * uTime, 0.0);
+ vec4 position = vec4(aPosition, 0.0) * size;
+ position = vec4(0.0, -15.0, -40.0, 1.0) + position + offset;
+ vTextureCoord = aTextureCoord;
+ gl_Position = uPMatrix * position;
+}
+</script>
+
+<script id="particle-quad-fs" type="x-shader/x-fragment">
+#ifdef GL_ES
+precision highp float;
+precision highp sampler2D;
+#endif
+
+varying vec2 vTextureCoord;
+uniform sampler2D uSampler;
+
+void main() {
+ gl_FragColor = texture2D(uSampler, vTextureCoord);
+}
+</script>
+
<body></body>
</html>
Please sign in to comment.
Something went wrong with that request. Please try again.