Tkinter库的学习记录06-变量类别

6、变量类别

6-1 变量类别的基本概念

有些widget控件在执行时会更改内容,例如,文本框(Entry)、选项按钮(Radio button)等。有些我们可以更改他们的内容,例如,标签Label等。如果想要更改它们的内容可以使用这些控件的参数,例如,textvariable、variable,onvalue等。

不过要将Widget控件的参数以变量方式处理时,需要借助tkinter模块内的变量类别(Variable Classes),这个类别有4个子类别,每一个类别其实是一个数据类型的构造方法,我们可以通过这4个子类别的数据类型将它们与Widget控件的相关参数结合。

python 复制代码
x = IntVar()        # 整形变量,默认是0
x = DoubleVar()     # 浮点型变量,默认是0.0
x = StringVar()     # 字符串变量,默认是""
x = BooleanVar()    # 布尔型变量,True是1,False是0

6-2 get()与set()

可以使用get()方法取得变量内容,使用set()方法设置变量内容。

下面程序实例,set()方法的应用。这个程序在执行时若单击Hit按钮可以显示"I like tkinter"字符串

,如果已经显示字符串则改成不显示字符串。这个程序第17行是将标签内容设为变量x,第8行是设置显示标签时的标签内容,第11行则是将标签内容设为空字符串以不显示标签内容。

python 复制代码
from tkinter import *

def btn_hit():
    global msg_on
    if msg_on == False:
        msg_on = True
        x.set("I lie tkinter")
    else:
        msg_on = False
        x.set("")

root = Tk()
root.title("ch6_1")

msg_on = False
x = StringVar()

label = Label(root, textvariable=x, 
              fg="blue", bg="lightyellow", 
              font="Verdana 20 bold", 
              width=25, height=2)
label.pack()
btn = Button(root, text="Click Me", command=btn_hit)
btn.pack()

root.mainloop()

运行结果

在上述实例中利用布尔值msg_on变量判断是否要显示"I lkie tkinter"字符串,如果msg_on是False表示没有显示"I lkie tkinter"字符串,如果msg_on是True表示目前有显示"I lkie tkinter"字符串。当单击Click Me按钮时,会更改msg_on状态,可参考第7行和第10行。同时也由set()方法更改label对象的参数textariable的内容,第8行设置显示"I lkie tkinter"字符串,第11行设置不显示"I lkie tkinter"字符串。

上述程序尽管可以运行,可是并没有使用本节中另一个get方法(),这个方法可以取得Widget控件某参数的变量内容,我们将时殷弘下列程序进行改良。

下面程序重新设计上面程序,取消布尔值msg_on变量,我们可以直接由get()方法获得目前Widget控件参数内容,然后由此内容判断是否显示"I lkie tkinter"字符串。判断方式是如果目前是空字符串zhi'xi则显示"I lkie tkinter"字符串,如果不是空字符串,则改成显示空字符串。

python 复制代码
from tkinter import *

def btn_hit():
    if x.get() == "":
        x.set("I lie tkinter")
    else:
        x.set("")

root = Tk()
root.title("ch6_1")

x = StringVar()

label = Label(root, textvariable=x, 
              fg="blue", bg="lightyellow", 
              font="Verdana 20 bold", 
              width=25, height=2)
label.pack()
btn = Button(root, text="Click Me", command=btn_hit)
btn.pack()

root.mainloop()

执行结果与上面代码一致。

6-3 追踪trace()使用模式w

了解6-2节的变量设置后,我们可以利用变量设置追踪Widget控件,当其内容更改时,让程序执行callback函数。

下面程序设计当Widget控件Entry内容改变时在Python Shell窗口中输出"Entry content changed!"。

python 复制代码
from tkinter import *

def callback(*args):
    print("data chnaged: ", x.get())

root = Tk()
root.title("ch6_3")

x = StringVar()
entry = Entry(root, textvariable=x)
entry.pack(padx=10, pady=5)
x.trace("w", callback)  # 若是有更改执行callback

root.mainloop()

运行结果

在看到上述窗口输出时,也可以在Python Shell窗口中看到下列输出。

上面程序的重点是

