Created
October 10, 2021 17:36
-
-
Save AndreasLonn/62b3a304d3938396b2f5ca4d1266efde to your computer and use it in GitHub Desktop.
Script to emulate keyboard or mouse actions with Xbox controller. Tested on Windows 10 with Xbox One S controller over both bluetooth and micro-USB cable. Can run in background. IMPORTANT: Remove the '2-' in the config file name. It is used to order the files correctly
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# How to use: | |
# This script requires: pygame, configparser, keyboard and mouse | |
# Tested on Windows 10 with Xbox One S controller | |
# over both bluetooth and micro-USB cable | |
# The config file ('config.ini') is stored in the same directory as the script | |
# The available keys are: | |
# For normal keys, see https://github.com/boppreh/keyboard#keyboard.send | |
# For mouse click, use "!m:click:" followed by button | |
# from https://github.com/boppreh/mouse#mouse.click | |
# For mouse movement, use "!m:move:hori" or "!m:move:vert" | |
# For scrolling, use "!m:scroll:hori" or "!m:scroll:vert" | |
import pygame, configparser, keyboard, mouse | |
pygame.init() | |
joysticks = [] | |
clock = pygame.time.Clock() | |
keepGoing = True | |
# mouseX, mouseY, scrollX and scrollY | |
mX, mY, sX, sY = 0, 0, 0, 0 | |
# Read the config file | |
config = configparser.RawConfigParser() | |
config.read(r'./config.ini') | |
# Setup mouse and scroll speed | |
mV = int(config.get('Mouse', 'mouseSpeed')) | |
sV = -int(config.get('Mouse', 'scrollSpeed')) / 100 | |
def act(key, v=0): | |
""" | |
Read from config and press the button, move the mouse or scroll | |
""" | |
global mX, mY, sX, sY, keepGoing | |
conf = config.get('Buttons', key) | |
# Handle mouse actions | |
if conf.startswith("!m:"): | |
cmd = conf[3:] | |
# For mouse click | |
if cmd.startswith("click:"): | |
mouse.click(button=cmd[7:]) | |
# For mouse movement | |
if cmd.startswith("move:"): | |
if cmd[7:] == 'hori': | |
mX = v | |
elif cmd[7:] == 'vert': | |
mY = v | |
# For scrolling | |
if cmd.startswith("scroll:"): | |
if cmd[8:] == 'hori': | |
sX = v | |
elif cmd[8:] == 'vert': | |
sY = v | |
# For exit | |
if cmd.startswith("exit"): | |
keepGoing = False | |
# If normal action | |
else: | |
keyboard.press_and_release(conf) | |
def initController(): | |
""" | |
Update list of connected controllers | |
""" | |
# English: 'Looking for controller' | |
print('Letar efter kontroller') | |
for i in range(0, pygame.joystick.get_count()): | |
joysticks.append(pygame.joystick.Joystick(i)) | |
joysticks[-1].init() | |
# English: "Detected joystick '", "' with ID: ", " and power level: " | |
print("Upptäckte joystick '", joysticks[-1].get_name(), | |
"' med ID: ", joysticks[-1].get_instance_id(), | |
" och batterinivå: ", joysticks[-1].get_power_level() ) | |
while keepGoing: | |
event = pygame.event.get() | |
if event: | |
for e in event: | |
# Type controller connect or disconnect: | |
if e.type == 1541 or e.type == 1542: | |
mX, mY, sX, sY = 0, 0, 0, 0 | |
joysticks.clear() | |
initController() | |
# Type button click | |
if e.type == 1539: | |
if e.button == 0: | |
act("A") | |
elif e.button == 1: | |
act("B") | |
elif e.button == 2: | |
act("X") | |
elif e.button == 3: | |
act("Y") | |
elif e.button == 4: | |
act("LB") | |
elif e.button == 5: | |
act("RB") | |
elif e.button == 6: | |
act("START") | |
elif e.button == 7: | |
act("SELECT") | |
elif e.button == 8: | |
act("LH") | |
elif e.button == 9: | |
act("RH") | |
# Type axis moved | |
elif e.type == 1536: | |
if e.axis == 4 and e.value > 0.99: | |
act("LT") | |
if e.axis == 5 and e.value > 0.99: | |
act("RT") | |
if e.axis == 0: | |
act("L_HORI", e.value) | |
if e.axis == 1: | |
act("L_VERT", e.value) | |
if e.axis == 2: | |
act("R_HORI", e.value) | |
if e.axis == 3: | |
act("R_VERT", e.value) | |
# Type dpad | |
elif e.type == 1538: | |
if e.value[0] == -1: | |
act("LEFT") | |
if e.value[0] == 1: | |
act("RIGHT") | |
if e.value[1] == 1: | |
act("UP") | |
if e.value[1] == -1: | |
act("DOWN") | |
# Move the mouse and scroll | |
mouse.move(mX * mV, mY * mV, absolute=False) | |
mouse.hWheel(-sX * sV) | |
mouse.wheel(sY * sV) | |
clock.tick(60) | |
# English: 'Closing' | |
print('Avslutar') |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
[Buttons] | |
A = c | |
B = x | |
X = v | |
Y = s | |
LB = i | |
RB = o | |
LT = F2 | |
RT = F1 | |
LH = !m:click:left | |
RH = !m:click:right | |
L_HORI = !m:move:hori | |
L_VERT = !m:move:vert | |
R_HORI = !m:scroll:hori | |
R_VERT = !m:scroll:vert | |
START = b | |
SELECT = t | |
UP = up | |
DOWN = down | |
LEFT = left | |
RIGHT = right | |
[Mouse] | |
mouseSpeed = 20 | |
scrollSpeed = 10 |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment