${guidance.encouragement || "Great question! Let's explore this together step by step! 🚀"}
+
Instead of giving you the answer right away, I'll help you think through this like a detective! 🕵️
+
+
+ `;
+ conversationContainer.appendChild(welcomeStep);
+
+ // Add thinking questions as interactive steps
+ const questions = guidance.steps ? guidance.steps.map(step => step.text) : guidance.questions || [
+ "What do you already know about this topic?",
+ "What do you think might be the reason for this?",
+ "Can you think of any examples or similar situations?"
+ ];
+
+ // Create chat interface
+ this.conversationContainer = conversationContainer;
+ this.questions = questions;
+ this.currentQuestionIndex = 0;
+
+ // Start the conversation with the first question
+ this.askNextQuestion();
+
+ // Add final reveal button (initially hidden)
+ const revealDiv = document.createElement('div');
+ revealDiv.className = 'reveal-section';
+ revealDiv.style.display = 'none';
+ revealDiv.innerHTML = `
+
+
🎉 Great thinking! You've explored this question step by step!
+
Would you like to see how close your thoughts were to the scientific explanation?
+
+
+
+ `;
+ conversationContainer.appendChild(revealDiv);
+
+ // Show first question
+ setTimeout(() => {
+ const firstStep = conversationContainer.querySelector('.step-0');
+ if (firstStep) {
+ firstStep.classList.add('visible');
+ firstStep.scrollIntoView({ behavior: 'smooth' });
+ }
+ }, 1000);
+
+ // Scroll to thinking section
+ this.thinkingSection.scrollIntoView({ behavior: 'smooth' });
+ }
+
+ displayLocalGuidance(question) {
+ console.log('📚 Displaying local guidance for:', question);
+
+ const encouragements = [
+ "Great question! You're thinking like a real scientist! 🔬",
+ "Wow, that's a fantastic thing to wonder about! 🌟",
+ "I love how curious you are! That's how great discoveries happen! 🚀"
+ ];
+
+ const randomEncouragement = encouragements[Math.floor(Math.random() * encouragements.length)];
+
+ this.displayGuidance({
+ questions: [
+ "What do you already know about this topic?",
+ "What do you think might be the reason for this?",
+ "Where could you look to find more information?",
+ "Can you think of any examples or similar situations?"
+ ],
+ encouragement: randomEncouragement
+ });
+ }
+
+ showLoading() {
+ console.log('⏳ Showing loading...');
+ if (this.loadingOverlay) {
+ this.loadingOverlay.classList.remove('hidden');
+ }
+ }
+
+ hideLoading() {
+ console.log('✅ Hiding loading...');
+ if (this.loadingOverlay) {
+ this.loadingOverlay.classList.add('hidden');
+ }
+ }
+
+ showMessage(message, type = 'info') {
+ console.log('💬 Showing message:', message, type);
+
+ // Create message popup
+ const messageDiv = document.createElement('div');
+ messageDiv.className = `message-popup ${type}`;
+ messageDiv.textContent = message;
+ messageDiv.style.cssText = `
+ position: fixed;
+ top: 20px;
+ right: 20px;
+ background: ${type === 'error' ? '#fed7d7' : type === 'warning' ? '#fef5e7' : '#e6fffa'};
+ color: ${type === 'error' ? '#c53030' : type === 'warning' ? '#d69e2e' : '#00695c'};
+ padding: 15px 20px;
+ border-radius: 10px;
+ box-shadow: 0 4px 12px rgba(0,0,0,0.2);
+ z-index: 1001;
+ max-width: 300px;
+ font-size: 14px;
+ `;
+
+ document.body.appendChild(messageDiv);
+
+ // Remove after 3 seconds
+ setTimeout(() => {
+ messageDiv.remove();
+ }, 3000);
+ }
+
+ submitAnswer(stepIndex) {
+ console.log('📝 Submit answer for step:', stepIndex);
+
+ const textarea = document.getElementById(`user-input-${stepIndex}`);
+ const inputArea = document.getElementById(`input-area-${stepIndex}`);
+ const responseDiv = document.getElementById(`response-${stepIndex}`);
+
+ if (!textarea || !inputArea || !responseDiv) {
+ console.error('❌ Could not find elements for step:', stepIndex);
+ return;
+ }
+
+ const answer = textarea.value.trim();
+
+ if (!answer) {
+ this.showMessage(
+ this.currentLanguage === 'de' ? 'Bitte schreibe deine Gedanken auf! 🤔' : 'Please write down your thoughts! 🤔',
+ 'warning'
+ );
+ return;
+ }
+
+ // Store the answer
+ this.userAnswers[stepIndex] = answer;
+
+ // Mark as answered
+ inputArea.classList.add('answered');
+ textarea.disabled = true;
+
+ // Show AI response
+ let aiResponse;
+
+ if (!answer || answer.toLowerCase().includes('nothing') || answer.toLowerCase().includes('don\'t know')) {
+ // Encouraging response for "nothing" or "don't know"
+ const encouragingResponses = [
+ "🌟 Great observation! You're thinking like a scientist! Starting fresh means you can discover everything step by step. Can you think of how the shape of a bird's wings helps them stay in the air and move around?",
+ "💡 That's the perfect starting point for learning! Every expert started by not knowing. You're right, birds do use their wings to fly. Can you think of how the wings might work differently above and below?",
+ "🚀 Perfect honesty! When we don't know something, it means we're about to learn something new! Maybe because the wind can flow faster on the above of the wing than on the below which creates pressure and pushes the bird up?"
+ ];
+ aiResponse = encouragingResponses[Math.floor(Math.random() * encouragingResponses.length)];
+ } else if (answer.length < 10) {
+ // Short answer - provide gentle guidance like in image 2
+ const guidingResponses = [
+ "🎯 That's a great observation! Birds use their wings to create lift by taking advantage of the difference in air pressure above and below their wings. Do you know why different bird species have different wing shapes?",
+ "✨ You're on the right track! Can you think of how the shape of a bird's wings helps them stay in the air and move around?",
+ "🔍 Good thinking! You're right, birds do use their wings to fly. Can you think of how the wings might work differently above and below?"
+ ];
+ aiResponse = guidingResponses[Math.floor(Math.random() * guidingResponses.length)];
+ } else {
+ // Longer, thoughtful answer - provide specific scientific guidance
+ const insightfulResponses = [
+ "🌟 Excellent thinking! You're really exploring this well! That's a great observation! Birds use their wings to create lift by taking advantage of the difference in air pressure above and below their wings. Do you know why different bird species have different wing shapes?",
+ "💡 Great observation! You're thinking like a scientist! You're right, birds do use their wings to fly. Can you think of how the wings might work differently above and below which creates pressure and pushes the bird up?",
+ "🔍 Wonderful insight! You're asking the right questions! That's exactly how flight works - the shape of a bird's wings helps them stay in the air and move around!",
+ "🎯 That's a thoughtful response! Keep exploring! Birds use their wings to create lift. Can you think of any other animals that can fly like birds, and how do they differ in their flying abilities?"
+ ];
+ aiResponse = insightfulResponses[Math.floor(Math.random() * insightfulResponses.length)];
+ }
+
+ responseDiv.innerHTML = `
+
${this.currentLanguage === 'de'
+ ? 'Ich kann die Antwort gerade nicht abrufen. Das ist eine tolle Frage! Du hast schon toll nachgedacht. Frag gerne einen Erwachsenen oder schaue in einem Buch nach.'
+ : 'I can\'t fetch the answer right now. That\'s a great question! You\'ve done great thinking already. Feel free to ask an adult or look it up in a book.'}
+
+
+ `;
+ answerContent.style.display = 'block';
+ }
+ }
+}
+
+// Global variable for external access
+let kidsAI;
+
+// Initialize when DOM is ready
+document.addEventListener('DOMContentLoaded', () => {
+ console.log('🚀 DOM loaded, initializing KidsAI Explorer...');
+
+ try {
+ kidsAI = new KidsAIExplorer();
+ window.kidsAI = kidsAI; // Make globally accessible
+ console.log('✅ KidsAI Explorer initialized successfully');
+
+ // Add visual indicator
+ const indicator = document.createElement('div');
+ indicator.innerHTML = '✅ KidsAI Ready!';
+ indicator.style.cssText = 'position:fixed;top:10px;left:10px;background:green;color:white;padding:5px;z-index:9999;border-radius:5px;font-size:12px;';
+ document.body.appendChild(indicator);
+
+ // Remove indicator after 3 seconds
+ setTimeout(() => indicator.remove(), 3000);
+
+ } catch (error) {
+ console.error('❌ Error initializing KidsAIExplorer:', error);
+
+ // Show error indicator
+ const indicator = document.createElement('div');
+ indicator.innerHTML = '❌ KidsAI Error: ' + error.message;
+ indicator.style.cssText = 'position:fixed;top:10px;left:10px;background:red;color:white;padding:5px;z-index:9999;border-radius:5px;font-size:12px;';
+ document.body.appendChild(indicator);
+ }
+});
+
+console.log('📜 KidsAI script-new.js loaded');
diff --git a/html/kidsai/server.js b/html/kidsai/server.js
index f8b0893..90d416d 100644
--- a/html/kidsai/server.js
+++ b/html/kidsai/server.js
@@ -123,363 +123,19 @@ app.post('/api/reveal-answer', async (req, res) => {
}
});
-// API endpoint for checking math answers
-app.post('/api/check-math-answer', async (req, res) => {
- const { question, userAnswer, language = 'en' } = req.body;
-
- if (!question || !userAnswer) {
- return res.status(400).json({
- success: false,
- error: 'Question and user answer are required'
- });
- }
-
- try {
- // Extract the math expression from the question
- const correctAnswer = calculateMathAnswer(question);
- const userAnswerNum = parseFloat(userAnswer.trim());
-
- const isCorrect = !isNaN(userAnswerNum) && Math.abs(userAnswerNum - correctAnswer) < 0.001;
-
- res.json({
- success: true,
- correct: isCorrect,
- expectedAnswer: correctAnswer,
- userAnswer: userAnswerNum,
- hint: !isCorrect ? (language === 'de' ? 'Überprüfe deine Rechnung nochmal.' : 'Check your calculation again.') : null
- });
-
- } catch (error) {
- console.error('Math check error:', error);
- res.json({
- success: true,
- correct: true, // Fallback to correct if calculation fails
- expectedAnswer: null,
- userAnswer: userAnswer
- });
- }
-});
-
-// API endpoint for getting additional math hints
-app.post('/api/get-more-hints', async (req, res) => {
- const { question, language = 'en', previousHints = [] } = req.body;
-
- if (!question) {
- return res.status(400).json({
- success: false,
- error: 'Question is required'
- });
- }
-
- try {
- // Generate additional hints based on the math problem
- const additionalHints = await generateAdditionalMathHints(question, language, previousHints);
-
- res.json({
- success: true,
- hints: additionalHints,
- question: question,
- language: language
- });
-
- } catch (error) {
- console.error('Additional hints error:', error);
-
- // Fallback hints if AI fails
- const fallbackHints = getFallbackMathHints(question, language);
-
- res.json({
- success: true,
- hints: fallbackHints,
- question: question,
- language: language,
- fallback: true
- });
- }
-});
-
-// API endpoint for interactive thinking feedback
-app.post('/api/think-response', async (req, res) => {
- const { question, thought, stepNumber, language = 'en' } = req.body;
-
- if (!question || !thought) {
- return res.status(400).json({
- success: false,
- error: 'Question and thought are required'
- });
- }
-
- try {
- // Get AI feedback on the child's thinking
- const feedback = await getThinkingFeedback(question, thought, stepNumber, language);
-
- res.json({
- success: true,
- feedback: feedback,
- question: question,
- thought: thought,
- language: language
- });
-
- } catch (error) {
- console.error('Thinking feedback error:', error);
-
- // Fallback positive feedback
- const fallbackFeedback = getFallbackThinkingFeedback(language);
-
- res.json({
- success: true,
- feedback: fallbackFeedback,
- question: question,
- thought: thought,
- language: language,
- fallback: true
- });
- }
-});
-
-// API endpoint for interactive thinking feedback
-app.post('/api/thinking-feedback', async (req, res) => {
- const { question, stepNumber, userThought, language = 'en' } = req.body;
-
- if (!question || !userThought || stepNumber === undefined) {
- return res.status(400).json({
- success: false,
- error: 'Question, step number, and user thought are required'
- });
- }
-
- try {
- // Get AI feedback on the child's thinking
- const feedback = await getThinkingFeedback(question, userThought, stepNumber, language);
-
- res.json({
- success: true,
- feedback: feedback,
- question: question,
- stepNumber: stepNumber,
- userThought: userThought,
- language: language
- });
-
- } catch (error) {
- console.error('Thinking feedback error:', error);
-
- // Fallback positive feedback
- const fallbackFeedback = {
- response: language === 'de'
- ? "Interessante Gedanken! Du denkst in die richtige Richtung. 👍"
- : "Interesting thoughts! You're thinking in the right direction. 👍",
- encouragement: language === 'de'
- ? "Weiter so!"
- : "Keep going!",
- type: 'positive'
- };
-
- res.json({
- success: true,
- feedback: fallbackFeedback,
- question: question,
- stepNumber: stepNumber,
- userThought: userThought,
- language: language,
- fallback: true
- });
- }
-});
-
-// API endpoint for AI conversation (when child replies to AI questions)
-app.post('/api/ai-conversation', async (req, res) => {
- const { originalQuestion, userReply, language = 'en' } = req.body;
-
- if (!originalQuestion || !userReply) {
- return res.status(400).json({
- success: false,
- error: 'Original question and user reply are required'
- });
- }
-
- try {
- // Get AI response to continue the conversation
- const aiResponse = await getConversationResponse(originalQuestion, userReply, language);
-
- res.json({
- success: true,
- aiResponse: aiResponse,
- originalQuestion: originalQuestion,
- userReply: userReply,
- language: language
- });
-
- } catch (error) {
- console.error('AI Conversation Error:', error);
-
- // Fallback response if AI fails
- const fallbackResponse = language === 'de'
- ? "Das ist eine interessante Antwort! Du denkst gut über das Thema nach."
- : "That's an interesting answer! You're thinking well about this topic.";
-
- res.json({
- success: true,
- aiResponse: fallbackResponse,
- originalQuestion: originalQuestion,
- userReply: userReply,
- language: language,
- fallback: true
- });
- }
-});
-
-// Generate conversational AI response
-async function getConversationResponse(originalQuestion, userReply, language) {
- const isGerman = language === 'de';
-
- const systemPrompt = isGerman
- ? "Du bist ein geduldiger Lehrer, der mit einem Kind über ein interessantes Thema spricht. Das Kind hat gerade auf eine deiner Fragen geantwortet. Reagiere natürlich auf ihre Antwort: anerkenne was sie gesagt haben, baue darauf auf, und stelle wenn nötig eine weiterführende Frage um ihr Verständnis zu vertiefen. Sei ermutigend und neugierig. Halte deine Antworten kurz (1-2 Sätze) und altersgerecht."
- : "You are a patient teacher having a conversation with a child about an interesting topic. The child just answered one of your questions. Respond naturally to their answer: acknowledge what they said, build upon it, and ask a follow-up question if needed to deepen their understanding. Be encouraging and curious. Keep your responses short (1-2 sentences) and age-appropriate.";
-
- const userPrompt = isGerman
- ? `Ursprüngliche Frage: "${originalQuestion}"\nKind hat geantwortet: "${userReply}"\n\nReagiere natürlich auf ihre Antwort und führe das Gespräch weiter.`
- : `Original question: "${originalQuestion}"\nChild replied: "${userReply}"\n\nRespond naturally to their answer and continue the conversation.`;
-
- try {
- const completion = await openai.chat.completions.create({
- model: "gpt-3.5-turbo",
- messages: [
- { role: "system", content: systemPrompt },
- { role: "user", content: userPrompt }
- ],
- max_tokens: 150,
- temperature: 0.8
- });
-
- const aiResponse = completion.choices[0]?.message?.content || '';
- console.log(`✅ AI conversation response: ${aiResponse.substring(0, 100)}...`);
-
- return aiResponse;
-
- } catch (error) {
- console.log('❌ AI conversation error:', error.message);
- throw error;
- }
-}
-
-// Function to calculate the correct answer for simple math expressions
-function calculateMathAnswer(question) {
- const questionLower = question.toLowerCase().trim();
-
- // Extract numbers and operation from common question formats
- let match;
-
- // Pattern: "what is X+Y" or "was ist X+Y"
- match = questionLower.match(/(?:what\s+is\s+|was\s+ist\s+)?(\d+(?:\.\d+)?)\s*\+\s*(\d+(?:\.\d+)?)/);
- if (match) {
- return parseFloat(match[1]) + parseFloat(match[2]);
- }
-
- // Pattern: "what is X-Y"
- match = questionLower.match(/(?:what\s+is\s+|was\s+ist\s+)?(\d+(?:\.\d+)?)\s*-\s*(\d+(?:\.\d+)?)/);
- if (match) {
- return parseFloat(match[1]) - parseFloat(match[2]);
- }
-
- // Pattern: "what is X*Y" or "X times Y"
- match = questionLower.match(/(?:what\s+is\s+|was\s+ist\s+)?(\d+(?:\.\d+)?)\s*[\*x]\s*(\d+(?:\.\d+)?)/);
- if (match) {
- return parseFloat(match[1]) * parseFloat(match[2]);
- }
-
- // Pattern: "what is X/Y" or "X divided by Y"
- match = questionLower.match(/(?:what\s+is\s+|was\s+ist\s+)?(\d+(?:\.\d+)?)\s*\/\s*(\d+(?:\.\d+)?)/);
- if (match) {
- return parseFloat(match[1]) / parseFloat(match[2]);
- }
-
- // If no pattern matches, throw error
- throw new Error('Could not parse math expression');
-}
-
-// Function to analyze question type and determine interaction mode
-function analyzeQuestionType(question) {
- const questionLower = question.toLowerCase().trim();
-
- // Mathematical questions - should guide to calculation
- const mathPatterns = [
- /what\s+is\s+\d+\s*[\+\-\*\/]\s*\d+/,
- /\d+\s*[\+\-\*\/]\s*\d+/,
- /\d+\s*plus\s*\d+/,
- /\d+\s*minus\s*\d+/,
- /\d+\s*times\s*\d+/,
- /\d+\s*divided\s*by\s*\d+/,
- /calculate/,
- /was\s+ist\s+\d+\s*[\+\-\*\/]\s*\d+/,
- /rechne/,
- /plus|minus|mal|geteilt|add|subtract|multiply|divide/
- ];
-
- // Simple factual questions - should guide to discovery
- const factualPatterns = [
- /what\s+color\s+is/,
- /how\s+many/,
- /what\s+day\s+is/,
- /what\s+time\s+is/,
- /welche\s+farbe/,
- /wie\s+viele/,
- /welcher\s+tag/,
- /wie\s+spät/
- ];
-
- if (mathPatterns.some(pattern => pattern.test(questionLower))) {
- console.log(`🧮 Detected mathematical question: "${question}"`);
- return 'mathematical';
- }
-
- if (factualPatterns.some(pattern => pattern.test(questionLower))) {
- console.log(`📋 Detected simple factual question: "${question}"`);
- return 'factual_simple';
- }
-
- // Default to exploratory for complex questions
- console.log(`🤔 Detected exploratory question: "${question}"`);
- return 'exploratory';
-}
-
// Function to get OpenAI-powered educational guidance (Primary)
async function getOpenAIGuidance(question, language) {
console.log('🤖 Calling OpenAI with GPT-3.5-turbo...');
const isGerman = language === 'de';
- const questionType = analyzeQuestionType(question);
- let systemPrompt;
- let userPrompt;
-
- if (questionType === 'mathematical') {
- systemPrompt = isGerman
- ? "Du bist ein Mathe-Tutor für Kinder. Für einfache Rechenaufgaben führst du das Kind durch konkrete mathematische Schritte, aber verrate NIEMALS die finale Antwort. Erkläre das Rechensymbol, verwende einfache Beispiele, und lass das Kind selbst rechnen. Gib 2-3 Schritte die zum Rechnen anleiten, aber sage NIE das Endergebnis."
- : "You are a math tutor for children. For simple math problems, guide the child through concrete mathematical steps, but NEVER reveal the final answer. Explain the math symbol, use simple examples, and let the child calculate themselves. Provide 2-3 steps that guide calculation, but NEVER state the final result.";
-
- userPrompt = isGerman
- ? `Ein Kind fragt: "${question}". Gib 2-3 konkrete Mathe-Schritte die zum Rechnen anleiten. Erkläre was das Symbol bedeutet, verwende zählbare Beispiele, aber verrate NIEMALS die finale Antwort. Das Kind soll selbst rechnen und die Antwort finden.`
- : `A child asks: "${question}". Provide 2-3 concrete math steps that guide calculation. Explain what the symbol means, use countable examples, but NEVER reveal the final answer. The child should calculate and find the answer themselves.`;
- } else if (questionType === 'factual_simple') {
- systemPrompt = isGerman
- ? "Du bist ein Lernbegleiter für Kinder. Bei einfachen Faktenfragen stellst du 2-3 spezifische, logische Schritte, die das Kind zur Antwort führen. Verwende konkrete Beispiele und Beobachtungen, die das Kind selbst machen kann. Keine allgemeinen Fragen, sondern spezifische Denkschritte."
- : "You are a learning companion for children. For simple factual questions, provide 2-3 specific, logical steps that lead the child to the answer. Use concrete examples and observations the child can make themselves. No general questions, but specific thinking steps.";
-
- userPrompt = isGerman
- ? `Ein Kind fragt: "${question}". Gib 2-3 konkrete Denkschritte, die spezifisch zu dieser Frage passen. Verwende Beispiele und lass das Kind selbst beobachten oder überlegen.`
- : `A child asks: "${question}". Provide 2-3 concrete thinking steps that are specific to this question. Use examples and have the child observe or think for themselves.`;
- } else {
- // For exploratory questions, provide a conversational AI response
- systemPrompt = isGerman
- ? "Du bist ein freundlicher AI-Lehrer für Kinder. Antworte auf ihre Fragen mit einfachen, altersgerechten Erklärungen. Stelle am Ende oft eine Rückfrage, um das Gespräch fortzusetzen und das Kind zum Nachdenken anzuregen. Verwende Emojis und eine warme, einladende Sprache."
- : "You are a friendly AI teacher for children. Answer their questions with simple, age-appropriate explanations. Often ask a follow-up question at the end to continue the conversation and encourage the child to think. Use emojis and warm, inviting language.";
-
- userPrompt = isGerman
- ? `Ein Kind fragt: "${question}". Gib eine freundliche, verständliche Antwort und stelle eine Rückfrage, um das Gespräch fortzusetzen.`
- : `A child asks: "${question}". Give a friendly, understandable answer and ask a follow-up question to continue the conversation.`;
- }
+ const systemPrompt = isGerman
+ ? "Du bist ein geduldiger Lehrer für Kinder. Anstatt direkte Antworten zu geben, führe das Kind Schritt für Schritt zum Verständnis. Stelle 3-4 aufbauende Fragen, die das Kind zum Nachdenken anregen und ihm helfen, die Antwort selbst zu entdecken. Jede Frage sollte auf der vorherigen aufbauen und dem Kind helfen, das Konzept zu verstehen. Verwende einfache Sprache und ermutigende Worte. Formatiere als nummerierte Liste."
+ : "You are a patient teacher for children. Instead of giving direct answers, guide the child step by step to understanding. Ask 3-4 building questions that encourage the child to think and help them discover the answer themselves. Each question should build on the previous one and help the child understand the concept. Use simple language and encouraging words. Format as a numbered list.";
+
+ const userPrompt = isGerman
+ ? `Ein Kind hat gefragt: "${question}". Führe es Schritt für Schritt zum Verständnis, ohne die Antwort direkt zu verraten. Stelle aufbauende Fragen, die dem Kind helfen, selbst zu denken und die Antwort zu entdecken. Jede Frage sollte das Kind näher zur Lösung führen.`
+ : `A child asked: "${question}". Guide them step by step to understanding without giving away the answer directly. Ask building questions that help the child think for themselves and discover the answer. Each question should bring the child closer to the solution.`;
try {
const completion = await openai.chat.completions.create({
@@ -495,29 +151,15 @@ async function getOpenAIGuidance(question, language) {
const aiResponse = completion.choices[0]?.message?.content || '';
console.log('✅ OpenAI response received:', aiResponse.substring(0, 100) + '...');
- if (questionType === 'exploratory') {
- // For exploratory questions, return conversational response
- return {
- type: 'ai-powered',
- questionType: questionType,
- conversationalResponse: aiResponse,
- encouragement: getRandomEncouragement(language),
- source: 'OpenAI GPT-3.5',
- showAnswerReveal: false
- };
- } else {
- // Parse the response into steps for math/factual questions
- const steps = parseOpenAIResponseToSteps(aiResponse, language);
+ // Parse the response into steps
+ const steps = parseOpenAIResponseToSteps(aiResponse, language);
- return {
- type: 'ai-powered',
- questionType: questionType,
- steps: steps,
- encouragement: getRandomEncouragement(language),
- source: 'OpenAI GPT-3.5',
- showAnswerReveal: questionType === 'exploratory' // Only show reveal for complex questions
- };
- }
+ return {
+ type: 'ai-powered',
+ steps: steps,
+ encouragement: getRandomEncouragement(language),
+ source: 'OpenAI GPT-3.5'
+ };
} catch (error) {
console.log('❌ OpenAI error:', error.message);
@@ -680,7 +322,48 @@ async function getAIGuidance(question, language) {
// Fallback guidance for when AI is unavailable
function getFallbackGuidance(question, language) {
const isGerman = language === 'de';
+ const questionLower = question.toLowerCase();
+ // Topic-specific guided questions like in the image
+ if (questionLower.includes('bird') || questionLower.includes('fly') || questionLower.includes('wing')) {
+ const birdQuestions = isGerman ? [
+ { id: 1, text: "Was weißt du bereits über Vögel und ihre Flügel?", type: 'question' },
+ { id: 2, text: "Wie denkst du, nutzen Vögel ihre Flügel, um sich durch die Luft zu bewegen?", type: 'question' },
+ { id: 3, text: "Kannst du an andere Tiere denken, die fliegen können, und wie unterscheiden sie sich in ihren Flugfähigkeiten?", type: 'question' }
+ ] : [
+ { id: 1, text: "What do you already know about this topic?", type: 'question' },
+ { id: 2, text: "How do birds use their wings to generate lift and propel themselves through the air?", type: 'question' },
+ { id: 3, text: "Can you think of any other animals that can fly like birds, and how do they differ in their flying abilities?", type: 'question' }
+ ];
+
+ return {
+ type: 'topic-specific',
+ steps: birdQuestions,
+ encouragement: getRandomEncouragement(language),
+ source: 'Educational Framework'
+ };
+ }
+
+ if (questionLower.includes('sky') || questionLower.includes('blue') || questionLower.includes('himmel') || questionLower.includes('blau')) {
+ const skyQuestions = isGerman ? [
+ { id: 1, text: "Was weißt du bereits über Licht und Farben?", type: 'question' },
+ { id: 2, text: "Was passiert mit Licht, wenn es durch die Luft geht?", type: 'question' },
+ { id: 3, text: "Warum siehst du manche Farben deutlicher als andere?", type: 'question' }
+ ] : [
+ { id: 1, text: "What do you already know about light and colors?", type: 'question' },
+ { id: 2, text: "What happens to light when it travels through the air?", type: 'question' },
+ { id: 3, text: "Why do you see some colors more clearly than others?", type: 'question' }
+ ];
+
+ return {
+ type: 'topic-specific',
+ steps: skyQuestions,
+ encouragement: getRandomEncouragement(language),
+ source: 'Educational Framework'
+ };
+ }
+
+ // Generic fallback questions
const fallbackSteps = isGerman ? [
{ id: 1, text: "Was weißt du bereits über dieses Thema?", type: 'question' },
{ id: 2, text: "Welche Teile der Frage verstehst du, und welche sind unklar?", type: 'question' },
@@ -825,201 +508,3 @@ function getFallbackAnswer(question, language) {
source: 'Educational Framework'
};
}
-
-// Generate additional math hints using AI
-async function generateAdditionalMathHints(question, language, previousHints) {
- const isGerman = language === 'de';
-
- const systemPrompt = isGerman
- ? "Du bist ein geduldiger Mathe-Tutor für Kinder. Das Kind hat bereits Schwierigkeiten mit einer Rechenaufgabe. Gib 2-3 zusätzliche, sehr einfache und konkrete Hilfestellungen. Verwende noch einfachere Beispiele, zerlege die Aufgabe in kleinere Schritte, oder verwende visuelle Hilfsmittel wie Finger oder Gegenstände. Sei ermutigend und geduldig."
- : "You are a patient math tutor for children. The child is already struggling with a math problem. Provide 2-3 additional, very simple and concrete hints. Use even simpler examples, break the problem into smaller steps, or use visual aids like fingers or objects. Be encouraging and patient.";
-
- const userPrompt = isGerman
- ? `Ein Kind hat Schwierigkeiten mit: "${question}". Es braucht zusätzliche, einfachere Hilfe. Gib 2-3 sehr konkrete, einfache Schritte mit visuellen Hilfsmitteln oder noch einfacheren Beispielen.`
- : `A child is struggling with: "${question}". They need additional, simpler help. Provide 2-3 very concrete, simple steps with visual aids or even simpler examples.`;
-
- try {
- const completion = await openai.chat.completions.create({
- model: "gpt-3.5-turbo",
- messages: [
- { role: "system", content: systemPrompt },
- { role: "user", content: userPrompt }
- ],
- max_tokens: 200,
- temperature: 0.7
- });
-
- const aiResponse = completion.choices[0]?.message?.content || '';
- const steps = parseOpenAIResponseToSteps(aiResponse, language);
-
- return {
- type: 'ai-powered',
- steps: steps,
- encouragement: isGerman ? "Keine Sorge, wir schaffen das zusammen! 💪" : "Don't worry, we can do this together! 💪",
- source: 'OpenAI GPT-3.5'
- };
-
- } catch (error) {
- console.log('❌ Additional hints AI error:', error.message);
- throw error;
- }
-}
-
-// Fallback hints for when AI is not available
-function getFallbackMathHints(question, language) {
- const isGerman = language === 'de';
- const questionLower = question.toLowerCase();
-
- // Determine operation type and generate appropriate hints
- let hints = [];
-
- if (questionLower.includes('+') || questionLower.includes('plus')) {
- hints = isGerman ? [
- "Verwende deine Finger zum Zählen - das macht es einfacher!",
- "Nimm die erste Zahl und zähle dann die zweite Zahl dazu.",
- "Du kannst auch kleine Gegenstände wie Münzen oder Stifte zum Zählen verwenden."
- ] : [
- "Use your fingers for counting - it makes it easier!",
- "Take the first number and count the second number on top of it.",
- "You can also use small objects like coins or pencils for counting."
- ];
- } else if (questionLower.includes('-') || questionLower.includes('minus')) {
- hints = isGerman ? [
- "Bei Minus nehmen wir etwas weg. Starte mit der ersten Zahl.",
- "Zähle rückwärts um die zweite Zahl.",
- "Stelle dir vor, du hast Süßigkeiten und gibst einige weg."
- ] : [
- "With minus, we take something away. Start with the first number.",
- "Count backwards by the second number.",
- "Imagine you have candies and you give some away."
- ];
- } else {
- // Generic math hints
- hints = isGerman ? [
- "Lass uns das Problem in kleinere Teile aufteilen.",
- "Verwende deine Finger oder male kleine Kreise zum Zählen.",
- "Nimm dir Zeit - Mathe ist wie ein Puzzle, das wir zusammen lösen."
- ] : [
- "Let's break the problem into smaller parts.",
- "Use your fingers or draw small circles for counting.",
- "Take your time - math is like a puzzle we solve together."
- ];
- }
-
- return {
- type: 'fallback',
- steps: hints.map((hint, index) => ({
- id: index + 1,
- text: hint,
- type: 'hint'
- })),
- encouragement: isGerman ? "Du schaffst das! 🌟" : "You can do it! 🌟",
- source: 'Fallback'
- };
-}
-
-// Generate AI feedback on child's thinking
-async function getThinkingFeedback(question, thought, stepNumber, language) {
- const isGerman = language === 'de';
-
- // Analyze the child's response to provide intelligent feedback
- const thoughtLower = thought.toLowerCase().trim();
-
- // Handle special cases first
- if (thoughtLower === '' || thoughtLower.length < 2) {
- return {
- response: isGerman ? "Erzähl mir mehr über deine Gedanken!" : "Tell me more about your thoughts!",
- encouragement: isGerman ? "Jede Idee zählt! 💭" : "Every idea counts! 💭",
- type: 'encouraging',
- source: 'Rule-based'
- };
- }
-
- if (thoughtLower === 'i dont know' || thoughtLower === 'i don\'t know' || thoughtLower === 'ich weiß nicht' || thoughtLower === 'weiß nicht') {
- return {
- response: isGerman ?
- "Das ist okay! Lass uns gemeinsam überlegen. Was fällt dir als erstes ein, wenn du an diese Frage denkst?" :
- "That's okay! Let's think together. What's the first thing that comes to mind when you think about this question?",
- encouragement: isGerman ? "Gemeinsam finden wir eine Antwort! 🤝" : "Together we'll find an answer! 🤝",
- type: 'supportive',
- source: 'Rule-based'
- };
- }
-
- if (thoughtLower === 'no' || thoughtLower === 'nein' || thoughtLower === 'ja' || thoughtLower === 'yes') {
- return {
- response: isGerman ?
- "Interessant! Kannst du mir mehr darüber erzählen, warum du so denkst?" :
- "Interesting! Can you tell me more about why you think that?",
- encouragement: isGerman ? "Deine Meinung ist wichtig! 💬" : "Your opinion matters! 💬",
- type: 'probing',
- source: 'Rule-based'
- };
- }
-
- // For substantial responses, use AI with much better prompts
- const systemPrompt = isGerman
- ? `Du bist ein intelligenter Tutor für Kinder. Ein Kind hat auf eine Denkfrage geantwortet. Deine Aufgabe:
-
-1. ANALYSIERE den Gedanken des Kindes sorgfältig
-2. ERKENNE richtige Ansätze und baue darauf auf
-3. KORRIGIERE sanft Missverständnisse ohne die Antwort zu verraten
-4. STELLE eine Nachfrage, die das Denken vertieft
-5. SEI spezifisch, nicht generisch
-
-Antworte in 1-2 Sätzen. Vermeide generische Phrasen wie "Gut gemacht!" oder "Weiter so!"`
- : `You are an intelligent tutor for children. A child has responded to a thinking question. Your job:
-
-1. ANALYZE the child's thought carefully
-2. RECOGNIZE correct approaches and build on them
-3. GENTLY correct misunderstandings without revealing the answer
-4. ASK a follow-up question that deepens thinking
-5. BE specific, not generic
-
-Respond in 1-2 sentences. Avoid generic phrases like "Good job!" or "Keep going!"`;
-
- const userPrompt = isGerman
- ? `Original Frage: "${question}"
-Schritt ${stepNumber}
-Kind antwortete: "${thought}"
-
-Gib intelligente, spezifische Rückmeldung zu diesem Gedanken. Baue auf richtigen Ansätzen auf oder korrigiere sanft Missverständnisse. Stelle eine durchdachte Nachfrage.`
- : `Original Question: "${question}"
-Step ${stepNumber}
-Child responded: "${thought}"
-
-Give intelligent, specific feedback about this thought. Build on correct approaches or gently correct misunderstandings. Ask a thoughtful follow-up question.`;
-
- try {
- const completion = await openai.chat.completions.create({
- model: "gpt-3.5-turbo",
- messages: [
- { role: "system", content: systemPrompt },
- { role: "user", content: userPrompt }
- ],
- max_tokens: 120,
- temperature: 0.8
- });
-
- const aiResponse = completion.choices[0]?.message?.content || '';
-
- // Determine feedback type based on content and child's response quality
- let responseType = 'neutral';
- if (thoughtLower.length > 10 || thoughtLower.includes('because') || thoughtLower.includes('weil')) {
- responseType = 'positive';
- } else if (thoughtLower.length < 5) {
- responseType = 'encouraging';
- }
-
- return {
- response: aiResponse.trim(),
- encouragement: isGerman ? "Du denkst gut mit! 🧠" : "You're thinking well! 🧠",
- type: responseType,
- source: 'OpenAI GPT-3.5'
- };
-
- } catch (error) {
- console.log('❌ Thinking feedback AI error:', error.message);
- throw error;
- }
-}
diff --git a/html/kidsai/style.css b/html/kidsai/style.css
index 093e849..d6e3574 100755
--- a/html/kidsai/style.css
+++ b/html/kidsai/style.css
@@ -269,6 +269,7 @@ body {
padding: 30px;
box-shadow: 0 10px 30px rgba(0, 0, 0, 0.2);
animation: fadeInUp 0.8s ease-out;
+ margin-bottom: 20px;
}
.thinking-header h3 {
@@ -293,9 +294,7 @@ body {
border-radius: 15px;
padding: 20px;
margin-bottom: 20px;
- box-shadow: 0 4px 20px rgba(0, 0, 0, 0.08);
- border: 1px solid rgba(102, 126, 234, 0.1);
- backdrop-filter: blur(10px);
+ box-shadow: 0 4px 15px rgba(0, 0, 0, 0.1);
display: flex;
align-items: flex-start;
gap: 15px;
@@ -329,25 +328,23 @@ body {
}
.step-thinking-space {
- margin-top: 15px;
- padding: 15px;
- background: rgba(255, 255, 255, 0.7);
- border-radius: 12px;
- backdrop-filter: blur(10px);
- border: 1px solid rgba(255, 255, 255, 0.3);
+ margin-top: 10px;
}
.step-thinking-space textarea {
width: 100%;
+ height: 60px;
min-height: 60px;
+ max-height: 100px;
padding: 12px;
border: 2px solid #e2e8f0;
border-radius: 8px;
font-family: inherit;
font-size: 0.95rem;
- resize: vertical;
+ resize: none;
transition: border-color 0.3s ease;
background: rgba(247, 250, 252, 0.8);
+ overflow-y: auto;
}
.step-thinking-space textarea:focus {
@@ -422,93 +419,6 @@ body {
font-weight: 400;
}
-/* Check Work Section Styles for Math/Factual Questions */
-.check-work-section {
- margin-top: 30px;
- padding: 0;
-}
-
-.check-work-prompt {
- background: linear-gradient(145deg, #2196F3, #1976D2);
- border-radius: 20px;
- padding: 25px;
- text-align: center;
- box-shadow: 0 8px 32px rgba(33, 150, 243, 0.3);
- border: 2px solid rgba(255, 255, 255, 0.2);
-}
-
-.check-work-prompt h4 {
- color: white;
- font-size: 1.3rem;
- margin-bottom: 15px;
- font-weight: 600;
-}
-
-.check-work-prompt p {
- color: rgba(255, 255, 255, 0.9);
- font-size: 1rem;
- margin-bottom: 20px;
- line-height: 1.5;
-}
-
-.check-work-btn {
- background: rgba(255, 255, 255, 0.2);
- border: 2px solid rgba(255, 255, 255, 0.3);
- color: white;
- padding: 12px 24px;
- border-radius: 25px;
- font-size: 1rem;
- font-weight: 600;
- cursor: pointer;
- transition: all 0.3s ease;
- backdrop-filter: blur(10px);
-}
-
-.check-work-btn:hover {
- background: rgba(255, 255, 255, 0.3);
- border-color: rgba(255, 255, 255, 0.5);
- transform: translateY(-2px);
- box-shadow: 0 5px 15px rgba(0, 0, 0, 0.2);
-}
-
-.check-work-btn:active {
- transform: translateY(0);
-}
-
-/* Encouragement Popup Styles */
-.encouragement-popup {
- position: fixed;
- top: 50%;
- left: 50%;
- transform: translate(-50%, -50%);
- z-index: 1000;
- max-width: 400px;
- width: 90%;
-}
-
-.encouragement-content {
- background: linear-gradient(145deg, #FF9800, #F57C00);
- border-radius: 20px;
- padding: 25px;
- text-align: center;
- box-shadow: 0 10px 40px rgba(255, 152, 0, 0.4);
- border: 2px solid rgba(255, 255, 255, 0.2);
-}
-
-.encouragement-icon {
- font-size: 2rem;
- display: block;
- margin-bottom: 15px;
-}
-
-.encouragement-content p {
- color: white;
- font-size: 1.1rem;
- font-weight: 500;
- margin: 0;
- line-height: 1.5;
-}
-
/* Action Buttons */
.action-buttons {
display: flex;
@@ -1070,697 +980,257 @@ body {
animation: answerReveal 0.6s ease-out;
}
-/* Completion Message Styles for Math/Factual Questions */
-.completion-message {
- margin-top: 30px;
- padding: 0;
-}
-
-.completion-box {
- background: linear-gradient(145deg, #4CAF50, #45a049);
- border-radius: 20px;
- padding: 30px;
- text-align: center;
- box-shadow: 0 8px 32px rgba(76, 175, 80, 0.3);
- border: 2px solid rgba(255, 255, 255, 0.2);
- position: relative;
- overflow: hidden;
-}
-
-.completion-box::before {
- content: '';
- position: absolute;
- top: -50%;
- left: -50%;
- width: 200%;
- height: 200%;
- background: linear-gradient(
- 45deg,
- transparent,
- rgba(255, 255, 255, 0.1),
- transparent
- );
- transform: rotate(45deg);
- animation: shimmer 3s ease-in-out infinite;
-}
-
-.completion-text {
- color: white;
- font-size: 1.2rem;
- font-weight: 600;
- margin-bottom: 20px;
- line-height: 1.6;
- position: relative;
- z-index: 2;
-}
-
-.completion-footer {
- position: relative;
- z-index: 2;
-}
-
-.new-question-btn {
- background: rgba(255, 255, 255, 0.2);
- border: 2px solid rgba(255, 255, 255, 0.3);
- color: white;
- padding: 12px 24px;
- border-radius: 25px;
- font-size: 1rem;
- font-weight: 600;
- cursor: pointer;
- transition: all 0.3s ease;
- backdrop-filter: blur(10px);
-}
-
-.new-question-btn:hover {
- background: rgba(255, 255, 255, 0.3);
- border-color: rgba(255, 255, 255, 0.5);
- transform: translateY(-2px);
- box-shadow: 0 5px 15px rgba(0, 0, 0, 0.2);
-}
-
-.new-question-btn:active {
- transform: translateY(0);
-}
-
-/* Animation for completion message */
-@keyframes shimmer {
- 0% { transform: translateX(-100%) rotate(45deg); }
- 50% { transform: translateX(100%) rotate(45deg); }
- 100% { transform: translateX(200%) rotate(45deg); }
-}
-
-/* Mobile responsiveness for completion section */
+/* Mobile responsiveness for answer section */
@media (max-width: 768px) {
- .completion-box {
- padding: 25px 20px;
- }
-
- .completion-text {
- font-size: 1.1rem;
- }
-
- .new-question-btn {
- padding: 10px 20px;
- font-size: 0.9rem;
- }
-
- .check-work-prompt {
+ .answer-reveal-section {
padding: 20px;
+ margin-top: 20px;
}
- .check-work-prompt h4 {
- font-size: 1.2rem;
- }
-
- .check-work-btn {
- padding: 10px 20px;
- font-size: 0.9rem;
- }
-
- .encouragement-popup {
- max-width: 350px;
- }
-
- .encouragement-content {
- padding: 20px;
- }
-
- .encouragement-content p {
+ .reveal-answer-btn {
+ padding: 12px 25px;
font-size: 1rem;
}
-}
-
-/* Answer Input Section for Math Questions */
-.answer-input-section {
- display: flex;
- gap: 10px;
- margin-top: 15px;
- align-items: center;
- justify-content: center;
- flex-wrap: wrap;
-}
-
-#math-answer-input {
- padding: 10px 15px;
- border: 2px solid rgba(255, 255, 255, 0.3);
- border-radius: 15px;
- background: rgba(255, 255, 255, 0.2);
- color: white;
- font-size: 1rem;
- text-align: center;
- width: 120px;
- backdrop-filter: blur(10px);
-}
-
-#math-answer-input::placeholder {
- color: rgba(255, 255, 255, 0.7);
-}
-
-#math-answer-input:focus {
- outline: none;
- border-color: rgba(255, 255, 255, 0.6);
- background: rgba(255, 255, 255, 0.3);
-}
-
-/* Try Again Section Styles */
-.try-again-section {
- margin-top: 20px;
- padding: 0;
-}
-
-.try-again-content {
- background: linear-gradient(145deg, #FF9800, #F57C00);
- border-radius: 20px;
- padding: 25px;
- text-align: center;
- box-shadow: 0 8px 32px rgba(255, 152, 0, 0.3);
- border: 2px solid rgba(255, 255, 255, 0.2);
-}
-
-.try-again-icon {
- font-size: 2rem;
- display: block;
- margin-bottom: 15px;
-}
-
-.try-again-text {
- color: white;
- font-size: 1.1rem;
- font-weight: 600;
- margin: 0 0 10px 0;
- line-height: 1.5;
-}
-
-.try-again-hint {
- color: rgba(255, 255, 255, 0.9);
- font-size: 0.9rem;
- display: block;
- margin-bottom: 20px;
- font-style: italic;
-}
-
-.try-again-buttons {
- display: flex;
- gap: 15px;
- justify-content: center;
- flex-wrap: wrap;
-}
-
-.more-hints-btn, .try-again-btn {
- background: rgba(255, 255, 255, 0.2);
- border: 2px solid rgba(255, 255, 255, 0.3);
- color: white;
- padding: 10px 20px;
- border-radius: 20px;
- font-size: 0.9rem;
- font-weight: 600;
- cursor: pointer;
- transition: all 0.3s ease;
- backdrop-filter: blur(10px);
-}
-
-.more-hints-btn:hover, .try-again-btn:hover {
- background: rgba(255, 255, 255, 0.3);
- border-color: rgba(255, 255, 255, 0.5);
- transform: translateY(-2px);
-}
-
-.more-hints-btn:disabled {
- opacity: 0.6;
- cursor: not-allowed;
- transform: none;
-}
-
-/* Additional Hints Section Styles */
-.additional-hints-section {
- margin-top: 25px;
- padding: 0;
-}
-
-.additional-hints-header {
- background: linear-gradient(145deg, #9C27B0, #7B1FA2);
- border-radius: 20px;
- padding: 20px;
- text-align: center;
- margin-bottom: 20px;
- box-shadow: 0 8px 32px rgba(156, 39, 176, 0.3);
- border: 2px solid rgba(255, 255, 255, 0.2);
-}
-
-.additional-hints-header h4 {
- color: white;
- font-size: 1.2rem;
- margin: 0 0 10px 0;
- font-weight: 600;
-}
-
-.additional-hints-header p {
- color: rgba(255, 255, 255, 0.9);
- margin: 0;
- font-size: 1rem;
-}
-
-.additional-hint {
- display: flex;
- align-items: flex-start;
- gap: 15px;
- background: rgba(156, 39, 176, 0.1);
- border: 2px solid rgba(156, 39, 176, 0.2);
- border-radius: 15px;
- padding: 20px;
- margin-bottom: 15px;
- backdrop-filter: blur(10px);
-}
-
-.hint-number {
- background: linear-gradient(145deg, #9C27B0, #7B1FA2);
- color: white;
- width: 35px;
- height: 35px;
- border-radius: 50%;
- display: flex;
- align-items: center;
- justify-content: center;
- font-weight: bold;
- font-size: 1rem;
- flex-shrink: 0;
- box-shadow: 0 4px 12px rgba(156, 39, 176, 0.3);
-}
-
-.hint-text {
- color: #2c3e50;
- font-size: 1rem;
- line-height: 1.6;
- flex: 1;
-}
-
-.hints-try-again {
- text-align: center;
- margin-top: 20px;
-}
-
-.try-again-after-hints-btn {
- background: linear-gradient(145deg, #4CAF50, #45a049);
- border: none;
- color: white;
- padding: 12px 25px;
- border-radius: 25px;
- font-size: 1rem;
- font-weight: 600;
- cursor: pointer;
- transition: all 0.3s ease;
- box-shadow: 0 6px 20px rgba(76, 175, 80, 0.3);
-}
-
-.try-again-after-hints-btn:hover {
- transform: translateY(-2px);
- box-shadow: 0 8px 25px rgba(76, 175, 80, 0.4);
-}
-
-/* Simple Message Styles */
-.simple-message .simple-message-content {
- background: linear-gradient(145deg, #607D8B, #455A64);
- border-radius: 15px;
- padding: 20px;
- text-align: center;
-}
-
-.simple-message-icon {
- font-size: 1.5rem;
- display: block;
- margin-bottom: 10px;
-}
-
-.simple-message-content p {
- color: white;
- margin: 0;
- font-size: 1rem;
-}
-
-/* Mobile responsiveness for hints */
-@media (max-width: 768px) {
- .try-again-buttons {
+
+ .answer-box {
+ padding: 20px;
+ }
+
+ .answer-header {
flex-direction: column;
- align-items: center;
- }
-
- .more-hints-btn, .try-again-btn {
- width: 100%;
- max-width: 200px;
- }
-
- .additional-hint {
- flex-direction: column;
- text-align: center;
- gap: 10px;
- }
-
- .hint-number {
- align-self: center;
- }
-
- .additional-hints-header {
- padding: 15px;
- }
-}
-
-/* Interactive Thinking Styles */
-.thinking-textarea {
- width: 100%;
- padding: 12px;
- border: 2px solid #e0e6ed;
- border-radius: 10px;
- font-size: 1rem;
- line-height: 1.4;
- resize: vertical;
- transition: all 0.3s ease;
- font-family: inherit;
-}
-
-.thinking-textarea:focus {
- outline: none;
- border-color: #667eea;
- box-shadow: 0 0 0 3px rgba(102, 126, 234, 0.1);
-}
-
-.share-thought-btn {
- background: linear-gradient(145deg, #667eea, #764ba2);
- border: none;
- color: white;
- padding: 8px 16px;
- border-radius: 20px;
- font-size: 0.9rem;
- font-weight: 500;
- cursor: pointer;
- margin-top: 10px;
- transition: all 0.3s ease;
- display: inline-flex;
- align-items: center;
- gap: 5px;
-}
-
-.share-thought-btn:hover {
- transform: translateY(-1px);
- box-shadow: 0 4px 12px rgba(102, 126, 234, 0.3);
-}
-
-.share-thought-btn:disabled {
- opacity: 0.6;
- cursor: not-allowed;
- transform: none;
-}
-
-/* AI Feedback Styles */
-.thinking-feedback {
- margin-top: 15px;
-}
-
-.ai-feedback {
- display: flex;
- align-items: flex-start;
- gap: 12px;
- padding: 15px;
- border-radius: 12px;
- backdrop-filter: blur(10px);
- border: 1px solid rgba(255, 255, 255, 0.2);
-}
-
-.positive-feedback {
- background: linear-gradient(145deg, rgba(76, 175, 80, 0.9), rgba(69, 160, 73, 0.9));
- color: white;
-}
-
-.neutral-feedback {
- background: linear-gradient(145deg, rgba(33, 150, 243, 0.9), rgba(30, 136, 229, 0.9));
- color: white;
-}
-
-.encouraging-feedback {
- background: linear-gradient(145deg, rgba(255, 152, 0, 0.9), rgba(245, 124, 0, 0.9));
- color: white;
-}
-
-.feedback-icon {
- font-size: 1.5rem;
- flex-shrink: 0;
-}
-
-.feedback-content {
- flex: 1;
-}
-
-.feedback-text {
- margin: 0 0 5px 0;
- font-size: 1rem;
- line-height: 1.4;
- font-weight: 500;
-}
-
-.feedback-source {
- opacity: 0.8;
- font-size: 0.8rem;
- font-style: italic;
-}
-
-/* Step thinking space improvements */
-.step-thinking-space {
- margin-top: 15px;
- padding: 15px;
- background: rgba(255, 255, 255, 0.7);
- border-radius: 12px;
- backdrop-filter: blur(10px);
- border: 1px solid rgba(255, 255, 255, 0.3);
-}
-
-/* Mobile responsiveness for interactive thinking */
-@media (max-width: 768px) {
- .thinking-textarea {
- font-size: 16px; /* Prevents zoom on iOS */
- }
-
- .share-thought-btn {
- width: 100%;
- justify-content: center;
- padding: 10px 16px;
- }
-
- .ai-feedback {
- flex-direction: column;
- text-align: center;
+ align-items: flex-start;
gap: 8px;
}
- .feedback-icon {
- align-self: center;
+ .answer-source {
+ margin-left: 0;
}
}
-/* AI Conversation Styles */
-.ai-question-reply {
- border-top: 1px solid rgba(255, 255, 255, 0.2);
- padding-top: 15px;
- margin-top: 15px;
- /* Debug: make sure it's visible */
- min-height: 50px;
- background: rgba(255, 255, 255, 0.1);
+/* Interactive Chat Interface Styles */
+.conversation-container {
+ max-width: 800px;
+ margin: 0 auto;
+ padding: 20px;
+ background: white;
+ border-radius: 20px;
+ box-shadow: 0 5px 20px rgba(0, 0, 0, 0.1);
+ min-height: 400px;
}
-.reply-input-section {
- display: flex;
- gap: 12px;
- align-items: flex-end;
- margin: 20px 0;
- padding: 15px;
- background: rgba(255, 255, 255, 0.05);
- border-radius: 15px;
- border: 1px solid rgba(255, 255, 255, 0.1);
+.conversation-step {
+ opacity: 0;
+ transform: translateY(30px);
+ transition: all 0.6s ease-out;
+ margin-bottom: 25px;
+ min-height: auto; /* Ensure no artificial height constraints */
}
-.ai-reply-input {
- flex: 1;
- padding: 10px 12px;
- border: 2px solid rgba(255, 255, 255, 0.4);
- border-radius: 12px;
- background: rgba(255, 255, 255, 0.9);
- color: #333;
- font-size: 0.9rem;
- resize: vertical;
- min-height: 44px;
- backdrop-filter: blur(10px);
- font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
+.conversation-step.visible {
+ opacity: 1;
+ transform: translateY(0);
}
-.ai-reply-input::placeholder {
- color: rgba(0, 0, 0, 0.5);
-}
-
-.ai-reply-input:focus {
- outline: none;
- border-color: #4CAF50;
- background: rgba(255, 255, 255, 0.95);
- box-shadow: 0 0 0 3px rgba(76, 175, 80, 0.2);
-}
-
-.reply-to-ai-btn {
- background: #4CAF50;
- border: 2px solid #4CAF50;
+.ai-message {
+ background: linear-gradient(135deg, #48bb78, #38a169);
+ border-radius: 20px 20px 20px 5px;
+ padding: 20px;
+ margin-bottom: 20px;
color: white;
- padding: 10px 16px;
- border-radius: 12px;
- font-size: 0.9rem;
+ box-shadow: 0 4px 15px rgba(72, 187, 120, 0.3);
+}
+
+.message-header {
+ display: flex;
+ align-items: center;
+ gap: 10px;
+ margin-bottom: 10px;
+}
+
+.ai-avatar {
+ font-size: 1.2em;
+}
+
+.ai-label {
+ font-weight: 600;
+ font-size: 0.9em;
+ opacity: 0.9;
+}
+
+.message-content {
+ line-height: 1.6;
+}
+
+.chat-message {
+ margin-bottom: 15px;
+ opacity: 0;
+ transform: translateY(20px);
+ transition: all 0.5s ease-out;
+ max-width: 85%;
+}
+
+.chat-message.visible {
+ opacity: 1;
+ transform: translateY(0);
+}
+
+.chat-message.ai-message {
+ align-self: flex-start;
+ margin-right: auto;
+}
+
+.chat-message.user-message {
+ align-self: flex-end;
+ margin-left: auto;
+ background: linear-gradient(135deg, #4299e1, #3182ce);
+ border-radius: 20px 20px 5px 20px;
+ padding: 15px 20px;
+ color: white;
+ box-shadow: 0 3px 10px rgba(66, 153, 225, 0.3);
+}
+
+.chat-message.ai-message {
+ background: linear-gradient(135deg, #48bb78, #38a169);
+ border-radius: 20px 20px 20px 5px;
+ padding: 15px 20px;
+ color: white;
+ box-shadow: 0 3px 10px rgba(72, 187, 120, 0.3);
+}
+
+.chat-message .message-header {
+ display: flex;
+ align-items: center;
+ gap: 8px;
+ margin-bottom: 8px;
+ font-size: 0.85em;
+ opacity: 0.9;
+}
+
+.chat-message .message-content {
+ line-height: 1.5;
+}
+
+.chat-message .message-content p {
+ margin: 0;
+ word-wrap: break-word;
+}
+
+.chat-input-container {
+ margin: 20px 0;
+ opacity: 0;
+ transform: translateY(10px);
+ transition: all 0.3s ease-out;
+}
+
+.chat-input-container.visible {
+ opacity: 1;
+ transform: translateY(0);
+}
+
+.chat-input-container .input-area {
+ display: flex;
+ gap: 10px;
+ align-items: flex-end;
+ background: #f8f9fa;
+ border-radius: 25px;
+ padding: 10px 15px;
+ border: 2px solid #e2e8f0;
+ transition: border-color 0.3s ease;
+}
+
+.chat-input-container .input-area:focus-within {
+ border-color: #4299e1;
+ box-shadow: 0 0 0 3px rgba(66, 153, 225, 0.1);
+}
+
+.chat-input-container .input-area.answered {
+ background: #f0f9ff;
+ border-color: #48bb78;
+ opacity: 0.7;
+}
+
+.chat-textarea {
+ flex: 1;
+ min-height: 20px;
+ max-height: 100px;
+ padding: 10px 0;
+ border: none;
+ background: transparent;
+ font-family: inherit;
+ font-size: 14px;
+ resize: none;
+ outline: none;
+ overflow-y: auto;
+}
+
+.chat-textarea::placeholder {
+ color: #a0aec0;
+ font-style: italic;
+}
+
+.chat-input-container .reply-btn {
+ background: linear-gradient(135deg, #4299e1, #3182ce);
+ color: white;
+ border: none;
+ border-radius: 20px;
+ padding: 8px 15px;
+ font-size: 13px;
font-weight: 600;
cursor: pointer;
transition: all 0.3s ease;
+ display: flex;
+ align-items: center;
+ gap: 5px;
white-space: nowrap;
- font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
}
-.reply-to-ai-btn:hover:not(:disabled) {
- background: #45a049;
- border-color: #45a049;
+.chat-input-container .reply-btn:hover {
transform: translateY(-1px);
- box-shadow: 0 4px 8px rgba(76, 175, 80, 0.3);
+ box-shadow: 0 4px 12px rgba(66, 153, 225, 0.4);
}
-.reply-to-ai-btn:disabled {
- opacity: 0.6;
+.chat-input-container .reply-btn:disabled {
+ opacity: 0.5;
cursor: not-allowed;
transform: none;
}
-/* Conversation Exchange Styles */
-.ai-conversation {
- max-height: 300px;
- overflow-y: auto;
- padding: 10px 0;
- border-radius: 12px;
-}
-
-.conversation-user,
-.conversation-ai {
- margin-bottom: 12px;
- opacity: 0;
- transform: translateY(10px);
- transition: all 0.4s ease-out;
-}
-
-.conversation-bubble {
+/* Ensure the conversation flows like a real chat */
+.conversation-container {
display: flex;
- gap: 10px;
- align-items: flex-start;
- padding: 15px;
- border-radius: 15px;
- max-width: 85%;
- margin-bottom: 12px;
- box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);
+ flex-direction: column;
}
-.user-bubble {
- background: rgba(255, 255, 255, 0.9);
- border: 1px solid rgba(255, 255, 255, 0.4);
- margin-left: auto;
- flex-direction: row-reverse;
-}
-
-.user-bubble .bubble-text {
- color: #333;
-}
-
-.ai-bubble {
- background: rgba(76, 175, 80, 0.15);
- border: 1px solid rgba(76, 175, 80, 0.3);
- margin-right: auto;
-}
-
-.bubble-icon {
- font-size: 1.2rem;
- flex-shrink: 0;
- width: 32px;
- height: 32px;
- display: flex;
- align-items: center;
- justify-content: center;
- border-radius: 50%;
- background: rgba(255, 255, 255, 0.3);
-}
-
-.bubble-text {
+/* Make reveal section part of the chat flow */
+.reveal-section {
+ margin-top: 30px;
+ padding: 20px;
+ background: linear-gradient(135deg, #667eea, #764ba2);
+ border-radius: 20px;
color: white;
- font-size: 0.95rem;
- line-height: 1.5;
- flex: 1;
- font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
-}
-
-.user-bubble .bubble-text {
- text-align: right;
-}
-
-/* Conversation Completion */
-.conversation-completion {
text-align: center;
- margin-top: 15px;
- opacity: 0;
- transform: translateY(10px);
- transition: all 0.4s ease-out;
}
-.completion-message {
- background: linear-gradient(145deg, #FFD700, #FFA500);
- border-radius: 15px;
- padding: 15px;
+.reveal-prompt p {
+ margin-bottom: 15px;
+ font-size: 1.1em;
+}
+
+.reveal-btn {
+ background: rgba(255, 255, 255, 0.2);
color: white;
+ border: 2px solid rgba(255, 255, 255, 0.3);
+ border-radius: 25px;
+ padding: 12px 25px;
+ font-size: 1em;
font-weight: 600;
+ cursor: pointer;
+ transition: all 0.3s ease;
+ backdrop-filter: blur(10px);
}
-.completion-icon {
- font-size: 1.5rem;
- display: block;
- margin-bottom: 8px;
-}
-
-.completion-message p {
- margin: 0;
- font-size: 0.9rem;
-}
-
-/* Mobile responsiveness for conversation */
-@media (max-width: 768px) {
- .reply-input-section {
- flex-direction: column;
- gap: 10px;
- }
-
- .reply-to-ai-btn {
- width: 100%;
- }
-
- .conversation-bubble {
- max-width: 95%;
- padding: 10px;
- }
-
- .bubble-icon {
- width: 25px;
- height: 25px;
- font-size: 1rem;
- }
-
- .bubble-text {
- font-size: 0.85rem;
- }
-
- .ai-conversation {
- max-height: 250px;
- }
-}
-
-/* AI Teacher Badge in Conversation Bubbles */
-.ai-teacher-badge {
- font-size: 0.75rem;
- color: rgba(255, 255, 255, 0.8);
- margin-top: 8px;
- text-align: right;
- font-style: italic;
+.reveal-btn:hover {
+ background: rgba(255, 255, 255, 0.3);
+ transform: translateY(-2px);
+ box-shadow: 0 5px 15px rgba(0, 0, 0, 0.2);
}