ruslanmv's picture
Update app.py
42397ec verified
raw
history blame
12.1 kB
# app.py
import gradio as gr
from tool2 import * # Make sure this is tool2, and tool2.py is updated with correct code
from backend1 import *
# Global variable to store the currently selected set of exam questions
selected_questions = []
description_str = """Developed by Ruslan Magana, this interactive quiz platform is designed to help you prepare and assess your knowledge in a variety of exams.
For more information about the developer, please visit [ruslanmv.com](https://ruslanmv.com/).
**Get Started with Your Quiz**
Select an exam from the dropdown menu below and start testing your skills. You can also choose to enable audio feedback to enhance your learning experience. Simply toggle the "Enable Audio" checkbox to turn it on or off."""
# --- FUNCTION DEFINITIONS ---
def start_exam(exam_choice, start_question, audio_enabled):
"""Starts the exam by selecting questions, setting up UI."""
global selected_questions
selected_questions = select_exam_vce(exam_choice)
if not selected_questions: # Handle case where no questions are loaded for selected exam
return (
gr.update(visible=True), # Show title
gr.update(value="**Error: No Questions Found for this Exam**", visible=True), # Update description to error message
gr.update(visible=True), # Show exam_selector
gr.update(visible=True), # Show start_button
gr.update(visible=True), # Show the audio_checkbox
gr.update(visible=True), # Show start_question_slider
# Hide quiz elements
gr.update(visible=False), # Hide question_text
"", # Question to display
gr.update(choices=[], visible=False), # Hide Radio choices
gr.update(visible=False), # Hide answer_button
gr.update(visible=False), # Hide next_button
gr.update(visible=False), # Hide prev_button
gr.update(visible=False), # Hide home_button
0, "", # Update the question state
None, # Provide the audio_path
gr.update(visible=False), # Hide explain_button
gr.update(visible=False),
None # None for audio stop
)
if start_question >= len(selected_questions):
start_question = 0 # Default to the first question if the input exceeds available questions
question, options, audio_path = display_question(start_question, audio_enabled, selected_questions)
return (
# Hide start screen elements
gr.update(visible=False), # Hide title
gr.update(visible=False), # Hide description
gr.update(visible=False), # Hide exam_selector
gr.update(visible=False), # Hide start_button
gr.update(visible=False), # Hide the audio_checkbox
gr.update(visible=False), # Hide start_question_slider
# Show quiz elements
gr.update(visible=True), # Show question_text
question, # Question to display
gr.update(choices=options, visible=True), # Update Radio choices and make visible
gr.update(visible=True), # Show answer_button
gr.update(visible=True),# Show next_button
gr.update(visible=True), # Show prev_button
gr.update(visible=True), # Show home_button
start_question, "", # Update the question state
audio_path, # Provide the audio_path
gr.update(visible=True), # Show explain_button
gr.update(visible=True),
None # None for the audio stop signal
)
def display_question_ui(index, audio_enabled): # Changed function name and parameters
"""Displays a question with options and generates audio (if enabled) and updates UI elements."""
question, options, audio_path = display_question(index, audio_enabled, selected_questions)
return question, gr.update(choices=options), audio_path
def show_explanation(index):
"""Shows the explanation for the current question and hides previous results."""
explanation, correct_answer = get_explanation_and_answer(index, selected_questions) # Get both explanation and answer
if 0 <= index < len(selected_questions):
return (
f"**Explanation:** {explanation}",
gr.update(visible=True), # Show explanation_text
gr.update(visible=True) # Show result_text - ensure result_text is shown when explanation is shown
)
else:
return "No explanation available for this question.", gr.update(visible=False), gr.update(visible=False)
def check_answer(index, answer):
"""Checks the given answer against the correct answer."""
explanation, correct_answer = get_explanation_and_answer(index, selected_questions) # Get correct answer
if answer == correct_answer:
return f"Correct! The answer is: {correct_answer}"
else:
return f"Incorrect. The correct answer is: {correct_answer}"
def update_question(index, audio_enabled):
"""Updates the displayed question when the index changes."""
return display_question_ui(index, audio_enabled) # Use display_question_ui for UI updates
def handle_answer(index, answer, audio_enabled, current_audio):
"""Handles answer submission, provides feedback, and generates audio."""
# Handle the case when no answer is selected
if answer is None:
return "Please select an option before submitting.", None, None
# Stop the current question audio before playing the answer audio
stop_audio = True if current_audio else False
result = check_answer(index, answer)
answer_audio_path = text_to_speech(result) if audio_enabled else None
return result, answer_audio_path, stop_audio
def handle_next(index, audio_enabled):
"""Moves to the next question and updates the UI."""
new_index = min(index + 1, len(selected_questions) - 1)
question, options, audio_path = update_question(new_index, audio_enabled)
return question, options, new_index, "", audio_path, gr.update(visible=False), gr.update(value="") # Hide explanation and clear result text
def handle_previous(index, audio_enabled):
"""Moves to the previous question and updates the UI."""
new_index = max(index - 1, 0)
question, options, audio_path = update_question(new_index, audio_enabled)
return question, options, new_index, "", audio_path, gr.update(visible=False), gr.update(value="") # Hide explanation and clear result text
def return_home():
"""Returns to the home screen."""
return (
# Show start screen elements
gr.update(visible=True), gr.update(value="**AWS Exam Simulator (Quiz)**", visible=True), gr.update(visible=True), gr.update(visible=True), # Reset title and description value
gr.update(visible=True), # Show the audio_checkbox
gr.update(visible=True), # Show start_question_slider - show slider on home return
# Hide quiz elements
gr.update(visible=False), gr.update(visible=False), gr.update(visible=False), gr.update(visible=False),
gr.update(visible=False), gr.update(visible=False), gr.update(visible=False), 0, "", gr.update(visible=False), gr.update(visible=False),
gr.update(visible=False), gr.update(value="") # Hide explain button and clear result text
)
with gr.Blocks() as demo:
# Home page elements
title = gr.Markdown(value="**AWS Exam Simulator (Quiz)**")
description = gr.Markdown(value=description_str)
exam_selector = gr.Dropdown(label="Select an exam", choices=exams, value=None)
audio_checkbox = gr.Checkbox(label="Enable Audio", value=True, visible=False)
start_question_slider = gr.Slider(minimum=0, maximum=50, step=1, label="Select starting question", visible=False) # Slider for selecting the starting question
start_button = gr.Button("Start Exam", visible=False)
# Quiz elements (initially hidden)
question_state = gr.State(0)
current_audio_state = gr.State(None) # State to track the current audio playing
question_text = gr.Markdown(visible=False, elem_id="question-text")
choices = gr.Radio(visible=False, label="Options")
result_text = gr.Markdown(visible=False) # Initially hidden, shown when answer is submitted or explanation is shown
explanation_text = gr.Markdown(visible=False)
answer_button = gr.Button("Submit Answer", visible=False)
next_button = gr.Button("Next Question", visible=False)
prev_button = gr.Button("Previous Question", visible=False)
home_button = gr.Button("Return to Home", visible=False)
explain_button = gr.Button("Explain", visible=False)
question_audio = gr.Audio(visible=False, label="Question Audio", autoplay=True)
answer_audio = gr.Audio(visible=False, label="Answer Audio", autoplay=True)
# Layout for the home page
with gr.Row():
gr.Column([title])
with gr.Row():
gr.Column([description])
with gr.Row():
gr.Column([exam_selector])
with gr.Row():
gr.Column([audio_checkbox, start_question_slider])
with gr.Row():
gr.Column([start_button])
# Layout for the quiz
with gr.Row():
gr.Column([question_text, question_audio])
with gr.Row():
gr.Column([choices])
with gr.Row():
gr.Column([result_text, explanation_text, answer_audio])
with gr.Row():
gr.Column([prev_button], scale=1)
gr.Column([], scale=8)
gr.Column([next_button], scale=1)
with gr.Row():
gr.Column([answer_button, explain_button])
with gr.Row():
gr.Column([home_button])
# Show settings after exam selection
def show_settings(exam_choice):
return gr.update(visible=True), gr.update(visible=True), gr.update(visible=True)
# Connect exam selection to display settings section
exam_selector.change(fn=show_settings, inputs=[exam_selector], outputs=[audio_checkbox, start_question_slider, start_button])
# Connect the start button to start the exam
start_button.click(
fn=start_exam,
inputs=[exam_selector, start_question_slider, audio_checkbox],
outputs=[
title, description, exam_selector, start_button,
audio_checkbox, # Ensure the checkbox visibility is updated
start_question_slider, # Ensure the slider is hidden
question_text, question_text, choices, answer_button,
next_button, prev_button, home_button, question_state, result_text, question_audio,
explain_button, explanation_text, current_audio_state # Add explanation_text to outputs, corrected from result_text, and use explanation_text for explanation
]
)
# Connect the quiz buttons to their functions
answer_button.click(fn=handle_answer, inputs=[question_state, choices, audio_checkbox, current_audio_state], outputs=[result_text, answer_audio, current_audio_state])
next_button.click(fn=handle_next, inputs=[question_state, audio_enabled], outputs=[question_text, choices, question_state, result_text, question_audio, explanation_text, result_text]) # Added result_text to clear on next
prev_button.click(fn=handle_previous, inputs=[question_state, audio_enabled], outputs=[question_text, choices, question_state, result_text, question_audio, explanation_text, result_text]) # Added result_text to clear on prev
explain_button.click(fn=show_explanation, inputs=[question_state], outputs=[explanation_text, result_text, explanation_text]) # Corrected output to explanation_text for the last element which was incorrectly result_text
home_button.click(fn=return_home, inputs=None, outputs=[
title, description, exam_selector, start_button,
audio_checkbox, # Ensure the checkbox visibility is updated
start_question_slider, # Ensure the slider is shown
question_text, question_text, choices, answer_button,
next_button, prev_button, home_button, question_state, result_text, explanation_text, explain_button, result_text # Added result_text to clear on home, and corrected outputs to include explanation_text
])
demo.launch()