lunarflu HF Staff commited on
Commit
35356ff
·
verified ·
1 Parent(s): 7b92311

Add 1 files

Browse files
Files changed (1) hide show
  1. index.html +744 -739
index.html CHANGED
@@ -162,639 +162,596 @@
162
  <span>Health</span>
163
  <span id="health-text">100/100</span>
164
  </div>
165
- <div class="w-full bg-gray-700 rounded-full h-4">
166
- <div id="health-bar" class="health-bar bg-red-500 h-4 rounded-full" style="width: 100%"></div>
167
- </div>
168
- </div>
169
-
170
- <div class="mb-4">
171
- <div class="flex justify-between mb-1">
172
- <span>Mana</span>
173
- <span id="mana-text">50/50</span>
174
- </div>
175
- <div class="w-full bg-gray-700 rounded-full h-4">
176
- <div id="mana-bar" class="health-bar bg-blue-500 h-4 rounded-full" style="width: 100%"></div>
177
- </div>
178
- </div>
179
-
180
- <div class="mb-4">
181
- <div class="flex justify-between mb-1">
182
- <span>Experience</span>
183
- <span id="exp-text">0/100</span>
184
- </div>
185
- <div class="w-full bg-gray-700 rounded-full h-4">
186
- <div id="exp-bar" class="health-bar bg-yellow-500 h-4 rounded-full" style="width: 0%"></div>
187
- </div>
188
- </div>
189
-
190
- <div class="grid grid-cols-2 gap-2 mb-4">
191
- <div class="bg-gray-700 p-2 rounded">
192
- <div class="text-sm text-gray-300">Level</div>
193
- <div class="font-bold" id="level-text">1</div>
194
- </div>
195
- <div class="bg-gray-700 p-2 rounded">
196
- <div class="text-sm text-gray-300">Gold</div>
197
- <div class="font-bold" id="gold-text">10</div>
198
- </div>
199
- <div class="bg-gray-700 p-2 rounded">
200
- <div class="text-sm text-gray-300">Attack</div>
201
- <div class="font-bold" id="attack-text">10</div>
202
- </div>
203
- <div class="bg-gray-700 p-2 rounded">
204
- <div class="text-sm text-gray-300">Defense</div>
205
- <div class="font-bold" id="defense-text">5</div>
206
- </div>
207
- </div>
208
-
209
- <button onclick="openInventory()" class="w-full bg-blue-600 hover:bg-blue-700 text-white py-2 rounded mb-2">
210
- <i class="fas fa-backpack mr-2"></i> Inventory
211
- </button>
212
- <button onclick="openQuests()" class="w-full bg-green-600 hover:bg-green-700 text-white py-2 rounded mb-2">
213
- <i class="fas fa-scroll mr-2"></i> Quests
214
- </button>
215
- <button onclick="saveGame()" class="w-full bg-purple-600 hover:bg-purple-700 text-white py-2 rounded">
216
- <i class="fas fa-save mr-2"></i> Save Game
217
- </button>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
218
  </div>
219
-
220
- <!-- Main Game Area -->
221
- <div class="flex-1">
222
- <!-- Game Messages -->
223
- <div id="game-messages" class="bg-gray-800 bg-opacity-90 rounded-lg p-4 mb-4 h-40 overflow-y-auto">
224
- <p class="text-yellow-300">Welcome to Epic RPG Adventure!</p>
225
- <p>Create your character and begin your journey.</p>
226
- </div>
227
-
228
- <!-- Action Buttons -->
229
- <div class="grid grid-cols-2 gap-4 mb-6">
230
- <button onclick="explore()" class="bg-green-600 hover:bg-green-700 text-white font-bold py-3 px-4 rounded-lg transition-all hover:scale-105">
231
- <i class="fas fa-binoculars mr-2"></i> Explore
232
- </button>
233
- <button onclick="rest()" class="bg-blue-600 hover:bg-blue-700 text-white font-bold py-3 px-4 rounded-lg transition-all hover:scale-105">
234
- <i class="fas fa-bed mr-2"></i> Rest
235
- </button>
236
- <button onclick="visitTown()" class="bg-yellow-600 hover:bg-yellow-700 text-white font-bold py-3 px-4 rounded-lg transition-all hover:scale-105">
237
- <i class="fas fa-city mr-2"></i> Visit Town
238
- </button>
239
- <button onclick="train()" class="bg-red-600 hover:bg-red-700 text-white font-bold py-3 px-4 rounded-lg transition-all hover:scale-105">
240
- <i class="fas fa-dumbbell mr-2"></i> Train
241
- </button>
242
- </div>
243
-
244
- <!-- Combat Area -->
245
- <div id="combat-area" class="hidden bg-gray-800 bg-opacity-90 rounded-lg p-6">
246
- <div class="flex flex-col md:flex-row justify-between items-center mb-8">
247
- <!-- Player -->
248
- <div class="text-center mb-6 md:mb-0 relative">
249
- <div class="text-6xl mb-2" id="player-combat-icon">
250
- <i class="fas fa-user"></i>
251
- </div>
252
- <h4 class="text-xl font-bold" id="player-combat-name">Hero</h4>
253
- <div class="w-full bg-gray-700 rounded-full h-3 mt-2">
254
- <div id="player-health-bar" class="health-bar bg-red-500 h-3 rounded-full" style="width: 100%"></div>
255
- </div>
256
- <div class="text-sm" id="player-health-text">100/100</div>
257
- </div>
258
-
259
- <!-- VS -->
260
- <div class="text-2xl font-bold mx-4 mb-6 md:mb-0">VS</div>
261
-
262
- <!-- Enemy -->
263
- <div class="text-center relative">
264
- <div class="text-6xl mb-2" id="enemy-icon">
265
- <i class="fas fa-spider"></i>
266
- </div>
267
- <h4 class="text-xl font-bold" id="enemy-name">Goblin</h4>
268
- <div class="w-full bg-gray-700 rounded-full h-3 mt-2">
269
- <div id="enemy-health-bar" class="health-bar bg-red-500 h-3 rounded-full" style="width: 100%"></div>
270
- </div>
271
- <div class="text-sm" id="enemy-health-text">30/30</div>
272
- </div>
273
- </div>
274
-
275
- <!-- Combat Actions -->
276
- <div id="combat-actions" class="grid grid-cols-2 gap-4">
277
- <button onclick="playerAttack()" class="bg-red-600 hover:bg-red-700 text-white font-bold py-3 px-4 rounded-lg">
278
- <i class="fas fa-sword mr-2"></i> Attack
279
- </button>
280
- <button onclick="playerSpell()" class="bg-blue-600 hover:bg-blue-700 text-white font-bold py-3 px-4 rounded-lg">
281
- <i class="fas fa-magic mr-2"></i> Cast Spell
282
- </button>
283
- <button onclick="playerDefend()" class="bg-gray-600 hover:bg-gray-700 text-white font-bold py-3 px-4 rounded-lg">
284
- <i class="fas fa-shield-alt mr-2"></i> Defend
285
- </button>
286
- <button onclick="playerFlee()" class="bg-yellow-600 hover:bg-yellow-700 text-white font-bold py-3 px-4 rounded-lg">
287
- <i class="fas fa-running mr-2"></i> Flee
288
- </button>
289
- </div>
290
- </div>
291
-
292
- <!-- Town Area -->
293
- <div id="town-area" class="hidden bg-gray-800 bg-opacity-90 rounded-lg p-6">
294
- <h3 class="text-2xl font-bold mb-4">Town Square</h3>
295
- <div class="grid grid-cols-1 md:grid-cols-3 gap-4">
296
- <button onclick="visitShop()" class="bg-blue-600 hover:bg-blue-700 text-white font-bold py-3 px-4 rounded-lg">
297
- <i class="fas fa-shopping-cart mr-2"></i> Shop
298
- </button>
299
- <button onclick="visitTavern()" class="bg-yellow-600 hover:bg-yellow-700 text-white font-bold py-3 px-4 rounded-lg">
300
- <i class="fas fa-beer mr-2"></i> Tavern
301
- </button>
302
- <button onclick="visitGuild()" class="bg-purple-600 hover:bg-purple-700 text-white font-bold py-3 px-4 rounded-lg">
303
- <i class="fas fa-scroll mr-2"></i> Adventurer's Guild
304
- </button>
305
- <button onclick="leaveTown()" class="bg-gray-600 hover:bg-gray-700 text-white font-bold py-3 px-4 rounded-lg">
306
- <i class="fas fa-door-open mr-2"></i> Leave Town
307
- </button>
308
- </div>
309
- </div>
310
  </div>
 
311
  </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
312
  </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
313
 
314
- <!-- Inventory Modal -->
315
- <div id="inventory-modal" class="hidden fixed inset-0 bg-black bg-opacity-50 flex items-center justify-center z-50">
316
- <div class="bg-gray-800 rounded-lg p-6 w-full max-w-2xl max-h-[80vh] overflow-y-auto">
317
- <div class="flex justify-between items-center mb-4">
318
- <h3 class="text-2xl font-bold">Inventory</h3>
319
- <button onclick="closeInventory()" class="text-gray-400 hover:text-white">
320
- <i class="fas fa-times"></i>
321
- </button>
322
- </div>
323
-
324
- <div class="grid grid-cols-2 md:grid-cols-4 gap-4 mb-6">
325
- <div class="bg-gray-700 p-4 rounded-lg text-center">
326
- <div class="text-3xl mb-2"><i class="fas fa-sword"></i></div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
327
  <div class="font-bold">Iron Sword</div>
328
  <div class="text-sm text-gray-300">Attack +5</div>
329
- <button class="mt-2 bg-blue-600 hover:bg-blue-700 text-white py-1 px-3 rounded text-sm">
330
- Equip
331
- </button>
332
  </div>
