Spaces:
Running
Running
Update index.html
Browse files- index.html +135 -5
index.html
CHANGED
@@ -116,6 +116,13 @@
|
|
116 |
<p>1000 Gold</p>
|
117 |
<p style="color: #4CAF50;">Air support from BF-109</p>
|
118 |
<button onclick="buyBF109()">Buy</button>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
119 |
</div>
|
120 |
<div id="apcr" style="text-align:center;">
|
121 |
<h3>APCR</h3>
|
@@ -156,6 +163,8 @@
|
|
156 |
let effects = [];
|
157 |
let hasAPCR = false; // APCR ꡬ맀 μ¬λΆ
|
158 |
let hasBF109 = false; // BF-109 ꡬ맀 μ¬λΆ
|
|
|
|
|
159 |
let supportUnits = []; // μ§μ μ λ λ°°μ΄
|
160 |
let lastSupportSpawn = 0; // λ§μ§λ§ μ§μ μ λ μμ± μκ°
|
161 |
// Load assets
|
@@ -246,7 +255,7 @@
|
|
246 |
return Date.now() - this.startTime > this.duration;
|
247 |
}
|
248 |
}
|
249 |
-
|
250 |
constructor(yPosition) {
|
251 |
this.x = 0;
|
252 |
this.y = yPosition;
|
@@ -257,24 +266,28 @@
|
|
257 |
this.angle = 0; // νμ μ€λ₯Έμͺ½μ ν₯ν¨
|
258 |
this.img = new Image();
|
259 |
this.img.src = 'bf109.png';
|
|
|
260 |
}
|
261 |
|
262 |
update() {
|
263 |
// μ΄λ
|
264 |
this.x += this.speed;
|
265 |
-
|
266 |
// λ°μ¬ (1μ΄μ 5λ°)
|
267 |
const now = Date.now();
|
268 |
if (now - this.lastShot > 200) {
|
269 |
this.shoot();
|
270 |
this.lastShot = now;
|
271 |
}
|
272 |
-
|
273 |
return this.x < canvas.width;
|
274 |
}
|
275 |
|
276 |
shoot() {
|
277 |
-
|
|
|
|
|
|
|
|
|
|
|
278 |
bullets.push({
|
279 |
x: this.x + Math.cos(this.angle) * 30,
|
280 |
y: this.y + Math.sin(this.angle) * 30,
|
@@ -286,6 +299,106 @@
|
|
286 |
});
|
287 |
}
|
288 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
289 |
class Enemy {
|
290 |
constructor(isBoss = false) {
|
291 |
this.x = Math.random() * canvas.width;
|
@@ -406,6 +519,15 @@ function buyTank(tankImg, cost, tankId) {
|
|
406 |
document.getElementById('bf109').style.display = 'none';
|
407 |
document.getElementById('shop').style.display = 'none';
|
408 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
409 |
}
|
410 |
function initRound() {
|
411 |
enemies = [];
|
@@ -501,7 +623,14 @@ function buyTank(tankImg, cost, tankId) {
|
|
501 |
// μ§μ μ λ μ
λ°μ΄νΈ λ° νλ©΄ λ° μ λ μ κ±°
|
502 |
supportUnits = supportUnits.filter(unit => unit.update());
|
503 |
}
|
504 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
505 |
enemies.forEach(enemy => enemy.update());
|
506 |
if(!isCountingDown) {
|
507 |
bullets = bullets.filter(bullet => {
|
@@ -689,6 +818,7 @@ restartBtn.addEventListener('click', () => {
|
|
689 |
gold = 0;
|
690 |
hasAPCR = false; // APCR μ΄κΈ°ν
|
691 |
hasBF109 = false; // BF109 μ΄κΈ°ν
|
|
|
692 |
supportUnits = []; // μ§μ μ λ λ°°μ΄ μ΄κΈ°ν
|
693 |
|
694 |
restartBtn.style.display = 'none';
|
|
|
116 |
<p>1000 Gold</p>
|
117 |
<p style="color: #4CAF50;">Air support from BF-109</p>
|
118 |
<button onclick="buyBF109()">Buy</button>
|
119 |
+
</div>
|
120 |
+
<div id="ju87" style="text-align:center;">
|
121 |
+
<h3>JU-87</h3>
|
122 |
+
<img src="ju87.png" width="100" height="100">
|
123 |
+
<p>1500 Gold</p>
|
124 |
+
<p style="color: #4CAF50;">Get ju-87 air support</p>
|
125 |
+
<button onclick="buyJU87()">Buy</button>
|
126 |
</div>
|
127 |
<div id="apcr" style="text-align:center;">
|
128 |
<h3>APCR</h3>
|
|
|
163 |
let effects = [];
|
164 |
let hasAPCR = false; // APCR ꡬ맀 μ¬λΆ
|
165 |
let hasBF109 = false; // BF-109 ꡬ맀 μ¬λΆ
|
166 |
+
let hasJU87 = false; // JU-87 ꡬ맀 μ¬λΆ
|
167 |
+
let lastJU87Spawn = 0; // λ§μ§λ§ JU-87 μμ± μκ°
|
168 |
let supportUnits = []; // μ§μ μ λ λ°°μ΄
|
169 |
let lastSupportSpawn = 0; // λ§μ§λ§ μ§μ μ λ μμ± μκ°
|
170 |
// Load assets
|
|
|
255 |
return Date.now() - this.startTime > this.duration;
|
256 |
}
|
257 |
}
|
258 |
+
class SupportUnit {
|
259 |
constructor(yPosition) {
|
260 |
this.x = 0;
|
261 |
this.y = yPosition;
|
|
|
266 |
this.angle = 0; // νμ μ€λ₯Έμͺ½μ ν₯ν¨
|
267 |
this.img = new Image();
|
268 |
this.img.src = 'bf109.png';
|
269 |
+
this.hasPlayedSound = false; // μ리 μ¬μ μ¬λΆ μΆκ°
|
270 |
}
|
271 |
|
272 |
update() {
|
273 |
// μ΄λ
|
274 |
this.x += this.speed;
|
|
|
275 |
// λ°μ¬ (1μ΄μ 5λ°)
|
276 |
const now = Date.now();
|
277 |
if (now - this.lastShot > 200) {
|
278 |
this.shoot();
|
279 |
this.lastShot = now;
|
280 |
}
|
|
|
281 |
return this.x < canvas.width;
|
282 |
}
|
283 |
|
284 |
shoot() {
|
285 |
+
// μ΅μ΄ λ°μ¬μμλ§ μ리 μ¬μ
|
286 |
+
if (!this.hasPlayedSound) {
|
287 |
+
new Audio('bf109mg.ogg').play();
|
288 |
+
this.hasPlayedSound = true;
|
289 |
+
}
|
290 |
+
|
291 |
bullets.push({
|
292 |
x: this.x + Math.cos(this.angle) * 30,
|
293 |
y: this.y + Math.sin(this.angle) * 30,
|
|
|
299 |
});
|
300 |
}
|
301 |
}
|
302 |
+
class JU87 {
|
303 |
+
constructor() {
|
304 |
+
this.x = canvas.width;
|
305 |
+
this.y = 50;
|
306 |
+
this.speed = 5;
|
307 |
+
this.width = 100;
|
308 |
+
this.height = 100;
|
309 |
+
this.angle = Math.PI;
|
310 |
+
this.img = new Image();
|
311 |
+
this.img.src = 'ju87.png';
|
312 |
+
this.target = null; // μ²μμλ νκ² μμ
|
313 |
+
this.lastShot = 0;
|
314 |
+
this.spawnTime = Date.now();
|
315 |
+
this.hasPlayedSound = false;
|
316 |
+
this.hasPlayedMGSound = false;
|
317 |
+
this.isReturning = false;
|
318 |
+
}
|
319 |
+
|
320 |
+
selectTarget() {
|
321 |
+
return enemies.length > 0 ?
|
322 |
+
enemies[Math.floor(Math.random() * enemies.length)] : null;
|
323 |
+
}
|
324 |
+
|
325 |
+
shoot() {
|
326 |
+
// μ΅μ΄ λ°μ¬μμλ§ μ리 μ¬μ
|
327 |
+
if (!this.hasPlayedMGSound) {
|
328 |
+
new Audio('ju87mg.ogg').play();
|
329 |
+
this.hasPlayedMGSound = true;
|
330 |
+
}
|
331 |
+
|
332 |
+
// μμͺ½ κΈ°κ΄μ΄ μμΉ
|
333 |
+
[[59, 36], [59, 62]].forEach(([x, y]) => {
|
334 |
+
const rotatedX = this.x + (Math.cos(this.angle) * x - Math.sin(this.angle) * y);
|
335 |
+
const rotatedY = this.y + (Math.sin(this.angle) * x + Math.cos(this.angle) * y);
|
336 |
+
|
337 |
+
bullets.push({
|
338 |
+
x: rotatedX,
|
339 |
+
y: rotatedY,
|
340 |
+
angle: this.angle,
|
341 |
+
speed: 10,
|
342 |
+
isEnemy: false,
|
343 |
+
damage: weapons.machinegun.damage,
|
344 |
+
size: weapons.machinegun.bulletSize
|
345 |
+
});
|
346 |
+
});
|
347 |
+
}
|
348 |
+
|
349 |
+
update() {
|
350 |
+
// μ΅μ΄ λ±μ₯μ μ¬μ΄λ
|
351 |
+
if (!this.hasPlayedSound) {
|
352 |
+
new Audio('ju87siren.ogg').play();
|
353 |
+
this.hasPlayedSound = true;
|
354 |
+
}
|
355 |
+
|
356 |
+
const timeSinceSpawn = Date.now() - this.spawnTime;
|
357 |
+
|
358 |
+
// 5μ΄ μ΄ν νλ
|
359 |
+
if (timeSinceSpawn > 5000) {
|
360 |
+
if (!this.isReturning) {
|
361 |
+
this.isReturning = true;
|
362 |
+
this.target = null;
|
363 |
+
// μ€μμΌλ‘ μ΄λ
|
364 |
+
this.angle = Math.atan2(canvas.height/2 - this.y, canvas.width/2 - this.x);
|
365 |
+
} else {
|
366 |
+
this.angle = Math.PI;
|
367 |
+
this.x -= this.speed;
|
368 |
+
return this.x > 0;
|
369 |
+
}
|
370 |
+
} else {
|
371 |
+
// νκ² μμΌλ©΄ μλ‘ μ ν
|
372 |
+
if (!this.target) this.target = this.selectTarget();
|
373 |
+
|
374 |
+
if (this.target) {
|
375 |
+
if (!enemies.includes(this.target) ||
|
376 |
+
Math.hypot(this.x - this.target.x, this.y - this.target.y) < 30) {
|
377 |
+
this.target = this.selectTarget();
|
378 |
+
}
|
379 |
+
|
380 |
+
if (this.target) {
|
381 |
+
this.angle = Math.atan2(this.target.y - this.y, this.target.x - this.x);
|
382 |
+
}
|
383 |
+
}
|
384 |
+
}
|
385 |
+
|
386 |
+
// μ΄λ
|
387 |
+
if (!this.isReturning || Math.hypot(this.x - canvas.width/2, this.y - canvas.height/2) > 10) {
|
388 |
+
this.x += Math.cos(this.angle) * this.speed;
|
389 |
+
this.y += Math.sin(this.angle) * this.speed;
|
390 |
+
}
|
391 |
+
|
392 |
+
// λ°μ¬
|
393 |
+
if (Date.now() - this.lastShot > 200 && this.target && !this.isReturning) {
|
394 |
+
this.shoot();
|
395 |
+
this.lastShot = Date.now();
|
396 |
+
}
|
397 |
+
|
398 |
+
return true;
|
399 |
+
}
|
400 |
+
}
|
401 |
+
|
402 |
class Enemy {
|
403 |
constructor(isBoss = false) {
|
404 |
this.x = Math.random() * canvas.width;
|
|
|
519 |
document.getElementById('bf109').style.display = 'none';
|
520 |
document.getElementById('shop').style.display = 'none';
|
521 |
}
|
522 |
+
}
|
523 |
+
function buyJU87() {
|
524 |
+
if (gold >= 1500 && !hasJU87) {
|
525 |
+
gold -= 1500;
|
526 |
+
hasJU87 = true;
|
527 |
+
document.getElementById('ju87').style.display = 'none';
|
528 |
+
document.getElementById('shop').style.display = 'none';
|
529 |
+
lastJU87Spawn = Date.now(); // ꡬ맀 μ¦μ μ€ν° νμ΄λ¨Έ μ΄κΈ°ν
|
530 |
+
}
|
531 |
}
|
532 |
function initRound() {
|
533 |
enemies = [];
|
|
|
623 |
// μ§μ μ λ μ
λ°μ΄νΈ λ° νλ©΄ λ° μ λ μ κ±°
|
624 |
supportUnits = supportUnits.filter(unit => unit.update());
|
625 |
}
|
626 |
+
// JU87 κ΄λ ¨ μ½λ μΆκ°
|
627 |
+
if (hasJU87 && !isCountingDown) {
|
628 |
+
const now = Date.now();
|
629 |
+
if (now - lastJU87Spawn > 15000) { // 15μ΄λ§λ€
|
630 |
+
supportUnits.push(new JU87());
|
631 |
+
lastJU87Spawn = now;
|
632 |
+
}
|
633 |
+
}
|
634 |
enemies.forEach(enemy => enemy.update());
|
635 |
if(!isCountingDown) {
|
636 |
bullets = bullets.filter(bullet => {
|
|
|
818 |
gold = 0;
|
819 |
hasAPCR = false; // APCR μ΄κΈ°ν
|
820 |
hasBF109 = false; // BF109 μ΄κΈ°ν
|
821 |
+
hasJU87 = false;
|
822 |
supportUnits = []; // μ§μ μ λ λ°°μ΄ μ΄κΈ°ν
|
823 |
|
824 |
restartBtn.style.display = 'none';
|