There are different ways to get widgets to align in Tkinter when using the grid()
layout-manager. For two widgets on the same row, the first could be given the sticky=E
option and the following one given sticky=W
. This will shove the two together. I've did that for the widgets in the first two rows.
Another way is to make the entire row a a nested Frame
that has all the widgets inside it. The layout inside the nested frame is independent of where the containing Frame
is positioned. I did that for the group of four widgets you have at the end.
Although it has nothing to do with alignment or layout, I also changed the display_music()
and divide()
function to be Button
callbacks (using the command=xxx
argument they accept) instead making them event-handlers attached to events by bind()
ing them to a particular widget (which means they'll no longer receive an event
argument—which you weren't using anyway).
from tkinter import *# Button callbacks (which are NOT event handlers)def display_music(): music = favoriteMusician.get() outputEntry.delete(0, 'end') outputEntry.insert(0, 'Your favorite musician is %s' % music)def divide(): answer = str(int(num1Entry.get())/int(num2Entry.get())) divideEntry.delete(0, 'end') divideEntry.insert(0, answer)root = Tk()# Row 0label1 = Label(root, text='Who is your favorite musician?')label1.grid(row=0, column=0, sticky=E)favoriteMusician = Entry(root)favoriteMusician.grid(row=0, column=1, sticky=W)# Row 1b1 = Button(root, text='Output:', command=display_music)b1.grid(row=1, column=0, sticky=E)#b1.bind('<Button-1>', display_music)outputEntry = Entry(root, width=30)#outputEntry.grid(row=1, column=1, columnspan=2, sticky=W)outputEntry.grid(row=1, column=1, sticky=W)# Row 2mathFrame = Frame(root)mathFrame.grid(row=2, column=0, columnspan=4)num1Entry = Entry(mathFrame)num1Entry.grid(row=2, column=0, sticky=W)label2 = Label(mathFrame, text='/')label2.grid(row=2, column=1, sticky=W)num2Entry = Entry(mathFrame)num2Entry.grid(row=2, column=2, sticky=W)b2 = Button(mathFrame, text='=', command=divide)b2.grid(row=2, column=3, sticky=W)#b2.bind('<Button-1>', divide)divideEntry = Entry(mathFrame)divideEntry.grid(row=2, column=4, sticky=W)root.mainloop()
Here's what it looks like running:
Here's a couple of links to relevant Tkinter articles:
The Tkinter Grid Geometry Manager by Fredrik Lundh (author of Tkinter)
Tkinter 8.5 reference: a GUI for Python by John Shipman (New Mexico Tech Computer Center)