I've found multiple proposed solutions to this issue, but all variations on the function proposed below either don't work or result in errors when applied to my code. As noted, I want my elements in the canvas frame to expand left & right, the issue appears to be with the canvas_configure()
function. This is a minimised version of the script I am using:
from tkinter import *
# Master frame
app = Tk()
app.columnconfigure(0, weight=1)
app.rowconfigure(0, weight=1)
def load_files():
# Do stuff which gives list of company names
companies_list = [x for x in range(0, 30)]
# Generates Tkinter elements
y = 0
for x in companies_list:
y = 1
old_co = Entry(frame)
old_co.insert(0, x)
old_co.grid(row=y, column=0, sticky=E W)
new_co = Entry(frame)
new_co.grid(row=y, column=1, sticky=E W)
prefix = Entry(frame)
prefix.grid(row=y, column=2, sticky=E W)
# Sub-Frame
company_header_frame = LabelFrame(app, text='Company Name')
company_header_frame.grid(row=0, column=0, sticky=N S E W)
company_header_frame.columnconfigure(0, weight=1)
company_header_frame.rowconfigure(0, weight=1)
# Canvas
canvas = Canvas(company_header_frame, height=100)
canvas.grid(row=0, column=0, sticky=N S E W)
# Canvas Frame
frame = Frame(canvas)
canvas.create_window((0, 0), window=frame, anchor='nw')
# Sidebar
scroll_y = Scrollbar(company_header_frame, orient="vertical")
scroll_y.grid(row=0, column=1, sticky=N S)
scroll_y.config(command=canvas.yview)
def canvas_configure(event):
canvas_width = event.width
event.itemconfig(frame, width=canvas_width)
def config_frame(_):
canvas.configure(scrollregion=canvas.bbox('all'), yscrollcommand=scroll_y.set)
canvas.bind('<Configure>', canvas_configure)
frame.bind('<Configure>', config_frame)
load_files()
app.mainloop()
This results in the following error:
AttributeError: 'Event' object has no attribute 'itemconfig'
I attempted adjusting the function to use .winfo_width()
in place of width
, replacing event with the actual canvas, but similar attribute errors result relating to either width or itemconfig. Any advise would be much appreciated.
CodePudding user response:
The error is telling you exactly what is wrong: an Event
object doesn't have an itemconfig
method. The canvas widget does, however, and the Event
object can give you the canvas widget:
def canvas_configure(event):
canvas_width = event.width
event.widget.itemconfig(frame, width=canvas_width)
# ^^^^^^^
Unrelated to the specific question that was asked, you also need to pass a valid item id to itemconfig
-- you can't pass the frame itself.
You either need to save the value returned from create_window
or you need to give the window a tag.
For example:
canvas.create_window(..., tags=("inner_frame",))
...
def canvas_configure(event):
canvas_width = event.width
event.widget.itemconfigure("inner_frame", width=canvas_width)