1. 程式人生 > >(轉)Python下使用Tkinter 製作圖形介面

(轉)Python下使用Tkinter 製作圖形介面

1.tkinter

tkinter是Python下面向tk的圖形介面介面庫,可以方便地進行圖形介面設計和互動操作程式設計。tkinter的優點是簡單易用、與Python的結合度好。tkinter在Python 3.x下預設整合,不需要額外的安裝操作;不足之處為缺少合適的視覺化介面設計工具,需要通過程式碼來完成視窗設計和元素佈局。

本節採用的Python版本為3.x,如果想在python 2.x下使用tkinter,請通過apt-get進行安裝。需要注意的是,不同Python版本下的tkinter使用方式可能略有不同,建議採用Python3。

1.1.hello tkinter

首先介紹一個tkinter的基本例子,在IDLE中新建hello_tkinter.py,程式碼如下:

import tkinter as tk

# 建立tkinter視窗,設定視窗標題

top = tk.Tk()

top.title("Hello Test")

# 在視窗中建立標籤

labelHello = tk.Label(top, text = "Hello Tkinter!")

labelHello.pack()

# 執行並顯示視窗

top.mainloop()

然後是top的概念和pack操作的說明:略……(懶得寫啦哈哈)

表1 Label元件常用引數

引數

描述

height

元件的高度(所佔行數)             

width

元件的寬度(所佔字元個數)     

fg

前景字型顏色

bg

背景顏色

justify

多行文字的對齊方式,可選引數為: LEFT、 CENTER、RIGHT

padx

文字左右兩側的空格數(預設為1)

pady

文字上下兩側的空格數(預設為1)

在Shell下執行程式,就可以顯示出一個簡單的視窗了。

$ python3 hello_tkinter.py

Tkinter視窗效果

1.2.tkinter常用元件

雖然1.1中我們已經設計出了tkinter的基本視窗,但這時的視窗還過於簡陋,除了顯示資訊以外無法實現任何有效的功能。為了完成更多的使用者互動功能,我們還需要了解更多的tkinter介面元素,本節將介紹一些常用的tkinter元件。

1.2.1.按鈕元件

按鈕元件(Button)是tkinter最常用的圖形元件之一,通過Button可以方便地與使用者進行互動。下列程式碼實現了通過觸發按鈕事件(按下按鈕)來執行指定操作(改變標籤內容)的例子。

import tkinter as tk

def btnHelloClicked():

                labelHello.config(text = "Hello Tkinter!")

top = tk.Tk()

top.title("Button Test")

labelHello = tk.Label(top, text = "Press the button...", height = 5, width = 20, fg = "blue")

labelHello.pack()

btn = tk.Button(top, text = "Hello", command = btnHelloClicked)

btn.pack()

top.mainloop()

程式碼中定義了btnHelloClicked()函式,並通過給Button的command屬性賦值來指定按鈕按下時執行btnHelloClicked()函式中的程式碼的功能。在該函式中,通過labelHello.config()更改了label的text引數,即更改了標籤的文字內容。

表2 Button元件基本引數

引數

描述

height

元件的高度(所佔行數)

width

元件的寬度(所佔字元個數)

fg

前景字型顏色

bg

背景顏色

activebackground

按鈕按下時的背景顏色

activeforeground

按鈕按下時的前景顏色

justify

多行文字的對齊方式,可選引數為: LEFT、 CENTER、RIGHT

padx

文字左右兩側的空格數(預設為1)

pady

文字上下兩側的空格數(預設為1)

Button元件效果

1.2.2.輸入框元件

輸入框(Entry)用來輸入單行內容,可以方便地向程式傳遞使用者引數。這裡通過一個轉換攝氏度和華氏度的小程式來演示該元件的使用。

import tkinter as tk

def btnHelloClicked():

                cd = float(entryCd.get())

                labelHello.config(text = "%.2f°C = %.2f°F" %(cd, cd*1.8+32))        