333
- <div class="bg-gray-700 p-4 rounded-lg text-center">
334
- <div class="text-3xl mb-2"><i class="fas fa-shield-alt"></i></div>
 
 
 
 
335
  <div class="font-bold">Wooden Shield</div>
336
  <div class="text-sm text-gray-300">Defense +3</div>
337
- <button class="mt-2 bg-blue-600 hover:bg-blue-700 text-white py-1 px-3 rounded text-sm">
338
- Equip
339
- </button>
340
- </div>
341
- <div class="bg-gray-700 p-4 rounded-lg text-center">
342
- <div class="text-3xl mb-2"><i class="fas fa-flask"></i></div>
343
- <div class="font-bold">Health Potion</div>
344
- <div class="text-sm text-gray-300">Restores 30 HP</div>
345
- <button class="mt-2 bg-green-600 hover:bg-green-700 text-white py-1 px-3 rounded text-sm">
346
- Use
347
- </button>
348
- </div>
349
- <div class="bg-gray-700 p-4 rounded-lg text-center">
350
- <div class="text-3xl mb-2"><i class="fas fa-flask"></i></div>
351
- <div class="font-bold">Mana Potion</div>
352
- <div class="text-sm text-gray-300">Restores 20 MP</div>
353
- <button class="mt-2 bg-green-600 hover:bg-green-700 text-white py-1 px-3 rounded text-sm">
354
- Use
355
- </button>
356
- </div>
357
- </div>
358
-
359
- <h4 class="text-xl font-bold mb-3">Equipped Items</h4>
360
- <div class="grid grid-cols-2 gap-4">
361
- <div class="bg-gray-700 p-3 rounded-lg">
362
- <div class="flex items-center">
363
- <div class="text-2xl mr-3"><i class="fas fa-sword"></i></div>
364
- <div>
365
- <div class="font-bold">Iron Sword</div>
366
- <div class="text-sm text-gray-300">Attack +5</div>
367
- </div>
368
- </div>
369
- </div>
370
- <div class="bg-gray-700 p-3 rounded-lg">
371
- <div class="flex items-center">
372
- <div class="text-2xl mr-3"><i class="fas fa-shield-alt"></i></div>
373
- <div>
374
- <div class="font-bold">Wooden Shield</div>
375
- <div class="text-sm text-gray-300">Defense +3</div>
376
- </div>
377
- </div>
378
  </div>
379
  </div>
380
  </div>
381
  </div>
 
 
382
 
383
- <!-- Credits Modal -->
384
- <div id="credits-modal" class="hidden fixed inset-0 bg-black bg-opacity-50 flex items-center justify-center z-50">
385
- <div class="bg-gray-800 rounded-lg p-6 w-full max-w-md">
386
- <div class="flex justify-between items-center mb-4">
387
- <h3 class="text-2xl font-bold">Credits</h3>
388
- <button onclick="hideCredits()" class="text-gray-400 hover:text-white">
389
- <i class="fas fa-times"></i>
390
- </button>
391
- </div>
392
-
393
- <div class="space-y-4">
394
- <div>
395
- <h4 class="text-xl font-bold text-yellow-400">Epic RPG Adventure</h4>
396
- <p class="text-gray-300">Created with HTML, CSS, and JavaScript</p>
397
- </div>
398
-
399
- <div>
400
- <h4 class="font-bold">Developer</h4>
401
- <p class="text-gray-300">Your Name Here</p>
402
- </div>
403
-
404
- <div>
405
- <h4 class="font-bold">Special Thanks</h4>
406
- <ul class="list-disc list-inside text-gray-300">
407
- <li>Tailwind CSS</li>
408
- <li>Font Awesome</li>
409
- <li>Unsplash for images</li>
410
- </ul>
411
- </div>
412
-
413
- <div class="pt-4 border-t border-gray-700">
414
- <p class="text-sm text-gray-400">© 2023 All Rights Reserved</p>
415
- </div>
416
- </div>
417
  </div>
418
  </div>
419
  </div>
 
 
420
 
421
- <script>
422
- // Game State
423
- const gameState = {
424
- player: {
425
- name: '',
426
- class: '',
427
- gender: '',
428
- level: 1,
429
- exp: 0,
430
- expToNextLevel: 100,
431
- health: 100,
432
- maxHealth: 100,
433
- mana: 50,
434
- maxMana: 50,
435
- attack: 10,
436
- defense: 5,
437
- gold: 10,
438
- inventory: [
439
- { name: 'Iron Sword', type: 'weapon', attack: 5, icon: 'fa-sword' },
440
- { name: 'Wooden Shield', type: 'shield', defense: 3, icon: 'fa-shield-alt' },
441
- { name: 'Health Potion', type: 'consumable', effect: 'heal', amount: 30, icon: 'fa-flask' },
442
- { name: 'Mana Potion', type: 'consumable', effect: 'mana', amount: 20, icon: 'fa-flask' }
443
- ],
444
- equipped: {
445
- weapon: { name: 'Iron Sword', type: 'weapon', attack: 5, icon: 'fa-sword' },
446
- shield: { name: 'Wooden Shield', type: 'shield', defense: 3, icon: 'fa-shield-alt' }
447
- }
448
- },
449
- currentEnemy: null,
450
- inCombat: false,
451
- gameMessages: []
452
- };
453
 
454
- // Enemies
455
- const enemies = [
456
- { name: 'Goblin', health: 30, maxHealth: 30, attack: 8, defense: 2, exp: 20, gold: 5, icon: 'fa-user-ninja' },
457
- { name: 'Orc', health: 50, maxHealth: 50, attack: 12, defense: 5, exp: 35, gold: 10, icon: 'fa-user-injured' },
458
- { name: 'Skeleton', health: 25, maxHealth: 25, attack: 10, defense: 3, exp: 25, gold: 8, icon: 'fa-skull' },
459
- { name: 'Wolf', health: 20, maxHealth: 20, attack: 7, defense: 1, exp: 15, gold: 3, icon: 'fa-paw' },
460
- { name: 'Bandit', health: 40, maxHealth: 40, attack: 11, defense: 4, exp: 30, gold: 15, icon: 'fa-user' }
461
- ];
 
 
 
 
 
462
 
463
- // Game Functions
464
- function startNewGame() {
465
- document.getElementById('main-menu').classList.add('hidden');
466
- document.getElementById('character-creation').classList.remove('hidden');
467
- addGameMessage('Begin your adventure by creating your character.');
468
- }
469
 
470
- function selectClass(characterClass) {
471
- const cards = document.querySelectorAll('.character-card');
472
- cards.forEach(card => card.classList.remove('ring-2', 'ring-yellow-400'));
473
-
474
- const selectedCard = document.querySelector(`.character-card:nth-child(${characterClass === 'warrior' ? 1 : characterClass === 'mage' ? 2 : 3})`);
475
- selectedCard.classList.add('ring-2', 'ring-yellow-400');
476
-
477
- gameState.player.class = characterClass;
478
-
479
- // Update stats based on class
480
- if (characterClass === 'warrior') {
481
- gameState.player.maxHealth = 120;
482
- gameState.player.health = 120;
483
- gameState.player.attack = 12;
484
- gameState.player.defense = 8;
485
- gameState.player.mana = 30;
486
- gameState.player.maxMana = 30;
487
- } else if (characterClass === 'mage') {
488
- gameState.player.maxHealth = 70;
489
- gameState.player.health = 70;
490
- gameState.player.attack = 8;
491
- gameState.player.defense = 3;
492
- gameState.player.mana = 80;
493
- gameState.player.maxMana = 80;
494
- } else if (characterClass === 'rogue') {
495
- gameState.player.maxHealth = 90;
496
- gameState.player.health = 90;
497
- gameState.player.attack = 10;
498
- gameState.player.defense = 5;
499
- gameState.player.mana = 50;
500
- gameState.player.maxMana = 50;
501
- }
502
-
503
- addGameMessage(`You selected the ${characterClass} class.`);
504
  }
 
 
 
505
 
