文章目录

  • 事件绑定的基本简介
  • Widget 的 command 参数
  • 事件绑定
  • 鼠标相关的事件参数
  • 鼠标绑定的基本应用
  • 键盘相关的事件参数
  • 键盘绑定的基本应用
  • 可打印的字符
  • 打印字符的基本应用
  • 组合键
  • 组合键的基本应用
  • 窗体事件
  • 窗体事件绑定的基本应用
  • Event
  • Event的基本应用
  • 对于ASCII的说明
  • 取消绑定
  • 一个事件绑定多个事件处理程序
  • Protocols


事件绑定的基本简介

  其实GUI程序是一种事件导向的应用程序设计,事件的来源可能是用户单击鼠标、键盘输入或是Widget 状态改变。tkinter提供一些机制让我们可以针对这些事件做更进一步的处理,这些处理的方式称为事件处理程序

Widget 的 command 参数

例子:复习

import tkinter

def show():
    label.config(text="Click")

def oneVar():
    if varOne.get():
        label.config(text="One!!!")
    else:
        label.config(text="One")

def twoVar():
    if varTwo.get():
        label.config(text="Two!!!")
    else:
        label.config(text="Two")

root = tkinter.Tk()
root.geometry("300x200")

btu = tkinter.Button(root, text="Click", command=show)
btu.pack(anchor=tkinter.W)

varOne = tkinter.BooleanVar()
cbnOne = tkinter.Checkbutton(root, text="One", variable=varOne, command=oneVar)
cbnOne.pack(anchor=tkinter.W)

varTwo = tkinter.BooleanVar()
cbnTwo = tkinter.Checkbutton(root, text="Two", variable=varTwo, command=twoVar)
cbnTwo.pack(anchor=tkinter.W)


label = tkinter.Label(root, bg="lightgreen", fg="red", height=2, width=12, font="Times 16 bold")
label.pack()

root.mainloop()

运行结果:

python3 tk python3 tkinter 按键绑定_gui


我们通过command=show,来设计show函数,这个show函数就是事件处理程序

事件绑定

语法格式如下

widget.bind(event, handler)

参数:

  • widget:事件的来源,可以是root窗口对象,或是任意的Widget控件,例如,功能按钮,选项按钮,复选框等等
  • 第一个参数:evevt,事件的参数,下面具体说明
  • 第二个参数:handler,事件处理程序,也就是根据event来触发的函数

下面我们来看具体参数

鼠标相关的事件参数

鼠标事件

说明

<Button-1>

鼠标左键单击

<Button-2>

鼠标中键单击

<Button-3>

鼠标右键单击

<Button-4>

鼠标滑轮向上滚动(Linux)

<Button-5>

鼠标滑轮向下滚动(Linux)

<B1-Motion>

鼠标左键拖动

<B2-Motion>

鼠标中键拖动

<B3-Motion>

鼠标右键拖动

<ButtonRelease-1>

鼠标左键释放

<ButtonRelease-2>

鼠标中键释放

<ButtonRelease-3>

鼠标右键释放

<Double-Button-1>

鼠标左键双击

<Double-Button-2>

鼠标中键双击

<Double-Button-3>

鼠标右键双击

<Enter>

鼠标指针进入控件

<Leave>

鼠标指针离开控件

  上述的参数,执行后鼠标光标相对控件的位置会被存入事件对象的x和y变量中,所以这就是为什么我们在handler函数中要加入event形参,这个是必须要传的

注:

<1> = <Button-1> =<ButtonPress-1>
<2> = <Button-2> = <ButtonPress-2>
<3> = <Button-3> =<ButtonPress-3>

这是通用的,<>不能省略

绑定的方式

button.bind("<Button-1>", handler)
鼠标绑定的基本应用

例子:鼠标移动,右下方看到鼠标目前的坐标

import tkinter

def moving(event):
    # .x_root, .y_root是相对于整个屏幕
    # 获取x轴坐标(相对于窗口)
    x = event.x
    # 获取y轴坐标(相对于窗口)
    y = event.y
    textvar = "坐标 : x:%r  y:%r" % (x, y)
    var.set(textvar)

root = tkinter.Tk()
root.geometry("300x200")
x, y = 0, 0
var = tkinter.StringVar()
text = "坐标 : x:%r  y:%r" % (x, y)
var.set(text)

label = tkinter.Label(root, textvariable=var)
label.pack(anchor=tkinter.S, side=tkinter.RIGHT, padx=10, pady=10)

# 事件是鼠标移动,执行moving函数
root.bind("<Motion>", moving)

root.mainloop()

运行结果:

python3 tk python3 tkinter 按键绑定_protocols_02


