Here is where I believe I would put the code for the restrictions
def savePassword():
os.system("Email.py")
if txt.get() == txt1.get():
# encode password for hashing
hashedPassword = hashPassword(txt.get().encode("utf-8"))
# insert masterpassword into database
insert_password = """INSERT INTO masterpassword(password)
VALUES(?) """
cursor.execute(insert_password, [hashedPassword])
sql_command = 'INSERT INTO details (email) VALUES(?) ' # Query
email = txt3.get()
cursor.execute(sql_command, [email])
db.commit()
passwordVault()
else:
lbl2.config(text="Passwords do not match")
i'd like it so that if the password does not reach a length requirement of say 7
Entry widget has validate and validatecommand that can do this job.
Here's an example code:
from tkinter import *
def check(ch):
return len(ch) <= 7 or ch==''
root = Tk()
ent = Entry(root, show='*')
ent.config(validate='key', validatecommand=(root.register(check), "%P"))
ent.pack()
root.mainloop()
update:
from tkinter import *
def savePasswd():
if len(ent.get())>7:
label['text'] = 'saved'
print("saved") # write save stmts here
else:
label['text']="Minimum length 7"
root = Tk()
label = Label(root)
label.pack()
ent = Entry(root, show='*')
ent.pack()
Button(root, text='save password', command=savePasswd).pack()
root.mainloop()
Related
I'm trying to build my first app using python and tkinter.
I'm stuck where I can't run the content from another class into the same first window.
The first window is a login window, here is the full code of the class:
import tkinter as tk
import sqlite3
from tkinter import *
from gamecontent import Gamecontent
class MainApp(Tk):
def __init__(self):
Tk.__init__(self)
self.title('Word Warrior - Sign In')
self.geometry("650x510")
self.resizable(width=False, height=False)
# Create widgets
self.label_username = tk.Label(self, text="Username")
self.label_password = tk.Label(self, text="Password")
self.entry_username = tk.Entry(self)
self.entry_password = tk.Entry(self, show="*")
self.button_login = tk.Button(self, text="Login", command=self.login)
self.button_createacc = tk.Button(self, text="Create Account", command=self.createacc)
# Place widgets
self.label_username.place(x=200, y=150)
self.label_password.place(x=200, y=200)
self.entry_username.place(x=280, y=152, width=140, height=27)
self.entry_password.place(x=280, y=202, width=140, height=27)
self.button_login.place(x=280, y=242, width=140, height=27)
self.button_createacc.place(x=280, y=282, width=140, height=27)
# Create database and tables and cursor object
self.conn = sqlite3.connect('users.db')
self.c = self.conn.cursor()
self.c.execute("CREATE TABLE IF NOT EXISTS users (username text UNIQUE, password text)")
self.conn.commit()
self.conn.close()
def clear_content(self):
for widget in self.winfo_children():
widget.destroy()
def login(self):
# Get the username and password from the entry widgets
username = self.entry_username.get()
password = self.entry_password.get()
# Fetch username and password from the database
conn = sqlite3.connect('users.db')
c = conn.cursor()
c.execute("SELECT * FROM users WHERE username=? AND password=?", (username, password))
result = c.fetchone()
conn.close()
# Check if the username and password are correct
if result:
# If the login is successful, open a new window with the flashcard game
self.clear_content()
Gamecontent()
else:
# If the login is not successful, display an error message
self.label_message = tk.Label(self, text=" Wrong credentials ")
self.label_message.place(x=285, y=322)
def createacc(self):
# Get the username and password from the entry widgets
username = self.entry_username.get()
password = self.entry_password.get()
# Checks if user is entering an empty username/password while creating
if username == "" or password == "":
self.label_message = tk.Label(self, text=" Can't be empty ")
self.label_message.place(x=290, y=322)
else:
# Connect to the database (or create it if it doesn't exist)
conn = sqlite3.connect('users.db')
c = conn.cursor()
# Create the table if it doesn't exist
c.execute('''CREATE TABLE IF NOT EXISTS users
(username text, password text)''')
# Checks if an account with the same username exists
c.execute("SELECT * FROM users WHERE username = ?", (username,))
if c.fetchone() is None:
c.execute("INSERT INTO users VALUES (?, ?)", (username, password))
conn.commit()
self.label_message = tk.Label(self, text=" Account created ")
self.label_message.place(x=290, y=322)
else:
self.label_message = tk.Label(self, text=" Username exists ")
self.label_message.place(x=290, y=322)
# Close the connection
conn.close()
app = MainApp()
app.mainloop()
The change must be done when the login is correct, exactly in
self.clear_content()
Gamecontent()
The problem is that Gamecontent opens in another window and not into the same window.
Here is the code for Gamecontent class
from tkinter import *
from random import randint
from gamedata import words, count
class Gamecontent(Tk):
def __init__(self):
Tk.__init__(self)
self.title('Word Warrior - Play')
self.geometry("650x510")
self.resizable(width=False, height=False)
def next():
global hinter, hinter_count
# Clear the screen
answer_label.config(text="")
my_entry.delete(0, END)
hint_label.config(text="")
# Reset Hint stuff
hinter = ""
hinter_count = 0
# Create random selection
global random_word
random_word = randint(0, count-1)
# update label with Spanish Word
spanish_word.config(text=words[random_word][0])
def answer():
if my_entry.get().capitalize() == words[random_word][1]:
answer_label.config(text=f"Correct! {words[random_word][0]} is {words[random_word][1]}")
else:
answer_label.config(text=f"Incorrect! {words[random_word][0]} is not {my_entry.get().capitalize()}")
def hint():
global hinter_count
global hinter
if hinter_count < len(words[random_word][1]):
hinter = hinter + words[random_word][1][hinter_count]
hint_label.config(text=hinter)
hinter_count +=1
# Labels
spanish_word = Label(self, text="", font=("Helvetica", 36))
spanish_word.pack(pady=50)
answer_label = Label(self, text="")
answer_label.pack(pady=20)
my_entry = Entry(self, font=("Helvetica", 18))
my_entry.pack(pady=20)
# Create Buttons
button_frame = Frame(self)
button_frame.pack(pady=20)
answer_button = Button(button_frame, text="Answer", command=answer)
answer_button.grid(row=0, column=0, padx=20)
next_button = Button(button_frame, text="Next", command=next)
next_button.grid(row=0, column=1)
hint_button = Button(button_frame, text="Hint", command=hint)
hint_button.grid(row=0, column=2, padx=20)
# Create Hint Label
hint_label = Label(self, text="")
hint_label.pack(pady=15)
# Run next function when program starts
next()
self.mainloop()
I'm stuck with this for a while and can't move forward, I'm not even sure it's possible with tkinter to do so.
I tried clearing the content of the window and start an instance of the second class but it opens in another window.
Change
self.clear_content()
Gamecontent()
to
self.clear_content()
Gamecontent(self)
In gamecontent itself change
class Gamecontent(Tk):
def __init__(self):
Tk.__init__(self)
self.title('Word Warrior - Play')
self.geometry("650x510")
self.resizable(width=False, height=False)
to
class Gamecontent(Frame):
def __init__(self, parent):
Frame.__init__(self, parent)
#self.config(bg="white")
self.pack(fill=BOTH, expand=True)
parent.title('Word Warrior - Play')
This makes gamecontent to a frame which packs itself into your main app
I have an iteration in my code which show for each line : ID / Name / Button Delete. You can see the image below. I would like when i click on one of the delete button that the data on the same line be deleted.
I try my best, you can see my code. How i can do it ?
Thank you a lot.
from tkinter import *
import mysql.connector
def main():
root = Tk()
conn = mysql.connector.connect(user='root', password='', host='localhost',
database='showmanager')
my_cursor = conn.cursor()
var_i = 3
def del_customer():
my_cursor.execute("DELETE FROM `spectator` "
"WHERE `spectator`.`id_customer` = "+user[0]+"")
my_cursor.execute("SELECT * FROM spectator")
users = my_cursor.fetchall()
for user in users:
label = Label(root, text=user, font=9)
label.grid(row=int(var_i), column=1)
Button(root, text="Delete spectator", font=9, height=1,
command=del_customer).grid(row=int(var_i), column=4)
var_i = var_i + 1
root.mainloop()
if __name__ == '__main__':
main()
You can pass the customer ID and corresponding widgets (label and button) to del_customer() so that you can remove the record in the database based on the customer ID and the corresponding label and button inside the function:
def del_customer(cust_id, widgets):
my_cursor.execute("DELETE FROM spectator WHERE id_customer = %s", [cust_id])
conn.commit() # make the change effective
# remove the corresponding label and button
for w in widgets:
w.destroy()
...
for user in users:
label = Label(root, text=user)
label.grid(row=var_i, column=1)
btn = Button(root, text="Delete spectator")
btn.grid(row=var_i, column=4)
var_i += 1
# pass the customer ID, label and button to del_customer()
btn['command'] = lambda cust_id=user[0], widgets=(label, btn): del_customer(cust_id, widgets)
my program is meant say 'Accessed granted' if i enter the correct username and password, however regardless of what i type, i keep getting 'Invalid login' can someone point out whats wrong? btw dont worry about it the indentation is wrong, it changes when it put code on this site.
from tkinter import *# Ingress all components from Tkinter
import tkinter.messagebox as box
def dialog1():
username=entry1.get()
password = entry2.get()
if (username == 'admin' and password == 'ad121'):#Correct log in details
box.showinfo('info','Access granted')# correct response
else:
box.showinfo('info','Invalid Login')# decline response
def condition():
while condition == (username == 'admin' and password == 'ad121'):
print = label(text('Welcome back admin user!',bg='Light Blue',font='none 14 bold').place(x=0,y=160))
window = Tk()
window.geometry('400x400')# The size of the form window
window.title('Office login system')#title of the form
frame = Frame(window)
mlabel = Label(text='Log in system', bg='Light Blue',font='none 18 bold underline')# The colours and font style and size used for the form title
mlabel.pack()
Label1 = Label(window,text = 'Username:',bg='Light Blue',font='none 14 bold').place(x=0,y=100)
entry2 = Entry(window).place(x=140,y=108)#Size and colour of the text box
entry1 = Entry(window,bd =5)
entry1.pack
Label2 = Label(window,text = 'Password:',bg='Light Blue',font='none 14 bold').place(x=0,y=150)
entry2 = Entry(window).place(x=140,y=155)#Size and colour of the text box
entry2 = Entry(window, bd=5)
entry2.pack
window.configure(background='Orange')
btn = Button(window, text = 'Check Login',command = dialog1)
btn.place(x=150,y=250)
frame.pack(padx =200,pady =190)
window.mainloop()# The code iterates
You are declaring entry2 multiple times in the scope of your script.
I tried this and it works as you expect.
from tkinter import Button, Entry, Tk
import tkinter.messagebox as box
class GUI:
def __init__(self):
self.root = Tk()
self.username_field = Entry(self.root)
self.password_field = Entry(self.root)
self.username_field.insert(0, "Enter Username")
self.password_field.insert(0, "Enter Password")
self.submit = Button(self.root, text="Submit", command=self.login)
self.username_field.pack()
self.password_field.pack()
self.submit.pack()
def login(self):
username = self.username_field.get()
password = self.password_field.get()
print(username, password)
# The while loop
while username == password:
box.showinfo("info", "Username and password must not match!")
break
if(username == "admin" and password == "ad121"):
box.showinfo("info", "Welcome " + username + "!")
else:
box.showinfo("info", "Invalid credentials")
app = GUI()
app.root.mainloop()
Working on a group program that has users and passwords. We are trying to insert our users and passwords via python to sqlite. But atm we are only sending blank data before our graphic window pops up with a button that is supposed to send the data. We have tried different variations found on multiple websites but nothing seems to work.
from tkinter import *
import sqlite3
import sys
conn = sqlite3.connect('indexCards.db')
cur = conn.cursor()
users ={}
def addUser(entUsername, entPassword):
#global entUsername, entPassword
NAME = entUsername.get()
PASSWORD = entPassword.get()
print("add User") #this is testing only
print(NAME, PASSWORD) # this is testing to see the passed variable
//
//This is where we are having the issues
conn.executemany('INSERT INTO USER(NAME,PASSWORD)\
VALUES (? ,?);', [(NAME,PASSWORD)])
conn.commit();
return (NAME, PASSWORD)
def makeWindow():
global entUsername, entPassword
window = Tk()
window.title('Add New User')
lblInst = Label(window, text = "Create your account here:", font=("Helvetica",16))
lblInst.pack()
lblUsername = Label(window, text="Please enter a username: ")
entUsername = Entry(window)
lblUsername.pack()
entUsername.pack()
lblPassword = Label(window, text="Please enter a password: ")
entPassword = Entry(window)
lblPassword.pack()
entPassword.pack()
btn = Button(window, text="Create", command=addUser(entUsername, entPassword))
btn.pack()
print (addUser(entUsername, entPassword))
print('entUsername', 'entPassword')
#window.mainloop()
return window
#if __name__ == '__main__':
# main():
window = makeWindow()
window.mainloop()
The problem is that you're calling the function immediately, before the user has a chance to enter any data.
See Why is Button parameter “command” executed when declared?
The reason it invokes the method immediately and pressing the button does nothing is that addUser(entUsername, entPassword) is evaluated and its return value is attributed as the command for the button. So if addUser prints something to tell you it has run and returns None, you just run addUser to evaluate its return value and given None as the command for the button.
To have buttons to call functions with different arguments you can use global variables, although I can't recommend it:
import sqlite3
from tkinter import *
conn = sqlite3.connect('indexCards.db')
cur = conn.cursor()
users = {}
cur = conn.cursor()
cur.execute('''
Create table if not exists USER(NAME varchar(100), PASSWORD varchar(100))
''')
def addUser():
NAME = entUsername.get()
PASSWORD = entPassword.get()
print("add User") # this is testing only
print(NAME, PASSWORD) # this is testing to see the passed variable
# This is where we are having the issues
conn.executemany('INSERT INTO USER(NAME,PASSWORD) VALUES (? ,?);', [(NAME, PASSWORD)])
conn.commit()
return (NAME, PASSWORD)
def makeWindow():
global entUsername
global entPassword
window = Tk()
window.title('Add New User')
lblInst = Label(window, text="Create your account here:", font=("Helvetica", 16))
lblInst.pack()
lblUsername = Label(window, text="Please enter a username: ")
entUsername = Entry(window)
lblUsername.pack()
entUsername.pack()
lblPassword = Label(window, text="Please enter a password: ")
entPassword = Entry(window)
lblPassword.pack()
entPassword.pack()
btn = Button(window, text="Create", command=addUser)
btn.pack()
print(addUser())
window.mainloop()
return window
window = makeWindow()
If you don't want to create global then you can pass the function with multiple arguments to an anonymous function i.e lambda function
btn = Button(window, text="Create", command= lambda : addUser(entUsername, entPassword))
In the below code two tkinter entry is created entry1 and entry2 respectively for username and password. What I am looking for is storing the value entered in the tkinter entry to the database table admin_details. But nothing is passed. Also I have no idea in using the condition i.e. " retrieve the values inserted in the tkinter entry and store the data inside the table after the button Login is pressed."
Code is something like below:
import MySQLdb as mdb
from Tkinter import *
from tkMessageBox import *
root = Tk()
test=StringVar()
label1=Label(root,text='Username').grid()
entry1 = Entry(root, textvariable='uname')
entry1.grid()
label2=Label(root,text='password').grid()
entry2 = Entry(root, textvariable='pword')
entry2.grid()
print entry2
uname = entry1.get()
pword= entry2.get()
tup=[uname,pword]
option1 = Button(root, text = 'Login', command = next)
option1.grid()
if uname!='':
def next():
con = mdb.connect('localhost', 'root', 'root', 'kuis');
with con:
cur = con.cursor()
insert_sql = 'INSERT INTO admin_details(username, password) VALUES("{0}","{1}")'.format(*tup)
cur.execute(insert_sql)
root.mainloop()
The obvious problem is you are getting the text from both Entries directly after they have been initialized. The two variables you are using for this will not be changed when the Text in the Entries changes.
Here is some basic code how to retrieve the values from the two entry fields and pass them to a function:
import tkinter as Tk
import tkinter.messagebox
def show_pass_user(password, user):
# show what we got
tkinter.messagebox.showinfo("Data received", "Hey just got your username \"" + user + "\"" +
" and password \"" + password + "\"")
# run your sql here
def main():
root = Tk.Tk()
entry_user = Tk.Entry(root)
entry_user.insert(0, "Username")
entry_pass = Tk.Entry(root)
entry_pass.insert(0, "Password")
# use a lambda to get Username and Password when button is pressed
pressme = Tk.Button(root, text="Press Me", command=lambda:
show_pass_user(entry_pass.get(), entry_user.get()))
entry_user.grid()
entry_pass.grid()
pressme.grid()
root.mainloop()
if __name__ == "__main__":
main()
This code runs only with Python3!