|
常用GUI框架
wxPython
安裝wxPython
pip install -U wxPython
C:\Users> pip install -U wxPython
Collecting wxPython
Downloading https://files./packages/34/41/e0e109a72966f596a5b93123d94eaabd53509ef6766fa3321b4bfadbbb14/wxPython-4.0.3-cp37-cp37m-win_amd64.whl (22.7MB)
100% |████████████████████████████████| 22.7MB 819kB/s
Collecting PyPubSub (from wxPython)
Downloading https://files./packages/ab/9e/3b50915d3346971aaa49074425788598ee4907e67c097e013f1a862bd45c/Pypubsub-4.0.0-py3-none-any.whl (63kB)
100% |████████████████████████████████| 71kB 1.5MB/s
Requirement already satisfied, skipping upgrade: six in d:\python\lib\site-packages (from wxPython) (1.11.0)
Installing collected packages: PyPubSub, wxPython
Successfully installed PyPubSub-4.0.0 wxPython-4.0.3
wxPython的兩個(gè)基礎(chǔ)對(duì)象,應(yīng)用程序?qū)ο蠛晚敿?jí)窗口:
- 應(yīng)用程序?qū)ο蠊芾碇魇录h(huán),主事件循環(huán)是wxPython程序的動(dòng)力。如果沒有應(yīng)用程序?qū)ο?,wxPython應(yīng)用程序?qū)⒉荒苓\(yùn)行。
- 頂級(jí)窗口通常用于管理最重要的數(shù)據(jù),控制并呈現(xiàn)給用戶。

創(chuàng)建一個(gè)wx.App的子類
- 定義子類wx.App
- 在定義子類中寫一個(gè)OnInit()初始化方法
- 在程序的主要部分創(chuàng)建這個(gè)類的一個(gè)實(shí)例
- 調(diào)用應(yīng)用程序?qū)嵗腗ainLoop方法。這個(gè)方法將程序的控制權(quán)轉(zhuǎn)交給wxPython
import wx # 導(dǎo)入wxPython
class App(wx.App):
def OnInit(self): # 初始化方法
frame = wx.Frame(parent=None, title='第一個(gè)窗口程序') # 創(chuàng)建頂級(jí)窗口
frame.Show() # 顯示窗口
return True # 返回值(返回窗口,在屏幕展示)
if __name__ == '__main__':
app = App() # 實(shí)例化App類
app.MainLoop() # 調(diào)用App類的MainLoop()主循環(huán)方法
執(zhí)行結(jié)果:

直接使用wx.App
通常,如果在系統(tǒng)中只有一個(gè)窗口的話,可以不創(chuàng)建wx.App子類,直接使用wx.App。這個(gè)類提供了一個(gè)最基本的OnInit()初始化方法。
import wx # 導(dǎo)入wxPython
app = wx.App() # 初始化wx.App類
frame = wx.Frame(None, title='第一個(gè)窗口程序') # 定義一個(gè)頂級(jí)窗口
frame.Show() # 顯示窗口
app.MainLoop() # 調(diào)用wx.App類的MainLoop()主循環(huán)方法
執(zhí)行結(jié)果:

使用wx.Frame框架
wx.Frame(parent=None, id=-1, title="", pos=wx.DefaultPosition, size=wx.DefaultSize, style=wx.DEFAULT_DIALOG_STYLE, name="frame")
- parent:框架的父窗口。如果是頂級(jí)窗口,這個(gè)值是None
- id:關(guān)于新窗口的wxPython ID號(hào)。通常設(shè)為-1,讓wxPython自動(dòng)生成一個(gè)新的ID
- title:窗口標(biāo)題
- pos:一個(gè)wx.Point對(duì)象,它指定這個(gè)新窗口的左上角在屏幕中的位置。在圖形用戶界面程序中,通常是(0,0)是顯示器的左上角。這個(gè)默認(rèn)值(-1,-1)將讓系統(tǒng)決定窗口的位置
- size:一個(gè)wx.Python對(duì)象,他指定這個(gè)窗口的初始尺寸,這個(gè)默認(rèn)值(-1,-1)將讓系統(tǒng)決定窗口的初始尺寸
- style:指定窗口的類型的常量。可以使用或運(yùn)算來組合他們。
- name:框架內(nèi)在的名字。可以使用它來尋找這個(gè)窗口
示例代碼:
import wx # 導(dǎo)入wxPython
class MyFrame(wx.Frame):
def __init__(self, parent, id):
wx.Frame.__init__(self, parent, id, title="創(chuàng)建Frame", pos=(100, 100), size=(300, 300))
if __name__ == '__main__':
app = wx.App() # 初始化應(yīng)用
frame = MyFrame(parent=None, id=1) # 實(shí)例MyFrame類,并傳遞參數(shù)
frame.Show() # 顯示窗口
app.MainLoop() # 調(diào)用MainLoop()主循環(huán)方法
執(zhí)行結(jié)果:

