python - tkinter 滚动区域不更新
问题描述
我试图让滚动条在我的 tkinter 应用程序中使用上一篇文章:在 Tkinter 中向一组小部件添加滚动条。如果我在 for 循环之前取消注释代码,一切都可以正常工作,但据我(有限)理解,我相信如果我取消注释 for 循环内的代码,它也应该工作。据我了解,调用canvas.configure(scrollregion=canvas.bbox("all"))
应该更新画布的滚动区域以包含放置在框架内的所有标签小部件。第一个只是在每次将新标签小部件添加到框架时自动执行,frame.bind("<Configure>",onFrameConfigure)
而第二个手动执行,那么有什么区别?为什么它不起作用?
import tkinter
root = tkinter.Tk()
canvas = tkinter.Canvas(root)
frame = tkinter.Frame(canvas)
scrollbar=tkinter.Scrollbar(root,orient="vertical",command=canvas.yview)
canvas.configure(yscrollcommand=scrollbar.set)
scrollbar.pack(side="right", fill="y")
canvas.pack(fill="both", expand=True)
canvas.create_window((0, 0), window=frame, anchor="nw")
# works
#def onFrameConfigure(event):
# canvas.configure(scrollregion=canvas.bbox("all"))
#
#frame.bind("<Configure>", onFrameConfigure)
for x in range(100):
new_label = tkinter.Label(frame, text="%d"%x)
new_label.pack()
# doesn't work
#canvas.configure(scrollregion=canvas.bbox("all"))
root.mainloop()
解决方案
第一个只是在每次使用 frame.bind("",onFrameConfigure) 将新标签小部件添加到框架时自动执行,而第二个手动执行,那么有什么区别?为什么它不起作用?
bbox
不同之处在于,响应事件的调用发生在框架实际绘制到屏幕上之后。在循环中调用它意味着在小部件可见并且它们的大小不确定之前调用它。
bbox
如果您在循环内调用(update_idletasks
或者可能update
,取决于平台)强制在屏幕上绘制小部件,则在循环内调用将起作用。但是,在循环完成后立即调用它会更有效,这样在添加所有小部件后才调用一次。
推荐阅读
- android - Android/Retrofit:“对象不是抽象的,也没有实现成员”
- shell - 在 BASH 中下载具有名称的多个文件的问题
- python - 将图像数组与opencv中的标量值相乘
- python - 如何根据每个元素中的子字符串过滤列表?
- go - 如何在 Go 中将字节数组转换为字符串数组?
- android - 如果我使用 Firebase 作为后端,我如何在 Android 应用程序的后端发生事件时自动发送推送通知
- c - 用于未来增长的结构末尾的填充物
- android - 如何删除相同片段之间的动画?
- android - 为什么 Android Studio 不接受这个 xml?为什么它要求我用鼠标绘制它?
- java - 从包含自定义类的 ArrayList 中删除重复元素