init: initialize project - 2 games

This commit is contained in:
Ahmad EL Masri 2025-06-05 06:32:33 +02:00
commit 4740d0003b
Signed by: ahmad
GPG key ID: 592CDF2A42C69D74
7 changed files with 1784 additions and 0 deletions

1
.gitignore vendored Normal file
View file

@ -0,0 +1 @@
.vscode/

215
find-and-write/index.html Normal file
View file

@ -0,0 +1,215 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Classroom Word Search Game</title>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/18.2.0/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/18.2.0/umd/react-dom.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/babel-standalone/7.23.5/babel.min.js"></script>
<link href="https://cdn.jsdelivr.net/npm/tailwindcss@2.2.19/dist/tailwind.min.css" rel="stylesheet">
</head>
<body>
<div id="root"></div>
<script type="text/babel">
const { useState, useEffect } = React;
function WordSearchGame() {
const wordLists = {
animals: ['elephant', 'giraffe', 'penguin', 'dolphin', 'kangaroo', 'octopus', 'butterfly', 'zebra'],
colors: ['purple', 'orange', 'yellow', 'green', 'blue', 'red', 'brown', 'pink'],
food: ['pizza', 'banana', 'cookie', 'apple', 'sandwich', 'pasta', 'carrot', 'burger'],
school: ['pencil', 'eraser', 'notebook', 'teacher', 'student', 'library', 'classroom', 'homework'],
// Arabic categories for beginners
arabicAnimals: ['فيل', 'أسد', 'قطة', 'كلب', 'زرافة', 'فأر', 'سمكة', 'طائر'],
arabicColors: ['أحمر', 'أزرق', 'أخضر', 'أصفر', 'أسود', 'أبيض', 'بني', 'برتقالي'],
arabicNumbers: ['واحد', 'اثنان', 'ثلاثة', 'أربعة', 'خمسة', 'ستة', 'سبعة', 'ثمانية'],
arabicGreetings: ['مرحبا', 'صباح الخير', 'مساء الخير', 'شكرا', 'عفوا', 'مع السلامة', 'كيف حالك', 'أنا بخير']
};
const [category, setCategory] = useState('animals');
const [isArabic, setIsArabic] = useState(false);
const [displayedWords, setDisplayedWords] = useState([]);
const [timer, setTimer] = useState(300);
const randomPosition = () => ({
left: `${Math.random() * 70 + 15}%`,
top: `${Math.random() * 50 + 20}%`, // Reduced vertical range to avoid bottom section
transform: `rotate(${Math.random() * 360}deg)`
});
useEffect(() => {
// When language is toggled, update to appropriate category
if (isArabic && !category.startsWith('arabic')) {
setCategory('arabicAnimals');
} else if (!isArabic && category.startsWith('arabic')) {
setCategory('animals');
}
}, [isArabic]);
useEffect(() => {
const words = wordLists[category].map((word, index) => ({
id: index,
text: word,
...randomPosition()
}));
setDisplayedWords(words);
}, [category]);
useEffect(() => {
const interval = setInterval(() => {
setTimer((prev) => (prev > 0 ? prev - 1 : 0));
}, 1000);
return () => clearInterval(interval);
}, []);
// Reset timer when language changes
useEffect(() => {
setTimer(300);
}, [isArabic]);
const changeCategory = () => {
// Filter categories based on language selection
const categories = Object.keys(wordLists).filter(cat =>
isArabic ? cat.startsWith('arabic') : !cat.startsWith('arabic')
);
const currentIndex = categories.indexOf(category);
const nextIndex = (currentIndex + 1) % categories.length;
setCategory(categories[nextIndex]);
setTimer(300);
};
const toggleLanguage = () => {
setIsArabic(!isArabic);
// Set to first category of the selected language
const categories = Object.keys(wordLists).filter(cat =>
!isArabic ? cat.startsWith('arabic') : !cat.startsWith('arabic')
);
setCategory(categories[0]);
setTimer(300);
};
// Format category name for display
const formatCategoryName = (cat) => {
if (cat.startsWith('arabic')) {
// Convert arabicAnimals to "Arabic Animals"
return cat.replace('arabic', 'Arabic ').replace(/([A-Z])/g, ' $1').trim();
}
return cat;
};
return (
<div className="relative w-full h-screen bg-gray-100 overflow-hidden">
<div className="absolute top-0 left-0 right-0 p-4 bg-white shadow-md flex justify-between items-center">
<div className="flex items-center gap-2">
<span className="text-2xl">📚</span>
<span className="text-2xl font-bold">Find and Write: {formatCategoryName(category)}</span>
</div>
<div className="flex items-center gap-4">
<button
onClick={toggleLanguage}
className="px-4 py-2 bg-green-500 text-white rounded hover:bg-green-600"
>
{isArabic ? "Switch to English" : "Switch to Arabic"}
</button>
<button
onClick={changeCategory}
className="px-4 py-2 bg-blue-500 text-white rounded hover:bg-blue-600"
>
Change Category
</button>
<div className="text-xl">
Words to find: {wordLists[category].length}
</div>
<div className="text-xl">
Time: {Math.floor(timer / 60)}:{(timer % 60).toString().padStart(2, '0')}
</div>
</div>
</div>
<div className="absolute top-20 left-4 right-4 bg-yellow-100 p-4 rounded-lg shadow">
<p className="text-lg">
🤫 Silently find and write down as many {formatCategoryName(category)} as you can!
Look carefully - words might be rotated!
{isArabic && (
<span className="block mt-2 text-gray-700">
<strong>Beginner tip:</strong> Try to find and memorize these Arabic words. Check the help section at the bottom for learning tips!
</span>
)}
</p>
</div>
<div className="mt-32 relative w-full h-full">
{displayedWords.map((word) => (
<div
key={word.id}
className={`absolute font-bold select-none ${isArabic ? 'text-3xl' : 'text-4xl'} text-gray-700`}
style={{
left: word.left,
top: word.top,
transform: word.transform,
direction: isArabic ? 'rtl' : 'ltr',
fontFamily: isArabic ? "'Arial', 'Tahoma', sans-serif" : 'inherit'
}}
>
{word.text}
</div>
))}
</div>
{isArabic && (
<div className="fixed bottom-0 left-0 right-0 bg-blue-100 p-2 shadow" style={{ maxHeight: '25vh', overflowY: 'auto' }}>
<button
className="absolute top-1 right-2 bg-red-500 text-white rounded-full w-6 h-6 flex items-center justify-center text-xs"
onClick={() => document.querySelector('.help-section').classList.toggle('hidden')}
>
×
</button>
<h3 className="text-lg font-bold text-center">Arabic Learning Guide</h3>
<div className="help-section grid grid-cols-1 md:grid-cols-4 gap-2 text-sm mt-1">
<div>
<strong>Animals (الحيوانات):</strong>
<ul className="list-disc pl-5">
<li>فيل - elephant</li>
<li>أسد - lion</li>
<li>قطة - cat</li>
<li>كلب - dog</li>
</ul>
</div>
<div>
<strong>Colors (الألوان):</strong>
<ul className="list-disc pl-5">
<li>أحمر - red</li>
<li>أزرق - blue</li>
<li>أخضر - green</li>
<li>أصفر - yellow</li>
</ul>
</div>
<div>
<strong>Numbers (الأرقام):</strong>
<ul className="list-disc pl-5">
<li>واحد - one</li>
<li>اثنان - two</li>
<li>ثلاثة - three</li>
<li>أربعة - four</li>
</ul>
</div>
<div>
<strong>Greetings (التحيات):</strong>
<ul className="list-disc pl-5">
<li>مرحبا - hello</li>
<li>شكرا - thank you</li>
<li>مع السلامة - goodbye</li>
<li>كيف حالك - how are you</li>
</ul>
</div>
</div>
</div>
)}
</div>
);
}
ReactDOM.render(<WordSearchGame />, document.getElementById('root'));
</script>
</body>
</html>

