diff --git a/html/main.html b/html/main.html
index 47c27a4..1a31d67 100644
--- a/html/main.html
+++ b/html/main.html
@@ -32,7 +32,103 @@
+
defiance v0.12.1
diff --git a/js/script.js b/js/script.js
index 7056cb3..e253dd2 100644
--- a/js/script.js
+++ b/js/script.js
@@ -12,7 +12,6 @@ document.addEventListener('DOMContentLoaded', () => {
DESERT: { acceptStructure:true,movements:['walk','ride','fly'],affinities:[('sand',0.8),('life',0.1),('fire',0.1)], name: 'Désert', winterColor: '#D4A373', fallColor: '#D4A373', summerColor: '#D4A373', autumnColor: '#D4A373',maxElevation:2,minElevation:2 },
RIVER: { acceptStructure:false,movements:['navigate','swim','fly'],affinities:[('water',0.6),('earth',0.2),('life',0.2)],name: 'Rivière', winterColor: '#97aabdff', fallColor: '#5A8AB8', summerColor: '#5A8AB8', autumnColor: '#5A8AB8',maxElevation:2,minElevation:2 },
SWAMP: { acceptStructure:false, movements:['fly'],affinities:[('water',0.6),('earth',0.2),('dark',0.2)],name: 'Marais', winterColor: '#0b2e10ff', fallColor: '#0b2e10ff', summerColor: '#0b2e10ff', autumnColor: '#0b2e10ff',maxElevation:1,minElevation:1 }
-
}
const NAME_PREFIXES = ["Chêne", "Sombre", "Pierre", "Haut", "Val", "Mur", "Guet", "Clair"];
const NAME_SUFFIXES = ["bourg", "fort", "ville", "mont", "port", "bois", "rivage", "gard"];
@@ -115,6 +114,8 @@ document.addEventListener('DOMContentLoaded', () => {
this.setElevation();
this.setStructure();
//this.setDesign(ctx);
+ //this.forestSvg=null;
+ //this.setSvg();
}
// Méthode de l'objet
@@ -134,47 +135,51 @@ document.addEventListener('DOMContentLoaded', () => {
else this.biome = Biome.GRASSLAND;
}
}
- setDesign(ctx){
+ setDesign(ctx,currentTime){
if (!this.biome) return;
const screenPos = this.position.cartToIso();
const elevationHeight = this.position.h * 8;
-
+ let baseColor=null;
ctx.save();
ctx.translate(screenPos.x, screenPos.y - elevationHeight);
- const baseColor = this.biome.summerColor;
+ if (currentTime.season == 'winter') { baseColor = this.biome.winterColor;}
+ if (currentTime.season == 'summer') { baseColor = this.biome.summerColor;}
+ if (currentTime.season == 'fall') { baseColor = this.biome.fallColor;}
+ if (currentTime.season == 'autumn') { baseColor = this.biome.autumnColor;}
const shadowColor = shadeColor(baseColor, -30);
+
+ // Right Face
ctx.fillStyle = shadowColor;
ctx.beginPath();
ctx.moveTo(0, 32); ctx.lineTo(32, 16); ctx.lineTo(32, 16 + elevationHeight); ctx.lineTo(0, 32 + elevationHeight);
ctx.closePath();
ctx.fill();
+
+ // Left Face
ctx.fillStyle = shadeColor(shadowColor, -10);
ctx.beginPath();
ctx.moveTo(0, 32); ctx.lineTo(-32, 16); ctx.lineTo(-32, 16 + elevationHeight); ctx.lineTo(0, 32 + elevationHeight);
ctx.closePath();
ctx.fill();
+
+ // Top Face
+ if (this.biome==Biome.FOREST && forestSVG.complete) {
+ ctx.drawImage(forestSVG, -20, -16, 40, 48);
+ } else { // Fallback to circle
+ ctx.fillStyle = this.shadowColor; ctx.beginPath(); ctx.arc(0, TILE_HEIGHT / 2 - 6, 8, 0, Math.PI * 2); ctx.fill();
+ }
ctx.fillStyle = baseColor;
ctx.beginPath();
ctx.moveTo(0, 0); ctx.lineTo(32, 16); ctx.lineTo(0, 32); ctx.lineTo(-32, 16);
ctx.closePath();
ctx.fill();
- if (this.structure && this.structure.type === 'village') {
- ctx.fillStyle = '#D4A373';
- ctx.fillRect(-8, -12, 16, 12);
- ctx.fillStyle = '#8B4513';
- ctx.beginPath();
- ctx.moveTo(0, -22); ctx.lineTo(-10, -12); ctx.lineTo(10, -12);
- ctx.closePath();
- ctx.fill();
- } else if (this.structure && this.structure.type === 'city') {
- ctx.fillStyle = '#C0C0C0';
- ctx.fillRect(-10, -20, 20, 20);
- ctx.fillStyle = '#808080';
- ctx.beginPath();
- ctx.moveTo(-10, -20); ctx.lineTo(-12, -22); ctx.lineTo(22, -22); ctx.lineTo(20, -20);
- ctx.closePath();
- ctx.fill();
+ if (this.structure) {
+ if (this.structure.type === 'village' && villageSVG) {
+ ctx.drawImage(villageSVG, -20, -16, 40, 40);
+ } else if (this.structure.type === 'city' && citySVG) {
+ ctx.drawImage(citySVG, -24, -28, 48, 48);
+ }
}
ctx.restore();
}
@@ -330,14 +335,32 @@ document.addEventListener('DOMContentLoaded', () => {
}
class Player {
- constructor(creature,equipments) {
+ constructor(creature,equipments,playerImage) {
this.creature=creature;
this.equipments=equipments;
this.color = '#E53E3E';
+ this.playerImage = playerImage ;
+ //this.setSvg();
}
get position() {
return this.creature.tile.position;
}
+ setSvg(){
+ const svgString = `
`;
+ const svgBase64 = "data:image/svg+xml;base64," + btoa(svgString);
+
+ this.playerImage = new Image();
+ this.playerImage.src = svgBase64;
+ this.playerImage.onload = () => {
+ console.log("Player SVG loaded");
+ loadingScreen.style.display = 'none';
+ };
+ this.playerImage.onerror = () => {
+ console.error("Failed to load player SVG");
+ loadingScreen.style.display = 'none';
+ };
+ }
+
setDesign(ctx) {
const tile = this.creature.tile
if(!tile) return;
@@ -347,9 +370,12 @@ document.addEventListener('DOMContentLoaded', () => {
ctx.save();
ctx.translate(screenPos.x, screenPos.y - elevationHeight);
- ctx.fillStyle = 'rgba(0, 0, 0, 0.4)'; ctx.beginPath(); ctx.ellipse(0, TILE_HEIGHT / 2 + 2, 6, 3, 0, 0, Math.PI * 2); ctx.fill();
- ctx.fillStyle = this.color; ctx.beginPath(); ctx.arc(0, TILE_HEIGHT / 2 - 6, 8, 0, Math.PI * 2); ctx.fill();
- ctx.strokeStyle = shadeColor(this.color, -30); ctx.lineWidth = 2; ctx.stroke();
+
+ if (this.playerImage && this.playerImage.complete) {
+ ctx.drawImage(this.playerImage, -25, -50, 50, 60);
+ } else { // Fallback to circle
+ ctx.fillStyle = this.color; ctx.beginPath(); ctx.arc(0, TILE_HEIGHT / 2 - 6, 8, 0, Math.PI * 2); ctx.fill();
+ }
ctx.restore();
}
move(dx, dy, gameMap) {
@@ -469,12 +495,6 @@ document.addEventListener('DOMContentLoaded', () => {
constructor(name) {
this.name = name;
this.map = new Map(200)
- let spawnX, spawnY;
- do {
- spawnX = Math.floor(Math.random() * this.map.size);
- spawnY = Math.floor(Math.random() * this.map.size);
- } while (!this.map.tiles[spawnY][spawnX].biome || !this.map.tiles[spawnY][spawnX].biome.movements.includes('walk') );
- this.player = new Player(new Creature('player',new Attributes(RACE.HUMAN),1,null,null,this.map.tiles[spawnY][spawnX],'human',RACE.HUMAN,10,null),null);
this.currentTime=new Time();
}
// Méthode de l'objet
@@ -506,14 +526,24 @@ document.addEventListener('DOMContentLoaded', () => {
this.camera = new Camera(0,0, canvas);
this.setControls();
this.loop = this.loop.bind(this);
+ this.player=null;
+ this.setInitial();
}
// Méthode de l'objet
loop(currentTime) {
this.handleMovement(currentTime);
- this.camera.setCamera(this.world.player.position);
+ this.camera.setCamera(this.player.position);
this.setDesign();
requestAnimationFrame(this.loop);
}
+ setInitial(){
+ let spawnX, spawnY;
+ do {
+ spawnX = Math.floor(Math.random() * this.world.map.size);
+ spawnY = Math.floor(Math.random() * this.world.map.size);
+ } while (!this.world.map.tiles[spawnY][spawnX].biome || !this.world.map.tiles[spawnY][spawnX].biome.movements.includes('walk') );
+ this.player = new Player(new Creature('player',new Attributes(RACE.HUMAN),1,null,null,this.world.map.tiles[spawnY][spawnX],'human',RACE.HUMAN,10,null),);
+ }
setControls() {
document.addEventListener('keydown', e => {
const key = e.key.toLowerCase();
@@ -544,8 +574,8 @@ document.addEventListener('DOMContentLoaded', () => {
ctx.save();
ctx.translate(this.camera.x, this.camera.y);
- for (let y = 0; y < this.world.map.size; y++) for (let x = 0; x < this.world.map.size; x++) this.world.map.tiles[y][x].setDesign(ctx);
- this.world.player.setDesign(ctx);
+ for (let y = 0; y < this.world.map.size; y++) for (let x = 0; x < this.world.map.size; x++) this.world.map.tiles[y][x].setDesign(ctx,this.world.currentTime);
+ this.player.setDesign(ctx);
this.world.currentTime.setDesign(ctx);
ctx.fillRect(this.camera.x * -1, this.camera.y * -1, canvas.width, canvas.height);
ctx.globalAlpha = 1.0;
@@ -557,10 +587,10 @@ document.addEventListener('DOMContentLoaded', () => {
handleMovement(currentTime) {
if (currentTime - lastMoveTime < 150) return;
let moved = false;
- if (controls.up) { this.world.player.move(0, -1,this.world.map); moved = true; }
- if (controls.down) { this.world.player.move(0, 1,this.world.map); moved = true; }
- if (controls.left) { this.world.player.move(-1, 0,this.world.map); moved = true; }
- if (controls.right) { this.world.player.move(1, 0,this.world.map); moved = true; }
+ if (controls.up) { this.player.move(0, -1,this.world.map); moved = true; }
+ if (controls.down) { this.player.move(0, 1,this.world.map); moved = true; }
+ if (controls.left) { this.player.move(-1, 0,this.world.map); moved = true; }
+ if (controls.right) { this.player.move(1, 0,this.world.map); moved = true; }
if(moved) lastMoveTime = currentTime;
}
}
@@ -577,28 +607,81 @@ document.addEventListener('DOMContentLoaded', () => {
const TILE_WIDTH = 64;
const TILE_HEIGHT = 32;
const ELEVATION_STEP = TILE_HEIGHT / 4;
-
+ let forestSVG, villageSVG, citySVG, playerSVG;
function seededRandom(seed) {
let s = seed;
return () => { s = (s * 9301 + 49297) % 233280; return s / 233280.0; };
}
-
-
+ function loadSvgAsImage(gElement) {
+ return new Promise((resolve, reject) => {
+ if (!gElement) {
+ return reject(new Error("SVG
element not found."));
+ }
+
+ const viewBox = gElement.getAttribute('viewBox') || '0 0 100 100';
+
+ // Create a new, standalone