mirror of
https://github.com/QuiteAFancyEmerald/Holy-Unblocker.git
synced 2025-05-15 04:40:01 -04:00
293 lines
6.7 KiB
Text
293 lines
6.7 KiB
Text
/*
|
|
* Javascript/Canvas Textured 3D Renderer v0.3.1
|
|
* Copyright (c) 2008 Jacob Seidelin, cupboy@gmail.com
|
|
* This software is free to use for non-commercial purposes. For anything else, please contact the author.
|
|
* This is a version modified by Stefano Gioffre'.
|
|
*/
|
|
|
|
Canvas3D.Camera = function() {
|
|
|
|
this._oPosition = new Canvas3D.Vec3(0,0,0);
|
|
|
|
this._oSideVec = new Canvas3D.Vec3(1,0,0);
|
|
this._oUpVec = new Canvas3D.Vec3(0,1,0);
|
|
this._oOutVec = new Canvas3D.Vec3(0,0,1);
|
|
|
|
this._oRotMat = new Canvas3D.Matrix3();
|
|
|
|
this._bDirty = false;
|
|
this._fFocal = 500;
|
|
this._fFocalDistance = this._fFocal;
|
|
|
|
this._bReverseX = false;
|
|
this._bReverseY = false;
|
|
|
|
this._bTarget = true;
|
|
|
|
this._iClipNear = 1;
|
|
this._iClipFar = 10000000;
|
|
|
|
this._fScale = 1;
|
|
|
|
this._oLookAt = new Canvas3D.Vec3(0,0,0);
|
|
|
|
};
|
|
|
|
var proto = Canvas3D.Camera.prototype;
|
|
|
|
proto.getDirty = function() {
|
|
return this._bDirty;
|
|
}
|
|
|
|
proto.setDirty = function(bDirty) {
|
|
this._bDirty = bDirty;
|
|
}
|
|
|
|
proto.setPosition = function(oPos) {
|
|
this._oPosition.set(oPos.x, oPos.y, oPos.z);
|
|
this._bDirty = true;
|
|
}
|
|
|
|
proto.getPosition = function() {
|
|
return this._oPosition;
|
|
}
|
|
|
|
proto.setScale = function(fScale) {
|
|
this._fScale = fScale;
|
|
this._bDirty = true;
|
|
}
|
|
|
|
proto.getScale = function() {
|
|
return this._fScale;
|
|
}
|
|
|
|
proto.getSide = function() {
|
|
return this._oSideVec;
|
|
}
|
|
|
|
proto.getUp = function() {
|
|
return this._oUpVec;
|
|
}
|
|
|
|
proto.setUp = function(oVec) {
|
|
this._oUpVec = oVec;
|
|
}
|
|
|
|
proto.getOut = function() {
|
|
return this._oOutVec;
|
|
}
|
|
|
|
proto.moveSideways = function(d) {
|
|
this._oPosition.x += this._oSideVec.x * d;
|
|
this._oPosition.y += this._oSideVec.y * d;
|
|
this._oPosition.z += this._oSideVec.z * d;
|
|
this.setDirty(true);
|
|
}
|
|
|
|
proto.moveUpwards = function(d) {
|
|
this._oPosition.x += this._oUpVec.x * d;
|
|
this._oPosition.y += this._oUpVec.y * d;
|
|
this._oPosition.z += this._oUpVec.z * d;
|
|
this.setDirty(true);
|
|
}
|
|
|
|
proto.moveForward = function(d) {
|
|
this._oPosition.x += this._oOutVec.x * d;
|
|
this._oPosition.y += this._oOutVec.y * d;
|
|
this._oPosition.z += this._oOutVec.z * d;
|
|
this.setDirty(true);
|
|
}
|
|
|
|
// rotate around the camera's side axis with a target center point (uses camera target if oTarget is null)
|
|
proto.pitchAroundTarget = function(fTheta, oTarget) {
|
|
var M = new Canvas3D.Matrix3();
|
|
var oPos = this.getPosition();
|
|
oTarget = oTarget || this.getLookAt();
|
|
|
|
// translate position to target space
|
|
oPos.subVector(oTarget);
|
|
|
|
// rotate around side axis
|
|
M.loadRotationAxis(this._oSideVec, Math.sin(fTheta * Math.PI / 180.0), Math.cos(fTheta * Math.PI / 180.0));
|
|
oPos = M.multiplyVector(oPos);
|
|
|
|
// translate position out of target space
|
|
oPos.addVector(oTarget);
|
|
|
|
this.setPosition(oPos);
|
|
this.setDirty(true);
|
|
}
|
|
|
|
proto.yaw = function(fTheta) {
|
|
var M = new Canvas3D.Matrix3();
|
|
M.loadRotationAxis(this._oUpVec, Math.sin(fTheta), Math.cos(fTheta));
|
|
this._oSideVec = M.multiplyVector(this._oSideVec);
|
|
this._oOutVec = M.multiplyVector(this._oOutVec);
|
|
this.setDirty(true);
|
|
}
|
|
|
|
// rotate around the camera's up axis with a target center point (uses camera target if oTarget is null)
|
|
proto.yawAroundTarget = function(fTheta, oTarget) {
|
|
var M = new Canvas3D.Matrix3();
|
|
var oPos = this.getPosition();
|
|
oTarget = oTarget || this.getLookAt();
|
|
|
|
// translate position to target space
|
|
oPos.subVector(oTarget);
|
|
|
|
// rotate around up axis
|
|
M.loadRotationAxis(this._oUpVec, Math.sin(fTheta * Math.PI / 180.0), Math.cos(fTheta * Math.PI / 180.0));
|
|
oPos = M.multiplyVector(oPos);
|
|
|
|
// translate position out of target space
|
|
oPos.addVector(oTarget);
|
|
|
|
this.setPosition(oPos);
|
|
this.setDirty(true);
|
|
}
|
|
|
|
// rotate around the camera's out axis with a target center point (uses camera target if oTarget is null)
|
|
proto.rollAroundTarget = function(fTheta, oTarget) {
|
|
var M = new Canvas3D.Matrix3();
|
|
var oPos = this.getPosition();
|
|
oTarget = oTarget || this.getLookAt();
|
|
|
|
// translate position to target space
|
|
oPos.subVector(oTarget);
|
|
|
|
// rotate around out axis
|
|
M.loadRotationAxis(this._oOutVec, Math.sin(fTheta * Math.PI / 180.0), Math.cos(fTheta * Math.PI / 180.0));
|
|
oPos = M.multiplyVector(oPos);
|
|
|
|
// translate position out of target space
|
|
oPos.addVector(oTarget);
|
|
|
|
this.setPosition(oPos);
|
|
this.setDirty(true);
|
|
}
|
|
|
|
proto.rotateY = function(sine, cosine) {
|
|
var M = new Canvas3D.Matrix3();
|
|
M.loadRotationY(sine, cosine);
|
|
this._oSideVec = M.multiplyVector(this._oSideVec);
|
|
this._oUpVec = M.multiplyVector(this._oUpVec);
|
|
this._oOutVec = M.multiplyVector(this._oOutVec);
|
|
this.setDirty(true);
|
|
}
|
|
|
|
|
|
proto.lookAt = function(P, Up) {
|
|
Up = Up || this._oUpVec;
|
|
this._oOutVec = P.returnSub(this._oPosition).unit();
|
|
|
|
//this._oSideVec = this._oOutVec.cross(new Canvas3D.Vec3 (0.0, 1.0, 0.0)).unit();
|
|
//this._oSideVec = this._oOutVec.cross(this._oUpVec).unit();
|
|
this._oSideVec = this._oOutVec.cross(Up).unit();
|
|
this._oUpVec = this._oSideVec.cross(this._oOutVec).unit();
|
|
this._vecLookAt = P.clone();
|
|
this.setDirty(true);
|
|
}
|
|
|
|
proto.getLookAt = function() {
|
|
return this._vecLookAt;
|
|
}
|
|
|
|
proto.updateRotationMatrix = function() {
|
|
var e0 = this._oRotMat.e[0];
|
|
var e1 = this._oRotMat.e[1];
|
|
var e2 = this._oRotMat.e[2];
|
|
|
|
e0[0] = this._oSideVec.x;
|
|
e0[1] = this._oSideVec.y;
|
|
e0[2] = this._oSideVec.z;
|
|
|
|
e1[0] = this._oUpVec.x;
|
|
e1[1] = this._oUpVec.y;
|
|
e1[2] = this._oUpVec.z;
|
|
|
|
e2[0] = this._oOutVec.x;
|
|
e2[1] = this._oOutVec.y;
|
|
e2[2] = this._oOutVec.z;
|
|
}
|
|
|
|
proto.transformPoint = function(P) {
|
|
var e = this._oRotMat.e;
|
|
var oPos = this._oPosition;
|
|
|
|
var e0 = e[0];
|
|
var e1 = e[1];
|
|
var e2 = e[2];
|
|
|
|
var vx = P.x - oPos.x;
|
|
var vy = P.y - oPos.y;
|
|
var vz = P.z - oPos.z;
|
|
|
|
return new Canvas3D.Vec3(
|
|
(vx * e0[0] + vy * e0[1] + vz * e0[2]),
|
|
(vx * e1[0] + vy * e1[1] + vz * e1[2]),
|
|
(vx * e2[0] + vy * e2[1] + vz * e2[2])
|
|
);
|
|
}
|
|
|
|
proto.project = function(P) {
|
|
var fFocal = this._fFocal;
|
|
return {
|
|
x: P.x * fFocal / (P.z + this._fFocalDistance) * this._fScale * (this._bReverseX?-1:1),
|
|
y: -P.y * fFocal / (P.z + this._fFocalDistance) * this._fScale * (this._bReverseY?-1:1)
|
|
};
|
|
}
|
|
|
|
proto.clip = function(P) {
|
|
if (P.z < 0) {
|
|
return true;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
proto.isBehind = function(P) {
|
|
if (P.z > 0) return false;
|
|
return false;
|
|
}
|
|
|
|
proto.getClipNear = function() {
|
|
return this._iClipNear;
|
|
}
|
|
|
|
proto.getClipFar = function() {
|
|
return this._iClipFar;
|
|
}
|
|
|
|
proto.clip = function(P) {
|
|
if (P.z > this._iClipNear && P.z < this._iClipFar) {
|
|
return false;
|
|
} else {
|
|
return true;
|
|
}
|
|
}
|
|
|
|
proto.setFOV = function(fFOV) {
|
|
this._fFOV = fFOV;
|
|
var fFocal = 1 / Math.tan(105 * Math.PI*Math.PI / (180*180 * 2));
|
|
this._fFocal = fFocal;
|
|
this._fFocalDistance = fFocal;
|
|
}
|
|
|
|
proto.getFOV = function() {
|
|
return this._fFOV;
|
|
}
|
|
|
|
proto.getFocal = function() {
|
|
return this._fFocal;
|
|
}
|
|
|
|
proto.setFocalDistance = function(fValue) {
|
|
this._fFocalDistance = fValue;
|
|
}
|
|
|
|
proto.setReverseX = function(bEnable) {
|
|
this._bReverseX = bEnable;
|
|
}
|
|
|
|
proto.setReverseY = function(bEnable) {
|
|
this._bReverseY = bEnable;
|
|
}
|