I've searched and found a few things on parent windows in python but that is not what I was looking for. I am trying make a simple program that opens a window and another window after that when the previous one is closed. I was also trying to implement some kind of loop or sleep time to destroy the window by default if the user does not. This is what I have (I'm new please don't laugh)
from tkinter import *
import time
root = Tk()
i = 0
if i < 1:
root.title("title")
logo = PhotoImage(file="burger.gif")
w1 = Label(root, image=logo).pack()
time.sleep(3)
root.destroy()
i = i + 1
if i == 1:
root.title("title")
photoTwo = PhotoImage(file="freedom.gif")
labelTwo = Label(root, image=photoTwo).pack()
time.sleep(3)
root.destroy()
i = i + 1
mainloop.()
Perhaps you're looking for something like this:
from tkinter import *
import time
def openNewWindow():
firstWindow.destroy()
secondWindow = Tk()
secondWindow.title("Second Window")
photoTwo = PhotoImage(file="freedom.gif")
labelTwo = Label(secondWindow, image=photoTwo).pack()
secondWindow.mainloop()
firstWindow = Tk()
firstWindow.title("First Window")
logo = PhotoImage(file="burger.gif")
w1 = Label(firstWindow, image=logo).pack()
closeBttn = Button(firstWindow, text="Close!", command=openNewWindow)
closeBttn.pack()
firstWindow.mainloop()
This creates a button in the first window, which the user clicks. This then calls the openNewWindow function, which destroys that window, and opens the second window. I'm not sure there's a way to do this using the window exit button.
To get create a more sustainable window creation, use this:
from tkinter import *
import time
def openThirdWindow(previouswindow):
previouswindow.destroy()
thirdWindow = Tk()
thirdWindow.title("Third Window")
photoTwo = PhotoImage(file="freedom.gif")
labelTwo = Label(thirdWindow, image=photoTwo).pack()
thirdWindow.mainloop()
def openSecondWindow(previouswindow):
previouswindow.destroy()
secondWindow = Tk()
secondWindow.title("Second Window")
photoTwo = PhotoImage(file="freedom.gif")
labelTwo = Label(secondWindow, image=photoTwo).pack()
closeBttn = Button(secondWindow, text="Close!", command= lambda: openThirdWindow(secondWindow))
closeBttn.pack()
secondWindow.mainloop()
def openFirstWindow():
firstWindow = Tk()
firstWindow.title("First Window")
logo = PhotoImage(file="burger.gif")
w1 = Label(firstWindow, image=logo).pack()
closeBttn = Button(firstWindow, text="Close!", command= lambda: openSecondWindow(firstWindow))
closeBttn.pack()
firstWindow.mainloop()
openFirstWindow()
This places the opening of each window in a seperate function, and passes the name of the window through the button presses into the next function. Another method would be setting the window names as global, but this is messy.
The function "lambda:" calls the function, in tkinter you must type this if you want to pass something through a command.
We initiate the whole process first first called "openFirstWindow()"
Related
Good days all, I am new here, and I have stuck the problem a few days a problem currently with Tkinter, I have done some research about how to close Tkinter window when the mouse has clicked away from it but there are not much information to do so.
So, my problem is how to close the Tkinter window when the mouse clicked outside the Tkinter? I have tried the method of FocusOut to my Tkinter. However, I have tried to bind with root, it will close the window even though I clicked inside the frame widget. Then, I bind with the frame, the Tkinter will close when I clicked outside the Tkinter. Therefore, I have proved that the idea to close the Tkinter is works so far.
Then a new problem has happened, when I clicked the Combobox widget in the window, the window will close also. Is there any better solution to prove this concept?
Here is the code to indicate my problem.
import tkinter as tk
from tkinter import StringVar, ttk,messagebox
root = tk.Tk()
root.title("Sample Window")
root.minsize(300,350)
info_frame = tk.LabelFrame(root, text = "Information")
info_frame.pack(padx = 5, pady = 5 , fill = "both",expand=True)
tabControl = ttk.Notebook(info_frame)
person1tab = ttk.Frame(tabControl)
tabControl.add(person1tab,text = "Person1")
tabControl.pack(expand=1,fill="both")
person2tab = ttk.Frame(tabControl)
tabControl.add(person2tab,text = "Person2")
tabControl.pack(expand=1,fill="both")
fname_var = tk.StringVar()
lname_var = tk.StringVar()
gender_var = tk.StringVar()
age_var = tk.IntVar()
fname_label = tk.Label(person1tab, text = "First name:").pack(padx=5,pady=3)
fname_entry = tk.Entry(person1tab, textvariable=fname_var).pack(padx=5,pady=3)
lname_label = tk.Label(person1tab, text = "Last name:").pack(padx=5,pady=3)
lname_entry = tk.Entry(person1tab, textvariable=lname_var).pack(padx=5,pady=3)
gender_label = tk.Label(person1tab, text = "Gender:").pack(padx=5,pady=3)
gender_combo = ttk.Combobox(person1tab, textvariable=gender_var,state='readonly')
gender_combo['values'] = ('Male','Female')
gender_combo.current(0)
gender_combo.pack(padx=5,pady=3)
age_label = tk.Label(person1tab, text = "Age:").pack(padx=5,pady=3)
age_label = tk.Entry(person1tab, textvariable=age_var).pack(padx=5,pady=3)
page2label = tk.Label(person2tab,text = "This is tab 2.").pack(padx=5,pady=3)
def lossfocus(event):
root.quit()
pass
tabControl.bind('<FocusOut>', lossfocus)
root.mainloop()
You can still bind <FocusOut> on root window, but you need to check:
whether the widget that trigger this event is root window
no other widget in this root window getting the focus:
def lossfocus(event):
if event.widget is root:
# check which widget getting the focus
w = root.tk.call('focus')
if not w:
# not widget in this window
root.destroy()
I have referred to this post Python tkinter: How can I ensure only ONE child window is created onclick and not a new window every time the button is clicked? but i couldn't get my code to work. Could anyone please help me?
from tkinter import *
import os
import sys
import _thread
from s2 import work
from s1 import work2
root = Tk()
root.resizable(width=False, height=False)
root.title("Sample tkinter")
root.geometry(r"550x550")
def open_entry():
os.system("data1.py")
def open_aisle():
os.system("data2.py")
def close_entry():
os.system("data10.py")
def close_aisle():
os.system("data20.py")
def run():
_thread.start_new_thread(work,())
_thread.start_new_thread(work2,())
def openNewWindow():
global createdb_btn
newWindow = Toplevel(root)
newWindow.resizable(width=False,height=False)
newWindow.title("New Window")
newWindow.geometry("300x300")
create_front = Button(newWindow,text="Entry DB",relief=FLAT,bg="black",fg="white",command=open_entry)
create_front.place(x=50,y=80)
create_aisle = Button(newWindow,text="Aisle DB",relief=FLAT,bg="black",fg="white",command=open_aisle)
create_aisle.place(x=145,y=80)
def openAnotherWindow():
global removedb_btn
otherWindow = Toplevel(root)
otherWindow.resizable(width=False,height=False)
otherWindow.title("New Window")
otherWindow.geometry("300x300")
remove_front = Button(otherWindow,text="Entry DB",relief=FLAT,bg="black",fg="white",command=close_entry)
remove_front.place(x=50,y=80)
remove_aisle = Button(otherWindow,text="Aisle DB",relief=FLAT,bg="black",fg="white",command=close_aisle)
remove_aisle.place(x=145,y=80)
removedb_btn = Button(root,text="Remove databases",relief=FLAT,bg="black",fg="white",state=DISABLED)
removedb_btn.place(x=380,y=120)
camera_btn = Button(root,text="Open Cams",relief=FLAT,bg="black",fg="white",command=run)
camera_btn.place(x=50,y=120)
createdb_btn = Button(root,text="Create databases",relief=FLAT,bg="black",fg="white",command=openNewWindow)
createdb_btn.place(x=205,y=120)
removedb_btn = Button(root,text="Remove databases",relief=FLAT,bg="black",fg="white",command=openAnotherWindow)
removedb_btn.place(x=380,y=120)
root.mainloop()
I am trying to achieve this in both the openNewWindow function and openAnotherWindow function.
This is what I did. Changed the lines:
createdb_btn = Button(root,text="Create databases",relief=FLAT,bg="black",fg="white")
createdb_btn.config(command=lambda b=createdb_btn: (openNewWindow(b), b.config(state='disabled')))
and added
newWindow.protocol("WM_DELETE_WINDOW", lambda:(button.config(state='active'), newWindow.destroy()))
Inside newWindow function so that when you pass in the button that created the window as a variable and use that on the overwrite of opennewWindows function to reactivate it just before newWindow.destroy()
Here is my code:
from tkinter import *
OPTIONS = ["Available","Busy","Invisible","Away"]
now = Toplevel()
variable = StringVar(now)
variable.set(OPTIONS[0]) # default value
details = {"U_status":""}
def verify():
global u_status
details["U_status"]=variable.get()
print ("value is:" + variable.get())
now.destroy()
def status():
w = OptionMenu(now, variable, *OPTIONS)
w.pack()
button = Button(now, text="OK", command=verify, relief='flat')
button.pack()
if __name__=='__main__':
status()
mainloop()
While running the above code, along with the window (I wanted) another empty window appears. Can anyone figure out what is wrong in this code?
Here now = Toplevel() should be replaced with Tk(), like:
now = Tk()
When you use Toplevel() a Tk() window is made in the background, if its not already made(your case), and that is the reason you are getting a blank new window. Actually that blank window is your main window.
Toplevel() is used to make child windows for the parent Tk() windows,ie, if you want sub windows within your main window(now), you will use Toplevel(). Because more than one Tk() in your code will cause some errors later on.
The blank window is actually the root window of your app that tkinter creates by default. You probably want to be explicit, and create a tk.Tk() root, and keep a reference to it.
New windows can be spawned and destroyed at leisure; your app will continue to exist as long as you keep the root active.
Maybe something like this:
import tkinter as tk
def verify():
now = tk.Toplevel(root)
details["U_status"] = variable.get()
txt = f'value is: {details["U_status"]}'
tk.Label(now, text=txt).pack()
now.after(3000, now.destroy)
def status():
tk.OptionMenu(root, variable, *OPTIONS).pack()
tk.Button(root, text="OK", command=verify, relief='flat').pack()
if __name__=='__main__':
OPTIONS = ["Available", "Busy", "Invisible", "Away"]
root = tk.Tk()
variable = tk.StringVar(root)
variable.set(OPTIONS[0])
details = {"U_status": ""}
status()
root.mainloop()
Im trying to make a simple shop which changes the background of the main window. But when you click the buy button (buyblue) it should change the text on the button to gekauft(sold in german). But because of the button beeing in another definition i acessed it with return and when i now click the button it opens a new window with the changed button. Is there a way to fix it that only the button on the already open window changes and no new window opens?
Its written in python 3 and with the tkinter module.
click = 10
bluecost = 10
def openshop():
global root2
root2 = Tk()
root2.title("SIMPLE CLICKER SHOP")
root2.geometry("700x400")
root2.resizable(height = False, width = False)
root2.configure(bg = "white")
buttonblue = Button(root2, text = "3000 Clicks", bg = "maroon1", command = buyblue)
buttonblue.place(x = 120, y = 120)
return buttonblue
def buyblue():
global click
global bluecost
buttonblue=openshop()
if click >= int(bluecost):
click -= int(bluecost)
global root
global label
global click1
root["bg"]="blue"
click1["bg"]="blue"
label["bg"]="blue"
buttonblue["bg"]="green"
buttonblue["text"] = "Gekauft"
bluecost = 0
Is there another way to pass a variable which is used in a defintion to another defintion?
You are creating the tkinter window in the function openshop. It means that whenever you run the function openshop, another window will be created. You have to modify your function from:
...
def openshop():
global root2
root2 = Tk() #< creates the window
...
to:
...
global root2
root2 = Tk() #< creates the window
def openshop():
...
This will reconfigure the root each time the openshop is run again but will not create another window.
So my first GUI window is meant for taking input from user :
from tkinter import *
from main import *
root = Tk()
root.configure(background="orange")
root.wm_title("Python Project")
label_1 = Label(root, text="Project Name",bg="orange",fg="black")
label_2 = Label(root, text="Site URL Link",bg="orange",fg="black")
entry_1 = Entry(root)
entry_2 = Entry(root)
label_1.grid(row=0,sticky=W)
label_2.grid(row=3333,sticky=W)
entry_1.grid(row=0,column=1,padx=50,ipadx=100)
entry_2.grid(row=3333,column=1,ipadx=100)
def callback():
a1 = entry_1.get()
a2 = entry_2.get()
mmm(a1,a2,root) # main program
button1 = Button(root,text="Run",command=callback)
button2=Button(root,text="Quit",command=root.quit)
button1.grid(row=3334,ipadx=15,padx=50,column=1)
button2.grid(row=3335,column=1,ipadx=15,padx=50)
root.mainloop()
And then i use another GUI window someone in this forum made to show my results :
from tkinter import *
root = Tk()
textbox = Text(root)
textbox.pack()
def redirector(inputStr):
textbox.insert(INSERT, inputStr)
sys.stdout.write = redirector # whenever sys.stdout.write is called, redirector is called.
sys.stderr.write = redirector
root.mainloop()
Now every time i run the first GUI , both GUIs open although there is no way the code reached the second GUI code yet... What is the problem here?
Also the second GUI is supposed to print from a class , but i have a bunch of error when I try to just put it there . What changes I need to make so I can make this 2nd GUI work with a class?