Home > database >  Positioning dynamically added labels using Tkinter pack manager
Positioning dynamically added labels using Tkinter pack manager

Time:11-17

I'm trying to pack() lables dynamically after pressing button. But for some reason these labels are being added under the button that was clicked instead of under the whole frame in which the button resides, even though the master for new labels is button's master.

I tried to use many side and anchor options combinations but nothing seems to work as I'd wish.

Working example and it's output:


from tkinter import *

class AddSButton(Button):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.config(command=self.click_function)

    def click_function(self):
        # for item in self.master.winfo_children():
        l = Label(self.master, text="texttexttext")
        l.pack(anchor=W)


class Application(Frame):

    def __init__(self, master=None):
        self.setLounge = 21.0
        Frame.__init__(self, master)

        self.frame = LabelFrame(self.master)
        self.frame.grid(row=0, column=0)

        self.frame_input_sc = LabelFrame(self.frame)
        self.frame_input_sc.pack()

        self.input_s_id = Entry(self.frame_input_sc, width=3, borderwidth=3)
        self.input_s_id.grid(row=0, column=0)  # columnspan=3, , sticky=W E
        self.input_s_id.insert(0, "Id")

        self.input_s_name = Entry(self.frame_input_sc, width=20, borderwidth=3)
        self.input_s_name.grid(row=0, column=1)
        self.input_s_name.insert(0, "Enter text...")

        btn_add_sc = Button(self.frame_input_sc, text="Add", command=self.add_sc_clicked)
        btn_add_sc.grid(row=0, column=2)

    def add_sc_clicked(self):
        sc = self.input_s_name.get().strip()
        id = self.input_s_id.get().strip()

        frame_s = LabelFrame(self.frame)
        frame_s.pack(fill=X)

        lbl_s_id = Label(frame_s, text=id   "    ")
        lbl_s_name = Label(frame_s, text=sc)

        lbl_s_id.grid(row=0, column=0, sticky=N   S)
        lbl_s_name.grid(row=0, column=1, sticky=N   S)

        frame_add_step = LabelFrame(frame_s)
        frame_add_step.grid(row=1, column=0, columnspan=2, sticky=N   S   W   E)

        input_s = Entry(frame_add_step, width=50, borderwidth=3)
        input_s.pack(side=LEFT, anchor=NW)
        input_s.insert(0, "Enter s...")

        btn_add_s = AddSButton(frame_add_step, text="Add")
        btn_add_s.pack(fill=X, anchor=NW)

root = Tk()
app = Application(master=root)
app.mainloop()

enter image description here

CodePudding user response:

You have added the entry widget to the left side of frame_add_step, which causes it to be allocated the entire left side of the frame. All new widgets will be added to the right of the entry widget. This is a fundamental aspect of how the packer works.

You either need to put the entry and "add" button in a frame that is packed to the top of frame_add_step so that the labels can be packed below, or you need to use grid.

  • Related