CampBuddy/Camp.Buddy v2.2.1/Camp_Buddy-2.2.1-pc/renpy/display/controller.py
2025-03-03 23:00:33 +01:00

211 lines
5.2 KiB
Python

# Copyright 2004-2019 Tom Rothamel <pytom@bishoujo.us>
#
# Permission is hereby granted, free of charge, to any person
# obtaining a copy of this software and associated documentation files
# (the "Software"), to deal in the Software without restriction,
# including without limitation the rights to use, copy, modify, merge,
# publish, distribute, sublicense, and/or sell copies of the Software,
# and to permit persons to whom the Software is furnished to do so,
# subject to the following conditions:
#
# The above copyright notice and this permission notice shall be
# included in all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
from __future__ import print_function
import pygame_sdl2.controller
import renpy.display
from pygame_sdl2 import CONTROLLERDEVICEADDED, CONTROLLERDEVICEREMOVED
from pygame_sdl2 import CONTROLLERAXISMOTION, CONTROLLERBUTTONDOWN, CONTROLLERBUTTONUP
from pygame_sdl2.controller import Controller, get_string_for_axis, get_string_for_button
import pygame_sdl2 as pygame
import os
def load_mappings():
try:
f = renpy.loader.load("renpycontrollerdb.txt")
pygame_sdl2.controller.add_mappings(f)
f.close()
except:
pass
try:
f = renpy.loader.load("gamecontrollerdb.txt")
pygame_sdl2.controller.add_mappings(f)
f.close()
except:
pass
try:
f = open(os.path.join(renpy.config.renpy_base, "gamecontrollerdb.txt"), "rb")
pygame_sdl2.controller.add_mappings(f)
f.close()
except:
pass
def init():
"""
Initialize gamepad support.
"""
if not renpy.game.preferences.pad_enabled:
return
try:
pygame_sdl2.controller.init()
load_mappings()
except:
renpy.display.log.exception()
for i in range(pygame_sdl2.controller.get_count()):
try:
c = Controller(i)
renpy.exports.write_log("controller: %r %r %r" % (c.get_guid_string(), c.get_name(), c.is_controller()))
except:
renpy.display.log.exception()
# A map from controller index to controller object.
controllers = { }
# A map from (controller, axis) to "pos", "neg", None position.
axis_positions = {}
# The axis threshold.
THRESHOLD = (32768 // 2)
# Should we ignore events?
ignore = False
def make_event(name):
"""
Creates an EVENTNAME event with `name`, and returns it.
"""
if not renpy.display.interface.keyboard_focused:
return None
if ignore:
return None
names = [ name ]
if renpy.config.map_pad_event:
names.extend(renpy.config.map_pad_event(name))
else:
names.extend(renpy.config.pad_bindings.get(name, ()))
return pygame_sdl2.event.Event(
renpy.display.core.EVENTNAME,
{ "eventnames" : names, "controller" : name, "up" : False })
def exists():
"""
Returns true if a controller exists, and False otherwise.
"""
if controllers:
return True
else:
return False
def quit(index): # @ReservedAssignment
"""
Quits the controller at index.
"""
if index in controllers:
controllers[index].quit()
del controllers[index]
renpy.exports.restart_interaction()
def start(index):
"""
Starts the controller at index.
"""
quit(index)
controllers[index] = c = Controller(index)
c.init()
renpy.exports.restart_interaction()
def event(ev):
"""
Processes an event and returns the same event, a new event, or None if
the event has been processed and should be ignored.
"""
if ev.type == CONTROLLERDEVICEADDED:
start(ev.which)
return None
elif ev.type == CONTROLLERDEVICEREMOVED:
quit(ev.which)
return None
elif ev.type == CONTROLLERAXISMOTION:
if ev.value > THRESHOLD:
pos = "pos"
elif ev.value < -THRESHOLD:
pos = "neg"
else:
pos = "zero"
old_pos = axis_positions.get((ev.which, ev.axis), None)
if pos == old_pos:
return None
axis_positions[(ev.which, ev.axis)] = pos
name = "pad_{}_{}".format(get_string_for_axis(ev.axis), pos)
ev = make_event(name)
elif ev.type in (CONTROLLERBUTTONDOWN, CONTROLLERBUTTONUP):
if ev.type == CONTROLLERBUTTONDOWN:
pr = "press"
else:
pr = "release"
name = "pad_{}_{}".format(get_string_for_button(ev.button), pr)
ev = make_event(name)
elif ev.type in (
pygame.JOYAXISMOTION,
pygame.JOYHATMOTION,
pygame.JOYBALLMOTION,
pygame.JOYBUTTONDOWN,
pygame.JOYBUTTONUP,
pygame.JOYDEVICEADDED,
pygame.JOYDEVICEREMOVED,
):
if not renpy.config.pass_joystick_events:
return None
return ev