Skip to content
Snippets Groups Projects
Commit 6744dec9 authored by SOYKIM's avatar SOYKIM
Browse files

Update webgl_tutorial

parent 94e2006d
No related branches found
No related tags found
No related merge requests found
This diff is collapsed.
<html>
<head>
<title>WebGL Tutorial - TransLate & Rotate </title>
<h1>Translation & Rotation</h1>
<meta http-equiv="content-type" content="text/html; charset=ISO-8859-1">
<script type="text/javascript" src="gl-matrix.js"> </script>
<script type="text/javascript" src="script.js"> </script>
</head>
<body onload="main()">
<canvas id="canvas1" style="border: none;" width="600" height="500"></canvas>
<canvas id="canvas2" style="border: none;" width="600" height="500"></canvas>
<br/> <br/>
<p>[Both Cube] <button onclick="toggleAnimation(0)">Toggle Animation</button> </p>
<p>
Speed:
<button onclick="speed_plus()"> + </button>
<button onclick="speed_minus()"> - </button>
| Draw Mode:
<button onclick="fn_draw_mode(2)"> Lines </button>
<button onclick="fn_draw_mode(4)"> Triangles </button>
<button onclick="fn_draw_mode(0)"> Points </button>
</p>
<br/><hr>
<p>[Left Cube] <button onclick="toggleAnimation(1)">Toggle Animation</button> </p>
<p>
FOV :
<input style="width:200px" id="fov_range1" type="range" min="30" max="170" value="90" oninput="fn_update_fov(this.value, 1);">
<input style="width:100px" type="text" id="textFOV1" value="90">
</p>
<label>Translate(x,y,z) :</label>
<lable> X <label><input id="translatex1" type="text" size="4" value="0">
<label> Y <label><input id="translatey1" type="text" size="4" value="0">
<label> Z <label><input id="translatez1" type="text" size="4" value="0">
<button onclick="fn_translate(1, 0)">Translate -> Rotate</button>
<button onclick="fn_translate(1, 1)">Rotate -> Translate</button>
<br/><hr>
<p>[Right Cube] <button onclick="toggleAnimation(2)">Toggle Animation</button> </p>
<p>
FOV :
<input style="width:200px" id="fov_range2" type="range" min="30" max="170" value="90" oninput="fn_update_fov(this.value, 2);">
<input style="width:100px" type="text" id="textFOV2" value="90">
</p>
<label>Translate(x,y,z)</label>
<lable> X <label><input id="translatex2" type="text" size="4" value="0">
<label> Y <label><input id="translatey2" type="text" size="4" value="0">
<label> Z <label><input id="translatez2" type="text" size="4" value="0">
<button onclick="fn_translate(2, 0)">Translate -> Rotate</button>
<button onclick="fn_translate(2, 1)">Rotate -> Translate</button>
</p>
<p>
Distance between center cube with side cubes :
<input style="width:200px" id="d" type="range" min="0" max="10" value="0" oninput="fn_update_dist(this.value);">
</p>
</body>
</html>
\ No newline at end of file
script.js 0 → 100644
var gl;
var gl1;
var gl2;
const {mat2, mat3, mat4, vec2, vec3, vec4} = glMatrix;
function testGLError(functionLastCalled) {
var lastError = gl.getError();
if (lastError != gl.NO_ERROR) {
alert(functionLastCalled + " failed (" + lastError + ")");
return false;
}
return true;
}
function initialiseGL(canvas1, canvas2) {
try {
gl1 = canvas1.getContext('webgl',
{stencil:true, alpha:true, depth:true, antialias:true, preserveDrawingBuffer:false});
gl1.viewport(0, 0, canvas1.width, canvas1.height);
gl2 = canvas2.getContext('webgl',
{stencil:true, alpha:true, depth:true, antialias: true, preserveDrawingBuffer:false});
gl2.viewport(0, 0, canvas2.width, canvas2.height);
}
catch (e) {
}
if (!gl1 || !gl2) {
alert("Unable to initialise WebGL. Your browser may not support it");
return false;
}
return true;
}
var shaderProgram;
var vertexData = [
// Backface (RED) -> z = 0.5
-0.5, -0.5, -0.5, 1.0, 0.0, 0.0, 1.0,
0.5, 0.5, -0.5, 1.0, 0.0, 0.0, 1.0,
0.5, -0.5, -0.5, 1.0, 0.0, 0.0, 1.0,
-0.5, -0.5, -0.5, 1.0, 0.0, 0.0, 1.0,
-0.5, 0.5, -0.5, 1.0, 0.0, 0.0, 1.0,
0.5, 0.5, -0.5, 1.0, 0.0, 1.0, 1.0,
// Front (BLUE) -> z = 0.5
-0.5, -0.5, 0.5, 0.0, 0.0, 1.0, 1.0,
0.5, -0.5, 0.5, 0.0, 0.0, 1.0, 1.0,
0.5, 0.5, 0.5, 0.0, 0.0, 1.0, 1.0,
-0.5, -0.5, 0.5, 0.0, 0.0, 1.0, 1.0,
0.5, 0.5, 0.5, 0.0, 0.0, 1.0, 1.0,
-0.5, 0.5, 0.5, 0.0, 0.0, 1.0, 1.0,
// LEFT (GREEN) -> z = 0.5
-0.5, -0.5, -0.5, 0.0, 1.0, 0.0, 1.0,
-0.5, 0.5, 0.5, 0.0, 1.0, 0.0, 1.0,
-0.5, 0.5, -0.5, 0.0, 1.0, 0.0, 1.0,
-0.5, -0.5, -0.5, 0.0, 1.0, 0.0, 1.0,
-0.5, -0.5, 0.5, 0.0, 1.0, 0.0, 1.0,
-0.5, 0.5, 0.5, 0.0, 1.0, 0.0, 1.0,
// RIGHT (YELLOW) -> z = 0.5
0.5, -0.5, -0.5, 1.0, 1.0, 0.0, 1.0,
0.5, 0.5, -0.5, 1.0, 1.0, 0.0, 1.0,
0.5, 0.5, 0.5, 1.0, 1.0, 0.0, 1.0,
0.5, -0.5, -0.5, 1.0, 1.0, 0.0, 1.0,
0.5, 0.5, 0.5, 1.0, 1.0, 0.0, 1.0,
0.5, -0.5, 0.5, 1.0, 1.0, 0.0, 1.0,
// BOTTON (MAGENTA) -> z = 0.5
-0.5, -0.5, -0.5, 1.0, 0.0, 1.0, 1.0,
0.5, -0.5, -0.5, 1.0, 0.0, 1.0, 1.0,
0.5, -0.5, 0.5, 1.0, 0.0, 1.0, 1.0,
-0.5, -0.5, -0.5, 1.0, 0.0, 1.0, 1.0,
0.5, -0.5, 0.5, 1.0, 0.0, 1.0, 1.0,
-0.5, -0.5, 0.5, 1.0, 0.0, 1.0, 1.0,
// TOP (CYAN) -> z = 0.5
-0.5, 0.5, -0.5, 0.0, 1.0, 1.0, 1.0,
0.5, 0.5, 0.5, 0.0, 1.0, 1.0, 1.0,
0.5, 0.5, -0.5, 0.0, 1.0, 1.0, 1.0,
-0.5, 0.5, -0.5, 0.0, 1.0, 1.0, 1.0,
-0.5, 0.5, 0.5, 0.0, 1.0, 1.0, 1.0,
0.5, 0.5, 0.5, 0.0, 1.0, 1.0, 1.0
];
function initialiseBuffer() {
gl.vertexBuffer = gl.createBuffer();
gl.bindBuffer(gl.ARRAY_BUFFER, gl.vertexBuffer);
gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(vertexData), gl.STATIC_DRAW);
return testGLError("initialiseBuffers");
}
function initialiseShaders() {
var fragmentShaderSource = '\
varying highp vec4 color; \
void main(void) \
{ \
gl_FragColor = color;\
}';
gl.fragShader = gl.createShader(gl.FRAGMENT_SHADER);
gl.shaderSource(gl.fragShader, fragmentShaderSource);
gl.compileShader(gl.fragShader);
if (!gl.getShaderParameter(gl.fragShader, gl.COMPILE_STATUS)) {
alert("Failed to compile the fragment shader.\n" + gl.getShaderInfoLog(gl.fragShader));
return false;
}
var vertexShaderSource = '\
attribute highp vec4 myVertex; \
attribute highp vec4 myColor; \
uniform mediump mat4 mMat; \
uniform mediump mat4 vMat; \
uniform mediump mat4 pMat; \
varying highp vec4 color;\
void main(void) \
{ \
gl_Position = pMat * vMat * mMat * myVertex; \
gl_PointSize = 8.0; \
color = myColor; \
}';
gl.vertexShader = gl.createShader(gl.VERTEX_SHADER);
gl.shaderSource(gl.vertexShader, vertexShaderSource);
gl.compileShader(gl.vertexShader);
if (!gl.getShaderParameter(gl.vertexShader, gl.COMPILE_STATUS)) {
alert("Failed to compile the vertex shader.\n" + gl.getShaderInfoLog(gl.vertexShader));
return false;
}
gl.programObject = gl.createProgram();
gl.attachShader(gl.programObject, gl.fragShader);
gl.attachShader(gl.programObject, gl.vertexShader);
gl.bindAttribLocation(gl.programObject, 0, "myVertex");
gl.bindAttribLocation(gl.programObject, 1, "myColor");
gl.linkProgram(gl.programObject);
if (!gl.getProgramParameter(gl.programObject, gl.LINK_STATUS)) {
alert("Failed to link the program.\n" + gl.getProgramInfoLog(gl.programObject));
return false;
}
gl.useProgram(gl.programObject);
return testGLError("initialiseShaders");
}
var xRot = 0.0;
var yRot = 0.0;
var zRot = 0.0;
var xRot2 = 0.0;
var yRot2 = 0.0;
var zRot2 = 0.0;
var speedRot = 0.01;
var left_flag = 0;
var right_flag = 0;
function toggleAnimation(a)
{
if(a == 1) {
left_flag ^= 1;
console.log("Left flag_animation=", a);
} else if(a == 2) {
right_flag ^= 1;
console.log("Right flag_animation=", a);
} else if(a == 0) {
right_flag ^= 1;
left_flag ^= 1;
console.log("Flag_animation=", a);
}
}
function speed_plus()
{
speedRot = speedRot * 1.1;
}
function speed_minus()
{
speedRot = speedRot / 1.1;
}
var draw_mode = 4; // 4 Triangles, 3 line_strip 0-Points
function fn_draw_mode(a)
{
draw_mode = a;
}
var fov_degree1 = 90.0;
var fov_degree2 = 90.0;
var translatex1 = 0.0;
var translatey1 = 0.0;
var translatez1 = 0.0;
var translatex2 = 0.0;
var translatey2 = 0.0;
var translatez2 = 0.0;
function fn_update_fov(val, a)
{
if(a == 1) {
document.getElementById('textFOV1').value = val;
fov_degree1 = val;
} else if(a == 2) {
document.getElementById('textFOV2').value = val;
fov_degree2 = val;
}
}
var order1 = 0;
var order2 = 0;
function fn_translate(a, order) {
if(a == 1) {
translatex1 = document.getElementById('translatex1').value / 2.0;
translatey1 = document.getElementById('translatey1').value / 2.0;
translatez1 = document.getElementById('translatez1').value / 2.0;
order1 = order;
} else if(a == 2) {
translatex2 = document.getElementById('translatex2').value / 2.0;
translatey2 = document.getElementById('translatey2').value / 2.0;
translatez2 = document.getElementById('translatez2').value / 2.0;
order2 = order;
}
}
var dist = 0;
function fn_update_dist(d) {
dist = document.getElementById('d').value / 2.0;
}
function renderScene() {
/***************** Left Cube *****************/
gl = gl1;
gl.clearColor(0.0, 0.0, 0.0, 1.0);
gl.clearDepth(1.0); // Added for depth Test
gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT); // Added for depth Test
gl.enable(gl.DEPTH_TEST); // Added for depth Test
var pMatLocation = gl.getUniformLocation(gl.programObject, "pMat");
var vMatLocation = gl.getUniformLocation(gl.programObject, "vMat");
var mMatLocation = gl.getUniformLocation(gl.programObject, "mMat");
pMat = mat4.create();
vMat = mat4.create();
mMat = mat4.create();
mat4.perspective(pMat, glMatrix.glMatrix.toRadian(fov_degree1), 6.0/5.0 , 0.5, 8);
mat4.lookAt(vMat, [0.0, 0.0, 2.0], [0.0,0.0,0.0], [0.0, 1.0, 0.0]);
mat4.scale(mMat, mMat, [0.5, 0.5, 0.5]);
if(order1 == 0) {
mat4.translate(mMat, mMat, [translatex1, translatey1, translatez1]);
mat4.rotateX(mMat, mMat, xRot);
mat4.rotateY(mMat, mMat, yRot);
mat4.rotateZ(mMat, mMat, zRot);
} else if(order1 == 1) {
mat4.rotateX(mMat, mMat, xRot);
mat4.rotateY(mMat, mMat, yRot);
mat4.rotateZ(mMat, mMat, zRot);
mat4.translate(mMat, mMat, [translatex1, translatey1, translatez1]);
} else {
mat4.rotateX(mMat, mMat, xRot);
mat4.rotateY(mMat, mMat, yRot);
mat4.rotateZ(mMat, mMat, zRot);
}
if (left_flag == 0)
{
xRot = xRot + speedRot;
yRot = yRot + speedRot;
zRot = zRot + speedRot;
}
gl.uniformMatrix4fv(mMatLocation, gl.FALSE, mMat);
gl.uniformMatrix4fv(vMatLocation, gl.FALSE, vMat);
gl.uniformMatrix4fv(pMatLocation, gl.FALSE, pMat);
if (!testGLError("gl.uniformMatrix4fv")) {
return false;
}
gl.bindBuffer(gl.ARRAY_BUFFER, gl.vertexBuffer);
gl.enableVertexAttribArray(0);
gl.vertexAttribPointer(0, 3, gl.FLOAT, gl.FALSE, 28, 0);
gl.enableVertexAttribArray(1);
gl.vertexAttribPointer(1, 4, gl.FLOAT, gl.FALSE, 28, 12);
if (!testGLError("gl.vertexAttribPointer")) {
return false;
}
//Left Cube
gl.drawArrays(draw_mode, 0, 36);
if (!testGLError("gl.drawArrays")) {
return false;
}
/***************** Right Cube *****************/
gl = gl2;
gl.clearColor(0.0, 0.0, 0.0, 1.0);
gl.clearDepth(1.0); // Added for depth Test
gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT); // Added for depth Test
gl.enable(gl.DEPTH_TEST); // Added for depth Test
var pMatLocation2 = gl.getUniformLocation(gl.programObject, "pMat");
var vMatLocation2 = gl.getUniformLocation(gl.programObject, "vMat");
var mMatLocation2 = gl.getUniformLocation(gl.programObject, "mMat");
pMat = mat4.create();
vMat = mat4.create();
mMat = mat4.create();
mat4.perspective(pMat, glMatrix.glMatrix.toRadian(fov_degree2), 6.0/5.0 , 0.5, 8);
mat4.lookAt(vMat, [0.0, 0.0, 2.0], [0.0,0.0,0.0], [0.0, 1.0, 0.0]);
mat4.scale(mMat, mMat, [0.5, 0.5, 0.5]);
if(order2 == 0) {
mat4.translate(mMat, mMat, [translatex2, translatey2, translatez2]);
mat4.rotateX(mMat, mMat, xRot2);
mat4.rotateY(mMat, mMat, yRot2);
mat4.rotateZ(mMat, mMat, zRot2);
} else if(order2 == 1) {
mat4.rotateX(mMat, mMat, xRot2);
mat4.rotateY(mMat, mMat, yRot2);
mat4.rotateZ(mMat, mMat, zRot2);
mat4.translate(mMat, mMat, [translatex2, translatey2, translatez2]);
}
else {
mat4.rotateX(mMat, mMat, xRot2);
mat4.rotateY(mMat, mMat, yRot2);
mat4.rotateZ(mMat, mMat, zRot2);
}
if (right_flag == 0)
{
xRot2 = xRot2 + speedRot;
yRot2 = yRot2 + speedRot;
zRot2 = zRot2 + speedRot;
}
gl.uniformMatrix4fv(mMatLocation2, gl.FALSE, mMat);
gl.uniformMatrix4fv(vMatLocation2, gl.FALSE, vMat);
gl.uniformMatrix4fv(pMatLocation2, gl.FALSE, pMat);
if (!testGLError("gl.uniformMatrix4fv")) {
return false;
}
gl.bindBuffer(gl.ARRAY_BUFFER, gl.vertexBuffer);
gl.enableVertexAttribArray(0);
gl.vertexAttribPointer(0, 3, gl.FLOAT, gl.FALSE, 28, 0);
gl.enableVertexAttribArray(1);
gl.vertexAttribPointer(1, 4, gl.FLOAT, gl.FALSE, 28, 12);
if (!testGLError("gl.vertexAttribPointer")) {
return false;
}
//Right Cube
gl.drawArrays(draw_mode, 0, 36);
var saveMat = mat4.create();
mat4.copy(saveMat,mMat);
for (var i = 0 ; i < 4 ; i++)
{
mat4.scale(mMat, mMat, [0.2, 0.2, 0.2]);
mat4.rotateY (mMat, mMat, glMatrix.glMatrix.toRadian(90*(i+1)));
mat4.translate(mMat, mMat, [3.0 + dist, 3.0 + dist, 3.0 + dist]);
mat4.rotateY (mMat, mMat, yRot2 * 5.0);
gl.uniformMatrix4fv(mMatLocation2, gl.FALSE, mMat);
gl.drawArrays(draw_mode, 0, 36);
mat4.copy(mMat, saveMat);
}
for (var i = 0 ; i < 4 ; i++)
{
mat4.scale(mMat, mMat, [0.2, 0.2, 0.2]);
mat4.rotateY (mMat, mMat, glMatrix.glMatrix.toRadian(90*(i+1)));
mat4.translate(mMat, mMat, [3.0 + dist, -3.0 - dist, 3.0 + dist]);
mat4.rotateY (mMat, mMat, yRot2 * 5.0);
gl.uniformMatrix4fv(mMatLocation2, gl.FALSE, mMat);
gl.drawArrays(draw_mode, 0, 36);
mat4.copy(mMat, saveMat);
}
if (!testGLError("gl.drawArrays")) {
return false;
}
return true;
}
function main() {
var canvas1 = document.getElementById("canvas1");
var canvas2 = document.getElementById("canvas2");
if (!initialiseGL(canvas1, canvas2)) {
return;
}
gl = gl1;
if (!initialiseBuffer()) {
return;
}
gl = gl2;
if (!initialiseBuffer()) {
return;
}
gl = gl1;
if (!initialiseShaders()) {
return;
}
gl = gl2;
if (!initialiseShaders()) {
return;
}
// Render loop
requestAnimFrame = (function () {
return window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame ||
function (callback) {
window.setTimeout(callback, 1000, 60);
};
})();
(function renderLoop() {
if (renderScene()) {
// Everything was successful, request that we redraw our scene again in the future
requestAnimFrame(renderLoop);
}
})();
}
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment