I am trying to create a macro that i can call in python , the macro would record what buttons i pressed , how long i pressed them for, and the time between button presses
i want to be able to store the macro in a txt file so i can call it back with another function later on in time
this was the basic idea i thought off since i can use rk = keyboard.record(until ='Esc')
then after i done recording the macro i use keyboard.play(rk, speed_factor=1)
, that concept i just described works wonderfull, but i want to be able to store the rk = keyboard.record(until ='Esc')
into a txt file and then be able to read it from the file and play it
this code below is the idea i was trying to achieve but it doesn't work
from pynput.keyboard import Key, Listener
import keyboard
import time
def recorder():
rk = keyboard.record(until ='Esc')
file = open("test.txt", "a")
for r in rk:
data = str(r) + "\n"
file.write(data)
def play_back():
file = open("test.txt", "r")
lists = []
Lines = file.readlines()
count = 0
# Strips the newline character
for line in Lines:
count += 1
if line[-1] == "\n":
lists.append(line[:-1])
else:
lists.append(line)
print(lists)
keyboard.play(lists, speed_factor=1)
this is the error code that appears after i call on the play_back()
function
['KeyboardEvent(s down)', 'KeyboardEvent(s up)', 'KeyboardEvent(s down)', 'KeyboardEvent(s up)', 'KeyboardEvent(a down)', 'KeyboardEvent(a up)', 'KeyboardEvent(a down)', 'KeyboardEvent(a up)', 'KeyboardEvent(d down)', 'KeyboardEvent(d up)', 'KeyboardEvent(d down)', 'KeyboardEvent(d up)', 'KeyboardEvent(backspace down)', 'KeyboardEvent(backspace up)', 'KeyboardEvent(backspace down)', 'KeyboardEvent(backspace up)', 'KeyboardEvent(backspace down)', 'KeyboardEvent(backspace up)', 'KeyboardEvent(backspace down)', 'KeyboardEvent(backspace up)', 'KeyboardEvent(backspace down)', 'KeyboardEvent(backspace up)', 'KeyboardEvent(backspace down)', 'KeyboardEvent(backspace up)', 'KeyboardEvent(esc down)', 'KeyboardEvent(left down)', 'KeyboardEvent(left up)', 'KeyboardEvent(down down)', 'KeyboardEvent(down up)', 'KeyboardEvent(right down)', 'KeyboardEvent(right up)', 'KeyboardEvent(right down)', 'KeyboardEvent(right up)', 'KeyboardEvent(s down)', 'KeyboardEvent(s up)', 'KeyboardEvent(s down)', 'KeyboardEvent(s up)', 'KeyboardEvent(d down)', 'KeyboardEvent(d up)', 'KeyboardEvent(a down)', 'KeyboardEvent(a up)', 'KeyboardEvent(s down)', 'KeyboardEvent(s up)', 'KeyboardEvent(esc down)']
Traceback (most recent call last):
File "c:\Users\pc\Desktop\code\program1\testing122.py", line 33, in <module>
play_back()
File "c:\Users\pc\Desktop\code\program1\testing122.py", line 31, in play_back
keyboard.play(lists, speed_factor=1)
File "C:\Users\pc\Desktop\code\program1\venv001\Lib\site-packages\keyboard\__init__.py", line 1060, in play
last_time = event.time
^^^^^^^^^^
AttributeError: 'str' object has no attribute 'time'. Did you mean: 'title'?
so just to summarize : I want to record a macro of my exact button presses including the timings within (how much I press a button for, how much time time between 2 button presses) i then want to be able to call that record with a function in python , my approach here might be wrong so i would love your inputs
Thanks in advance
update:
with the help of LhasaDad he came up with this bit of code that records the keyboard inputs and puts them in a txt file and call them back with theplay_back()
function
def recorder():
rk = keyboard.record(until ='Esc')
file = open("test.txt", "w")
for r in rk:
# serialize the object to json format
data = r.to_json() + "\n"
file.write(data)
file.close()
def play_back():
lists = []
with open("test.txt", "r") as file:
lines = file.readlines()
# Strips the newline character
for line in lines:
# recreate the object from the json dict by loading the json and
# use as keyword parameters to KeyboardEvent
lists.append(keyboard.KeyboardEvent(**json.loads(line)))
print(lists)
keyboard.play(lists, speed_factor=1)
now the problem now is a wierd one if i run the code by calling therecorder()
function followed by the play_back()
like this
recorder()
play_back()
it works as intended but if i run the recorder()
function first and record my inputs and let the recorder function finish and the program finish running all its code
example
recorder()
so am only running the recorder function that saves it to a file, then i try to run it later with the play_back after the first program is done
play_back()
it doesnot work
ok i have found the answer , it turns out there is a problem withing the keyboard.record
and keyboard.play
for some reason as mentioned in this stack overflow article over here
keyboard.play function not working correctly
here is the solution
from pynput.keyboard import Key, Listener
import keyboard
import time
import json
import pickle
def recorder():
with open('keys.txt','wb') as f:
pickle.dump(keyboard.record(until='*'),f)
def play_back():
keyboard.start_recording()
keyboard.stop_recording()
with open('keys.txt','rb') as f:
keyboard.play(pickle.load(f))
play_back()
in the above example am using pickle and I have already used the record()
function to record the actions
keyboard.start_recording
and keyboard.stop_recording
donot impact the code but for some random reason it makes it work
https://github.com/boppreh/keyboard/issues/283
This is an open issue on the keyboard repository. Looks like keyboard.play()
does not initialize the OS-specific modules required to interface with the keyboard (or maybe there's something else going on, I'm not sure).