Spaces:
Running
Running
UI modification
Browse files
app.py
CHANGED
@@ -5,7 +5,7 @@ import torch
|
|
5 |
import os
|
6 |
import spaces
|
7 |
|
8 |
-
# --- Initialize the Model Pipeline ---
|
9 |
print("Loading MedGemma model...")
|
10 |
try:
|
11 |
pipe = pipeline(
|
@@ -21,15 +21,14 @@ except Exception as e:
|
|
21 |
model_loaded = False
|
22 |
print(f"Error loading model: {e}")
|
23 |
|
24 |
-
# --- Core CONVERSATIONAL Logic ---
|
25 |
@spaces.GPU()
|
26 |
def handle_conversation_turn(user_input: str, user_image: Image.Image, history: list):
|
27 |
"""
|
28 |
-
Manages a single conversation turn with
|
29 |
"""
|
30 |
if not model_loaded:
|
31 |
history.append((user_input, "Error: The AI model is not loaded."))
|
32 |
-
# *** THE FIX: Return history twice to update both UI and State ***
|
33 |
return history, history, None
|
34 |
|
35 |
try:
|
@@ -71,54 +70,71 @@ def handle_conversation_turn(user_input: str, user_image: Image.Image, history:
|
|
71 |
ai_response = full_text.split("<start_of_turn>model")[-1].strip()
|
72 |
|
73 |
history.append((user_input, ai_response))
|
74 |
-
# *** THE FIX: Return history twice to update both UI and State ***
|
75 |
return history, history, None
|
76 |
|
77 |
except Exception as e:
|
78 |
history.append((user_input, f"An error occurred: {str(e)}"))
|
79 |
print(f"An exception occurred during conversation turn: {type(e).__name__}: {e}")
|
80 |
-
# *** THE FIX: Return history twice to update both UI and State ***
|
81 |
return history, history, None
|
82 |
|
83 |
-
# ---
|
84 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
85 |
# The gr.State object that holds the conversation history.
|
86 |
conversation_history = gr.State([])
|
87 |
|
88 |
-
|
89 |
-
|
90 |
-
|
91 |
-
<p>A conversational AI to help you understand your symptoms, powered by Google's MedGemma</p>
|
92 |
-
</div>
|
93 |
-
""")
|
94 |
-
gr.HTML("""
|
95 |
-
<div style="background-color: #fff3cd; border: 1px solid #ffeaa7; border-radius: 8px; padding: 1rem; margin: 1rem 0; color: #856404;">
|
96 |
-
<strong>⚠️ Medical Disclaimer:</strong> This is not a diagnosis. This AI is for informational purposes and is not a substitute for professional medical advice.
|
97 |
-
</div>
|
98 |
-
""")
|
99 |
|
100 |
-
|
101 |
-
|
102 |
with gr.Row():
|
103 |
-
|
104 |
with gr.Column(scale=4):
|
105 |
user_textbox = gr.Textbox(label="Your Message", placeholder="Describe your primary symptom to begin...", lines=4)
|
106 |
send_button = gr.Button("Send Message", variant="primary")
|
107 |
|
108 |
-
#
|
|
|
|
|
|
|
|
|
|
|
|
|
109 |
send_button.click(
|
110 |
fn=handle_conversation_turn,
|
111 |
-
inputs=[user_textbox,
|
112 |
-
|
113 |
-
outputs=[chatbot_display, conversation_history, image__input]
|
114 |
).then(
|
115 |
lambda: "", outputs=user_textbox
|
116 |
)
|
117 |
|
118 |
-
clear_button = gr.Button("🗑️ Start New Consultation")
|
119 |
clear_button.click(
|
120 |
lambda: ([], [], None, ""),
|
121 |
-
outputs=[chatbot_display, conversation_history,
|
122 |
)
|
123 |
|
124 |
if __name__ == "__main__":
|
|
|
5 |
import os
|
6 |
import spaces
|
7 |
|
8 |
+
# --- Initialize the Model Pipeline (No changes) ---
|
9 |
print("Loading MedGemma model...")
|
10 |
try:
|
11 |
pipe = pipeline(
|
|
|
21 |
model_loaded = False
|
22 |
print(f"Error loading model: {e}")
|
23 |
|
24 |
+
# --- Core CONVERSATIONAL Logic (No changes) ---
|
25 |
@spaces.GPU()
|
26 |
def handle_conversation_turn(user_input: str, user_image: Image.Image, history: list):
|
27 |
"""
|
28 |
+
Manages a single conversation turn with state management.
|
29 |
"""
|
30 |
if not model_loaded:
|
31 |
history.append((user_input, "Error: The AI model is not loaded."))
|
|
|
32 |
return history, history, None
|
33 |
|
34 |
try:
|
|
|
70 |
ai_response = full_text.split("<start_of_turn>model")[-1].strip()
|
71 |
|
72 |
history.append((user_input, ai_response))
|
|
|
73 |
return history, history, None
|
74 |
|
75 |
except Exception as e:
|
76 |
history.append((user_input, f"An error occurred: {str(e)}"))
|
77 |
print(f"An exception occurred during conversation turn: {type(e).__name__}: {e}")
|
|
|
78 |
return history, history, None
|
79 |
|
80 |
+
# --- UI MODIFICATION: Custom CSS for a more compact layout ---
|
81 |
+
css = """
|
82 |
+
.header {
|
83 |
+
text-align: center;
|
84 |
+
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
85 |
+
color: white;
|
86 |
+
padding: 1rem; /* Reduced padding */
|
87 |
+
border-radius: 10px;
|
88 |
+
margin-bottom: 1rem; /* Reduced margin */
|
89 |
+
}
|
90 |
+
.header h1 {
|
91 |
+
font-size: 1.8rem; /* Smaller title font */
|
92 |
+
margin-bottom: 0.2rem;
|
93 |
+
}
|
94 |
+
.warning {
|
95 |
+
background-color: #fff3cd;
|
96 |
+
border: 1px solid #ffeaa7;
|
97 |
+
border-radius: 8px;
|
98 |
+
padding: 0.75rem; /* Reduced padding */
|
99 |
+
margin: 0.5rem 0 1rem 0; /* Reduced margin */
|
100 |
+
color: #856404;
|
101 |
+
}
|
102 |
+
"""
|
103 |
+
|
104 |
+
# --- Gradio Interface with New Compact Layout ---
|
105 |
+
with gr.Blocks(theme=gr.themes.Soft(), title="AI Doctor Consultation", css=css) as demo:
|
106 |
# The gr.State object that holds the conversation history.
|
107 |
conversation_history = gr.State([])
|
108 |
|
109 |
+
# UI MODIFICATION: Using the custom CSS class
|
110 |
+
gr.HTML('<div class="header"><h1>🩺 AI Symptom Consultation</h1><p>A conversational AI to help you understand your symptoms.</p></div>')
|
111 |
+
gr.HTML('<div class="warning"><strong>⚠️ Medical Disclaimer:</strong> This is not a diagnosis. This AI is for informational purposes only.</div>')
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
112 |
|
113 |
+
# UI MODIFICATION: Input controls are now at the TOP.
|
|
|
114 |
with gr.Row():
|
115 |
+
image_input = gr.Image(label="Upload Symptom Image (Optional)", type="pil", height=150)
|
116 |
with gr.Column(scale=4):
|
117 |
user_textbox = gr.Textbox(label="Your Message", placeholder="Describe your primary symptom to begin...", lines=4)
|
118 |
send_button = gr.Button("Send Message", variant="primary")
|
119 |
|
120 |
+
# UI MODIFICATION: Chatbot output is now at the BOTTOM with reduced height.
|
121 |
+
chatbot_display = gr.Chatbot(height=380, label="Consultation", show_copy_button=True)
|
122 |
+
|
123 |
+
# The clear button is now more prominent.
|
124 |
+
clear_button = gr.Button("🗑️ Start New Consultation")
|
125 |
+
|
126 |
+
# Event handlers remain the same but reference the reordered components.
|
127 |
send_button.click(
|
128 |
fn=handle_conversation_turn,
|
129 |
+
inputs=[user_textbox, image_input, conversation_history],
|
130 |
+
outputs=[chatbot_display, conversation_history, image_input]
|
|
|
131 |
).then(
|
132 |
lambda: "", outputs=user_textbox
|
133 |
)
|
134 |
|
|
|
135 |
clear_button.click(
|
136 |
lambda: ([], [], None, ""),
|
137 |
+
outputs=[chatbot_display, conversation_history, image_input, user_textbox]
|
138 |
)
|
139 |
|
140 |
if __name__ == "__main__":
|