Wes Tomer
Wes Tomer

Reputation: 329

Can't force Tkinter GUI column width

I'm coding a GUI for inputting parameters, images and text all associated with a particular step (One single row per step) and then outputting it as JavaScript code to be used in another program. But this is beside my point:

I am having trouble forcing the column widths. It seems that both canv_1.grid_columnconfigure(6, weight=2) and canv_1.grid_columnconfigure(1, weight=0) do nothing. I'm trying to keep the width of the column 2nd from the left to a minimum. And I want column 6 to be twice as wide as the others.

import tkinter as tk
from tkinter import simpledialog,filedialog,colorchooser,messagebox,Frame,Button
from PIL import ImageTk, Image
import textwrap

root = tk.Tk()

load1 = Image.open("example.jpg")
root.render1 = ImageTk.PhotoImage(load1)

canv_1 = tk.Canvas(root, bg="gray")
canv_1.grid_rowconfigure(0, weight=1)
canv_1.grid_columnconfigure(6, weight=2)
canv_1.grid_columnconfigure(2, weight=0)

canv_1.grid(row=0, column=0, sticky="news")
canv_1.grid(row=1, column=0, sticky="news")

labels = ["Image", "Chapter #", "Chapter Title", "Step", "Slide", "Sequence Step", "Instructions"]
root.label_wid = []
font1 = ("arial", 15, "bold")

ch_text = []
def exportCode():
    # Gather text input for each chapter
    for i in range(0,5):
        # Get the text (unwrapped) from a single input cell:
        a_temp = instruction_col[i].get('1.0','10.0')
        # Wrap the text at 54 characters, then append it to the list ch_text
        ch_text.append(textwrap.wrap(a_temp,54))
    # Create a new file
    f = open("demofile2.js", "w")
    # For each chapter
    for i in range(1,5):
        # Write to this file line by line
        #
        # stepID = str()
        # stepHeading = "if(place==\""
        for j in range(1,11):
            tnum = str(j)
            nline1st = "        scopeSet(\"T"+tnum+"\",\"text\",\""
            if (len(ch_text[i-1])<j):
                nline2nd = ""
            else:
                nline2nd = ch_text[i-1][j-1]
            f.write(nline1st+nline2nd+"\")\n")
    f.close()
    print("Code exported.")
for i in range(len(labels)):
    root.label_wid.append(tk.Label(canv_1, font=font1, relief="raised", text=labels[i]).grid(row=0, column=i, sticky="we"))


root.images = [
    ImageTk.PhotoImage(Image.open("example.jpg"))
    for y in range(1,6)
]

def change_img(y):
    #print(y)
    #print(len(root.images))
    root.img1 = filedialog.askopenfilename()
    root.load_img1 = Image.open(root.img1)
    root.render_img1 = ImageTk.PhotoImage(root.load_img1)
    image_col[y]['image'] = root.render_img1
    print(image_col[y]['image'])
    print(image_col[y-1]['image'])
    print(root.render_img1)

c1 = "#a9d08e"
c2 = "#8dd1bf"

image_col = [
    tk.Button(
        canv_1,
        image=root.render1,
        relief="raised",
        bg="light gray",
        command = lambda y=y: change_img(y),
    )
    for y in range(0, 5)
]

ChNum_col = [
    tk.Entry(
        canv_1,
        bg = c1,
        font = ("arial", 15))
    for y in range(0, 5)
]

Title_col = [
    tk.Entry(
        canv_1,
        bg = c1,
        font = ("arial", 15))
    for y in range(0, 5)
]

Step_col = [
    tk.Entry(
        canv_1,
        bg = c1,
        font = ("arial", 15))
    for y in range(0, 5)
]

Slide_col = [
    tk.Entry(
        canv_1,
        bg = c2,
        font = ("arial", 15))
    for y in range(0, 5)
]

SeqS_col = [
    tk.Entry(
        canv_1,
        bg = c2,
        font = ("arial", 15))
    for y in range(0, 5)
]

