本教程是博主個人心血,未經允許不可引用,引用必舉報,舉報必封號。
博主個人博客【魏大王官網】,內容更精彩!!
《tkinter實用教程一》Linux 環境下安裝tkinter
《tkinter實用教程三》tkinter Button 控件
《tkinter實用教程四》tkinter 布局管理 Grid
《tkinter實用教程五》tkinter ttk.Frame控件
tkinter 表格布局管理 Grid
在學習其他控件之前,我們需要先了解 tkinter 布局管理概念(解決控件放在哪里的問題)。
雖然, tkinter 提供了多種控制布局的方式,但我還是建議使用 grid 處理所有布局問題。
下面,本文將聚焦 grid 布局管理方式,如果你有學習其他布局方式的需要,可以留言給我,我會在后繼章節優先更新其他布局方式。
行與列
在 grid 布局中的所有控件都會被賦予一個行號和一個列號,這是每個控件相對於其他控件位置的憑證。
同一列控件上下排布,同一行控件左右排布。
行與列的寬度和高度由內部的控件決定,在使用 grid 布局時,不需要關注行和列的大小。
使用 grid 布局
使用 grid 按鈕非常簡單,只需要在創建控件之后,指定控件放置的表格行號和列號就可以了。
示例代碼如下:
from tkinter import *
from tkinter import ttk
root = Tk()
btn1 = ttk.Button(text="第一個按鈕") # 創建按鈕
btn2 = ttk.Button(text="第二個按鈕")
btn3 = ttk.Button(text="第三個按鈕")
btn1.grid(column=0,row=0) # 放置按鈕
btn2.grid(column=1,row=1)
btn3.grid(column=2,row=2)
root.mainloop()
以上代碼創建了三個按鈕,排列在窗口左上到右下的對角線上,如下圖所示:

控件跨行、跨列放置
有些時候,會有一些較大的控件,需要占據多行、多列的窗口空間,此時就需要在指定空間位置時額外指定占據的行數和列數。
示例代碼如下:
from tkinter import *
from tkinter import ttk
root = Tk()
s = ttk.Style()
s.configure('1.TFrame',background='red')
btn1 = ttk.Button(root,text="第一個按鈕") # 創建按鈕
btn2 = ttk.Button(root,text="第二個按鈕")
ety1 = ttk.Entry(root)
frm = ttk.Frame(root,width=200,height=200,style='1.TFrame')
btn1.grid(column=0,row=0)
btn2.grid(column=1,row=0)
ety1.grid(column=0,row=1,columnspan=2) # 使用 columnspan 跨越兩列
frm.grid(column=0,row=2,columnspan=2,rowspan=2)
root.mainloop()
代碼執行效果如下:

以上代碼涉及了兩個還沒有介紹到的控件 ttk.Entry 和 ttk.Frame ,后繼都會更新上的。
ipadx、ipady參數
這兩個可選參數類似於 css 樣式中的 padding,屬於內邊距。
ipadx:內部橫向填充,添加到控件內部的左側和右側。
ipady:內部縱向填充,添加到控件內部的上側和下側。
代碼示例如下:
from tkinter import *
from tkinter import ttk
root = Tk()
btn = ttk.Button(root,text="一個按鈕")
btn.grid(column=0,row=0)
btn2 = ttk.Button(root,text="兩個按鈕")
btn2.grid(column=0,row=1,ipadx=10)
btn3 = ttk.Button(root,text='三個按鈕')
btn3.grid(column=0,row=2,ipady=10)
btn4 = ttk.Button(root,text="四個按鈕")
btn4.grid(column=0,row=3,ipady=10,ipadx=10)
root.mainloop()
代碼執行結果如下圖:

按鈕控件的內部被填充了額外的控件,變得臃腫。
padx、pady 參數
padx 和 pady 參數屬於外邊距,類似於 css 樣式中的 margin 參數。
padx:外部橫向填充,添加到控件外部的左側和右側。
pady:外部縱向填充,添加到控件外部的上側和下側。
示例代碼如下:
from tkinter import *
from tkinter import ttk
root = Tk()
btn = ttk.Button(root,text="一個按鈕")
btn.grid(column=0,row=0)
btn2 = ttk.Button(root,text="兩個按鈕")
btn2.grid(column=0,row=1,pady=10)
btn3 = ttk.Button(root,text='三個按鈕')
btn3.grid(column=0,row=2)
btn4 = ttk.Button(root,text="四個按鈕")
btn4.grid(column=1,row=0,padx=10)
root.mainloop()
代碼執行結果如下圖:

第二個和第四個按鈕因為增加了外邊距和其他按鈕中間產生了空隙。
sticky 參數
sticky 選項確定如何在單元格內分配控件件未以其自然大小占用的任何額外空間。
如果不指定 sticky 參數,控件將居於單元格中部,未占據的額外控件均勻分布四周。
sticky 有四個可選值,分別為:N、S、W、E,分別對應上、下、左、右。
sticky=(N,S) 使控件上下方向拉伸,並保持橫向居中。
sticky=(W,E) 使控件左右方向拉伸,並保持上下居中。
示例代碼如下:
from tkinter import *
from tkinter import ttk
root = Tk()
btn1 = ttk.Button(root,text="第一個按鈕")
btn2 = ttk.Button(root,text="第二個按鈕")
btn3 = ttk.Button(root,text="第三個按鈕")
btn4 = ttk.Button(root,text="第四個按鈕")
btn5 = ttk.Button(root,text="第五個按鈕")
btn1.grid(column=0,row=0,sticky=N)
btn2.grid(column=0,row=1,sticky=E)
btn3.grid(column=0,row=2,sticky=W)
btn4.grid(column=0,row=3,sticky=S)
btn5.grid(column=0,row=4,sticky=(E,W))
root.columnconfigure(0,weight=1)
root.rowconfigure(2,weight=1)
root.rowconfigure(3,weight=1)
root.mainloop()
代碼執行結果:

rowconfigure 和 columnconfigure 方法可以設定每個行和列的比例,我們可以通過這種方式使控件伴隨窗口大小變化,自動適應。
編寫一個簡單的計算器界面
編寫一個簡單的計算器界面是練習 grid 布局最有效的方式,下面代碼就是一個計算器界面的簡單實現:
from tkinter import *
from tkinter import ttk
root = Tk()
s = ttk.Style()
s.configure('1.TFrame',background='red',width=16)
s.configure('1.TButton',width=3)
main = ttk.Frame(root,style='1.TFrame')
ety = ttk.Entry(main,width=17)
btn_add = ttk.Button(main,text=' + ',style='1.TButton')
btn_ac = ttk.Button(main,text="AC",style='1.TButton')
btn_del = ttk.Button(main,text="Del",style='1.TButton')
btn_mol = ttk.Button(main,text=" % ",style="1.TButton")
btn_div = ttk.Button(main,text=' ÷ ',style="1.TButton")
btn_7 = ttk.Button(main,text=" 7 ",style='1.TButton')
btn_8 = ttk.Button(main,text=" 8 ",style='1.TButton')
btn_9 = ttk.Button(main,text=" 9 ",style="1.TButton")
btn_times = ttk.Button(main,text=' × ',style="1.TButton")
btn_4 = ttk.Button(main,text=" 4 ",style='1.TButton')
btn_5 = ttk.Button(main,text=" 5 ",style='1.TButton')
btn_6 = ttk.Button(main,text=" 6 ",style="1.TButton")
btn_minus = ttk.Button(main,text=' - ',style="1.TButton")
btn_1 = ttk.Button(main,text=" 1 ",style='1.TButton')
btn_2 = ttk.Button(main,text=" 2 ",style='1.TButton')
btn_3 = ttk.Button(main,text=" 3 ",style="1.TButton")
btn_add = ttk.Button(main,text=' + ',style="1.TButton")
btn_dot = ttk.Button(main,text=" . ", style="1.TButton")
btn_0 = ttk.Button(main,text=" 0 ",style="1.TButton")
btn_eq = ttk.Button(main,text=" + ",width=7)
ety.grid(column=0,row=0,columnspan=4,sticky=(E,W))
btn_ac.grid(row=1,column=0,sticky=(E,W))
btn_del.grid(row=1,column=1,sticky=(E,W))
btn_mol.grid(row=1,column=2,sticky=(E,W))
btn_div.grid(row=1,column=3,sticky=(E,W))
btn_7.grid(row=2,column=0,sticky=(E,W))
btn_8.grid(row=2,column=1,sticky=(E,W))
btn_9.grid(row=2,column=2,sticky=(E,W))
btn_times.grid(row=2,column=3,sticky=(E,W))
btn_4.grid(row=3,column=0,sticky=(E,W))
btn_5.grid(row=3,column=1,sticky=(E,W))
btn_6.grid(row=3,column=2,sticky=(E,W))
btn_minus.grid(row=3,column=3,sticky=(E,W))
btn_1.grid(row=4,column=0,sticky=(E,W))
btn_2.grid(row=4,column=1,sticky=(E,W))
btn_3.grid(row=4,column=2,sticky=(E,W))
btn_add.grid(row=4,column=3,sticky=(E,W))
btn_dot.grid(row=5,column=0,sticky=(E,W))
btn_0.grid(row=5,column=1,sticky=(E,W))
btn_eq.grid(row=5,column=2,columnspan=2,sticky=(E,W))
main.grid(column=0,row=0,sticky=(E,W,N,S))
main.columnconfigure(0,weight=1)
main.columnconfigure(1,weight=1)
main.columnconfigure(2,weight=1)
main.columnconfigure(3,weight=1)
root.rowconfigure(0,weight=1)
root.columnconfigure(0,weight=1)
root.mainloop()
這段代碼中出現了很多之前沒有提到的參數,如果由困惑的地方,就給我留言吧!!
代碼執行結果:

上述代碼還有一個故意隱藏的 BUG , 當我們拖拽窗口邊緣,改變窗口大小時,會出現奇怪的現象。
如果我們橫向拖動窗口邊框,使窗口變寬,結果如下:

如果我們縱向拖動窗口邊框,使窗口變高,結果如下:

為什么會出現這種情況呢?如何解決這種情況呢?趕快留言告訴博主吧!!
博主個人博客【魏大王官網】,內容更精彩!!
《tkinter實用教程一》Linux 環境下安裝tkinter
《tkinter實用教程三》tkinter Button 控件