70
tictactoe/README.md Normal file
View file

@ -0,0 +1,70 @@
# Educational Tic Tac Toe
A Tic Tac Toe game with an educational twist! Players must correctly answer questions to make their moves.
## Features
- Classic Tic Tac Toe gameplay
- Educational questions that must be answered correctly to make a move
- Support for both True/False and Multiple Choice questions
- Full support for Arabic language
- Different question categories: General Knowledge, Math, Science, and Language
- Score tracking for multiple games
- Responsive design that works on all devices
## How to Play
1. Open `index.html` in a web browser
2. Players take turns clicking on empty cells
3. When a cell is clicked, a question appears
4. If the player answers correctly, they get to place their mark (X or O)
5. If the player answers incorrectly, their turn is skipped
6. The first player to get three marks in a row (horizontally, vertically, or diagonally) wins
7. If all cells are filled without a winner, the game is a draw
## Game Settings
You can customize the game experience using the settings panel:
### Question Type
- **True/False**: Simple true or false questions
- **Multiple Choice**: Questions with multiple options
### Language
- **English**: Questions and interface in English
- **Arabic**: Questions and interface in Arabic (with RTL support)
### Category
- **General Knowledge**: Various general knowledge questions
- **Math**: Mathematical questions and problems
- **Science**: Science-related questions
- **Language**: Questions about language and vocabulary
## Running the Game
Simply open the `index.html` file in any modern web browser:
```
firefox index.html
```
or
```
google-chrome index.html
```
## Customizing Questions
You can add or modify questions by editing the `questions.js` file. The questions are organized by:
- Language (english, arabic)
- Category (general, math, science, language)
- Type (truefalse, multiplechoice)
## Browser Compatibility
This game works in all modern browsers:
- Chrome
- Firefox
- Safari
- Edge

598
tictactoe/game.js Normal file
View file

