How we set the grid for gender so that they will be close to 2 columns only.
I want gender(label), male and female(options) are packed into 2 columns.
Here is my code...
from Tkinter import *
root = Tk()
root.geometry('500x500')
root.title('Registration Form')
head = Frame(root)
entry = Frame(root)
head.pack()
entry.pack()
var = StringVar()
heading = Label(head,text='Registration Form',font='Helvetica 25 bold',pady=10).pack()
name_label = Label(entry,text='Name ',font='Helvetica 10 bold',pady=5)
name_entry = Entry(entry,width=30, font='Helvetica 10')
email_label = Label(entry,text='Email ',font='Helvetica 10 bold',pady=5)
email_entry = Entry(entry,width=30, font='Helvetica 10')
mob_label = Label(entry,text='Mobile ',font='Helvetica 10 bold',pady=5)
mob_entry = Entry(entry,width=30, font='Helvetica 10')
gender_label = Label(entry,text='Gender ',font='Helvetica 10 bold',pady=5)
male = Radiobutton(entry,text='Male',variable=var,value='male')
female = Radiobutton(entry,text='Female',variable=var,value='female')
name_label.grid(row=1, column=1)
name_entry.grid(row=1, column=2)
email_label.grid(row=2, column=1)
email_entry.grid(row=2, column=2)
mob_label.grid(row=3, column=1)
mob_entry.grid(row=3, column=2)
gender_label.grid(row=4, column=1)
male.grid(row=4,column=2, sticky="nsew")
female.grid(row=4,column=2,sticky="nsew")
root.mainloop()
Put male or female in next column and use columnspan=2 for Entry
from tkinter import *
root = Tk()
name_label = Label(root, text='Name')
name_entry = Entry(root)
gender_label = Label(root, text='Gender')
male = Radiobutton(root, text='Male')
female = Radiobutton(root, text='Female')
name_label.grid(row=1, column=1)
name_entry.grid(row=1, column=2, columnspan=2)
gender_label.grid(row=4, column=1)
male.grid(row=4, column=2, sticky="nsew")
female.grid(row=4, column=3, sticky="nsew")
root.mainloop()
See on effbot.org: The Tkinter Grid Geometry Manager
Related
Instead of appending the job_list entry to the list, it replaces the item before when you try to input a new value. I think you can mainly focus on the store_job method, the job number entry and the enter job button. I'm not sure if I need a reset method or something so that the Entry widgets can take more data. Any help would be much appreciated.
from tkinter import *
class EntryGUI:
def __init__(self, parent):
self.cb = IntVar()
self.job_number_label= Label(parent, text = "Job number:")
self.job_number_label.grid(row = 1, column = 0)
self.job_number = Entry(parent)
self.job_number.focus()
self.job_number.grid(row=1, column = 1)
self.customer_name_label = Label(parent, text = "Customer name:")
self.customer_name_label.grid(row = 2, column = 0)
self.customer_name = Entry(parent)
self.customer_name.grid(row=2, column = 1)
self.distance_label= Label(parent, text = "Distance Travelled (km):")
self.distance_label.grid(row = 3, column = 0)
self.distance = Entry(parent)
self.distance.grid(row=3, column = 1)
self.min_spent_label= Label(parent, text = "Minutes spent on Virus protection:")
self.min_spent_label.grid(row = 4, column = 0)
self.min_spent = Entry(parent)
self.min_spent.grid(row=4, column = 1)
wof_tune= Checkbutton(parent, variable = self.cb, text = "check if WOF and tune is required",
onvalue = 100, offvalue = 0)
wof_tune.grid(row = 5, column = 0)
self.enter = Button(parent, text = "Enter Job", command = lambda:[self.store_job(),self.calculate()])
self.enter.grid(row = 6, column = 0)
self.show_all = Button(parent, text = "Show All")
self.show_all.grid(row = 6, column = 1)
def store_job(self):
self.job_list = []
self.customer_list = []
self.job_list.append(self.job_number.get())
self.customer_list.append(self.customer_name.get())
for i in self.job_list:
print (i)
def calculate(self):
self.cost_list = []
self.distance_calc = int(self.distance.get())
self.min_calc = int(self.min_spent.get())
self.cost = 0
#calculates the travel cost
#if the distance is less than 5km it costs 10
if self.distance_calc <= 5:
self.cost = 10
else:
self.distance_calc = self.distance_calc - 5 #-5 as you calclate the extra distance
self.distance_calc = self.distance_calc / 2 #divide by two as you add 50c per km
self.cost = self.distance_calc + 10 #initial 10 plus half the extra distance
#print(self.cost)
self.cost = self.cost + (self.min_calc * 0.8)
self.cost = self.cost + int(self.cb.get())
self.cost_list.append(self.cost)
print(self.cost_list)
self.enter_next()
def enter_next(self):
self.job_number.delete(0,END)
self.customer_name.delete(0, END)
self.distance.delete(0, END)
self.min_spent.delete(0, END)
self.enter.configure(state = NORMAL)
if __name__=="__main__":
root = Tk()
show_label = EntryGUI(root)
root.mainloop()
You were resetting the lists used to store the data entered every time the data is entered; you need to declare storage attributes in __init__, then use them to accumulate the data:
class EntryGUI:
def __init__(self, parent):
self.cb = IntVar()
self.job_number_label = Label(parent, text="Job number:")
self.job_number_label.grid(row=1, column=0)
self.job_number = Entry(parent)
self.job_number.focus()
self.job_number.grid(row=1, column=1)
self.customer_name_label = Label(parent, text="Customer name:")
self.customer_name_label.grid(row=2, column=0)
self.customer_name = Entry(parent)
self.customer_name.grid(row=2, column=1)
self.distance_label = Label(parent, text="Distance Travelled (km):")
self.distance_label.grid(row=3, column=0)
self.distance = Entry(parent)
self.distance.grid(row=3, column=1)
self.min_spent_label = Label(parent, text="Minutes spent on Virus protection:")
self.min_spent_label.grid(row=4, column=0)
self.min_spent = Entry(parent)
self.min_spent.grid(row=4, column=1)
wof_tune= Checkbutton(parent, variable=self.cb, text="check if WOF and tune is required",
onvalue =100, offvalue=0)
wof_tune.grid(row=5, column=0)
self.enter = Button(parent, text="Enter Job", command=self.acquire_entries)
self.enter.grid(row=6, column=0)
self.show_all = Button(parent, text="Show All")
self.show_all.grid(row=6, column=1)
self.job_list = []
self.customer_list = []
self.cost_list = []
def acquire_entries(self):
self.store_job()
self.calculate()
def store_job(self):
self.job_list.append(self.job_number.get())
self.customer_list.append(self.customer_name.get())
def calculate(self):
self.distance_calc = int(self.distance.get())
self.min_calc = int(self.min_spent.get())
self.cost = 0
# ... unchanged below
I need help with changing "textvariable" to a int var. Here is my code:
from Tkinter import *
root = Tk()
strfname = IntVar()
strlname = IntVar()
labelf = Label(root, text = 'number').pack()
fname = Entry(root, justify='left', textvariable = strfname).pack()
labell = Label(root, text = 'number 2').pack()
lname = Entry(root, justify='left', textvariable = strlname).pack()
root.mainloop()
Thanks!
use .get
number_variable = strfname.get()
I am trying to navigate to the next frame on which new buttons or new labels will be displayed. I mean frame1 should disappear when user clicks any button of the four buttons and frame2 should appear.But the below code does not work.
from Tkinter import *
import tkFileDialog
from PIL import ImageTk, Image
root = Tk()
#my_widget = Widget-name (its container window, ** its configuration options)
def callback():
path = tkFileDialog.askopenfilename()
print path
def create_widgets_in_first_frame():
first_window_label1 = Label(root, text="Analysis of Machine Learning Methods using Titanic Disaster Dataset",justify=CENTER,font=("Helvetica", 20,"bold")).place(x=200,y=20)
first_window_label5 = Label(root, text="Choose your Method:",justify=LEFT,font=("Helvetica", 15,"italic")).place(x=20,y=180)
first_window_label2 = Label(root, text="Upload your Titanic datasets .csv extension here:",justify=LEFT,font=("Helvetica", 15,"italic")).place(x=20,y=60)
first_window_label3 = Label(root, text="Training dataset ->",justify=LEFT,font=("Helvetica", 12)).place(x=50,y=100)
training_data_path = StringVar()
first_window_entry1 = Entry(root, textvariable=training_data_path).place(x=350,y=100)
first_window_button1 = Button(root, text="Browse",command=lambda:training_data_path.set(tkFileDialog.askopenfilename())).place(x=550,y=100)
first_window_label4 = Label(root, text="Testing dataset ->",justify=LEFT,font=("Helvetica", 12)).place(x=50,y=140)
testing_data_path = StringVar()
first_window_entry2 = Entry(root, textvariable=testing_data_path).place(x=350,y=140)
first_window_button2 = Button(root, text="Browse",command=lambda:testing_data_path.set(tkFileDialog.askopenfilename())).place(x=550,y=140)
first_window_button3 = Button(root, text="Decision Tree",font=("Helvetica", 15))
first_window_button3.place(x=50,y=220)
first_window_button3.bind('<Button-1>', call_second_frame_on_top)
first_window_button4 = Button(root, text="Random Forests",font=("Helvetica", 15))
first_window_button4.place(x=350,y=220)
first_window_button4.bind('<Button-1>', call_second_frame_on_top)
first_window_button5 = Button(root, text="Logistic Regression",font=("Helvetica", 15))
first_window_button5.place(x=650,y=220)
first_window_button5.bind('<Button-1>', call_second_frame_on_top)
first_window_button6 = Button(root, text="Analysis",font=("Helvetica", 15))
first_window_button6.place(x=1000,y=220)
first_window_button6.bind('<Button-1>', call_second_frame_on_top)
def create_widgets_in_second_frame():
second_window_label6 = Label(root, text="Decision Trees",justify=CENTER,font=("Helvetica", 20,"bold")).place(x=200,y=20)
print "graph is below"
def call_second_frame_on_top(event):
first_frame.grid_forget()
second_frame.grid(column=0, row=0, padx=20, pady=5)
window_width = 1300
window_heigth = 700
first_frame=Frame(root, width=window_width, height=window_heigth)
first_frame['borderwidth'] = 2
first_frame['relief'] = 'sunken'
first_frame.grid(column=0, row=0, padx=20, pady=5)
second_frame=Frame(root, width=window_width, height=window_heigth)
second_frame['borderwidth'] = 2
second_frame['relief'] = 'sunken'
second_frame.grid(column=0, row=0, padx=20, pady=5)
create_widgets_in_second_frame()
create_widgets_in_first_frame()
second_frame.grid_forget()
#root.minsize(width=1300, height=700)
#root.configure(background='lavender')
root.mainloop()
The problem is that you put all the widgets into root which is the whole window, so when you forget the frame, you forget nothing, as nothing is in the frame.
Just change the root to first_frame
Here is a working code:
from Tkinter import *
import tkFileDialog
from PIL import ImageTk, Image
root = Tk()
#my_widget = Widget-name (its container window, ** its configuration options)
def callback():
path = tkFileDialog.askopenfilename()
print path
def create_widgets_in_first_frame():
first_window_label1 = Label(first_frame, text="Analysis of Machine Learning Methods using Titanic Disaster Dataset",justify=CENTER,font=("Helvetica", 20,"bold")).place(x=200,y=20)
first_window_label5 = Label(first_frame, text="Choose your Method:",justify=LEFT,font=("Helvetica", 15,"italic")).place(x=20,y=180)
first_window_label2 = Label(first_frame, text="Upload your Titanic datasets .csv extension here:",justify=LEFT,font=("Helvetica", 15,"italic")).place(x=20,y=60)
first_window_label3 = Label(first_frame, text="Training dataset ->",justify=LEFT,font=("Helvetica", 12)).place(x=50,y=100)
training_data_path = StringVar()
first_window_entry1 = Entry(first_frame, textvariable=training_data_path).place(x=350,y=100)
first_window_button1 = Button(first_frame, text="Browse",command=lambda:training_data_path.set(tkFileDialog.askopenfilename())).place(x=550,y=100)
first_window_label4 = Label(first_frame, text="Testing dataset ->",justify=LEFT,font=("Helvetica", 12)).place(x=50,y=140)
testing_data_path = StringVar()
first_window_entry2 = Entry(first_frame, textvariable=testing_data_path).place(x=350,y=140)
first_window_button2 = Button(first_frame, text="Browse",command=lambda:testing_data_path.set(tkFileDialog.askopenfilename())).place(x=550,y=140)
first_window_button3 = Button(first_frame, text="Decision Tree",font=("Helvetica", 15))
first_window_button3.place(x=50,y=220)
first_window_button3.bind('<Button-1>', call_second_frame_on_top)
first_window_button4 = Button(first_frame, text="Random Forests",font=("Helvetica", 15))
first_window_button4.place(x=350,y=220)
first_window_button4.bind('<Button-1>', call_second_frame_on_top)
first_window_button5 = Button(first_frame, text="Logistic Regression",font=("Helvetica", 15))
first_window_button5.place(x=650,y=220)
first_window_button5.bind('<Button-1>', call_second_frame_on_top)
first_window_button6 = Button(first_frame, text="Analysis",font=("Helvetica", 15))
first_window_button6.place(x=1000,y=220)
first_window_button6.bind('<Button-1>', call_second_frame_on_top)
def create_widgets_in_second_frame():
second_window_label6 = Label(root, text="Decision Trees",justify=CENTER,font=("Helvetica", 20,"bold")).place(x=200,y=20)
print "graph is below"
def call_second_frame_on_top(event):
first_frame.grid_forget()
second_frame.grid(column=0, row=0, padx=20, pady=5)
window_width = 1300
window_heigth = 700
first_frame=Frame(root, width=window_width, height=window_heigth)
first_frame['borderwidth'] = 2
first_frame['relief'] = 'sunken'
first_frame.grid(column=0, row=0, padx=20, pady=5)
second_frame=Frame(root, width=window_width, height=window_heigth)
second_frame['borderwidth'] = 2
second_frame['relief'] = 'sunken'
second_frame.grid(column=0, row=0, padx=20, pady=5)
create_widgets_in_second_frame()
create_widgets_in_first_frame()
second_frame.grid_forget()
#root.minsize(width=1300, height=700)
#root.configure(background='lavender')
root.mainloop()
Note, that the label you get when you click any buttons is still in the main root so you will have to put that into the second_frame, or wherever you wish.
I have the following layout:
btnReset = Button(self.upperButtonFrame, text = "Reset", width = 12, command=self.__parent.reset)
btnReset.grid(row=0, column=0, sticky="W", pady=5)
btnRender = Button(self.upperButtonFrame, text = "Render", width = 9, command = self.render)
btnRender.grid(row=0, column=1, pady=5)
self.bScattered = Radiobutton(self.upperButtonFrame, text="Backscattered", variable=self.plotType, value=1).grid(row=1, column=0, sticky="W")
self.depolarized = Radiobutton(self.upperButtonFrame, text="Depolarized", variable=self.plotType, value=2).grid(row=2, column=0, sticky="W")
self.rng = Label(self.upperButtonFrame, text="Step").grid(row=3, column=0, sticky="W")
self.e = Entry(self.upperButtonFrame).grid(row=3,column=1)
self.to = Label(self.upperButtonFrame, text="to").grid(row=3, column=2)
self.e2 = Entry(self.upperButtonFrame).grid(row=3,column=3)
The problem is my third row looks like:
Instead of evenly spacing the 4 widgets I'm trying to place. How can I fix grid manager cutting off the last two and evenly space them on the screen?
EDIT: Here's a minimal example of my problem, running it should reproduce the results shown above
from Tkinter import Label, Toplevel, Frame, Button, IntVar, \
BOTH, BOTTOM, Radiobutton, Entry, TOP, Tk
CHILDWIDTH = 200
CHILDHEIGHT = 325
class ToolsWindow(Toplevel):
def __init__(self, root):
Toplevel.__init__(self, root)
self.__root = root
self.plotType = IntVar()
self.title("Tools")
self.geometry('%dx%d+%d+%d' % (CHILDWIDTH, CHILDHEIGHT,0, 0))
#self.resizable(width=FALSE, height=FALSE)
self.protocol("WM_DELETE_WINDOW", ToolsWindow.ignore)
self.container = Frame(self, background="red")
self.container.pack(side=TOP, fill=BOTH, expand=True )
self.coordinateFrame = Frame(self.container, background="green", width=50, height=50)
self.coordinateFrame.config(highlightthickness=1) # create a small border around the frame
self.coordinateFrame.config(highlightbackground="grey")
self.coordinateFrame.pack(side=BOTTOM, fill=BOTH, expand=False)
#staticmethod
def ignore():
pass
def setupToolBarButtons(self):
self.upperButtonFrame = Frame(self.container, background="blue") # upper button frame holding text buttons
self.upperButtonFrame.pack(side=TOP)
btnReset = Button(self.upperButtonFrame, text = "Reset", width = 12, command=self.render)
btnReset.grid(row=0, column=0, sticky="w")
btnRender = Button(self.upperButtonFrame, text = "Render", width = 9, command = self.render)
btnRender.grid(row=0, column=1, sticky="w")
self.bScattered = Radiobutton(self.upperButtonFrame, text="Backscattered",
variable=self.plotType, value=1).grid(row=1, column=0, sticky="w")
self.depolarized = Radiobutton(self.upperButtonFrame, text="Depolarized",
variable=self.plotType, value=2).grid(row=2, column=0, sticky="w")
self.rng = Label(self.upperButtonFrame, text="Step")
self.rng.grid(row=3, column=0, sticky="w")
self.e = Entry(self.upperButtonFrame, width=8)
self.e.grid(row=3, column=1, sticky="w")
self.to = Label(self.upperButtonFrame, text="to")
self.to.grid(row=3, column=2, sticky="w")
self.e2 = Entry(self.upperButtonFrame, width=8)
self.e2.grid(row=3, column=3, sticky="w")
def render(self):
pass
root = Tk()
tool = ToolsWindow(root)
tool.setupToolBarButtons()
root.mainloop()
The slightly modified program posted below renders properly, so it must be something in the code you did not post that is causing the problem. Are you limiting the size of the root window's, geometry anywhere? I do not know what you mean by "evenly spaced" but you can use the width parameter on most widgets to increase the size.
from Tkinter import *
class TestIt(object):
def __init__(self, top):
self.upperButtonFrame=top
btnReset = Button(self.upperButtonFrame, text = "Reset", width = 12)
btnReset.grid(row=0, column=0, sticky="W", pady=5)
btnRender = Button(self.upperButtonFrame, text = "Render", width = 9)
btnRender.grid(row=0, column=1, pady=5)
self.bScattered = Radiobutton(self.upperButtonFrame, text="Backscattered").grid(row=1, column=0
self.depolarized = Radiobutton(self.upperButtonFrame, text="Depolarized").grid(row=2, column=0,
self.rng = Label(self.upperButtonFrame, text="Step").grid(row=3, column=0, sticky="e")
self.e = Entry(self.upperButtonFrame).grid(row=3,column=1)
self.to = Label(self.upperButtonFrame, text="to").grid(row=3, column=2, sticky="e")
self.e2 = Entry(self.upperButtonFrame).grid(row=3,column=3)
top = Tk()
TI=TestIt(top)
top.mainloop()
I am writing a GUI for my application using Tkinter. I am using class to describe the whole structure, as described here. For some reason this program runs commands bounded to buttons (even though one of buttons is disabled) on start-up and doesn't react on same buttons afterwards. Please see my code below.
from Tkinter import *
from new_plot_main import PlotClass
class MainWindow:
def __init__(self, master):
Frame(master).grid()
self.main_check = [NoneType, NoneType, NoneType, NoneType]
self.scope_check = [NoneType, NoneType, NoneType, NoneType]
self.main_check[0] = Checkbutton(master, text="Lines")
self.main_check[1] = Checkbutton(master, text="Errors")
self.main_check[2] = Checkbutton(master, text="Upstream Snr")
self.main_check[3] = Checkbutton(master, text="Downstream Snr")
self.scope_check[0] = Checkbutton(master, text="Lines")
self.scope_check[1] = Checkbutton(master, text="Errors")
self.scope_check[2] = Checkbutton(master, text="Upstream Snr")
self.scope_check[3] = Checkbutton(master, text="Downstream Snr")
self.stats_check = Checkbutton(master, text="Enable statistics") # Statistics trigger
self.csi_check = Checkbutton(master, text="Enable CSI") # CSI calculation trigger
self.scope_range = Entry(master, width=15).grid(row=4, column=3) # To specify scope range
self.lines_entry = Entry(master, width=15).grid(row=6, column=1) # Lines to analyze
self.save_to_pdf_button = Button(master,
text="Save to PDF",
state=DISABLED,
width=10)
self.plot_button = Button(master, text="Plot", width=10, command=self.plot_action())
self.set_button = Button(master,
text="Set", state=DISABLED,
width=10, command=self.scope_action()) # Button to apply range from scope_range
#------Setting coordinates via grid--------
Label(master, text="Main", font=("Helvetica", 10, "bold")).grid(row=0, column=0, sticky=SW)
Label(master, text="Scope", font=("Helvetica", 10, "bold")).grid(row=0, column=1, sticky=SW)
Label(master, text="Options", font=("Helvetica", 10, "bold")).grid(row=0, column=3, sticky=SW)
Label(master, text="Lines to plot").grid(row=6, column=0, sticky=E)
Label(master, text="Set scope").grid(row=3, column=3, sticky=S)
self.stats_check.grid(row=1, column=3, sticky=W)
self.stats_check.select()
self.csi_check.grid(row=2, column=3, sticky=W)
self.csi_check.select()
self.save_to_pdf_button.grid(row=6, column=4, sticky=E)
self.plot_button.grid(row=6, column=2, sticky=W)
self.set_button.grid(row=4, column=4, sticky=W)
for i in xrange(0, 4):
self.main_check[i].grid(row=i+1, column=0, sticky=W)
self.scope_check[i].grid(row=i+1, column=1, sticky=W)
self.main_check[i].select()
self.scope_check[i].select()
def plot_action(self):
# plot = PlotClass()
# self.top = Toplevel()
print "Potatoes"
def scope_action(self):
# self.bot = Toplevel()
print "Banana"
def handler():
"""
Exiting GUI and stopping all processes, when system exit button is pressed.
"""
root.quit()
root.destroy()
root = Tk()
root.wm_title("Plot tool [new]")
app = MainWindow(root)
root.protocol("WM_DELETE_WINDOW", handler)
root.mainloop()
This code outputs Potatoes Banana upon execution.
You need to use just the function, not the function result. Instead of:
self.plot_button = Button(master, text="Plot", width=10,
command=self.plot_action())
and
self.set_button = Button(master, text="Set", state=DISABLED,
width=10, command=self.scope_action())
use:
self.plot_button = Button(master, text="Plot", width=10,
command=self.plot_action)
and
self.set_button = Button(master, text="Set", state=DISABLED,
width=10, command=self.scope_action)
That way the commands will be called only when the button is pressed.