python 复制代码
x.trace("w", callback)  # w其实是write的缩写

第一个参数是模式,w代表当有执行写入时,就自动去执行callback函数。也可以自行取函数名称,这个动作称为变动追踪。我们可以通过x变量类别追踪Widget控件内容的改变时执行特定动作,本实例是在Python Shell窗口中输出Entry的内容。上述程序的另一个重点,内容如下:

python 复制代码
def callback(*args):

后续将说明上述"*args"参数的含义。

下面程序扩充上述实例,同时在Entry控件下方建立Label控件,当在Entry中有输入时,同时在下方的Label控件中显示。

python 复制代码
from tkinter import *

def callback(*args):
    xL.set(xE.get())
    print("data chnaged: ", xE.get())

root = Tk()
root.title("ch6_3")

xE = StringVar()
entry = Entry(root, textvariable=xE)
entry.pack(padx=10, pady=5)
xE.trace("w", callback)  # 若是有更改执行callback

xL = StringVar()
label = Label(root, textvariable=xL)
xL.set("同步显示")
label.pack(padx=10, pady=5)


root.mainloop()

运行结果

6-4 追踪trace()使用模式r

上一节介绍了当Widget控件内容更改时,执行追踪并执行特定函数,其实我们也可以设计当控件内容被读取时,执行追踪并执行特定函数。

下面程序扩展与修改上面的代码,增加一个"读取"按钮,当在Entry中输入数据时Python Shell窗口不显示数据,但是下方的Label将同步显示。主要功能是如果单击了"读取"按钮,系统将发出数据被读取的警告,同时输出所读取的数据。

python 复制代码
from tkinter import *

def callbackW(*args):
    xL.set(xE.get())

def callbackR(*args):
    print("Warning: 数据被读取!")

def hit():
    print("读取数据: ", xE.get())

root = Tk()
root.title("ch6_5")

xE = StringVar()
entry = Entry(root, textvariable=xE)
entry.pack(padx=10, pady=5)
xE.trace("w", callbackW)  # 若是有更改执行callback
xE.trace("r", callbackR)  # 若是有被读取执行callback

xL = StringVar()
label = Label(root, textvariable=xL)
xL.set("同步显示")
label.pack(padx=10, pady=5)

btn = Button(root, text="读取", command=hit)
btn.pack(pady=5)

root.mainloop()

运行结果

上述程序的重点是

python 复制代码
xE.trace("r", callbackR)  # r其实是read缩写

上述第一个参数是模式,r代表当执行读取时,就会自动会执行callbackR函数。也可以自行取函数名称,这个动作称为读取追踪。我们可以通过xE变量类别追踪Widget控件内容被读取时执行的特定动作,本实例是在Python Shell窗口输出"Warning: 数据被读取!"和Entry中的内容。

6-5 trace()方法调用的callback方法参数

参考上面的内容

python 复制代码
def callback(*args):

其实是传递三个参数,分别是tk变量名称、index索引、mode模式。不过目前有关tk变量名称和index索引部分尚未完成实际支持,至于第三个参数则是可以列出是r或w模式。由于我们所设计的程序并不需要传递参数,所以可以直接用"*args"当作参数内容。

下面程序列出trace()方法所调用callback()方法内的参数。

python 复制代码
from tkinter import *

def callbackW(name, index, mode):
    xL.set(xE.get())
    print("name = %r, index = %r, mode = %r" % (name, index, mode))


root = Tk()
root.title("ch6_5")

xE = StringVar()
entry = Entry(root, textvariable=xE)
entry.pack(padx=10, pady=5)
xE.trace("w", callbackW)  # 若是有更改执行callback

xL = StringVar()
label = Label(root, textvariable=xL)
xL.set("同步显示")
label.pack(padx=10, pady=5)

root.mainloop()

运行结果

6-6 计算器的设计

在4-3节有介绍过简易计算器按钮布局的设计,在5-9节有介绍过eval()方法的用法,本章已经学会了使用变量类别控制标签的输出,其实有这些概念就可以设计简单的计算器了。下面将介绍完整的计算器设计。