@ -0,0 +1,598 @@
// Educational Tic Tac Toe Game
// Game variables
let currentPlayer = 'X';
let gameBoard = ['', '', '', '', '', '', '', '', ''];
let gameActive = true;
let scores = { X: 0, O: 0 };
let gameSettings = {
questionType: 'multiplechoice',
language: 'arabic',
category: 'beginners', // Changed to beginners for new users
timerSeconds: 5 // 5 seconds timer
};
// Timer variables
let timerInterval = null;
let timeLeft = 0;
// DOM Elements
const cells = document.querySelectorAll('.cell');
const player1Element = document.getElementById('player1');
const player2Element = document.getElementById('player2');
const resetButton = document.getElementById('resetBtn');
const newGameButton = document.getElementById('newGameBtn');
const questionModal = document.getElementById('questionModal');
const questionText = document.getElementById('questionText');
const answerOptions = document.getElementById('answerOptions');
const feedback = document.getElementById('feedback');
const gameOverModal = document.getElementById('gameOverModal');
const gameResult = document.getElementById('gameResult');
const playAgainButton = document.getElementById('playAgainBtn');
const applySettingsButton = document.getElementById('applySettingsBtn');
// Timer elements
const timerContainer = document.getElementById('timerContainer');
const timerBar = document.getElementById('timerBar');
const timerText = document.getElementById('timerText');
// Settings elements
const questionTypeSelect = document.getElementById('questionType');
const questionLanguageSelect = document.getElementById('questionLanguage');
const questionCategorySelect = document.getElementById('questionCategory');
const questionTimerSelect = document.getElementById('questionTimer');
// Current question and selected cell
let currentQuestion = null;
let selectedCellIndex = null;
let questionPlayer = null; // Track which player clicked the cell
// Initialize the game
function initGame() {
// Add event listeners to cells
cells.forEach(cell => {
cell.addEventListener('click', () => handleCellClick(parseInt(cell.dataset.index)));
});
// Add event listeners to buttons
resetButton.addEventListener('click', resetGame);
newGameButton.addEventListener('click', newGame);
playAgainButton.addEventListener('click', newGame);
applySettingsButton.addEventListener('click', applySettings);
// Add event listener to language select to update categories
questionLanguageSelect.addEventListener('change', updateCategoryOptions);
// Initialize settings from selects
questionTypeSelect.value = gameSettings.questionType;
questionLanguageSelect.value = gameSettings.language;
questionCategorySelect.value = gameSettings.category;
questionTimerSelect.value = gameSettings.timerSeconds;
// Update category options based on selected language
updateCategoryOptions();
// Set up the initial game state
updateGameDisplay();
// Update UI language immediately based on default settings
updateUILanguage();
// Set document direction for Arabic
if (gameSettings.language === 'arabic') {
document.documentElement.dir = 'rtl';
}
}
// Update category options based on selected language
function updateCategoryOptions() {
const language = questionLanguageSelect.value;
// Clear existing options
questionCategorySelect.innerHTML = '';
if (language === 'english') {
// Add English categories
const mathOption = document.createElement('option');
mathOption.value = 'math';
mathOption.textContent = 'Mathematics';
questionCategorySelect.appendChild(mathOption);
// Set default for English
questionCategorySelect.value = 'math';
} else if (language === 'arabic') {
// Add Arabic categories
const islamicOption = document.createElement('option');
islamicOption.value = 'islamic';
islamicOption.textContent = 'Islamic';
questionCategorySelect.appendChild(islamicOption);
const beginnersOption = document.createElement('option');
beginnersOption.value = 'beginners';
beginnersOption.textContent = 'Beginners Arabic';
questionCategorySelect.appendChild(beginnersOption);
// Set default for Arabic
questionCategorySelect.value = 'beginners';
}
}
// Handle cell click
function handleCellClick(index) {
// Ignore clicks if game is not active or cell is already filled
if (!gameActive || gameBoard[index] !== '') return;
// Store the selected cell index and current player
selectedCellIndex = index;
questionPlayer = currentPlayer; // Store which player clicked the cell
// Get a random question based on current settings
currentQuestion = getRandomQuestion(
gameSettings.language,
gameSettings.category,
gameSettings.questionType
);
// Display the question
showQuestion(currentQuestion);
}
// Show question modal
function showQuestion(question) {
// Set the question text with appropriate language attribute
questionText.textContent = question.question;
if (gameSettings.language === 'arabic') {
questionText.setAttribute('lang', 'ar');
} else {
questionText.removeAttribute('lang');
}
// Clear previous answer options and feedback
answerOptions.innerHTML = '';
feedback.textContent = '';
feedback.className = 'feedback';
// Create answer options based on question type
if (gameSettings.questionType === 'truefalse') {
// True/False question
const trueOption = document.createElement('div');
trueOption.className = 'answer-option';
trueOption.textContent = gameSettings.language === 'arabic' ? 'صحيح' : 'True';
trueOption.addEventListener('click', () => checkAnswer(true));
const falseOption = document.createElement('div');
falseOption.className = 'answer-option';
falseOption.textContent = gameSettings.language === 'arabic' ? 'خطأ' : 'False';
falseOption.addEventListener('click', () => checkAnswer(false));
answerOptions.appendChild(trueOption);
answerOptions.appendChild(falseOption);
} else {
// Multiple choice question
// Create a shuffled array of indices
const originalAnswer = question.answer;
const indices = Array.from({ length: question.options.length }, (_, i) => i);
const shuffledIndices = shuffleArray([...indices]);
// Create a mapping from shuffled positions to original positions
const shuffleMap = {};
shuffledIndices.forEach((originalIndex, newIndex) => {
shuffleMap[newIndex] = originalIndex;
});
// Display options in shuffled order
shuffledIndices.forEach((originalIndex, newIndex) => {
const optionElement = document.createElement('div');
optionElement.className = 'answer-option';
optionElement.textContent = question.options[originalIndex];
if (gameSettings.language === 'arabic') {
optionElement.setAttribute('lang', 'ar');
}
// When clicked, map back to the original index for checking
optionElement.addEventListener('click', () => checkAnswer(originalIndex, shuffleMap));
answerOptions.appendChild(optionElement);
});
}
// Show the modal
questionModal.classList.add('show');
// Setup timer if enabled
if (gameSettings.timerSeconds > 0) {
// Show timer container
timerContainer.style.display = 'block';
// Reset timer
timeLeft = gameSettings.timerSeconds;
updateTimerDisplay();
// Clear any existing timer
if (timerInterval) {
clearInterval(timerInterval);
}
// Start the timer
timerInterval = setInterval(() => {
timeLeft--;
updateTimerDisplay();
if (timeLeft <= 0) {
// Time's up
clearInterval(timerInterval);
timeOut();
}
}, 1000);
} else {
// Hide timer if disabled
timerContainer.style.display = 'none';
}
}
// Update the timer display
function updateTimerDisplay() {
// Update text
timerText.textContent = `${timeLeft}s`;
// Update progress bar
const percentage = (timeLeft / gameSettings.timerSeconds) * 100;
timerBar.style.width = `${percentage}%`;
// Change color based on time left
timerBar.className = 'timer-bar';
if (timeLeft <= Math.floor(gameSettings.timerSeconds / 3)) {
timerBar.classList.add('danger');
} else if (timeLeft <= Math.floor(gameSettings.timerSeconds / 2)) {
timerBar.classList.add('warning');
}
}
// Handle time out
function timeOut() {
// Show feedback
feedback.textContent = gameSettings.language === 'arabic'
? 'انتهى الوقت!'
: 'Time\'s up!';
feedback.classList.add('incorrect');
// Switch players after a delay
setTimeout(() => {
hideQuestionModal();
switchPlayer();
}, 1500);
}
// Check the answer
function checkAnswer(userAnswer, shuffleMap = null) {
// Clear the timer if it's running
if (timerInterval) {
clearInterval(timerInterval);
timerInterval = null;
}
// Get all answer options
const options = document.querySelectorAll('.answer-option');
// Determine if the answer is correct
let isCorrect = false;
if (gameSettings.questionType === 'truefalse') {
isCorrect = userAnswer === currentQuestion.answer;
// Highlight the selected option
options[userAnswer ? 0 : 1].classList.add('selected');
// Highlight the correct option
options[currentQuestion.answer ? 0 : 1].classList.add('correct');
// If wrong, highlight as incorrect
if (!isCorrect) {
options[userAnswer ? 0 : 1].classList.add('incorrect');
}
} else {
isCorrect = userAnswer === currentQuestion.answer;
// Find the positions in the shuffled array
let selectedPosition = -1;
let correctPosition = -1;
if (shuffleMap) {
// Find the position of the selected answer in the shuffled array
for (let i = 0; i < options.length; i++) {
if (shuffleMap[i] === userAnswer) {
selectedPosition = i;
}
if (shuffleMap[i] === currentQuestion.answer) {
correctPosition = i;
}
}
} else {
// If no shuffle map (shouldn't happen), use original positions
selectedPosition = userAnswer;
correctPosition = currentQuestion.answer;
}
// Highlight the selected option
if (selectedPosition >= 0 && selectedPosition < options.length) {
options[selectedPosition].classList.add('selected');
}
// Highlight the correct option
if (correctPosition >= 0 && correctPosition < options.length) {
options[correctPosition].classList.add('correct');
}
// If wrong, highlight as incorrect
if (!isCorrect && selectedPosition >= 0 && selectedPosition < options.length) {
options[selectedPosition].classList.add('incorrect');
}
}
// Show feedback
feedback.textContent = isCorrect
? (gameSettings.language === 'arabic' ? 'إجابة صحيحة!' : 'Correct!')
: (gameSettings.language === 'arabic' ? 'إجابة خاطئة!' : 'Incorrect!');
feedback.classList.add(isCorrect ? 'correct' : 'incorrect');
// Show explanation if available
if (currentQuestion.explanation) {
setTimeout(() => {
feedback.textContent += ' ' + currentQuestion.explanation;
}, 500);
}
// If correct, make the move after a short delay
if (isCorrect) {
setTimeout(() => {
// Make sure we're using the player who clicked the cell
if (currentPlayer !== questionPlayer) {
// If the player has changed, switch back to the original player
currentPlayer = questionPlayer;
// Update the active player display
player1Element.classList.toggle('active', currentPlayer === 'X');
player2Element.classList.toggle('active', currentPlayer === 'O');
}
makeMove(selectedCellIndex);
hideQuestionModal();
}, 1500);
} else {
// If incorrect, close the modal after a delay and switch players
setTimeout(() => {
hideQuestionModal();
// Only switch if the current player is still the one who clicked
if (currentPlayer === questionPlayer) {
switchPlayer();
}
// Reset the question player
questionPlayer = null;
}, 2000);
}
}
// Hide the question modal
function hideQuestionModal() {
// Clear the timer if it's running
if (timerInterval) {
clearInterval(timerInterval);
timerInterval = null;
}
questionModal.classList.remove('show');
}
// Make a move on the board
function makeMove(index) {
// Update the game board
gameBoard[index] = currentPlayer;
// Update the cell display
cells[index].textContent = currentPlayer;
cells[index].classList.add(currentPlayer.toLowerCase());
// Check for win or draw
if (checkWin()) {
endGame(false);
} else if (checkDraw()) {
endGame(true);
} else {
// Switch players
switchPlayer();
}
}
// Switch the current player
function switchPlayer() {
currentPlayer = currentPlayer === 'X' ? 'O' : 'X';
// Update the active player display
player1Element.classList.toggle('active');
player2Element.classList.toggle('active');
}
// Check if the current player has won
function checkWin() {
const winPatterns = [
[0, 1, 2], [3, 4, 5], [6, 7, 8], // Rows
[0, 3, 6], [1, 4, 7], [2, 5, 8], // Columns
[0, 4, 8], [2, 4, 6] // Diagonals
];
for (const pattern of winPatterns) {
const [a, b, c] = pattern;
if (gameBoard[a] && gameBoard[a] === gameBoard[b] && gameBoard[a] === gameBoard[c]) {
// Highlight the winning cells
cells[a].classList.add('highlight');
cells[b].classList.add('highlight');
cells[c].classList.add('highlight');
return true;
}
}
return false;
}
// Check if the game is a draw
function checkDraw() {
return gameBoard.every(cell => cell !== '');
}
// End the game
function endGame(isDraw) {
gameActive = false;
if (!isDraw) {
// Update scores
scores[currentPlayer]++;
document.querySelector(`#player${currentPlayer === 'X' ? '1' : '2'} .player-score`).textContent = scores[currentPlayer];
// Show game over message
gameResult.textContent = gameSettings.language === 'arabic'
? `اللاعب ${currentPlayer} فاز!`
: `Player ${currentPlayer} wins!`;
} else {
// Show draw message
gameResult.textContent = gameSettings.language === 'arabic' ? 'تعادل!' : 'It\'s a draw!';
}
// Show game over modal
setTimeout(() => {
gameOverModal.classList.add('show');
}, 1000);
}
// Reset the current game
function resetGame() {
// Clear the board
gameBoard = ['', '', '', '', '', '', '', '', ''];
gameActive = true;
currentPlayer = 'X';
// Reset the UI
cells.forEach(cell => {
cell.textContent = '';
cell.className = 'cell';
});
player1Element.classList.add('active');
player2Element.classList.remove('active');
// Clear any active timers
if (timerInterval) {
clearInterval(timerInterval);
timerInterval = null;
}
// Hide modals
questionModal.classList.remove('show');
gameOverModal.classList.remove('show');
}
// Start a new game (reset game and scores)
function newGame() {
// Reset scores
scores = { X: 0, O: 0 };
document.querySelector('#player1 .player-score').textContent = '0';
document.querySelector('#player2 .player-score').textContent = '0';
// Reset the game
resetGame();
}
// Apply new settings
function applySettings() {
gameSettings.questionType = questionTypeSelect.value;
gameSettings.language = questionLanguageSelect.value;
gameSettings.category = questionCategorySelect.value;
gameSettings.timerSeconds = parseInt(questionTimerSelect.value);
// Validate language-category combination
// Make sure the selected category exists for the selected language
if (gameSettings.language === 'english' && gameSettings.category !== 'math') {
// For English, only math category is available
gameSettings.category = 'math';
questionCategorySelect.value = 'math';
} else if (gameSettings.language === 'arabic' &&
(gameSettings.category !== 'islamic' && gameSettings.category !== 'beginners')) {
// For Arabic, only islamic and beginners categories are available
gameSettings.category = 'beginners';
questionCategorySelect.value = 'beginners';
}
// Update UI language if needed
updateUILanguage();
// Start a new game with new settings
newGame();
}
// Update UI language based on selected language
function updateUILanguage() {
const isArabic = gameSettings.language === 'arabic';
// Update document direction
document.documentElement.dir = isArabic ? 'rtl' : 'ltr';
// Update button texts
resetButton.textContent = isArabic ? 'إعادة اللعبة' : 'Reset Game';
newGameButton.textContent = isArabic ? 'لعبة جديدة' : 'New Game';
playAgainButton.textContent = isArabic ? 'العب مرة أخرى' : 'Play Again';
applySettingsButton.textContent = isArabic ? 'تطبيق الإعدادات' : 'Apply Settings';
// Update headings
document.querySelector('h1').textContent = isArabic ? 'لعبة تيك تاك تو التعليمية' : 'Educational Tic Tac Toe';
document.querySelector('.settings h3').textContent = isArabic ? 'إعدادات اللعبة' : 'Game Settings';
document.querySelector('.used-words-container h3').textContent = isArabic ? 'الكلمات المستخدمة:' : 'Selected Words:';
// Update player names
document.querySelector('#player1 .player-name').textContent = isArabic ? 'اللاعب 1' : 'Player 1';
document.querySelector('#player2 .player-name').textContent = isArabic ? 'اللاعب 2' : 'Player 2';
// Update settings labels
const labels = document.querySelectorAll('.setting-group label');
if (isArabic) {
labels[0].textContent = 'نوع السؤال:';
labels[1].textContent = 'اللغة:';
labels[2].textContent = 'الفئة:';
labels[3].textContent = 'الوقت المحدد (ثواني):';
} else {
labels[0].textContent = 'Question Type:';
labels[1].textContent = 'Language:';
labels[2].textContent = 'Category:';
labels[3].textContent = 'Time Limit (seconds):';
}
// Update modal texts
document.querySelector('#questionModal h2').textContent = isArabic
? 'أجب على السؤال لإجراء حركتك'
: 'Answer the question to make your move';
}
// Update the game display
function updateGameDisplay() {
// Update UI language
updateUILanguage();
// Update player scores
document.querySelector('#player1 .player-score').textContent = scores.X;
document.querySelector('#player2 .player-score').textContent = scores.O;
// Update active player
player1Element.classList.toggle('active', currentPlayer === 'X');
player2Element.classList.toggle('active', currentPlayer === 'O');
}
// Utility function to shuffle an array (Fisher-Yates algorithm)
function shuffleArray(array) {
for (let i = array.length - 1; i > 0; i--) {
const j = Math.floor(Math.random() * (i + 1));
[array[i], array[j]] = [array[j], array[i]];
}
return array;
}
// Initialize the game when the page loads
window.addEventListener('load', initGame);

