I want to capture the time(in milliseconds) taken by a person to type a password, that is, from the first key press to the time the person presses Enter
button. To accomplish this, I have the following code:
import tkinter as tk
import time
class MyApp(object):
start=0.0
end=0.0
total_time=0.0
def __init__(self, master):
self.pass1 = tk.Entry(master,show="*")
self.pass1.bind('<Key>', self.callback1)
self.pass1.pack()
def callback1(self, event): # Called Only by first key press
self.start=time.time()*1000.0 # start variable must be modified ONLY by first key press
def callback2(self,event): # called by Enter Key press
self.end=time.time()*1000.0
self.total_time=self.start-self.end
print(self.totaltime)
root = tk.Tk()
app = MyApp(root)
root.mainloop()
The problem I am having is I am not able to bind callback1
and callback2
on pass1
. What I wanted was that when a person hit the first key of their password, start
is set to the current time and when the person press Enter
end
is initialized to the current time. I hope these two would give me an approximate of the time.
How can i modify the program above to accomplish what I want? Thanks.
To bind the <Enter> key with an event in Tkinter window, we can use bind('<Return>', callback) by specifying the key and the callback function as the arguments. Once we bind the key to an event, we can get full control over the events.
The binding function is used to deal with the events. We can bind Python's Functions and methods to an event as well as we can bind these functions to any particular widget. Code #1: Binding mouse movement with tkinter Frame.
The Tkinter button has only one command property so that multiple commands or functions should be wrapped to one function that is bound to this command .
Firstly, you need to bind callback2
to the Enter / Return Key
this is done using '<Return>'
.
def __init__(self, master):
self.pass1 = tk.Entry(master,show="*")
self.pass1.bind('<Key>', self.callback1)
self.pass1.bind('<Return>', self.callback2) # callback2 bound to Enter / Return key
self.pass1.pack()
Next, you want to only allow callback1 to run once. To do this, unbind it from the widget like so
def callback1(self, event):
self.start=time.time()*1000.0
self.pass1.unbind('<Key>') # unbind callback1
And then finally rebind it once the Enter key is pressed, so in the callback2 function
def callback2(self,event): # called by Enter Key press
self.end=time.time()*1000.0
self.total_time=self.end-self.start
print(self.total_time)
self.pass1.bind('<Key>', self.callback1) # rebind callback1
Side Notes:
As you can see I changed the ordering for the time to end - start
instead of what you had before which was start - end
which gives you a negative value.
I also suggest changing '<Key>'
to '<KeyRelease>'
Your other options if you don't want to unbind the function is to use an if statement checking if self.start
has a value.
if self.start == 0.0:
self.start=time.time()*1000.0
You should also put your variables inside the __init__
function.
def __init__(self, master):
self.start=0.0
self.end=0.0
self.total_time=0.0
...
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With