Moving buttons/entries using grid in tkinter Python - python

I have just started learning tkinter and am having troubles with moving items around using grid. I am assuming this is an easy fix but I am trying to get my password entry and "generate password" button to be located much closer than they are as seen in the attached image (essentially I want everything aligned). How can I do this? I have looked on here and elsewhere but can't seem to find anything that replicates my problem.
from tkinter import *
window = Tk()
window.title("Password Manager")
window.config(padx=50, pady=50)
canvas = Canvas(height=200, width=200)
canvas.grid(column=1, row=0)
lock = PhotoImage(file="logo.png")
canvas.create_image(100, 100, image=lock)
website = Label(text="Website:")
website.grid(column=0, row=1)
email_user_name = Label(text="Email/Username:")
email_user_name.grid(column=0, row=2)
password = Label(text="Password:")
password.grid(column=0, row=3)
website_entry = Entry(width=35)
website_entry.grid(column=1, row=1, columnspan=2)
email_entry = Entry(width=35)
email_entry.grid(column=1, row=2, columnspan=2)
password_entry = Entry(width=21)
password_entry.grid(column=1, row=3)
generate_button = Button(text="Generate Password")
generate_button.grid(column=2, row=3)
add_button = Button(text="Add", width=30)
add_button.grid(column=1, row=4, columnspan=2)
window.mainloop()

You can add sticky="e" to grid(...) on the labels and sticky="w" on the entries:
from tkinter import *
window = Tk()
window.title("Password Manager")
window.config(padx=50, pady=50)
canvas = Canvas(height=200, width=200)
canvas.grid(column=1, row=0)
lock = PhotoImage(file="logo.png")
canvas.create_image(100, 100, image=lock)
website = Label(text="Website:")
website.grid(column=0, row=1, sticky="e")
email_user_name = Label(text="Email/Username:")
email_user_name.grid(column=0, row=2, sticky="e")
password = Label(text="Password:")
password.grid(column=0, row=3, sticky="e")
website_entry = Entry(width=35)
website_entry.grid(column=1, row=1, columnspan=2, sticky="w")
email_entry = Entry(width=35)
email_entry.grid(column=1, row=2, columnspan=2, sticky="w")
password_entry = Entry(width=21)
password_entry.grid(column=1, row=3, columnspan=2, sticky="w")
generate_button = Button(text="Generate Password")
generate_button.grid(column=3, row=3, sticky="w")
add_button = Button(text="Add", width=30)
add_button.grid(column=1, row=4, columnspan=2)
window.mainloop()
Note that I have added columnspan=2 to password_entry.grid(...) and moved generate_button to column 3.

Related

Python tkinter : how to resize widgets when i resize the screen

I'm beginner...
When the code below is executed, how do I make the widgets inside increase when the screen size is increased to width? but, it couldn't resized..
Does it matter if I use either pack or grid?
i can't solve it....
from tkinter import *
from tkinter import ttk
class program:
def __init__(self):
self.root = Tk()
self.root.title("Python")
self.root.resizable(True, True)
self.create_project()
def create_project(self):
Topic_Label = ttk.Label(self.root, text="program")
Topic_Label.pack(side="top")
Record_LabelFrame = LabelFrame(self.root, text="Record information")
Record_LabelFrame.pack(side="top", anchor=W, padx=10)
date = ttk.Label(Record_LabelFrame, text="date")
date.grid(column=0, row=0, sticky=W)
Topic_Label_Entry1 = ttk.Entry(Record_LabelFrame)
Topic_Label_Entry1.grid(column=0, row=1)
time = ttk.Label(Record_LabelFrame, text="time")
time.grid(column=1, row=0, sticky=W)
Topic_Label_Combo1 = ttk.Combobox(Record_LabelFrame)
Topic_Label_Combo1.grid(column=1, row=1)
recorder = ttk.Label(Record_LabelFrame, text="record")
recorder.grid(column=2, row=0, sticky=W)
Topic_Label_Entry2 = ttk.Entry(Record_LabelFrame)
Topic_Label_Entry2.grid(column=2, row=1)
loc = ttk.Label(Record_LabelFrame, text="location")
loc.grid(column=0, row=2, sticky="W")
RadioVar = IntVar()
Radio_Frame = Frame(Record_LabelFrame)
Radio_Frame.grid(column=0, row=3, sticky=W)
Topic_Label_Radio1 = ttk.Radiobutton(Radio_Frame, text="A", variable=RadioVar, value=1)
Topic_Label_Radio1.grid(column=0, row=0)
Topic_Label_Radio2 = ttk.Radiobutton(Radio_Frame, text="B", variable=RadioVar, value=2)
Topic_Label_Radio2.grid(column=1, row=0)
Topic_Label_Radio3 = ttk.Radiobutton(Radio_Frame, text="C", variable=RadioVar, value=3)
Topic_Label_Radio3.grid(column=2, row=0)
count = ttk.Label(Record_LabelFrame, text="count")
count.grid(column=1, row=2, sticky="W")
Topic_Label_Combo2 = ttk.Combobox(Record_LabelFrame)
Topic_Label_Combo2.grid(column=1, row=3)
seed_name = ttk.Label(Record_LabelFrame, text="seed")
seed_name.grid(column=2, row=2, sticky="W")
Topic_Label_Entry4 = ttk.Entry(Record_LabelFrame)
Topic_Label_Entry4.grid(column=2, row=3)
mt = program()
mt.root.mainloop()
I want to print like this that widget resize automatically when i resize the screen
https://i.stack.imgur.com/iSbaJ.png
https://i.stack.imgur.com/mzv9R.png

