"use strict"; //collision groups // cat.player | cat.map | cat.body | cat.bullet | cat.powerUp | cat.mob | cat.mobBullet | cat.mobShield const cat = { player: 0x1, map: 0x10, body: 0x100, bullet: 0x1000, powerUp: 0x10000, mob: 0x100000, mobBullet: 0x1000000, mobShield: 0x10000000, } //build build grid display const build = { pauseGrid() { // let text = `
` let text = `
PAUSED               press P to resume
`; //
// ${game.SVGleftMouse} fire gun // ${game.SVGrightMouse} use field //
let countGuns = 0 let countMods = 0 for (let i = 0, len = b.guns.length; i < len; i++) { if (b.guns[i].have) { text += `
  ${b.guns[i].name}
${b.guns[i].description}
` countGuns++ } } let el = document.getElementById("pause-grid-left") el.style.display = "grid" el.innerHTML = text text = ""; text += `
  ${mech.fieldUpgrades[mech.fieldMode].name}
${mech.fieldUpgrades[mech.fieldMode].description}
` for (let i = 0, len = b.mods.length; i < len; i++) { if (b.mods[i].count > 0) { if (b.mods[i].count === 1) { text += `
  ${b.mods[i].name}
${b.mods[i].description}
` } else { text += `
  ${b.mods[i].name} (${b.mods[i].count}x)
${b.mods[i].description}
` } countMods++ } } el = document.getElementById("pause-grid-right") el.style.display = "grid" el.innerHTML = text if (countMods > 5 || countGuns > 6) { document.body.style.overflowY = "scroll"; document.body.style.overflowX = "hidden"; } }, unPauseGrid() { document.body.style.overflow = "hidden" document.getElementById("pause-grid-left").style.display = "none" document.getElementById("pause-grid-right").style.display = "none" }, isCustomSelection: false, choosePowerUp(who, index, type) { if (type === "gun") { let isDeselect = false for (let i = 0, len = b.inventory.length; i < len; i++) { //look for selection in inventory if (b.guns[b.inventory[i]].name === b.guns[index].name) { //if already clicked, remove gun isDeselect = true who.classList.remove("build-gun-selected"); //remove gun b.inventory.splice(i, 1) b.guns[index].count = 0; b.guns[index].have = false; if (b.guns[index].ammo != Infinity) b.guns[index].ammo = 0; if (b.inventory.length === 0) b.activeGun = null; game.makeGunHUD(); break } } if (!isDeselect) { //add gun who.classList.add("build-gun-selected"); b.giveGuns(index) } } else if (type === "field") { if (mech.fieldMode !== index) { document.getElementById("field-" + mech.fieldMode).classList.remove("build-field-selected"); mech.setField(index) who.classList.add("build-field-selected"); } } else if (type === "mod") { //remove mod if you have too many if (b.mods[index].count < b.mods[index].maxCount) { if (!who.classList.contains("build-mod-selected")) who.classList.add("build-mod-selected"); b.giveMod(index) // if (b.mods[index].count > 1) who.innerHTML = `
  ${b.mods[index].name} (${b.mods[index].count}x)
${b.mods[index].description}` } else { b.removeMod(index); // who.innerHTML = `
  ${b.mods[index].name}
${b.mods[index].description}` who.classList.remove("build-mod-selected"); } } //update mod text //disable not allowed mods for (let i = 0, len = b.mods.length; i < len; i++) { const modID = document.getElementById("mod-" + i) if (b.mods[i].allowed()) { if (b.mods[i].count > 1) { modID.innerHTML = `
  ${b.mods[i].name} (${b.mods[i].count}x)
${b.mods[i].description}` } else { modID.innerHTML = `
  ${b.mods[i].name}
${b.mods[i].description}` } if (modID.classList.contains("build-grid-disabled")) { modID.classList.remove("build-grid-disabled"); modID.setAttribute("onClick", `javascript: build.choosePowerUp(this,${i},'mod')`); } } else { modID.innerHTML = `
  ${b.mods[i].name}
