Tkinter 小部件上的垂直和水平滚动条

Posted

技术标签:

【中文标题】Tkinter 小部件上的垂直和水平滚动条【英文标题】:Vertical and Horizontal Scrollbars on Tkinter Widget 【发布时间】:2012-03-22 14:14:21 【问题描述】:

我正在尝试将数据库的内容输出到 Tkinter 小部件。数据库有足够的行和列,我需要同时启用水平和垂直滚动条,但我很难让水平和垂直滚动同时工作。我不知道使用了哪个 Tkinter 小部件,但这是我当前的实现:

# Create root
self.root = Tk()
self.root.geometry('1000x500+0+0')

# Create canvas
self.canvas = Canvas(self.root)
self.canvas.pack(side=TOP, fill=BOTH, expand=TRUE)

# Create scrollbars
self.xscrollbar = Scrollbar(self.root, orient=HORIZONTAL, command=self.canvas.xview)
self.xscrollbar.pack(side=BOTTOM, fill=X)
self.yscrollbar = Scrollbar(self.root, orient=VERTICAL, command=self.canvas.yview)
self.yscrollbar.pack(side=RIGHT, fill=Y)

# Attach canvas to scrollbars
self.canvas.configure(xscrollcommand=self.xscrollbar.set)
self.canvas.configure(yscrollcommand=self.yscrollbar.set)

# Create frame inside canvas
self.frame = Frame(self.canvas)
self.canvas.create_window((0,0), window=self.frame, anchor=NW)
self.frame.bind('<Configure>', self.set_scrollregion)

# Write db contents to canvas
self.print_dbcontents()

# Invoke main loop
self.root.mainloop()

def set_scrollregion(self, event):
    self.canvas.configure(scrollregion=self.canvas.bbox('all'))

在这个实现中,我只能在一个方向上滚动,这取决于我如何打包画布:

self.canvas.pack(side=TOP, fill=BOTH, expand=TRUE) # scrolling works in x but not y
self.canvas.pack(side=LEFT, fill=BOTH, expand=TRUE) # scrolling works in y but not x

我只需要让水平和垂直滚动同时工作,或者找到替代解决方案。

【问题讨论】:

教程中的 Scrolling example 按预期工作(应针对 Python 2.x 修改导入)。 【参考方案1】:

我没有看到任何会阻止滚动条工作的代码。我确实看到了一个问题,它阻止滚动条之一出现在您期望的位置(假设您希望它们出现在传统位置)。当您说您希望它们“同时工作”时,这就是您的意思吗?

您的布局是使用以下代码并按以下顺序完成的:

self.canvas.pack(side=TOP, fill=BOTH, expand=TRUE)
self.xscrollbar.pack(side=BOTTOM, fill=X)
self.yscrollbar.pack(side=RIGHT, fill=Y)

第一行使画布填满小部件的整个顶部,从左到右。当您稍后将 yscrollbar 放在右侧时,这意味着它会在画布填满顶部后 移动到剩余空间的右侧。由于画布填充了顶部,因此右侧没有剩余空间,只有下方。因此,您的滚动条将显示为一个关于画布下方水平滚动条高度的小部件。

一个快速的解决方法是先打包垂直滚动条,然后是水平滚动条,然后是然后画布。您的“主要”小部件应该始终是您打包/网格的最后一件事。一,您这样做的原因很明显,在这种情况下您需要获得预期的效果,而且还因为它使您的调整大小行为正确。我要在这个答案中解释原因,所以请阅读 this answer on *** 了解更多信息。

其次,在使用滚动条时,如果您想要专业的外观,最好使用网格。如果您使用 pack,滚动条将不会在它们相遇的角落对齐属性。您希望它们看起来像这样,在右下角有一个小空白:

  ||
==

但是,如果您使用 pack,它们将看起来像以下之一:

   ||    -or-      ||
 ====            ==||

最后,我鼓励你不要 import *,这可能会导致问题。相反,养成使用import Tkinter as tk 的习惯,然后在所有 tk 命令前加上“tk”。 (例如:tk.Canvas 等)。当你第一次尝试在同一个 UI 中混合 ttk 和 tkinter 小部件时,你会明白为什么这很重要,但如果你也从其他包中“导入 *”,你可能会在其他地方遇到问题。另外,当您使用 tk 功能以及使用其他包中的功能时,这种方式很明显。

【讨论】:

以上是关于Tkinter 小部件上的垂直和水平滚动条的主要内容,如果未能解决你的问题,请参考以下文章

在 Tkinter 中为一组小部件添加滚动条

如何在小部件中添加垂直滚动条?

修复了带有水平滚动条和垂直滚动条的标题表

CSS 如何添加水平滚动条

tkinter学习-滚动条

在Tkinter中调整滚动条高度?