Why i can't fix the boxes alignment in Gridview on windows

there are some space between the result as you can see in the image that password entry and generate password aren't aligning together
*Result image
from tkinter import
window = Tk()
window.title("Password Manager")
window.config(padx=20, pady=20)
canvas = Canvas(width=200, height=200, highlightthickness=0)
password_image = PhotoImage(file="logo.png")
image = canvas.create_image(100, 100, image=password_image)
canvas.itemconfig(image)
canvas.grid(row=0, column=1)
website_label = Label(text="Website")
website_label.grid(row=1, column=0)
Email_username_label = Label(text="Email/Username")
Email_username_label.grid(row=2, column=0)
password_label = Label(text="Password")
password_label.grid(row=3, column=0)
website_input = Entry(width=35)
website_input.grid(row=1, column=1, columnspan=2)
Email_username_input = Entry(width=35)
Email_username_input.grid(row=2,column=1, columnspan=2)
password = Entry(width=21)
password.grid(row=3, column=1)
generate_button = Button(text="Generate Password")
generate_button.grid(row=3, column=2)
add_password_button = Button(text="Add", width=36)
add_password_button.grid(row=4, column=1, columnspan=2)
window.mainloop()
You can see that there is some space in password entry and generate password how to fix it
As noted in the comments, using the grid method allows you to just add sticky to align elements. In this case, I've removed all the width options in your entries and buttons with stick='EW' to expand East and West, or to the maximum left and right of the column the widget is in.
from tkinter import *
window = Tk()
window.title("Password Manager")
window.config(padx=20, pady=20)
# Canvas
canvas = Canvas(width=200, height=200, highlightthickness=0)
password_image = PhotoImage(file="logo.png")
image = canvas.create_image(100, 100, image=password_image)
canvas.itemconfig(image)
canvas.grid(row=0, column=1)
# Labels
website_label = Label(text="Website")
website_label.grid(row=1, column=0)
Email_username_label = Label(text="Email/Username")
Email_username_label.grid(row=2, column=0)
password_label = Label(text="Password")
password_label.grid(row=3, column=0)
# Entries
website_input = Entry()
website_input.grid(row=1, column=1, columnspan=2, sticky='EW') # sticky
Email_username_input = Entry()
Email_username_input.grid(row=2, column=1, columnspan=2, sticky='EW') # sticky
password = Entry()
password.grid(row=3, column=1, sticky='EW') # sticky
# Buttons
generate_button = Button(text="Generate Password")
generate_button.grid(row=3, column=2)
add_password_button = Button(text="Add")
add_password_button.grid(row=4, column=1, columnspan=2, sticky='EW') # sticky
window.mainloop()
You may also want to consider reading up on column and row weights using columnconfigure and rowconfigure if you want your GUI to resize dynamically.

How to save tkinter checkbox and Entry status and load it in next running