109
tictactoe/index.html Normal file
View file

@ -0,0 +1,109 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Educational Tic Tac Toe</title>
<link rel="stylesheet" href="styles.css">
</head>
<body>
<div class="container">
<h1>Educational Tic Tac Toe</h1>
<div class="game-info">
<div class="player-info">
<div id="player1" class="player active">
<span class="player-symbol">X</span>
<span class="player-name">Player 1</span>
<span class="player-score">0</span>
</div>
<div id="player2" class="player">
<span class="player-symbol">O</span>
<span class="player-name">Player 2</span>
<span class="player-score">0</span>
</div>
</div>
<div class="game-controls">
<button id="resetBtn">Reset Game</button>
<button id="newGameBtn">New Game</button>
</div>
</div>
<div class="game-board" id="gameBoard">
<div class="cell" data-index="0"></div>
<div class="cell" data-index="1"></div>
<div class="cell" data-index="2"></div>
<div class="cell" data-index="3"></div>
<div class="cell" data-index="4"></div>
<div class="cell" data-index="5"></div>
<div class="cell" data-index="6"></div>
<div class="cell" data-index="7"></div>
<div class="cell" data-index="8"></div>
</div>
<div id="questionModal" class="modal">
<div class="modal-content">
<h2>Answer the question to make your move</h2>
<div id="timerContainer" class="timer-container">
<div id="timerBar" class="timer-bar"></div>
<div id="timerText" class="timer-text"></div>
</div>
<div id="questionText" class="question-text"></div>
<div id="answerOptions" class="answer-options">
<!-- Answer options will be inserted here dynamically -->
</div>
<div id="feedback" class="feedback"></div>
</div>
</div>
<div id="gameOverModal" class="modal">
<div class="modal-content">
<h2 id="gameResult">Game Over</h2>
<button id="playAgainBtn">Play Again</button>
</div>
</div>
<div class="settings">
<h3>Game Settings</h3>
<div class="setting-group">
<label for="questionType">Question Type:</label>
<select id="questionType">
<option value="truefalse">True/False</option>
<option value="multiplechoice" selected>Multiple Choice</option>
</select>
</div>
<div class="setting-group">
<label for="questionLanguage">Language:</label>
<select id="questionLanguage">
<option value="english">English</option>
<option value="arabic" selected>Arabic</option>
</select>
</div>
<div class="setting-group">
<label for="questionCategory">Category:</label>
<select id="questionCategory">
<option value="math">Mathematics</option>
<option value="islamic" selected>Islamic</option>
<option value="beginners">Beginners Arabic</option>
</select>
</div>
<div class="setting-group">
<label for="questionTimer">Time Limit (seconds):</label>
<select id="questionTimer">
<option value="0">No Limit</option>
<option value="5" selected>5 Seconds</option>
<option value="10">10 Seconds</option>
<option value="15">15 Seconds</option>
<option value="30">30 Seconds</option>
</select>
</div>
<button id="applySettingsBtn">Apply Settings</button>
</div>
</div>
<script src="questions.js"></script>
<script src="game.js"></script>
</body>
</html>

