随机密码生成器

一个简单的随机密码生成器,采用了tkinter来完成GUI设计

from tkinter import * # 导入tkinter库,用于创建图形用户界面(GUI)
# tkinter是Python的标准GUI库,提供了创建窗口、按钮、标签等控件的功能
import random
import string
import secrets

# 定义生成随机密码的方法,本段代码注释参考Random_Password_Generator_V1_comment.py
def generate_password(length, use_digits, use_lowercase, use_uppercase, use_special):
    characters = ''
    selected_types = []
    password_chars = []

    if use_digits:
        characters += string.digits
        selected_types.append(string.digits)
    if use_lowercase:
        characters += string.ascii_lowercase
        selected_types.append(string.ascii_lowercase)
    if use_uppercase:
        characters += string.ascii_uppercase
        selected_types.append(string.ascii_uppercase)
    if use_special:
        characters += string.punctuation
        selected_types.append(string.punctuation)

    if not characters:
        return "未选择任何字符类型,无法生成密码"

    num_types = len(selected_types)
    if num_types > length:
        return "密码长度太短,无法包含所有选择的字符类型"

    base_count = length // num_types
    remaining = length % num_types

    for i, char_type in enumerate(selected_types):
        count = base_count + (1 if i < remaining else 0)
        password_chars.extend(secrets.choice(char_type) for _ in range(count))

    random.shuffle(password_chars)
    return ''.join(password_chars)

# 定义修改生成密码的回调函数,回调函数是指在某个事件发生时被调用的函数,这里是指当用户点击“生成密码”按钮时被调用的函数
# 这个函数是GUI界面的核心部分,负责处理用户输入和操作并传参调用生成密码的方法
def generate_password_callback():
    try:
        length = int(float(entry.get()))  # 获取用户输入的密码长度,这里的entry变量是一个Entry控件,是tkinter库中用于输入文本的控件
        if length <= 0: # 如果用户输入的密码长度小于等于0,则提示用户输入有效的密码长度
            result_entry.config(state="normal") # 将result_entry控件的状态设置为可编辑
            result_entry.delete(0, END) # 清空result_entry控件中的内容,第一个参数表示从第0个字符开始删除,第二个参数表示删除到最后一个字符
            result_entry.insert(0, "密码位数必须是正整数") # 在result_entry控件中插入提示信息,第一个参数表示从第0个字符开始插入,第二个参数表示插入的内容
            result_entry.config(state="readonly") # 将result_entry控件的状态设置为只读,防止用户编辑
            return

        # 获取用户选择的参数
        use_digits = use_digits_var.get() == 1 # 获取use_digits_var变量的值,如果值为1,则表示用户选择了数字,use_digits被赋值为True
        # 这里的use_digits_var是一个IntVar对象,是tkinter库中用于存储整数值的变量,主要用于存储用户选择的选项的值
        use_lowercase = use_lowercase_var.get() == 1
        use_uppercase = use_uppercase_var.get() == 1
        use_special = use_special_var.get() == 1

        # 调用密码生成方法
        password = generate_password(length, use_digits, use_lowercase, use_uppercase, use_special)
        result_entry.config(state="normal")
        result_entry.delete(0, END)
        result_entry.insert(0, password)
        result_entry.config(state="readonly")
    except ValueError: # 如果用户输入的内容无法转换为整数,则提示用户输入有效的密码长度
        result_entry.config(state="normal")
        result_entry.delete(0, END)
        result_entry.insert(0, "请输入有效的密码位数")
        result_entry.config(state="readonly")

# 定义复制到剪贴板的方法
def copy_to_clipboard():
    root.clipboard_clear() # root是tkinter库中创建的主窗口对象,调用clipboard_clear()方法清空剪贴板中的内容,以便后续复制新的内容
    root.clipboard_append(result_entry.get()) # 将result_entry控件中的内容复制到剪贴板中,调用clipboard_append()方法将内容添加到剪贴板中
    root.update()  # 强制更新Tkinter主窗口及其所有子控件的状态及显示内容,确保剪贴板的内容立即生效并可用

    # 显示提示信息
    copy_label.config(text="密码已复制!") # 设置copy_label控件的文本为“密码已复制!”
    root.after(2000, lambda: copy_label.config(text=""))  
    # 2秒后清除提示信息,after()方法第一个参数表示延迟的时间(单位为毫秒),第二个参数表示要执行的函数,这里使用lambda表达式定义了一个匿名函数,用于清除提示信息

