├── .gitignore ├── LICENSE ├── README.md ├── game ├── index.html ├── package.json ├── server.js └── static │ ├── client │ ├── controller.js │ ├── game.css │ ├── pixi │ │ ├── pixi.min.js │ │ └── pixi.min.js.map │ ├── sprites │ │ ├── _.htaccess │ │ ├── brick.png │ │ ├── bullet.png │ │ ├── dead.png │ │ ├── doublePistols.png │ │ ├── edge.png │ │ ├── floor.png │ │ ├── gatling.png │ │ ├── grass.png │ │ ├── healthPack.png │ │ ├── lava.png │ │ ├── pistol.png │ │ ├── player.png │ │ ├── revolver.png │ │ ├── rifle.png │ │ ├── sand.png │ │ ├── smg.png │ │ └── water.png │ └── view.js │ └── server │ └── Model.js ├── help.html ├── img ├── mouse.png └── wasd.jpg ├── index.html ├── menu.css └── screenshot.png /.gitignore: -------------------------------------------------------------------------------- 1 | /game/node_modules 2 | screenshot.png 3 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | BSD 3-Clause License 2 | 3 | Copyright (c) 2018, Grzegorz 4 | All rights reserved. 5 | 6 | Redistribution and use in source and binary forms, with or without 7 | modification, are permitted provided that the following conditions are met: 8 | 9 | * Redistributions of source code must retain the above copyright notice, this 10 | list of conditions and the following disclaimer. 11 | 12 | * Redistributions in binary form must reproduce the above copyright notice, 13 | this list of conditions and the following disclaimer in the documentation 14 | and/or other materials provided with the distribution. 15 | 16 | * Neither the name of the copyright holder nor the names of its 17 | contributors may be used to endorse or promote products derived from 18 | this software without specific prior written permission. 19 | 20 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 21 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 22 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 23 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE 24 | FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 25 | DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 26 | SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 27 | CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 28 | OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 29 | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 30 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # PixiJS-NodeJS-Game 2 | Browser 2D shooting game. Frag scrubs using weapons, use lava to get to them faster. Use wasd+LMB. Avoid water and sand cause it slows you down. Don't let Rick Roll you. Setup: 3 | ```bash 4 | cd game 5 | npm install 6 | node server.js 7 | ``` 8 | Go to [http://localhost:54070/](http://localhost:54070/) 9 | ![Screenshot](screenshot.png?raw=true "Title") 10 | -------------------------------------------------------------------------------- /game/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | Game 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 94 | 95 | 96 | 97 | -------------------------------------------------------------------------------- /game/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "game", 3 | "version": "1.0.0", 4 | "description": "", 5 | "main": "server.js", 6 | "dependencies": { 7 | "express": "^4.17.1", 8 | "socket.io": "^2.3.0" 9 | }, 10 | "devDependencies": {}, 11 | "scripts": { 12 | "test": "echo \"Error: no test specified\" && exit 1", 13 | "start": "node server.js" 14 | }, 15 | "keywords": [], 16 | "author": "", 17 | "license": "ISC" 18 | } 19 | -------------------------------------------------------------------------------- /game/server.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | let Model = require ('./static/server/Model.js'); 4 | let model = new Model(); 5 | let express = require('express'); 6 | let http = require('http'); 7 | let path = require('path'); 8 | let socketIO = require('socket.io'); 9 | 10 | let app = express(); 11 | let server = http.Server(app); 12 | let io = socketIO(server); 13 | 14 | let bodyParser = require('body-parser'); 15 | app.use(bodyParser.json()); // support json encoded bodies 16 | app.use(bodyParser.urlencoded({ extended: true })); // support encoded bodies 17 | 18 | app.set('port', 54070); 19 | app.use('/static', express.static(__dirname + '/static')); 20 | 21 | 22 | // Routing 23 | app.get('/', function(req, res) { 24 | res.sendFile(path.join(__dirname, '../index.html')); 25 | 26 | }); 27 | 28 | app.get('/menu.css', function(req, res) { 29 | res.sendFile(path.join(__dirname + '/../menu.css')); 30 | }); 31 | 32 | app.get('/help.html', function(req, res) { 33 | res.sendFile(path.join(__dirname + '/../help.html')); 34 | }); 35 | 36 | app.get('/img/mouse.png', function(req, res) { 37 | res.sendFile(path.join(__dirname + '/../img/mouse.png')); 38 | }); 39 | 40 | app.get('/img/wasd.jpg', function(req, res) { 41 | res.sendFile(path.join(__dirname + '/../img/wasd.jpg')); 42 | }); 43 | 44 | app.post('/goGame', function(req, res) { 45 | res.sendFile(path.join(__dirname, '/index.html')); 46 | console.log(req.body); 47 | playersInQueue.push(req.body.nick); 48 | }); 49 | 50 | server.listen(54070, "0.0.0.0"); 51 | 52 | require('dns').lookup(require('os').hostname(), function (err, add, fam) { 53 | console.log('addr: '+add); 54 | }) 55 | 56 | 57 | let bulletPhysics = model.getBulletPhysics(); 58 | let players = {}; 59 | let playersInQueue = []; 60 | 61 | io.on('connection', function(socket) { 62 | socket.on('new player', function() { 63 | if (playersInQueue.length > 0) { 64 | let x,y; 65 | do { 66 | x = Math.floor(Math.random()*5000); 67 | y = Math.floor(Math.random()*5000); 68 | } while(!model.map.square[Math.floor(y/50)][Math.floor(x/50)].isPassable) 69 | 70 | players[socket.id] = model.getNewPlayer(x,y,1000,0, playersInQueue.shift()); 71 | } 72 | else 73 | players[socket.id] = model.getNewPlayer(500,500,0,0, 'noName'); 74 | console.log("Player connected: " + players[socket.id].name + " " + socket.id); 75 | model.leaderboard.addEntry(players[socket.id].name, socket.id, 0); 76 | }); 77 | 78 | socket.on('disconnect', function() { 79 | for (let i=0; i 2 | * { 3 | box-sizing: border-box; 4 | } 5 | 6 | body { 7 | cursor: crosshair; 8 | font-family: Arial, Helvetica, sans-serif; 9 | padding: 40px; 10 | background-color: #262626; 11 | } 12 | 13 | 14 | -------------------------------------------------------------------------------- /game/static/client/sprites/_.htaccess: -------------------------------------------------------------------------------- 1 | Options +Indexes -------------------------------------------------------------------------------- /game/static/client/sprites/brick.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/brick.png -------------------------------------------------------------------------------- /game/static/client/sprites/bullet.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/bullet.png -------------------------------------------------------------------------------- /game/static/client/sprites/dead.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/dead.png -------------------------------------------------------------------------------- /game/static/client/sprites/doublePistols.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/doublePistols.png -------------------------------------------------------------------------------- /game/static/client/sprites/edge.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/edge.png -------------------------------------------------------------------------------- /game/static/client/sprites/floor.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/floor.png -------------------------------------------------------------------------------- /game/static/client/sprites/gatling.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/gatling.png -------------------------------------------------------------------------------- /game/static/client/sprites/grass.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/grass.png -------------------------------------------------------------------------------- /game/static/client/sprites/healthPack.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/healthPack.png -------------------------------------------------------------------------------- /game/static/client/sprites/lava.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/lava.png -------------------------------------------------------------------------------- /game/static/client/sprites/pistol.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/pistol.png -------------------------------------------------------------------------------- /game/static/client/sprites/player.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/player.png -------------------------------------------------------------------------------- /game/static/client/sprites/revolver.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/revolver.png -------------------------------------------------------------------------------- /game/static/client/sprites/rifle.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/rifle.png -------------------------------------------------------------------------------- /game/static/client/sprites/sand.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/sand.png -------------------------------------------------------------------------------- /game/static/client/sprites/smg.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/smg.png -------------------------------------------------------------------------------- /game/static/client/sprites/water.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/game/static/client/sprites/water.png -------------------------------------------------------------------------------- /game/static/client/view.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | let type = "WebGL" 3 | if(!PIXI.utils.isWebGLSupported()){ 4 | type = "canvas" 5 | } 6 | 7 | 8 | 9 | let app = new PIXI.Application({ 10 | width: controller.width, 11 | height: controller.height, 12 | antialias: true, 13 | transparent: false, 14 | resolution: 1 15 | } 16 | ); 17 | 18 | 19 | PIXI.loader 20 | .add("static/client/sprites/grass.png") 21 | .add("static/client/sprites/sand.png") 22 | .add("static/client/sprites/edge.png") 23 | .add("static/client/sprites/water.png") 24 | .add("static/client/sprites/lava.png") 25 | .add("static/client/sprites/brick.png") 26 | .add("static/client/sprites/floor.png") 27 | 28 | .add("static/client/sprites/player.png") 29 | .add("static/client/sprites/pistol.png") 30 | .add("static/client/sprites/revolver.png") 31 | .add("static/client/sprites/doublePistols.png") 32 | .add("static/client/sprites/rifle.png") 33 | .add("static/client/sprites/smg.png") 34 | .add("static/client/sprites/gatling.png") 35 | .add("static/client/sprites/bullet.png") 36 | .add("static/client/sprites/healthPack.png") 37 | .add("static/client/sprites/dead.png") 38 | .load(setup); 39 | function setup() { 40 | controller.newPlayer(); 41 | controller.emitInput(); 42 | controller.listenToUpdate(); 43 | controller.listenToDeath(); 44 | app.ticker.add(delta => gameLoop(delta)); 45 | } 46 | 47 | function gameLoop(delta){ 48 | app.stage.removeChildren(); 49 | if (controller.mode == 'dead') 50 | { 51 | let deadSprite = new PIXI.Sprite(PIXI.loader.resources['static/client/sprites/dead.png'].texture); 52 | deadSprite.position.set(0,0); 53 | app.stage.addChild(deadSprite); 54 | return; 55 | } 56 | 57 | for (let i = 0; i < 17; i++) { 58 | for (let j = 0; j < 21; j++) { 59 | let square = new PIXI.Sprite(PIXI.loader.resources[gameMap.square[i][j].path].texture); 60 | square.x=controller.squareWidthInPixels*j-currentPlayer.xAbsolute%50; 61 | square.y=controller.squareHeightInPixels*i-currentPlayer.yAbsolute%50; 62 | app.stage.addChild(square); 63 | } 64 | } 65 | for (let id in players) { 66 | let player = players[id]; 67 | let playerSprite = new PIXI.Sprite(PIXI.loader.resources['static/client/sprites/player.png'].texture); 68 | playerSprite.anchor.set(0.5,0.5); 69 | playerSprite.position.set(player.x,player.y); 70 | app.stage.addChild(playerSprite); 71 | 72 | let weaponSprite = new PIXI.Sprite(PIXI.loader.resources['static/client/sprites/'+player.weapon.spriteName].texture); 73 | weaponSprite.anchor.set(0.5,0.5); 74 | weaponSprite.rotation = player.direction; 75 | weaponSprite.x=player.x+10*Math.cos(player.direction); 76 | weaponSprite.y=player.y+10*Math.sin(player.direction); 77 | app.stage.addChild(weaponSprite); 78 | 79 | let name = new PIXI.Text(player.name); 80 | name.style = {fill: 'white', stroke: 'black', strokeThickness: 2}; 81 | name.anchor.set(0.5,0.5); 82 | name.position.set(player.x, player.y-55); 83 | app.stage.addChild(name); 84 | 85 | let redBar = new PIXI.Graphics(); 86 | redBar.lineStyle(1, 0x000000, 1); 87 | redBar.beginFill(0xFF0000); 88 | redBar.drawRect(player.x-40, player.y-40, 80, 10); 89 | redBar.endFill(); 90 | app.stage.addChild(redBar); 91 | 92 | let greenBar = new PIXI.Graphics(); 93 | greenBar.lineStyle(1, 0x000000, 1); 94 | greenBar.beginFill(0x008111); 95 | greenBar.drawRect(player.x-40, player.y-40, Math.max(0,player.health*(80/1000)), 10); 96 | greenBar.endFill(); 97 | app.stage.addChild(greenBar); 98 | } 99 | 100 | 101 | let len = items.length; 102 | for (let i=0; i=7) 183 | break; 184 | } 185 | } 186 | -------------------------------------------------------------------------------- /game/static/server/Model.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | class Terrain { 4 | constructor(speedArg, typeArg, damageArg, isPassableArg) { 5 | this.speed = speedArg; 6 | this.type=typeArg; 7 | this.damage = damageArg; 8 | this.isPassable = isPassableArg; 9 | } 10 | } 11 | 12 | 13 | let sand = new Terrain (3, 'sand', 0, 1); 14 | let edge = new Terrain (3, 'edge', 0, 0); 15 | let grass = new Terrain (5, 'grass', 0, 1); 16 | let water = new Terrain (2, 'water', 0, 1); 17 | let lava = new Terrain (10, 'lava', 5, 1); 18 | let brick = new Terrain (3, 'brick', 0, 0); 19 | let floor = new Terrain (6, 'floor', 0, 1); 20 | 21 | class Point { 22 | constructor(xArg, yArg) { 23 | this.x=xArg; 24 | this.y=yArg; 25 | } 26 | } 27 | 28 | class Map { 29 | constructor() { 30 | this.square = []; 31 | this.heightInSquares = 100; 32 | this.widthInSquares = 100; 33 | for (let i = 0; i < this.heightInSquares; i++) { 34 | this.square[i] = []; 35 | for (let j = 0; j < this.widthInSquares; j++) { 36 | if (i==0 || j==0 || i==99 || j==99) 37 | this.square[i][j]=edge; 38 | else 39 | this.square[i][j]=grass; 40 | 41 | } 42 | } 43 | this.createArea(new Point(1, 1), 50, 0.75, sand); 44 | this.createArea(new Point(10, 30), 200, 0.75, sand); 45 | this.createArea(new Point(97, 50), 1000, 0.65, sand); 46 | this.createArea(new Point(50, 20), 500, 0.65, sand); 47 | this.createArea(new Point(10, 50), 500, 0.80, sand); 48 | this.createArea(new Point(97, 97), 1000, 0.90, water); 49 | this.createArea(new Point(20, 30), 200, 0.75, water); 50 | this.createArea(new Point(20, 5), 100, 0.75, water); 51 | this.createArea(new Point(50, 50), 800, 0.60, water); 52 | this.createArea(new Point(50, 90), 800, 0.65, lava); 53 | this.createArea(new Point(2, 2), 30, 0.65, lava); 54 | this.createWall(50, 10, 4, "horizontally"); 55 | this.createWall(80, 30, 4, "vertically"); 56 | 57 | this.createBuilding(15,15,10, 10, 2); 58 | this.createBuilding(20,20,15, 20, 3); 59 | this.createBuilding(45,45,10,10, 18); 60 | this.createBuilding(60,10,30, 10, 9); 61 | this.createBuilding(20,80,40, 5, 7); 62 | this.createBridge(80,80,10); 63 | this.createBuilding(3, 43, 20, 15, 2); 64 | 65 | } 66 | 67 | 68 | createArea(center, size, randomness, type) { ///using a DFS algorithm 69 | let queue = []; 70 | queue.push(center); 71 | let currentSize=0; 72 | while (queue.length!=0 && currentSize=1 && current.x+1 <=98 && current.y >= 1 && current.y <=98 && this.square[current.x+1][current.y] !== type) { 81 | let currentNew = new Point(current.x+1, current.y); 82 | queue.push(currentNew); 83 | } 84 | if (Math.random()<=randomness && current.x >=1 && current.x <=98 && current.y+1 >= 1 && current.y+1 <=98 && this.square[current.x][current.y+1].type !== type) { 85 | let currentNew = new Point(current.x, current.y+1); 86 | queue.push(currentNew); 87 | } 88 | if (Math.random()<=randomness && current.x-1 >=1 && current.x-1 <=98 && current.y >= 1 && current.y <=98 && this.square[current.x-1][current.y].type !== type) { 89 | let currentNew = new Point(current.x-1, current.y); 90 | queue.push(currentNew); 91 | } 92 | if (Math.random()<=randomness && current.x >=1 && current.x <=98 && current.y-1 >= 1 && current.y-1 <=98 && this.square[current.x][current.y-1].type !== type) { 93 | let currentNew = new Point(current.x, current.y-1); 94 | queue.push(currentNew); 95 | } 96 | } 97 | } 98 | 99 | createBuilding(x, y, width, height, numberOfDoors ) { 100 | 101 | this.createWall(x,y,width,"horizontally"); 102 | this.createWall(x,y+height-1,width,"horizontally"); 103 | this.createWall(x,y,height,"vertically"); 104 | this.createWall(x+width-1,y,height,"vertically"); 105 | 106 | while(numberOfDoors--) 107 | { 108 | let doorsX, doorsY; 109 | switch (Math.floor(Math.random()*4)) { 110 | case 0://east 111 | doorsX = x+width-1; 112 | doorsY = y+Math.floor(Math.random()*(height-4))+1; 113 | this.square[doorsY][doorsX] = floor; 114 | this.square[doorsY+1][doorsX] = floor; 115 | break; 116 | 117 | case 1://north 118 | doorsX = x+Math.floor(Math.random()*(width-4))+1; 119 | doorsY = y; 120 | this.square[doorsY][doorsX] = floor; 121 | this.square[doorsY][doorsX+1] = floor; 122 | 123 | break; 124 | 125 | case 2://west 126 | doorsX = x; 127 | doorsY = y+Math.floor(Math.random()*(height-4))+1; 128 | this.square[doorsY][doorsX] = floor; 129 | this.square[doorsY+1][doorsX] = floor; 130 | break; 131 | 132 | case 3://south 133 | doorsX = x+Math.floor(Math.random()*(width-4))+1; 134 | doorsY = y+height-1; 135 | this.square[doorsY][doorsX] = floor; 136 | this.square[doorsY][doorsX+1] = floor; 137 | break; 138 | } 139 | 140 | }//numberOfDoors is changed now 141 | 142 | for (let i=1;i0.5) 195 | dirX = 1; 196 | let dirY = -1; 197 | if(Math.random()>0.5) 198 | dirY = 1; 199 | this.weapon.x=this.x + 100*dirX; 200 | this.weapon.y=this.y + 100*dirY; 201 | if (!(this.weapon instanceof Pistol)) 202 | items.push(this.weapon); 203 | } 204 | 205 | } 206 | 207 | class Bullet { 208 | constructor(xArg, yArg, directionArg, damageArg, ownerArg) { 209 | this.x = xArg; 210 | this.y = yArg; 211 | this.direction = directionArg; 212 | this.speed = 20; 213 | this.range = 800; 214 | this.distanceTraveled = 0; 215 | this.damage = damageArg; 216 | this.owner = ownerArg; 217 | }; 218 | 219 | } 220 | 221 | class BulletPhysics { 222 | constructor () { 223 | this.bullets = []; 224 | } 225 | 226 | update(map) { 227 | for (let i=0; i=this.bullets[i].range) { 242 | this.bullets.splice(i,1); 243 | length--; 244 | i--; 245 | } 246 | 247 | } 248 | } 249 | 250 | checkHits(players) { 251 | for (let id in players) 252 | { 253 | let player=players[id]; 254 | for (let i=0; i=player.x-20 && this.bullets[i].x<=player.x+20 && this.bullets[i].y>=player.y-20 && this.bullets[i].y<=player.y+20) { 256 | player.health -= this.bullets[i].damage; 257 | if (player.health<=0) 258 | player.killedBy = this.bullets[i].owner; 259 | this.bullets.splice(i,1); 260 | i--; 261 | } 262 | } 263 | } 264 | } 265 | } 266 | 267 | class Item { 268 | constructor(x, y) { 269 | this.x = x; 270 | this.y = y; 271 | } 272 | } 273 | 274 | class Items { 275 | constructor(mapSquares) { 276 | this.array = []; 277 | this.generateItems(100, mapSquares); 278 | }; 279 | 280 | checkColissions(players) { 281 | for (let id in players) 282 | { 283 | let player=players[id]; 284 | for (let i=0; i=player.x-this.array[i].spriteWidth && this.array[i].x<=player.x+this.array[i].spriteWidth && this.array[i].y>=player.y-this.array[i].spriteHeight && this.array[i].y<=player.y+this.array[i].spriteHeight) { 286 | if (this.array[i] instanceof Weapon) 287 | player.pickUpItem(this.array[i], this.array); 288 | else 289 | this.array[i].heal(player); 290 | this.array.splice(i,1); 291 | i--; 292 | } 293 | } 294 | } 295 | }; 296 | 297 | generateItems(amount, mapSquares) { 298 | let gatling = new Gatling(); 299 | gatling.x=2500; 300 | gatling.y=2500; 301 | this.array.push(gatling); 302 | for (let i=0; i= this.fireRate) { 386 | this.lastShot = time; 387 | let spread = (Math.random() - 0.5)*Math.PI*(100-this.accuracy)/100; 388 | let bullet = new Bullet(x+30*Math.cos(direction), y+30*Math.sin(direction), direction+spread, this.damage, shooter); 389 | this.setBulletStats(bullet); 390 | bulletPhysics.bullets.push(bullet); 391 | } 392 | } 393 | } 394 | 395 | class SemiAutomaticWeapon extends Weapon { 396 | constructor(dmg, acc, fireRate) { 397 | super(dmg, acc, fireRate); 398 | }; 399 | 400 | shoot (x, y, direction, bulletPhysics, shooter) 401 | { 402 | let time = new Date(); 403 | if(!this.triggered && time - this.lastShot >= this.fireRate) { 404 | this.lastShot = time; 405 | let spread = (Math.random() - 0.5)*Math.PI*(100-this.accuracy)/100; 406 | let bullet = new Bullet(x +30*Math.cos(direction), y+30*Math.sin(direction), direction+spread, this.damage, shooter); 407 | this.setBulletStats(bullet); 408 | bulletPhysics.bullets.push(bullet); 409 | this.triggered = 1; 410 | } 411 | } 412 | } 413 | 414 | class Pistol extends SemiAutomaticWeapon { 415 | constructor() { 416 | super(300, 95, 400); 417 | this.spriteName = "pistol.png"; 418 | this.spriteWidth = 30; 419 | this.spriteHeight = 18; 420 | } 421 | } 422 | 423 | class Revolver extends SemiAutomaticWeapon { 424 | constructor() { 425 | super(600, 100, 500); 426 | this.spriteName = "revolver.png"; 427 | this.spriteWidth = 30; 428 | this.spriteHeight = 18; 429 | } 430 | } 431 | 432 | class DoublePistol extends SemiAutomaticWeapon { 433 | constructor() { 434 | super(300, 95, 400); 435 | this.spriteName = "doublePistols.png"; 436 | this.spriteWidth = 30; 437 | this.spriteHeight = 48; 438 | } 439 | 440 | shoot (x, y, direction, bulletPhysics, shooter) 441 | { 442 | let time = new Date(); 443 | if(!this.triggered && time - this.lastShot >= this.fireRate) { 444 | this.lastShot = time; 445 | let spread1 = (Math.random() - 0.5)*Math.PI*(100-this.accuracy)/100; 446 | let bullet1 = new Bullet(x + 20*Math.cos(direction+Math.PI/2) + 50*Math.cos(direction), y + 20*Math.sin(direction+Math.PI/2) + 50*Math.sin(direction), direction+spread1, this.damage, shooter); 447 | this.setBulletStats(bullet1); 448 | bulletPhysics.bullets.push(bullet1); 449 | let spread2 = (Math.random() - 0.5)*Math.PI*(100-this.accuracy)/100; 450 | let bullet2 = new Bullet(x - 20*Math.cos(direction+Math.PI/2) + 50*Math.cos(direction), y - 20*Math.sin(direction+Math.PI/2) + 50*Math.sin(direction), direction+spread2, this.damage, shooter); 451 | this.setBulletStats(bullet2); 452 | bulletPhysics.bullets.push(bullet2); 453 | this.triggered = 1; 454 | } 455 | } 456 | } 457 | 458 | class Rifle extends AutomaticWeapon { 459 | constructor() { 460 | super(400, 98, 150); 461 | this.spriteName = "rifle.png"; 462 | this.spriteWidth = 90; 463 | this.spriteHeight = 33; 464 | } 465 | 466 | } 467 | 468 | class Smg extends AutomaticWeapon { 469 | constructor() { 470 | super(100, 80, 50); 471 | this.spriteName = "smg.png"; 472 | this.spriteWidth = 80; 473 | this.spriteHeight = 65; 474 | } 475 | } 476 | 477 | class Gatling extends AutomaticWeapon { 478 | constructor() { 479 | super(300, 70, 15); 480 | this.spriteName = "gatling.png"; 481 | this.spriteWidth = 90; 482 | this.spriteHeight = 33; 483 | } 484 | } 485 | 486 | class Entry { 487 | constructor(name, socketId, score) { 488 | this.name = name; 489 | this.socketId = socketId; 490 | this.score = score; 491 | } 492 | } 493 | 494 | class Leaderboard { 495 | constructor() { 496 | this.array = []; 497 | } 498 | 499 | addEntry(name, socketId, score) { 500 | this.array.push(new Entry(name, socketId, score)); 501 | this.sort(); 502 | } 503 | 504 | addPoint(socketId) { 505 | for (let i=0; i<=this.array.length; i++ ) { 506 | if (this.array[i].socketId == socketId) { 507 | console.log("added"); 508 | this.array[i].score++; 509 | break; 510 | } 511 | } 512 | this.sort(); 513 | } 514 | 515 | sort() { 516 | this.array.sort(function(a, b) { 517 | return a.score < b.score; 518 | }); 519 | } 520 | } 521 | 522 | class Model { 523 | constructor() { 524 | this.map = new Map(); 525 | this.items = new Items(this.map.square); 526 | this.leaderboard = new Leaderboard(); 527 | }; 528 | 529 | getLeaderboard() { 530 | return this.leaderboard; 531 | } 532 | 533 | getMap() { 534 | return this.map; 535 | } 536 | getItems() { 537 | return this.items; 538 | } 539 | 540 | 541 | getNewPlayer(xArg, yArg, healthArg, directionArg, nameArg) { 542 | return new Player(xArg, yArg, healthArg, directionArg, nameArg); 543 | } 544 | 545 | getBulletPhysics(){ 546 | return new BulletPhysics(); 547 | } 548 | 549 | getBullet(xArg, yArg, directionArg){ 550 | return new Bullet(xArg, yArg, directionArg); 551 | } 552 | 553 | } 554 | 555 | 556 | module.exports = Model; 557 | -------------------------------------------------------------------------------- /help.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Game 5 | 6 | 7 | 8 | 9 | 10 | 11 |
12 |

