Quantcast
Channel: Active questions tagged row - Stack Overflow
Viewing all articles
Browse latest Browse all 447

python adding rows to gui

$
0
0

i have difficulties adding rows below each button where the "add row" button is located. My program somehow places the new rows at different locations other than directly below it.

could you please show me where my logic error is?

import tkinter as tkfrom tkinter import ttkfrom PIL import Image, ImageTkdropdown_values_dict = {}def get_identifier(tab_index, section_name, row_name):    return f"tab_{tab_index}_{section_name}_{row_name}"def store_input(entry, dropdown_menu, identifier):    input_text = entry.get()    if input_text:        dropdown_values = set(dropdown_menu['values'])  # Convert to set to remove duplicates        dropdown_values.add(input_text)        dropdown_menu['values'] = sorted(dropdown_values, key=lambda x: (isinstance(x, str), x))  # Sort values alphabetically        dropdown_menu.current(len(dropdown_menu['values']) - 1)        entry.delete(0, tk.END)        save_dropdown_values(identifier, list(dropdown_values))  # Save unique values without duplicates        update_dropdown_values_dict(identifier, list(dropdown_values))        # Ensure that the dictionary exists for the identifier        existing_dict = dropdown_values_dict.get(identifier, {})        # Update existing dictionary with new input        existing_dict[input_text] = True        dropdown_values_dict[identifier] = existing_dictdef remove_selected(dropdown_menu, identifier):    selected_index = dropdown_menu.current()    dropdown_values = list(dropdown_menu['values'])    if selected_index != -1:        del dropdown_values[selected_index]        dropdown_menu['values'] = dropdown_values        if dropdown_values:  # Check if there are still items in the menu            dropdown_menu.current(0)  # Set selection to the first item        else:            dropdown_menu.set("")  # Reset selection if no items left        save_dropdown_values(identifier, dropdown_values)        update_dropdown_values_dict(identifier, dropdown_values)        dropdown_values_dict[identifier] = dropdown_values  # Update the dictionary for the rowdef add_new_row(tab, section_index, row_num, row_name, identifier, add_button):    # Ensure correct section handling    section_offset = section_index * 8    # Find the index of the clicked row in the grid    clicked_row_index = row_num    # Update the row indices of existing rows below the clicked row    for slave in tab.grid_slaves():        info = slave.grid_info()        slave_row = int(info.get('row', 0))        if slave_row > clicked_row_index:            slave.grid(row=slave_row + 1, column=info['column'])    new_row_num = clicked_row_index + 1    # Create new widgets for the new row    text_label = tk.Label(tab, text=f"{row_name}:")    text_label.grid(row=new_row_num, column=0, padx=5, pady=5, sticky="w")    entry = tk.Entry(tab)    entry.grid(row=new_row_num, column=1, padx=5, pady=5, sticky="ew")    dropdown_var = tk.StringVar()    dropdown_menu = ttk.Combobox(tab, textvariable=dropdown_var, state="readonly")    dropdown_menu.grid(row=new_row_num, column=2, padx=5, pady=5, sticky="w")    dropdown_values = load_dropdown_values(identifier)    dropdown_menu['values'] = dropdown_values    update_dropdown_values_dict(identifier, dropdown_values)    store_button = tk.Button(tab, text="Store", command=lambda entry=entry, dropdown_menu=dropdown_menu, identifier=identifier: store_input(entry, dropdown_menu, identifier))    store_button.grid(row=new_row_num, column=3, padx=5, pady=5, sticky="w")    remove_button = tk.Button(tab, text="Remove", command=lambda dropdown_menu=dropdown_menu, identifier=identifier: remove_selected(dropdown_menu, identifier))    remove_button.grid(row=new_row_num, column=4, padx=5, pady=5, sticky="w")    # Ensure that the dictionary exists for the identifier    dropdown_values_dict.setdefault(identifier, [])    # Update the dictionary for the row    dropdown_values_dict[identifier].append(dropdown_values)def save_dropdown_values(identifier, values):    with open(f"dropdown_values_{identifier}.txt", "w") as f:        for value in values:            f.write(value +"\n")def load_dropdown_values(identifier):    try:        with open(f"dropdown_values_{identifier}.txt", "r") as f:            values = [line.strip() for line in f.readlines()]            return sorted(values, key=lambda x: (isinstance(x, str), x))  # Sort by type and value    except FileNotFoundError:        return []def update_dropdown_values_dict(identifier, values):    global dropdown_values_dict    dropdown_values_dict[identifier] = valuesdef tab_content(tab_index, tab):    sections = ["AL1", "AL2"]    # Counters to keep track of occurrences of row names    AL1_all_counter = 0    AL1_first_and_any_other_counter = 0    AL1_first_and_no_other_counter = 0    AL1_all_first_and_any_other_counter = 0    AL2_all_counter = 0    AL2_first_and_any_other_counter = 0    AL2_first_and_no_other_counter = 0    AL2_all_first_and_any_other_counter = 0    for section_index, section_name in enumerate(sections):        # Label for section name        section_label = tk.Label(tab, text=section_name)        section_label.grid(row=(section_index * 8), column=0, columnspan=5, padx=5, pady=10, sticky="w")        for i, row_name in enumerate(["ANY", "ALL", "ALL", "First and any other", "First and any other", "First and no other", "All first and any other"]):            identifier = get_identifier(tab_index, section_name, row_name)            row_num = i + (section_index * 8) + 1            # Initialize add_button as None            add_button = None            # Logic to determine which rows get an "Add Row" button            if section_name == "AL1":                if row_name == "ALL":                    AL1_all_counter += 1                    if AL1_all_counter == 2:                        add_button = tk.Button(tab, text="Add Row")                elif row_name == "First and any other":                    AL1_first_and_any_other_counter += 1                    if AL1_first_and_any_other_counter == 2:                        add_button = tk.Button(tab, text="Add Row")                elif row_name == "First and no other":                    AL1_first_and_no_other_counter += 1                    if AL1_first_and_no_other_counter == 1:                        add_button = tk.Button(tab, text="Add Row")                elif row_name == "All first and any other":                    AL1_all_first_and_any_other_counter += 1                    if AL1_all_first_and_any_other_counter == 1:                        add_button = tk.Button(tab, text="Add Row")            elif section_name == "AL2":                if row_name == "ALL":                    AL2_all_counter += 1                    if AL2_all_counter == 2:                        add_button = tk.Button(tab, text="Add Row")                elif row_name == "First and any other":                    AL2_first_and_any_other_counter += 1                    if AL2_first_and_any_other_counter == 2:                        add_button = tk.Button(tab, text="Add Row")                elif row_name == "First and no other":                    AL2_first_and_no_other_counter += 1                    if AL2_first_and_no_other_counter == 1:                        add_button = tk.Button(tab, text="Add Row")                elif row_name == "All first and any other":                    AL2_all_first_and_any_other_counter += 1                    if AL2_all_first_and_any_other_counter == 1:                        add_button = tk.Button(tab, text="Add Row")            if add_button:                add_button.config(command=lambda row_num=row_num, row_name=row_name, add_button=add_button: add_new_row(tab, section_index, row_num, row_name, identifier, add_button))                add_button.grid(row=row_num, column=5, padx=5, pady=5, sticky="w")            # Initial row            text_label = tk.Label(tab, text=f"{row_name}:")            text_label.grid(row=row_num, column=0, padx=5, pady=5, sticky="w")            entry = tk.Entry(tab)            entry.grid(row=row_num, column=1, padx=5, pady=5, sticky="w")            dropdown_var = tk.StringVar()            dropdown_menu = ttk.Combobox(tab, textvariable=dropdown_var, state="readonly")            dropdown_menu.grid(row=row_num, column=2, padx=5, pady=5, sticky="w")            dropdown_values = load_dropdown_values(identifier)            dropdown_menu['values'] = dropdown_values            update_dropdown_values_dict(identifier, dropdown_values)            store_button = tk.Button(tab, text="Store", command=lambda entry=entry, dropdown_menu=dropdown_menu, identifier=identifier: store_input(entry, dropdown_menu, identifier))            store_button.grid(row=row_num, column=3, padx=5, pady=5, sticky="w")            remove_button = tk.Button(tab, text="Remove", command=lambda dropdown_menu=dropdown_menu, identifier=identifier: remove_selected(dropdown_menu, identifier))            remove_button.grid(row=row_num, column=4, padx=5, pady=5, sticky="w")            dropdown_values_dict[identifier] = dropdown_values  # Update the dictionary for the rowroot = tk.Tk()root.title("Tabbed GUI")# Create a Notebook (tabs container)notebook = ttk.Notebook(root)# Create tabstabs = []for i in range(4):    tab = ttk.Frame(notebook)    tabs.append(tab)    notebook.add(tab, text=f'Tab {i+1}')notebook.pack(expand=1, fill='both')# Content for each tabfor i, tab in enumerate(tabs):    tab_content(i, tab)  # Pass the tab index and the tab to tab_contentroot.mainloop()

i tried to adjust the functions tab cotent and add new row. i was expecting the new rows to be inserted directly below each row where the add row button was clicked. instead, it seems like it randomly places the new rows at different lcations.


Viewing all articles
Browse latest Browse all 447

Trending Articles



<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>