top = tk.Tk()

top.title("Entry Test")

labelHello = tk.Label(top, text = "Convert °C to °F...", height = 5, width = 20, fg = "blue")

labelHello.pack()

entryCd = tk.Entry(top, text = "0")

entryCd.pack()

btnCal = tk.Button(top, text = "Calculate", command = btnHelloClicked)

btnCal.pack()

top.mainloop()

本例的程式碼從1.2.1中修改而來,並新建了一個Entry元件entryCd,text引數設定了輸入框的預設值為“0”。當按鈕按下後,通過entryCd.get()獲取輸入框中的文字內容,該內容為字串型別,需要通過float()函式轉換成數字,自後再進行換算並更新label顯示內容。

表3 Entry元件常用引數

引數

描述

height

元件的高度(所佔行數)           (無)

width

元件的寬度(所佔字元個數)

fg

前景字型顏色

bg

背景顏色

show

將Entry框中的文字替換為指定字元,用於輸入密碼等,如設定 show="*"

state

設定元件狀態,預設為normal,可設定為:disabled—禁用元件,readonly—只讀

執行效果

華氏攝氏溫度換算程式效果

1.2.3.單選、複選框

單選框(Radiobutton)和複選框(Checkbutton)分別用於實現選項的單選和複選功能。本例中的程式碼實現了通過單選框、複選框設定文字樣式的功能。

import tkinter as tk

def colorChecked():

                labelHello.config(fg = color.get())

def typeChecked():

        textType = typeBlod.get() + typeItalic.get()

        if textType == 1:

                labelHello.config(font = ("Arial", 12, "bold"))

        elif textType == 2:

                labelHello.config(font = ("Arial", 12, "italic"))

        elif textType == 3:

                labelHello.config(font = ("Arial", 12, "bold italic"))

        else :

                labelHello.config(font = ("Arial", 12))

top = tk.Tk()

top.title("Radio & Check Test")

labelHello = tk.Label(top, text = "Check the format of text.", height = 3, font=("Arial", 12))

labelHello.pack()

color = tk.StringVar()

tk.Radiobutton(top, text = "Red", variable = color, value = "red", command = colorChecked).pack(side = tk.LEFT)

tk.Radiobutton(top, text = "Blue", variable = color, value = "blue", command = colorChecked).pack(side = tk.LEFT)

tk.Radiobutton(top, text = "Green", variable = color, value = "green", command = colorChecked).pack(side = tk.LEFT)

typeBlod = tk.IntVar()

typeItalic = tk.IntVar()

tk.Checkbutton(top, text = "Blod", variable = typeBlod, onvalue = 1, offvalue = 0, command = typeChecked).pack(side = tk.LEFT)

tk.Checkbutton(top, text = "Italic", variable = typeItalic, onvalue = 2, offvalue = 0, command = typeChecked).pack(side = tk.LEFT)

top.mainloop()

在程式碼中,文字的顏色通過Radiobutton來選擇,同一時間只能選擇一個顏色。在三個Red、Blue和Green三個單選框中,定義了同樣的變數引數color,選擇不同的單選框會為該變數賦予不同的字串值,內容即為對應的顏色。

任何單選框被選中都會觸發colorChecked()函式,將標籤修改為對應單選框表示的顏色。

表4 Radiobutton元件常用引數

引數

描述

variable

單選框索引變數,通過變數的值確定哪個單選框被選中。一組單選框使用同一個索引變數

value

單選框選中時變數的值

command

單選框選中時執行的命令(函式)

文字的粗體、斜體樣式則由複選框實現,分別定義了typeBlod和typeItalic變數來表示文字是否為粗體和斜體。

當某個複選框的狀態改變時會觸發typeChecked()函式。該函式負責判斷當前那些複選框被選中,並將字型設定為對應的樣式。

表5 Checkbutton元件常用引數

引數

描述

variable

複選框索引變數,通過變數的值確定哪些複選框被選中。每個複選框使用不同的變數,使複選框之間相互獨立

