import tkinter as tk
from tkinter import ttk, filedialog, messagebox
from PIL import Image, ImageDraw, ImageFont, ImageTk
import os
import datetime

class StudentIDGenerator:
    def __init__(self, root):
        self.root = root
        self.root.title("学生证件生成器")
        self.root.geometry("600x700")
        self.root.resizable(False, False)
        
        # 存储照片路径
        self.photo_path = None
        
        # 创建界面
        self.create_widgets()
    
    def create_widgets(self):
        # 标题
        title_label = tk.Label(self.root, text="学生证件生成器", 
                              font=("Arial", 16, "bold"))
        title_label.pack(pady=10)
        
        # 基本信息框架
        info_frame = ttk.LabelFrame(self.root, text="学生基本信息", padding=10)
        info_frame.pack(fill="x", padx=20, pady=5)
        
        # 姓名
        ttk.Label(info_frame, text="姓名:").grid(row=0, column=0, sticky="w", pady=2)
        self.name_entry = ttk.Entry(info_frame, width=30)
        self.name_entry.grid(row=0, column=1, padx=10, pady=2)
        
        # 学号
        ttk.Label(info_frame, text="学号:").grid(row=1, column=0, sticky="w", pady=2)
        self.student_id_entry = ttk.Entry(info_frame, width=30)
        self.student_id_entry.grid(row=1, column=1, padx=10, pady=2)
        
        # 专业
        ttk.Label(info_frame, text="专业:").grid(row=2, column=0, sticky="w", pady=2)
        self.major_entry = ttk.Entry(info_frame, width=30)
        self.major_entry.grid(row=2, column=1, padx=10, pady=2)
        
        # 年级
        ttk.Label(info_frame, text="年级:").grid(row=3, column=0, sticky="w", pady=2)
        self.grade_entry = ttk.Entry(info_frame, width=30)
        self.grade_entry.grid(row=3, column=1, padx=10, pady=2)
        
        # 班级
        ttk.Label(info_frame, text="班级:").grid(row=4, column=0, sticky="w", pady=2)
        self.class_entry = ttk.Entry(info_frame, width=30)
        self.class_entry.grid(row=4, column=1, padx=10, pady=2)
        
        # 有效期
        ttk.Label(info_frame, text="有效期:").grid(row=5, column=0, sticky="w", pady=2)
        current_year = datetime.datetime.now().year
        self.valid_entry = ttk.Entry(info_frame, width=30)
        self.valid_entry.insert(0, f"{current_year}-{current_year + 4}")
        self.valid_entry.grid(row=5, column=1, padx=10, pady=2)
        
        # 照片上传
        photo_frame = ttk.LabelFrame(self.root, text="学生照片", padding=10)
        photo_frame.pack(fill="x", padx=20, pady=5)
        
        upload_btn = ttk.Button(photo_frame, text="选择照片", 
                               command=self.upload_photo)
        upload_btn.pack(pady=5)
        
        self.photo_label = ttk.Label(photo_frame, text="未选择照片")
        self.photo_label.pack(pady=5)
        
        # 预览区域
        preview_frame = ttk.LabelFrame(self.root, text="证件预览", padding=10)
        preview_frame.pack(fill="both", expand=True, padx=20, pady=10)
        
        self.preview_canvas = tk.Canvas(preview_frame, width=400, height=250, 
                                       bg="white", relief="solid", bd=1)
        self.preview_canvas.pack(pady=5)
        
        # 生成按钮
        generate_btn = ttk.Button(self.root, text="生成学生证件", 
                                 command=self.generate_id_card, style="Accent.TButton")
        generate_btn.pack(pady=10)
        
        # 添加样式
        style = ttk.Style()
        style.configure("Accent.TButton", font=("Arial", 10, "bold"))
    
    def upload_photo(self):
        file_path = filedialog.askopenfilename(
            title="选择学生照片",
            filetypes=[("Image files", "*.jpg *.jpeg *.png *.bmp")]
        )
        
        if file_path:
            self.photo_path = file_path
            filename = os.path.basename(file_path)
            self.photo_label.config(text=f"已选择: {filename}")
            # 可以在这里添加照片预览功能
    
    def generate_id_card(self):
        # 获取输入信息
        name = self.name_entry.get().strip()
        student_id = self.student_id_entry.get().strip()
        major = self.major_entry.get().strip()
        grade = self.grade_entry.get().strip()
        class_name = self.class_entry.get().strip()
        valid_period = self.valid_entry.get().strip()
        
        # 验证必填字段
        if not all([name, student_id, major, grade, class_name]):
            messagebox.showerror("错误", "请填写所有必填信息！")
            return
        
        try:
            # 创建证件图像
            id_card = self.create_id_card(name, student_id, major, grade, 
                                        class_name, valid_period)
            
            # 保存文件
            save_path = filedialog.asksaveasfilename(
                title="保存学生证件",
                defaultextension=".png",
                filetypes=[("PNG files", "*.png"), ("JPEG files", "*.jpg")]
            )
            
            if save_path:
                id_card.save(save_path)
                messagebox.showinfo("成功", "学生证件生成成功！")
                
                # 显示预览
                self.show_preview(id_card)
                
        except Exception as e:
            messagebox.showerror("错误", f"生成证件时出错: {str(e)}")
    
    def create_id_card(self, name, student_id, major, grade, class_name, valid_period):
        # 创建证件底图
        width, height = 400, 250
        id_card = Image.new('RGB', (width, height), 'white')
        draw = ImageDraw.Draw(id_card)
        
        try:
            # 尝试使用系统字体，如果失败则使用默认字体
            font_large = ImageFont.truetype("arial.ttf", 24)
            font_medium = ImageFont.truetype("arial.ttf", 16)
            font_small = ImageFont.truetype("arial.ttf", 12)
        except:
            font_large = ImageFont.load_default()
            font_medium = ImageFont.load_default()
            font_small = ImageFont.load_default()
        
        # 绘制边框
        draw.rectangle([5, 5, width-5, height-5], outline="black", width=2)
        
        # 绘制标题
        draw.text((width//2 - 60, 15), "学生证", fill="black", font=font_large)
        
        # 左侧信息区域
        info_x = 20
        info_y = 60
        
        info_text = [
            f"姓名: {name}",
            f"学号: {student_id}",
            f"专业: {major}",
            f"年级: {grade}",
            f"班级: {class_name}",
            f"有效期: {valid_period}"
        ]
        
        for i, text in enumerate(info_text):
            draw.text((info_x, info_y + i*25), text, fill="black", font=font_medium)
        
        # 右侧照片区域
        photo_x = 280
        photo_y = 60
        photo_width = 100
        photo_height = 120
        
        # 绘制照片边框
        draw.rectangle([photo_x, photo_y, photo_x+photo_width, photo_y+photo_height], 
                      outline="black", width=1)
        
        # 如果有照片，添加照片
        if self.photo_path:
            try:
                photo = Image.open(self.photo_path)
                # 调整照片大小
                photo = photo.resize((photo_width, photo_height), Image.Resampling.LANCZOS)
                id_card.paste(photo, (photo_x, photo_y))
            except Exception as e:
                # 如果照片加载失败，在照片区域显示文字
                draw.text((photo_x+10, photo_y+50), "照片", fill="gray", font=font_medium)
        else:
            draw.text((photo_x+10, photo_y+50), "照片", fill="gray", font=font_medium)
        
        # 添加学校名称（可以自定义）
        school_name = "XX大学"
        draw.text((width//2 - len(school_name)*6, height-30), school_name, 
                 fill="black", font=font_small)
        
        return id_card
    
    def show_preview(self, image):
        # 转换为tkinter可用的格式
        preview_image = image.copy()
        preview_image.thumbnail((380, 230))
        photo = ImageTk.PhotoImage(preview_image)
        
        # 清除之前的预览
        self.preview_canvas.delete("all")
        
        # 显示新预览
        self.preview_canvas.create_image(190, 115, image=photo)
        self.preview_canvas.image = photo  # 保持引用

def main():
    root = tk.Tk()
    app = StudentIDGenerator(root)
    root.mainloop()

if __name__ == "__main__":
    main()