I'm working on tkinter python file with some changeable values using checkbox and Entry widgets, so i need to save these widgets state and values and load it in the next file execution, and this is my python code:
from tkinter import *
from tkinter import messagebox
gui=Tk()
firstVal = IntVar(value=90)
secVal = IntVar(value=1)
thirdVal = IntVar(value=0)
def apply_conf():
try:
int(textBox.get())
messagebox.showinfo(title="done", message="your done")
except ValueError:
messagebox.showerror(title="error", message="please enter valid number")
labelPlist = Label(gui,text = "first value ")
labelPlist.grid(column=0, row=3, padx=10, pady=4, sticky='w')
labelPlist = Label(gui,text = "second value")
labelPlist.grid(column=0, row=5, padx=10, pady=4, sticky='w')
labelPlist = Label(gui,text = "third value ")
labelPlist.grid(column=0, row=7, padx=10, pady=4, sticky='w')
textBox=Entry(gui, width=8, borderwidth=0)
textBox.grid(column=1, row=3, padx=7, pady=4, sticky='w')
checkBox = Checkbutton(gui,variable = secVal, borderwidth=0 )
checkBox.grid(column=1, row=5, padx=7, pady=4, sticky='w')
checkBox1 = Checkbutton(gui, variable = thirdVal, borderwidth=0 )
checkBox1.grid(column=1, row=7, padx=7, pady=4, sticky='w')
buttonDel=Button(gui, height=0, width=16, text="Apply all Changes", borderwidth=0, command=lambda: apply_conf())
buttonDel.grid(column=0, row=9,padx=10,pady=12)
buttonExit=Button(gui, height=0, width=8, text="Exit", borderwidth=0, command=gui.destroy)
buttonExit.grid(column=0, row=10, padx=20,pady=4)
gui.geometry("220x190")
mainloop()
Thanks in advance.
I encourage you to use pickle for this purpose. I modified slightly your code to exemplify how it works in case of the first variable:
from tkinter import *
from tkinter import messagebox
import pickle
import numpy as np
gui=Tk()
try:
firstVal_store=pickle.load(open("storage1.p","rb"))
firstVal=IntVar(value=firstVal_store)
secVal = IntVar(value=1)
thirdVal = IntVar(value=0)
print('Initial values loaded from memory!')
except:
firstVal = IntVar(value=90)
secVal = IntVar(value=1)
thirdVal = IntVar(value=0)
def apply_conf():
try:
int(textBox.get())
messagebox.showinfo(title="done", message="your done")
#let's save the variables...
firstVal_store=textBox.get()
pickle.dump(firstVal_store,open("storage1.p","wb"))
print("Stored!",firstVal_store)
except ValueError:
messagebox.showerror(title="error", message="please enter valid number")
labelPlist = Label(gui,text = "first value ")
labelPlist.grid(column=0, row=3, padx=10, pady=4, sticky='w')
labelPlist = Label(gui,text = "second value")
labelPlist.grid(column=0, row=5, padx=10, pady=4, sticky='w')
labelPlist = Label(gui,text = "third value ")
labelPlist.grid(column=0, row=7, padx=10, pady=4, sticky='w')
textBox=Entry(gui, width=8, borderwidth=0)
textBox.insert(0,firstVal.get())
textBox.grid(column=1, row=3, padx=7, pady=4, sticky='w')
checkBox = Checkbutton(gui,variable = secVal, borderwidth=0 )
checkBox.grid(column=1, row=5, padx=7, pady=4, sticky='w')
checkBox1 = Checkbutton(gui, variable = thirdVal, borderwidth=0 )
checkBox1.grid(column=1, row=7, padx=7, pady=4, sticky='w')
buttonDel=Button(gui, height=0, width=16, text="Apply all Changes", borderwidth=0, command=lambda: apply_conf())
buttonDel.grid(column=0, row=9,padx=10,pady=12)
buttonExit=Button(gui, height=0, width=8, text="Exit", borderwidth=0, command=gui.destroy)
buttonExit.grid(column=0, row=10, padx=20,pady=4)
gui.geometry("220x190")
mainloop()
...if you find it convenient, simply extend the idea to cover also the other variables.

Adjusting location of Entry in Tkinter