instruction_col = [
    tk.Text(
        canv_1,
        bg="white",
        wrap="word",
        font=("arial",15), width=20, height=10)
    for y in range(0, 5)
]
example_text_1 = "The purpose of this app is for the user to select an image and designate the associated parameters and text before exporting it as a JavaScript file to be used in a separate program."
example_text_2 = " Here is another example of text that might be used. This can be used for a specific chapter to test this code. It's getting closer to being ready for use"
instruction_col[0].insert(1.0,example_text_1)
instruction_col[1].insert(1.0,example_text_2)

# for y, image_cell in enumerate(image_col, 1):
#     image_cell.grid(row=y, column=0, sticky='news')
# for y, image_cell in enumerate(instruction_col, 1):
#     image_cell.grid(row=y, column=6, sticky='news')
# above is same as below
for y in range(0,5):
    image_col[y].grid(row=y + 1, column=0, sticky='news')
    ChNum_col[y].grid(row=y + 1, column=1, sticky='news')
    Title_col[y].grid(row=y + 1, column=2, sticky='news')
    Step_col[y].grid(row=y + 1, column=3, sticky='news')
    Slide_col[y].grid(row=y + 1, column=4, sticky='news')
    SeqS_col[y].grid(row=y + 1, column=5, sticky='news')
    instruction_col[y].grid(row=y+1, column=6, sticky='news')


# ================================================================================================

bt1 = tk.Button(canv_1, text="Export", font=font1, command=exportCode).grid(row=0, column=7)
load2 = Image.open("scroll-up.png")
root.render2 = ImageTk.PhotoImage(load2)
load3 = Image.open("scroll-down.png")
root.render3 = ImageTk.PhotoImage(load3)
scroll_up = tk.Button(canv_1, image=root.render2).grid(row=1, column=7, rowspan=2)  # , sticky="n")
scroll_up = tk.Button(canv_1, image=root.render3).grid(row=3, column=7, rowspan=2)  # , sticky="s")

root.mainloop()

enter image description here

Upvotes: 0

Views: 285

Answers (2)

Space
Space

Reputation: 142

First

As mentioned by

@jizhihaoSAMA

width must be set.

I configured all Entry widths as width = 1, that seemed to shrink the column the to minimum width that matches the width of the accompanying Label above it.

Second

In addition to weight, it seems you need uniform = 999 (or any number / string) that will identify the column as part of a group that will proportion the width according to weight = 1, wieght = 2 per respective column.

In the modified script I made column 7 as 5 times the width of column 1

import tkinter as tk
from tkinter import simpledialog,filedialog,colorchooser,messagebox,Frame,Button,PhotoImage
#from PIL import ImageTk, Image
import textwrap

root = tk.Tk()

#load1 = Image.open("example.jpg")
root.render1 = PhotoImage(file="yes.png")

canv_1 = tk.Canvas(root, bg="red")
## Here uniform = ... must be set ##
canv_1.grid_rowconfigure(0, weight=1,uniform = 999)
canv_1.grid_columnconfigure(6, weight=5, uniform = 999)
canv_1.grid_columnconfigure(2, weight=0, uniform = 999)

canv_1.grid(row=0, column=0, sticky="news")
canv_1.grid(row=1, column=0, sticky="news")

labels = ["Image", "Chapter #", "Chapter Title", "Step", "Slide", "Sequence Step", "Instructions"]
root.label_wid = []
font1 = ("arial", 15, "bold")

ch_text = []
def exportCode():
    # Gather text input for each chapter
    for i in range(0,5):
        # Get the text (unwrapped) from a single input cell:
        a_temp = instruction_col[i].get('1.0','10.0')
        # Wrap the text at 54 characters, then append it to the list ch_text
        ch_text.append(textwrap.wrap(a_temp,54))
    # Create a new file
    #f = open("demofile2.js", "w")
    # For each chapter
    for i in range(1,5):
        # Write to this file line by line
        #
        # stepID = str()
        # stepHeading = "if(place==\""
        for j in range(1,11):
            tnum = str(j)
            nline1st = "        scopeSet(\"T"+tnum+"\",\"text\",\""
            if (len(ch_text[i-1])<j):
                nline2nd = ""
            else:
                nline2nd = ch_text[i-1][j-1]
            #f.write(nline1st+nline2nd+"\")\n")
    #f.close()
    print("Code exported.")
