Tkinter Grid – Set Default Grid Size

When placing widgets (text boxes, buttons, etc.) in your user interface using Grid there will not be any whitespace between your widgets that are seperated by empty columns or rows by default unless you explicitly give weight to the empty rows or columns between your widgets. The empty cells in the grid do exist but Grid considers them to not matter because they do not contain any widgets or have a weight, because of that they will not display until they do.

On the surface it might sound like a complex problem that requires a lot of extra code if you have a UI that consists of more than 2 rows and 2 columns, but there is an elegant way to solve this. The easiest way for me is to define every single row and column in my frame when it is defined, then i can know when I am placing my widgets several rows or columns apart how much empty space will occupy between them.

In a previous post I showed how to create a blank window The code from that is below and is what I will add to for this demo.

#!/usr/bin/python
from Tkinter import *


main = Tk()
main.title('My cool new window!')  
main.geometry('500x500')  


main.mainloop()
Base Code

Right now if we place a button using Grid in column 1 and another in  column 5, they will appear right next to each other as shown below

#!/usr/bin/python
from Tkinter import *


main = Tk()
main.title('My cool new window!')
main.geometry('500x500')

# defines Button 1 and places it using grid
button1 = Button(main, text='Button 1')
button1.grid(row=1, column=1)

# defines Button 2 and places it using grid
button2 = Button(main, text='Button 2')
button2.grid(row=1, column=5)


main.mainloop()
Adding Buttons

There should be some whitespace between those buttons as I placed Button 1 in column 1 and Button 2 in column 5. The reason there is none is because we have not defined that cells that are not used still need to occupy space, to do this we need to assign a weight to the empty cells which is not 0, you could do this by adding a weight to each cell individually but that would require a line of code for each cell you want to give weight to. I like to give weight to the entire grid right away which only takes 5 lines of code using a while loop. in this example i will create the grid 50 rows x 50 columns. we will do this by using ‘rowconfigure’ and ‘columnconfigure’, below is the updated code and the resulting window from running that code

#!/usr/bin/python
from Tkinter import *


main = Tk()
main.title('My cool new window!')
main.geometry('500x500')

# creates a grid 50 x 50 in the main window
rows = 0
while rows < 50:
    main.rowconfigure(rows, weight=1)
    main.columnconfigure(rows,weight=1)
    rows += 1

# defines Button 1 and places it using grid
button1 = Button(main, text='Button 1')
button1.grid(row=1, column=1)

# defines Button 2 and places it using grid
button2 = Button(main, text='Button 2')
button2.grid(row=1, column=5)


main.mainloop()
Configuring Grid

As you can see we now have our whitespace showing because the highlighted text above is giving a weight to each cell in a 50×50 grid. so if we placed button 2 in column 50 it would show up on the opposite side of button 1.

Now if your not familiar with programing a GUI in Python you may wonder if the while loop needs to be before the buttons are declared and gridded out. The answer is no because all of that code is running in ‘main.mainloop()’ so as long as the while loop is between ‘main = Tk()’ and ‘main.mainloop()’ it will grid out all of the cells within the frame as you would expect even if the buttons are already defined and placed in a cell within that 50×50 grid.

2 Comments

  1. What if I want to make the Grid smaller after declaring it to be a certain size earlier in my program?
    In my situation, I have a grid thats 6×2, then when I destroy all the widgets using winfo_Children() and draw new buttons to the screen that only take up a 4×1 space, I notice that the grid does not resize to 4×1, but remains the same 6×2 grid. so when i drag the edge of the window to expand the view, the widgets which i want to be expanding symmetrically across the page are offset to the left side slightly. This is most noticeable if i set their background colors different than the frame background so when using columnconfigure and sticky’news’ together, the 6×2 frame will appear uniformly colored while the 4×1 will have white to the bottom and right of the buttons.

    • If you want to be able to dynamically change your grid size I would suggest putting that code into a function and when you define your grid or redefine your grid just call that function and pass in the parameters for the dimensions. Just make sure when you draw your new widgets after redefining your grid size you account for the different grid dimensions

      def define_grid(width, height):
           rows = 0
           columns = 0
           while rows < height:
                main.rowconfigure(rows, weight=1)
                rows += 1

           while columns < width:
                main.columnconfigure(columns, weight=1)
                columns += 1

2 Trackbacks / Pingbacks

  1. Tkinter Grid - Create Whitespace Between Widgets - Kyle Kowalczyk
  2. Tkinter Grid - Adding a Button - Kyle Kowalczyk

Leave a Reply

Your email address will not be published.


*