Tkinter - Disable button on click made in a for loop - python

I need to change the background color and disable the button that is clicked in the following code. I have tried to pass button in the command for the button but it doesn't seem to work.
I tried adding to my lambda call on the button variable: btn=button and then passing that through my function call, but I get the error "UnboundLocalError: local variable 'button' referenced before assignment"
How can i add to my disable_btn() function to disable the button and turn it grey.
Thanks
import tkinter as tk
from tkinter import font as tkfont
class SampleApp(tk.Tk):
def __init__(self, *args, **kwargs):
tk.Tk.__init__(self, *args, **kwargs)
self.title_font = tkfont.Font(family='Helvetica', size=18, weight="bold", slant="italic")
container = tk.Frame(self)
container.pack(side="top", fill="both", expand=True)
container.grid_rowconfigure(0, weight=1)
container.grid_columnconfigure(0, weight=1)
self.frames = {}
self.frames["StartPage"] = StartPage(parent=container, controller=self)
self.frames["StartPage"].grid(row=0, column=0, sticky="nsew")
self.show_frame("StartPage")
def show_frame(self, page_name):
'''Show a frame for the given page name'''
frame = self.frames[page_name]
frame.tkraise()
class StartPage(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
self.controller = controller
self.grid(columnspan=5, rowspan=5)
self.populate = tk.Button(self, text='Populate Data', command=lambda : self.data())
self.populate.pack(side='top')
self.frame = tk.Frame(self)
self.frame.pack()
self.canvas = tk.Canvas(self.frame, borderwidth=0)
self.canvas.pack(side='left', fill='both', expand=True)
def data(self):
row = 1
for x in range(5):
print(x)
label = tk.Label(self.canvas, text='Line {}'.format(row))
label.grid(row=row, column=1, padx=15, pady=15)
text = tk.Text(self.canvas, width=5, height=1)
text.grid(row=row, column=2, padx=15, pady=15)
button = tk.Button(self.canvas, text='Click me', bg='white', command=lambda line=row:stored_functions.disable_btn(self, line))
button.grid(row=row, column=3, padx=15, pady=15)
row+=1
class stored_functions():
def disable_btn(self, line):
print('Disabled the button on line {}'.format(line))
btn.configure(state='disabled', bg='grey')
if __name__ == "__main__":
app = SampleApp()
app.mainloop()

You need to pass the button widget as an argument to the function associated with its command. However you can't do it in the same call as the one that creates the Button because it doesn't exist yet. A simple way to workaround that impediment is to do it in two steps:
def data(self):
row = 1
for x in range(5):
print(x)
label = tk.Label(self.canvas, text='Line {}'.format(row))
label.grid(row=row, column=1, padx=15, pady=15)
text = tk.Text(self.canvas, width=5, height=1)
text.grid(row=row, column=2, padx=15, pady=15)
button = tk.Button(self.canvas, text='Click me', bg='white')
button.grid(row=row, column=3, padx=15, pady=15)
button.config(command=lambda btn=button, line=row: disable_btn(btn, line))
row += 1
def disable_btn(btn, line):
print('Disabled the button on line {}'.format(line))
btn.configure(state='disabled', bg='grey')

Related

Frame inside A OOP Tkinter Frame

Right so I am trying to put a frame into the waiter page to split it into different frames
like this design but nothings working.
This is the design:
I've tried to create a basic Frame inside but it doesn't appear.
The Frame that I created doesnt throw an error however it might be in a different position, So I attempted to move it but it didn't change anything and just didn't display it on the WaiterPage.
Note There is no validation for the login so just click login after choosing WaiterPage.
import tkinter as tk
from tkinter import SUNKEN, Label, ttk
from tkinter import IntVar
from tkinter.constants import BOTH, BOTTOM, CENTER, GROOVE, LEFT, RIGHT
from typing import Container
class App(tk.Tk):
def __init__(self, *args, **kwargs):
tk.Tk.__init__(self,*args,**kwargs)
self.bg = tk.PhotoImage(file="D:/talha\Documents\Projects For Portfolio\Some Fun\CourseWork\Testbg.png")
container = tk.Frame(self)
self.geometry("800x500")
self.resizable(False,False)
container.pack(side="top", fill="both", expand=True)
container.grid_rowconfigure(0, weight=1)
container.grid_columnconfigure(0, weight=1)
self.frames = {}
for page in (ManagerPage, WaiterPage, Login):
frame = page(container,self)
self.frames[page] = frame
frame.grid(row=0, column=0, sticky="nsew")
self.show_frame(page)
def show_frame(self, cont):
frame = self.frames[cont]
frame.tkraise()
class WaiterPage(tk.Frame):
def __init__(self, parent, controller):
MainFrame = tk.Frame.__init__(self, parent)
RightFrame = tk.Frame(MainFrame, background='blue')
class ManagerPage(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
tk.Label(self, text="Manager Page:").pack()
LeftFrame = tk.Frame(self)
LeftFrame.pack(side=LEFT)
CurrentTables = tk.Listbox(LeftFrame, width=70,height=33).pack(side=LEFT,fill=BOTH)
AddTable = ttk.Button(self, text="Add Table").place(width=160,height=37,relx=0.65, rely=0.5, anchor=CENTER)
AddBooking = ttk.Button(self, text="Add Booking").place(width=160,height=37,relx=0.875, rely=0.5, anchor=CENTER)
ViewBooking = ttk.Button(self, text="View Booking").place(width=160, height=37,relx=0.65, rely=0.65, anchor=CENTER)
Collection = ttk.Button(self, text="Collection").place(width=160,height=37,relx=0.875, rely=0.65, anchor=CENTER)
Inventory = ttk.Button(self, text="View Inventory").place(width=160,height=37,relx=0.75, rely=0.8, anchor=CENTER)
Exit = ttk.Button(self, text="Exit").place(width=160,height=37,relx=0.75, rely=0.9, anchor=CENTER)
class Login(tk.Frame):
def __init__(self, parent, controller):
def CallBack():
if ManagerValue.get() == 1:
WaiterCheck.configure(state='disabled')
if WaiterValue.get() == 1:
ManagerCheck.configure(state='disabled')
if ManagerValue.get() == 0:
WaiterCheck.configure(state='normal')
if WaiterValue.get() == 0:
ManagerCheck.configure(state='normal')
def CheckPage():
if ManagerValue.get() == 1:
self.controller.show_frame(ManagerPage)
if WaiterValue.get() == 1:
self.controller.show_frame(WaiterPage)
tk.Frame.__init__(self,parent)
self.controller = controller
label_bkgr = tk.Label(self, image=self.controller.bg)
label_bkgr.place(relx=0.5, rely=0.5, anchor=CENTER)
tk.Label(self, text="Username: ",font=("Segoe UI", 12),bg='#59C8E3').place(relx=0.3, rely=0.35, anchor=CENTER)
tk.Label(self, text="Password: ",font=("Segoe UI", 12),bg='#59C8E3').place(relx=0.3, rely=0.45, anchor=CENTER)
ManagerValue = IntVar()
WaiterValue = IntVar()
ManagerCheck = tk.Checkbutton(self, text="Manager",variable=ManagerValue,command=CallBack,font=("Segoe UI", 12),bg='#59C8E3',activebackground='#59C8E3')
ManagerCheck.place(relx=0.43, rely=0.535, anchor=CENTER)
WaiterCheck = tk.Checkbutton(self, text="Waiter",variable=WaiterValue,command=CallBack,font=("Segoe UI", 12),bg='#59C8E3',activebackground='#59C8E3')
WaiterCheck.place(relx=0.59, rely=0.535, anchor=CENTER)
UserEntry = ttk.Entry(self)
UserEntry.place(width=160,
height=37,relx=0.5, rely=0.35, anchor=CENTER)
PassEntry = ttk.Entry(self)
PassEntry.configure(show="*")
PassEntry.place(width=160,
height=37,relx=0.5, rely=0.45, anchor=CENTER)
Submit = ttk.Button(self, text="Submit",command=CheckPage)
Submit.place(width=160,
height=37,relx=0.5, rely=0.6, anchor=CENTER)
app = App()
app.mainloop()
The first problem is that you never call pack or grid on RightFrame, so it will never appear.
The second problem is that RightFrame needs to be a child of self because MainFrame is None.
class WaiterPage(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
RightFrame = tk.Frame(self, background='blue')
RightFrame.pack(fill="both", expand=True)
I don't know if pack(fill="both", expand=True) are the right options, but the point is you have to call pack or grid or place on the frame in order for it to be visible.

How to show proccess output in text box in other frame using Python tkinter [closed]

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 2 years ago.
Improve this question
I'm trying to write the 'ping' output to a text box that will be
created in the 'output' tkinter frame
When I press the 'Submit' button while writing the output to file.
Questions:
1: Is there a way to place the text box inside the 'output' frame?
2: How can I print lines from files inside the 'output' frame?
3: How can I use threading or multiproccess to display the output in realtime?
Before clicking 'Submit':
import tkinter as tk
import subprocess as sub
from multiprocessing import Queue
import os
class GUI(tk.Tk):
def __init__(self, *args, **kwargs):
tk.Tk.__init__(self, *args, **kwargs)
self.geometry("650x500")
self.title("Gil Shwartz GUI Project")
menu = tk.Frame(self, height=250, width=10, relief="solid")
menu.pack(side=tk.LEFT, fill="both", anchor="w")
container = tk.Frame(self, relief="flat")
container.pack(side=tk.TOP, fill="y", expand=True)
output = tk.LabelFrame(self, text="Output", height=350, width=70)
output.pack(side=tk.BOTTOM, fill="both", expand=True)
menu.grid_columnconfigure(0, weight=1)
menu.grid_rowconfigure(0, weight=1)
self.frames = ["Menu", "MainWelcome", "testPing", "PageOne", "PageTwo"]
self.frames[0] = Menu(parent=menu, controller=self)
self.frames[1] = MainWelcome(parent=container, controller=self)
self.frames[2] = testPing(parent=container, controller=self)
self.frames[3] = PageOne(parent=container, controller=self)
self.frames[4] = PageTwo(parent=container, controller=self)
self.frames[0].grid(row=0, column=0, sticky="nsew")
self.frames[1].grid(row=0, column=0, sticky="nsew")
self.frames[2].grid(row=0, column=0, sticky="nsew")
self.frames[3].grid(row=0, column=0, sticky="nsew")
self.frames[4].grid(row=0, column=0, sticky="nsew")
self.show_frame(1)
def show_frame(self, page_name):
frame = self.frames[page_name]
print(frame)
frame.tkraise()
frame.grid(row=0, column=0, sticky="nsew")
class Menu(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
self.controller = controller
button1 = tk.Button(self, text="Ping Test",
command=lambda: controller.show_frame(2))
button1.config(bg="royalblue2")
button2 = tk.Button(self, text="Page Two",
command=lambda: controller.show_frame(4))
button2.config(bg="dark violet")
button3 = tk.Button(self, text="Quit",
command=lambda: Menu.terminate(self))
button3.config(bg="gray40")
button1.pack(fill="both", expand=True)
button2.pack(fill="both", expand=True)
button3.pack(fill="both", expand=True)
button1.grid_columnconfigure(0, weight=1)
button2.grid_columnconfigure(0, weight=0)
button3.grid_rowconfigure(0, weight=0)
def terminate(self):
exit()
class MainWelcome(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
self.controller = controller
label = tk.Label(self, text="Text 1", bg="yellow")
label.pack(fill="x", expand=True)
label = tk.Label(self, text="Text 2", bg="yellow")
label.pack(fill="x")
class testPing(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
self.controller = controller
urlLabel = tk.Label(self, text="Enter URL : ", padx=5, pady=5)
urlLabel.pack(anchor="w")
urlInputBox = tk.Entry(self)
urlInputBox.pack(anchor="w")
urlInputBox.grid_columnconfigure(0, weight=0)
clearFileLabel = tk.Label(self, text="Clear File?", padx=5, pady=5)
clearFileLabel.pack(anchor="w")
clearFile = tk.BooleanVar()
clearFile.set(False)
clearFileRadioYes = tk.Radiobutton(self, text="yes", value=True, var=clearFile,
command=lambda: self.callback(clearFile.get()))
clearFileRadioYes.pack(anchor="w")
clearFileRadioNo = tk.Radiobutton(self, text="no", value=False, var=clearFile,
command=lambda: self.callback(clearFile.get()))
clearFileRadioNo.pack(anchor="w")
urlSubmitButton = tk.Button(self, text="Submit",
command=lambda: self.pingURL(urlInputBox.get(),
clearFile.get()))
urlSubmitButton.pack(side=tk.RIGHT, anchor="e")
def callback(self, clearFile):
print(clearFile) # Debugging Mode - check Radio box Var.
def pingURL(self, host, clearFile):
global r
file = fr'c:/users/{os.getlogin()}/Desktop/ping.txt'
text = tk.Text(self, height=5, width=100, wrap=tk.WORD)
text.pack(side=tk.TOP, expand=True)
if clearFile == True:
with open(file, 'a') as output:
output.truncate(0)
sub.call(['ping', f'{host}'], stdout=output)
else:
with open(file, 'a') as output:
sub.call(['ping', f'{host}'], stdout=output)
output.close()
class PageOne(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
self.controller = controller
label = tk.Label(self, text="This is page 1", bg="red")
label.pack(side="top", fill="x", pady=10)
button = tk.Button(self, text="Go to page 2",
command=lambda: controller.show_frame(2))
button.pack()
class PageTwo(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
self.controller = controller
label = tk.Label(self, text="This is page 2", bg="blue")
label.pack(side="top", fill="x", pady=10)
button = tk.Button(self, text="Go to the start page",
command=lambda: controller.show_frame(1))
button.pack()
if __name__ == "__main__":
app = GUI()
app.mainloop()
After clicking 'Submit':
First, you have to make the output frame available or else you can't access it later:
self.output = tk.LabelFrame(self, text="Output", height=350, width=70)
self.output.pack(side=tk.BOTTOM, fill="both", expand=True)
Then, in the testPing() class pingURL() method you can pack the Text() widget in the output labelframe:
text = tk.Text(self.controller.output, height=5, width=100, wrap=tk.WORD)
I don't know about using threading or multiproccess. In general I think you will get a better response if you post questions for each of your problems instead of listing them in the same question.

How to print out ttk.Combobox options in multiple frames?

In my code, there are two frames. In the first one, I put in an Add button that will produce a new frame with a Combobox. The idea is to add a few Combobox like that in the first frame, pick different options for different Combobox, and then print them out in the next frame. But when I hit the Show options button in the second frame, it doesn't print out the options that I just chose in the first frame. How can I solve this?
from tkinter import *
from tkinter import ttk
list_1 = []
class Validation_Tool(Tk):
def __init__(self, *args, **kwargs):
Tk.__init__(self, *args, **kwargs)
container = Frame(self)
container.pack(side="top", fill="both", expand=True)
container.grid_rowconfigure(0, weight=1)
container.grid_columnconfigure(0, weight=1)
self.frames = {}
for F in (PageOne, PageTwo):
page_name = F.__name__
frame = F(parent=container, controller=self)
self.frames[page_name] = frame
frame.grid(row=0, column=0, sticky="nsew")
self.show_frame("PageOne")
def show_frame(self, page_name):
frame = self.frames[page_name]
frame.tkraise()
def quit(self):
self.destroy()
class PageOne(Frame):
def __init__(self, parent, controller):
Frame.__init__(self, parent)
self.controller = controller
def add_compare():
global list_1
frame = Frame(self)
frame.pack()
label_1 = Label(frame, text='Options')
label_1.grid(row=0, column=0)
self.options_1 = ttk.Combobox(frame, values=['a','b','c','d','e'])
self.options_1.grid(row=1, column=0)
list_1.append(self.options_1.get())
quit_button = Button(self, text="Quit Program",
command=lambda: controller.quit())
next_button = Button(self, text="Next",
command=lambda: controller.show_frame("PageTwo"))
add_button = Button(self, text='Add', command=add_compare)
quit_button.place(relx=0.98, rely=0.98, anchor=SE)
next_button.place(relx=0.76, rely=0.98, anchor=SE)
add_button.place(relx=0.661, rely=0.98, anchor=SE)
class PageTwo(Frame):
def __init__(self, parent, controller):
Frame.__init__(self, parent)
self.controller = controller
def button():
label = Label(self, text=list_1)
label.pack()
quit_button = Button(self, text="Quit Program",
command=lambda: controller.quit())
back_button = Button(self, text="Back",
command=lambda: controller.show_frame("PageOne"))
show_button = Button(self, text='Show options', command=button)
show_button.pack()
back_button.place(relx=0.76, rely=0.98, anchor=SE)
quit_button.place(relx=0.98, rely=0.98, anchor=SE)
if __name__ == "__main__":
root = Validation_Tool()
root.geometry('400x300+430+250')
root.title("Validation Tool")
root.mainloop()
Here's a modified version of your code that will print the options selected so far when the Next is pressed. To prevent the Comboboxes from interferring with each other a list of them and an associated StringVars is kept.
Having separate StringVars avoids the problem of choosing an option on one of them from changing it on the others — i.e. a different textvar gets associated with each one.
To make collecting all the options together into list_1, a callback function named selected() has been defined and gets "bound" to Combobox selection events. This make it so that, in addition to the above, the option selected will also get appended to the global list_1, which is what the Show options button displays.
from tkinter import *
from tkinter import ttk
list_1 = []
class Validation_Tool(Tk):
def __init__(self, *args, **kwargs):
Tk.__init__(self, *args, **kwargs)
container = Frame(self)
container.pack(side="top", fill="both", expand=True)
container.grid_rowconfigure(0, weight=1)
container.grid_columnconfigure(0, weight=1)
self.comboboxes = [] # Comboboxes created. ADDED
self.combobox_vars = [] # Vars for Comboboxes. ADDED.
self.frames = {}
for F in (PageOne, PageTwo):
page_name = F.__name__
frame = F(parent=container, controller=self)
self.frames[page_name] = frame
frame.grid(row=0, column=0, sticky="nsew")
self.show_frame("PageOne")
def show_frame(self, page_name):
frame = self.frames[page_name]
frame.tkraise()
def quit(self):
self.destroy()
class PageOne(Frame):
def __init__(self, parent, controller):
Frame.__init__(self, parent)
self.controller = controller
# Combobox event handler. ADDED
def selected(event, var):
list_1.append(var.get()) # Append Combobox option selected.
def add_compare():
frame = Frame(self)
frame.pack()
label_1 = Label(frame, text='Options')
label_1.grid(row=0, column=0)
combobox_var = StringVar() # ADDED.
combobox = ttk.Combobox(frame, values=list('abcde'),
textvar=combobox_var) # For each Combobox. ADDED.
combobox.grid(row=1, column=0)
combobox.bind('<<ComboboxSelected>>', # Bind event handler. ADDED.
lambda event, var=combobox_var: selected(event, var)) # ADDED.
self.controller.comboboxes.append(combobox) # ADDED.
self.controller.combobox_vars.append(combobox_var) # ADDED.
quit_button = Button(self, text="Quit Program",
command=lambda: controller.quit())
next_button = Button(self, text="Next",
command=lambda: controller.show_frame("PageTwo"))
add_button = Button(self, text='Add',
command=add_compare)
quit_button.place(relx=0.98, rely=0.98, anchor=SE)
next_button.place(relx=0.76, rely=0.98, anchor=SE)
add_button.place(relx=0.661, rely=0.98, anchor=SE)
class PageTwo(Frame):
def __init__(self, parent, controller):
Frame.__init__(self, parent)
self.controller = controller
def button():
label = Label(self, text=list_1)
label.pack()
quit_button = Button(self, text="Quit Program",
command=lambda: controller.quit())
back_button = Button(self, text="Back",
command=lambda: controller.show_frame("PageOne"))
show_button = Button(self, text='Show options', command=button)
show_button.pack()
back_button.place(relx=0.76, rely=0.98, anchor=SE)
quit_button.place(relx=0.98, rely=0.98, anchor=SE)
if __name__ == "__main__":
root = Validation_Tool()
root.geometry('400x300+430+250')
root.title("Validation Tool")
root.mainloop()

Issues with .grid in Tkinter

I am VERY new to coding/Python, but basically I am trying to move a button and label around using .grid, however, the button and label in the StartPage class just won't move to where I ask (or even at all).
Everything in the BMR class works fine (although the positions you see aren't the final positions, I was just checking).
What is the difference? Why do they not appear at the same position if I give the same details in both classes?
import tkinter as tk
class initials(tk.Tk):
def __init__(self, *args, **kwargs):
tk.Tk.__init__(self, *args, **kwargs)
container = tk.Frame(self)
container.pack(side='top', fill='both', expand= True)
container.grid_rowconfigure(0, weight=1)
container.grid_columnconfigure(0, weight=1)
self.frames = {}
for F in (StartPage, BMR):
frame = F(container, self)
self.frames[F] = frame
frame.grid(row=0, column=0, sticky='nsew')
self.show_frame(StartPage)
def show_frame(self, cont):
frame = self.frames[cont]
frame.tkraise()
class StartPage(tk.Frame): #GRID WON'T WORK HOW I WANT IT TO
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
label = tk.Label(self, text="Start Page")
label.grid(column=3, row=3, sticky='we')
button = tk.Button(self, text="Calculate BMR",
command=lambda: controller.show_frame(BMR))
button.grid(row=4, column=3, sticky='we')
class BMR(tk.Frame): #GRID WORKS PERFECTLY
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
label = tk.Label(self, text="BMR Calculator")
label.grid(column=1,row=1)
button1 = tk.Button(self, text="Back to Home",
command=lambda: controller.show_frame(StartPage))
button1.grid(column=2, row=2)
submit = tk.Button(self, text="Calculate")
submit.grid(column=3, row=3)
var1 = tk.IntVar()
tk.Checkbutton(self, text='Male', bg='white', variable=var1).grid(column=4, row=4)
var2= tk.IntVar()
tk.Checkbutton(self, text='Female', bg='white', variable=var2).grid(column=5, row=5)
height_inp = tk.Entry(self, width=20, bg="white").grid(column=6, row=6)
app = initials()
app.mainloop()
class StartPage(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
label = tk.Label(self, text="Start Page", width = 80)
# Added width property in the line above
# and changed sticky property to N
label.grid(row = 3, column=3, sticky = 'N')
label.width = 20
button = tk.Button(self, text="Calculate BMR",
command=lambda: controller.show_frame(BMR))
button.grid(row=4, column=3)
# Removed sticky property for the button
I understand this is how you wish to position the label and the button.
Pleaase see the comments. You can edit the value for the width property and make it suitable for your frame.

Object Orientated Tkinter Functions - How would I put this in?

I am coding a program which will need functions to change labels and enter text into text boxes however I do not know how to do this with a new style of programming which I am using (Object Orientated). I have done the program before however I generated the frames using this code:
f = [Frame(root) for i in range(0,5)]
for i in f:
i.place(relx=0,rely=0,relwidth=1,relheight=1)
and then I put it all in one class which I ran however that was bad form so I am redoing it. My code so far is as follows:
import tkinter as tk
import datetime,time,os,sys
import sqlite3 as lite
from datetime import date
Title_Font= ("Times", 18, "underline italic")
unix = time.time()
time_curr = str(datetime.datetime.fromtimestamp(unix).strftime('%H:%M'))
date1 = str(datetime.datetime.fromtimestamp(unix).strftime('%d-%m-%Y'))
class Creating_Stuff(tk.Tk):
def __init__(self, *args, **kwargs):
tk.Tk.__init__(self, *args, **kwargs)
container = tk.Frame(self)
container.pack(side="top", fill="both", expand = True)
container.grid_rowconfigure(0, weight=1)
container.grid_columnconfigure(0, weight=1)
self.frames = {}
for F in (StartPage, PageOne, PageTwo):
frame = F(container, self)
self.frames[F] = frame
frame.grid(row=0, column=0, sticky="nsew")
self.show_frame(StartPage)
def show_frame(self, cont):
frame = self.frames[cont]
frame.tkraise()
class StartPage(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self,parent)
self.grid_columnconfigure(0, weight=1)
self.grid_columnconfigure(3, weight=1)
self.option_add( "*font", "Times 12" )
self.tk_setPalette(background='#bbfff0', foreground='black',
activeBackground='#d9d9d9', activeForeground='#ff9933')
label = tk.Label(self, text="Laptop Booking System", font=Title_Font)
label.grid(row=0, column=1, pady = 30)
time = tk.Label(self, text="Time: " + time_curr + "\nDate: " + date1, font="Times 10")
time.grid(row=0, column=2,columnspan=2)
Booking_1 = tk.Button(self, text="Booking",
command=lambda: controller.show_frame(PageOne),bg='#f2f2f2',width=20)
Booking_1.grid(row=2, column=1, pady=10)
Tbl_q1 = tk.Button(self, text="Table Querying",
command=lambda: controller.show_frame(PageTwo),bg='#f2f2f2',width=20)
Tbl_q1.grid(row=3, column=1, pady=10)
Exit = tk.Button(self, text ="Exit",command=lambda:destroy(),bg='#f2f2f2')
Exit.grid(row=5, column=1)
class PageOne(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
self.grid_columnconfigure(0, weight=1)
self.grid_columnconfigure(3, weight=1)
label = tk.Label(self, text="Page One!!!", font=Title_Font)
label.grid(row=1, column=1)
bk2_menu = tk.Button(self, text="Back to Home",
command=lambda: controller.show_frame(StartPage))
bk2_menu.grid(row=3, column=1)
class PageTwo(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
self.grid_columnconfigure(0, weight=1)
self.grid_columnconfigure(3, weight=1)
label = tk.Label(self, text="Page Two!!!", font=Title_Font)
label.grid(row=1, column=1)
bk2_Menu2 = tk.Button(self, text="Back to menu",
command=lambda: controller.show_frame(StartPage))
bk2_Menu2.grid(row=3, column=1)
app = Creating_Stuff()
def destroy():
app.destroy()
app.title("Laptop Booking System")
app.geometry("700x400")
app.mainloop()
If you try it out it works however it just has 3 different frames. How can I get a button in a frame to make a label say "Hello" in the frame after it is pressed?
I've modified one of your page classes to illustrate how it could be done. It involved adding a Label to hold the message, a Button to control it, and a function, called simply handler(), to call when the latter is pressed. It saves the widgets by making them attributes of the containing Frame subclass instance, self, so they can be easily referenced in the handler() function (without resorting to global variables).
class PageOne(tk.Frame):
def __init__(self, parent, controller):
tk.Frame.__init__(self, parent)
self.grid_columnconfigure(0, weight=1)
self.grid_columnconfigure(3, weight=1)
label = tk.Label(self, text="Page One!!!", font=Title_Font)
label.grid(row=1, column=1)
self.msg_label = tk.Label(self, text="")
self.msg_label.grid(row=2, column=1)
self.msg_button = tk.Button(self, text='Show Message',
command=self.handler)
self.msg_button.grid(row=3, column=1)
self.msg_toggle = False
bk2_menu = tk.Button(self, text="Back to Home",
command=lambda: controller.show_frame(StartPage))
bk2_menu.grid(row=5, column=1)
def handler(self):
self.msg_toggle = not self.msg_toggle
if self.msg_toggle:
self.msg_label.config(text='Hello')
self.msg_button.config(text='Clear Message')
else:
self.msg_label.config(text='')
self.msg_button.config(text='Show Message')
Screenshots
Before button is pressed:
After button is pressed:

Categories

Resources