diff --git a/css/index.css b/css/index.css
deleted file mode 100644
index 1843fb8..0000000
--- a/css/index.css
+++ /dev/null
@@ -1,33 +0,0 @@
-html, body {
- margin: 0;
- height: 100vh;
- width: 100vw;
- background: lightskyblue;
- font-family: sans-serif;
-}
-
-h1 {
- text-align: center;
-}
-
-ul {
- list-style-type: none;
- text-align: center;
- padding: 0;
- display: grid;
-}
-
-li {
- width: 25vw;
- padding: 10px 20px;
- margin: 0 auto;
- margin-top: 20px;
- background: #9ea399;
- border-radius: 5px;
- border: 2px solid #1c1914;
- cursor: pointer;
-}
-
-li:hover {
- box-shadow: 2px 2px #1c1914;
-}
\ No newline at end of file
diff --git a/game.html b/html/game.html
similarity index 67%
rename from game.html
rename to html/game.html
index 35dd510..bfeba34 100644
--- a/game.html
+++ b/html/game.html
@@ -3,20 +3,20 @@
-
-
+
+
Game
-
+
diff --git a/index.html b/index.html
deleted file mode 100644
index 15d8c4b..0000000
--- a/index.html
+++ /dev/null
@@ -1,18 +0,0 @@
-
-
-
-
-
- Caa-game
-
-
-
- Caa-game
-
- - Resume game
- - Settings
- - Quit game
-
-
-
-
\ No newline at end of file
diff --git a/main.js b/main.js
index d541e63..08901e5 100644
--- a/main.js
+++ b/main.js
@@ -28,7 +28,7 @@ function createWindow () {
win.removeMenu();
// and load the index.html of the app.
- win.loadFile(path.join("index.html"));
+ win.loadFile(path.join("html/game.html"));
// Open the DevTools.
win.webContents.openDevTools();
diff --git a/package-lock.json b/package-lock.json
index da887ea..03e97a0 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -193,9 +193,9 @@
}
},
"asdf-games": {
- "version": "1.0.12",
- "resolved": "https://registry.npmjs.org/asdf-games/-/asdf-games-1.0.12.tgz",
- "integrity": "sha512-XaramOeOnLK4eH3HRRR6joCQClvuZZ/ANBEjKzMpMHsZ/+O/G3arMI2h6KQ86yrWrT0TZGTc89vrfmBhQmqNrQ=="
+ "version": "1.0.14",
+ "resolved": "https://registry.npmjs.org/asdf-games/-/asdf-games-1.0.14.tgz",
+ "integrity": "sha512-0CCsgxfPjJL5BI7a8CYw49Y14rslG1BIsg20gnaf8Hi0SOaXJ61mZXf6Q96l9h5OhDaOLsv9e/yAMY9P0vq3IQ=="
},
"astral-regex": {
"version": "1.0.0",
diff --git a/package.json b/package.json
index d57fffe..4d99a7c 100644
--- a/package.json
+++ b/package.json
@@ -13,7 +13,7 @@
"author": "McArn",
"license": "ISC",
"dependencies": {
- "asdf-games": "^1.0.12"
+ "asdf-games": "^1.0.14"
},
"devDependencies": {
"cross-env": "^7.0.2",
diff --git a/res/aseprite/example.aseprite b/res/images/aseprite/example.aseprite
similarity index 100%
rename from res/aseprite/example.aseprite
rename to res/images/aseprite/example.aseprite
diff --git a/res/aseprite/pointers.aseprite b/res/images/aseprite/pointers.aseprite
similarity index 100%
rename from res/aseprite/pointers.aseprite
rename to res/images/aseprite/pointers.aseprite
diff --git a/res/aseprite/tilemap.aseprite b/res/images/aseprite/tilemap.aseprite
similarity index 100%
rename from res/aseprite/tilemap.aseprite
rename to res/images/aseprite/tilemap.aseprite
diff --git a/res/cog-solid.svg b/res/images/cog-solid.svg
similarity index 100%
rename from res/cog-solid.svg
rename to res/images/cog-solid.svg
diff --git a/res/mage.png b/res/images/mage.png
similarity index 100%
rename from res/mage.png
rename to res/images/mage.png
diff --git a/res/player.png b/res/images/player.png
similarity index 100%
rename from res/player.png
rename to res/images/player.png
diff --git a/res/pointers.png b/res/images/pointers.png
similarity index 100%
rename from res/pointers.png
rename to res/images/pointers.png
diff --git a/res/tilemap.png b/res/images/tilemap.png
similarity index 100%
rename from res/tilemap.png
rename to res/images/tilemap.png
diff --git a/res/lang/default.js b/res/lang/default.js
new file mode 100644
index 0000000..630166e
--- /dev/null
+++ b/res/lang/default.js
@@ -0,0 +1,31 @@
+module.exports = {
+ titleScreen: {
+ instructions: [
+ "Press Space to Start!",
+ "Press T for the tutorial",
+ "Press Q to quit",
+ ]
+ },
+ tutorial: [
+ "Use WASD or the direction keys to move",
+ "Press Ctrl to sprint, but watch your stamina!",
+ "Press space to interact with objects",
+ "If the arrow above an object is red, you cannot interact with it",
+ "You might be missing key or have already interacted with it",
+ "Press space to return"
+ ],
+ gameOver: {
+ dead: "You died!",
+ instruction: "Press space to return to title"
+ },
+ logoScreen: [
+ "Made by JoVo and McArn"
+ ],
+ game: {
+ lives: "Lives",
+ stamina: "Stamina",
+ keyFind: "You found a key!",
+ keyMiss: "You do not have the key for this door!",
+ chestOpen: "You already opened this chest"
+ }
+};
\ No newline at end of file
diff --git a/res/sounds/forbidden.wav b/res/sounds/forbidden.wav
new file mode 100644
index 0000000..176f4cb
Binary files /dev/null and b/res/sounds/forbidden.wav differ
diff --git a/src/entities/bullet.js b/src/entities/bullet.js
index bd152b6..8547f00 100644
--- a/src/entities/bullet.js
+++ b/src/entities/bullet.js
@@ -1,8 +1,8 @@
var asdf = require("asdf-games");
// eslint-disable-next-line no-unused-vars
-const { Texture, TileSprite, AnimManager, wallslide, entity } = asdf;
+const { Texture, TileSprite, deadInTracks, entity } = asdf;
-const texture = new Texture("./res/tilemap.png");
+const texture = new Texture(__dirname + "/../../res/images/tilemap.png");
class Bullet extends TileSprite {
constructor(pos, angle, parent, player, level) {
@@ -41,9 +41,15 @@ class Bullet extends TileSprite {
} else {
const xo = Math.cos(this.rotation) * 100 * dt;
const yo = Math.sin(this.rotation) * 100 * dt;
+ const r = deadInTracks.deadInTracks(this, this.level, xo, yo);
- this.pos.x += xo;
- this.pos.y += yo;
+ if (r.x == 0 || r.y == 0) {
+ this.parent.bullet = false;
+ this.dead = true;
+ } else {
+ this.pos.x += xo;
+ this.pos.y += yo;
+ }
}
}
}
diff --git a/src/entities/chest.js b/src/entities/chest.js
index 113a245..6fdfa43 100644
--- a/src/entities/chest.js
+++ b/src/entities/chest.js
@@ -1,9 +1,13 @@
var asdf = require("asdf-games");
// eslint-disable-next-line no-unused-vars
-const { Texture, TileSprite, AnimManager, entity } = asdf;
+const { Texture, Sound, TileSprite, entity } = asdf;
-var texture = new Texture("./res/tilemap.png");
-var Pointer = require("./pointer.js");
+const texture = new Texture(__dirname + "/../../res/images/tilemap.png");
+const sounds = {
+ forbidden: new Sound(__dirname + "/../../res/sounds/forbidden.wav")
+};
+
+const Pointer = require("./pointer.js");
const state = {
open: 0,
@@ -29,6 +33,7 @@ class Chest extends TileSprite {
this.level = level;
this.pointer = false;
+ this.pressed = false;
this.hitBox = {
x: 1,
@@ -57,10 +62,21 @@ class Chest extends TileSprite {
this.pointer.anims.play("red");
}
- if (this.keys.action && this.state == state.closed) {
- this.state = state.open;
- this.action();
+ if (this.keys.action) {
+ if (this.state == state.closed) {
+ this.state = state.open;
+ this.pressed = true;
+ this.action();
+ } else {
+ if (!sounds.forbidden.playing && !this.pressed) {
+ sounds.forbidden.play();
+ this.pressed = true;
+ }
+ }
+ } else {
+ this.pressed = false;
}
+
} else {
this.level.entities.remove(this.pointer);
this.pointer = false;
diff --git a/src/entities/mage.js b/src/entities/mage.js
index 161a275..5f90c33 100644
--- a/src/entities/mage.js
+++ b/src/entities/mage.js
@@ -2,8 +2,8 @@ var asdf = require("asdf-games");
// eslint-disable-next-line no-unused-vars
const { Texture, TileSprite, AnimManager, wallslide, entity } = asdf;
+const texture = new Texture("../res/images/mage.png");
const Bullet = require("./bullet.js");
-const texture = new Texture("./res/mage.png");
const states = {
idle: 0,
@@ -126,7 +126,6 @@ class Mage extends TileSprite {
}
shoot(angle) {
- console.log("shoot");
this.bullet = true;
var pos = {
x: this.pos.x + 8,
diff --git a/src/entities/player.js b/src/entities/player.js
index d6a734a..e702148 100644
--- a/src/entities/player.js
+++ b/src/entities/player.js
@@ -1,7 +1,7 @@
var asdf = require("asdf-games");
const { Texture, TileSprite, AnimManager, wallslide } = asdf;
-var texture = new Texture("./res/player.png");
+const texture = new Texture("../res/images/player.png");
class Player extends TileSprite {
constructor(keys, window) {
diff --git a/src/entities/pointer.js b/src/entities/pointer.js
index ac637db..c301c68 100644
--- a/src/entities/pointer.js
+++ b/src/entities/pointer.js
@@ -1,13 +1,8 @@
var asdf = require("asdf-games");
// eslint-disable-next-line no-unused-vars
-const { Texture, TileSprite, AnimManager, entity } = asdf;
+const { Texture, TileSprite, AnimManager } = asdf;
-const texture = new Texture("./res/pointers.png");
-
-// const states = {
-// white: 0,
-// red: 1
-// };
+const texture = new Texture("../res/images/pointers.png");
class Pointer extends TileSprite {
constructor(pos) {
diff --git a/src/entities/portal.js b/src/entities/portal.js
index 42c654b..6ec2143 100644
--- a/src/entities/portal.js
+++ b/src/entities/portal.js
@@ -1,8 +1,12 @@
var asdf = require("asdf-games");
// eslint-disable-next-line no-unused-vars
-const { Texture, TileSprite, entity } = asdf;
+const { Texture, Sound, TileSprite, entity } = asdf;
+
+const texture = new Texture(__dirname + "/../../res/images/tilemap.png");
+const sounds = {
+ forbidden: new Sound(__dirname + "/../../res/sounds/forbidden.wav")
+};
-var texture = new Texture("./res/tilemap.png");
var Pointer = require("./pointer.js");
class Portal extends TileSprite {
@@ -15,6 +19,8 @@ class Portal extends TileSprite {
this.action = action;
this.pointer = false;
+ this.pressed = false;
+
this.keys = keys;
this.key = key;
@@ -75,23 +81,42 @@ class Portal extends TileSprite {
if (this.player.items.keys.length > 0) {
for (let index = 0; index < this.player.items.keys.length; index++) {
const element = this.player.items.keys[index];
+ console.log(this.key);
+ console.log(element);
if (element == this.key) {
// Correct key
this.pointer.anims.play("white");
if (this.keys.action) {
this.action();
+ console.warn("action");
}
break;
} else {
// Not the correct key
- this.pointer.anims.play("red");
console.log("correct keyn't");
+ this.pointer.anims.play("red");
+ if (this.keys.action) {
+ if (!sounds.forbidden.playing && !this.pressed) {
+ sounds.forbidden.play();
+ this.pressed = true;
+ }
+ } else {
+ this.pressed = false;
+ }
}
}
} else {
// No keys at all
+ console.log("You have no keys");
this.pointer.anims.play("red");
- console.log("keyn't");
+ if (this.keys.action) {
+ if (!sounds.forbidden.playing && !this.pressed) {
+ sounds.forbidden.play();
+ this.pressed = true;
+ }
+ } else {
+ this.pressed = false;
+ }
}
} else {
if (this.keys.action) {
diff --git a/src/game.js b/src/game.js
deleted file mode 100644
index 4290e42..0000000
--- a/src/game.js
+++ /dev/null
@@ -1,110 +0,0 @@
-const { ipcRenderer, remote } = require("electron");
-
-var asdf = require("asdf-games");
-// eslint-disable-next-line no-unused-vars
-const { Game, KeyControls, MouseControls, Camera } = asdf;
-
-const window = { w: 640, h: 320 };
-
-const game = new Game(window.w, window.h, true);
-ipcRenderer.send("resize", window);
-
-const { scene } = game;
-
-const mouseAim = new MouseControls(document.getElementById("board"));
-const keys = new KeyControls();
-
-const Stats = require("./src/helpers/stats.js");
-var Player = require("./src/entities/player.js");
-var Level = require("./src/helpers/level.js");
-
-// Initialise first level 1-1.js at startPosition 0
-var player = new Player(keys, window);
-
-var level = new Level(require("./src/levels/1-1.js"), keys, player);
-player.pos.x = level.startPos[0].x / 1;
-player.pos.y = level.startPos[0].y / 1;
-player.level = level;
-
-const camera = new Camera(player, window, { w: level.w * 2, h: level.h * 2 });
-var stats = new Stats(player);
-
-scene.add(camera);
-camera.add(level);
-camera.add(player);
-scene.add(stats);
-
-function switchLevel(module, pos = 0) {
- scene.remove(stats);
- console.log(scene);
- camera.map(function(e) {
- camera.remove(e);
- if (e instanceof Level) {
- var lives = player.lives;
- var items = player.items;
-
- var p = new Player(keys, window);
- player = p;
-
- e = new Level(module, keys, player);
- level = e;
-
- player.pos.x = level.startPos[pos].x / 1;
- player.pos.y = level.startPos[pos].y / 1;
-
- player.lives = lives;
- player.items = items;
- player.level = e;
-
- stats = new Stats(player);
-
- camera.add(e);
- camera.add(player);
- camera.setSubject(player);
- scene.add(stats);
- }
- });
-}
-
-game.run(() => {
- // Debugging tools
- if (mouseAim.isDown) {
- console.log("cliccccccccccc");
- console.log(player);
- console.log(level);
- }
-
- // Switch to another level
- if (level.switch) {
- console.log("Switching level!", level);
- switchLevel(require(level.switch.module), level.switch.pos);
- level.switch = undefined;
- }
-
- // Refocus camera to player when player is moved by a portal
- if (player.refocus) {
- camera.setSubject(player);
- player.refocus = false;
- }
-});
-
-
-/* *********************************************************
- Settings behavior
-********************************************************* */
-
-// Opening and closing of menu.
-document.getElementById("settings").addEventListener("click", () => {
- const menuRef = document.getElementById("menu");
- menuRef.style.display = menuRef.style.display === "block" ? "none" : "block";
-});
-
-// Quit Game handling.
-document.getElementById("close").addEventListener("click", () => {
- remote.app.quit();
-});
-
-// Return to main menu button
-document.getElementById("mainmenu").addEventListener("click", () => {
- remote.getCurrentWindow().loadFile(__dirname + "/index.html");
-});
\ No newline at end of file
diff --git a/src/helpers/level.js b/src/helpers/level.js
index 2cbe0fb..c7f5041 100644
--- a/src/helpers/level.js
+++ b/src/helpers/level.js
@@ -1,8 +1,8 @@
var asdf = require("asdf-games");
// eslint-disable-next-line no-unused-vars
-const { Texture, TileMap, entity, Container } = asdf;
+const { Texture, TileMap, Container } = asdf;
-const texture = new Texture("./res/tilemap.png");
+const texture = new Texture(__dirname + "/../../res/images/tilemap.png");
const tiles = require("../../res/tilemap.js");
const tileSize = 32;
diff --git a/src/helpers/stats.js b/src/helpers/stats.js
index 25f1429..4d4c931 100644
--- a/src/helpers/stats.js
+++ b/src/helpers/stats.js
@@ -1,8 +1,10 @@
const { Container, TileSprite, Rect, Texture, Text } = require("asdf-games");
-const tilemapFrames = require("../../res/tilemap.js");
-const tilemap = new Texture("res/tilemap.png");
+const tilemapFrames = require("../../res/tilemap.js");
+const tilemap = new Texture("../res/images/tilemap.png");
const tileSize = 32;
+
+const text = require(__dirname + "/../../res/lang/default.js");
const fillStyle = {fill: "#ffffff", font: "24px Arial"};
class Stats extends Container {
@@ -14,7 +16,7 @@ class Stats extends Container {
const background = new Rect(640, 42, {fill: "rgba(0,0,0, 0.5)"});
background.pos = {x: 0, y: 280};
- const livesText = new Text("LIVES:", fillStyle);
+ const livesText = new Text(text.game.lives + ":", fillStyle);
livesText.pos = {x: 10, y: 310};
const livesCounter = new Text(player.lives, fillStyle);
@@ -24,7 +26,7 @@ class Stats extends Container {
heart.frame = {x: tilemapFrames[42].x / tileSize, y: tilemapFrames[42].y / tileSize};
heart.pos = {x: 104, y: 284};
- const staminaText = new Text("| STAMINA:", fillStyle);
+ const staminaText = new Text("| " + text.game.stamina + ":", fillStyle);
staminaText.pos = {x: 140, y: 310};
this.children = [
@@ -48,7 +50,6 @@ class Stats extends Container {
this.children[2].text = this.player.lives;
Array(5).fill().forEach((_val, index) => {
- //console.log(Math.round(this.player.stamina.current) - 1, index);
this.children[index + 5].frame =
(Math.round(this.player.stamina.current)) <= index
? {x: tilemapFrames[45].x / tileSize, y: tilemapFrames[45].y / tileSize}
diff --git a/src/index.js b/src/index.js
index b3f72f7..f1dcb9d 100644
--- a/src/index.js
+++ b/src/index.js
@@ -1,14 +1,69 @@
-const { remote } = require("electron");
+const { ipcRenderer, remote } = require("electron");
+var asdf = require("asdf-games");
+// eslint-disable-next-line no-unused-vars
+const { Game, KeyControls, MouseControls } = asdf;
-document.addEventListener("DOMContentLoaded", () => {
+const
+ Logo = require(__dirname + "/../src/screens/logo.js"),
+ Title = require(__dirname + "/../src/screens/title.js"),
+ Tutorial = require(__dirname + "/../src/screens/tutorial.js"),
+ GameScreen = require(__dirname + "/../src/screens/game.js"),
+ Gameover = require(__dirname + "/../src/screens/gameover.js")
+;
- // Start game
- document.getElementById("resume").addEventListener("click", () => {
- remote.getCurrentWindow().loadFile(__dirname + "/game.html");
+const window = { w: 640, h: 320 };
+
+const game = new Game(window.w, window.h, true);
+ipcRenderer.send("resize", window);
+
+const keys = new KeyControls();
+
+function titleScreen() {
+ game.scene = new Title(game, keys, newGame, tutorial, remote.app.quit);
+}
+
+function tutorial() {
+ game.scene = new Tutorial(game, keys, titleScreen);
+}
+
+function gameOver() {
+ game.scene = new Gameover(game, keys, titleScreen);
+}
+
+function newGame() {
+ game.scene = new GameScreen(game, window, keys, gameOver);
+}
+
+game.scene = new Logo(game, titleScreen);
+
+game.run();
+
+
+/* *********************************************************
+ Settings behavior
+********************************************************* */
+
+// Opening and closing of menu.
+function toggleMenu() {
+ const menuRef = document.getElementById("menu");
+ menuRef.style.display = menuRef.style.display === "block" ? "none" : "block";
+}
+
+const elements = [...document.querySelectorAll("#settings, #resume")];
+elements.forEach(element => {
+ element.addEventListener("click", () => {
+ toggleMenu();
});
+});
+
+// Return to main menu button
+document.getElementById("mainmenu").addEventListener("click", () => {
+ titleScreen();
+ toggleMenu();
+});
- // Quit game
- document.getElementById("quit").addEventListener("click", () => {
- remote.app.quit();
- });
-});
\ No newline at end of file
+// Quit Game handling.
+document.getElementById("close").addEventListener("click", () => {
+ remote.app.quit();
+});
+
diff --git a/src/levels/1-1 copy.js b/src/levels/1-1 copy.js
index 4d6fafe..6738bfc 100644
--- a/src/levels/1-1 copy.js
+++ b/src/levels/1-1 copy.js
@@ -1,6 +1,6 @@
const tileSize = 32;
-let level = {
+var level = {
tiles: [
1, 2, 2, 2, 2, 6, 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 5, 6,
4, 21, 22, 23, 21, 7, 0, 4, 22, 23, 21, 22, 23, 21, 22, 23, 21, 22, 23, 21, 22, 23, 21, 22, 23, 21, 22, 23, 21, 7,
@@ -47,7 +47,7 @@ let level = {
pos: { x: 8 * tileSize, y: 2 * tileSize },
texture: "Ladder",
action: (_player, level) => {
- level.switch = { module: "./src/levels/1-1.js", pos: 0 };
+ level.switch = { module: __dirname + "/1-1.js", pos: 0 };
},
key: "1-2_3"
}
diff --git a/src/levels/1-1.js b/src/levels/1-1.js
index ed935ba..5da8ad1 100644
--- a/src/levels/1-1.js
+++ b/src/levels/1-1.js
@@ -1,6 +1,6 @@
const tileSize = 32;
-let level = {
+var level = {
tiles: [
1, 2, 2, 2, 2, 6, 0, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 5, 6,
4, 21, 22, 23, 21, 7, 0, 4, 22, 23, 21, 22, 23, 21, 22, 23, 21, 22, 23, 21, 22, 23, 21, 22, 23, 21, 22, 23, 21, 7,
@@ -47,7 +47,7 @@ let level = {
pos: { x: 8 * tileSize, y: 2 * tileSize },
texture: "Ladder",
action: (_player, level) => {
- level.switch = { module: "./src/levels/1-1 copy.js", pos: 0 };
+ level.switch = { module: __dirname + "/1-1 copy.js", pos: 0 };
},
key: "1-1_1"
}
diff --git a/src/screens/game.js b/src/screens/game.js
new file mode 100644
index 0000000..c37e9d8
--- /dev/null
+++ b/src/screens/game.js
@@ -0,0 +1,110 @@
+const asdf = require("asdf-games");
+// eslint-disable-next-line no-unused-vars
+const { Container, Camera } = asdf;
+
+const debugMode = true;
+
+const Stats = require(__dirname + "/../helpers/stats.js");
+var Player = require(__dirname + "/../entities/player.js");
+var Level = require(__dirname + "/../helpers/level.js");
+
+class GameScreen extends Container {
+ constructor(game, window, keys, onGameOver) {
+ super();
+
+ this.window = window;
+ this.keys = keys;
+ this.onGameOver = onGameOver;
+
+ // Initialise first level 1-1.js at startPosition 0
+ var player = new Player(keys, window);
+
+ var level = new Level(require(__dirname + "/../levels/1-1.js"), keys, player);
+ player.pos.x = level.startPos[0].x / 1;
+ player.pos.y = level.startPos[0].y / 1;
+ player.level = level;
+
+ var camera = new Camera(player, window, { w: level.w * 2, h: level.h * 2 });
+ var stats = new Stats(player);
+
+ this.add(camera);
+ camera.add(level);
+ camera.add(player);
+ this.add(stats);
+
+ this.camera = camera;
+ this.player = player;
+ this.level = level;
+ this.stats = stats;
+ }
+
+ switchLevel(module, pos = 0) {
+ var { camera, player, level, stats, keys } = this;
+
+ camera.map(function(e) {
+ camera.remove(e);
+ if (e instanceof Level) {
+ var lives = player.lives;
+ var items = player.items;
+
+ var p = new Player(keys, window);
+ player = p;
+
+ e = new Level(module, keys, player);
+ level = e;
+
+ player.pos.x = level.startPos[pos].x / 1;
+ player.pos.y = level.startPos[pos].y / 1;
+
+ player.lives = lives;
+ player.items = items;
+ player.level = e;
+
+ stats.player = player;
+
+ camera.add(e);
+ camera.worldSize = { w: e.w, h: e.h };
+
+ camera.add(player);
+ camera.setSubject(player);
+ }
+ });
+
+ this.player = player;
+ this.level = level;
+ this.stats = stats;
+ this.camera = camera;
+ }
+
+ update(dt, t) {
+ super.update(dt, t);
+ var { camera, player, level, keys } = this;
+
+ // Debug options
+ if (debugMode && keys.ctrl && keys.key(66)) {
+ console.debug(level);
+ console.debug(player);
+ }
+
+ if (player.lives <= 0) {
+ this.onGameOver();
+ }
+
+ // Switch to another level
+ if (level.switch) {
+ if (debugMode) {
+ console.debug("Switching level!", level);
+ }
+ this.switchLevel(require(level.switch.module), level.switch.pos);
+ level.switch = undefined;
+ }
+
+ // Refocus camera to player when player is moved by a portal
+ if (player.refocus) {
+ camera.setSubject(player);
+ player.refocus = false;
+ }
+ }
+}
+
+module.exports = GameScreen;
\ No newline at end of file
diff --git a/src/screens/gameover.js b/src/screens/gameover.js
new file mode 100644
index 0000000..4bdc639
--- /dev/null
+++ b/src/screens/gameover.js
@@ -0,0 +1,36 @@
+const asdf = require("asdf-games");
+// eslint-disable-next-line no-unused-vars
+const { Texture, Text, Container, Sprite } = asdf;
+
+const text = require(__dirname + "/../../res/lang/default.js");
+const fillStyle = {fill: "#ffffff", font: "24px Arial"};
+
+class GameOver extends Container {
+ constructor(game, keys, onEnd) {
+ super();
+ this.game = game;
+ this.keys = keys;
+ this.onEnd = onEnd;
+
+ this.children = [];
+
+ var gameover = new Text(text.gameOver.dead, {fill: "#ffffff", font: "32px Arial"});
+ gameover.pos = { x: 200, y: 200 };
+ this.add(gameover);
+
+ var instruction = new Text(text.gameOver.instruction, fillStyle);
+ instruction.pos = { x: 200, y: 236 };
+ this.add(instruction);
+ }
+
+ update(dt, t) {
+ super.update(dt, t);
+
+ if (this.keys.action) {
+ this.onEnd();
+ }
+
+ }
+}
+
+module.exports = GameOver;
\ No newline at end of file
diff --git a/src/screens/logo.js b/src/screens/logo.js
new file mode 100644
index 0000000..b289d87
--- /dev/null
+++ b/src/screens/logo.js
@@ -0,0 +1,40 @@
+const asdf = require("asdf-games");
+// eslint-disable-next-line no-unused-vars
+const { Texture, Text, Container, Sprite } = asdf;
+
+const text = require(__dirname + "/../../res/lang/default.js");
+const fillStyle = {fill: "#ffffff", font: "24px Arial"};
+
+class Logo extends Container {
+ constructor(game, onEnd) {
+ super();
+ this.game = game;
+ this.onEnd = onEnd;
+
+ this.children = [];
+
+ const textPos = { x: 200, y: 150 };
+ for (let index = 0; index < text.logoScreen.length; index++) {
+ const element = new Text(text.logoScreen[index], fillStyle);
+ element.pos = {
+ x: textPos.x,
+ y: textPos.y + 24 * index
+ };
+ this.add(element);
+ }
+
+ this.lifetime = 2;
+ }
+
+ update(dt, t) {
+ super.update(dt, t);
+
+ if (this.lifetime <= 0) {
+ this.onEnd();
+ } else {
+ this.lifetime -= dt;
+ }
+ }
+}
+
+module.exports = Logo;
\ No newline at end of file
diff --git a/src/screens/title.js b/src/screens/title.js
new file mode 100644
index 0000000..b55fc96
--- /dev/null
+++ b/src/screens/title.js
@@ -0,0 +1,51 @@
+const asdf = require("asdf-games");
+// eslint-disable-next-line no-unused-vars
+const { Texture, Container, Sprite, Text } = asdf;
+
+const text = require(__dirname + "/../../res/lang/default.js");
+const fillStyle = {fill: "#ffffff", font: "24px Arial"};
+
+class Title extends Container {
+ constructor(game, keys, onStart, onTutorial, onQuit) {
+ super();
+ this.game = game;
+ this.keys = keys;
+
+ this.onStart = onStart;
+ this.onTutorial = onTutorial;
+ this.onQuit = onQuit;
+
+ this.keys.reset();
+
+ this.children = [];
+
+ const textPos = { x: 200, y: 200 };
+ for (let index = 0; index < text.titleScreen.instructions.length; index++) {
+ const element = new Text(text.titleScreen.instructions[index], fillStyle);
+ element.pos = {
+ x: textPos.x,
+ y: textPos.y + 28 * index
+ };
+ this.add(element);
+ }
+ }
+
+ update(dt, t) {
+ super.update(dt, t);
+
+ if (this.keys.action) {
+ this.onStart();
+ }
+
+ if (this.keys.key(84)) {
+ this.onTutorial();
+ }
+
+ if (this.keys.key(81)) {
+ this.onQuit();
+ }
+
+ }
+}
+
+module.exports = Title;
\ No newline at end of file
diff --git a/src/screens/tutorial.js b/src/screens/tutorial.js
new file mode 100644
index 0000000..74e300c
--- /dev/null
+++ b/src/screens/tutorial.js
@@ -0,0 +1,38 @@
+const asdf = require("asdf-games");
+// eslint-disable-next-line no-unused-vars
+const { Texture, Container, Text, Sprite } = asdf;
+
+const text = require(__dirname + "/../../res/lang/default.js");
+const fillStyle = {fill: "#ffffff", font: "20px Arial"};
+
+class Tutorial extends Container {
+ constructor(game, keys, onEnd) {
+ super();
+ this.game = game;
+ this.keys = keys;
+ this.onEnd = onEnd;
+
+ this.children = [];
+
+ const textPos = { x: 50, y: 150 };
+ for (let index = 0; index < text.tutorial.length; index++) {
+ const element = new Text(text.tutorial[index], fillStyle);
+ element.pos = {
+ x: textPos.x,
+ y: textPos.y + 24 * index
+ };
+ this.add(element);
+ }
+ }
+
+ update(dt, t) {
+ super.update(dt, t);
+
+ if (this.keys.action) {
+ this.onEnd();
+ }
+
+ }
+}
+
+module.exports = Tutorial;
\ No newline at end of file