short summary:
I am trying to create a program that will send keyboard events to the computer that for all purposes the simulated events should be t
For both python3 and python2 you can use pyautogui (pip install pyautogui
)
from pyautogui import press, typewrite, hotkey
press('a')
typewrite('quick brown fox')
hotkey('ctrl', 'w')
It's also crossplatform with Windows, OSX, and Ubuntu LTS.
regarding the recommended answer's code,
For my bot the recommended answer did not work. This is because I'm using Chrome which is requiring me to use KEYEVENTF_SCANCODE in my dwFlags.
To get his code to work I had to modify these code blocks:
class KEYBDINPUT(ctypes.Structure):
_fields_ = (("wVk", wintypes.WORD),
("wScan", wintypes.WORD),
("dwFlags", wintypes.DWORD),
("time", wintypes.DWORD),
("dwExtraInfo", wintypes.ULONG_PTR))
def __init__(self, *args, **kwds):
super(KEYBDINPUT, self).__init__(*args, **kwds)
# some programs use the scan code even if KEYEVENTF_SCANCODE
# isn't set in dwFflags, so attempt to map the correct code.
#if not self.dwFlags & KEYEVENTF_UNICODE:l
#self.wScan = user32.MapVirtualKeyExW(self.wVk,
#MAPVK_VK_TO_VSC, 0)
# ^MAKE SURE YOU COMMENT/REMOVE THIS CODE^
def PressKey(keyCode):
input = INPUT(type=INPUT_KEYBOARD,
ki=KEYBDINPUT(wScan=keyCode,
dwFlags=KEYEVENTF_SCANCODE))
user32.SendInput(1, ctypes.byref(input), ctypes.sizeof(input))
def ReleaseKey(keyCode):
input = INPUT(type=INPUT_KEYBOARD,
ki=KEYBDINPUT(wScan=keyCode,
dwFlags=KEYEVENTF_SCANCODE | KEYEVENTF_KEYUP))
user32.SendInput(1, ctypes.byref(input), ctypes.sizeof(input))
time.sleep(5) # sleep to open browser tab
PressKey(0x26) # press right arrow key
time.sleep(2) # hold for 2 seconds
ReleaseKey(0x26) # release right arrow key
I hope this helps someone's headache!
Here is the more complete version of @Phylliida answer in form of class with code example:
#!/usr/bin/python
# Script simulating keyboard events in macOS.
# See: https://stackoverflow.com/q/13564851/55075
import sys
import time
from Quartz.CoreGraphics import CGEventCreateKeyboardEvent
from Quartz.CoreGraphics import CGEventPost
from Quartz.CoreGraphics import kCGHIDEventTap
#from Quartz.CoreGraphics import CFRelease # Python releases things automatically.
class Keyboard():
shiftChars = {
'~': '`',
'!': '1',
'@': '2',
'#': '3',
'$': '4',
'%': '5',
'^': '6',
'&': '7',
'*': '8',
'(': '9',
')': '0',
'_': '-',
'+': '=',
'{': '[',
'}': ']',
'|': '\\',
':': ';',
'"': '\'',
'<': ',',
'>': '.',
'?': '/'
}
keyCodeMap = {
'a' : 0x00,
's' : 0x01,
'd' : 0x02,
'f' : 0x03,
'h' : 0x04,
'g' : 0x05,
'z' : 0x06,
'x' : 0x07,
'c' : 0x08,
'v' : 0x09,
'b' : 0x0B,
'q' : 0x0C,
'w' : 0x0D,
'e' : 0x0E,
'r' : 0x0F,
'y' : 0x10,
't' : 0x11,
'1' : 0x12,
'2' : 0x13,
'3' : 0x14,
'4' : 0x15,
'6' : 0x16,
'5' : 0x17,
'=' : 0x18,
'9' : 0x19,
'7' : 0x1A,
'-' : 0x1B,
'8' : 0x1C,
'0' : 0x1D,
']' : 0x1E,
'o' : 0x1F,
'u' : 0x20,
'[' : 0x21,
'i' : 0x22,
'p' : 0x23,
'l' : 0x25,
'j' : 0x26,
'\'' : 0x27,
'k' : 0x28,
';' : 0x29,
'\\' : 0x2A,
',' : 0x2B,
'/' : 0x2C,
'n' : 0x2D,
'm' : 0x2E,
'.' : 0x2F,
'`' : 0x32,
'k.' : 0x41,
'k*' : 0x43,
'k+' : 0x45,
'kclear' : 0x47,
'k/' : 0x4B,
'k\n' : 0x4C,
'k-' : 0x4E,
'k=' : 0x51,
'k0' : 0x52,
'k1' : 0x53,
'k2' : 0x54,
'k3' : 0x55,
'k4' : 0x56,
'k5' : 0x57,
'k6' : 0x58,
'k7' : 0x59,
'k8' : 0x5B,
'k9' : 0x5C,
# keycodes for keys that are independent of keyboard layout
'\n' : 0x24,
'\t' : 0x30,
' ' : 0x31,
'del' : 0x33,
'delete' : 0x33,
'esc' : 0x35,
'escape' : 0x35,
'cmd' : 0x37,
'command' : 0x37,
'shift' : 0x38,
'caps lock' : 0x39,
'option' : 0x3A,
'ctrl' : 0x3B,
'control' : 0x3B,
'right shift' : 0x3C,
'rshift' : 0x3C,
'right option' : 0x3D,
'roption' : 0x3D,
'right control' : 0x3E,
'rcontrol' : 0x3E,
'fun' : 0x3F,
'function' : 0x3F,
'f17' : 0x40,
'volume up' : 0x48,
'volume down' : 0x49,
'mute' : 0x4A,
'f18' : 0x4F,
'f19' : 0x50,
'f20' : 0x5A,
'f5' : 0x60,
'f6' : 0x61,
'f7' : 0x62,
'f3' : 0x63,
'f8' : 0x64,
'f9' : 0x65,
'f11' : 0x67,
'f13' : 0x69,
'f16' : 0x6A,
'f14' : 0x6B,
'f10' : 0x6D,
'f12' : 0x6F,
'f15' : 0x71,
'help' : 0x72,
'home' : 0x73,
'pgup' : 0x74,
'page up' : 0x74,
'forward delete' : 0x75,
'f4' : 0x76,
'end' : 0x77,
'f2' : 0x78,
'page down' : 0x79,
'pgdn' : 0x79,
'f1' : 0x7A,
'left' : 0x7B,
'right' : 0x7C,
'down' : 0x7D,
'up' : 0x7E
}
# See: https://stackoverflow.com/q/3202629/55075
def toKeyCode(self, c):
shiftKey = False
# Letter
if c.isalpha():
if not c.islower():
shiftKey = True
c = c.lower()
if c in Keyboard.shiftChars:
shiftKey = True
c = Keyboard.shiftChars[c]
if c in Keyboard.keyCodeMap:
keyCode = Keyboard.keyCodeMap[c]
else:
keyCode = ord(c)
return keyCode, shiftKey
def KeyDown(self, k):
keyCode, shiftKey = self.toKeyCode(k)
time.sleep(0.0001)
if shiftKey:
CGEventPost(kCGHIDEventTap, CGEventCreateKeyboardEvent(None, 0x38, True))
time.sleep(0.0001)
CGEventPost(kCGHIDEventTap, CGEventCreateKeyboardEvent(None, keyCode, True))
time.sleep(0.0001)
if shiftKey:
CGEventPost(kCGHIDEventTap, CGEventCreateKeyboardEvent(None, 0x38, False))
time.sleep(0.0001)
def KeyUp(self, k):
keyCode, shiftKey = self.toKeyCode(k)
time.sleep(0.0001)
CGEventPost(kCGHIDEventTap, CGEventCreateKeyboardEvent(None, keyCode, False))
time.sleep(0.0001)
def KeyPress(self, k):
keyCode, shiftKey = self.toKeyCode(k)
time.sleep(0.0001)
if shiftKey:
CGEventPost(kCGHIDEventTap, CGEventCreateKeyboardEvent(None, 0x38, True))
time.sleep(0.0001)
CGEventPost(kCGHIDEventTap, CGEventCreateKeyboardEvent(None, keyCode, True))
time.sleep(0.0001)
CGEventPost(kCGHIDEventTap, CGEventCreateKeyboardEvent(None, keyCode, False))
time.sleep(0.0001)
if shiftKey:
CGEventPost(kCGHIDEventTap, CGEventCreateKeyboardEvent(None, 0x38, False))
time.sleep(0.0001)
def Type(self, text):
for key in text:
self.KeyDown(key)
self.KeyUp(key)
Here is the demo code using above class:
# DEMO
if __name__ == '__main__':
keyboard = Keyboard()
if sys.platform == "darwin":
keyboard.Type('Hello World!')
elif sys.platform == "win32":
print("Error: Platform not supported!")
which will simulate typing Hello World!
text on the current window.
You can run above code as a shell script. Check the link to the keyboard.py file.
I tried lib keyboard and it works good on Windows. Below line helps me switch tabs in browser:
keyboard.press_and_release('ctrl+tab')
For Python2.7(windows32) I installed only pywin32-223. And I wrote simple python`s code:
import win32api
import time
import win32con
# simulate the pressing-DOWN "ARROW key" of 200 times
for i in range(200):
time.sleep(0.5)
win32api.keybd_event(0x28, 0,0,0)
time.sleep(.05)
win32api.keybd_event(0x28,0 ,win32con.KEYEVENTF_KEYUP ,0)
It can be checked if you run the code and immediately go to the notepad window (where the text already exists) and place the cursor on the top line.