﻿/* 
 * Copyright (c) 2011 Chen Zhuhui
 * 
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 * 
 *     http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

"use strict";

var listener = {
    vshaderText : "" + 
	"uniform mat4 mv;\n" +
	"uniform mat4 proj;\n" +
	"\n" +
	"attribute vec3 location;\n" +
	"attribute vec3 normal;\n" +
	"\n" +
	"uniform vec3 pv;\n" +
	"\n" +
	"uniform vec3 kd;\n" +
	"uniform vec3 ks;\n" +
	"\n" +
	"uniform float m;\n" +
	"\n" +
	"uniform vec3 l;\n" +
	"uniform vec3 e;\n" +
	"\n" +
	"varying vec3 Lo;\n" +
	"void main(void) {\n" +
	"  vec4 p = mv * vec4(location, 1.0);\n" +
	"  vec4 n = normalize(mv * vec4(normal, 1.0));\n" +
	"\n" +
	"  vec4 v = normalize(p - vec4(pv, 1.0));\n" +
	"  Lo = vec3(0.0, 0.0, 0.0);\n" +
	"\n" +
	"  vec4 light = vec4(l, 1.0);\n" +
	"  vec4 h = normalize(v + light);\n" +
	"  float cosTi = clamp(dot(n, light), 0.0, 1.0);\n" +
	"  float cosTh = clamp(dot(n, h), 0.0, 1.0);\n" +
	"\n" +
	"  Lo = (kd + ks * pow(cosTh, m)) * e * cosTi;\n" +
	"  gl_Position = proj * p;\n" +
	"}\n",

    fshaderText : "" +
	"#ifdef GL_ES\n" + 
	"precision highp float;\n" +
	"#endif\n" +
	"varying vec3 Lo;" +
	"void main(void) {\n" +
	"    gl_FragColor = vec4(Lo, 1.0);\n" +
	"}\n",

    onInitialize : function() {
	this.$.glc("clearColor", 1, 1, 1, 1);
	this.$.glc("enable", WebGLRenderingContext.DEPTH_TEST);
	this.mvMat = mat4.create();
	mat4.identity(this.mvMat);
	this.projMat = mat4.ortho(-this.$.canvas.width / 2,
				  this.$.canvas.width / 2,
				  -this.$.canvas.height / 2,
				  this.$.canvas.height / 2,
				  -150,
				  150);
	
	var vshader = this.$.create(galgames.ShaderModule);
	vshader.define(this.vshaderText, galgames.VertexShader);
	var fshader = this.$.create(galgames.ShaderModule);
	fshader.define(this.fshaderText, galgames.FragmentShader);
	
	this.$.shader = this.$.create(galgames.Shader);
	this.$.shader.define(vshader, fshader);
	this.$.shader.setAttribute("location", galgames.VFUsagePosition);
	this.$.shader.setAttribute("normal", galgames.VFUsageNormal);
	this.$.shader.use();
	this.$.shader.setUniform("m", 0.5);	
	this.$.shader.setUniform("pv", [0, 0, 100]);
	this.$.shader.setUniform("kd", [0.5, 0.5, 0.5]);
	this.$.shader.setUniform("ks", [0.5, 0.5, 0.5]);
	var light = [1.0, 1.0, 1.0];
	vec3.normalize(light);
	this.$.shader.setUniform("l",  light);
	this.$.shader.setUniform("e",  [1.0, 1.0, 1.0]);

	this.$.shader.setUniform("proj", this.projMat);
	
	var vf = this.$.create(galgames.VertexFormat);
	vf.declare(galgames.VFUsagePosition,
		   galgames.VFTypeFloat,
		   3,
		   galgames.VFUsageNormal,
		   galgames.VFTypeFloat,
		   3);

	this.mesh = this.$.create(galgames.Mesh);
	this.mesh.define(vf,
			 monkey.vertices.length, galgames.BufUsageStatic,
			 monkey.vertices.length, galgames.BufUsageStatic);
	this.mesh.primitiveType = galgames.Mesh.Triangles;
	this.mesh.setVertices(0, monkey.vertices);
	this.mesh.setIndices(0, monkey.faces);

	this.r = 0;
    },

    onDraw : function() {
	this.$.glc("clear", 
		   WebGLRenderingContext.COLOR_BUFFER_BIT |
		   WebGLRenderingContext.DEPTH_BUFFER_BIT);
	mat4.identity(this.mvMat);
	mat4.rotate(this.mvMat, this.r, [1, 0, 0]);
	mat4.rotate(this.mvMat, this.r, [0, 1, 0]);
	mat4.rotate(this.mvMat, this.r, [0, 0, 1]);
	mat4.scale(this.mvMat, [ 100, 100, 100 ]);

	this.$.shader.setUniform("mv", this.mvMat);
	this.mesh.draw();

	this.r = this.r + 0.01;
    }

};

var context = galgames.initialize({
    container : "lighting",
    debug : true,
    width : 360,
    height: 360,
    listener : listener
});