下面程序中设计简易的计算器,这个程序中在按钮设计时大量使用Lambda,主要是因为数字按钮与算术表达式按钮使用相同的函数,只是传递的参数不一样,所以用Lambda可以简化设计。

python 复制代码
from tkinter import *

def calculate():
    result = eval(equ.get())
    equ.set(equ.get() + "=\n" + str(result))

def show(buttonString):
    content = equ.get()
    if content == "0":
        content = ""
    equ.set(content + buttonString)

def backspace():                         # 删除最后一个字符
    equ.set(equ.get()[:-1])

def clear():                             # 清除显示区,重置为0
    equ.set("0")

root = Tk()
root.title("计算器")

equ = StringVar()
equ.set("0")                            # 默认显示0

# 设计显示区
label = Label(root, width=25, height=2, relief="raised", anchor=SE, 
              textvariable=equ)
label.grid(row=0, column=0, columnspan=4, padx=5, pady=5)

# 清除显示区按钮
clearButton = Button(root, text="C", fg="blue", width=5, command=clear)
clearButton.grid(row=1, column=0)
# 以下是rowl的其它按钮
Button(root, text="DEL", width=5, command=backspace).grid(row=1, column=1)
Button(root, text="%", width=5, command=lambda:show("%")).grid(row=1, column=2)
Button(root, text="/", width=5, command=lambda:show("/")).grid(row=1, column=3)
# 以下是row2的其它按钮
Button(root, text="7", width=5, command=lambda:show("7")).grid(row=2, column=0)
Button(root, text="8", width=5, command=lambda:show("8")).grid(row=2, column=1)
Button(root, text="9", width=5, command=lambda:show("9")).grid(row=2, column=2)
Button(root, text="*", width=5, command=lambda:show("*")).grid(row=2, column=3)
# 以下是row3的其它按钮
Button(root, text="4", width=5, command=lambda:show("4")).grid(row=3, column=0)
Button(root, text="5", width=5, command=lambda:show("5")).grid(row=3, column=1)
Button(root, text="6", width=5, command=lambda:show("6")).grid(row=3, column=2)
Button(root, text="-", width=5, command=lambda:show("-")).grid(row=3, column=3)
# 以下是row4的其它按钮
Button(root, text="1", width=5, command=lambda:show("1")).grid(row=4, column=0)
Button(root, text="2", width=5, command=lambda:show("2")).grid(row=4, column=1)
Button(root, text="3", width=5, command=lambda:show("3")).grid(row=4, column=2)
Button(root, text="+", width=5, command=lambda:show("+")).grid(row=4, column=3)
# 以下是row5的其它按钮
Button(root, text="0", width=12, command=lambda:show("0")).grid(row=5, column=0, columnspan=2)
Button(root, text=".", width=5, command=lambda:show(".")).grid(row=5, column=2)
Button(root, text="=", width=5, bg="yellow", command=lambda:calculate()).grid(row=5, column=3)
root.mainloop()

运行结果

相关推荐
笨鸟先飞,勤能补拙2 小时前
AI 赋能网络安全:技术全景、成熟度评估与实战案例
人工智能·python·安全·web安全·网络安全·sqlite·github
长和信泰光伏储能3 小时前
京津冀光伏发电:绿色能源的未来之路
python·能源
浦信仿真大讲堂3 小时前
从重复操作到自动化闭环:如何让 CST 与 Python 真正协同起来
python·自动化·cst·仿真软件·达索软件
Gu Gu Study4 小时前
ScoutLoop开放域深度研究引擎(agent的初步设计想法)
人工智能·python
卷无止境4 小时前
写代码这件事,到底该讲究点什么?
后端·python
卷无止境5 小时前
循环复杂度到底在算什么,Python 代码怎么才能写得让人一看就懂
后端·python
lpfasd1235 小时前
MediaCrawler 项目深度分析
chrome·python·chrome devtools
Dxy12393102165 小时前
Python项目打包成EXE完整教程(PyInstaller实战避坑)
开发语言·python
bamb006 小时前
一个项目带你入门AI应用开发01
python
0566466 小时前
Python康复训练——常用标准库
开发语言·python·学习