| document.addEventListener('DOMContentLoaded', () => { |
| |
| const gridContainer = document.getElementById('grid-container'); |
| const targetCoordsDisplay = document.getElementById('target-coords'); |
| const feedbackDisplay = document.getElementById('feedback'); |
| const itemNameDisplay = document.getElementById('item-name'); |
| const yAxisLabelsContainer = document.getElementById('y-axis-labels'); |
| const xAxisLabelsContainer = document.getElementById('x-axis-labels'); |
| const xAxisContainer = document.getElementById('x-axis-container'); |
| const scoreDisplay = document.getElementById('score-display'); |
|
|
| |
| const gridSize = 8; |
| const cellSize = 40; |
|
|
| |
| const itemsToFind = [ |
| { name: "a sparkling diamond", emoji: "π" }, { name: "a red apple", emoji: "π" }, |
| { name: "a yummy pizza slice", emoji: "π" }, { name: "a fast rocket", emoji: "π" }, |
| { name: "a cute puppy", emoji: "πΆ" }, { name: "a bright star", emoji: "β" }, |
| { name: "a cool robot", emoji: "π€" }, { name: "a friendly ghost", emoji: "π»" }, |
| { name: "a birthday cake", emoji: "π" }, { name: "a magical unicorn", emoji: "π¦" } |
| ]; |
| const totalItems = itemsToFind.length; |
|
|
| |
| let targetX = -1, targetY = -1, currentItemIndex = 0, foundCurrent = false, score = 0; |
|
|
| |
| function initializeGameArea() { |
| gridContainer.innerHTML = ''; |
| xAxisLabelsContainer.innerHTML = ''; |
| yAxisLabelsContainer.innerHTML = ''; |
| score = 0; |
| currentItemIndex = 0; |
| updateScoreDisplay(); |
|
|
| document.documentElement.style.setProperty('--cell-size', `${cellSize}px`); |
|
|
| const gridTotalSize = gridSize * cellSize; |
| const yAxisWidth = 20; |
| const yAxisMargin = 5; |
|
|
| |
| gridContainer.style.width = `${gridTotalSize}px`; |
| gridContainer.style.height = `${gridTotalSize}px`; |
| gridContainer.style.display = 'grid'; |
| gridContainer.style.gridTemplateColumns = `repeat(${gridSize}, ${cellSize}px)`; |
| gridContainer.style.gridTemplateRows = `repeat(${gridSize}, ${cellSize}px)`; |
|
|
| |
| yAxisLabelsContainer.style.height = `${gridTotalSize}px`; |
| xAxisLabelsContainer.style.width = `${gridTotalSize}px`; |
| xAxisContainer.style.width = `${yAxisWidth + yAxisMargin + gridTotalSize}px`; |
| xAxisLabelsContainer.style.marginLeft = `${yAxisWidth + yAxisMargin}px`; |
|
|
| |
| for (let y = 1; y <= gridSize; y++) { |
| const label = document.createElement('div'); |
| label.classList.add('axis-label', 'y-axis-label'); |
| label.textContent = y; |
| label.style.height = `${cellSize}px`; |
| yAxisLabelsContainer.appendChild(label); |
| } |
|
|
| |
| for (let x = 1; x <= gridSize; x++) { |
| const label = document.createElement('div'); |
| label.classList.add('axis-label', 'x-axis-label'); |
| label.textContent = x; |
| label.style.width = `${cellSize}px`; |
| xAxisLabelsContainer.appendChild(label); |
| } |
|
|
| |
| for (let y = gridSize; y >= 1; y--) { |
| for (let x = 1; x <= gridSize; x++) { |
| const cell = document.createElement('div'); |
| cell.classList.add('grid-cell'); |
| cell.dataset.x = x; cell.dataset.y = y; |
| cell.style.width = `${cellSize}px`; cell.style.height = `${cellSize}px`; |
| cell.addEventListener('click', handleCellClick); |
| gridContainer.appendChild(cell); |
| } |
| } |
| console.log(`Grid (${gridSize}x${gridSize}), Axes, and Score Initialized.`); |
| } |
|
|
| |
| function updateScoreDisplay() { |
| scoreDisplay.textContent = `Score: ${score} / ${totalItems}`; |
| } |
|
|
| |
| function setNewTarget() { |
| foundCurrent = false; |
| if (currentItemIndex >= totalItems) { |
| let finalMessage = `All done! Your final score: ${score} / ${totalItems}! π`; |
| if (score === totalItems) finalMessage += " Perfect score! π₯³"; |
| else if (score >= totalItems * 0.7) finalMessage += " Great job! π"; |
| feedbackDisplay.textContent = finalMessage; |
| feedbackDisplay.className = 'correct-feedback'; |
| targetCoordsDisplay.textContent = "(β,β)"; |
| itemNameDisplay.textContent = 'all the items'; |
| return; |
| } |
| const currentItem = itemsToFind[currentItemIndex]; |
| let newTargetFound = false, attempts = 0; |
| const maxAttempts = gridSize * gridSize * 2; |
| while (!newTargetFound && attempts < maxAttempts) { |
| targetX = Math.floor(Math.random() * gridSize) + 1; |
| targetY = Math.floor(Math.random() * gridSize) + 1; |
| const potentialCell = gridContainer.querySelector(`.grid-cell[data-x="${targetX}"][data-y="${targetY}"]`); |
| if (potentialCell && potentialCell.textContent.trim() === '') { newTargetFound = true; } |
| attempts++; |
| if(attempts >= maxAttempts){ |
| let allFilled = true; |
| gridContainer.querySelectorAll('.grid-cell').forEach(cell => { if(cell.textContent === '') allFilled = false; }); |
| if(allFilled) { console.warn("Grid appears full!"); break; } |
| else { attempts = 0; } |
| } |
| } |
| if (!newTargetFound) { |
| console.error("Could not find an empty cell!"); |
| feedbackDisplay.textContent = "Uh oh, map is full! Refresh maybe?"; |
| return; |
| } |
| itemNameDisplay.textContent = currentItem.name; |
| targetCoordsDisplay.textContent = `(${targetX}, ${targetY})`; |
| feedbackDisplay.textContent = `Where is ${currentItem.name}? (${currentItemIndex + 1}/${totalItems})`; |
| feedbackDisplay.className = ''; |
| document.querySelectorAll('.grid-cell').forEach(cell => { |
| cell.classList.remove('just-found', 'incorrect'); |
| }); |
| console.log(`Round ${currentItemIndex + 1}: Find ${currentItem.name} at (${targetX}, ${targetY})`); |
| } |
|
|
| |
| function handleCellClick(event) { |
| if (foundCurrent || currentItemIndex >= totalItems) return; |
| const clickedCell = event.target; |
| if (clickedCell.classList.contains('found-item')) return; |
|
|
| const clickedX = parseInt(clickedCell.dataset.x); |
| const clickedY = parseInt(clickedCell.dataset.y); |
| document.querySelectorAll('.grid-cell.incorrect').forEach(cell => { cell.classList.remove('incorrect'); }); |
|
|
| if (clickedX === targetX && clickedY === targetY) { |
| foundCurrent = true; score++; updateScoreDisplay(); |
| const currentItem = itemsToFind[currentItemIndex]; |
| feedbackDisplay.textContent = `You found ${currentItem.name}! π`; |
| feedbackDisplay.className = 'correct-feedback'; |
| clickedCell.textContent = currentItem.emoji; |
| clickedCell.classList.add('just-found'); |
| setTimeout(() => { |
| clickedCell.classList.remove('just-found'); |
| clickedCell.classList.add('found-item'); |
| }, 600); |
| currentItemIndex++; |
| setTimeout(setNewTarget, 1800); |
| } else { |
| feedbackDisplay.textContent = "Not quite! Try again. π€"; |
| feedbackDisplay.className = 'incorrect-feedback'; |
| clickedCell.classList.add('incorrect'); |
| setTimeout(() => { |
| if (clickedCell.classList.contains('incorrect')) { clickedCell.classList.remove('incorrect'); } |
| }, 500); |
| } |
| } |
|
|
| |
| initializeGameArea(); |
| setNewTarget(); |
|
|
| }); |