簡體   English   中英

tkinter - 了解包和網格 - 簡單的布局。 (總是迷茫……)

[英]tkinter - understand pack and grid - simple layout. (always confused…)

我正在嘗試配置一個文本框,並在文本框下方連續設置 3 個按鈕,我不想擴展它們以填充所有區域。 只是在中心保持原來的大小。

我試圖用包或網格來做到這一點。 但我真的很困惑。 我還嘗試將文本框和按鈕放在不同的框架上,所以它可能會將小部件分開並讓我配置它而不會弄亂東西(因為一切都是相對於另一個......)......但我什么都沒有這看起來不錯。

我還想學習如何以正確的方式使用網格,如果我有各種小部件和按鈕,一個在另一個下面沒有“列跨度”,或者調整按鈕內的文本長度以匹配它們上面的小部件......

在這個例子中。 我怎樣才能使按鈕居中? 我必須使用 side=tkinter.LEFT 才能將它們一個接一個地放置。 但他們也堅持向左的問題......

import tkinter

window = tkinter.Tk()

frame1 = tkinter.Frame(window).pack()

textbox1 = tkinter.Text(frame1, width=70, height=15).pack(side=tkinter.TOP)

button1 = tkinter.Button(frame1, text="button1").pack(side=tkinter.LEFT)
button2 = tkinter.Button(frame1, text="button2").pack(side=tkinter.LEFT)
button3 = tkinter.Button(frame1, text="button3").pack(side=tkinter.LEFT)

window.mainloop()

在這個例子中,如果我設置另一個框架來分隔小部件......它也沒有到達中心......

import tkinter

window = tkinter.Tk()

frame1 = tkinter.Frame(window).pack(side=tkinter.TOP)

textbox1 = tkinter.Text(frame1, width=70, height=15).pack(side=tkinter.TOP)

frame2 = tkinter.Frame(window).pack(side=tkinter.TOP)

button1 = tkinter.Button(frame2, text="button1").pack(side=tkinter.LEFT)
button2 = tkinter.Button(frame2, text="button2").pack(side=tkinter.LEFT)
button3 = tkinter.Button(frame2, text="button3").pack(side=tkinter.LEFT)

window.mainloop()

在這個例子中。 使用網格,如果我使用不同的框架,按鈕只會跳到文本框上並搞砸一切......

import tkinter

window = tkinter.Tk()

frame0 = tkinter.Frame(window).grid(row=0, column=0)

frame1 = tkinter.Frame(window).grid(row=1, column=0)

textbox = tkinter.Text(frame0, width=70, height=15).grid(row=0, column=0)

button1 = tkinter.Button(frame1, text="button1").grid(row=0, column=0)
button2 = tkinter.Button(frame1, text="button2").grid(row=0, column=1)
button3 = tkinter.Button(frame1, text="button3").grid(row=0, column=2)

window.mainloop()

有人可以向我解釋哪種方式更好使用以及如何更好地理解它......? 它總是讓我感到困惑......

在此先感謝, eliran

我試圖用包或網格來做到這一點。 但我真的很困惑。 我還嘗試將文本框和按鈕放在不同的框架上,所以它可能會將小部件分開並讓我配置它而不會弄亂東西(因為一切都是相對於另一個......)......但我什么都沒有這看起來不錯。

你的第二個例子非常接近工作,但它有一個致命的缺陷。 如果您添加一些調試語句,您會看到frame1frame2None 因此,任何以它們為父的小部件實際上最終都在根 window 中。

這是因為foo().bar()總是返回.bar()的結果。 在 tkinter 中, .grid(...)總是返回None ,所以Frame(...).grid(...)總是返回None

最佳實踐是始終將小部件創建與小部件布局分開。 例如:

frame1 = tkinter.Frame(window)
frame2 = tkinter.Frame(window)

frame1.pack(side="top")
frame2.pack(side="top")

這樣, frame1frame2被正確設置為幀。 發生這種情況時,第二個示例中代碼的 rest 將按預期工作,並且按鈕居中。

在這個例子中。 使用網格,如果我使用不同的框架,按鈕只會跳到文本框上並搞砸一切......

發生這種情況的原因與上面提到的相同:您認為您正在使用單獨的框架,但所有內容都在根 window 中。 因為它們都在根 window 中,並且您將文本小部件和按鈕放在同一行和同一列中,所以它們重疊。

我還想學習如何以正確的方式使用網格,如果我有各種小部件和按鈕,一個在另一個下面沒有“列跨度”,或者調整按鈕內的文本長度以匹配它們上面的小部件......

在這種特定情況下, grid不是正確的選擇,因為您實際上並沒有創建網格。 你可以使用它,但它比使用pack需要更多的代碼。 如果您要創建實際的網格, grid是正確的選擇。 在這種情況下,你不是。

在這種情況下使用grid需要一點創造力。 雖然這不是唯一的解決方案,但我建議您將底部框架分為五列 - 左右各空一列,中間三列用於按鈕。 空列可用於占用所有額外空間,迫使中間列全部居中。

使用grid的最佳實踐是每個使用grid來管理其子級的 window 至少需要具有非零權重的一行和一列。 這讓 tkinter 知道在哪里分配任何額外空間,例如當用戶調整 window 的大小時。

這是使用grid的完整解決方案:

import tkinter

window = tkinter.Tk()

frame0 = tkinter.Frame(window)
frame1 = tkinter.Frame(window)

window.grid_rowconfigure(0, weight=1)
window.grid_columnconfigure(0, weight=1)

frame0.grid(row=0, column=0, sticky="nsew")
frame1.grid(row=1, column=0, sticky="nsew")

frame0.grid_rowconfigure(0, weight=1)
frame0.grid_columnconfigure(0, weight=1)

textbox = tkinter.Text(frame0, width=70, height=15)
textbox.grid(row=0, column=0, sticky="nsew")

button1 = tkinter.Button(frame1, text="button1")
button2 = tkinter.Button(frame1, text="button2")
button3 = tkinter.Button(frame1, text="button3")

frame1.grid_rowconfigure(0, weight=1)
frame1.grid_columnconfigure((0,4), weight=1)

button1.grid(row=0, column=1)
button2.grid(row=0, column=2)
button3.grid(row=0, column=3)

window.mainloop()

有人可以向我解釋哪種方式更好使用以及如何更好地理解它......?

總之,使用單獨框架的直覺是正確的起點。 您應該將您的 UI 划分為邏輯組,並為每個組使用單獨的框架。 然后,您可以自由地為每個組分別選擇gridpack 但是,您需要仔細使用grid ,以確保正確使用sticky選項,並且您已為所有正確的列設置了權重。

最后,您必須從將小部件創建與小部件布局分開的正確做法開始。

我以前也遇到過這類問題。 盡管.pack().grid()系統非常出色,但當事情變得忙碌時,您可以使用.place()系統。 .place()允許您使用 xy 軸坐標精確定位 tkinter 和 ttk 小部件。

坐標 (0,0) 不在中心,而是在 tkinter window 的最左上角。

例如:

some_widget_name = Button(root, text="Click me!"....)
some_widget_name.place(x=100, y=50)

這將使您的小部件向右移動 100 像素,並從最左上角向下移動 50 像素。

但是,有時當您真的想要使小部件的位置精確時,您可能需要進行一些反復試驗以使其在視覺上令人愉悅。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM