0

I am trying to use the TTK Treeview object to display varying data that require different columns/column names, for some reason when looping through the list of column headings I have created I can never get more than the first and last heading regardless of the numbers although 2 will work.

I have tried adding a sleep section encase it was to create the column to quickly before the heading, I have tried removing the list completely and just trying to create 4 headings in a loop and still the same result.

The treeview object stores the columns in a tuples tree2["columns"] which I print out at the end to verify all the headings references are stored, see example code below.

import tkinter as tk
from tkinter import ttk

headings = ["Heading0", "Heading1", "Heading2", "Heading3"]

root = tk.Tk()
root.title("Add headings")

frame1 = tk.Frame(root)
frame1.pack()

tree = ttk.Treeview(frame1)
tree["columns"] = ("C1", "C2")
tree.column("#0", width=500, minwidth=400, stretch=tk.NO)
tree.column("C1", width=200, minwidth=200, stretch=tk.NO)
tree.column("C2", width=200, minwidth=200, stretch=tk.NO)
tree.heading("#0", text="Name", anchor=tk.W)
tree.heading("C1", text="Type", anchor=tk.W)
tree.heading("C2", text="Index", anchor=tk.W)
print(tree["columns"])

t = {}

for i in range(5):
    t[i] = tree.insert("", i, text="Example " + str(i), values=("val1", "val2"))
tree.pack(expand=True, fill="both")

def create():
    for i, val in enumerate(headings):
        if i == 0:
            tree2.column("#0", width=200, minwidth=200, stretch=tk.NO)
            tree2.heading("#0", text=val, anchor=tk.W)
        elif i == 1:
            tree2["columns"] = tree2["columns"] + ("C1")
            tree2.column("C1", width=800, minwidth=200, stretch=tk.NO)
            tree2.heading("C1", text=val[1], anchor=tk.W)
        else:
            tree2["columns"] = tree2["columns"] + ("C" + str(i),)
            tree2.column("C" + str(i), width=800, minwidth=200, stretch=tk.NO)
            tree2.heading("C" + str(i), text=val, anchor=tk.W)
        print(val)
    print(tree2["columns"])


btn1 = tk.Button(frame1, text="Add", command=create)
btn1.pack(side="top")

tree2 = ttk.Treeview(frame1)


tree2.pack(expand=True, fill="both")

root.mainloop()

here's an example:

Example

The question here adding multiple columns to a treeview demonstrates an issue with getting the correct number of columns but does not give the explicit answer below of calling columns prior to the headings to ensure they are displayed.

6
  • 3
    first create all columns tree2["columns"] = tuple(f"C{i}" for i in range(1, len(headings))) Commented Jan 24, 2020 at 14:27
  • To add onto this you should also config your columns first. I'll post a working example. Commented Jan 24, 2020 at 14:34
  • Does this answer your question? Tkinter - Adding multiple columns to a Treeview Commented Jan 24, 2020 at 14:41
  • @stovfl im not sure this question explicitly answer this question directly however it does accidentally demonstrate the principals of the answer below, i don't know think i would of figured out this from that question though. Commented Jan 24, 2020 at 14:53
  • Feel free, not to agree that it truly is a duplicate, read Why are some questions marked as duplicate? Commented Jan 24, 2020 at 14:57

1 Answer 1

3

Here's the example I mentioned in the comments. This could be formatted better but I'm simply adding onto your code to show how it works. Additionally, there was a bug where you were continuously building onto your tuple with each function call.

import tkinter as tk
from tkinter import ttk

headings = ["Heading0", "Heading1", "Heading2", "Heading3"]

root = tk.Tk()
root.title("Add headings")

frame1 = tk.Frame(root)
frame1.pack()

tree = ttk.Treeview(frame1)
tree["columns"] = ("C1", "C2")
tree.column("#0", width=500, minwidth=400, stretch=tk.NO)
tree.column("C1", width=200, minwidth=200, stretch=tk.NO)
tree.column("C2", width=200, minwidth=200, stretch=tk.NO)
tree.heading("#0", text="Name", anchor=tk.W)
tree.heading("C1", text="Type", anchor=tk.W)
tree.heading("C2", text="Index", anchor=tk.W)

t = {}

for i in range(5):
    t[i] = tree.insert("", i, text="Example " + str(i), values=("val1", "val2"))
tree.pack(expand=True, fill="both")

def create():
    for i, val in enumerate(headings):
        if i == 0:
            tree2.column("#0", width=200, minwidth=200, stretch=tk.NO)
        elif i == 1:
            tree2["columns"] = ("C1", )
            tree2.column("C1", width=800, minwidth=200, stretch=tk.NO)
        else:
            tree2["columns"] = tree2["columns"] + ("C" + str(i), )
            tree2.column("C" + str(i), width=800, minwidth=200, stretch=tk.NO)

    for i, val in enumerate(headings):
        if i == 0:
            tree2.heading("#0", text=val, anchor=tk.W)
        elif i == 1:
            tree2.heading("C1", text=val, anchor=tk.W)
        else:
            tree2.heading("C" + str(i), text=val, anchor=tk.W)


btn1 = tk.Button(frame1, text="Add", command=create)
btn1.pack(side="top")

tree2 = ttk.Treeview(frame1)


tree2.pack(expand=True, fill="both")

root.mainloop()
Sign up to request clarification or add additional context in comments.

1 Comment

Thank you Axe319 and @furas both your suggestions work and i now understand that you must setup the columns first, my formatting is that of a program re-arranged six dozen times in the last hour i do apologize although do we know why this occurs in the first place?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.