moving(event)中的event是可以自定义的,但是不能没有

键盘相关的事件参数

键盘事件

说明

<Return>

回车

<Cancel>

Break键

<BackSpace>

BackSpace键

<Tab>

Tab键

<Shift_L>

左Shift键

<Alt_L>

左Alt键

<Control_L>

左Control键

<Shift_R>

右Shift键

<Alt_R>

右Alt键

<Control_R>

右Control键

<Pause>

Pause键

<Caps_Lock>

Caps_Lock键

<Escape>

Escapel键,俗称Esc

<Prior>

PageUp键

<Next>

PageDown键

<End>

End键

<Home>

Home键

<Left>

左箭头

<Up>

上箭头

<Right>

右箭头

<Down>

下箭头

<Print>

Print Screen

<Insert>

Insert键

<Delete>

Delete键

<F1>

F1键

<F2>

F2键

<F3>

F3键

<F4>

F4键

<F5>

F5键

<F6>

F6键

<F7>

F7键

<F8>

F8键

<F9>

F9键

<F10>

F10键

<F11>

F11键

<F12>

F12键

<Num_Lock>

Num_Lock键

<Scroll_Lock>

Scroll_Lock键

<plus>

小键盘上的 + 键

<minus>

小键盘上的 - 键

<asterisk>

小键盘上的 * 键

<slash>

小键盘上的 / 键

<key>

任意键

注:

<key> = <KeyPress> = <KeyRelease>
键盘绑定的基本应用

例子:当我们按下Tab时,tkinter做出响应

import tkinter

def tab(event):
	# keysym 键盘事件对应的字符串
    print(f"按下了{event.keysym}键")

root = tkinter.Tk()
root.geometry("100x80")
root.bind("<Tab>", tab)

root.mainloop()

运行结果:

python3 tk python3 tkinter 按键绑定_protocols_03

可打印的字符

字符

说明

<a>

字母a

<b>

字母b

此处省略剩下的24个字母

此处省略剩下的24个字母

<1>

数字1

<2>

数字2

此处省略剩下的8个数字

此处省略剩下的8个数字

<A>

按键shift+a或者字母大写A

<B>

按键shift+b或者字母大写B

此处省略剩下的24个大写字母

此处省略剩下的24个写字母

注:

<a> = <Key-a> = <KeyPress-a> = <KeyRelease-a>
打印字符的基本应用

例子:当我们按下a时,tkinter做出响应

import tkinter

def tab(event):
    print(f"按下了{event.keysym}键")

root = tkinter.Tk()
root.geometry("100x80")
root.bind("<a>", tab)

root.mainloop()

运行结果:

python3 tk python3 tkinter 按键绑定_protocols_04

组合键

组合键

说明

<Shift-Home>

Shift+Home

<Alt-Home>

Alt+Home

<Control-Home>

Ctrl+Home

<Control-A>

Ctrl+shift+a

注:

组合键不止这些,可以自由组合

组合键的基本应用

例子:当我们按下Alt+Home时,tkinter做出响应

import tkinter

def tab(event):
    print(f"按下了home键")

root = tkinter.Tk()
root.geometry("100x80")
root.bind("<Alt-Home>", tab)

root.mainloop()

运行结果:

python3 tk python3 tkinter 按键绑定_gui_05

窗体事件

窗体事件

说明

<Configure>

改变大小或位置

<Visibility>

当组件变为可视状态时触发

<Unmap>

当组件由显示状态变为隐藏状态时触发

<Map>

当组件由隐藏状态变为显示状态时触发

<Expose>

当组件从原本被其他组件遮盖的状态中暴漏出来时触发

<FocusIn>

组件获得焦点时触发

<FocusOut>

组件失去焦点时触发

<Circulate>

当窗体由于系统协议要求在堆栈中置顶或压底时触发

<Colormap>

当窗体的颜色或外貌改变时触发,Tk中忽略此细则

<Property>

当窗体的属性被删除或改变时触发,属于TK的核心

<Destroy>

当组件被销毁时触发

<Activate>

与组件选项中的state项有关,表示组件由不可用变为可用时触发

<Deactiavte>

与组件选项中的state项有关,表示组件由可用变为不可用时候触发

窗体事件绑定的基本应用

例子:获得焦点与失去焦点,由Tab键进行切换

import tkinter

def a(event):
    label.config(text="获取焦点")

def b(event):
    label.config(text="失去焦点")

root = tkinter.Tk()
root.geometry("300x200")

btu = tkinter.Button(root, text="Click")
btu.pack(anchor=tkinter.W)
btu.bind("<FocusIn>", a)
btu.bind("<FocusOut>", b)

