Neu: Emoji Doodle Jump
This commit is contained in:
		
							
								
								
									
										321
									
								
								emoji_jump/index.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										321
									
								
								emoji_jump/index.html
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,321 @@ | ||||
| <!DOCTYPE html> | ||||
| <html lang="de"> | ||||
| <head> | ||||
|     <meta charset="UTF-8"> | ||||
|     <meta name="viewport" content="width=device-width, initial-scale=1.0"> | ||||
|     <title>Emoji Doodle Jump</title> | ||||
|     <script src="https://html2canvas.hertzen.com/dist/html2canvas.min.js"></script> | ||||
|     <style> | ||||
|         body { | ||||
|             margin: 0; | ||||
|             overflow: hidden; | ||||
|             background: #f0f0f0; | ||||
|             font-family: Arial, sans-serif; | ||||
|             touch-action: none; | ||||
|         } | ||||
|          | ||||
|         #gameContainer { | ||||
|             position: relative; | ||||
|             width: 320px; | ||||
|             height: 480px; | ||||
|             margin: 20px auto; | ||||
|         } | ||||
|  | ||||
|         #canvas { | ||||
|             background: linear-gradient(#87CEEB, #E0F6FF); | ||||
|             border-radius: 10px; | ||||
|         } | ||||
|  | ||||
|         #lives { | ||||
|             position: absolute; | ||||
|             top: 10px; | ||||
|             left: 10px; | ||||
|             font-size: 24px; | ||||
|         } | ||||
|  | ||||
|         #score { | ||||
|             position: absolute; | ||||
|             top: 10px; | ||||
|             right: 10px; | ||||
|             font-size: 24px; | ||||
|             color: white; | ||||
|         } | ||||
|  | ||||
|         .popup { | ||||
|             position: fixed; | ||||
|             top: 50%; | ||||
|             left: 50%; | ||||
|             transform: translate(-50%, -50%); | ||||
|             background: white; | ||||
|             padding: 20px; | ||||
|             border-radius: 10px; | ||||
|             box-shadow: 0 0 20px rgba(0,0,0,0.2); | ||||
|             text-align: center; | ||||
|             display: none; | ||||
|         } | ||||
|  | ||||
|         #charSelect { | ||||
|             display: flex; | ||||
|             gap: 10px; | ||||
|             font-size: 40px; | ||||
|             cursor: pointer; | ||||
|         } | ||||
|  | ||||
|         .emoji:hover { | ||||
|             transform: scale(1.2); | ||||
|         } | ||||
|  | ||||
|         button { | ||||
|             background: #4CAF50; | ||||
|             color: white; | ||||
|             border: none; | ||||
|             padding: 10px 20px; | ||||
|             border-radius: 5px; | ||||
|             cursor: pointer; | ||||
|             margin: 5px; | ||||
|         } | ||||
|  | ||||
|         #instructions { | ||||
|             max-width: 320px; | ||||
|             margin: 20px auto; | ||||
|             padding: 10px; | ||||
|         } | ||||
|     </style> | ||||
| </head> | ||||
| <body> | ||||
|     <div id="gameContainer"> | ||||
|         <div id="lives">❤️❤️❤️</div> | ||||
|         <div id="score">0</div> | ||||
|         <canvas id="canvas" width="320" height="480"></canvas> | ||||
|     </div> | ||||
|  | ||||
|     <div id="charSelectPopup" class="popup"> | ||||
|         <h3>Wähle deinen Charakter!</h3> | ||||
|         <div id="charSelect"> | ||||
|             <div class="emoji">💩</div> | ||||
|             <div class="emoji">🤡</div> | ||||
|             <div class="emoji">👾</div> | ||||
|             <div class="emoji">🍌</div> | ||||
|         </div> | ||||
|     </div> | ||||
|  | ||||
|     <div id="gameOverPopup" class="popup"> | ||||
|         <h3>Game Over!</h3> | ||||
|         <p>Highscore: <span id="highscore">0</span></p> | ||||
|         <button onclick="takeScreenshot()">Screenshot</button> | ||||
|         <button onclick="startGame()">Neustart</button> | ||||
|     </div> | ||||
|  | ||||
|     <div id="instructions"> | ||||
|         <h3>Anleitung:</h3> | ||||
|         <p>Steuere mit Maus/Touch nach links/rechts<br> | ||||
|            Sammle Punkte indem du höher springst<br> | ||||
|            Vermeide Gegner 💀👻👽<br> | ||||
|            Zerbrechliche Plattformen brechen!<br> | ||||
|            3 Leben ❤️ - Bei 0 ist Spiel vorbei</p> | ||||
|     </div> | ||||
|  | ||||
|     <script> | ||||
|         let canvas = document.getElementById('canvas'); | ||||
|         let ctx = canvas.getContext('2d'); | ||||
|         let player = { x: 160, y: 400, vy: 0, character: '🍌' }; | ||||
|         let platforms = []; | ||||
|         let enemies = []; | ||||
|         let lives = 3; | ||||
|         let score = 0; | ||||
|         let highscore = localStorage.getItem('highscore') || 0; | ||||
|         let touchStartX = 0; | ||||
|      | ||||
|         function init() { | ||||
|             document.getElementById('charSelectPopup').style.display = 'block'; | ||||
|         } | ||||
|      | ||||
|         function startGame() { | ||||
|             document.getElementById('gameOverPopup').style.display = 'none'; | ||||
|             document.getElementById('charSelectPopup').style.display = 'block'; | ||||
|         } | ||||
|      | ||||
|         function initGame() { | ||||
|             document.getElementById('charSelectPopup').style.display = 'none'; | ||||
|             lives = 3; | ||||
|             score = 0; | ||||
|             player.y = 400; | ||||
|             player.vy = -8; | ||||
|             platforms = []; | ||||
|             enemies = []; | ||||
|              | ||||
|             // Initialplatformen unter dem Spieler | ||||
|             for(let i = 0; i < 8; i++) { | ||||
|                 platforms.push({ | ||||
|                     x: Math.random() * 290, | ||||
|                     y: 400 + i * 80, | ||||
|                     type: Math.random() < 0.2 && i > 2 ? 'breaking' : 'normal' | ||||
|                 }); | ||||
|             } | ||||
|      | ||||
|             // Positioniere Spieler auf erster Plattform | ||||
|             player.x = platforms[0].x + 30; | ||||
|             player.y = platforms[0].y - 30; | ||||
|              | ||||
|             gameLoop(); | ||||
|             updateDisplay(); | ||||
|         } | ||||
|      | ||||
|         function gameLoop() { | ||||
|             update(); | ||||
|             draw(); | ||||
|             if(lives > 0) requestAnimationFrame(gameLoop); | ||||
|             else showGameOver(); | ||||
|         } | ||||
|      | ||||
|         function update() { | ||||
|             // Physik-Update | ||||
|             player.y += player.vy; | ||||
|             player.vy += 0.2; | ||||
|      | ||||
|             // Begrenze X-Position des Spielers | ||||
|             player.x = Math.max(20, Math.min(300, player.x)); | ||||
|      | ||||
|             // Plattform-Kollision | ||||
|             platforms.forEach((p, i) => { | ||||
|                 if(player.vy > 0 &&  | ||||
|                    player.x + 20 > p.x &&  | ||||
|                    player.x - 20 < p.x + 60 && | ||||
|                    player.y + 40 > p.y &&  | ||||
|                    player.y + 40 < p.y + 15) { | ||||
|                     if(p.type === 'breaking') platforms.splice(i, 1); | ||||
|                     player.vy = -8; | ||||
|                     score += 10; | ||||
|                     updateDisplay(); | ||||
|                 } | ||||
|             }); | ||||
|      | ||||
|             // Plattform-Generierung | ||||
|             if (platforms.length > 0) {  // Prüfe ob Plattformen existieren | ||||
|                 let lowestPlatform = Math.max(...platforms.map(p => p.y)); | ||||
|                 while(platforms.length < 15) { | ||||
|                     const newY = Math.min(...platforms.map(p => p.y)) - 80; | ||||
|                     platforms.unshift({ | ||||
|                         x: Math.random() * 290, | ||||
|                         y: newY, | ||||
|                         type: Math.random() < (score > 500 ? 0.4 : score > 200 ? 0.3 : 0.2) ? 'breaking' : 'normal' | ||||
|                     }); | ||||
|                 } | ||||
|             } | ||||
|      | ||||
|             // Entferne alte Plattformen | ||||
|             platforms = platforms.filter(p => p.y < 600); | ||||
|      | ||||
|             // Gegner-Logik | ||||
|             enemies.forEach((e, i) => { | ||||
|                 if(Math.abs(player.x - e.x) < 30 && Math.abs(player.y - e.y) < 30) { | ||||
|                     lives--; | ||||
|                     enemies.splice(i, 1); | ||||
|                     updateDisplay(); | ||||
|                 } | ||||
|                 e.x += e.vx; | ||||
|                 if(e.x < 0 || e.x > 300) e.vx *= -1; | ||||
|             }); | ||||
|      | ||||
|             // Generiere neue Gegner | ||||
|             if(Math.random() < 0.005 && score > 200 && enemies.length < 3) {  // Reduzierte Wahrscheinlichkeit und max 3 Gegner | ||||
|                 enemies.push({ | ||||
|                     x: Math.random() * 300, | ||||
|                     y: player.y - 500, | ||||
|                     vx: Math.random() * 2 - 1  // Langsamere Bewegung | ||||
|                 }); | ||||
|             } | ||||
|  | ||||
|             // Entferne Gegner die zu weit unten sind | ||||
|             enemies = enemies.filter(e => e.y < 600); | ||||
|      | ||||
|             // Bildlauf-System | ||||
|             if(player.y < 200) { | ||||
|                 const scrollAmount = Math.floor(200 - player.y); | ||||
|                 player.y = 200; | ||||
|                 platforms.forEach(p => p.y += scrollAmount); | ||||
|                 enemies.forEach(e => e.y += scrollAmount); | ||||
|                 score = Math.floor(score + scrollAmount); | ||||
|             } | ||||
|      | ||||
|             // Spielende-Check | ||||
|             if(player.y > 600) lives = 0; | ||||
|         } | ||||
|      | ||||
|         function draw() { | ||||
|             ctx.clearRect(0, 0, 320, 480); | ||||
|              | ||||
|             // Zeichne Plattformen | ||||
|             platforms.forEach(p => { | ||||
|                 ctx.fillStyle = p.type === 'breaking' ? '#ff5555' : '#55ff55'; | ||||
|                 ctx.fillRect(p.x, p.y, 60, 10); | ||||
|             }); | ||||
|      | ||||
|             // Zeichne Gegner | ||||
|             enemies.forEach(e => { | ||||
|                 ctx.font = '30px Arial'; | ||||
|                 ctx.fillText(['💀','👻','👽'][Math.floor(Math.random()*3)], e.x, e.y); | ||||
|             }); | ||||
|      | ||||
|             // Zeichne Spieler | ||||
|             ctx.font = '40px Arial'; | ||||
|             ctx.fillText(player.character, player.x-20, player.y); | ||||
|         } | ||||
|  | ||||
|         function updateDisplay() { | ||||
|             document.getElementById('score').textContent = Math.floor(score); | ||||
|             document.getElementById('lives').innerHTML = '❤️'.repeat(lives) + '🖤'.repeat(3-lives); | ||||
|             if(score > highscore) { | ||||
|                 highscore = Math.floor(score); | ||||
|                 localStorage.setItem('highscore', highscore); | ||||
|             } | ||||
|         } | ||||
|  | ||||
|         function showGameOver() { | ||||
|             document.getElementById('gameOverPopup').style.display = 'block'; | ||||
|             document.getElementById('highscore').textContent = highscore; | ||||
|         } | ||||
|  | ||||
|         function takeScreenshot() { | ||||
|             html2canvas(document.querySelector("#gameContainer")).then(canvas => { | ||||
|                 let link = document.createElement('a'); | ||||
|                 link.download = 'doodle-score.png'; | ||||
|                 link.href = canvas.toDataURL(); | ||||
|                 link.click(); | ||||
|             }); | ||||
|         } | ||||
|  | ||||
|         // Event Listeners | ||||
|         document.getElementById('charSelect').addEventListener('click', (e) => { | ||||
|             if(e.target.classList.contains('emoji')) { | ||||
|                 player.character = e.target.textContent; | ||||
|                 initGame(); | ||||
|             } | ||||
|         }); | ||||
|  | ||||
|         // Controls | ||||
|         canvas.addEventListener('mousedown', e => { | ||||
|             touchStartX = e.clientX; | ||||
|         }); | ||||
|  | ||||
|         canvas.addEventListener('mousemove', e => { | ||||
|             if(e.buttons === 1) { | ||||
|                 player.x += e.movementX; | ||||
|             } | ||||
|         }); | ||||
|  | ||||
|         canvas.addEventListener('touchstart', e => { | ||||
|             touchStartX = e.touches[0].clientX; | ||||
|         }); | ||||
|  | ||||
|         canvas.addEventListener('touchmove', e => { | ||||
|             let touch = e.touches[0]; | ||||
|             player.x += touch.clientX - touchStartX; | ||||
|             touchStartX = touch.clientX; | ||||
|             e.preventDefault(); | ||||
|         }, { passive: false }); | ||||
|  | ||||
|         init(); | ||||
|     </script> | ||||
| </body> | ||||
| </html> | ||||
		Reference in New Issue
	
	Block a user