diff --git a/.gitignore b/.gitignore index e63ac66..6632892 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,3 @@ -/build/ -/dist/ -client.spec +/yun/build/ +/yun/dist/ +/yun/client.spec diff --git a/yun/client.py b/yun/client.py index a6b6b14..f13eff4 100644 --- a/yun/client.py +++ b/yun/client.py @@ -3,9 +3,8 @@ from tkinter import messagebox, simpledialog import time import requests -API_URL = "http://47.80.30.142:6364" # Flask 接口地址 +API_URL = "http://47.80.30.142:6364/" -# 读取排行榜数据(从 Flask 获取) def load_leaderboard(): try: resp = requests.get(f"{API_URL}/get_board") @@ -17,52 +16,62 @@ def load_leaderboard(): messagebox.showerror("错误", f"无法加载排行榜数据:{e}") return [] -# 获取参赛者姓名 def get_player_name(): name = simpledialog.askstring("参赛者姓名", "请输入您的姓名:") if not name: - messagebox.showwarning("警告", "姓名不能为空,请重新输入。") + messagebox.showwarning("警告", "姓名不能为空") return get_player_name() return name -# 上传成绩并刷新排行榜 -def submit_result(name, error): - try: - # 先下载当前排行榜 - leaderboard = load_leaderboard() +def get_player_message(): + return simpledialog.askstring("祝贺留言", "你太棒了!要留下什么话?") - # 查找或更新当前用户成绩(误差更小的) - found = False +def submit_result(name, error, message=None): + try: + leaderboard = load_leaderboard() + updated = False for entry in leaderboard: if entry["name"] == name: - found = True if abs(error) < entry["error"]: entry["error"] = round(abs(error), 3) + if abs(error) < 0.1 and message: + entry["message"] = message + updated = True break - if not found: - leaderboard.append({"name": name, "error": round(abs(error), 3)}) + if not updated: + entry = {"name": name, "error": round(abs(error), 3)} + if abs(error) < 0.1 and message: + entry["message"] = message + leaderboard.append(entry) - # 按误差升序排序 leaderboard.sort(key=lambda x: x["error"]) - - # 提交新的排行榜到服务器 resp = requests.post(f"{API_URL}/set_board", json=leaderboard) if resp.status_code == 200: update_rank_display(leaderboard) + update_message_display(leaderboard) else: - messagebox.showerror("提交失败", "提交成绩失败,请稍后再试。") + messagebox.showerror("提交失败", "成绩上传失败") except Exception as e: messagebox.showerror("错误", f"提交成绩时出错:{e}") - -# 显示排行榜 def update_rank_display(leaderboard): rank_listbox.delete(0, tk.END) for i, entry in enumerate(leaderboard, 1): - n, e = entry["name"], entry["error"] - rank_listbox.insert(tk.END, f"{i}. {n:<8} 误差: {e:.3f}s") + rank_listbox.insert(tk.END, f"{i}. {entry['name']:<8} 误差: {entry['error']:.3f}s") + +def update_message_display(leaderboard): + messages.clear() + for entry in leaderboard: + if "message" in entry and entry["message"]: + messages.append(f"{entry['name']}:{entry['message']}") + +def scroll_messages(): + if messages: + msg = messages.pop(0) + message_var.set(msg) + messages.append(msg) + root.after(3000, scroll_messages) -# 更新时间函数 def update_time(): if flag: now = time.time() @@ -72,30 +81,13 @@ def update_time(): def show_win_animation(): anim = tk.Toplevel(root) - anim.geometry("320x200") - anim.title("🎉 胜利动画") - anim.configure(bg="#ffffff") - anim.attributes("-topmost", True) + anim.geometry("300x150") + anim.configure(bg="white") + tk.Label(anim, text="🎉 完美掌控时间!", font=("微软雅黑", 18, "bold"), bg="white").pack(expand=True) + anim.after(1500, anim.destroy) - label = tk.Label(anim, text="🎉 完美掌控时间!🎉", font=("微软雅黑", 18, "bold"), bg="#ffffff") - label.pack(expand=True) - - colors = ["#ff6666", "#66cc66", "#3399ff", "#ffcc00", "#cc66ff"] - sizes = [18, 22, 26, 30, 26, 22, 18] - - def animate(i=0): - if i < len(sizes): - label.config(font=("微软雅黑", sizes[i], "bold"), fg=colors[i % len(colors)]) - anim.after(150, animate, i + 1) - else: - anim.destroy() - - animate() - -# 控制开始/停止 def change(): global flag, start_time - if not flag: flag = True start_time = time.time() @@ -105,57 +97,57 @@ def change(): end_time = time.time() timex = end_time - start_time error = timex - 10 - timex_label.config(text=f"✅ 实际时间:{timex:.3f} 秒\n误差:{error:.3f} 秒") name = get_player_name() - submit_result(name, error) - - if abs(error) < 0.01: + message = None + if abs(error) < 0.1: + message = get_player_message() show_win_animation() else: - messagebox.showinfo("结果", "还差一点点,再接再厉吧!") + messagebox.showinfo("结果", "再接再厉!") + submit_result(name, error, message) -# ================================ -# 主窗口 -# ================================ +# ============================ UI ============================ root = tk.Tk() -root.geometry("340x500") +root.geometry("360x550") root.title("10秒挑战") root.configure(bg="#f0faff") -# 标题 -title_label = tk.Label(root, text="🎯 10 秒挑战 🎯", font=("微软雅黑", 18, "bold"), fg="#004466", bg="#f0faff") -title_label.pack(pady=15) +title_label = tk.Label(root, text="🎯 10 秒挑战 🎯", font=("微软雅黑", 18, "bold"), bg="#f0faff", fg="#004466") +title_label.pack(pady=10) -# 排行榜框 rank_frame = tk.Frame(root, bg="#ffffff", bd=2, relief="groove") -rank_frame.pack(pady=10) +rank_frame.pack(pady=5) -rank_title = tk.Label(rank_frame, text="🏆 排行榜(误差越小越靠前)", font=("微软雅黑", 10, "bold"), bg="#ffffff", fg="#333333") -rank_title.pack(pady=(5, 0)) +rank_title = tk.Label(rank_frame, text="🏆 排行榜", font=("微软雅黑", 10, "bold"), bg="#ffffff") +rank_title.pack(pady=5) rank_listbox = tk.Listbox(rank_frame, font=("Courier", 10), height=5, width=35, bg="#f9f9f9") rank_listbox.pack(padx=10, pady=5) -# 初始显示排行榜 -leaderboard = load_leaderboard() -update_rank_display(leaderboard) - -# 时间标签 -timex_label = tk.Label(root, text="点击按钮开始挑战", font=("微软雅黑", 12), bg="#f0faff", fg="#333333") +timex_label = tk.Label(root, text="点击按钮开始挑战", font=("微软雅黑", 12), bg="#f0faff") timex_label.pack(pady=20) -# 按钮 start_button = tk.Button(root, text="🎮 开始 / 停止", font=("微软雅黑", 12, "bold"), bg="#66ccff", fg="white", activebackground="#3399cc", - width=20, height=2, command=change, relief="raised", bd=3) -start_button.pack(pady=30) + width=20, height=2, command=change) +start_button.pack(pady=10) + +# 滚动留言框 +message_var = tk.StringVar() +message_label = tk.Label(root, textvariable=message_var, font=("微软雅黑", 10), fg="#444", bg="#f0faff", wraplength=320, justify="center") +message_label.pack(pady=20) + +# 初始数据加载 +messages = [] +leaderboard = load_leaderboard() +update_rank_display(leaderboard) +update_message_display(leaderboard) +scroll_messages() -# 控制变量 flag = False start_time = 0 -# 启动主循环 root.mainloop() diff --git a/yun/client.spec b/yun/client.spec new file mode 100644 index 0000000..e5bf8f7 --- /dev/null +++ b/yun/client.spec @@ -0,0 +1,39 @@ +# -*- mode: python ; coding: utf-8 -*- + + +a = Analysis( + ['client.py'], + pathex=[], + binaries=[], + datas=[], + hiddenimports=[], + hookspath=[], + hooksconfig={}, + runtime_hooks=[], + excludes=[], + noarchive=False, + optimize=0, +) +pyz = PYZ(a.pure) + +exe = EXE( + pyz, + a.scripts, + a.binaries, + a.datas, + [], + name='client', + debug=False, + bootloader_ignore_signals=False, + strip=False, + upx=True, + upx_exclude=[], + runtime_tmpdir=None, + console=False, + disable_windowed_traceback=False, + argv_emulation=False, + target_arch=None, + codesign_identity=None, + entitlements_file=None, + icon=['icon.ico'], +) diff --git a/yun/server.py b/yun/server.py index ea54567..66bd391 100644 --- a/yun/server.py +++ b/yun/server.py @@ -3,35 +3,32 @@ import json import os app = Flask(__name__) -LEADERBOARD_FILE = "../leaderboard.json" +LEADERBOARD_FILE = "leaderboard.json" -# 加载排行榜数据 +# 加载排行榜 def load_leaderboard(): if os.path.exists(LEADERBOARD_FILE): with open(LEADERBOARD_FILE, "r", encoding="utf-8") as f: return json.load(f) return [] -# 保存排行榜数据 +# 保存排行榜 def save_leaderboard(data): with open(LEADERBOARD_FILE, "w", encoding="utf-8") as f: json.dump(data, f, ensure_ascii=False, indent=2) -# 获取排行榜 @app.route("/get_board", methods=["GET"]) def get_board(): return jsonify(load_leaderboard()) -# 上传排行榜 @app.route("/set_board", methods=["POST"]) def set_board(): try: data = request.json save_leaderboard(data) - return jsonify(data) # 直接返回排行榜 + return jsonify(data) except Exception as e: return jsonify({"status": "error", "message": str(e)}), 400 - if __name__ == "__main__": - app.run(debug=True, port=5000) + app.run(host="0.0.0.0", port=5000)