requires: ${b.mods[i].requires}` if (!modID.classList.contains("build-grid-disabled")) { modID.classList.add("build-grid-disabled"); modID.onclick = null } if (b.mods[i].count > 0) { b.removeMod(i) } if (modID.classList.contains("build-mod-selected")) { modID.classList.remove("build-mod-selected"); } } } }, populateGrid() { let text = `
start reset
starting level:
` for (let i = 0, len = mech.fieldUpgrades.length; i < len; i++) { text += `
  ${mech.fieldUpgrades[i].name}
${mech.fieldUpgrades[i].description}
` } for (let i = 0, len = b.guns.length; i < len; i++) { text += `
  ${b.guns[i].name}
${b.guns[i].description}
` } for (let i = 0, len = b.mods.length; i < len; i++) { if (!b.mods[i].allowed()) { // || b.mods[i].name === "+1 cardinality") { //|| b.mods[i].name === "leveraged investment" text += `
  ${b.mods[i].name}
requires: ${b.mods[i].requires}
` } else if (b.mods[i].count > 1) { text += `
  ${b.mods[i].name} (${b.mods[i].count}x)
${b.mods[i].description}
` } else { text += `
  ${b.mods[i].name}
${b.mods[i].description}
` } } document.getElementById("build-grid").innerHTML = text document.getElementById("difficulty-select-custom").value = document.getElementById("difficulty-select").value document.getElementById("difficulty-select-custom").addEventListener("input", () => { game.difficultyMode = Number(document.getElementById("difficulty-select-custom").value) localSettings.difficultyMode = Number(document.getElementById("difficulty-select-custom").value) document.getElementById("difficulty-select").value = document.getElementById("difficulty-select-custom").value localStorage.setItem("localSettings", JSON.stringify(localSettings)); //update local storage }); }, reset() { mech.setField(0) b.inventory = []; //removes guns and ammo for (let i = 0, len = b.guns.length; i < len; ++i) { b.guns[i].count = 0; b.guns[i].have = false; if (b.guns[i].ammo != Infinity) b.guns[i].ammo = 0; } b.activeGun = null; game.makeGunHUD(); b.setupAllMods(); build.isCustomSelection = true; build.populateGrid(); document.getElementById("field-0").classList.add("build-field-selected"); document.getElementById("build-grid").style.display = "grid" }, startBuildRun() { build.isCustomSelection = false; spawn.setSpawnList(); //gives random mobs, not starter mobs spawn.setSpawnList(); if (b.inventory.length > 0) { b.activeGun = b.inventory[0] //set first gun to active gun game.makeGunHUD(); } //remove any bullets that might have spawned from mods for (let i = 0; i < bullet.length; ++i) Matter.World.remove(engine.world, bullet[i]); bullet = []; const increase = Math.min(99, Number(document.getElementById("starting-level").value) * game.difficultyMode) level.levelsCleared += increase; level.difficultyIncrease(increase) //increase difficulty based on modes document.body.style.cursor = "none"; document.body.style.overflow = "hidden" document.getElementById("build-grid").style.display = "none" game.paused = false; requestAnimationFrame(cycle); } } document.getElementById("build-button").addEventListener("click", () => { //setup build run document.getElementById("build-button").style.display = "none"; const el = document.getElementById("build-grid") el.style.display = "grid" document.body.style.overflowY = "scroll"; document.body.style.overflowX = "hidden"; document.getElementById("info").style.display = 'none' level.isBuildRun = true; game.startGame(); //starts game, but pauses it game.paused = true; build.reset(); }); // local storage let localSettings = JSON.parse(localStorage.getItem("localSettings")); // console.log(localSettings) if (localSettings) { game.isBodyDamage = localSettings.isBodyDamage document.getElementById("body-damage").checked = localSettings.isBodyDamage game.isEasyToAimMode = localSettings.isEasyToAimMode document.getElementById("track-pad-mode").checked = localSettings.isEasyToAimMode game.difficultyMode = localSettings.difficultyMode document.getElementById("difficulty-select").value = localSettings.difficultyMode if (localSettings.fpsCapDefault === 'max') { game.fpsCapDefault = 999999999; } else { game.fpsCapDefault = Number(localSettings.fpsCapDefault) } document.getElementById("fps-select").value = localSettings.fpsCapDefault } else { localSettings = { isBodyDamage: true, isEasyToAimMode: false, difficultyMode: '1', fpsCapDefault: 'max', }; localStorage.setItem("localSettings", JSON.stringify(localSettings)); //update local storage document.getElementById("body-damage").checked = localSettings.isBodyDamage document.getElementById("track-pad-mode").checked = localSettings.isEasyToAimMode document.getElementById("difficulty-select").value = localSettings.difficultyMode document.getElementById("fps-select").value = localSettings.fpsCapDefault } //set up canvas var canvas = document.getElementById("canvas"); //using "const" causes problems in safari when an ID shares the same name. const ctx = canvas.getContext("2d"); document.body.style.backgroundColor = "#fff"; //disable pop up menu on right click document.oncontextmenu = function () { return false; } function setupCanvas() { canvas.width = window.innerWidth; canvas.height = window.innerHeight; canvas.width2 = canvas.width / 2; //precalculated because I use this often (in mouse look) canvas.height2 = canvas.height / 2; canvas.diagonal = Math.sqrt(canvas.width2 * canvas.width2 + canvas.height2 * canvas.height2); ctx.font = "15px Arial"; ctx.lineJoin = "round"; ctx.lineCap = "round"; // ctx.lineCap='square'; game.setZoom(); } setupCanvas(); window.onresize = () => { setupCanvas(); }; //mouse move input document.body.addEventListener("mousemove", (e) => { game.mouse.x = e.clientX; game.mouse.y = e.clientY; }); document.body.addEventListener("mouseup", (e) => { // game.buildingUp(e); //uncomment when building levels // game.mouseDown = false; // console.log(e) if (e.which === 3) { game.mouseDownRight = false; } else { game.mouseDown = false; } }); document.body.addEventListener("mousedown", (e) => { if (e.which === 3) { game.mouseDownRight = true; } else { game.mouseDown = true; } }); //keyboard input const keys = []; document.body.addEventListener("keydown", (e) => { keys[e.keyCode] = true; if (mech.alive) game.keyPress(); }); document.body.addEventListener("keyup", (e) => { keys[e.keyCode] = false; }); document.body.addEventListener("wheel", (e) => { if (!game.paused) { if (e.deltaY > 0) { game.nextGun(); } else { game.previousGun(); } } }, { passive: true }); document.getElementById("fps-select").addEventListener("input", () => { let value = document.getElementById("fps-select").value if (value === 'max') { game.fpsCapDefault = 999999999; } else { game.fpsCapDefault = Number(value) } localSettings.fpsCapDefault = value localStorage.setItem("localSettings", JSON.stringify(localSettings)); //update local storage }); document.getElementById("body-damage").addEventListener("input", () => { game.isBodyDamage = document.getElementById("body-damage").checked localSettings.isBodyDamage = game.isBodyDamage localStorage.setItem("localSettings", JSON.stringify(localSettings)); //update local storage }); document.getElementById("track-pad-mode").addEventListener("input", () => { game.isEasyToAimMode = document.getElementById("track-pad-mode").checked localSettings.isEasyToAimMode = game.isEasyToAimMode localStorage.setItem("localSettings", JSON.stringify(localSettings)); //update local storage }); // difficulty-select-custom event listener is set in build.makeGrid document.getElementById("difficulty-select").addEventListener("input", () => { game.difficultyMode = Number(document.getElementById("difficulty-select").value) localSettings.difficultyMode = game.difficultyMode localStorage.setItem("localSettings", JSON.stringify(localSettings)); //update local storage }); //main loop ************************************************************ //********************************************************************** game.loop = game.normalLoop; function cycle() { if (!game.paused) requestAnimationFrame(cycle); const now = Date.now(); const elapsed = now - game.then; // calc elapsed time since last loop if (elapsed > game.fpsInterval) { // if enough time has elapsed, draw the next frame game.then = now - (elapsed % game.fpsInterval); // Get ready for next frame by setting then=now. Also, adjust for fpsInterval not being multiple of 16.67 game.cycle++; //tracks game cycles mech.cycle++; //tracks player cycles //used to alow time to stop for everything, but the player if (game.clearNow) { game.clearNow = false; game.clearMap(); level.start(); } game.loop(); // for (let i = 0, len = loop.length; i < len; i++) { // loop[i]() // } } }