Welcome to a shooting game

13 |
14 | 15 |
16 | 17 |

18 |
19 | 20 |
21 |
22 |
23 | HTML5 Icon 24 |

Use wasd buttons to move.

25 |
26 |
27 | HTML5 Icon 28 |

Use a mouse to aim and shoot.

29 |
30 |
31 |
32 | 33 |
34 |

Created by Grzegorz Rypeść

35 |
36 | 37 | 38 | 39 | -------------------------------------------------------------------------------- /img/mouse.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/img/mouse.png -------------------------------------------------------------------------------- /img/wasd.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/img/wasd.jpg -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Game 5 | 6 | 7 | 8 | 9 | 10 | 11 |
12 |

Welcome to a shooting game

13 |
14 | 15 |
16 | 17 |
18 |

Enter your nick


19 |

20 |

21 |
22 |

23 |
24 | 25 |
26 |

About

27 |

This is a 2d shooting game. Server and client side are pure Javascript. Damn, that's crazy.

28 |

Graphic library is PIXI.js. Enjoy your stay. Don't try this at home. Peace.

29 |
30 |
31 | 32 |
33 |

Created by Grzegorz Rypeść

34 |
35 | 36 | 37 | 38 | -------------------------------------------------------------------------------- /menu.css: -------------------------------------------------------------------------------- 1 | 123 | -------------------------------------------------------------------------------- /screenshot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/grypesc/getRickRolled/f46a7b23f1791883336cda5fdb4592e8df3ff95f/screenshot.png --------------------------------------------------------------------------------