btu1 = tkinter.Button(root, text="Other")
btu1.pack(anchor=tkinter.W)


label = tkinter.Label(root, bg="lightgreen", fg="red", height=2, width=12, font="Times 16 bold")
label.pack()

root.mainloop()

运行结果:

python3 tk python3 tkinter 按键绑定_事件绑定_06


例子:组件由隐藏状态变为显示状态,显示状态变为隐藏状态

from tkinter import *

def show(event):
    b2.config(bg="lightyellow")
    # SystemButtonFace 默认的颜色,就是那个灰色
    b1.config(bg="SystemButtonFace")

def Unshow(event):
    b1.config(bg="lightblue")
    b2.config(bg="SystemButtonFace")

root = Tk()

l1 = Label(root, text='pack_forget')
b3 = Button(root, text='按钮')
b3.bind("<Unmap>", Unshow)
b3.bind("<Map>", show)

# pack_forget 不显示
b1 = Button(root, text='隐藏', command=b3.pack_forget)
b2 = Button(root, text='显示', command=b3.pack)

l1.pack(fill=X)
b1.pack(fill=X)
b2.pack(fill=X)
b3.pack()

root.mainloop()

运行结果:

python3 tk python3 tkinter 按键绑定_gui_07

Event

Event

说明

widget

事件被触发的控件

.x, .y

鼠标距离窗体左上角的位置(坐标)

.x_root, .y_root

鼠标距离屏幕左上角的位置(坐标)

.char

键盘事件对应的字符代码

.keysym

键盘事件对应的字符串

.keycode

键盘事件对应的按键码

.num

鼠标事件对应的按键码

.width, .height

控件的新大小

.type

事件类型

Event的基本应用

例子:键盘输入,tkinter响应字符串和按键码(ASCII)

import tkinter

def show(event):
    print(f"{event.keysym}对应的ASCII码:{event.keycode}")

win = tkinter.Tk()
win.geometry("150x100")
win.bind("<Key>", show)

win.mainloop()

运行结果:

python3 tk python3 tkinter 按键绑定_gui_08

对于ASCII的说明

  每套键盘可能对应的ASCII都不同,所以在这里我并没有写明每个字母、字符、数字的ASCII值,即使写了可能也与大家的ASCII值不同,怎样得知自己键盘的ASCII值呢?

  上述的方法获取是最好验证的,请参照Event的基本应用中的例子

取消绑定

取消绑定xx的方法如下:

# <xxx>是绑定方式
xx.unbind("<xxx>")

例子

import tkinter

def show(event):
    label.config(text="ForPython!")

def choose(x):
    if var.get():
        x.bind("<Button-1>", show)
    else:
        label.config(text="")
        x.unbind("<Button-1>")

root = tkinter.Tk()
root.geometry("300x200")

btu = tkinter.Button(root, text="Click")
btu.pack(anchor=tkinter.W)

var = tkinter.BooleanVar()
cbut = tkinter.Checkbutton(root, text="bind/unbind", variable=var, command=lambda: choose(btu))
cbut.pack(anchor=tkinter.W)


label = tkinter.Label(root, bg="lightgreen", fg="red", height=2, width=12, font="Times 16 bold")
label.pack()

root.mainloop()

运行结果:

python3 tk python3 tkinter 按键绑定_python3 tk_09

一个事件绑定多个事件处理程序

  使用bind()方法可以绑定一个事件处理程序,tkinter也允许我们执行一个事件绑定多个事件处理程序,同样使用bind()方法,但是新增加的时间处理程序需要在bind()方法内增加参数add = "+"

例子

import tkinter


def show():
    print("???")


def shower(event):
    print("!!!")


root = tkinter.Tk()
button = tkinter.Button(root, text="Click", command=show)
button.pack()
button.bind("<1>", shower, add="+")

root.mainloop()

python3 tk python3 tkinter 按键绑定_事件绑定_10

程序会先执行bind()绑定的程序,然后再执行Button()command指定的程序

Protocols

Protocols 可以翻译为通信协议,在tkinter内可以解释为窗口管理程序(Windows Manager)与应用程序(Application)之间的通信协议。tkinter也支持使用绑定概念更改此通信协议

例子:退出程序询问是否要退出

import tkinter
from tkinter import messagebox


def show():
    res = messagebox.askokcancel("提示", "请问您确定要退出吗?")
    if res:
        root.destroy()
    else:
        return


root = tkinter.Tk()
root.protocol("WM_DELETE_WINDOW", show)

root.mainloop()

运行结果:

python3 tk python3 tkinter 按键绑定_事件绑定_11

谢谢观看,笔者会持续更新,如有错误或者建议,请私信我