我們在日常使用用戶介面時,偶而會看到供用戶參考閱讀的獨立一段文字框(例如說明事項或警語提示)或需讓用戶輸入一些內容來填寫表達(例如客訴內容或自傳描述),這樣的文字框在您使用python時Tkinter提供了text文字框的部件供您使用,另外,在視窗大小有限的情況下,我們不希望這種文字框佔據太多篇幅,這時候就會運用到卷軸scrollbar部件,這樣就能在有限的範圍內透過卷軸完整的閱覽完整的資訊,本章節就是介紹Tkinter中的text及scrollbar部件給各位,讓各位在設計互動式UI時對於多行文字的顯示及用戶的多行輸入能夠透過這兩個部件完成,最後有個小驚喜,請您耐心地讀完,當然Tkinter一直在進步,這也是Python opensource(開源軟體的優勢)。
首先介紹文字對話框text
前面的教材提到,我們可以運用tkinter的Entry部件來建立用戶輸入功能,但Entry部件僅能支援單行的輸入及顯示功能,遇到了多行說明文字顯示或多行文字輸入時,在tkinter中,text的舞台就出現了,它就像大一點且功能強大的entry部件。所以,這邊歸納text部件很適用的運用場景如下:
- 多行文字的輸入項,且容許不同的格式(如字型或顏色)
- 多行文字的說明顯示項(例如說明或提示警語)
- 文字框中也可以是兼具圖片、文字或網址的超連結
本篇的內容就帶著各位,運用tkinter中text、scrollbar、scrolledtext部件,來建立可供輸入及捲動閱覽說明的文字框,以下,我們會一動接著一動的帶著您了解及練習。
我們就先建立一個文字框
- 產生text(文字框)部件的語法:
文字框物件(自訂名稱) = tk.Text ( 基底視窗, option, ... )
文字框部件跟其他部件一樣具有多個屬性option來讓我們描述或設計文字框的樣貌及特色,例如width用來定義文字框的寬度,height用來定義文字框的高度,bd用來定義文字框框線的寬度。
我們可以運用以下的指令產生一個寬30字元高5個字元且邊寬為5象素的文字框。
text1=tk.Text(window,height=5,width=30,bd=4)
這樣就可以建立一個文字框物件text1,同時,我們運用參數同時給予這個文字框高度為5個字元,寬度為30個字元,也給予這個文字框4象素大小的邊框以利識別,這裡的單位會依文字框參數屬性的特性變化,例如高及寬的單位就是字元,但邊框的寬度就是象素,是不是很聰明呢?另外,我們個別設計一個有些長度的說明,打算放入文字框中,目的是要鋪之後的梗,讓您看看文字框遇到過多的文字內容後,會出現什麼樣的狀況?我們可以用什麼樣的技巧來應對?
text_content=```這是一個文字框的說明說明的……….. ```
text_content就是我們產生後用來放置說明內容的物件,並將多行的文字內容指派給這個物件
除了屬性之外,文字框部件同時也存在許多成員函式,讓我們可以針對文字框做動作,最常用到的就是insert及get成員函式,顧名思義的 部件物件.insert用途就是用來將文字內容置入文字框中,部件物件.get用途就是取得文字框物件中的內容。
text1.insert(tk.END,text_content)
指令中tk.END代表著插入文字的位置,這邊代表著從文字框中最後的位置開始放入文字物件。
接著,我們基於這個文字框不是用來讓用戶輸入資料之用,而只是用來顯示文字說明讓用戶參閱用,故我們不希望用戶可以更改或編輯文字框中的內容,因為這樣的特性,我們必須在插入文字內容後,將這的部件物件的屬性設定為不可編輯,這時運用到部件物件.configure的函式來變更此物件的屬性,其中,要變更的屬性參數為state,一般若不特別宣告的話text部件物件的state預設值為`normal`(是可以編輯模式),在我們完成文字框內容的插入後,我們再透過configure成員函式將此文字框的state屬性變更為disable,目的就是讓此文字框只能閱讀而不可編輯變更。
text1.configure(state='disable')
整個建立文字框部件的程式碼如下
程式執行的結果如下
從執行後的結果,您可以發現,因為受限於文字框的大小限制,雖然我們順利的將文字內容塞入在文字框中,且也被設定為純閱讀模式(不可編輯變更),但很顯然的,直覺上用戶只能看到部分的內容,當然聰明的用戶可以藉由上下左右按鍵來翻捲內容,但這樣的設計只能充其量稱為可行,但是並不友善,用戶缺少了一些在使用介面上的必要引導。
基於這樣的不完美,我們接著要做的是,讓它變成友善且專業,所以必需在文字框邊加裝一個卷軸,讓使用者很明顯地知道運用卷軸可以達到全文閱讀的目的,當然,如果您不想安裝卷軸也可以,但為了達到閱讀的方便性,你也可以把文字框設計的很大,讓用戶不需卷軸即可閱讀全文,但問題是,難道您設計的互動介面只有這個文字框嗎,通常都不只,一定還有許多其他的部件,所以,善用卷軸變成一件重要的事情,它會常常搭配著文字框一起出現。
接著,我們就來談談如何搭配著一個卷軸,在tkinter中scrollbar部件的產生通常跟隨著entry、listbox或text部件,原因很簡單,在有限的空間中,較多的內容或選項無法在有限的布建空間中一次全部展現,習慣上,使用卷軸的必要就會發生。
- 產生一個卷軸部件scrollbar1。
卷軸部件(自訂名稱) = tk.Scrollbar ( 基底視窗, option, ... )
其中在option中一個一定會用到的參數是command,而且command參數後面跟著屬性內容通常為text、listbox或entry部件的xview或yview成員函式,我們範例中建立scrollbar部件的指令完整如下
scrollbar1=tk.Scrollbar(window,command=text1.yview)
由於要連結卷軸部件與原文字框部件text1的連動關係,我們會利用
command=text1.yview來連結,代表著卷軸的移動會牽動text1文字框內容的捲動,由於是y軸的移動,故用yview來連動,若是水平卷軸的移動則用command=xview來定義連結。
但是光剛剛的scrollbar的一廂情願還不夠,text1也必須靠文字框部件的configure成員函式來建立與卷軸部件scrollbar1的關係,所以,還必須加上以下的指令來建立text對scrollbar部件的連動關係
text1.configure(yscrollcommand=scrollbar1.set)
就如同上面指令的描述,我們必須再定義text1中新增一個yscrollcommand的參數並定義為卷軸部件scrollbar1.set成員函式
有了這兩種近乎交叉的連結關係,你會運作起來text部件與scrollbar部件的連動關係。
當然,依慣例的,我們在產生部件後也必須利用布局方法來告訴python怎放置這個部件,我們之前是運用grid方法,這邊把它定義為視窗中的第1row第1column(第0row為label1標籤部件,第1row第0column為text1部件,所以卷軸部件會被安置在text1文字框部件的右邊),又由於讓卷軸的長度能搭配文字框的高度(因為row1的格子已經被文字框部件text1撐大),所以我們在grid屬性中特別運用sticky=tk.NS,其中N代表北,S代表南,意思是讓這個布局能夠在此格子中及於從南到北的長度,要不然它會明顯的小於文字框的長度,文字框的長度與卷軸的長度變的很不搭。指令的全文如下
scrollbar1.grid(row=1,column=1,sticky=tk.NS)
加入卷軸的程式碼如下
執行之後的結果如下
因為在程式中text1與scrollbar1交互連結的設定,使得卷軸和文字框可以天衣無縫的成為一體。
學完了這一段,聰明如你一定會問,方便的python為什麼沒有更便利的方式讓我們產生帶有卷軸的文字框呢,若您心中產生這樣的疑問,就代表您有進步及前衛的想法,確實,以下我們要介紹一種更便利的方式,可以直接產生帶有卷軸的文字框。
- 用更簡潔便利的程式碼直覺的建立帶有卷軸的文字框
感謝同學您可以耐心的讀到這裡,我們運用text、scrollbar兩個部件完成了一個完整的卷軸文字框的設計,說來簡單但又不是那麼簡單,原因是,中間提到的交互連結所使用的command=yview及yscrollcommand=scrollbar1.set的設計需要讓初學者多花一些記憶力及理解力,但tkinter也發現有強化更方便的空間,接下來要介紹在tkinter中一個子模組(module)- 從tkinter.scrolledtext module中運用ScrolledText 部件可以輕易地完成前面所練習的功能。
整個建立文字框部件的程式碼如下
程式執行的結果如下
所以帶有卷軸的文字框,在實作上,最敏捷且最有效率的做法,請運用
- 引入tkinter.scrolledtext子模組
- 建立ScrolledText部件,就讓您輕輕鬆鬆地完成帶有卷軸文字框的運用
這樣的做法,大大的省去建立兩個部件在交叉建立關係的複雜處理,是不是一個大驚喜呢?
留言列表