In python (2.7.12) with tkinter I try to achieve the following: I want to dynamically hide and unhide certain text labels. This I try to do using pack_forget and then later doing a pack again. The labels I am about to hide and unhide are in a fixed place (relative position) among other labels. When the labels are hidden, they shall consume no space.
For example, think about a label with the text "not" appearing or disappearing as part of a sentence. The other parts of the sentence would also be formed with labels. Thus, I can not simply use pack_forget followed by pack on that "not" label: The pack would not place the label at its previous position, but at the end of the packing list.
Thus, to ensure the label keeps its relative position (and to avoid re-packing everything again) I do the following: I create a frame, pack it at the location where my label shall be appearing/disappearing, and put the label inside. Then, I hide/unhide the label, but not the frame.
My expectation is, that the frame's size should adjust itself depending on whether the label within is hidden or not. Certainly, when the label is visible, the frame should be large enough to contain it. But, after calling pack_forget on the label, the frame's size should shrink to zero again.
However, this does not work: Initially, the frame actually has zero size. But, after the text label within has been visible once, the frame keeps its size. After calling pack_forget on the label within the frame, the text of the label actually disappears, but the frame does not shrink to zero.
What am I doing wrong?
Here is a complete code example (adapted from an example by Tony Veijalainen). On my system at least it shows the behaviour, that the text actually disappears, but the frame keeps its width (and height), which should not be the case.
from Tkinter import *
def toggle():
if label.winfo_ismapped():
button['text']='unmap'
label.pack_forget()
else:
button['text']='map'
label.pack()
root = Tk()
button = Button(text="Push me", command=toggle)
button.pack()
labelFrame = Frame()
labelFrame.pack()
label = Label(labelFrame, text="Hello Big Big World")
label.pack()
root.wait_window()
If in the example you remove labelFrame and create label directly as a child of root, everything works fine: The hidden label really consumes zero space.