| import os |
| import re |
| import streamlit as st |
| from openai import OpenAI |
| from dotenv import load_dotenv |
|
|
| load_dotenv() |
| client = OpenAI(api_key=os.getenv("OPENAI_API_KEY")) |
|
|
| |
| |
| |
|
|
| def default_prompt_builder( |
| math_subject: str, |
| topic: str, |
| difficulty: str, |
| speaking_style: str, |
| example1: str, |
| problem1: str, |
| wordproblem: str, |
| prev_lecture: str |
| ) -> str: |
| """ |
| Builds the base lecture prompt. |
| """ |
| return f""" |
| You are a math teacher. Create a comprehensive lecture script for a lesson in "{math_subject}" on the topic "{topic}" |
| that transitions seamlessly from start to finish. Deliver the lecture in a {speaking_style} style, |
| appropriate for a(n) {difficulty} audience, using English only. |
| |
| The script must be fluent with smooth transitions and detailed explanations of the concepts. |
| |
| 1. **Hook :** |
| Provide a concise, empowering introduction that engages the learners and clearly introduces the subject and topic. |
| If any relevant material from a previous lecture should be mentioned, briefly reference it here: |
| "{prev_lecture}" |
| |
| 2. **Topic Intro :** |
| Present a concise background or interesting fact about the topic. |
| |
| 3. **Core Concept Definition :** |
| Provide a clear definition of the core concepts. Explain their importance and mention any |
| fundamental equations, theorems, or limit definitions that underlie them. Include mathematical equations if necessary. |
| |
| 4. **Detailed Explanation :** |
| Offer a detailed, step-by-step explanation of the topic. Incorporate deeper theoretical underpinnings— |
| such as derivations from first principles or explanations of common misconceptions and how to avoid them. |
| |
| 5. **Example Problem :** |
| Use the following example problem for a thorough walkthrough: |
| "{example1}" |
| - Provide a step-by-step solution (e.g., Step1, Step2, Step3, etc.). |
| - Reference relevant theorems or limit definitions. |
| - Mention common mistakes with transitions and how to correct them. |
| - Summarize the final result clearly. |
| |
| 6. **Problem 1 :** |
| Use the following second problem: |
| "{problem1}" |
| Provide a detailed solution with numbered steps and transitions, referencing theorems/definitions, and summarizing the result. |
| |
| 7. **Word Problem :** |
| Use the following word problem: |
| "{wordproblem}" |
| Solve it thoroughly with numbered steps and transitions, referencing key theorems, discussing pitfalls, and offering alternative approaches. |
| |
| 8. **Engagement, Reinforcement, and Conclusion :** |
| Summarize the key points and offer additional tips or alternative approaches for deeper understanding. |
| End with a motivational wrap-up, leaving the audience with a final thought or question. |
| |
| Begin your response now. |
| """ |
|
|
| def call_openai_chat(prompt: str, max_tokens: int = 2000, temperature: float = 0.4) -> str: |
| """ |
| Calls the OpenAI chat completions API with the provided prompt. |
| """ |
| response = client.chat.completions.create( |
| model="gpt-4o-2024-08-06", |
| messages=[{"role": "user", "content": prompt}], |
| max_tokens=max_tokens, |
| temperature=temperature |
| ) |
| return response.choices[0].message.content.strip() |
|
|
| def check_transitions(lecture_script: str) -> str: |
| prompt = f""" |
| Review the following lecture script and identify any sections that lack smooth transitions. |
| Point out where transitions are missing and suggest improvements. |
| |
| Lecture Script: |
| \"\"\"{lecture_script}\"\"\" |
| |
| Return only your feedback and suggestions. |
| """ |
| return call_openai_chat(prompt) |
|
|
| def check_errors(lecture_script: str) -> str: |
| prompt = f""" |
| Review the following lecture script for any errors including grammar, mathematical inaccuracies, or formatting issues. |
| List the errors and provide suggestions for corrections. |
| |
| Lecture Script: |
| \"\"\"{lecture_script}\"\"\" |
| |
| Return only your feedback and suggestions. |
| """ |
| return call_openai_chat(prompt) |
|
|
| def check_step_organization(lecture_script: str) -> str: |
| prompt = f""" |
| Analyze the following lecture script and check whether all problem solutions have their steps clearly enumerated (e.g., Step1, Step2, Step3, etc.). |
| If any solutions are missing this clear organization, list those sections and suggest improvements. |
| |
| Lecture Script: |
| \"\"\"{lecture_script}\"\"\" |
| |
| Return only your feedback and suggestions. |
| """ |
| return call_openai_chat(prompt) |
|
|
| def refine_lecture_manual(lecture_script: str, transitions_feedback: str, errors_feedback: str, steps_feedback: str) -> str: |
| """ |
| Produces a refined version of the lecture script using agent feedback. |
| This version may include a separate **Common Mistakes:** section. |
| """ |
| prompt = f""" |
| You are an expert in educational content design. Below is the original lecture script along with feedback from three specialized agents: |
| |
| --- Original Lecture Script --- |
| \"\"\"{lecture_script}\"\"\" |
| |
| --- Feedback --- |
| Transitions Feedback: |
| {transitions_feedback} |
| |
| Errors Feedback: |
| {errors_feedback} |
| |
| Step Organization Feedback: |
| {steps_feedback} |
| |
| Using this feedback, provide a refined version of the lecture script that addresses all the issues mentioned. |
| Ensure that transitions between sections are smooth, all errors are corrected, and all problem solutions have clearly enumerated steps. |
| Include a section labeled **Common Mistakes:** if necessary. |
| Return only the refined lecture script. |
| """ |
| return call_openai_chat(prompt) |
|
|
| def add_extra_transitions(lecture_script: str) -> str: |
| """ |
| Enhances the refined lecture script by integrating transitions, summaries, and commentary on common mistakes seamlessly into the narrative. |
| This function checks if the refined script contains integrated commentary on common mistakes (e.g., "Common Mistake:" or "**Pitfall:**") |
| and summary insights (e.g., "Summary:"). If such elements are missing or not well integrated, it weaves them naturally into the text. |
| """ |
| prompt = f""" |
| You are provided with a refined lecture script. Your task is to enhance it by: |
| 1. Adding explicit transitions between steps and sections. |
| 2. Seamlessly integrating key conclusions, summary insights, and commentary on common mistakes directly into the narrative. |
| 3. Checking whether the lecture script includes integrated remarks on common mistakes (e.g., "Common Mistake:" or "**Pitfall:**") and summaries (e.g., "Summary:"); if not, embed these elements naturally into the content. |
| 4. Avoid appending these as separate sections—instead, ensure the final output reads as a unified, continuous lecture script. |
| |
| Return only the enhanced lecture script. |
| |
| Lecture Script: |
| \"\"\"{lecture_script}\"\"\" |
| """ |
| return call_openai_chat(prompt) |
|
|
| |
| |
| |
|
|
| st.sidebar.header("Input Parameters") |
|
|
| math_subject = st.sidebar.text_input("Math Subject", value="Algebra") |
| topic = st.sidebar.text_input("Topic", value="Quadratic Equations") |
| difficulty = st.sidebar.selectbox("Difficulty", options=["beginner", "intermediate", "advanced"], index=1) |
| speaking_style = st.sidebar.text_input("Speaking Style", value="engaging and clear") |
| example1 = st.sidebar.text_area("Example Problem", value="Solve x^2 - 5x + 6 = 0") |
| problem1 = st.sidebar.text_area("Problem 1", value="Find the roots of 2x^2 - 4x - 6 = 0") |
| wordproblem = st.sidebar.text_area("Word Problem", value="A projectile is launched with a height given by h(t) = -4.9t^2 + 20t + 5. Determine when it reaches the ground.") |
| prev_lecture = st.sidebar.text_area("Previous Lecture Reference", value="We covered linear equations and basic factoring techniques.") |
|
|
| |
| |
| |
|
|
| st.title("Lecture Script Generator and Refinement Interface") |
|
|
| |
| default_prompt = default_prompt_builder( |
| math_subject, topic, difficulty, speaking_style, example1, problem1, wordproblem, prev_lecture |
| ) |
|
|
| |
| if "custom_prompt" not in st.session_state: |
| st.session_state.custom_prompt = default_prompt |
|
|
| st.subheader("Lecture Prompt Template (Editable)") |
| st.write("This is the template with numbered sections and placeholders. Use the button below to update it based on the current input parameters, or edit it directly.") |
| if st.button("Update Prompt Template with current placeholder values"): |
| st.session_state.custom_prompt = default_prompt |
|
|
| |
| custom_prompt = st.text_area("Edit Lecture Prompt Template", value=st.session_state.custom_prompt, height=400, key="custom_prompt_main") |
| st.session_state.custom_prompt = custom_prompt |
|
|
| |
| |
| |
|
|
| if st.button("Generate Lecture Script"): |
| with st.spinner("Generating lecture script and running agent checks..."): |
| |
| lecture_script = call_openai_chat(custom_prompt) |
| |
| transitions_feedback = check_transitions(lecture_script) |
| errors_feedback = check_errors(lecture_script) |
| steps_feedback = check_step_organization(lecture_script) |
| |
| refined_script = refine_lecture_manual(lecture_script, transitions_feedback, errors_feedback, steps_feedback) |
| |
| scriptified_script = add_extra_transitions(refined_script) |
| |
| st.session_state['lecture_script'] = lecture_script |
| st.session_state['transitions_feedback'] = transitions_feedback |
| st.session_state['errors_feedback'] = errors_feedback |
| st.session_state['steps_feedback'] = steps_feedback |
| st.session_state['refined_script'] = refined_script |
| st.session_state['scriptified_script'] = scriptified_script |
| st.success("Lecture script, agent feedback, and both refined scripts generated!") |
|
|
| |
| |
| |
|
|
| if "lecture_script" in st.session_state: |
| st.subheader("Generated Lecture Script (Editable)") |
| lecture_script = st.text_area("Lecture Script", value=st.session_state['lecture_script'], height=300) |
| st.session_state['lecture_script'] = lecture_script |
|
|
| if st.button("Update Agent Feedback"): |
| with st.spinner("Fetching updated agent feedback..."): |
| transitions_feedback = check_transitions(lecture_script) |
| errors_feedback = check_errors(lecture_script) |
| steps_feedback = check_step_organization(lecture_script) |
| st.session_state['transitions_feedback'] = transitions_feedback |
| st.session_state['errors_feedback'] = errors_feedback |
| st.session_state['steps_feedback'] = steps_feedback |
| st.success("Agent feedback updated!") |
|
|
| |
| |
| |
| if "lecture_script" in st.session_state and st.session_state.get("transitions_feedback") is not None: |
| if st.button("Regenerate Refined Lecture Scripts"): |
| with st.spinner("Regenerating refined lecture scripts..."): |
| refined_script = refine_lecture_manual( |
| st.session_state["lecture_script"], |
| st.session_state.get('transitions_feedback', ''), |
| st.session_state.get('errors_feedback', ''), |
| st.session_state.get('steps_feedback', '') |
| ) |
| scriptified_script = add_extra_transitions(refined_script) |
| st.session_state['refined_script'] = refined_script |
| st.session_state['scriptified_script'] = scriptified_script |
| st.success("Both refined lecture scripts regenerated!") |
|
|
| |
| |
| |
| if "refined_script" in st.session_state and "scriptified_script" in st.session_state: |
| st.subheader("Refined and Scriptified Lectures") |
| col1, col2 = st.columns(2) |
| with col1: |
| st.text_area("Refined Lecture Script", value=st.session_state['refined_script'], height=300) |
| with col2: |
| st.text_area("Scriptified Lecture Script", value=st.session_state['scriptified_script'], height=300) |
|
|
| |
| |
| |
| if "transitions_feedback" in st.session_state: |
| st.subheader("Agent Feedback") |
| st.markdown("**Transitions Feedback:**") |
| st.text_area("", value=st.session_state.get('transitions_feedback', ''), height=150) |
| st.markdown("**Errors Feedback:**") |
| st.text_area("", value=st.session_state.get('errors_feedback', ''), height=150) |
| st.markdown("**Step Organization Feedback:**") |
| st.text_area("", value=st.session_state.get('steps_feedback', ''), height=150) |
|
|