| <!DOCTYPE html> |
| <html lang="en"> |
| <head> |
| <meta charset="UTF-8"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Housie Game</title> |
| <script src="https://cdn.tailwindcss.com"></script> |
| <link href="https://fonts.googleapis.com/css2?family=Poppins:wght@400;600;700&display=swap" rel="stylesheet"> |
| <style> |
| @keyframes spin { |
| 0% { transform: scale(0.8) rotate(-10deg); opacity: 0; } |
| 50% { transform: scale(1.1) rotate(5deg); } |
| 100% { transform: scale(1) rotate(0deg); opacity: 1; } |
| } |
| @keyframes pulse { |
| 0% { transform: scale(1); } |
| 50% { transform: scale(1.05); } |
| 100% { transform: scale(1); } |
| } |
| .spin-animation { |
| animation: spin 0.5s ease-out; |
| } |
| .pulse-animation { |
| animation: pulse 1s infinite; |
| } |
| .highlight-number { |
| background-color: #f59e0b; |
| color: white; |
| font-weight: bold; |
| transform: scale(1.1); |
| box-shadow: 0 0 15px rgba(245, 158, 11, 0.5); |
| } |
| .number-cell { |
| transition: all 0.3s ease; |
| } |
| .number-cell:hover { |
| transform: scale(1.05); |
| } |
| body { |
| font-family: 'Poppins', sans-serif; |
| background-color: #1e40af; |
| color: white; |
| } |
| .glow-text { |
| text-shadow: 0 0 10px rgba(255, 255, 255, 0.8); |
| } |
| </style> |
| </head> |
| <body class="min-h-screen flex flex-col"> |
| |
| <div id="welcomeScreen" class="fixed inset-0 bg-blue-900 bg-opacity-95 flex flex-col items-center justify-center z-50 transition-opacity duration-500"> |
| <div class="text-center px-4"> |
| <h1 class="text-6xl md:text-8xl font-bold mb-6 text-yellow-300 glow-text">HOUSIE!</h1> |
| <p class="text-2xl md:text-3xl mb-8">Let's Play Tambola!</p> |
| <div class="max-w-2xl mx-auto bg-blue-800 p-6 rounded-xl shadow-xl mb-8"> |
| <h2 class="text-xl font-semibold mb-4">How to Play:</h2> |
| <ul class="text-left space-y-2 text-lg"> |
| <li>• The host will call out random numbers from 1 to 90</li> |
| <li>• Mark the numbers on your ticket when they're called</li> |
| <li>• First to complete a line wins! Then full house!</li> |
| </ul> |
| </div> |
| <button id="startGameBtn" class="bg-yellow-400 hover:bg-yellow-300 text-blue-900 font-bold py-4 px-8 rounded-full text-xl md:text-2xl transition-all transform hover:scale-105 shadow-lg"> |
| START GAME |
| </button> |
| </div> |
| </div> |
|
|
| |
| <div id="gameContainer" class="flex-1 flex flex-col p-4 md:p-8 hidden"> |
| |
| <header class="flex justify-between items-center mb-6"> |
| <div class="text-2xl font-bold text-yellow-300">HOUSIE GAME</div> |
| <div class="flex space-x-4"> |
| <button id="resetGameBtn" class="bg-red-500 hover:bg-red-400 text-white px-4 py-2 rounded-lg transition-all"> |
| Reset Game |
| </button> |
| <button id="undoBtn" class="bg-gray-500 hover:bg-gray-400 text-white px-4 py-2 rounded-lg transition-all"> |
| Undo Last |
| </button> |
| <button id="showAllBtn" class="bg-green-500 hover:bg-green-400 text-white px-4 py-2 rounded-lg transition-all"> |
| Show All |
| </button> |
| </div> |
| </header> |
|
|
| |
| <div class="flex-1 flex flex-col lg:flex-row gap-6"> |
| |
| <div class="lg:w-1/3 flex flex-col items-center justify-center"> |
| <div class="mb-4 text-2xl font-semibold">Current Number</div> |
| <div id="currentNumberDisplay" class="w-64 h-64 bg-white rounded-full flex items-center justify-center shadow-xl mb-6"> |
| <span id="currentNumber" class="text-8xl font-bold text-blue-900">-</span> |
| </div> |
| <div class="text-xl mb-4"> |
| Numbers left: <span id="numbersLeft" class="font-bold">90</span> |
| </div> |
| <button id="nextNumberBtn" class="bg-yellow-400 hover:bg-yellow-300 text-blue-900 font-bold py-4 px-12 rounded-full text-2xl transition-all transform hover:scale-105 shadow-lg"> |
| NEXT NUMBER |
| </button> |
| </div> |
|
|
| |
| <div class="lg:w-2/3"> |
| <div class="text-2xl font-semibold mb-4 text-center">Called Numbers</div> |
| <div id="historyBoard" class="grid grid-cols-10 gap-2 bg-blue-800 bg-opacity-50 p-4 rounded-xl"> |
| |
| </div> |
| </div> |
| </div> |
|
|
| |
| <div id="fullListModal" class="fixed inset-0 bg-black bg-opacity-75 flex items-center justify-center z-50 hidden"> |
| <div class="bg-blue-900 p-6 rounded-xl max-w-4xl w-full max-h-screen overflow-y-auto"> |
| <div class="flex justify-between items-center mb-4"> |
| <h2 class="text-2xl font-bold">All Called Numbers</h2> |
| <button id="closeFullListBtn" class="text-white hover:text-yellow-300 text-2xl">×</button> |
| </div> |
| <div id="fullListContainer" class="grid grid-cols-10 gap-2"> |
| |
| </div> |
| </div> |
| </div> |
| </div> |
|
|
| <audio id="numberSound" src="https://assets.mixkit.co/sfx/preview/mixkit-arcade-game-jump-coin-216.mp3"></audio> |
| <audio id="startSound" src="https://assets.mixkit.co/sfx/preview/mixkit-game-show-suspense-waiting-668.mp3"></audio> |
|
|
| <script> |
| |
| const gameState = { |
| calledNumbers: [], |
| remainingNumbers: Array.from({length: 90}, (_, i) => i + 1), |
| isGameStarted: false |
| }; |
| |
| |
| const welcomeScreen = document.getElementById('welcomeScreen'); |
| const gameContainer = document.getElementById('gameContainer'); |
| const currentNumberDisplay = document.getElementById('currentNumberDisplay'); |
| const currentNumber = document.getElementById('currentNumber'); |
| const historyBoard = document.getElementById('historyBoard'); |
| const numbersLeft = document.getElementById('numbersLeft'); |
| const nextNumberBtn = document.getElementById('nextNumberBtn'); |
| const resetGameBtn = document.getElementById('resetGameBtn'); |
| const undoBtn = document.getElementById('undoBtn'); |
| const showAllBtn = document.getElementById('showAllBtn'); |
| const startGameBtn = document.getElementById('startGameBtn'); |
| const fullListModal = document.getElementById('fullListModal'); |
| const fullListContainer = document.getElementById('fullListContainer'); |
| const closeFullListBtn = document.getElementById('closeFullListBtn'); |
| const numberSound = document.getElementById('numberSound'); |
| const startSound = document.getElementById('startSound'); |
| |
| |
| function initializeHistoryBoard() { |
| historyBoard.innerHTML = ''; |
| for (let i = 1; i <= 90; i++) { |
| const numberCell = document.createElement('div'); |
| numberCell.className = 'number-cell w-10 h-10 md:w-12 md:h-12 flex items-center justify-center rounded-lg bg-blue-700 cursor-pointer'; |
| numberCell.textContent = i; |
| numberCell.id = `number-${i}`; |
| historyBoard.appendChild(numberCell); |
| } |
| } |
| |
| |
| function callNextNumber() { |
| if (gameState.remainingNumbers.length === 0) { |
| alert('All numbers have been called!'); |
| return; |
| } |
| |
| |
| const randomIndex = Math.floor(Math.random() * gameState.remainingNumbers.length); |
| const calledNumber = gameState.remainingNumbers[randomIndex]; |
| |
| |
| gameState.calledNumbers.push(calledNumber); |
| gameState.remainingNumbers.splice(randomIndex, 1); |
| |
| |
| updateCurrentNumberDisplay(calledNumber); |
| updateHistoryBoard(); |
| updateNumbersLeft(); |
| |
| |
| numberSound.currentTime = 0; |
| numberSound.play(); |
| } |
| |
| |
| function updateCurrentNumberDisplay(number) { |
| currentNumberDisplay.classList.add('spin-animation'); |
| setTimeout(() => { |
| currentNumber.textContent = number; |
| currentNumberDisplay.classList.remove('spin-animation'); |
| }, 200); |
| } |
| |
| |
| function updateHistoryBoard() { |
| |
| document.querySelectorAll('.number-cell').forEach(cell => { |
| cell.classList.remove('highlight-number'); |
| }); |
| |
| |
| gameState.calledNumbers.forEach(num => { |
| const cell = document.getElementById(`number-${num}`); |
| if (cell) { |
| cell.classList.add('bg-green-500', 'text-white'); |
| } |
| }); |
| |
| |
| if (gameState.calledNumbers.length > 0) { |
| const lastCalled = gameState.calledNumbers[gameState.calledNumbers.length - 1]; |
| const lastCell = document.getElementById(`number-${lastCalled}`); |
| if (lastCell) { |
| lastCell.classList.add('highlight-number'); |
| } |
| } |
| } |
| |
| |
| function updateNumbersLeft() { |
| numbersLeft.textContent = gameState.remainingNumbers.length; |
| } |
| |
| |
| function resetGame() { |
| gameState.calledNumbers = []; |
| gameState.remainingNumbers = Array.from({length: 90}, (_, i) => i + 1); |
| gameState.isGameStarted = false; |
| |
| currentNumber.textContent = '-'; |
| initializeHistoryBoard(); |
| updateNumbersLeft(); |
| |
| welcomeScreen.classList.remove('hidden'); |
| gameContainer.classList.add('hidden'); |
| } |
| |
| |
| function undoLastNumber() { |
| if (gameState.calledNumbers.length === 0) return; |
| |
| const lastCalled = gameState.calledNumbers.pop(); |
| gameState.remainingNumbers.push(lastCalled); |
| gameState.remainingNumbers.sort((a, b) => a - b); |
| |
| if (gameState.calledNumbers.length === 0) { |
| currentNumber.textContent = '-'; |
| } else { |
| currentNumber.textContent = gameState.calledNumbers[gameState.calledNumbers.length - 1]; |
| } |
| |
| updateHistoryBoard(); |
| updateNumbersLeft(); |
| } |
| |
| |
| function showAllCalledNumbers() { |
| fullListContainer.innerHTML = ''; |
| gameState.calledNumbers.forEach(num => { |
| const numberCell = document.createElement('div'); |
| numberCell.className = 'number-cell w-10 h-10 md:w-12 md:h-12 flex items-center justify-center rounded-lg bg-green-500 text-white'; |
| numberCell.textContent = num; |
| fullListContainer.appendChild(numberCell); |
| }); |
| fullListModal.classList.remove('hidden'); |
| } |
| |
| |
| function startGame() { |
| startSound.play(); |
| welcomeScreen.classList.add('hidden'); |
| gameContainer.classList.remove('hidden'); |
| gameState.isGameStarted = true; |
| initializeHistoryBoard(); |
| } |
| |
| |
| nextNumberBtn.addEventListener('click', callNextNumber); |
| resetGameBtn.addEventListener('click', resetGame); |
| undoBtn.addEventListener('click', undoLastNumber); |
| showAllBtn.addEventListener('click', showAllCalledNumbers); |
| startGameBtn.addEventListener('click', startGame); |
| closeFullListBtn.addEventListener('click', () => { |
| fullListModal.classList.add('hidden'); |
| }); |
| |
| |
| initializeHistoryBoard(); |
| </script> |
| </html> |