diff --git a/TODO.md b/TODO.md new file mode 100644 index 0000000..642bc03 --- /dev/null +++ b/TODO.md @@ -0,0 +1,7 @@ +## Plan +- [ ] - fog (draw distance) +- [ ] - покачивание камеры +## Complete +- [ ] `...` +## Dropped +- [ ] `...` diff --git a/src/game.js b/src/game.js index 4236e70..a139080 100644 --- a/src/game.js +++ b/src/game.js @@ -1,19 +1,19 @@ var raycast = raycast || {}; window.requestAnimFrame = (function(){ - return window.requestAnimationFrame || - window.webkitRequestAnimationFrame || - window.mozRequestAnimationFrame || - window.oRequestAnimationFrame || - window.msRequestAnimationFrame || - function(callback, element){ + return window.requestAnimationFrame || + window.webkitRequestAnimationFrame || + window.mozRequestAnimationFrame || + window.oRequestAnimationFrame || + window.msRequestAnimationFrame || + function(callback, element) { window.setTimeout(callback, 1000 / 60); }; })(); function start() { - document.onkeyup = raycast.keyhandler.onKeyup; - document.onkeydown = raycast.keyhandler.onKeydown; + document.onkeyup = raycast.keyHandler.onKeyup; + document.onkeydown = raycast.keyHandler.onKeydown; var textureFiles = ["img/brick.png", "img/ground.png", "img/sky.png"]; raycast.texture.initiateLoad(textureFiles, raycast.engine.start); }; diff --git a/src/index.html b/src/index.html index c86f326..bfa02ec 100644 --- a/src/index.html +++ b/src/index.html @@ -4,13 +4,15 @@ JSRay + - -
- + +
+
- + + diff --git a/src/keyhandler.js b/src/keyHandler.js similarity index 86% rename from src/keyhandler.js rename to src/keyHandler.js index cdabd80..ab7f69d 100644 --- a/src/keyhandler.js +++ b/src/keyHandler.js @@ -1,16 +1,22 @@ var raycast = raycast || {}; -raycast.keyhandler = (function () { +raycast.keyHandler = (function() { var codes = { + // forward up: 38, w: 87, + // backward down: 40, + s: 83, + // turn left left: 37, a: 65, + // turn right right: 39, d: 68, + // special space: 32, - ctrl: 17, + ctrl: 17, // change filtering type esc: 27 }; diff --git a/src/raycast.js b/src/raycast.js index a6cb53c..4ab9437 100644 --- a/src/raycast.js +++ b/src/raycast.js @@ -1,13 +1,10 @@ -// http://lodev.org/cgtutor/raycasting.html var raycast = raycast || {}; -raycast.engine = (function () { - var canvas = document.getElementById("viewport"); +raycast.engine = (function() { + var canvas = document.getElementById("canvas"); var g = canvas.getContext("2d"); var filtering = false; - var mapWidth = 24, - mapHeight = 24, - texHeight = 64, + let texHeight = 64, // mapWidth = 24, mapHeight = 24 texWidth = 64; var texture; @@ -24,24 +21,14 @@ raycast.engine = (function () { } } } + /* - texture[0] = raycast.texture.load("ground"); + texture[0] = raycast.texture.load("..."); texture[1] = raycast.texture.load("brick"); - texture[2] = raycast.texture.load("sky"); + texture[2] = raycast.texture.load("ground"); + texture[3] = raycast.texture.load("sky"); */ - var worldMap = [ - [1,1,1,1,1,1,1,1,1,1], - [1,0,0,0,0,0,0,0,0,1], - [1,0,0,0,0,0,0,0,0,1], - [1,0,0,1,0,0,1,0,0,1], - [1,0,0,0,0,0,0,0,0,1], - [1,0,0,0,0,0,0,0,0,1], - [1,0,0,1,0,0,1,0,0,1], - [1,0,0,0,0,0,0,0,0,1], - [1,0,0,0,0,0,0,0,0,1], - [1,1,1,1,1,1,1,1,1,1] - ]; var posX = 2, posY = 2, dirX = -1, dirY = 0, @@ -54,7 +41,6 @@ raycast.engine = (function () { h = canvas.height; function verLine(arr, x, yStart, yEnd, color){ - //console.log(x, yStart, yEnd); for (var y = yStart | 0; y < yEnd | 0; y++) { var i = 4 * (w * y) + 4 * x; arr[i + 0] = color[0]; @@ -67,20 +53,21 @@ raycast.engine = (function () { imagedata = g.getImageData(0,0,w,h); var buffer = imagedata.data; - var keys = raycast.keyhandler; + var keys = raycast.keyHandler; function input() { - if (keys.isKeydown("up")) { + // player move forward + if (keys.isKeydown("up") || keys.isKeydown("w")) { if(worldMap[(posX + dirX * moveSpeed) | 0][posY | 0] == 0) posX += dirX * moveSpeed; if(worldMap[posX | 0][(posY + dirY * moveSpeed) | 0] == 0) posY += dirY * moveSpeed; } - //move backwards if no wall behind you - if (keys.isKeydown("down")) { + // player move backwards if no wall behind you + if (keys.isKeydown("down") || keys.isKeydown("s")) { if(worldMap[(posX - dirX * moveSpeed) | 0][posY | 0] == 0) posX -= dirX * moveSpeed; if(worldMap[posX | 0][(posY - dirY * moveSpeed) | 0] == 0) posY -= dirY * moveSpeed; } - if (keys.isKeydown("right")) { - //both camera direction and camera plane must be rotated + if (keys.isKeydown("right") || keys.isKeydown("d")) { + // both camera direction and camera plane must be rotated var oldDirX = dirX; dirX = dirX * Math.cos(-rotSpeed) - dirY * Math.sin(-rotSpeed); dirY = oldDirX * Math.sin(-rotSpeed) + dirY * Math.cos(-rotSpeed); @@ -88,8 +75,8 @@ raycast.engine = (function () { planeX = planeX * Math.cos(-rotSpeed) - planeY * Math.sin(-rotSpeed); planeY = oldPlaneX * Math.sin(-rotSpeed) + planeY * Math.cos(-rotSpeed); } - if (keys.isKeydown("left")) { - //both camera direction and camera plane must be rotated + if (keys.isKeydown("left") || keys.isKeydown("a")) { + // both camera direction and camera plane must be rotated var oldDirX = dirX; dirX = dirX * Math.cos(rotSpeed) - dirY * Math.sin(rotSpeed); dirY = oldDirX * Math.sin(rotSpeed) + dirY * Math.cos(rotSpeed); @@ -97,7 +84,7 @@ raycast.engine = (function () { planeX = planeX * Math.cos(rotSpeed) - planeY * Math.sin(rotSpeed); planeY = oldPlaneX * Math.sin(rotSpeed) + planeY * Math.cos(rotSpeed); } - if (keys.isKeypress("d")) + if (keys.isKeypress("ctrl")) filtering = !filtering; } @@ -158,10 +145,10 @@ raycast.engine = (function () { else perpWallDist = Math.abs((mapY - rayPosY + (1 - stepY) / 2) / rayDirY); - //Calculate height of line to draw on screen + // calculate height of line to draw on screen var lineHeight = Math.abs((h / perpWallDist) | 0); - //calculate lowest and highest pixel to fill in current stripe + // calculate lowest and highest pixel to fill in current stripe var drawStart = ((h - lineHeight) / 2) | 0; if(drawStart < 0) drawStart = 0; @@ -247,7 +234,7 @@ raycast.engine = (function () { var ceilTex = texture[2]; var floorTex = texture[1]; - //draw the floor from drawEnd to the bottom of the screen + // draw the floor from drawEnd to the bottom of the screen for(var y = drawEnd; y < h; y++) { currentDist = h / (2.0 * y - h); //you could make a small lookup table for this instead @@ -286,7 +273,7 @@ raycast.engine = (function () { color = floorTex[texWidth * (floorTexY|0) + (floorTexX|0)]; } - //floor + // floor i = 4 * (w * y) + 4 * x; buffer[i+0] = (color[0])/2; @@ -308,7 +295,7 @@ raycast.engine = (function () { color = ceilTex[texWidth * (floorTexY|0) + (floorTexX|0)]; } - //ceiling (symmetrical!) + // ceiling (symmetrical!) i = 4 * (w * (h - y - 1)) + 4 * x; buffer[i+0] = color[0]/2; @@ -327,8 +314,8 @@ raycast.engine = (function () { rotSpeed = frameTime * 3.0; //the constant value is in radians/second g.putImageData(imagedata, 0, 0); - g.font = "bold 30pt Monospace"; - g.fillText(""+((1000 / (time - oldTime))|0), 0, 30); + g.font = "14pt Monospace"; + g.fillText("FPS: " + ((1000 / (time - oldTime)) | 0), 5, 20); }; function tick() { @@ -337,7 +324,6 @@ raycast.engine = (function () { keys.tick(); window.requestAnimFrame(tick); - //window.setTimeout(tick, 1); }; function start() { diff --git a/src/styles.css b/src/styles.css new file mode 100644 index 0000000..461e407 --- /dev/null +++ b/src/styles.css @@ -0,0 +1,20 @@ +* { margin: 0; padding: 0; outline: 0; } + +html, body { + height: 100%; +} + +body { + background-color: #444; +} + +.container { + display: flex; + align-items: center; + justify-content: center; + height: 100%; +} + +canvas { + border: 2px solid #000; +} diff --git a/src/worldMap.js b/src/worldMap.js new file mode 100644 index 0000000..2ef262e --- /dev/null +++ b/src/worldMap.js @@ -0,0 +1,31 @@ +/*let worldMap = [ + [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1], + [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1], + [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1], + [1,0,0,1,1,1,0,0,0,0,0,0,0,0,1,0,0,1], + [1,0,0,1,0,0,0,0,0,0,0,0,0,0,1,0,0,1], + [1,0,0,1,0,0,0,0,0,0,0,0,0,0,1,0,0,1], + [1,0,0,1,0,1,0,0,0,0,0,0,0,0,1,0,0,1], + [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1], + [1,1,1,1,0,1,0,0,0,0,0,0,0,0,1,1,1,1], + [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1], + [1,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,0,1], + [1,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,0,1], + [1,1,0,1,1,0,0,0,0,0,0,0,0,0,1,0,0,1], + [1,0,0,1,0,0,0,0,0,0,0,0,0,0,1,1,0,1], + [1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1], + [1,0,0,1,0,1,0,0,0,0,0,0,0,0,1,0,1,1], + [1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1], + [1,0,0,1,1,1,0,0,0,0,0,0,0,0,0,1,1,1], + [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1], + [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] +];*/ + +let worldMap = [ + [1,1,1,1,1,1,1,1,1,1,1,1], + [1,0,0,0,0,0,0,0,0,0,0,1], + [1,0,0,0,0,0,0,0,0,0,0,1], + [1,0,0,1,1,1,0,0,1,0,0,1], + [1,0,0,0,0,0,0,0,0,0,0,1], + [1,1,1,1,1,1,1,1,1,1,1,1] +];