网格传播和柱跨度之间的奇异相互作用



将columnspan(而不是1(分配给子对象似乎会抵消uniform=1和grid_product(False(的效果。这里有一个简单的例子来说明我的意思(点击文本来回切换并观察变化(。

import tkinter as tk
class TestInterface:
def __init__(self, master):
self.master = master
self.master.title("Interface Template")
self.master.configure(bg='#000000', relief=tk.RIDGE, borderwidth=16)
self.master.attributes('-fullscreen', True)
self.demonstration_frame = tk.Frame()
self.dummy_frame = tk.Frame()
self.button = tk.Button()
self.button1()
def button1(self):
self.remake_test_frame()
self.button = tk.Button(self.demonstration_frame, text="LONG PHRASE MODIFYING THE GRID STRUCTURE", bg='#111111',
relief=tk.FLAT, fg="#FFFFFF", font=('Courier', 12), anchor='center', borderwidth=6,
command=lambda: self.button2())
self.button.grid(row=2, column=3, columnspan=2, sticky='nsew')
def button2(self):
self.remake_test_frame()
self.button = tk.Button(self.demonstration_frame, text="LONG PHRASE BEING CUT OFF AS INTENDED", bg='#111111',
relief=tk.FLAT, fg="#FFFFFF", font=('Courier', 12), anchor='center', borderwidth=6,
command=lambda: self.button1())
self.button.grid(row=2, column=3, sticky='nsew')
def remake_test_frame(self):
self.demonstration_frame.destroy()
self.demonstration_frame = tk.Frame(master=self.master, relief=tk.FLAT, borderwidth=4, bg='blue')
self.demonstration_frame.pack(expand=True, fill="both")
self.demonstration_frame.grid_propagate(False)
for k in range(4):
self.demonstration_frame.grid_rowconfigure(k, weight=1, uniform=1)
for i in range(6):
self.demonstration_frame.grid_columnconfigure(i, weight=1, uniform=1)
for j in range(4):
self.dummy_frame = tk.Frame(self.demonstration_frame, relief=tk.RIDGE, borderwidth=1,
bg='#' + str(int(j / 2)) + str(int(j / 2)) + str(int(j / 2))
+ str(int(i / 2)) + str(int(i / 2)) + str(int(i / 2)))
self.dummy_frame.grid(row=j, column=i, sticky='nsew')
root = tk.Tk()
my_gui = TestInterface(root)
root.mainloop()

我有一个演示框架,每次点击按钮都是从头开始重新形成的,所以我们知道每次都是以相同的方式创建的。虚设框架只是为了弄清楚发生了什么。self.button1((和self.button 2((之间的唯一区别是删除了";columnspan=2;

我希望这些网格线锁定在适当的位置(我对文本不可见/脱离框架很满意(。有人能解释一下columnspan为什么要在这里改变grid_proppositive((的行为吗?

edit:这是没有演示frame.destroy方法的代码。它的行为方式完全相同。

import tkinter as tk

class TestInterface:
def __init__(self, master):
self.master = master
self.master.title("Interface Template")
self.master.configure(bg='#000000', relief=tk.RIDGE, borderwidth=16)
self.master.attributes('-fullscreen', True)
self.demonstration_frame = tk.Frame(master=self.master, relief=tk.FLAT, borderwidth=4, bg='blue')
self.demonstration_frame.pack(expand=True, fill="both")
self.demonstration_frame.grid_propagate(False)
for k in range(4):
self.demonstration_frame.grid_rowconfigure(k, weight=1, uniform=1)
for i in range(6):
self.demonstration_frame.grid_columnconfigure(i, weight=1, uniform=1)
for j in range(4):
self.dummy_frame = tk.Frame(self.demonstration_frame, relief=tk.RIDGE, borderwidth=1,
bg='#' + str(int(j / 2)) + str(int(j / 2)) + str(int(j / 2))
+ str(int(i / 2)) + str(int(i / 2)) + str(int(i / 2)))
self.dummy_frame.grid(row=j, column=i, sticky='nsew')
self.dummy_frame = tk.Frame()
self.button = tk.Button()
self.button1()
def button1(self):
self.button = tk.Button(self.demonstration_frame, text="LONG PHRASE MODIFYING THE GRID STRUCTURE", bg='#111111',
relief=tk.FLAT, fg="#FFFFFF", font=('Courier', 12), anchor='center', borderwidth=6,
command=lambda: self.button2())
self.button.grid(row=2, column=3, columnspan=2, sticky='nsew')
def button2(self):
self.button.destroy()
self.button = tk.Button(self.demonstration_frame, text="LONG PHRASE BEING CUT OFF AS INTENDED", bg='#111111',
relief=tk.FLAT, fg="#FFFFFF", font=('Courier', 12), anchor='center', borderwidth=6,
command=lambda: self.button1())
self.button.grid(row=2, column=3, sticky='nsew')

root = tk.Tk()
my_gui = TestInterface(root)
root.mainloop()

有人能解释一下columnspan为什么要在这里更改grid_propposition((的行为吗?

在本例中,columnspan不是更改grid_propagate的行为。仅关闭网格传播告诉父对象不要基于子对象进行增长或收缩。当您使用columnspan时,父帧的大小不会改变——帧保持原来的大小。改变的是内部柱的大小,这与几何体传播无关。

我以前从未见过这种行为,而且它看起来确实很不直观。然而,我认为它按设计运行。

网格算法的规范文档从以下内容开始:

";要计算布局的最小大小,网格几何图形管理器首先查看列跨度和行跨度值为一的所有内容,并计算每行或每列的标称大小,使其为该行或该列的最小大小或填充加上最大内容的大小之和,以较大者为准。之后,每个统一组中的行或列相互适应">

在算法的这一点上,示例中的行和列都应该具有相同的宽度和高度。到目前为止,一切都很好。

然后,文档说明了当小部件跨越两行或多列时会发生什么:

";然后检查行跨度或列跨度大于1的内容。如果一组行或列的大小需要增加以容纳这些内容,则会根据其权重为组中的每一行或列添加额外的空间。对于每一个权重都为零的组,额外的空间被平均分配">

这似乎正好描述了您所看到的内容:在第3列和第4列中添加了额外的空间,以便按钮能够容纳。

我的猜测是,你可以把按钮放在一个没有宽度和高度的帧中,然后关闭该帧中的几何体传播。请确保使用使按钮填充框架的选项。然后,您可以将该框架放置在当前放置按钮的位置,横跨两列。由于帧将具有1x1的请求大小,因此不会导致列增长。

最新更新