# 创建主窗口
root = Tk() # 创建一个Tk对象,表示主窗口,Tk()是tkinter库中创建主窗口的函数,root是主窗口的变量名
root.title("随机密码生成器") # 设置主窗口的标题
root.geometry("500x500") # 设置主窗口的大小,参数格式为“宽x高”,这里设置为500x500像素
root.resizable(False, False) # 设置主窗口不可调整大小,参数格式为“宽是否可调整,高是否可调整”,这里设置为False表示不可调整大小

# 创建一个 Frame,用于整体布局
main_frame = Frame(root) # Frame是tkinter库中用于创建框架的类,Frame对象是一个可以包含其他控件的容器,这里创建了一个Frame对象,作为主窗口的容器
main_frame.pack(pady=20) # 将main_frame控件放置在主窗口中,pack()方法用于将控件放置在主窗口中,pady参数表示main_frame控件和主窗口的上下间距为20像素

# 第一行:输入密码位数
label = Label(main_frame, text="请输入你需要的密码位数:", font=("Arial", 12))
# Label是tkinter库中用于创建标签的类,Label对象是一个用于显示文本或图像的控件,这里创建了一个Label对象,作为输入密码位数的提示信息
# 参数text表示标签的文本内容,font参数表示标签的字体和大小,这里设置为Arial字体,大小为12号
label.grid(row=0, column=0, padx=10, pady=10, sticky=W)
# 将label控件放置在main_frame中,grid()方法用于将控件放置在网格布局中
# row和column参数表示控件所在的行和列,padx和pady参数表示左右和上下间距,sticky参数表示控件在单元格中的对齐方式,这里设置为左对齐

entry = Entry(main_frame, font=("Arial", 12))
# Entry是tkinter库中用于创建输入框的类,Entry对象是一个用于输入单行文本的控件,这里创建了一个Entry对象,作为输入密码位数的输入框
entry.grid(row=0, column=1, padx=10, pady=10)
# 将entry控件放置在main_frame中,grid()方法用于将控件放置在网格布局中,padx和pady参数表示左右和上下间距

# 第二行:是否需要数字
digits_label = Label(main_frame, text="是否需要数字:", font=("Arial", 12))
digits_label.grid(row=1, column=0, padx=10, pady=10, sticky=W) 
# 这里的sticky=W表示控件在单元格中的对齐方式为左对齐,N表示上对齐,E表示右对齐,S表示下对齐,W表示左对齐

# IntVar()是tkinter库中用于存储整数值的变量,主要用于存储用户选择的选项的值
use_digits_var = IntVar(value=1)  # 初始化use_digits_var,默认值设置为 1(是)

# 创建一个 Frame 用于包含“是”和“否”按钮
lowercase_buttons_frame = Frame(main_frame) # 再创建一个Frame对象,作为“是”和“否”按钮的容器,Frame(main_frame)表示该Frame对象是main_frame的子控件
lowercase_buttons_frame.grid(row=1, column=1, padx=5, pady=5, sticky=W) # 将lowercase_buttons_frame控件用grid()方法用于将控件放置在网格布局中

# Radiobutton是tkinter库中用于创建单选按钮的类,Radiobutton对象是一个用于选择单个选项的控件,这里创建了两个Radiobutton对象,作为“是”和“否”按钮
# Radiobutton第一个参数是父容器,第二个参数是按钮的文本,第三个参数是与按钮关联的变量,第四个参数是按钮的值,第五个参数是字体设置
yes_lowercase_button = Radiobutton(lowercase_buttons_frame, text="是", variable=use_digits_var, value=1, font=("Arial", 12))
yes_lowercase_button.pack(side=LEFT, padx=30) # 将yes_lowercase_button控件放置在lowercase_buttons_frame中,pack()方法用于将控件放置在容器中
# side参数表示控件在容器中的位置,这里设置为左对齐,padx参数表示左右间距

no_lowercase_button = Radiobutton(lowercase_buttons_frame, text="否", variable=use_digits_var, value=0, font=("Arial", 12))
no_lowercase_button.pack(side=LEFT, padx=20)

# 第二行:是否需要小写字母
lowercase_label = Label(main_frame, text="是否需要小写字母:", font=("Arial", 12))
lowercase_label.grid(row=2, column=0, padx=10, pady=10, sticky=W)