onvalue

複選框選中(有效)時變數的值

offvalue

複選框未選中(無效)時變數的值

command

複選框選中時執行的命令(函式)

執行效果

1.2.4.繪圖元件

繪圖元件(Canvas)可以在GUI中實現2D圖形的繪製,相當於畫圖板。元件內建了多種繪圖函式,可以通過簡單的2D座標繪製直線、矩形、圓形、多邊形等。本例程式碼演示了Canvas元件的繪圖功能,更多的繪圖函式可以查閱Canvas的參考頁面。

import tkinter as tk

def drawCircle(self, x, y, r, **kwargs):

    return self.create_oval(x-r, y-r, x+r, y+r, **kwargs)

top = tk.Tk()

top.title("Canvas Test")

cvs = tk.Canvas(top, width = 600, height = 400)

cvs.pack()

cvs.create_line(50, 50, 50, 300)

cvs.create_line(100, 50, 200, 300, fill = "red", dash = (4, 4), arrow = tk.LAST)

cvs.create_rectangle(200, 50, 400, 200, fill = "blue")

cvs.create_oval(450, 50, 550, 200, fill = "green" )

drawCircle(cvs, 450, 300, 50, fill = "red")

cvs.create_polygon(200, 250, 350, 250, 350, 350, 220, 300, fill="yellow")

top.mainloop()

繪圖函式的引數都比較好理解,包括基本的座標和顏色、線型等附加引數。

直線(line),即線段,通過兩個端點定義。座標順序為x1、y1、x2、y2。

矩形(rectangle)通過對角線上的兩個點來定義。

需要注意的是Canvas中沒有畫圓函式,這裡通過繪製橢圓間接實現了繪製圓形的函式drawCircle()。橢圓(oval)是通過外切矩形的對角線兩點來定義的(別告訴我你不知道什麼是外切矩形……)。如下圖所示:

執行效果

1.2.5.訊息視窗

訊息視窗(messagebox)用於彈出提示框向用戶進行告警,或讓使用者選擇下一步如何操作。訊息框包括很多型別,常用的有info、warning、error、yeno、okcancel等,包含不同的圖示、按鈕以及彈出提示音。下面的程式碼演示了各訊息框的執行效果,大家可以自己一一嘗試。

import tkinter as tk

from tkinter import messagebox as msgbox

def btn1_clicked():

                msgbox.showinfo("Info", "Showinfo test.")

def btn2_clicked():

                msgbox.showwarning("Warning", "Showwarning test.")

def btn3_clicked():

                msgbox.showerror("Error", "Showerror test.")               

def btn4_clicked():

                msgbox.askquestion("Question", "Askquestion test.")

def btn5_clicked():

                msgbox.askokcancel("OkCancel", "Askokcancel test.")

def btn6_clicked():

                msgbox.askyesno("YesNo", "Askyesno test.")               

def btn7_clicked():

                msgbox.askretrycancel("Retry", "Askretrycancel test.")

top = tk.Tk()

top.title("MsgBox Test")

btn1 = tk.Button(top, text = "showinfo", command = btn1_clicked)

btn1.pack(fill = tk.X)

btn2 = tk.Button(top, text = "showwarning", command = btn2_clicked)

btn2.pack(fill = tk.X)

btn3 = tk.Button(top, text = "showerror", command = btn3_clicked)

btn3.pack(fill = tk.X)

btn4 = tk.Button(top, text = "askquestion", command = btn4_clicked)

btn4.pack(fill = tk.X)

btn5 = tk.Button(top, text = "askokcancel", command = btn5_clicked)

btn5.pack(fill = tk.X)

btn6 = tk.Button(top, text = "askyesno", command = btn6_clicked)

btn6.pack(fill = tk.X)

btn7 = tk.Button(top, text = "askretrycancel", command = btn7_clicked)

btn7.pack(fill = tk.X)

top.mainloop()

執行效果