439
tictactoe/questions.js Normal file
View file

@ -0,0 +1,439 @@
// Questions database for the Educational Tic Tac Toe game
// Organized by language, category, and question type
const questionsDB = {
english: {
math: {
truefalse: [
{
question: "The sum of angles in a triangle is 180 degrees.",
answer: true,
explanation: "In Euclidean geometry, the sum of the angles in any triangle is 180 degrees."
},
{
question: "Pi (π) is exactly equal to 22/7.",
answer: false,
explanation: "22/7 is just an approximation of pi. Pi is an irrational number."
},
{
question: "Any number raised to the power of 0 equals 1.",
answer: true,
explanation: "By definition, any non-zero number raised to the power of 0 equals 1."
},
{
question: "The square root of 4 is 2.",
answer: true,
explanation: "The square root of 4 is 2 because 2 × 2 = 4."
},
{
question: "There are 13 prime numbers less than 40.",
answer: false,
explanation: "There are 12 prime numbers less than 40: 2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, and 37."
}
],
multiplechoice: [
{
question: "What is 7 × 8?",
options: ["54", "56", "64", "72"],
answer: 1,
explanation: "7 × 8 = 56"
},
{
question: "Which of these is a prime number?",
options: ["15", "21", "27", "29"],
answer: 3,
explanation: "29 is a prime number because it is only divisible by 1 and itself."
},
{
question: "What is the area of a square with sides of length 5?",
options: ["10", "20", "25", "30"],
answer: 2,
explanation: "The area of a square is side length squared: 5² = 25"
},
{
question: "If x + 5 = 12, what is x?",
options: ["5", "7", "12", "17"],
answer: 1,
explanation: "x + 5 = 12, so x = 12 - 5 = 7"
},
{
question: "What is the next number in the sequence: 2, 4, 8, 16, ...?",
options: ["24", "32", "36", "64"],
answer: 1,
explanation: "Each number is doubled to get the next number. 16 × 2 = 32"
}
]
}
},
arabic: {
islamic: {
multiplechoice: [
{
question: "س: من هو النبي محمد ﷺ؟",
options: [
"هو محمد بن عبد الله بن عبد المطلب، آخر الأنبياء والمرسلين",
"هو عيسى بن مريم، نبي من أنبياء الله",
"هو موسى بن عمران، كليم الله",
"هو إبراهيم الخليل، أبو الأنبياء"
],
answer: 0,
explanation: "ج: هو محمد بن عبد الله بن عبد المطلب، آخر الأنبياء والمرسلين"
},
{
question: "س: متى ولد النبي ﷺ؟",
options: [
"ولد يوم الاثنين 12 ربيع الأول في عام الفيل (حوالي سنة 571 ميلادية)",
"ولد يوم الجمعة 17 رمضان (حوالي سنة 570 ميلادية)",
"ولد يوم الأربعاء 10 محرم (حوالي سنة 569 ميلادية)",
"ولد يوم السبت 25 شوال (حوالي سنة 572 ميلادية)"
],
answer: 0,
explanation: "ج: ولد يوم الاثنين 12 ربيع الأول في عام الفيل (حوالي سنة 571 ميلادية)"
},
{
question: "س: لماذا سمي النبي ﷺ بالصادق الأمين؟",
options: [
"لأنه كان معروفًا بالصدق والأمانة بين الناس قبل البعثة",
"لأنه كان يحب الصدق ويكره الكذب",
"لأن قريش أطلقت عليه هذا اللقب بعد الهجرة",
"لأنه كان يأمر الناس بالصدق والأمانة"
],
answer: 0,
explanation: "ج: لأنه كان معروفًا بالصدق والأمانة بين الناس قبل البعثة."
},
{
question: "س: كم كان عمر النبي ﷺ عندما نزل عليه الوحي؟",
options: [
"30 سنة",
"35 سنة",
"40 سنة",
"45 سنة"
],
answer: 2,
explanation: "ج: كان عمره 40 سنة"
},
{
question: "س: أين نزل أول وحي على النبي ﷺ؟",
options: [
"في المسجد الحرام",
"في غار حراء بمكة",
"في بيته",
"في المدينة المنورة"
],
answer: 1,
explanation: "ج: في غار حراء بمكة"
},
{
question: "س: ما هي أول آية نزلت على النبي ﷺ؟",
options: [
"﴿اقْرَأْ بِاسْمِ رَبِّكَ الَّذِي خَلَقَ﴾",
"﴿بِسْمِ اللَّهِ الرَّحْمَنِ الرَّحِيمِ﴾",
"﴿الْحَمْدُ لِلَّهِ رَبِّ الْعَالَمِينَ﴾",
"﴿يَا أَيُّهَا الْمُدَّثِّرُ﴾"
],
answer: 0,
explanation: "ج: ﴿اقْرَأْ بِاسْمِ رَبِّكَ الَّذِي خَلَقَ﴾ (سورة العلق:1)."
}
]
},
beginners: {
truefalse: [
{
question: "كتاب = boek (Nederlands) / book (English)",
answer: true,
explanation: "Correct! كتاب betekent 'boek' in het Nederlands"
},
{
question: "قلم = tafel (Nederlands) / table (English)",
answer: false,
explanation: "Nee, قلم betekent 'pen' in het Nederlands. 'Tafel' is طاولة in het Arabisch"
},
{
question: "باب = deur (Nederlands) / door (English)",
answer: true,
explanation: "Correct! باب betekent 'deur' in het Nederlands"
},
{
question: "ماء = vuur (Nederlands) / fire (English)",
answer: false,
explanation: "Nee, ماء betekent 'water' in het Nederlands. 'Vuur' is نار in het Arabisch"
},
{
question: "شمس = zon (Nederlands) / sun (English)",
answer: true,
explanation: "Correct! شمس betekent 'zon' in het Nederlands"
},
{
question: "طعام = eten (Nederlands) / food (English)",
answer: true,
explanation: "Correct! طعام betekent 'eten' in het Nederlands"
},
{
question: "يد = voet (Nederlands) / foot (English)",
answer: false,
explanation: "Nee, يد betekent 'hand' in het Nederlands. 'Voet' is قدم in het Arabisch"
},
{
question: "قطة = kat (Nederlands) / cat (English)",
answer: true,
explanation: "Correct! قطة betekent 'kat' in het Nederlands"
},
{
question: "عين = oog (Nederlands) / eye (English)",
answer: true,
explanation: "Correct! عين betekent 'oog' in het Nederlands"
},
{
question: "أنف = oor (Nederlands) / ear (English)",
answer: false,
explanation: "Nee, أنف betekent 'neus' in het Nederlands. 'Oor' is أذن in het Arabisch"
},
{
question: "فم = mond (Nederlands) / mouth (English)",
answer: true,
explanation: "Correct! فم betekent 'mond' in het Nederlands"
},
{
question: "رأس = haar (Nederlands) / hair (English)",
answer: false,
explanation: "Nee, رأس betekent 'hoofd' in het Nederlands. 'Haar' is شعر in het Arabisch"
},
{
question: "قدم = voet (Nederlands) / foot (English)",
answer: true,
explanation: "Correct! قدم betekent 'voet' in het Nederlands"
},
{
question: "أب = moeder (Nederlands) / mother (English)",
answer: false,
explanation: "Nee, أب betekent 'vader' in het Nederlands. 'Moeder' is أم in het Arabisch"
},
{
question: "أخ = broer (Nederlands) / brother (English)",
answer: true,
explanation: "Correct! أخ betekent 'broer' in het Nederlands"
},
{
question: "جد = opa (Nederlands) / grandfather (English)",
answer: true,
explanation: "Correct! جد betekent 'opa' in het Nederlands"
},
{
question: "جدة = tante (Nederlands) / aunt (English)",
answer: false,
explanation: "Nee, جدة betekent 'oma' in het Nederlands. 'Tante' is عمة of خالة in het Arabisch"
},
{
question: "صديق = vriend (Nederlands) / friend (English)",
answer: true,
explanation: "Correct! صديق betekent 'vriend' in het Nederlands"
},
{
question: "مطبخ = badkamer (Nederlands) / bathroom (English)",
answer: false,
explanation: "Nee, مطبخ betekent 'keuken' in het Nederlands. 'Badkamer' is حمام in het Arabisch"
},
{
question: "غرفة = kamer (Nederlands) / room (English)",
answer: true,
explanation: "Correct! غرفة betekent 'kamer' in het Nederlands"
},
{
question: "سرير = stoel (Nederlands) / chair (English)",
answer: false,
explanation: "Nee, سرير betekent 'bed' in het Nederlands. 'Stoel' is كرسي in het Arabisch"
},
{
question: "طاولة = tafel (Nederlands) / table (English)",
answer: true,
explanation: "Correct! طاولة betekent 'tafel' in het Nederlands"
},
{
question: "حليب = melk (Nederlands) / milk (English)",
answer: true,
explanation: "Correct! حليب betekent 'melk' in het Nederlands"
},
{
question: "بيضة = kaas (Nederlands) / cheese (English)",
answer: false,
explanation: "Nee, بيضة betekent 'ei' in het Nederlands. 'Kaas' is جبن in het Arabisch"
},
{
question: "لحم = vlees (Nederlands) / meat (English)",
answer: true,
explanation: "Correct! لحم betekent 'vlees' in het Nederlands"
}
],
multiplechoice: [
{
question: "بيت",
options: ["Auto / Car", "Huis / House", "School / School", "Boom / Tree"],
answer: 1,
explanation: "Correct! بيت betekent 'huis' in het Nederlands (house in English)"
},
{
question: "مدرسة",
options: ["Ziekenhuis / Hospital", "Markt / Market", "School / School", "Bibliotheek / Library"],
answer: 2,
explanation: "Correct! مدرسة betekent 'school' in het Nederlands"
},
{
question: "سيارة",
options: ["Auto / Car", "Bus / Bus", "Fiets / Bicycle", "Trein / Train"],
answer: 0,
explanation: "Correct! سيارة betekent 'auto' in het Nederlands (car in English)"
},
{
question: "قمر",
options: ["Ster / Star", "Zon / Sun", "Maan / Moon", "Planeet / Planet"],
answer: 2,
explanation: "Correct! قمر betekent 'maan' in het Nederlands (moon in English)"
},
{
question: "كلب",
options: ["Kat / Cat", "Hond / Dog", "Vogel / Bird", "Vis / Fish"],
answer: 1,
explanation: "Correct! كلب betekent 'hond' in het Nederlands (dog in English)"
},
{
question: "طفل",
options: ["Man / Man", "Vrouw / Woman", "Kind / Child", "Opa / Grandfather"],
answer: 2,
explanation: "Correct! طفل betekent 'kind' in het Nederlands (child in English)"
},
{
question: "فاكهة",
options: ["Fruit / Fruit", "Groente / Vegetable", "Vlees / Meat", "Brood / Bread"],
answer: 0,
explanation: "Correct! فاكهة betekent 'fruit' in het Nederlands"
},
{
question: "نافذة",
options: ["Deur / Door", "Raam / Window", "Muur / Wall", "Vloer / Floor"],
answer: 1,
explanation: "Correct! نافذة betekent 'raam' in het Nederlands (window in English)"
},
{
question: "شعر",
options: ["Haar / Hair", "Oog / Eye", "Neus / Nose", "Oor / Ear"],
answer: 0,
explanation: "Correct! شعر betekent 'haar' in het Nederlands (hair in English)"
},
{
question: "أذن",
options: ["Neus / Nose", "Mond / Mouth", "Oor / Ear", "Tand / Tooth"],
answer: 2,
explanation: "Correct! أذن betekent 'oor' in het Nederlands (ear in English)"
},
{
question: "أم",
options: ["Vader / Father", "Moeder / Mother", "Zus / Sister", "Broer / Brother"],
answer: 1,
explanation: "Correct! أم betekent 'moeder' in het Nederlands (mother in English)"
},
{
question: "أخت",
options: ["Oom / Uncle", "Tante / Aunt", "Broer / Brother", "Zus / Sister"],
answer: 3,
explanation: "Correct! أخت betekent 'zus' in het Nederlands (sister in English)"
},
{
question: "خبز",
options: ["Brood / Bread", "Kaas / Cheese", "Melk / Milk", "Ei / Egg"],
answer: 0,
explanation: "Correct! خبز betekent 'brood' in het Nederlands (bread in English)"
},
{
question: "ماء",
options: ["Koffie / Coffee", "Thee / Tea", "Water / Water", "Sap / Juice"],
answer: 2,
explanation: "Correct! ماء betekent 'water' in het Nederlands"
},
{
question: "تفاحة",
options: ["Banaan / Banana", "Appel / Apple", "Sinaasappel / Orange", "Aardbei / Strawberry"],
answer: 1,
explanation: "Correct! تفاحة betekent 'appel' in het Nederlands (apple in English)"
},
{
question: "موز",
options: ["Appel / Apple", "Peer / Pear", "Banaan / Banana", "Druif / Grape"],
answer: 2,
explanation: "Correct! موز betekent 'banaan' in het Nederlands (banana in English)"
},
{
question: "برتقال",
options: ["Aardbei / Strawberry", "Sinaasappel / Orange", "Citroen / Lemon", "Kiwi / Kiwi"],
answer: 1,
explanation: "Correct! برتقال betekent 'sinaasappel' in het Nederlands (orange in English)"
},
{
question: "دجاج",
options: ["Vlees / Meat", "Vis / Fish", "Kip / Chicken", "Varken / Pork"],
answer: 2,
explanation: "Correct! دجاج betekent 'kip' in het Nederlands (chicken in English)"
},
{
question: "سمك",
options: ["Kip / Chicken", "Vlees / Meat", "Varken / Pork", "Vis / Fish"],
answer: 3,
explanation: "Correct! سمك betekent 'vis' in het Nederlands (fish in English)"
},
{
question: "جبن",
options: ["Kaas / Cheese", "Boter / Butter", "Yoghurt / Yogurt", "Room / Cream"],
answer: 0,
explanation: "Correct! جبن betekent 'kaas' in het Nederlands (cheese in English)"
},
{
question: "بيضة",
options: ["Melk / Milk", "Ei / Egg", "Boter / Butter", "Suiker / Sugar"],
answer: 1,
explanation: "Correct! بيضة betekent 'ei' in het Nederlands (egg in English)"
},
{
question: "كرسي",
options: ["Tafel / Table", "Stoel / Chair", "Kast / Cabinet", "Bed / Bed"],
answer: 1,
explanation: "Correct! كرسي betekent 'stoel' in het Nederlands (chair in English)"
},
{
question: "سرير",
options: ["Kast / Cabinet", "Tafel / Table", "Stoel / Chair", "Bed / Bed"],
answer: 3,
explanation: "Correct! سرير betekent 'bed' in het Nederlands (bed in English)"
},
{
question: "مطبخ",
options: ["Keuken / Kitchen", "Badkamer / Bathroom", "Slaapkamer / Bedroom", "Woonkamer / Living room"],
answer: 0,
explanation: "Correct! مطبخ betekent 'keuken' in het Nederlands (kitchen in English)"
},
{
question: "حمام",
options: ["Slaapkamer / Bedroom", "Woonkamer / Living room", "Badkamer / Bathroom", "Keuken / Kitchen"],
answer: 2,
explanation: "Correct! حمام betekent 'badkamer' in het Nederlands (bathroom in English)"
}
]
}
}
};
// Function to get a random question based on settings
function getRandomQuestion(language, category, type) {
// Validate parameters
if (!questionsDB[language] || !questionsDB[language][category] || !questionsDB[language][category][type]) {
console.error(`Invalid question parameters: ${language}, ${category}, ${type}`);
return null;
}
// Get the questions array
const questions = questionsDB[language][category][type];
// Return a random question
return questions[Math.floor(Math.random() * questions.length)];
}
// Export the function for use in other files
window.getRandomQuestion = getRandomQuestion;