use_lowercase_var = IntVar(value=1)  # 默认值设置为 1(是)

# 创建一个 Frame 用于包含“是”和“否”按钮
lowercase_buttons_frame = Frame(main_frame)
lowercase_buttons_frame.grid(row=2, column=1, padx=5, pady=5, sticky=W)

yes_lowercase_button = Radiobutton(lowercase_buttons_frame, text="是", variable=use_lowercase_var, value=1, font=("Arial", 12))
yes_lowercase_button.pack(side=LEFT, padx=30)

no_lowercase_button = Radiobutton(lowercase_buttons_frame, text="否", variable=use_lowercase_var, value=0, font=("Arial", 12))
no_lowercase_button.pack(side=LEFT, padx=20)

# 第三行:是否需要大写字母
uppercase_label = Label(main_frame, text="是否需要大写字母:", font=("Arial", 12))
uppercase_label.grid(row=3, column=0, padx=10, pady=10, sticky=W)

use_uppercase_var = IntVar(value=1)  # 默认值设置为 1(是)

# 创建一个 Frame 用于包含“是”和“否”按钮
uppercase_buttons_frame = Frame(main_frame)
uppercase_buttons_frame.grid(row=3, column=1, padx=5, pady=5, sticky=W)

yes_uppercase_button = Radiobutton(uppercase_buttons_frame, text="是", variable=use_uppercase_var, value=1, font=("Arial", 12))
yes_uppercase_button.pack(side=LEFT, padx=30)

no_uppercase_button = Radiobutton(uppercase_buttons_frame, text="否", variable=use_uppercase_var, value=0, font=("Arial", 12))
no_uppercase_button.pack(side=LEFT, padx=20)

# 第五行:是否需要特殊字符
special_label = Label(main_frame, text="是否需要特殊字符:", font=("Arial", 12))
special_label.grid(row=4, column=0, padx=10, pady=10, sticky=W)

use_special_var = IntVar(value=1)  # 默认值设置为 1(是)

# 创建一个 Frame 用于包含“是”和“否”按钮
special_buttons_frame = Frame(main_frame)
special_buttons_frame.grid(row=4, column=1, padx=5, pady=5, sticky=W)

yes_special_button = Radiobutton(special_buttons_frame, text="是", variable=use_special_var, value=1, font=("Arial", 12))
yes_special_button.pack(side=LEFT, padx=30)

no_special_button = Radiobutton(special_buttons_frame, text="否", variable=use_special_var, value=0, font=("Arial", 12))
no_special_button.pack(side=LEFT, padx=20)

# 第五行:显示结果框
# Entry是tkinter库中用于创建输入框的类,Entry对象是一个用于输入单行文本的控件,这里创建了一个Entry对象,作为显示生成的密码的结果框
# 参数font表示字体和大小,fg表示字体颜色,state表示控件的状态,这里设置为只读状态,width表示控件的宽度
result_entry = Entry(main_frame, font=("Arial", 12), fg="blue", state="readonly", width=45)
result_entry.grid(row=5, column=0, columnspan=2, padx=10, pady=10) # columnspan参数表示控件跨越的列数,这里设置为2,表示跨越2列,padx和pady参数表示左右和上下间距

# 第六行:生成密码按钮和复制密码按钮在同一个Frame中
buttons_frame = Frame(main_frame)
buttons_frame.grid(row=6, column=0, columnspan=2, padx=5, pady=10, sticky=N+S+E+W)
# sticky参数表示控件在单元格中的对齐方式,这里设置为上下左右对齐会使控件拉伸填满整个单元格

# command参数表示按钮被点击时调用的函数,这里设置为generate_password_callback()函数,font参数表示按钮的字体和大小
generate_button = Button(buttons_frame, text="生成密码", command=generate_password_callback, font=("Arial", 12))
generate_button.pack(side=LEFT, padx=60)  # 增加左右间距

copy_button = Button(buttons_frame, text="复制密码", command=copy_to_clipboard, font=("Arial", 12))
copy_button.pack(side=LEFT, padx=60)  # 增加左右间距

# 第七行:显示复制提示
copy_label = Label(main_frame, text="", font=("Arial", 12), fg="green") # fg参数表示字体颜色,这里设置为绿色
copy_label.grid(row=7, column=0, columnspan=2, pady=5)

# 启动主循环
mainloop() # 用于启动事件循环,保持GUI界面运行并响应用户事件,否则窗口会立即关闭

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值