import tkinter as tk
from tkinter import ttk, filedialog, messagebox
from PIL import Image, ImageDraw, ImageFont, ImageTk
import os

# 主程序类


class StudentIDCardGenerator:
    def __init__(self, root):
        self.root = root
        self.root.title("学生证生成器")
        self.root.geometry("500x450")
        self.root.resizable(False, False)

        # 变量存储
        self.name = tk.StringVar()
        self.student_id = tk.StringVar()
        self.grade = tk.StringVar()
        self.major = tk.StringVar()
        self.photo_path = ""  # 照片路径

        # 创建界面
        self.create_widgets()

    def create_widgets(self):
        # 标题标签
        title_label = ttk.Label(self.root, text="学生证信息填写",
                                font=("微软雅黑", 16, "bold"))
        title_label.pack(pady=10)

        # 表单框架
        form_frame = ttk.Frame(self.root)
        form_frame.pack(pady=10, fill=tk.X, padx=30)

        # 姓名
        ttk.Label(form_frame, text="姓名：", font=("微软雅黑", 12)).grid(
            row=0, column=0, sticky=tk.W, pady=8)
        ttk.Entry(form_frame, textvariable=self.name, font=(
            "微软雅黑", 12), width=25).grid(row=0, column=1, pady=8)

        # 学号
        ttk.Label(form_frame, text="学号：", font=("微软雅黑", 12)).grid(
            row=1, column=0, sticky=tk.W, pady=8)
        ttk.Entry(form_frame, textvariable=self.student_id, font=(
            "微软雅黑", 12), width=25).grid(row=1, column=1, pady=8)

        # 班级
        ttk.Label(form_frame, text="班级：", font=("微软雅黑", 12)).grid(
            row=2, column=0, sticky=tk.W, pady=8)
        ttk.Entry(form_frame, textvariable=self.grade, font=(
            "微软雅黑", 12), width=25).grid(row=2, column=1, pady=8)

        # 专业
        ttk.Label(form_frame, text="专业：", font=("微软雅黑", 12)).grid(
            row=3, column=0, sticky=tk.W, pady=8)
        ttk.Entry(form_frame, textvariable=self.major, font=(
            "微软雅黑", 12), width=25).grid(row=3, column=1, pady=8)

        # 照片选择区域
        photo_frame = ttk.Frame(self.root)
        photo_frame.pack(pady=10, fill=tk.X, padx=30)

        self.photo_btn = ttk.Button(
            photo_frame, text="选择证件照片", command=self.select_photo)
        self.photo_btn.grid(row=0, column=0, padx=5)

        self.photo_status = ttk.Label(
            photo_frame, text="未选择照片", font=("微软雅黑", 10), foreground="red")
        self.photo_status.grid(row=0, column=1, padx=5)

        # 预览&生成按钮区域
        btn_frame = ttk.Frame(self.root)
        btn_frame.pack(pady=20)

        ttk.Button(btn_frame, text="生成学生证", command=self.generate_id_card,
                   width=15).grid(row=0, column=0, padx=10)
        ttk.Button(btn_frame, text="清空信息", command=self.clear_info,
                   width=15).grid(row=0, column=1, padx=10)

        # 状态提示
        self.status_label = ttk.Label(
            self.root, text="", font=("微软雅黑", 11), foreground="green")
        self.status_label.pack(pady=5)

    # 选择照片
    def select_photo(self):
        file_path = filedialog.askopenfilename(
            title="选择证件照",
            filetypes=[("图片文件", "*.jpg *.jpeg *.png *.bmp")]
        )
        if file_path:
            self.photo_path = file_path
            self.photo_status.config(text="已选择照片", foreground="green")

    # 清空信息
    def clear_info(self):
        self.name.set("")
        self.student_id.set("")
        self.grade.set("")
        self.major.set("")
        self.photo_path = ""
        self.photo_status.config(text="未选择照片", foreground="red")
        self.status_label.config(text="")

    # 生成学生证
    def generate_id_card(self):
        # 校验信息
        if not all([self.name.get(), self.student_id.get(), self.grade.get(), self.major.get()]):
            messagebox.showerror("错误", "请填写完整的学生信息！")
            return

        if not self.photo_path:
            messagebox.showerror("错误", "请选择证件照片！")
            return

        try:
            # 学生证基础设置
            card_width, card_height = 400, 250
            card = Image.new("RGB", (card_width, card_height), "white")
            draw = ImageDraw.Draw(card)

            # 绘制蓝色边框
            draw.rectangle([5, 5, card_width-5, card_height-5],
                           outline="#0052cc", width=3)

            # 加载字体（Windows默认字体，跨系统兼容）
            try:
                font_title = ImageFont.truetype("simhei.ttf", 24)
                font_text = ImageFont.truetype("simhei.ttf", 18)
            except:
                font_title = ImageFont.load_default(size=24)
                font_text = ImageFont.load_default(size=18)

            # 绘制标题
            draw.text((card_width//2, 30), "学生证", font=font_title,
                      fill="#0052cc", anchor="mm")

            # 处理并粘贴照片
            photo = Image.open(self.photo_path).convert("RGB")
            photo = photo.resize((100, 130))  # 证件照尺寸
            card.paste(photo, (40, 70))

            # 绘制学生信息
            draw.text((160, 80), f"姓名：{self.name.get()}",
                      font=font_text, fill="black")
            draw.text(
                (160, 115), f"学号：{self.student_id.get()}", font=font_text, fill="black")
            draw.text((160, 150), f"班级：{self.grade.get()}",
                      font=font_text, fill="black")
            draw.text((160, 185), f"专业：{self.major.get()}",
                      font=font_text, fill="black")

            # 保存文件
            save_path = filedialog.asksaveasfilename(
                defaultextension=".png",
                filetypes=[("PNG图片", "*.png"), ("JPG图片", "*.jpg")],
                title="保存学生证"
            )

            if save_path:
                card.save(save_path)
                self.status_label.config(
                    text=f"学生证已保存：{os.path.basename(save_path)}")
                messagebox.showinfo("成功", "学生证生成完成！")

        except Exception as e:
            messagebox.showerror("生成失败", f"错误信息：{str(e)}")


# 运行程序
if __name__ == "__main__":
    root = tk.Tk()
    app = StudentIDCardGenerator(root)
    root.mainloop()