352
tictactoe/styles.css Normal file
View file

@ -0,0 +1,352 @@
* {
margin: 0;
padding: 0;
box-sizing: border-box;
font-family: Arial, sans-serif;
}
body {
background-color: #f5f5f5;
display: flex;
justify-content: center;
padding: 20px;
}
.container {
width: 100%;
max-width: 800px;
background-color: white;
border-radius: 10px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
padding: 20px;
}
h1 {
text-align: center;
margin-bottom: 20px;
color: #333;
}
/* Game Info Styles */
.game-info {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 20px;
padding: 10px;
background-color: #f0f0f0;
border-radius: 5px;
}
.player-info {
display: flex;
gap: 20px;
}
.player {
display: flex;
flex-direction: column;
align-items: center;
padding: 10px;
border-radius: 5px;
opacity: 0.7;
transition: all 0.3s;
}
.player.active {
background-color: #e3f2fd;
opacity: 1;
box-shadow: 0 2px 5px rgba(0, 0, 0, 0.1);
}
.player-symbol {
font-size: 24px;
font-weight: bold;
margin-bottom: 5px;
}
.player-name {
font-size: 14px;
}
.player-score {
font-size: 18px;
font-weight: bold;
margin-top: 5px;
}
.game-controls {
display: flex;
gap: 10px;
}
button {
padding: 10px 15px;
border: none;
border-radius: 5px;
background-color: #4CAF50;
color: white;
cursor: pointer;
font-size: 16px;
transition: background-color 0.3s;
}
button:hover {
background-color: #45a049;
}
#resetBtn {
background-color: #f44336;
}
#resetBtn:hover {
background-color: #d32f2f;
}
/* Game Board Styles */
.game-board {
display: grid;
grid-template-columns: repeat(3, 1fr);
grid-gap: 10px;
margin: 0 auto 30px;
max-width: 400px;
}
.cell {
aspect-ratio: 1/1;
background-color: #e0e0e0;
border-radius: 5px;
display: flex;
align-items: center;
justify-content: center;
font-size: 48px;
font-weight: bold;
cursor: pointer;
transition: all 0.3s;
}
.cell:hover {
background-color: #d0d0d0;
}
.cell.x {
color: #f44336;
}
.cell.o {
color: #2196F3;
}
.cell.highlight {
background-color: #ffeb3b;
}
/* Modal Styles */
.modal {
display: none;
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-color: rgba(0, 0, 0, 0.5);
z-index: 100;
justify-content: center;
align-items: center;
}
.modal.show {
display: flex;
}
.modal-content {
background-color: white;
padding: 30px;
border-radius: 10px;
max-width: 500px;
width: 90%;
box-shadow: 0 5px 15px rgba(0, 0, 0, 0.3);
}
.modal h2 {
margin-bottom: 20px;
text-align: center;
color: #333;
}
.timer-container {
width: 100%;
height: 30px;
background-color: #f0f0f0;
border-radius: 15px;
margin-bottom: 15px;
position: relative;
overflow: hidden;
}
.timer-bar {
height: 100%;
width: 100%;
background-color: #4CAF50;
border-radius: 15px;
transition: width 1s linear;
}
.timer-text {
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
font-weight: bold;
color: #333;
}
.timer-bar.warning {
background-color: #FFC107;
}
.timer-bar.danger {
background-color: #F44336;
}
.question-text {
font-size: 28px;
margin-bottom: 30px;
line-height: 1.6;
text-align: center;
font-weight: bold;
}
.answer-options {
display: flex;
flex-direction: column;
gap: 15px;
margin-bottom: 25px;
}
.answer-option {
padding: 20px;
border: 3px solid #ddd;
border-radius: 8px;
cursor: pointer;
transition: all 0.3s;
font-size: 22px;
text-align: center;
}
.answer-option:hover {
background-color: #f5f5f5;
border-color: #bbb;
}
.answer-option.selected {
border-color: #2196F3;
background-color: #e3f2fd;
}
.answer-option.correct {
border-color: #4CAF50;
background-color: #e8f5e9;
}
.answer-option.incorrect {
border-color: #f44336;
background-color: #ffebee;
}
.feedback {
text-align: center;
font-weight: bold;
margin-top: 25px;
min-height: 30px;
font-size: 24px;
padding: 15px;
border-radius: 8px;
}
.feedback.correct {
color: #4CAF50;
background-color: #e8f5e9;
border: 3px solid #4CAF50;
}
.feedback.incorrect {
color: #f44336;
background-color: #ffebee;
border: 3px solid #f44336;
}
/* Settings Styles */
.settings {
margin-top: 30px;
padding: 20px;
background-color: #f9f9f9;
border-radius: 5px;
}
.settings h3 {
margin-bottom: 15px;
color: #333;
}
.setting-group {
margin-bottom: 15px;
display: flex;
align-items: center;
}
.setting-group label {
width: 120px;
font-weight: bold;
color: #555;
}
.setting-group select {
flex: 1;
padding: 8px;
border-radius: 5px;
border: 1px solid #ddd;
font-size: 16px;
background-color: white;
}
#applySettingsBtn {
margin-top: 10px;
background-color: #2196F3;
}
#applySettingsBtn:hover {
background-color: #1976D2;
}
/* RTL Support for Arabic */
[lang="ar"] {
direction: rtl;
text-align: right;
}
/* Responsive Styles */
@media (max-width: 600px) {
.game-info {
flex-direction: column;
gap: 15px;
}
.cell {
font-size: 36px;
}
.setting-group {
flex-direction: column;
align-items: flex-start;
}
.setting-group label {
margin-bottom: 5px;
width: 100%;
}
.setting-group select {
width: 100%;
}
}