for i in range(len(labels)):
    tmp = tk.Label(canv_1, font=font1, relief="raised", text=labels[i])
    tmp.grid(row=0, column=i, sticky="we")
    root.label_wid.append(tmp)
print(root.label_wid[0].winfo_reqwidth())
root.images = [PhotoImage(file="yes.png") for y in range(1,6)]

def change_img(y):
    #print(y)
    #print(len(root.images))
    root.img1 = filedialog.askopenfilename()
    root.load_img1 = Image.open(root.img1)
    root.render_img1 = PhotoImage(root.load_img1)
    image_col[y]['image'] = root.render_img1
    print(image_col[y]['image'])
    print(image_col[y-1]['image'])
    print(root.render_img1)

c1 = "#a9d08e"
c2 = "#8dd1bf"

image_col = [ tk.Button(canv_1, image=root.render1,relief="raised",bg="light gray",command = lambda y=y: change_img(y),width = 1) for y in range(0, 5) ]

ChNum_col = [tk.Entry(canv_1,bg = c1,font = ("arial", 15),width = 1) for y in range(0, 5) ]

Title_col = [tk.Entry(canv_1,bg = c1,font = ("arial", 15),width = 1) for y in range(0, 5) ]

Step_col = [tk.Entry(canv_1,bg = c1,font = ("arial", 15),width = 1) for y in range(0, 5)]

Slide_col = [tk.Entry( canv_1, bg = c2,font = ("arial", 15),width = 1) for y in range(0, 5)]

SeqS_col = [tk.Entry(canv_1,bg = c2,font = ("arial", 15),width = 1) for y in range(0, 5)]

instruction_col = [ tk.Text(  canv_1, bg="white",wrap="word", font=("arial",15), width=5, height=10) for y in range(0, 5)
]
example_text_1 = "The purpose of this app is for the user to select an image and designate the associated parameters and text before exporting it as a JavaScript file to be used in a separate program."
example_text_2 = " Here is another example of text that might be used. This can be used for a specific chapter to test this code. It's getting closer to being ready for use"
instruction_col[0].insert(1.0,example_text_1)
instruction_col[1].insert(1.0,example_text_2)

# for y, image_cell in enumerate(image_col, 1):
#     image_cell.grid(row=y, column=0, sticky='news')
# for y, image_cell in enumerate(instruction_col, 1):
#     image_cell.grid(row=y, column=6, sticky='news')
# above is same as below
for y in range(0,5):
    image_col[y].grid(row=y + 1, column=0, sticky='news')
    ChNum_col[y].grid(row=y + 1, column=1, sticky='news')
    Title_col[y].grid(row=y + 1, column=2, sticky='news')
    Step_col[y].grid(row=y + 1, column=3, sticky='news')
    Slide_col[y].grid(row=y + 1, column=4, sticky='news')
    SeqS_col[y].grid(row=y + 1, column=5, sticky='news')
    instruction_col[y].grid(row=y+1, column=6, sticky='news')


# ================================================================================================

bt1 = tk.Button(canv_1, text="Export", font=font1, command=exportCode).grid(row=0, column=7)
#load2 = Image.open("scroll-up.png")
root.render2 = PhotoImage(file="yes.png")
#load3 = Image.open("scroll-down.png")
root.render3 = PhotoImage(file="yes.png")
scroll_up = tk.Button(canv_1, image=root.render2).grid(row=1, column=7, rowspan=2)  # , sticky="n")
scroll_up = tk.Button(canv_1, image=root.render3).grid(row=3, column=7, rowspan=2)  # , sticky="s")

root.mainloop()

5 times

Upvotes: 1

Wes Tomer
Wes Tomer

Reputation: 329

Use width I tried width earlier, but it didn't seem to work- possibly because I had empty columns? Now the code is working though:

ChNum_col = [
    tk.Entry(
        canv_1,
        bg = c1,
        width = 10,
        font = ("arial", 15))
    for y in range(0, 5)
]

Upvotes: 0

Related Questions