Compare commits
2 Commits
64118090d6
...
ff462fb53c
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ff462fb53c | ||
|
|
ad487e766c |
26
index.html
26
index.html
@@ -1,13 +1,17 @@
|
||||
<!doctype html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<link rel="icon" type="image/png" href="/favicon.png" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>rogue</title>
|
||||
</head>
|
||||
<body>
|
||||
<div id="app"></div>
|
||||
<script type="module" src="/src/main.ts"></script>
|
||||
</body>
|
||||
</html>
|
||||
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<link rel="icon" type="image/png" href="/favicon.png" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<link rel="stylesheet" href="/src/style.css" />
|
||||
<title>rogue</title>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<div id="app"></div>
|
||||
<script type="module" src="/src/main.ts"></script>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
@@ -6,8 +6,11 @@ import { StartScene } from "./scenes/StartScene";
|
||||
new Phaser.Game({
|
||||
type: Phaser.AUTO,
|
||||
parent: "app",
|
||||
width: 960,
|
||||
height: 540,
|
||||
scale: {
|
||||
mode: Phaser.Scale.RESIZE,
|
||||
width: window.innerWidth,
|
||||
height: window.innerHeight,
|
||||
},
|
||||
backgroundColor: "#111",
|
||||
pixelArt: true,
|
||||
roundPixels: true,
|
||||
|
||||
@@ -17,9 +17,31 @@ export class DungeonRenderer {
|
||||
// State refs
|
||||
private world!: World;
|
||||
|
||||
// Minimap
|
||||
private minimapGfx!: Phaser.GameObjects.Graphics;
|
||||
private minimapContainer!: Phaser.GameObjects.Container;
|
||||
private minimapBg!: Phaser.GameObjects.Graphics;
|
||||
private minimapScale = 2; // pixels per tile
|
||||
private minimapPadding = 8;
|
||||
|
||||
constructor(scene: Phaser.Scene) {
|
||||
this.scene = scene;
|
||||
this.gfx = this.scene.add.graphics();
|
||||
|
||||
// Initialize minimap
|
||||
this.initMinimap();
|
||||
}
|
||||
|
||||
private initMinimap() {
|
||||
this.minimapContainer = this.scene.add.container(0, 0);
|
||||
this.minimapContainer.setScrollFactor(0); // Fixed to camera
|
||||
this.minimapContainer.setDepth(100);
|
||||
|
||||
this.minimapBg = this.scene.add.graphics();
|
||||
this.minimapGfx = this.scene.add.graphics();
|
||||
|
||||
this.minimapContainer.add(this.minimapBg);
|
||||
this.minimapContainer.add(this.minimapGfx);
|
||||
}
|
||||
|
||||
initializeLevel(world: World) {
|
||||
@@ -32,6 +54,21 @@ export class DungeonRenderer {
|
||||
if (!inBounds(this.world, x, y)) return false;
|
||||
return !isWall(this.world, x, y);
|
||||
});
|
||||
|
||||
// Position minimap
|
||||
this.positionMinimap();
|
||||
}
|
||||
|
||||
private positionMinimap() {
|
||||
const cam = this.scene.cameras.main;
|
||||
const minimapWidth = this.world.width * this.minimapScale + this.minimapPadding * 2;
|
||||
const minimapHeight = this.world.height * this.minimapScale + this.minimapPadding * 2;
|
||||
|
||||
// Position in bottom right corner (accounting for zoom)
|
||||
const x = cam.width / cam.zoom - minimapWidth - 10;
|
||||
const y = cam.height / cam.zoom - minimapHeight - 10;
|
||||
|
||||
this.minimapContainer.setPosition(x, y);
|
||||
}
|
||||
|
||||
computeFov(playerId: EntityId) {
|
||||
@@ -135,6 +172,90 @@ export class DungeonRenderer {
|
||||
this.gfx.fillStyle(color, 1);
|
||||
this.gfx.fillRect(a.pos.x * TILE_SIZE + 4, a.pos.y * TILE_SIZE + 4, TILE_SIZE - 8, TILE_SIZE - 8);
|
||||
}
|
||||
|
||||
// Render minimap
|
||||
this.renderMinimap();
|
||||
}
|
||||
|
||||
private renderMinimap() {
|
||||
this.minimapBg.clear();
|
||||
this.minimapGfx.clear();
|
||||
|
||||
if (!this.world) return;
|
||||
|
||||
const minimapWidth = this.world.width * this.minimapScale + this.minimapPadding * 2;
|
||||
const minimapHeight = this.world.height * this.minimapScale + this.minimapPadding * 2;
|
||||
|
||||
// Background
|
||||
this.minimapBg.fillStyle(0x000000, 0.7);
|
||||
this.minimapBg.fillRect(0, 0, minimapWidth, minimapHeight);
|
||||
|
||||
// Border
|
||||
this.minimapBg.lineStyle(1, 0x666666, 1);
|
||||
this.minimapBg.strokeRect(0, 0, minimapWidth, minimapHeight);
|
||||
|
||||
// Draw only seen tiles
|
||||
for (let y = 0; y < this.world.height; y++) {
|
||||
for (let x = 0; x < this.world.width; x++) {
|
||||
const i = idx(this.world, x, y);
|
||||
const isSeen = this.seen[i] === 1;
|
||||
|
||||
if (!isSeen) continue;
|
||||
|
||||
const wall = isWall(this.world, x, y);
|
||||
const color = wall ? 0x666666 : 0x333333;
|
||||
|
||||
this.minimapGfx.fillStyle(color, 1);
|
||||
this.minimapGfx.fillRect(
|
||||
this.minimapPadding + x * this.minimapScale,
|
||||
this.minimapPadding + y * this.minimapScale,
|
||||
this.minimapScale,
|
||||
this.minimapScale
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// Draw exit if seen
|
||||
const ex = this.world.exit.x;
|
||||
const ey = this.world.exit.y;
|
||||
const exitIdx = idx(this.world, ex, ey);
|
||||
if (this.seen[exitIdx] === 1) {
|
||||
this.minimapGfx.fillStyle(0xffd166, 1);
|
||||
this.minimapGfx.fillRect(
|
||||
this.minimapPadding + ex * this.minimapScale,
|
||||
this.minimapPadding + ey * this.minimapScale,
|
||||
this.minimapScale,
|
||||
this.minimapScale
|
||||
);
|
||||
}
|
||||
|
||||
// Draw player
|
||||
const player = [...this.world.actors.values()].find(a => a.isPlayer);
|
||||
if (player) {
|
||||
this.minimapGfx.fillStyle(0x66ff66, 1);
|
||||
this.minimapGfx.fillRect(
|
||||
this.minimapPadding + player.pos.x * this.minimapScale,
|
||||
this.minimapPadding + player.pos.y * this.minimapScale,
|
||||
this.minimapScale,
|
||||
this.minimapScale
|
||||
);
|
||||
}
|
||||
|
||||
// Draw visible enemies
|
||||
for (const a of this.world.actors.values()) {
|
||||
if (a.isPlayer) continue;
|
||||
const i = idx(this.world, a.pos.x, a.pos.y);
|
||||
const isVis = this.visible[i] === 1;
|
||||
if (!isVis) continue;
|
||||
|
||||
this.minimapGfx.fillStyle(0xff6666, 1);
|
||||
this.minimapGfx.fillRect(
|
||||
this.minimapPadding + a.pos.x * this.minimapScale,
|
||||
this.minimapPadding + a.pos.y * this.minimapScale,
|
||||
this.minimapScale,
|
||||
this.minimapScale
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
showDamage(x: number, y: number, amount: number) {
|
||||
|
||||
@@ -16,7 +16,13 @@ export class SplashScene extends Scene {
|
||||
// Background (Placeholder for Image)
|
||||
// If we successfully load the image 'splash', we use it.
|
||||
if (this.textures.exists('splash')) {
|
||||
this.add.image(width / 2, height / 2, 'splash').setDisplaySize(width, height);
|
||||
const splash = this.add.image(width / 2, height / 2, 'splash');
|
||||
|
||||
// Scale to cover the screen while maintaining aspect ratio
|
||||
const scaleX = width / splash.width;
|
||||
const scaleY = height / splash.height;
|
||||
const scale = Math.max(scaleX, scaleY);
|
||||
splash.setScale(scale);
|
||||
} else {
|
||||
this.add.rectangle(0, 0, width, height, 0x110022).setOrigin(0);
|
||||
this.add.text(width/2, height/2, "ROGUE LEGACY", {
|
||||
|
||||
24
src/style.css
Normal file
24
src/style.css
Normal file
@@ -0,0 +1,24 @@
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
html, body {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
#app {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
background: #111;
|
||||
}
|
||||
|
||||
canvas {
|
||||
display: block;
|
||||
}
|
||||
Reference in New Issue
Block a user