I am trying to get the text username and password in the below Tkinter to be next to the Entry, I have tried to play with the columns but it didn't fix it. I was previously using pack() but switched to grid() to be more in control of the location of the labels.
Here is the code:
root = Tk()
root.title("Bookmark Search")
root.resizable(0,0)
greeting= Label(root, text="Hi, This is a Trial to see how the label works !")
help=Label(root, text=" How can I help you today?")
greeting.grid(row = 0, column= 1, pady=5, padx=200)
help.grid(row = 1, column= 1,pady=5)
e = Entry(root, width=50)
e.grid(row=2, column = 1,rowspan=2, pady=15)
mySubmit = Label(root)
-------several lines of unrelated code-------
mySubmit.bind("<Button-1>", open_url)
root.bind('<Return>', myClick)
myButton= Button(root, text="Submit", command=myClick)
myButton.grid(row=4, column = 1,rowspan=2, pady=10)
# username
username_label = Label(root, text="Username:")
username_label.grid(column=0, row=8, padx=5, pady=5)
username_entry = Entry(root)
username_entry.grid(column=1, row=8, padx=5, pady=5)
# password
password_label = Label(root, text="Password:")
password_label.grid(column=0, row=9, padx=5, pady=5)
password_entry = Entry(root)
password_entry.grid(column=1, row=9, padx=5, pady=5)
# login button
login_button = Button(root, text="Login")
login_button.grid(column=1, row=10,padx=5, pady=5)
root.mainloop()
Here is a print screen of the current output:
Here is the required output:
You can put Labels and Buttons in Frame and then Frame put in main window.
import tkinter as tk # PEP8: `import *` is not preferred
# --- functions --- (PEP8: lower_case_names)
def open_url():
pass
def my_click():
pass
# --- main ---
root = tk.Tk()
root.title("Bookmark Search")
root.resizable(0,0)
greeting = tk.Label(root, text="Hi, This is a Trial to see how the label works !")
help = tk.Label(root, text=" How can I help you today?")
greeting.grid(row=0, column=1, pady=5, padx=200)
help.grid(row=1, column=1, pady=5)
e = tk.Entry(root, width=50)
e.grid(row=2, column=1, pady=15)
my_submit = tk.Label(root, text='LABEL')
my_submit.grid(row=3, column=1, pady=10)
my_submit.bind("<Button-1>", open_url)
root.bind('<Return>', my_click)
my_button = tk.Button(root, text="Submit", command=my_click)
my_button.grid(row=4, column=1, pady=10)
# - start Frame - to group widgets -
frame = tk.Frame(root)
frame.grid(column=1, row=5)
# username
username_label = tk.Label(frame, text="Username:")
username_label.grid(column=0, row=8, padx=5, pady=5)
username_entry = tk.Entry(frame)
username_entry.grid(column=1, row=8, padx=5, pady=5)
# password
password_label = tk.Label(frame, text="Password:")
password_label.grid(column=0, row=9, padx=5, pady=5)
password_entry = tk.Entry(frame)
password_entry.grid(column=1, row=9, padx=5, pady=5)
# - end Frame -
# login button
login_button = tk.Button(root, text="Login")
login_button.grid(column=1, row=10, padx=5, pady=5)
root.mainloop()
PEP 8 -- Style Guide for Python Code

How to get only a corresponding entry box regardless of how many times I change radiobutton?

from tkinter import *
win=Tk()
var = StringVar()
l = Label(win, bg='white', width=15)
l.grid(row=17,column=1,padx=10, pady=10, sticky='w')
def print1_selection():
if var.get()=="Number":
lab1= Label(win, text="Enter a number").grid(row=4, column=0)
ent1=Entry(win).grid(row=4, column=1)
l.config(text='you have selected ' + var.get())
elif var.get()=="Alphabet":
lab21= Label(win, text="Enter an alphabet").grid(row=5, column=0)
ent21=Entry(win).grid(row=5, column=1)
l.config(text='you have selected ' + var.get())
lbl4=Label(win, text="Select One", bg="crimson", fg="white", font=("times new
roman",15,"bold")).grid(row=1, column=0, padx=10, pady=10, sticky='w')
r1 = Radiobutton(win, text='Number',variable=var, value='Number', command=print1_selection, width=22)
r1.grid(row=2,column=0,padx=10, pady=10)
r2 = Radiobutton(win, text='Alphabet', variable=var, value='Alphabet', command=print1_selection, width=22)
r2.grid(row=2,column=1,padx=10, pady=10)
win.mainloop()
In this code I want that when I select radiobutton number, only enter a number should appear and same for the other.
But the problem is that when I select number after selecting alphabet, it shows both. I need only the selected one and eliminate the other instantly.
This is how I would approach this issue:
from tkinter import Tk, StringVar, Label, Frame, Entry, Radiobutton
def print1_selection():
for widget in entry_frame.winfo_children():
widget.destroy()
value = var.get()
lbl.config(text='You have selected ' + value)
if value == "Number":
Label(entry_frame, text="Enter a number").grid(row=0, column=0)
Entry(entry_frame).grid(row=0, column=1)
elif value == "Alphabet":
Label(entry_frame, text="Enter an alphabet").grid(row=0, column=0)
Entry(entry_frame).grid(row=0, column=1)
win = Tk()
var = StringVar(value=0)
entry_frame = Frame(win)
entry_frame.grid(row=2, column=0, columnspan=2)
lbl = Label(win, bg='white', width=20)
lbl.grid(row=3, column=0, columnspan=2, padx=10, pady=10, sticky='w')
Label(win, text="Select One", bg="crimson", fg="white", font=("times new roman", 15, "bold")).grid(row=0, column=0, padx=10, pady=10, sticky='w')
Radiobutton(win, text='Number', variable=var, value='Number', command=print1_selection, width=22).grid(row=1, column=0, padx=10, pady=10)
Radiobutton(win, text='Alphabet', variable=var, value='Alphabet', command=print1_selection, width=22).grid(row=1, column=1, padx=10, pady=10)
win.mainloop()
As You can see if You don't plan on using the widgets instance anywhere You don't have to assign it to a variable. Also no need to configure label in both statements since that will be done anyways so just do it at the beginning, also rows start from 0 too. Frames help with organizing widgets. Also if You want neither of the radiobuttons selected set the variable to 0.

Categories