506
- function finalizeCharacter() {
507
- const nameInput = document.getElementById('character-name');
508
- const genderSelect = document.getElementById('character-gender');
509
-
510
- if (!nameInput.value.trim()) {
511
- addGameMessage('Please enter a name for your character.', 'error');
512
- return;
513
- }
514
-
515
- if (!gameState.player.class) {
516
- addGameMessage('Please select a class for your character.', 'error');
517
- return;
518
- }
519
-
520
- gameState.player.name = nameInput.value.trim();
521
- gameState.player.gender = genderSelect.value;
522
-
523
- // Start the game
524
- document.getElementById('character-creation').classList.add('hidden');
525
- document.getElementById('game-screen').classList.remove('hidden');
526
-
527
- // Update character display
528
- updateCharacterDisplay();
529
-
530
- addGameMessage(`Welcome, ${gameState.player.name} the ${gameState.player.class}! Your adventure begins now.`, 'success');
531
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
532
 
533
- function updateCharacterDisplay() {
534
- // Update character panel
535
- document.getElementById('character-display-name').textContent = gameState.player.name;
536
- document.getElementById('character-display-class').textContent = `Class: ${capitalizeFirstLetter(gameState.player.class)}`;
537
-
538
- // Update stats
539
- document.getElementById('health-text').textContent = `${gameState.player.health}/${gameState.player.maxHealth}`;
540
- document.getElementById('mana-text').textContent = `${gameState.player.mana}/${gameState.player.maxMana}`;
541
- document.getElementById('exp-text').textContent = `${gameState.player.exp}/${gameState.player.expToNextLevel}`;
542
- document.getElementById('level-text').textContent = gameState.player.level;
543
- document.getElementById('gold-text').textContent = gameState.player.gold;
544
- document.getElementById('attack-text').textContent = gameState.player.attack + (gameState.player.equipped.weapon ? gameState.player.equipped.weapon.attack : 0);
545
- document.getElementById('defense-text').textContent = gameState.player.defense + (gameState.player.equipped.shield ? gameState.player.equipped.shield.defense : 0);
546
-
547
- // Update health bar
548
- const healthPercent = (gameState.player.health / gameState.player.maxHealth) * 100;
549
- document.getElementById('health-bar').style.width = `${healthPercent}%`;
550
-
551
- // Update mana bar
552
- const manaPercent = (gameState.player.mana / gameState.player.maxMana) * 100;
553
- document.getElementById('mana-bar').style.width = `${manaPercent}%`;
554
-
555
- // Update exp bar
556
- const expPercent = (gameState.player.exp / gameState.player.expToNextLevel) * 100;
557
- document.getElementById('exp-bar').style.width = `${expPercent}%`;
558
-
559
- // Update character icon based on class
560
- const characterIcon = document.getElementById('character-icon');
561
- const playerCombatIcon = document.getElementById('player-combat-icon');
562
-
563
- if (gameState.player.class === 'warrior') {
564
- characterIcon.innerHTML = '<i class="fas fa-shield-alt text-red-500"></i>';
565
- playerCombatIcon.innerHTML = '<i class="fas fa-shield-alt text-red-500"></i>';
566
- } else if (gameState.player.class === 'mage') {
567
- characterIcon.innerHTML = '<i class="fas fa-hat-wizard text-blue-500"></i>';
568
- playerCombatIcon.innerHTML = '<i class="fas fa-hat-wizard text-blue-500"></i>';
569
- } else if (gameState.player.class === 'rogue') {
570
- characterIcon.innerHTML = '<i class="fas fa-user-ninja text-green-500"></i>';
571
- playerCombatIcon.innerHTML = '<i class="fas fa-user-ninja text-green-500"></i>';
572
- }
573
-
574
- // Update player combat name
575
- document.getElementById('player-combat-name').textContent = gameState.player.name;
576
  }
 
 
 
 
577
 
578
- function addGameMessage(message, type = 'info') {
579
- const messagesDiv = document.getElementById('game-messages');
580
- const messageElement = document.createElement('p');
581
-
582
- if (type === 'error') {
583
- messageElement.className = 'text-red-400';
584
- } else if (type === 'success') {
585
- messageElement.className = 'text-green-400';
586
- } else if (type === 'warning') {
587
- messageElement.className = 'text-yellow-400';
588
- } else {
589
- messageElement.className = 'text-gray-300';
590
- }
591
-
592
- messageElement.textContent = message;
593
- messagesDiv.appendChild(messageElement);
594
- messagesDiv.scrollTop = messagesDiv.scrollHeight;
595
-
596
- // Add to game state for saving
597
- gameState.gameMessages.push(message);
598
  }
 
 
 
 
 
 
 
 
599
 
600
- function explore() {
601
- if (gameState.inCombat) {
602
- addGameMessage('You are already in combat!', 'error');
603
- return;
604
- }
605
-
606
- // 70% chance to find an enemy
607
- if (Math.random() < 0.7) {
608
- startCombat();
 
 
 
 
 
 
 
 
 
 
609
  } else {
610
- // 30% chance to find something else
611
- const randomEvent = Math.random();
612
-
613
- if (randomEvent < 0.5) {
614
- // Found gold
615
- const goldFound = Math.floor(Math.random() * 10) + 5;
616
- gameState.player.gold += goldFound;
617
- updateCharacterDisplay();
618
- addGameMessage(`You found ${goldFound} gold coins on the ground!`, 'success');
619
- } else {
620
- // Found a health potion
621
- gameState.player.inventory.push({
622
- name: 'Health Potion',
623
- type: 'consumable',
624
- effect: 'heal',
625
- amount: 30,
626
- icon: 'fa-flask'
627
- });
628
- addGameMessage('You found a Health Potion!', 'success');
629
- }
630
  }
631
  }
 
632
 
633
- function startCombat() {
634
- gameState.inCombat = true;
635
-
636
- // Select a random enemy
637
- const randomEnemyIndex = Math.floor(Math.random() * enemies.length);
638
- gameState.currentEnemy = {...enemies[randomEnemyIndex]};
639
-
640
- // Update combat UI
641
- document.getElementById('combat-area').classList.remove('hidden');
642
- document.getElementById('enemy-name').textContent = gameState.currentEnemy.name;
643
- document.getElementById('enemy-health-text').textContent = `${gameState.currentEnemy.health}/${gameState.currentEnemy.maxHealth}`;
644
- document.getElementById('enemy-health-bar').style.width = '100%';
645
- document.getElementById('enemy-icon').innerHTML = `<i class="fas ${gameState.currentEnemy.icon}"></i>`;
646
-
647
- // Update player stats in combat
648
- document.getElementById('player-health-text').textContent = `${gameState.player.health}/${gameState.player.maxHealth}`;
649
- const healthPercent = (gameState.player.health / gameState.player.maxHealth) * 100;
650
- document.getElementById('player-health-bar').style.width = `${healthPercent}%`;
651
-
652
- addGameMessage(`A wild ${gameState.currentEnemy.name} appears!`, 'warning');
653
- }
654
 
655
- function playerAttack() {
656
- if (!gameState.inCombat || !gameState.currentEnemy) {
657
- addGameMessage('There is nothing to attack!', 'error');
658
- return;
659
- }
660
-
661
- // Calculate player damage
662
- const playerAttackPower = gameState.player.attack + (gameState.player.equipped.weapon ? gameState.player.equipped.weapon.attack : 0);
663
- const damage = Math.max(1, playerAttackPower - Math.floor(gameState.currentEnemy.defense / 2));
664
-
665
- // Apply damage to enemy
666
- gameState.currentEnemy.health -= damage;
667
-
668
- // Update enemy health bar
669
- const enemyHealthPercent = (gameState.currentEnemy.health / gameState.currentEnemy.maxHealth) * 100;
670
- document.getElementById('enemy-health-bar').style.width = `${Math.max(0, enemyHealthPercent)}%`;
671
- document.getElementById('enemy-health-text').textContent = `${Math.max(0, gameState.currentEnemy.health)}/${gameState.currentEnemy.maxHealth}`;
672
-
673
- // Show damage text
674
- showDamageText(document.querySelector('#combat-area .relative:last-child'), damage);
675
-
676
- addGameMessage(`You attack the ${gameState.currentEnemy.name} for ${damage} damage!`, 'success');
677
-
678
- // Check if enemy is defeated
679
- if (gameState.currentEnemy.health <= 0) {
680
- enemyDefeated();
681
- return;
682
- }
683
-
684
- // Enemy attacks back
685
- setTimeout(() => {
686
- enemyAttack();
687
- }, 1000);
688
  }
689
-
690
- function playerSpell() {
691
- if (!gameState.inCombat || !gameState.currentEnemy) {
692
- addGameMessage('There is nothing to attack!', 'error');
693
- return;
694
- }
695
-
696
- if (gameState.player.mana < 15) {
697
- addGameMessage('Not enough mana to cast a spell!', 'error');
698
- return;
699
- }
700
-
701
- // Use mana
702
- gameState.player.mana -= 15;
703
- updateCharacterDisplay();
704
-
705
- // Calculate spell damage (more powerful than regular attack)
706
- let spellDamage;
707
- if (gameState.player.class === 'mage') {
708
- spellDamage = Math.max(3, 15 + Math.floor(Math.random() * 10));
709
- } else {
710
- spellDamage = Math.max(3, 10 + Math.floor(Math.random() * 5));
711
- }
712
-
713
- // Apply damage to enemy
714
- gameState.currentEnemy.health -= spellDamage;
715
-
716
- // Update enemy health bar
717
- const enemyHealthPercent = (gameState.currentEnemy.health / gameState.currentEnemy.maxHealth) * 100;
718
- document.getElementById('enemy-health-bar').style.width = `${Math.max(0, enemyHealthPercent)}%`;
719
- document.getElementById('enemy-health-text').textContent = `${Math.max(0, gameState.currentEnemy.health)}/${gameState.currentEnemy.maxHealth}`;
720
-
721
- // Show damage text
722
- showDamageText(document.querySelector('#combat-area .relative:last-child'), spellDamage, 'blue');
723
-
724
- addGameMessage(`You cast a spell on the ${gameState.currentEnemy.name} for ${spellDamage} damage!`, 'success');
725
-
726
- // Check if enemy is defeated
727
- if (gameState.currentEnemy.health <= 0) {
728
- enemyDefeated();
729
- return;
730
- }
731
-
732
- // Enemy attacks back
733
- setTimeout(() => {
734
- enemyAttack();
735
- }, 1000);
736
  }
 
 
 
 
 
 
737
 
738
- function playerDefend() {
739
- if (!gameState.inCombat || !gameState.currentEnemy) {
740
- addGameMessage('There is nothing to defend against!', 'error');
741
- return;
742
- }
743
-
744
- addGameMessage(`You take a defensive stance, reducing damage from the next attack.`, 'info');
745
-
746
- // Enemy attacks with reduced damage
747
- setTimeout(() => {
748
- // Calculate enemy damage (reduced by 50% when defending)
749
- const enemyDamage = Math.max(1, Math.floor((gameState.currentEnemy.attack - (gameState.player.defense + (gameState.player.equipped.shield ? gameState.player.equipped.shield.defense : 0))) / 2));
750
-
751
- // Apply damage to player
752
- gameState.player.health -= enemyDamage;
753
-
754
- // Update player health bar
755
- const healthPercent = (gameState.player.health / gameState.player.maxHealth) * 100;
756
- document.getElementById('player-health-bar').style.width = `${Math.max(0, healthPercent)}%`;
757
- document.getElementById('player-health-text').textContent = `${Math.max(0, gameState.player.health)}/${gameState.player.maxHealth}`;
758
- document.getElementById('health-bar').style.width = `${Math.max(0, healthPercent)}%`;
759
- document.getElementById('health-text').textContent = `${Math.max(0, gameState.player.health)}/${gameState.player.maxHealth}`;
760
-
761
- // Show damage text
762
- showDamageText(document.querySelector('#combat-area .relative:first-child'), enemyDamage);
763
-
764
- addGameMessage(`The ${gameState.currentEnemy.name} attacks you for ${enemyDamage} damage (reduced by your defense)!`, 'warning');
765
-
766
- // Check if player is defeated
767
- if (gameState.player.health <= 0) {
768
- playerDefeated();
769
- }
770
- }, 1000);
771
  }
772
-
773
- function playerFlee() {
774
- if (!gameState.inCombat || !gameState.currentEnemy) {
775
- addGameMessage('There is nothing to flee from!', 'error');
776
- return;
777
- }
778
-
779
- // 60% chance to flee successfully
780
- if (Math.random() < 0.6) {
781
- addGameMessage(`You successfully fled from the ${gameState.currentEnemy.name}!`, 'success');
782
- endCombat();
783
- } else {
784
- addGameMessage(`You failed to flee! The ${gameState.currentEnemy.name} attacks you!`, 'error');
785
-
786
- // Enemy attacks
787
- setTimeout(() => {
788
- enemyAttack();
789
- }, 1000);
790
- }
791
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
792
 
793
- function enemyAttack() {
794
- if (!gameState.inCombat || !gameState.currentEnemy) return;
795
-
796
- // Calculate enemy damage
797
- const enemyDamage = Math.max(1, gameState.currentEnemy.attack - (gameState.player.defense + (gameState.player.equipped.shield ? gameState.player.equipped.shield.defense : 0)));
 
 
 
 
 
 
 
798
 
799
  // Apply damage to player
800
  gameState.player.health -= enemyDamage;
@@ -809,183 +766,231 @@
809
  // Show damage text
810
  showDamageText(document.querySelector('#combat-area .relative:first-child'), enemyDamage);
811
 
812
- addGameMessage(`The ${gameState.currentEnemy.name} attacks you for ${enemyDamage} damage!`, 'warning');
813
 
814
  // Check if player is defeated
815
  if (gameState.player.health <= 0) {
816
  playerDefeated();
817
  }
818
- }
 
819
 
820
- function enemyDefeated() {
821
- addGameMessage(`You defeated the ${gameState.currentEnemy.name}!`, 'success');
822
-
823
- // Gain experience and gold
824
- gameState.player.exp += gameState.currentEnemy.exp;
825
- gameState.player.gold += gameState.currentEnemy.gold;
826
-
827
- addGameMessage(`Gained ${gameState.currentEnemy.exp} experience and ${gameState.currentEnemy.gold} gold.`, 'success');
828
-
829
- // Check for level up
830
- checkLevelUp();
831
-
832
- // End combat
833
- endCombat();
834
  }
835
-
836
- function playerDefeated() {
837
- addGameMessage(`You were defeated by the ${gameState.currentEnemy.name}!`, 'error');
838
- addGameMessage('You wake up in town, having lost some gold and experience.', 'warning');
839
-
840
- // Penalty for dying
841
- gameState.player.exp = Math.max(0, gameState.player.exp - 10);
842
- gameState.player.gold = Math.max(0, gameState.player.gold - 5);
843
-
844
- // Restore some health
845
- gameState.player.health = Math.floor(gameState.player.maxHealth * 0.3);
846
-
847
- // Update display
848
- updateCharacterDisplay();
849
-
850
- // End combat
851
  endCombat();
 
 
 
 
 
 
 
852
  }
 
853
 
854
- function endCombat() {
855
- gameState.inCombat = false;
856
- gameState.currentEnemy = null;
857
- document.getElementById('combat-area').classList.add('hidden');
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
858
  }
 
859
 
860
- function checkLevelUp() {
861
- if (gameState.player.exp >= gameState.player.expToNextLevel) {
862
- gameState.player.level++;
863
- gameState.player.exp -= gameState.player.expToNextLevel;
864
- gameState.player.expToNextLevel = Math.floor(gameState.player.expToNextLevel * 1.2);
865
-
866
- // Improve stats
867
- gameState.player.maxHealth += 10;
868
- gameState.player.health = gameState.player.maxHealth;
869
- gameState.player.maxMana += 5;
870
- gameState.player.mana = gameState.player.maxMana;
871
- gameState.player.attack += 2;
872
- gameState.player.defense += 1;
873
-
874
- addGameMessage(`Level up! You are now level ${gameState.player.level}!`, 'success');
875
- addGameMessage('Your stats have improved!', 'info');
876
-
877
- updateCharacterDisplay();
878
- }
879
- }
880
 
881
- function rest() {
882
- if (gameState.inCombat) {
883
- addGameMessage('You cannot rest while in combat!', 'error');
884
- return;
885
- }
886
-
887
- // Restore health and mana
888
- const healthRestored = Math.floor(gameState.player.maxHealth * 0.3);
889
- const manaRestored = Math.floor(gameState.player.maxMana * 0.3);
890
-
891
- gameState.player.health = Math.min(gameState.player.maxHealth, gameState.player.health + healthRestored);
892
- gameState.player.mana = Math.min(gameState.player.maxMana, gameState.player.mana + manaRestored);
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
893
 
894
- addGameMessage(`You rest and recover ${healthRestored} health and ${manaRestored} mana.`, 'success');
895
  updateCharacterDisplay();
896
  }
 
897
 
898
- function visitTown() {
899
- if (gameState.inCombat) {
900
- addGameMessage('You cannot visit town while in combat!', 'error');
901
- return;
902
- }
903
-
904
- document.getElementById('town-area').classList.remove('hidden');
905
- addGameMessage('You enter the town square.', 'info');
906
  }
 
 
 
 
 
 
 
 
 
 
 
907
 
908
- function leaveTown() {
909
- document.getElementById('town-area').classList.add('hidden');
910
- addGameMessage('You leave the town.', 'info');
 
911
  }
 
 
 
 
912
 
913
- function visitShop() {
914
- addGameMessage('The shop is currently closed. Come back later!', 'info');
915
- }
 
916
 
917
- function visitTavern() {
918
- addGameMessage('You enjoy a drink at the tavern and hear rumors of a dragon in the mountains.', 'info');
919
- }
920
 
921
- function visitGuild() {
922
- addGameMessage('The Adventurer\'s Guild has no quests available right now.', 'info');
923
- }
924
 
925
- function train() {
926
- if (gameState.inCombat) {
927
- addGameMessage('You cannot train while in combat!', 'error');
928
- return;
929
- }
930
-
931
- // Training costs gold but improves stats
932
- if (gameState.player.gold < 5) {
933
- addGameMessage('You need at least 5 gold to train!', 'error');
934
- return;
935
- }
936
-
937
- gameState.player.gold -= 5;
938
-
939
- // Random stat improvement
940
- const statToImprove = ['attack', 'defense'][Math.floor(Math.random() * 2)];
941
- const improvement = 1;
942
-
943
- if (statToImprove === 'attack') {
944
- gameState.player.attack += improvement;
945
- addGameMessage(`After training, your attack increased by ${improvement}! (Cost: 5 gold)`, 'success');
946
- } else {
947
- gameState.player.defense += improvement;
948
- addGameMessage(`After training, your defense increased by ${improvement}! (Cost: 5 gold)`, 'success');
949
- }
950
-
951
- updateCharacterDisplay();
952
- }
953
 
954
- function openInventory() {
955
- document.getElementById('inventory-modal').classList.remove('hidden');
 
 
956
  }
957
-
958
- function closeInventory() {
959
- document.getElementById('inventory-modal').classList.add('hidden');
 
 
960
  }
961
-
962
- function openQuests() {
963
- addGameMessage('You have no active quests at the moment.', 'info');
 
 
 
 
 
 
 
 
 
 
964
  }
 
 
 
965
 
966
- function saveGame() {
967
- localStorage.setItem('epicRpgSave', JSON.stringify(gameState));
968
- addGameMessage('Game saved successfully!', 'success');
969
- }
970
 
971
- function loadGame() {
972
- const savedGame = localStorage.getItem('epicRpgSave');
973
-
974
- if (savedGame) {
975
- try {
976
- const parsedGame = JSON.parse(savedGame);
977
- Object.assign(gameState, parsedGame);
978
-
979
- document.getElementById('main-menu').classList.add('hidden');
980
- document.getElementById('game-screen').classList.remove('hidden');
981
-
982
- updateCharacterDisplay();
983
- addGameMessage(`Welcome back, ${gameState.player.name}! Game loaded successfully.`, 'success');
984
- } catch (e) {
985
- addGameMessage('Failed to load saved game.', 'error');
986
- }
987
- } else {
988
- addGameMessage('No saved game found.', 'error');
 
 
 
 
 
 
 
 
 
 
 
 
 
989
  }
990
  }
991
 
 
162
  <span>Health</span>
163
  <span id="health-text">100/100</span>
164
  </div>
165
+ <div class="w-full bg-gray-700 rounded-full h-4">
166
+ <div id="health-bar" class="health-bar bg-red-500 h-4 rounded-full" style="width: 100%"></div>
167
+ </div>
168
+ </div>
169
+
170
+ <div class="mb-4">
171
+ <div class="flex justify-between mb-1">
172
+ <span>Mana</span>
173
+ <span id="mana-text">50/50</span>
174
+ </div>
175
+ <div class="w-full bg-gray-700 rounded-full h-4">
176
+ <div id="mana-bar" class="health-bar bg-blue-500 h-4 rounded-full" style="width: 100%"></div>
177
+ </div>
178
+ </div>
179
+
180
+ <div class="mb-4">
181
+ <div class="flex justify-between mb-1">
182
+ <span>Experience</span>
183
+ <span id="exp-text">0/100</span>
184
+ </div>
185
+ <div class="w-full bg-gray-700 rounded-full h-4">
186
+ <div id="exp-bar" class="health-bar bg-yellow-500 h-4 rounded-full" style="width: 0%"></div>
187
+ </div>
188
+ </div>
189
+
190
+ <div class="grid grid-cols-2 gap-2 mb-4">
191
+ <div class="bg-gray-700 p-2 rounded">
192
+ <div class="text-sm text-gray-300">Level</div>
193
+ <div class="font-bold" id="level-text">1</div>
194
+ </div>
195
+ <div class="bg-gray-700 p-2 rounded">
196
+ <div class="text-sm text-gray-300">Gold</div>
197
+ <div class="font-bold" id="gold-text">10</div>
198
+ </div>
199
+ <div class="bg-gray-700 p-2 rounded">
200
+ <div class="text-sm text-gray-300">Attack</div>
201
+ <div class="font-bold" id="attack-text">10</div>
202
+ </div>
203
+ <div class="bg-gray-700 p-2 rounded">
204
+ <div class="text-sm text-gray-300">Defense</div>
205
+ <div class="font-bold" id="defense-text">5</div>
206
+ </div>
207
+ </div>
208
+
209
+ <button onclick="openInventory()" class="w-full bg-blue-600 hover:bg-blue-700 text-white py-2 rounded mb-2">
210
+ <i class="fas fa-backpack mr-2"></i> Inventory
211
+ </button>
212
+ <button onclick="openQuests()" class="w-full bg-green-600 hover:bg-green-700 text-white py-2 rounded mb-2">
213
+ <i class="fas fa-scroll mr-2"></i> Quests
214
+ </button>
215
+ <button onclick="saveGame()" class="w-full bg-purple-600 hover:bg-purple-700 text-white py-2 rounded">
216
+ <i class="fas fa-save mr-2"></i> Save Game
217
+ </button>
218
+ </div>
219
+
220
+ <!-- Main Game Area -->
221
+ <div class="flex-1">
222
+ <!-- Game Messages -->
223
+ <div id="game-messages" class="bg-gray-800 bg-opacity-90 rounded-lg p-4 mb-4 h-40 overflow-y-auto">
224
+ <p class="text-yellow-300">Welcome to Epic RPG Adventure!</p>
225
+ <p>Create your character and begin your journey.</p>
226
+ </div>
227
+
228
+ <!-- Action Buttons -->
229
+ <div class="grid grid-cols-2 gap-4 mb-6">
230
+ <button onclick="explore()" class="bg-green-600 hover:bg-green-700 text-white font-bold py-3 px-4 rounded-lg transition-all hover:scale-105">
231
+ <i class="fas fa-binoculars mr-2"></i> Explore
232
+ </button>
233
+ <button onclick="rest()" class="bg-blue-600 hover:bg-blue-700 text-white font-bold py-3 px-4 rounded-lg transition-all hover:scale-105">
234
+ <i class="fas fa-bed mr-2"></i> Rest
235
+ </button>
236
+ <button onclick="visitTown()" class="bg-yellow-600 hover:bg-yellow-700 text-white font-bold py-3 px-4 rounded-lg transition-all hover:scale-105">
237
+ <i class="fas fa-city mr-2"></i> Visit Town
238
+ </button>
239
+ <button onclick="train()" class="bg-red-600 hover:bg-red-700 text-white font-bold py-3 px-4 rounded-lg transition-all hover:scale-105">
240
+ <i class="fas fa-dumbbell mr-2"></i> Train
241
+ </button>
242
+ </div>
243
+
244
+ <!-- Combat Area -->
245
+ <div id="combat-area" class="hidden bg-gray-800 bg-opacity-90 rounded-lg p-6">
246
+ <div class="flex flex-col md:flex-row justify-between items-center mb-8">
247
+ <!-- Player -->
248
+ <div class="text-center mb-6 md:mb-0 relative">
249
+ <div class="text-6xl mb-2" id="player-combat-icon">
250
+ <i class="fas fa-user"></i>
251
  </div>
252
+ <h4 class="text-xl font-bold" id="player-combat-name">Hero</h4>
253
+ <div class="w-full bg-gray-700 rounded-full h-3 mt-2">
254
+ <div id="player-health-bar" class="health-bar bg-red-500 h-3 rounded-full" style="width: 100%"></div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
255
  </div>
256
+ <div class="text-sm" id="player-health-text">100/100</div>
257
  </div>
258
+
259
+ <!-- VS -->
260
+ <div class="text-2xl font-bold mx-4 mb-6 md:mb-0">VS</div>
261
+
262
+ <!-- Enemy -->
263
+ <div class="text-center relative">
264
+ <div class="text-6xl mb-2" id="enemy-icon">
265
+ <i class="fas fa-spider"></i>
266
+ </div>
267
+ <h4 class="text-xl font-bold" id="enemy-name">Goblin</h4>
268
+ <div class="w-full bg-gray-700 rounded-full h-3 mt-2">
269
+ <div id="enemy-health-bar" class="health-bar bg-red-500 h-3 rounded-full" style="width: 100%"></div>
270
+ </div>
271
+ <div class="text-sm" id="enemy-health-text">30/30</div>
272
+ </div>
273
+ </div>
274
+
275
+ <!-- Combat Actions -->
276
+ <div id="combat-actions" class="grid grid-cols-2 gap-4">
277
+ <button onclick="playerAttack()" class="bg-red-600 hover:bg-red-700 text-white font-bold py-3 px-4 rounded-lg">
278
+ <i class="fas fa-sword mr-2"></i> Attack
279
+ </button>
280
+ <button onclick="playerSpell()" class="bg-blue-600 hover:bg-blue-700 text-white font-bold py-3 px-4 rounded-lg">
281
+ <i class="fas fa-magic mr-2"></i> Cast Spell
282
+ </button>
283
+ <button onclick="playerDefend()" class="bg-gray-600 hover:bg-gray-700 text-white font-bold py-3 px-4 rounded-lg">
284
+ <i class="fas fa-shield-alt mr-2"></i> Defend
285
+ </button>
286
+ <button onclick="playerFlee()" class="bg-yellow-600 hover:bg-yellow-700 text-white font-bold py-3 px-4 rounded-lg">
287
+ <i class="fas fa-running mr-2"></i> Flee
288
+ </button>
289
  </div>
290
+ </div>
291
+
292
+ <!-- Town Area -->
293
+ <div id="town-area" class="hidden bg-gray-800 bg-opacity-90 rounded-lg p-6">
294
+ <h3 class="text-2xl font-bold mb-4">Town Square</h3>
295
+ <div class="grid grid-cols-1 md:grid-cols-3 gap-4">
296
+ <button onclick="visitShop()" class="bg-blue-600 hover:bg-blue-700 text-white font-bold py-3 px-4 rounded-lg">
297
+ <i class="fas fa-shopping-cart mr-2"></i> Shop
298
+ </button>
299
+ <button onclick="visitTavern()" class="bg-yellow-600 hover:bg-yellow-700 text-white font-bold py-3 px-4 rounded-lg">
300
+ <i class="fas fa-beer mr-2"></i> Tavern
301
+ </button>
302
+ <button onclick="visitGuild()" class="bg-purple-600 hover:bg-purple-700 text-white font-bold py-3 px-4 rounded-lg">
303
+ <i class="fas fa-scroll mr-2"></i> Adventurer's Guild
304
+ </button>
305
+ <button onclick="leaveTown()" class="bg-gray-600 hover:bg-gray-700 text-white font-bold py-3 px-4 rounded-lg">
306
+ <i class="fas fa-door-open mr-2"></i> Leave Town
307
+ </button>
308
+ </div>
309
+ </div>
310
+ </div>
311
+ </div>
312
+ </div>
313
 
314
+ <!-- Inventory Modal -->
315
+ <div id="inventory-modal" class="hidden fixed inset-0 bg-black bg-opacity-50 flex items-center justify-center z-50">
316
+ <div class="bg-gray-800 rounded-lg p-6 w-full max-w-2xl max-h-[80vh] overflow-y-auto">
317
+ <div class="flex justify-between items-center mb-4">
318
+ <h3 class="text-2xl font-bold">Inventory</h3>
319
+ <button onclick="closeInventory()" class="text-gray-400 hover:text-white">
320
+ <i class="fas fa-times"></i>
321
+ </button>
322
+ </div>
323
+
324
+ <div class="grid grid-cols-2 md:grid-cols-4 gap-4 mb-6">
325
+ <div class="bg-gray-700 p-4 rounded-lg text-center">
326
+ <div class="text-3xl mb-2"><i class="fas fa-sword"></i></div>
327
+ <div class="font-bold">Iron Sword</div>
328
+ <div class="text-sm text-gray-300">Attack +5</div>
329
+ <button class="mt-2 bg-blue-600 hover:bg-blue-700 text-white py-1 px-3 rounded text-sm">
330
+ Equip
331
+ </button>
332
+ </div>
333
+ <div class="bg-gray-700 p-4 rounded-lg text-center">
334
+ <div class="text-3xl mb-2"><i class="fas fa-shield-alt"></i></div>
335
+ <div class="font-bold">Wooden Shield</div>
336
+ <div class="text-sm text-gray-300">Defense +3</div>
337
+ <button class="mt-2 bg-blue-600 hover:bg-blue-700 text-white py-1 px-3 rounded text-sm">
338
+ Equip
339
+ </button>
340
+ </div>
341
+ <div class="bg-gray-700 p-4 rounded-lg text-center">
342
+ <div class="text-3xl mb-2"><i class="fas fa-flask"></i></div>
343
+ <div class="font-bold">Health Potion</div>
344
+ <div class="text-sm text-gray-300">Restores 30 HP</div>
345
+ <button class="mt-2 bg-green-600 hover:bg-green-700 text-white py-1 px-3 rounded text-sm">
346
+ Use
347
+ </button>
348
+ </div>
349
+ <div class="bg-gray-700 p-4 rounded-lg text-center">
350
+ <div class="text-3xl mb-2"><i class="fas fa-flask"></i></div>
351
+ <div class="font-bold">Mana Potion</div>
352
+ <div class="text-sm text-gray-300">Restores 20 MP</div>
353
+ <button class="mt-2 bg-green-600 hover:bg-green-700 text-white py-1 px-3 rounded text-sm">
354
+ Use
355
+ </button>
356
+ </div>
357
+ </div>
358
+
359
+ <h4 class="text-xl font-bold mb-3">Equipped Items</h4>
360
+ <div class="grid grid-cols-2 gap-4">
361
+ <div class="bg-gray-700 p-3 rounded-lg">
362
+ <div class="flex items-center">
363
+ <div class="text-2xl mr-3"><i class="fas fa-sword"></i></div>
364
+ <div>
365
  <div class="font-bold">Iron Sword</div>
366
  <div class="text-sm text-gray-300">Attack +5</div>
 
 
 
367
  </div>
368
+ </div>
369
+ </div>
370
+ <div class="bg-gray-700 p-3 rounded-lg">
371
+ <div class="flex items-center">
372
+ <div class="text-2xl mr-3"><i class="fas fa-shield-alt"></i></div>
373
+ <div>
374
  <div class="font-bold">Wooden Shield</div>
375
  <div class="text-sm text-gray-300">Defense +3</div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
376
  </div>
377
  </div>
378
  </div>
379
  </div>
380
+ </div>
381
+ </div>
382
 
383
+ <!-- Credits Modal -->
384
+ <div id="credits-modal" class="hidden fixed inset-0 bg-black bg-opacity-50 flex items-center justify-center z-50">
385
+ <div class="bg-gray-800 rounded-lg p-6 w-full max-w-md">
386
+ <div class="flex justify-between items-center mb-4">
387
+ <h3 class="text-2xl font-bold">Credits</h3>
388
+ <button onclick="hideCredits()" class="text-gray-400 hover:text-white">
389
+ <i class="fas fa-times"></i>
390
+ </button>
391
+ </div>
392
+
393
+ <div class="space-y-4">
394
+ <div>
395
+ <h4 class="text-xl font-bold text-yellow-400">Epic RPG Adventure</h4>
396
+ <p class="text-gray-300">Created with HTML, CSS, and JavaScript</p>
397
+ </div>
398
+
399
+ <div>
400
+ <h4 class="font-bold">Developer</h4>
401
+ <p class="text-gray-300">Your Name Here</p>
402
+ </div>
403
+
404
+ <div>
405
+ <h4 class="font-bold">Special Thanks</h4>
406
+ <ul class="list-disc list-inside text-gray-300">
407
+ <li>Tailwind CSS</li>
408
+ <li>Font Awesome</li>
409
+ <li>Unsplash for images</li>
410
+ </ul>
411
+ </div>
412
+
413
+ <div class="pt-4 border-t border-gray-700">
414
+ <p class="text-sm text-gray-400">© 2023 All Rights Reserved</p>
 
 
415
  </div>
416
  </div>
417
  </div>
418
+ </div>
419
+ </div>
420
 
421
+ <script>
422
+ // Game State
423
+ const gameState = {
424
+ player: {
425
+ name: '',
426
+ class: '',
427
+ gender: '',
428
+ level: 1,
429
+ exp: 0,
430
+ expToNextLevel: 100,
431
+ health: 100,
432
+ maxHealth: 100,
433
+ mana: 50,
434
+ maxMana: 50,
435
+ attack: 10,
436
+ defense: 5,
437
+ gold: 10,
438
+ inventory: [
439
+ { name: 'Iron Sword', type: 'weapon', attack: 5, icon: 'fa-s sword' },
440
+ { name: 'Wooden Shield', type: 'shield', defense: 3, icon: 'fa-shield-alt' },
441
+ { name: 'Health Potion', type: 'consumable', effect: 'heal', amount: 30, icon: 'fa-flask' },
442
+ { name: 'Mana Potion', type: 'consumable', effect: 'mana', amount: 20, icon: 'fa-flask' }
443
+ ],
444
+ equipped: {
445
+ weapon: { name: 'Iron Sword', type: 'weapon', attack: 5, icon: 'fa-sword' },
446
+ shield: { name: 'Wooden Shield', type: 'shield', defense: 3, icon: 'fa-shield-alt' }
447
+ }
448
+ },
449
+ currentEnemy: null,
450
+ inCombat: false,
451
+ gameMessages: []
452
+ };
453
 
454
+ // Cute Monstergirl Enemies
455
+ const enemies = [
456
+ { name: 'Goblin Girl', health: 30, maxHealth: 30, attack: 8, defense: 2, exp: 20, gold: 5, icon: 'fa-user-ninja' },
457
+ { name: 'Orc Girl', health: 50, maxHealth: 50, attack: 12, defense: 5, exp: 35, gold: 10, icon: 'fa-user-injured' },
458
+ { name: 'Skeleton Girl', health: 25, maxHealth: 25, attack: 10, defense: 3, exp: 25, gold: 8, icon: 'fa-skull' },
459
+ { name: 'Wolf Girl', health: 20, maxHealth: 20, attack: 7, defense: 1, exp: 15, gold: 3, icon: 'fa-paw' },
460
+ { name: 'Bandit Girl', health: 40, maxHealth: 40, attack: 11, defense: 4, exp: 30, gold: 15, icon: 'fa-user' },
461
+ { name: 'Catgirl', health: 25, maxHealth: 25, attack: 9, defense: 2, exp: 22, gold: 7, icon: 'fa-cat' },
462
+ { name: 'Bunny Girl', health: 35, maxHealth: 35, attack: 7, defense: 3, exp: 25, gold: 8, icon: 'fa-paw' },
463
+ { name: 'Fox Girl', health: 28, maxHealth: 28, attack: 10, defense: 2, exp: 24, gold: 9, icon: 'fa-paw' },
464
+ { name: 'Slime Girl', health: 45, maxHealth: 45, attack: 6, defense: 6, exp: 28, gold: 10, icon: 'fa-droplet' },
465
+ { name: 'Dragon Girl', health: 60, maxHealth: 60, attack: 15, defense: 8, exp: 50, gold: 25, icon: 'fa-dragon' }
466
+ ];
467
 
468
+ // Game Functions
469
+ function startNewGame() {
470
+ document.getElementById('main-menu').classList.add('hidden');
471
+ document.getElementById('character-creation').classList.remove('hidden');
472
+ addGameMessage('Begin your adventure by creating your character.');
473
+ }
474
 
475
+ function selectClass(characterClass) {
476
+ const cards = document.querySelectorAll('.character-card');
477
+ cards.forEach(card => card.classList.remove('ring-2', 'ring-yellow-400'));
478
+
479
+ const selectedCard = document.querySelector(`.character-card:nth-child(${characterClass === 'warrior' ? 1 : characterClass === 'mage' ? 2 : 3})`);
480
+ selectedCard.classList.add('ring-2', 'ring-yellow-400');
481
+
482
+ gameState.player.class = characterClass;
483
+
484
+ // Update stats based on class
485
+ if (characterClass === 'warrior') {
486
+ gameState.player.maxHealth = 120;
487
+ gameState.player.health = 120;
488
+ gameState.player.attack = 12;
489
+ gameState.player.defense = 8;
490
+ gameState.player.mana = 30;
491
+ gameState.player.maxMana = 30;
492
+ } else if (characterClass === 'mage') {
493
+ gameState.player.maxHealth = 70;
494
+ gameState.player.health = 70;
495
+ gameState.player.attack = 8;
496
+ gameState.player.defense = 3;
497
+ gameState.player.mana = 80;
498
+ gameState.player.maxMana = 80;
499
+ } else if (characterClass === 'rogue') {
500
+ gameState.player.maxHealth = 90;
501
+ gameState.player.health = 90;
502
+ gameState.player.attack = 10;
503
+ gameState.player.defense = 5;
504
+ gameState.player.mana = 50;
505
+ gameState.player.maxMana = 50;
 
 
 
506
  }
507
+
508
+ addGameMessage(`You selected the ${characterClass} class.`);
509
+ }
510
 
511
+ function finalizeCharacter() {
512
+ const nameInput = document.getElementById('character-name');
513
+ const genderSelect = document.getElementById('character-gender');
514
+
515
+ if (!nameInput.value.trim()) {
516
+ addGameMessage('Please enter a name for your character.', 'error');
517
+ return;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
518
  }
519
+
520
+ if (!gameState.player.class) {
521
+ addGameMessage('Please select a class for your character.', 'error');
522
+ return;
523
+ }
524
+
525
+ gameState.player.name = nameInput.value.trim();
526
+ gameState.player.gender = genderSelect.value;
527
+
528
+ // Start the game
529
+ document.getElementById('character-creation').classList.add('hidden');
530
+ document.getElementById('game-screen').classList.remove('hidden');
531
+
532
+ // Update character display
533
+ updateCharacterDisplay();
534
+
535
+ addGameMessage(`Welcome, ${gameState.player.name} the ${gameState.player.class}! Your adventure begins now.`, 'success');
536
+ }
537
 
538
+ function updateCharacterDisplay() {
539
+ // Update character panel
540
+ document.getElementById('character-display-name').textContent = gameState.player.name;
541
+ document.getElementById('character-display-class').textContent = `Class: ${capitalizeFirstLetter(gameState.player.class)}`;
542
+
543
+ // Update stats
544
+ document.getElementById('health-text').textContent = `${gameState.player.health}/${gameState.player.maxHealth}`;
545
+ document.getElementById('mana-text').textContent = `${gameState.player.mana}/${gameState.player.maxMana}`;
546
+ document.getElementById('exp-text').textContent = `${gameState.player.exp}/${gameState.player.expToNextLevel}`;
547
+ document.getElementById('level-text').textContent = gameState.player.level;
548
+ document.getElementById('gold-text').textContent = gameState.player.gold;
549
+ document.getElementById('attack-text').textContent = gameState.player.attack + (gameState.player.equipped.weapon ? gameState.player.equipped.weapon.attack : 0);
550
+ document.getElementById('defense-text').textContent = gameState.player.defense + (gameState.player.equipped.shield ? gameState.player.equipped.shield.defense : 0);
551
+
552
+ // Update health bar
553
+ const healthPercent = (gameState.player.health / gameState.player.maxHealth) * 100;
554
+ document.getElementById('health-bar').style.width = `${healthPercent}%`;
555
+
556
+ // Update mana bar
557
+ const manaPercent = (gameState.player.mana / gameState.player.maxMana) * 100;
558
+ document.getElementById('mana-bar').style.width = `${manaPercent}%`;
559
+
560
+ // Update exp bar
561
+ const expPercent = (gameState.player.exp / gameState.player.expToNextLevel) * 100;
562
+ document.getElementById('exp-bar').style.width = `${expPercent}%`;
563
+
564
+ // Update character icon based on class
565
+ const characterIcon = document.getElementById('character-icon');
566
+ const playerCombatIcon = document.getElementById('player-combat-icon');
567
+
568
+ if (gameState.player.class === 'warrior') {
569
+ characterIcon.innerHTML = '<i class="fas fa-shield-alt text-red-500"></i>';
570
+ playerCombatIcon.innerHTML = '<i class="fas fa-shield-alt text-red-500"></i>';
571
+ } else if (gameState.player.class === 'mage') {
572
+ characterIcon.innerHTML = '<i class="fas fa-hat-wizard text-blue-500"></i>';
573
+ playerCombatIcon.innerHTML = '<i class="fas fa-hat-wizard text-blue-500"></i>';
574
+ } else if (gameState.player.class === 'rogue') {
575
+ characterIcon.innerHTML = '<i class="fas fa-user-ninja text-green-500"></i>';
576
+ playerCombatIcon.innerHTML = '<i class="fas fa-user-ninja text-green-500"></i>';
 
 
 
 
577
  }
578
+
579
+ // Update player combat name
580
+ document.getElementById('player-combat-name').textContent = gameState.player.name;
581
+ }
582
 
583
+ function addGameMessage(message, type = 'info') {
584
+ const messagesDiv = document.getElementById('game-messages');
585
+ const messageElement = document.createElement('p');
586
+
587
+ if (type === 'error') {
588
+ messageElement.className = 'text-red-400';
589
+ } else if (type === 'success') {
590
+ messageElement.className = 'text-green-400';
591
+ } else if (type === 'warning') {
592
+ messageElement.className = 'text-yellow-400';
593
+ } else {
594
+ messageElement.className = 'text-gray-300';
 
 
 
 
 
 
 
 
595
  }
596
+
597
+ messageElement.textContent = message;
598
+ messagesDiv.appendChild(messageElement);
599
+ messagesDiv.scrollTop = messagesDiv.scrollHeight;
600
+
601
+ // Add to game state for saving
602
+ gameState.gameMessages.push(message);
603
+ }
604
 
605
+ function explore() {
606
+ if (gameState.inCombat) {
607
+ addGameMessage('You are already in combat!', 'error');
608
+ return;
609
+ }
610
+
611
+ // 70% chance to find an enemy
612
+ if (Math.random() < 0.7) {
613
+ startCombat();
614
+ } else {
615
+ // 30% chance to find something else
616
+ const randomEvent = Math.random();
617
+
618
+ if (randomEvent < 0.5) {
619
+ // Found gold
620
+ const goldFound = Math.floor(Math.random() * 10) + 5;
621
+ gameState.player.gold += goldFound;
622
+ updateCharacterDisplay();
623
+ addGameMessage(`You found ${goldFound} gold coins on the ground!`, 'success');
624
  } else {
625
+ // Found a health potion
626
+ gameState.player.inventory.push({
627
+ name: 'Health Potion',
628
+ type: 'consumable',
629
+ effect: 'heal',
630
+ amount: 30,
631
+ icon: 'fa-flask'
632
+ });
633
+ addGameMessage('You found a Health Potion!', 'success');
 
 
 
 
 
 
 
 
 
 
 
634
  }
635
  }
636
+ }
637
 
638
+ function startCombat() {
639
+ gameState.inCombat = true;
640
+
641
+ // Select a random enemy
642
+ const randomEnemyIndex = Math.floor(Math.random() * enemies.length);
643
+ gameState.currentEnemy = {...enemies[randomEnemyIndex]};
644
+
645
+ // Update combat UI
646
+ document.getElementById('combat-area').classList.remove('hidden');
647
+ document.getElementById('enemy-name').textContent = gameState.currentEnemy.name;
648
+ document.getElementById('enemy-health-text').textContent = `${gameState.currentEnemy.health}/${gameState.currentEnemy.maxHealth}`;
649
+ document.getElementById('enemy-health-bar').style.width = '100%';
650
+ document.getElementById('enemy-icon').innerHTML = `<i class="fas ${gameState.currentEnemy.icon}"></i>`;
651
+
652
+ // Update player stats in combat
653
+ document.getElementById('player-health-text').textContent = `${gameState.player.health}/${gameState.player.maxHealth}`;
654
+ const healthPercent = (gameState.player.health / gameState.player.maxHealth) * 100;
655
+ document.getElementById('player-health-bar').style.width = `${healthPercent}%`;
656
+
657
+ addGameMessage(`A wild ${gameState.currentEnemy.name} appears!`, 'warning');
658
+ }
659
 
660
+ function playerAttack() {
661
+ if (!gameState.inCombat || !gameState.currentEnemy) {
662
+ addGameMessage('There is nothing to attack!', 'error');
663
+ return;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
664
  }
665
+
666
+ // Calculate player damage
667
+ const playerAttackPower = gameState.player.attack + (gameState.player.equipped.weapon ? gameState.player.equipped.weapon.attack : 0);
668
+ const damage = Math.max(1, playerAttackPower - Math.floor(gameState.currentEnemy.defense / 2));
669
+
670
+ // Apply damage to enemy
671
+ gameState.currentEnemy.health -= damage;
672
+
673
+ // Update enemy health bar
674
+ const enemyHealthPercent = (gameState.currentEnemy.health / gameState.currentEnemy.maxHealth) * 100;
675
+ document.getElementById('enemy-health-bar').style.width = `${Math.max(0, enemyHealthPercent)}%`;
676
+ document.getElementById('enemy-health-text').textContent = `${Math.max(0, gameState.currentEnemy.health)}/${gameState.currentEnemy.maxHealth}`;
677
+
678
+ // Show damage text
679
+ showDamageText(document.querySelector('#combat-area .relative:last-child'), damage);
680
+
681
+ addGameMessage(`You attack the ${gameState.currentEnemy.name} for ${damage} damage!`, 'success');
682
+
683
+ // Check if enemy is defeated
684
+ if (gameState.currentEnemy.health <= 0) {
685
+ enemyDefeated();
686
+ return;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
687
  }
688
+
689
+ // Enemy attacks back
690
+ setTimeout(() => {
691
+ enemyAttack();
692
+ }, 1000);
693
+ }
694
 
695
+ function playerSpell() {
696
+ if (!gameState.inCombat || !gameState.currentEnemy) {
697
+ addGameMessage('There is nothing to attack!', 'error');
698
+ return;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
699
  }
700
+
701
+ if (gameState.player.mana < 15) {
702
+ addGameMessage('Not enough mana to cast a spell!', 'error');
703
+ return;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
704
  }
705
+
706
+ // Use mana
707
+ gameState.player.mana -= 15;
708
+ updateCharacterDisplay();
709
+
710
+ // Calculate spell damage (more powerful than regular attack)
711
+ let spellDamage;
712
+ if (gameState.player.class === 'mage') {
713
+ spellDamage = Math.max(3, 15 + Math.floor(Math.random() * 10));
714
+ } else {
715
+ spellDamage = Math.max(3, 10 + Math.floor(Math.random() * 5));
716
+ }
717
+
718
+ // Apply damage to enemy
719
+ gameState.currentEnemy.health -= spellDamage;
720
+
721
+ // Update enemy health bar
722
+ const enemyHealthPercent = (gameState.currentEnemy.health / gameState.currentEnemy.maxHealth) * 100;
723
+ document.getElementById('enemy-health-bar').style.width = `${Math.max(0, enemyHealthPercent)}%`;
724
+ document.getElementById('enemy-health-text').textContent = `${Math.max(0, gameState.currentEnemy.health)}/${gameState.currentEnemy.maxHealth}`;
725
+
726
+ // Show damage text
727
+ showDamageText(document.querySelector('#combat-area .relative:last-child'), spellDamage, 'blue');
728
+
729
+ addGameMessage(`You cast a spell on the ${gameState.currentEnemy.name} for ${spellDamage} damage!`, 'success');
730
+
731
+ // Check if enemy is defeated
732
+ if (gameState.currentEnemy.health <= 0) {
733
+ enemyDefeated();
734
+ return;
735
+ }
736
+
737
+ // Enemy attacks back
738
+ setTimeout(() => {
739
+ enemyAttack();
740
+ }, 1000);
741
+ }
742
 
743
+ function playerDefend() {
744
+ if (!gameState.inCombat || !gameState.currentEnemy) {
745
+ addGameMessage('There is nothing to defend against!', 'error');
746
+ return;
747
+ }
748
+
749
+ addGameMessage(`You take a defensive stance, reducing damage from the next attack.`, 'info');
750
+
751
+ // Enemy attacks with reduced damage
752
+ setTimeout(() => {
753
+ // Calculate enemy damage (reduced by 50% when defending)
754
+ const enemyDamage = Math.max(1, Math.floor((gameState.currentEnemy.attack - (gameState.player.defense + (gameState.player.equipped.shield ? gameState.player.equipped.shield.defense : 0))) / 2));
755
 
756
  // Apply damage to player
757
  gameState.player.health -= enemyDamage;
 
766
  // Show damage text
767
  showDamageText(document.querySelector('#combat-area .relative:first-child'), enemyDamage);
768
 
769
+ addGameMessage(`The ${gameState.currentEnemy.name} attacks you for ${enemyDamage} damage (reduced by your defense)!`, 'warning');
770
 
771
  // Check if player is defeated
772
  if (gameState.player.health <= 0) {
773
  playerDefeated();
774
  }
775
+ }, 1000);
776
+ }
777
 
778
+ function playerFlee() {
779
+ if (!gameState.inCombat || !gameState.currentEnemy) {
780
+ addGameMessage('There is nothing to flee from!', 'error');
781
+ return;
 
 
 
 
 
 
 
 
 
 
782
  }
783
+
784
+ // 60% chance to flee successfully
785
+ if (Math.random() < 0.6) {
786
+ addGameMessage(`You successfully fled from the ${gameState.currentEnemy.name}!`, 'success');
 
 
 
 
 
 
 
 
 
 
 
 
787
  endCombat();
788
+ } else {
789
+ addGameMessage(`You failed to flee! The ${gameState.currentEnemy.name} attacks you!`, 'error');
790
+
791
+ // Enemy attacks
792
+ setTimeout(() => {
793
+ enemyAttack();
794
+ }, 1000);
795
  }
796
+ }
797
 
798
+ function enemyAttack() {
799
+ if (!gameState.inCombat || !gameState.currentEnemy) return;
800
+
801
+ // Calculate enemy damage
802
+ const enemyDamage = Math.max(1, gameState.currentEnemy.attack - (gameState.player.defense + (gameState.player.equipped.shield ? gameState.player.equipped.shield.defense : 0)));
803
+
804
+ // Apply damage to player
805
+ gameState.player.health -= enemyDamage;
806
+
807
+ // Update player health bar
808
+ const healthPercent = (gameState.player.health / gameState.player.maxHealth) * 100;
809
+ document.getElementById('player-health-bar').style.width = `${Math.max(0, healthPercent)}%`;
810
+ document.getElementById('player-health-text').textContent = `${Math.max(0, gameState.player.health)}/${gameState.player.maxHealth}`;
811
+ document.getElementById('health-bar').style.width = `${Math.max(0, healthPercent)}%`;
812
+ document.getElementById('health-text').textContent = `${Math.max(0, gameState.player.health)}/${gameState.player.maxHealth}`;
813
+
814
+ // Show damage text
815
+ showDamageText(document.querySelector('#combat-area .relative:first-child'), enemyDamage);
816
+
817
+ addGameMessage(`The ${gameState.currentEnemy.name} attacks you for ${enemyDamage} damage!`, 'warning');
818
+
819
+ // Check if player is defeated
820
+ if (gameState.player.health <= 0) {
821
+ playerDefeated();
822
  }
823
+ }
824
 
825
+ function enemyDefeated() {
826
+ addGameMessage(`You defeated the ${gameState.currentEnemy.name}!`, 'success');
827
+
828
+ // Gain experience and gold
829
+ gameState.player.exp += gameState.currentEnemy.exp;
830
+ gameState.player.gold += gameState.currentEnemy.gold;
831
+
832
+ addGameMessage(`Gained ${gameState.currentEnemy.exp} experience and ${gameState.currentEnemy.gold} gold.`, 'success');
833
+
834
+ // Check for level up
835
+ checkLevelUp();
836
+
837
+ // End combat
838
+ endCombat();
839
+ }
 
 
 
 
 
840
 
841
+ function playerDefeated() {
842
+ addGameMessage(`You were defeated by the ${gameState.currentEnemy.name}!`, 'error');
843
+ addGameMessage('You wake up in town, having lost some gold and experience.', 'warning');
844
+
845
+ // Penalty for dying
846
+ gameState.player.exp = Math.max(0, gameState.player.exp - 10);
847
+ gameState.player.gold = Math.max(0, gameState.player.gold - 5);
848
+
849
+ // Restore some health
850
+ gameState.player.health = Math.floor(gameState.player.maxHealth * 0.3);
851
+
852
+ // Update display
853
+ updateCharacterDisplay();
854
+
855
+ // End combat
856
+ endCombat();
857
+ }
858
+
859
+ function endCombat() {
860
+ gameState.inCombat = false;
861
+ gameState.currentEnemy = null;
862
+ document.getElementById('combat-area').classList.add('hidden');
863
+ }
864
+
865
+ function checkLevelUp() {
866
+ if (gameState.player.exp >= gameState.player.expToNextLevel) {
867
+ gameState.player.level++;
868
+ gameState.player.exp -= gameState.player.expToNextLevel;
869
+ gameState.player.expToNextLevel = Math.floor(gameState.player.expToNextLevel * 1.2);
870
+
871
+ // Improve stats
872
+ gameState.player.maxHealth += 10;
873
+ gameState.player.health = gameState.player.maxHealth;
874
+ gameState.player.maxMana += 5;
875
+ gameState.player.mana = gameState.player.maxMana;
876
+ gameState.player.attack += 2;
877
+ gameState.player.defense += 1;
878
+
879
+ addGameMessage(`Level up! You are now level ${gameState.player.level}!`, 'success');
880
+ addGameMessage('Your stats have improved!', 'info');
881
 
 
882
  updateCharacterDisplay();
883
  }
884
+ }
885
 
886
+ function rest() {
887
+ if (gameState.inCombat) {
888
+ addGameMessage('You cannot rest while in combat!', 'error');
889
+ return;
 
 
 
 
890
  }
891
+
892
+ // Restore health and mana
893
+ const healthRestored = Math.floor(gameState.player.maxHealth * 0.3);
894
+ const manaRestored = Math.floor(gameState.player.maxMana * 0.3);
895
+
896
+ gameState.player.health = Math.min(gameState.player.maxHealth, gameState.player.health + healthRestored);
897
+ gameState.player.mana = Math.min(gameState.player.maxMana, gameState.player.mana + manaRestored);
898
+
899
+ addGameMessage(`You rest and recover ${healthRestored} health and ${manaRestored} mana.`, 'success');
900
+ updateCharacterDisplay();
901
+ }
902
 
903
+ function visitTown() {
904
+ if (gameState.inCombat) {
905
+ addGameMessage('You cannot visit town while in combat!', 'error');
906
+ return;
907
  }
908
+
909
+ document.getElementById('town-area').classList.remove('hidden');
910
+ addGameMessage('You enter the town square.', 'info');
911
+ }
912
 
913
+ function leaveTown() {
914
+ document.getElementById('town-area').classList.add('hidden');
915
+ addGameMessage('You leave the town.', 'info');
916
+ }
917
 
918
+ function visitShop() {
919
+ addGameMessage('The shop is currently closed. Come back later!', 'info');
920
+ }
921
 
922
+ function visitTavern() {
923
+ addGameMessage('You enjoy a drink at the tavern and hear rumors of a dragon in the mountains.', 'info');
924
+ }
925
 
926
+ function visitGuild() {
927
+ addGameMessage('The Adventurer\'s Guild has no quests available right now.', 'info');
928
+ }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
929
 
930
+ function train() {
931
+ if (gameState.inCombat) {
932
+ addGameMessage('You cannot train while in combat!', 'error');
933
+ return;
934
  }
935
+
936
+ // Training costs gold but improves stats
937
+ if (gameState.player.gold < 5) {
938
+ addGameMessage('You need at least 5 gold to train!', 'error');
939
+ return;
940
  }
941
+
942
+ gameState.player.gold -= 5;
943
+
944
+ // Random stat improvement
945
+ const statToImprove = ['attack', 'defense'][Math.floor(Math.random() * 2)];
946
+ const improvement = 1;
947
+
948
+ if (statToImprove === 'attack') {
949
+ gameState.player.attack += improvement;
950
+ addGameMessage(`After training, your attack increased by ${improvement}! (Cost: 5 gold)`, 'success');
951
+ } else {
952
+ gameState.player.defense += improvement;
953
+ addGameMessage(`After training, your defense increased by ${improvement}! (Cost: 5 gold)`, 'success');
954
  }
955
+
956
+ updateCharacterDisplay();
957
+ }
958
 
959
+ function openInventory() {
960
+ document.getElementById('inventory-modal').classList.remove('hidden');
961
+ }
 
962
 
963
+ function closeInventory() {
964
+ document.getElementById('inventory-modal').classList.add('hidden');
965
+ }
966
+
967
+ function openQuests() {
968
+ addGameMessage('You have no active quests at the moment.', 'info');
969
+ }
970
+
971
+ function saveGame() {
972
+ localStorage.setItem('epicRpgSave', JSON.stringify(gameState));
973
+ addGameMessage('Game saved successfully!', 'success');
974
+ }
975
+
976
+ function loadGame() {
977
+ const savedGame = localStorage.getItem('epicRpgSave');
978
+
979
+ if (savedGame) {
980
+ try {
981
+ const parsedGame = JSON.parse(savedGame);
982
+ Object.assign(gameState, parsedGame);
983
+
984
+ document.getElementById('main-menu').classList.add('hidden');
985
+ document.getElementById('game-screen').classList.remove('hidden');
986
+
987
+ updateCharacterDisplay();
988
+ addGameMessage(`Welcome back, ${gameState.player.name}! Game loaded successfully.`, 'success');
989
+ } catch (e) {
990
+ addGameMessage('Failed to load saved game.', 'error');
991
+ }
992
+ } else {
993
+ addGameMessage('No saved game found.', 'error');
994
  }
995
  }
996