常用控件
StaticText文本類
創(chuàng)建完窗口以后,我們可以在窗口內(nèi)添加一些控件,所謂的控件,就是經(jīng)常使用的按鈕、文本、輸入框、單選框等。
wx.StaticText(parent, id, lable, pos=wx.DefaultPosition, size=wx.DefaultSize, style=0, name="staticText")
- parent:父窗口部件
- id:標(biāo)識(shí)符。使用-1可以自動(dòng)創(chuàng)建一個(gè)唯一的標(biāo)識(shí)
- lable:顯示在靜態(tài)控件中的文本內(nèi)容
- pos:一個(gè)wx.Point或者一個(gè)Python元組,它是窗口部件的位置
- size:一個(gè)wx.Size或一個(gè)Python元組,它是窗口部件的尺寸
- style:樣式標(biāo)記
- name:對(duì)象名字
實(shí)例代碼:
使用wx.StaticText輸出Python之禪
# -*- coding:utf-8 -*-
import wx
class MyFrame(wx.Frame):
def __init__(self, parent, id):
wx.Frame.__init__(self, parent, id, title="創(chuàng)建StaticText類",
pos=(100, 100), size=(600, 400))
panel = wx.Panel(self) # 創(chuàng)建畫板
# 創(chuàng)建標(biāo)題,并設(shè)置字體
title = wx.StaticText(panel, label='Python之禪——Tim Peters', pos=(100, 20))
font = wx.Font(16, wx.DEFAULT, wx.FONTSTYLE_NORMAL, wx.NORMAL)
title.SetFont(font)
# 創(chuàng)建文本
wx.StaticText(panel, label='優(yōu)美勝于丑陋',pos=(50, 50))
wx.StaticText(panel, label='明了勝于晦澀',pos=(50, 70))
wx.StaticText(panel, label='簡潔勝于復(fù)雜',pos=(50, 90))
wx.StaticText(panel, label='復(fù)雜勝于凌亂',pos=(50, 110))
wx.StaticText(panel, label='扁平勝于嵌套',pos=(50, 130))
wx.StaticText(panel, label='間隔勝于緊湊',pos=(50, 150))
wx.StaticText(panel, label='可讀性很重要',pos=(50, 170))
wx.StaticText(panel, label='即便假借特例的實(shí)用性之名,也不可違背這些規(guī)則', pos=(50,190))
wx.StaticText(panel, label='不要包容所有錯(cuò)誤,除非你確定需要這樣做', pos=(50, 210))
wx.StaticText(panel, label='當(dāng)存在多種可能,不要嘗試去猜測(cè)', pos=(50, 230))
wx.StaticText(panel, label='而是盡量找一種,最好是唯一一種明顯的解決方案', pos=(50, 250))
wx.StaticText(panel, label='雖然這并不容易,因?yàn)槟悴皇?Python 之父', pos=(50, 270))
wx.StaticText(panel, label='做也許好過不做,但不假思索就動(dòng)手還不如不做', pos=(50, 290))
wx.StaticText(panel, label='如果你無法向人描述你的方案,那肯定不是一個(gè)好方案;反之亦然', pos=(50, 310))
wx.StaticText(panel, label='命名空間是一種絕妙的理念,我們應(yīng)當(dāng)多加利用', pos=(50, 330))
if __name__ == '__main__':
app = wx.App() # 初始化應(yīng)用
frame = MyFrame(parent=None, id=-1) # 實(shí)例MyFrame類,并傳遞參數(shù)
frame.Show() # 顯示窗口
app.MainLoop() # 調(diào)用主循環(huán)方法
上述代碼中,使用panel = wx.Panel(self)來創(chuàng)建畫板,并將panel 作為父類,然后將組件放入窗體中,此外,使用wx.Font類來設(shè)置字體。創(chuàng)建一個(gè)字體實(shí)例,需要使用如下構(gòu)造函數(shù):
wx.Font(pointSize, family, style, weight, underline=False, faceName="", encoding=wx.FONTENCODING_DEFAULT)
- pointSize:字體的整數(shù)尺寸,單位為磅
- family:用于快速的指定一個(gè)字體而不需要知道該字體實(shí)際的名字
- style:用于指定字體是否傾斜
- weight:指明字體醒目程度
- underline:僅在Windows系統(tǒng)下有效,如果取值為True,則加下劃線,如果為False則無下劃線
- faceName:指定字體名
- encoding:運(yùn)行在幾個(gè)編碼中選擇一個(gè),大多數(shù)情況可以使用默認(rèn)編碼
執(zhí)行結(jié)果:

TextCtrl輸入文本
wx.TextCtrl(parent, id, value="", pos=wx.DefaultPosition, size=wx.DefaultSize,style=0,validator=wx.DefaultValidator name=wx.TextCtrlNameStr)
- style:單行wx.TextCtrl的樣式,取值如下:
- wx.TE_CENTER:控件中的文本居中
- wx.TE_LEFT:控件中的文本左對(duì)齊
- wx.TE_NOHIDESEL:文本始終高亮顯示,僅適用于Windows
- wx.TE_PASSWORD:不顯示所鍵入的文本,以(*)代替顯示
- wx.TE_PROCESS_ENTER:如果使用改參數(shù),那么當(dāng)用戶在控件內(nèi)按下
Enter鍵時(shí),一個(gè)文本輸入事件將被觸發(fā)。否則,按鍵事件由該文本控件或該對(duì)話框管理
- wx.TE_PROCESS_TAB:如果指定了這個(gè)樣式,那么通常的字符事件在按下
Tab鍵時(shí)創(chuàng)建(一般意味著一個(gè)制表符將被插入文本)。否則,tab由對(duì)話框來管理,通常是控件間切換
- wx.TE_READONLY:文本控件為只讀,用戶不能修改其中文本
- wx.TE_RIGHT:控件中的文本右對(duì)齊
- value:顯示在該控件中的初始文本
- validator:常用于過濾數(shù)據(jù)以確保只能鍵入要接受的數(shù)據(jù)
示例代碼:
# -*- coding:utf-8 -*-
import wx
class MyFrame(wx.Frame):
def __init__(self, parent, id):
wx.Frame.__init__(self, parent, id, title="創(chuàng)建TextCtrl類", size=(400, 300))
#創(chuàng)建面板
panel = wx.Panel(self)
# 創(chuàng)建文本和輸入框
self.title = wx.StaticText(panel, label="請(qǐng)輸入用戶名和密碼", pos=(140, 20))
self.label_user = wx.StaticText(panel, label="用戶名:", pos=(50, 50))
self.text_user = wx.TextCtrl(panel, pos=(100, 50), size=(235, 25), style=wx.TE_LEFT)
self.label_pwd = wx.StaticText(panel, pos=(50, 90), label="密 碼:")
self.text_password = wx.TextCtrl(panel, pos=(100, 90), size=(235, 25), style=wx.TE_PASSWORD)
if __name__ == '__main__':
app = wx.App() # 初始化應(yīng)用
frame = MyFrame(parent=None, id=-1) # 實(shí)例MyFrame類,并傳遞參數(shù)
frame.Show() # 顯示窗口
app.MainLoop() # 調(diào)用主循環(huán)方法
執(zhí)行結(jié)果:

Button按鈕類
wx.Button(parent, id, lable, pos, size=wx.DefaultSize, style=0, validator, name="button")
wx.Button和wx.TextCtrl的參數(shù)基本相同,其中參數(shù)lable是顯示在按鈕上的文本
示例代碼:
# -*- coding:utf-8 -*-
import wx
class MyFrame(wx.Frame):
def __init__(self, parent, id):
wx.Frame.__init__(self, parent, id, title="創(chuàng)建TextCtrl類", size=(400, 300))
panel = wx.Panel(self) # 創(chuàng)建面板
# 創(chuàng)建文本和輸入框
self.title = wx.StaticText(panel, label="請(qǐng)輸入用戶名和密碼", pos=(140, 20))
self.label_user = wx.StaticText(panel, label="用戶名:", pos=(50, 50))
self.text_user = wx.TextCtrl(panel, pos=(100, 50), size=(235, 25), style=wx.TE_LEFT)
self.label_pwd = wx.StaticText(panel, pos=(50, 90), label="密 碼:")
self.text_password = wx.TextCtrl(panel, pos=(100, 90), size=(235, 25), style=wx.TE_PASSWORD)
self.bt_confirm = wx.Button(panel, label='確定', pos=(105, 130)) # 創(chuàng)建“確定”按鈕
self.bt_cancel = wx.Button(panel, label='取消', pos=(195, 130)) # 創(chuàng)建“取消”按鈕
if __name__ == '__main__':
app = wx.App() # 初始化
frame = MyFrame(parent=None, id=-1) # 實(shí)例MyFrame類,并傳遞參數(shù)
frame.Show() # 顯示窗口
app.MainLoop() # 調(diào)用主循環(huán)方法
執(zhí)行結(jié)果:

綁定事件
當(dāng)我們點(diǎn)擊按鈕后需要讓系統(tǒng)做出相應(yīng)的響應(yīng),如執(zhí)行某個(gè)判斷并給出提示,使用Bind()方法可以將事件處理函數(shù)綁定到給定的事件上:
bt_confirm.Bind(wx.EVT_BUTTON, OnclickSubmit)
示例代碼:
點(diǎn)擊確定,判斷密碼是否正確等
# -*- coding:utf-8 -*-
import wx
class MyFrame(wx.Frame):
def __init__(self, parent, id):
wx.Frame.__init__(self, parent, id, '用戶登錄', size=(400, 300))
# 創(chuàng)建面板
panel = wx.Panel(self)
# 創(chuàng)建“確定”和“取消”按鈕, 并綁定事件
self.bt_confirm = wx.Button(panel, label='確定')
self.bt_confirm.Bind(wx.EVT_BUTTON, self.OnclickSubmit)
self.bt_cancel = wx.Button(panel, label='取消')
self.bt_cancel.Bind(wx.EVT_BUTTON, self.OnclickCancel)
# 創(chuàng)建文本,左對(duì)齊
self.title = wx.StaticText(panel, label="請(qǐng)輸入用戶名和密碼")
self.label_user = wx.StaticText(panel, label="用戶名:")
self.text_user = wx.TextCtrl(panel, style=wx.TE_LEFT)
self.label_pwd = wx.StaticText(panel, label="密 碼:")
self.text_password = wx.TextCtrl(panel, style=wx.TE_PASSWORD)
# 添加容器,容器中控件按橫向并排排列
hsizer_user = wx.BoxSizer(wx.HORIZONTAL)
hsizer_user.Add(self.label_user, proportion=0, flag=wx.ALL, border=5)
hsizer_user.Add(self.text_user, proportion=1, flag=wx.ALL, border=5)
hsizer_pwd = wx.BoxSizer(wx.HORIZONTAL)
hsizer_pwd.Add(self.label_pwd, proportion=0, flag=wx.ALL, border=5)
hsizer_pwd.Add(self.text_password, proportion=1, flag=wx.ALL, border=5)
hsizer_button = wx.BoxSizer(wx.HORIZONTAL)
hsizer_button.Add(self.bt_confirm, proportion=0, flag=wx.ALIGN_CENTER, border=5)
hsizer_button.Add(self.bt_cancel, proportion=0, flag=wx.ALIGN_CENTER, border=5)
# 添加容器,容器中控件按縱向并排排列
vsizer_all = wx.BoxSizer(wx.VERTICAL)
vsizer_all.Add(self.title, proportion=0, flag=wx.BOTTOM | wx.TOP | wx.ALIGN_CENTER,
border=15)
vsizer_all.Add(hsizer_user, proportion=0, flag=wx.EXPAND | wx.LEFT | wx.RIGHT, border=45)
vsizer_all.Add(hsizer_pwd, proportion=0, flag=wx.EXPAND | wx.LEFT | wx.RIGHT, border=45)
vsizer_all.Add(hsizer_button, proportion=0, flag=wx.ALIGN_CENTER | wx.TOP, border=15)
panel.SetSizer(vsizer_all)
def OnclickSubmit(self, event):
""" 點(diǎn)擊確定按鈕,執(zhí)行方法 """
message = ""
username = self.text_user.GetValue() # 獲取輸入的用戶名
password = self.text_password.GetValue() # 獲取輸入的密碼
if username == "" or password == "": # 判斷用戶名或密碼是否為空
message = '用戶名或密碼不能為空'
elif username == 'admin' and password == '123456': # 用戶名和密碼正確
message = '登錄成功'
else:
message = '用戶名和密碼不匹配' # 用戶名或密碼錯(cuò)誤
wx.MessageBox(message) # 彈出提示框
def OnclickCancel(self, event): # 沒有event點(diǎn)擊取消會(huì)報(bào)錯(cuò)
""" 點(diǎn)擊取消按鈕,執(zhí)行方法 """
self.text_user.SetValue("") # 清空輸入的用戶名
self.text_password.SetValue("") # 清空輸入的密碼
if __name__ == '__main__':
app = wx.App() # 初始化
frame = MyFrame(parent=None, id=-1) # 實(shí)例MyFrame類,并傳遞參數(shù)
frame.Show() # 顯示窗口
app.MainLoop() # 調(diào)用主循環(huán)方法
執(zhí)行結(jié)果:

|