我使用过 AutoScrollbar (http://effbot.org/zone/tkinter-autoscrollbar.htm),并添加了一个水平的。
from Tkconstants import VERTICAL, N, S, HORIZONTAL, W, E, END
import Tkinter as Tk
class AutoScrollbar(Tk.Scrollbar):
""" a scrollbar that hides itself if it's not needed. only
works if you use the grid geometry manager."""
def set(self, lo, hi):
if float(lo) <= 0.0 and float(hi) >= 1.0:
# grid_remove is currently missing from Tkinter!
self.tk.call("grid", "remove", self)
else:
self.grid()
Tk.Scrollbar.set(self, lo, hi)
def pack(self, **kw):
raise Tk.TclError, "cannot use pack with this widget"
def place(self, **kw):
raise Tk.TclError, "cannot use place with this widget"
if __name__ == '__main__':
root = Tk.Tk()
scrollbarY = AutoScrollbar(root,orient=VERTICAL)
scrollbarY.grid(column=1, row=0,sticky=N+S)
scrollbarX = AutoScrollbar(root,orient=HORIZONTAL)
scrollbarX.grid(column=0, row=1,sticky=W+E)
mylist = Tk.Listbox(root, xscrollcommand = scrollbarX.set, yscrollcommand = scrollbarY.set )
for line in range(50):
mylist.insert(END, "This is line number " + str(line) + ", and then just for whatever reason this text goes on and on")
mylist.grid(column=0, row=0,sticky=N+S+E+W)
scrollbarX.config( command = mylist.xview )
scrollbarY.config( command = mylist.yview )
root.columnconfigure(0, weight=1)
root.rowconfigure(0, weight=1)
Tk.mainloop()
现在我想:拥有这个功能而不是杂乱无章不是很有趣吗?所以我开始编写带有自动隐藏滚动条的 tk.Frame。想法是:您向 AutoscrollFrame 添加一个小部件,Atuoscrollframe 在内部将该小部件放置在 2x2 网格上的 (0,0) 处,其中 (0,1) 和 (1,0) 是 x- 和 y- 自动隐藏滚动条和(1,1) 留空。滚动条当然只有在需要时才可见。
现在这个想法在我脑海中似乎很容易实现。可悲的是,我很快就发现它不是。我必须重写什么方法来实现“将子小部件添加到框架”功能(通常不将小部件添加到框架而是添加到(0,0)网格位置,并且还使用小部件注册滚动条)?
到目前为止,我的代码如下所示:
import Tkinter as tk
from Tkconstants import VERTICAL, N, S, HORIZONTAL, W, E, END
class AutoscrollFrame(tk.Frame):
"""A Frame extension that automatically adds scrollbars
if the content of the frame exceeds it's dimensions.
"""
def __init__(self,master,*args,**kwargs):
self.master = master
super(AutoscrollFrame,self).__init__(master=master,*args,**kwargs)
self.scrollbarY = _AutoScrollbar(self,orient=VERTICAL)
self.scrollbarY.grid(column=1, row=0,sticky=N+S)
self.scrollbarX = _AutoScrollbar(self,orient=HORIZONTAL)
self.scrollbarX.grid(column=0, row=1,sticky=W+E)
self.columnconfigure(0, weight=1)
self.rowconfigure(0, weight=1)
def add_child_placeholder(self,child):
self.child = child
self.child.config(xscrollcommand=scrollbarX.set, yscrollcommand=scrollbarY.set )
self.child.grid(column=0, row=0,sticky=N+S+E+W)
self.scrollbarX.config( command = self.child.xview )
self.scrollbarY.config( command = self.child.yview )
这add_child_placeholder
是发生这种情况时我想调用的方法的原型:
frame = AutoscrollFrame(root)
myList = tk.Listbox(frame)
这意味着如果我将框架设置为另一个小部件的主控,我想调用框架add_child_placeholder
方法。这是一种明智的做法吗?我不完全确定这不是脑残,因此将不胜感激。
PS:我想将此功能添加到 tk.Frame(而不是 tk.ListBox),因为我还不确定 Listbox 是否是我最终会使用的。