AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA PENAT
This commit is contained in:
parent
decb897401
commit
88bfd9bd04
205
Script.js
205
Script.js
@ -191,8 +191,8 @@ function preRenderAssets() {
|
|||||||
mCtx.fillStyle = mg;
|
mCtx.fillStyle = mg;
|
||||||
mCtx.beginPath();
|
mCtx.beginPath();
|
||||||
mCtx.moveTo(mPad, mPad);
|
mCtx.moveTo(mPad, mPad);
|
||||||
mCtx.lineTo(mPad + 30, mPad + 6);
|
mCtx.lineTo(mPad + 30, mPad + 6);
|
||||||
mCtx.lineTo(mPad, mPad + 12);
|
mCtx.lineTo(mPad, mPad + 12);
|
||||||
mCtx.fill();
|
mCtx.fill();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -201,7 +201,7 @@ window.onload = function () {
|
|||||||
};
|
};
|
||||||
|
|
||||||
function init() {
|
function init() {
|
||||||
preRenderAssets();
|
preRenderAssets();
|
||||||
c = document.getElementById("canvas");
|
c = document.getElementById("canvas");
|
||||||
|
|
||||||
ctx = c.getContext("2d", { alpha: false });
|
ctx = c.getContext("2d", { alpha: false });
|
||||||
@ -633,7 +633,7 @@ function drawUI() {
|
|||||||
drawNewText(game.level, canvasWidth - 140, 50, "#00ff00", "30px");
|
drawNewText(game.level, canvasWidth - 140, 50, "#00ff00", "30px");
|
||||||
|
|
||||||
// Lives (Stacked Icons)
|
// Lives (Stacked Icons)
|
||||||
const lifeSize = 40;
|
const lifeSize = 40;
|
||||||
const lifePadding = 5;
|
const lifePadding = 5;
|
||||||
|
|
||||||
if (livesImg.complete) {
|
if (livesImg.complete) {
|
||||||
@ -837,7 +837,7 @@ class backgroundObj {
|
|||||||
this.height = 900;
|
this.height = 900;
|
||||||
this.img = img;
|
this.img = img;
|
||||||
this.img = img;
|
this.img = img;
|
||||||
this.factor = speed;
|
this.factor = speed;
|
||||||
}
|
}
|
||||||
draw() {
|
draw() {
|
||||||
ctx.save();
|
ctx.save();
|
||||||
@ -1172,7 +1172,7 @@ class AbilityToken {
|
|||||||
constructor(x, y) {
|
constructor(x, y) {
|
||||||
this.x = x;
|
this.x = x;
|
||||||
this.y = y;
|
this.y = y;
|
||||||
this.width = 40;
|
this.width = 40;
|
||||||
this.height = 40;
|
this.height = 40;
|
||||||
this.speed = 4;
|
this.speed = 4;
|
||||||
let r = Math.random();
|
let r = Math.random();
|
||||||
@ -1355,24 +1355,133 @@ class Explosion {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function drawGameOver() {
|
function drawGameOver() {
|
||||||
ctx.fillStyle = "rgba(53, 0, 0, 0.7)";
|
// Dark overlay with gradient
|
||||||
|
const gradient = ctx.createRadialGradient(
|
||||||
|
canvasWidth / 2,
|
||||||
|
canvasHeight / 2,
|
||||||
|
0,
|
||||||
|
canvasWidth / 2,
|
||||||
|
canvasHeight / 2,
|
||||||
|
canvasWidth / 1.5
|
||||||
|
);
|
||||||
|
gradient.addColorStop(0, "rgba(10, 0, 0, 0.85)");
|
||||||
|
gradient.addColorStop(0.5, "rgba(30, 0, 10, 0.92)");
|
||||||
|
gradient.addColorStop(1, "rgba(0, 0, 0, 0.97)");
|
||||||
|
ctx.fillStyle = gradient;
|
||||||
ctx.fillRect(0, 0, canvasWidth, canvasHeight);
|
ctx.fillRect(0, 0, canvasWidth, canvasHeight);
|
||||||
|
|
||||||
ctx.font = "80px Arial";
|
// Animated pulsing effect
|
||||||
ctx.fillStyle = "red";
|
const pulseTime = Date.now() / 1000;
|
||||||
|
const pulse = Math.sin(pulseTime * 2) * 0.15 + 0.85;
|
||||||
|
|
||||||
|
ctx.save();
|
||||||
ctx.textAlign = "center";
|
ctx.textAlign = "center";
|
||||||
ctx.fillText("GAME OVER", canvasWidth / 2, canvasHeight / 2 - 50);
|
|
||||||
|
|
||||||
ctx.font = "40px Arial";
|
// "GAME OVER" main title with glowing effect
|
||||||
ctx.fillStyle = "white";
|
ctx.font = "900 100px Orbitron, Arial";
|
||||||
ctx.fillText(
|
|
||||||
"Final Score: " + player1.score,
|
// Outer glow layers
|
||||||
canvasWidth / 2,
|
for (let i = 30; i > 0; i -= 3) {
|
||||||
canvasHeight / 2 + 20
|
ctx.shadowColor = `rgba(255, 50, 50, ${(30 - i) / 100})`;
|
||||||
|
ctx.shadowBlur = i;
|
||||||
|
ctx.fillStyle = `rgba(255, 0, 0, ${(30 - i) / 100})`;
|
||||||
|
ctx.fillText("GAME OVER", canvasWidth / 2, canvasHeight / 2 - 120);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Main title gradient
|
||||||
|
const titleGradient = ctx.createLinearGradient(
|
||||||
|
canvasWidth / 2 - 300,
|
||||||
|
0,
|
||||||
|
canvasWidth / 2 + 300,
|
||||||
|
0
|
||||||
);
|
);
|
||||||
ctx.fillText("Refresh to Restart", canvasWidth / 2, canvasHeight / 2 + 70);
|
titleGradient.addColorStop(0, "#ff0033");
|
||||||
|
titleGradient.addColorStop(0.5, "#ff3366");
|
||||||
|
titleGradient.addColorStop(1, "#ff0033");
|
||||||
|
|
||||||
ctx.textAlign = "left";
|
ctx.shadowColor = "rgba(255, 51, 102, 0.8)";
|
||||||
|
ctx.shadowBlur = 40 * pulse;
|
||||||
|
ctx.fillStyle = titleGradient;
|
||||||
|
ctx.fillText("GAME OVER", canvasWidth / 2, canvasHeight / 2 - 120);
|
||||||
|
|
||||||
|
// Reset shadow
|
||||||
|
ctx.shadowBlur = 0;
|
||||||
|
|
||||||
|
// Statistics panel background
|
||||||
|
const panelY = canvasHeight / 2 - 20;
|
||||||
|
const panelWidth = 500;
|
||||||
|
const panelHeight = 200;
|
||||||
|
const panelX = canvasWidth / 2 - panelWidth / 2;
|
||||||
|
|
||||||
|
// Panel border glow
|
||||||
|
ctx.strokeStyle = "rgba(0, 234, 255, 0.6)";
|
||||||
|
ctx.lineWidth = 3;
|
||||||
|
ctx.shadowColor = "rgba(0, 234, 255, 0.8)";
|
||||||
|
ctx.shadowBlur = 20;
|
||||||
|
ctx.strokeRect(panelX, panelY, panelWidth, panelHeight);
|
||||||
|
|
||||||
|
// Panel background
|
||||||
|
const panelGradient = ctx.createLinearGradient(
|
||||||
|
panelX,
|
||||||
|
panelY,
|
||||||
|
panelX,
|
||||||
|
panelY + panelHeight
|
||||||
|
);
|
||||||
|
panelGradient.addColorStop(0, "rgba(10, 10, 30, 0.85)");
|
||||||
|
panelGradient.addColorStop(1, "rgba(20, 20, 40, 0.9)");
|
||||||
|
ctx.fillStyle = panelGradient;
|
||||||
|
ctx.fillRect(panelX, panelY, panelWidth, panelHeight);
|
||||||
|
|
||||||
|
ctx.shadowBlur = 0;
|
||||||
|
|
||||||
|
// Statistics text - centered
|
||||||
|
ctx.textAlign = "center";
|
||||||
|
|
||||||
|
// "Your score:" label
|
||||||
|
ctx.font = "700 28px Orbitron, Arial";
|
||||||
|
ctx.fillStyle = "#00eaff";
|
||||||
|
ctx.fillText("Your score:", canvasWidth / 2, panelY + 70);
|
||||||
|
|
||||||
|
// Score value
|
||||||
|
ctx.font = "900 64px Orbitron, Arial";
|
||||||
|
ctx.shadowColor = "rgba(255, 255, 255, 0.5)";
|
||||||
|
ctx.shadowBlur = 15;
|
||||||
|
ctx.fillStyle = "#ffffff";
|
||||||
|
ctx.fillText(player1.score.toString(), canvasWidth / 2, panelY + 145);
|
||||||
|
ctx.shadowBlur = 0;
|
||||||
|
|
||||||
|
// Restart instruction with pulsing effect
|
||||||
|
ctx.textAlign = "center";
|
||||||
|
ctx.font = "700 28px Orbitron, Arial";
|
||||||
|
const instructionAlpha = Math.sin(pulseTime * 3) * 0.3 + 0.7;
|
||||||
|
ctx.fillStyle = `rgba(0, 234, 255, ${instructionAlpha})`;
|
||||||
|
ctx.shadowColor = "rgba(0, 234, 255, 0.6)";
|
||||||
|
ctx.shadowBlur = 15 * pulse;
|
||||||
|
ctx.fillText("PRESS F5 TO RESTART", canvasWidth / 2, panelY + panelHeight + 60);
|
||||||
|
|
||||||
|
// Additional decorative elements
|
||||||
|
ctx.shadowBlur = 0;
|
||||||
|
|
||||||
|
// Corner decorations (top-left and bottom-right)
|
||||||
|
const cornerSize = 40;
|
||||||
|
ctx.strokeStyle = "rgba(255, 51, 102, 0.5)";
|
||||||
|
ctx.lineWidth = 3;
|
||||||
|
|
||||||
|
// Top-left corner
|
||||||
|
ctx.beginPath();
|
||||||
|
ctx.moveTo(panelX - 10, panelY - 10 + cornerSize);
|
||||||
|
ctx.lineTo(panelX - 10, panelY - 10);
|
||||||
|
ctx.lineTo(panelX - 10 + cornerSize, panelY - 10);
|
||||||
|
ctx.stroke();
|
||||||
|
|
||||||
|
// Bottom-right corner
|
||||||
|
ctx.beginPath();
|
||||||
|
ctx.moveTo(panelX + panelWidth + 10, panelY + panelHeight + 10 - cornerSize);
|
||||||
|
ctx.lineTo(panelX + panelWidth + 10, panelY + panelHeight + 10);
|
||||||
|
ctx.lineTo(panelX + panelWidth + 10 - cornerSize, panelY + panelHeight + 10);
|
||||||
|
ctx.stroke();
|
||||||
|
|
||||||
|
ctx.restore();
|
||||||
}
|
}
|
||||||
|
|
||||||
function drawPauseOverlay() {
|
function drawPauseOverlay() {
|
||||||
@ -1423,7 +1532,7 @@ function drawScreenShading() {
|
|||||||
let intensity = (game.surge - 1.0) / (7.0 - 1.0);
|
let intensity = (game.surge - 1.0) / (7.0 - 1.0);
|
||||||
if (intensity > 0) {
|
if (intensity > 0) {
|
||||||
ctx.save();
|
ctx.save();
|
||||||
ctx.globalCompositeOperation = "hard-light";
|
ctx.globalCompositeOperation = "hard-light";
|
||||||
ctx.fillStyle = "white";
|
ctx.fillStyle = "white";
|
||||||
ctx.globalAlpha = intensity * 0.4;
|
ctx.globalAlpha = intensity * 0.4;
|
||||||
ctx.fillRect(0, 0, canvasWidth, canvasHeight);
|
ctx.fillRect(0, 0, canvasWidth, canvasHeight);
|
||||||
@ -1433,8 +1542,8 @@ function drawScreenShading() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function updateSurge() {
|
function updateSurge() {
|
||||||
const RAMP_UP_FRAMES = 240;
|
const RAMP_UP_FRAMES = 240;
|
||||||
const HOLD_FRAMES = 780;
|
const HOLD_FRAMES = 780;
|
||||||
const RAMP_DOWN_FRAMES = 300;
|
const RAMP_DOWN_FRAMES = 300;
|
||||||
const MAX_SURGE_SPEED = 7.0;
|
const MAX_SURGE_SPEED = 7.0;
|
||||||
|
|
||||||
@ -1549,14 +1658,14 @@ window.addEventListener('DOMContentLoaded', () => {
|
|||||||
// === START BUTTON ===
|
// === START BUTTON ===
|
||||||
startBtn.addEventListener('click', () => {
|
startBtn.addEventListener('click', () => {
|
||||||
playSound(menuClickSound);
|
playSound(menuClickSound);
|
||||||
|
|
||||||
// Apply settings to game
|
// Apply settings to game
|
||||||
applySettings();
|
applySettings();
|
||||||
|
|
||||||
// Hide menu, show game
|
// Hide menu, show game
|
||||||
mainMenu.style.display = 'none';
|
mainMenu.style.display = 'none';
|
||||||
gameContainer.style.display = 'block';
|
gameContainer.style.display = 'block';
|
||||||
|
|
||||||
// Start the game
|
// Start the game
|
||||||
if (!gameStarted) {
|
if (!gameStarted) {
|
||||||
init();
|
init();
|
||||||
@ -1573,7 +1682,7 @@ optionBtn.addEventListener('click', () => {
|
|||||||
// === EXIT BUTTON ===
|
// === EXIT BUTTON ===
|
||||||
exitBtn.addEventListener('click', () => {
|
exitBtn.addEventListener('click', () => {
|
||||||
playSound(menuClickSound);
|
playSound(menuClickSound);
|
||||||
|
|
||||||
// Create exit confirmation
|
// Create exit confirmation
|
||||||
const confirmExit = document.createElement('div');
|
const confirmExit = document.createElement('div');
|
||||||
confirmExit.style.cssText = `
|
confirmExit.style.cssText = `
|
||||||
@ -1590,7 +1699,7 @@ exitBtn.addEventListener('click', () => {
|
|||||||
box-shadow: 0 0 40px rgba(0, 234, 255, 0.6);
|
box-shadow: 0 0 40px rgba(0, 234, 255, 0.6);
|
||||||
backdrop-filter: blur(10px);
|
backdrop-filter: blur(10px);
|
||||||
`;
|
`;
|
||||||
|
|
||||||
confirmExit.innerHTML = `
|
confirmExit.innerHTML = `
|
||||||
<h3 style="
|
<h3 style="
|
||||||
color: #00eaff;
|
color: #00eaff;
|
||||||
@ -1648,9 +1757,9 @@ exitBtn.addEventListener('click', () => {
|
|||||||
">NO</button>
|
">NO</button>
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
document.body.appendChild(confirmExit);
|
document.body.appendChild(confirmExit);
|
||||||
|
|
||||||
// YES button hover effect
|
// YES button hover effect
|
||||||
const yesBtn = document.getElementById('confirmYes');
|
const yesBtn = document.getElementById('confirmYes');
|
||||||
yesBtn.addEventListener('mouseenter', () => {
|
yesBtn.addEventListener('mouseenter', () => {
|
||||||
@ -1665,7 +1774,7 @@ exitBtn.addEventListener('click', () => {
|
|||||||
yesBtn.style.transform = 'translateY(0) scale(1)';
|
yesBtn.style.transform = 'translateY(0) scale(1)';
|
||||||
yesBtn.style.boxShadow = '0 4px 0 #cc0033, 0 0 12px rgba(255, 51, 102, 0.4), inset 0 0 15px rgba(255, 51, 102, 0.1)';
|
yesBtn.style.boxShadow = '0 4px 0 #cc0033, 0 0 12px rgba(255, 51, 102, 0.4), inset 0 0 15px rgba(255, 51, 102, 0.1)';
|
||||||
});
|
});
|
||||||
|
|
||||||
// NO button hover effect
|
// NO button hover effect
|
||||||
const noBtn = document.getElementById('confirmNo');
|
const noBtn = document.getElementById('confirmNo');
|
||||||
noBtn.addEventListener('mouseenter', () => {
|
noBtn.addEventListener('mouseenter', () => {
|
||||||
@ -1680,7 +1789,7 @@ exitBtn.addEventListener('click', () => {
|
|||||||
noBtn.style.transform = 'translateY(0) scale(1)';
|
noBtn.style.transform = 'translateY(0) scale(1)';
|
||||||
noBtn.style.boxShadow = '0 4px 0 #00bcd4, 0 0 12px rgba(0, 234, 255, 0.4), inset 0 0 15px rgba(0, 234, 255, 0.2)';
|
noBtn.style.boxShadow = '0 4px 0 #00bcd4, 0 0 12px rgba(0, 234, 255, 0.4), inset 0 0 15px rgba(0, 234, 255, 0.2)';
|
||||||
});
|
});
|
||||||
|
|
||||||
// Click handlers
|
// Click handlers
|
||||||
yesBtn.addEventListener('click', () => {
|
yesBtn.addEventListener('click', () => {
|
||||||
window.close();
|
window.close();
|
||||||
@ -1688,7 +1797,7 @@ exitBtn.addEventListener('click', () => {
|
|||||||
window.location.href = 'about:blank';
|
window.location.href = 'about:blank';
|
||||||
}, 100);
|
}, 100);
|
||||||
});
|
});
|
||||||
|
|
||||||
noBtn.addEventListener('click', () => {
|
noBtn.addEventListener('click', () => {
|
||||||
playSound(menuClickSound);
|
playSound(menuClickSound);
|
||||||
document.body.removeChild(confirmExit);
|
document.body.removeChild(confirmExit);
|
||||||
@ -1706,18 +1815,18 @@ backBtn.addEventListener('click', () => {
|
|||||||
musicBtns.forEach(btn => {
|
musicBtns.forEach(btn => {
|
||||||
btn.addEventListener('click', () => {
|
btn.addEventListener('click', () => {
|
||||||
playSound(menuClickSound);
|
playSound(menuClickSound);
|
||||||
|
|
||||||
musicBtns.forEach(b => b.classList.remove('active'));
|
musicBtns.forEach(b => b.classList.remove('active'));
|
||||||
|
|
||||||
btn.classList.add('active');
|
btn.classList.add('active');
|
||||||
|
|
||||||
gameSettings.musicEnabled = btn.dataset.music === 'on';
|
gameSettings.musicEnabled = btn.dataset.music === 'on';
|
||||||
|
|
||||||
if (typeof currentBGM !== 'undefined') {
|
if (typeof currentBGM !== 'undefined') {
|
||||||
if (gameSettings.musicEnabled) {
|
if (gameSettings.musicEnabled) {
|
||||||
currentBGM.volume = 1;
|
currentBGM.volume = 1;
|
||||||
if (!game.gameOver && gameStarted) {
|
if (!game.gameOver && gameStarted) {
|
||||||
currentBGM.play().catch(() => {});
|
currentBGM.play().catch(() => { });
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
currentBGM.volume = 0;
|
currentBGM.volume = 0;
|
||||||
@ -1731,11 +1840,11 @@ musicBtns.forEach(btn => {
|
|||||||
sfxBtns.forEach(btn => {
|
sfxBtns.forEach(btn => {
|
||||||
btn.addEventListener('click', () => {
|
btn.addEventListener('click', () => {
|
||||||
playSound(menuClickSound);
|
playSound(menuClickSound);
|
||||||
|
|
||||||
sfxBtns.forEach(b => b.classList.remove('active'));
|
sfxBtns.forEach(b => b.classList.remove('active'));
|
||||||
|
|
||||||
btn.classList.add('active');
|
btn.classList.add('active');
|
||||||
|
|
||||||
gameSettings.sfxEnabled = btn.dataset.sfx === 'on';
|
gameSettings.sfxEnabled = btn.dataset.sfx === 'on';
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
@ -1760,7 +1869,7 @@ function applySettings() {
|
|||||||
currentBGM.pause();
|
currentBGM.pause();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (typeof gameOverBGM !== 'undefined') {
|
if (typeof gameOverBGM !== 'undefined') {
|
||||||
if (gameSettings.musicEnabled) {
|
if (gameSettings.musicEnabled) {
|
||||||
gameOverBGM.volume = 1;
|
gameOverBGM.volume = 1;
|
||||||
@ -1775,7 +1884,7 @@ function playSound(audio) {
|
|||||||
if (gameSettings.sfxEnabled) {
|
if (gameSettings.sfxEnabled) {
|
||||||
audio.volume = 0.3;
|
audio.volume = 0.3;
|
||||||
audio.currentTime = 0;
|
audio.currentTime = 0;
|
||||||
audio.play().catch(() => {});
|
audio.play().catch(() => { });
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1789,7 +1898,7 @@ document.addEventListener('keydown', (e) => {
|
|||||||
togglePause();
|
togglePause();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Enter to start game from main menu
|
// Enter to start game from main menu
|
||||||
if (e.key === 'Enter' && mainMenu.style.display === 'flex') {
|
if (e.key === 'Enter' && mainMenu.style.display === 'flex') {
|
||||||
startBtn.click();
|
startBtn.click();
|
||||||
@ -1808,7 +1917,7 @@ function returnToMenu() {
|
|||||||
gameOverBGM.pause();
|
gameOverBGM.pause();
|
||||||
currentBGM.currentTime = 0;
|
currentBGM.currentTime = 0;
|
||||||
gameOverBGM.currentTime = 0;
|
gameOverBGM.currentTime = 0;
|
||||||
|
|
||||||
game.gameOver = false;
|
game.gameOver = false;
|
||||||
game.frames = 0;
|
game.frames = 0;
|
||||||
game.level = 1;
|
game.level = 1;
|
||||||
@ -1817,7 +1926,7 @@ function returnToMenu() {
|
|||||||
game.surgePhase = 0;
|
game.surgePhase = 0;
|
||||||
game.surgeTimer = 0;
|
game.surgeTimer = 0;
|
||||||
game.surgeCooldown = 2400;
|
game.surgeCooldown = 2400;
|
||||||
|
|
||||||
missilesArray = [];
|
missilesArray = [];
|
||||||
playerMissilesArray = [];
|
playerMissilesArray = [];
|
||||||
enemyShipArray = [];
|
enemyShipArray = [];
|
||||||
@ -1825,11 +1934,11 @@ function returnToMenu() {
|
|||||||
explosions = [];
|
explosions = [];
|
||||||
abilityTokens = [];
|
abilityTokens = [];
|
||||||
particles = [];
|
particles = [];
|
||||||
|
|
||||||
player1 = new PlayerObject(100, 300);
|
player1 = new PlayerObject(100, 300);
|
||||||
player1.lives = 6;
|
player1.lives = 1;
|
||||||
player1.score = 0;
|
player1.score = 0;
|
||||||
|
|
||||||
respawnCounter = 0;
|
respawnCounter = 0;
|
||||||
damageFlash = 0;
|
damageFlash = 0;
|
||||||
currentWave = null;
|
currentWave = null;
|
||||||
@ -1839,7 +1948,7 @@ function returnToMenu() {
|
|||||||
cameraY = 0;
|
cameraY = 0;
|
||||||
gameStarted = false;
|
gameStarted = false;
|
||||||
gamePaused = false;
|
gamePaused = false;
|
||||||
|
|
||||||
if (gameContainer) gameContainer.style.display = 'none';
|
if (gameContainer) gameContainer.style.display = 'none';
|
||||||
if (mainMenu) mainMenu.style.display = 'flex';
|
if (mainMenu) mainMenu.style.display = 'flex';
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user