Spaces:
Sleeping
Sleeping
Update app.py
Browse files
app.py
CHANGED
|
@@ -209,47 +209,104 @@ with gr.Blocks(
|
|
| 209 |
file_status = gr.Markdown("📁 文件状态:未上传", elem_classes="hint")
|
| 210 |
|
| 211 |
# 右侧:聊天区
|
|
|
|
| 212 |
with gr.Column(scale=2, min_width=MIN_WIDTH_RIGHT):
|
| 213 |
with gr.Group(elem_classes="table"):
|
| 214 |
-
#
|
| 215 |
chatbot = gr.Chatbot(
|
| 216 |
height=CHATBOT_HEIGHT,
|
| 217 |
-
type="messages",
|
| 218 |
elem_classes="custom-chatbot",
|
| 219 |
-
avatar_images=("landlord.png", "bot.png")
|
| 220 |
)
|
|
|
|
|
|
|
| 221 |
|
|
|
|
| 222 |
user_input = gr.Textbox(
|
| 223 |
placeholder="例如:设计一个适合3-5人的派对风格扑克游戏(请写清目标人群/时长/创新点)…",
|
| 224 |
show_label=False,
|
| 225 |
max_lines=5,
|
| 226 |
lines=3,
|
| 227 |
-
show_copy_button=True
|
|
|
|
| 228 |
)
|
| 229 |
|
| 230 |
-
#
|
| 231 |
-
|
| 232 |
-
|
| 233 |
-
|
| 234 |
-
|
| 235 |
-
|
| 236 |
-
|
| 237 |
-
|
| 238 |
-
|
| 239 |
-
|
| 240 |
-
"
|
| 241 |
-
|
| 242 |
-
|
| 243 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 244 |
)
|
| 245 |
|
|
|
|
| 246 |
with gr.Row():
|
| 247 |
export_btn = gr.Button("导出对话(Markdown)", variant="secondary")
|
| 248 |
export_file = gr.File(label="点击下载导出文件", interactive=False)
|
| 249 |
|
| 250 |
-
#
|
| 251 |
with gr.Row():
|
| 252 |
-
clear_dialog_btn = gr.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 253 |
|
| 254 |
# ==================== 事件绑定 ====================
|
| 255 |
# 清空缓存按钮
|
|
|
|
| 209 |
file_status = gr.Markdown("📁 文件状态:未上传", elem_classes="hint")
|
| 210 |
|
| 211 |
# 右侧:聊天区
|
| 212 |
+
# 右侧:聊天区(改为手动事件绑定,彻底规避 ChatInterface 的样式/版本差异)
|
| 213 |
with gr.Column(scale=2, min_width=MIN_WIDTH_RIGHT):
|
| 214 |
with gr.Group(elem_classes="table"):
|
| 215 |
+
# 聊天消息采用新格式 messages
|
| 216 |
chatbot = gr.Chatbot(
|
| 217 |
height=CHATBOT_HEIGHT,
|
| 218 |
+
type="messages",
|
| 219 |
elem_classes="custom-chatbot",
|
| 220 |
+
avatar_images=("landlord.png", "bot.png"),
|
| 221 |
)
|
| 222 |
+
# 用一个 State 保存 messages 历史,便于多处复用
|
| 223 |
+
chat_state = gr.State([]) # list[dict]: [{"role":"user","content":...}, {"role":"assistant","content":...}, ...]
|
| 224 |
|
| 225 |
+
# 输入框(支持 Shift+Enter 换行;回车提交我们手动绑定)
|
| 226 |
user_input = gr.Textbox(
|
| 227 |
placeholder="例如:设计一个适合3-5人的派对风格扑克游戏(请写清目标人群/时长/创新点)…",
|
| 228 |
show_label=False,
|
| 229 |
max_lines=5,
|
| 230 |
lines=3,
|
| 231 |
+
show_copy_button=True,
|
| 232 |
+
autofocus=True,
|
| 233 |
)
|
| 234 |
|
| 235 |
+
# 显式“发送”按钮(大按钮)
|
| 236 |
+
with gr.Row():
|
| 237 |
+
send_btn = gr.Button("发送", variant="primary")
|
| 238 |
+
stop_info = gr.Markdown("", visible=False) # 预留:如需做流式/停止提示
|
| 239 |
+
|
| 240 |
+
# —— 提交处理:把 messages 历史交给你的 design_poker_game,返回助手回复并更新 UI ——
|
| 241 |
+
def _messages_to_tuples(history_msgs):
|
| 242 |
+
"""[{role,content}] -> [(user, bot)] 供现有 design_poker_game 使用"""
|
| 243 |
+
pairs, last_user = [], None
|
| 244 |
+
for m in history_msgs or []:
|
| 245 |
+
r, c = m.get("role"), m.get("content", "")
|
| 246 |
+
if r == "user":
|
| 247 |
+
last_user = c
|
| 248 |
+
elif r == "assistant":
|
| 249 |
+
pairs.append((last_user or "", c))
|
| 250 |
+
last_user = None
|
| 251 |
+
return pairs
|
| 252 |
+
|
| 253 |
+
def on_submit(user_text, history_msgs, files, custom_prompt, mode):
|
| 254 |
+
user_text = (user_text or "").strip()
|
| 255 |
+
# 空文本不提交(与 Gradio 5 的默认交互一致)
|
| 256 |
+
if not user_text:
|
| 257 |
+
return gr.update(), gr.update(), history_msgs
|
| 258 |
+
|
| 259 |
+
# 1) 先把用户消息写入 messages(前端立即看到气泡)
|
| 260 |
+
history_msgs = list(history_msgs or [])
|
| 261 |
+
history_msgs.append({"role": "user", "content": user_text})
|
| 262 |
+
|
| 263 |
+
# 2) 调用你的核心函数(传入 tuple 历史以兼容)
|
| 264 |
+
tuples_hist = _messages_to_tuples(history_msgs)
|
| 265 |
+
try:
|
| 266 |
+
bot_reply = design_poker_game(user_text, tuples_hist, files, custom_prompt, mode)
|
| 267 |
+
except Exception as e:
|
| 268 |
+
bot_reply = f"(出错){type(e).__name__}: {e}"
|
| 269 |
+
|
| 270 |
+
# 3) 追加助手回复
|
| 271 |
+
history_msgs.append({"role": "assistant", "content": str(bot_reply)})
|
| 272 |
+
|
| 273 |
+
# 4) 更新 Chatbot 与清空输入框,同时回写 state
|
| 274 |
+
return history_msgs, "", history_msgs
|
| 275 |
+
|
| 276 |
+
# 绑定:回车提交(Enter=提交;Shift+Enter=换行由浏览器原生处理)
|
| 277 |
+
user_input.submit(
|
| 278 |
+
fn=on_submit,
|
| 279 |
+
inputs=[user_input, chat_state, file_uploader, custom_prompt_box, prompt_mode],
|
| 280 |
+
outputs=[chatbot, user_input, chat_state],
|
| 281 |
+
preprocess=True,
|
| 282 |
+
)
|
| 283 |
+
|
| 284 |
+
# 绑定:点击“发送”按钮提交(与回车完全等价)
|
| 285 |
+
send_btn.click(
|
| 286 |
+
fn=on_submit,
|
| 287 |
+
inputs=[user_input, chat_state, file_uploader, custom_prompt_box, prompt_mode],
|
| 288 |
+
outputs=[chatbot, user_input, chat_state],
|
| 289 |
+
preprocess=True,
|
| 290 |
)
|
| 291 |
|
| 292 |
+
# 导出对话(直接读取 Chatbot 的 messages 值)
|
| 293 |
with gr.Row():
|
| 294 |
export_btn = gr.Button("导出对话(Markdown)", variant="secondary")
|
| 295 |
export_file = gr.File(label="点击下载导出文件", interactive=False)
|
| 296 |
|
| 297 |
+
# 清空对话(同时清空 Chatbot + 输入 + state)
|
| 298 |
with gr.Row():
|
| 299 |
+
clear_dialog_btn = gr.Button("清空对话", variant="secondary")
|
| 300 |
+
|
| 301 |
+
def _clear_chat():
|
| 302 |
+
return [], "", []
|
| 303 |
+
|
| 304 |
+
clear_dialog_btn.click(
|
| 305 |
+
fn=_clear_chat,
|
| 306 |
+
inputs=None,
|
| 307 |
+
outputs=[chatbot, user_input, chat_state],
|
| 308 |
+
)
|
| 309 |
+
|
| 310 |
|
| 311 |
# ==================== 事件绑定 ====================
|
| 312 |
# 清空缓存按钮
|