Compare commits
3 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
b9038483ce | ||
|
|
e57de52cc4 | ||
|
|
ee05f9516a |
8
.gitmodules
vendored
8
.gitmodules
vendored
@@ -4,9 +4,9 @@
|
||||
[submodule "lib/tinyusb"]
|
||||
path = lib/tinyusb
|
||||
url = https://github.com/hathach/tinyusb.git
|
||||
[submodule "src/usbd"]
|
||||
path = src/usbd
|
||||
url = https://github.com/wiredopposite/usbd.git
|
||||
[submodule "lib/tusb_gamepad"]
|
||||
path = lib/tusb_gamepad
|
||||
url = https://github.com/wiredopposite/tusb_gamepad.git
|
||||
[submodule "lib/tusb_xinput"]
|
||||
path = lib/tusb_xinput
|
||||
url = https://github.com/Ryzee119/tusb_xinput.git
|
||||
url = https://github.com/wiredopposite/tusb_xinput.git
|
||||
|
||||
@@ -1,17 +1,18 @@
|
||||
cmake_minimum_required(VERSION 3.12)
|
||||
|
||||
set(CMAKE_BUILD_TYPE Release)
|
||||
message("Build type: \"${CMAKE_BUILD_TYPE}\"")
|
||||
|
||||
# Project name
|
||||
set(NAME OGX-Mini)
|
||||
|
||||
# Board type
|
||||
set(PICO_BOARD none)
|
||||
|
||||
# Fixes that allow some MCH2022 badges with a slowly starting oscillator to boot properly
|
||||
add_compile_definitions(PICO_BOOT_STAGE2_CHOOSE_GENERIC_03H=1 PICO_XOSC_STARTUP_DELAY_MULTIPLIER=64)
|
||||
# add_compile_definitions(PICO_BOOT_STAGE2_CHOOSE_GENERIC_03H=1 PICO_XOSC_STARTUP_DELAY_MULTIPLIER=64)
|
||||
|
||||
# add_compile_options(-Wno-unused-parameter -Wno-unused-variable -Wno-missing-field-initializers -Wno-unused-function)
|
||||
add_compile_options(-Wno-missing-field-initializers)
|
||||
|
||||
# SDK
|
||||
include($ENV{PICO_SDK_PATH}/pico_sdk_init.cmake)
|
||||
|
||||
project(${NAME} C CXX ASM)
|
||||
@@ -22,66 +23,48 @@ if (PICO_SDK_VERSION_STRING VERSION_LESS "1.3.0")
|
||||
message(FATAL_ERROR "Raspberry Pi Pico SDK version 1.3.0 (or later) required. Your version is ${PICO_SDK_VERSION_STRING}")
|
||||
endif()
|
||||
|
||||
set(PICO_PIO_USB_PATH "${CMAKE_CURRENT_LIST_DIR}/lib/Pico-PIO-USB")
|
||||
set(PICO_TINYUSB_PATH "${CMAKE_CURRENT_LIST_DIR}/lib/tinyusb")
|
||||
set(TUSB_XINPUT_PATH "${CMAKE_CURRENT_LIST_DIR}/lib/tusb_xinput")
|
||||
add_subdirectory(${TUSB_XINPUT_PATH} xinput_host)
|
||||
set(ROOT ${CMAKE_CURRENT_LIST_DIR})
|
||||
|
||||
set(PICO_PIO_USB_PATH ${ROOT}/lib/Pico-PIO-USB)
|
||||
set(PICO_TINYUSB_PATH ${ROOT}/lib/tinyusb)
|
||||
set(TUSB_GAMEPAD_PATH ${ROOT}/lib/tusb_gamepad)
|
||||
set(XINPUT_HOST_PATH ${ROOT}/lib/tusb_xinput)
|
||||
|
||||
pico_sdk_init()
|
||||
|
||||
add_subdirectory(lib/Pico-PIO-USB)
|
||||
add_subdirectory(lib)
|
||||
# add_subdirectory(${ROOT}/lib)
|
||||
add_subdirectory(${ROOT}/lib/CRC32 CRC32)
|
||||
add_subdirectory(${XINPUT_HOST_PATH} xinput_host)
|
||||
add_subdirectory(${PICO_PIO_USB_PATH})
|
||||
add_subdirectory(${TUSB_GAMEPAD_PATH})
|
||||
target_include_directories(tusb_gamepad PRIVATE ${ROOT}/src) # so tusb_gamepad can see tusb_config.h
|
||||
|
||||
set(SRC_DIR ${ROOT}/src)
|
||||
file(GLOB_RECURSE SOURCES
|
||||
"src/main.cpp"
|
||||
"src/input_mode.cpp"
|
||||
"src/Gamepad.cpp"
|
||||
${SRC_DIR}/main.cpp
|
||||
${SRC_DIR}/input_mode.cpp
|
||||
|
||||
"src/utilities/log.cpp"
|
||||
|
||||
"src/usbh/tusb_host_manager.cpp"
|
||||
"src/usbh/tusb_host.cpp"
|
||||
"src/usbh/n64usb/N64USB.cpp"
|
||||
"src/usbh/ps3/Dualshock3.cpp"
|
||||
"src/usbh/ps3/DInput.cpp"
|
||||
"src/usbh/ps4/Dualshock4.cpp"
|
||||
"src/usbh/ps5/Dualsense.cpp"
|
||||
"src/usbh/psclassic/PSClassic.cpp"
|
||||
"src/usbh/switch/SwitchPro.cpp"
|
||||
"src/usbh/switch/SwitchWired.cpp"
|
||||
"src/usbh/xinput/XInput.cpp"
|
||||
"src/usbh/shared/hid_class_driver.c"
|
||||
"src/usbh/shared/scaling.cpp"
|
||||
|
||||
"src/usbd/usbdriver.cpp"
|
||||
"src/usbd/drivermanager.cpp"
|
||||
"src/usbd/drivers/shared/driverhelper.h"
|
||||
"src/usbd/drivers/shared/scaling.cpp"
|
||||
"src/usbd/drivers/dinput/DInputDriver.cpp"
|
||||
# "src/usbd/drivers/hid/HIDDriver.cpp"
|
||||
# "src/usbd/drivers/ps3/PS3Driver.cpp"
|
||||
"src/usbd/drivers/psclassic/PSClassicDriver.cpp"
|
||||
"src/usbd/drivers/switch/SwitchDriver.cpp"
|
||||
"src/usbd/drivers/usbserial/USBSerialDriver.cpp"
|
||||
"src/usbd/drivers/xinput/XInputDriver.cpp"
|
||||
"src/usbd/drivers/xboxog/XboxOriginalDriver.cpp"
|
||||
"src/usbd/drivers/xboxog/xid/xid.c"
|
||||
"src/usbd/drivers/xboxog/xid/xid_driver.c"
|
||||
"src/usbd/drivers/xboxog/xid/xid_gamepad.c"
|
||||
"src/usbd/drivers/xboxog/xid/xid_remote.c"
|
||||
"src/usbd/drivers/xboxog/xid/xid_steelbattalion.c"
|
||||
${SRC_DIR}/usbh/tusb_host_manager.cpp
|
||||
${SRC_DIR}/usbh/tusb_host.cpp
|
||||
${SRC_DIR}/usbh/n64usb/N64USB.cpp
|
||||
${SRC_DIR}/usbh/ps3/Dualshock3.cpp
|
||||
${SRC_DIR}/usbh/ps3/DInput.cpp
|
||||
${SRC_DIR}/usbh/ps4/Dualshock4.cpp
|
||||
${SRC_DIR}/usbh/ps5/Dualsense.cpp
|
||||
${SRC_DIR}/usbh/psclassic/PSClassic.cpp
|
||||
${SRC_DIR}/usbh/switch/SwitchPro.cpp
|
||||
${SRC_DIR}/usbh/switch/SwitchWired.cpp
|
||||
${SRC_DIR}/usbh/xinput/XInput.cpp
|
||||
${SRC_DIR}/usbh/shared/hid_class_driver.c
|
||||
${SRC_DIR}/usbh/shared/scaling.cpp
|
||||
)
|
||||
|
||||
# Firmware
|
||||
add_executable(${NAME}
|
||||
${SOURCES}
|
||||
)
|
||||
add_executable(${NAME} ${SOURCES})
|
||||
|
||||
target_include_directories(${NAME} PUBLIC
|
||||
${CMAKE_CURRENT_LIST_DIR}/src ${CMAKE_CURRENT_LIST_DIR}/lib)
|
||||
|
||||
include_directories(
|
||||
lib/)
|
||||
${ROOT}/src
|
||||
${ROOT}/lib)
|
||||
|
||||
target_link_libraries(${NAME}
|
||||
pico_stdlib
|
||||
@@ -102,6 +85,7 @@ target_link_libraries(${NAME}
|
||||
CRC32
|
||||
cmsis_core
|
||||
xinput_host
|
||||
tusb_gamepad
|
||||
)
|
||||
|
||||
pico_add_extra_outputs(${NAME})
|
||||
pico_add_extra_outputs(${NAME})
|
||||
40
Makefile
40
Makefile
@@ -1,40 +0,0 @@
|
||||
# Copyright (c) 2022 Nicolai Electronics
|
||||
# SPDX-License-Identifier: MIT
|
||||
|
||||
INSTALL_PREFIX := $PWD
|
||||
BUILD_DIR := build
|
||||
GENERATED_DIR := generated
|
||||
|
||||
.PHONY: all firmware flash clean install_rules $(BUILD_DIR) format
|
||||
|
||||
all: build flash
|
||||
@echo "All tasks completed"
|
||||
|
||||
build:
|
||||
mkdir -p $(BUILD_DIR)
|
||||
mkdir -p $(GENERATED_DIR)
|
||||
cd $(BUILD_DIR); cmake -DCMAKE_INSTALL_PREFIX=$INSTALL_PREFIX -DCMAKE_BUILD_TYPE=Release ..
|
||||
$(MAKE) -C $(BUILD_DIR) --no-print-directory all
|
||||
|
||||
debug:
|
||||
mkdir -p $(BUILD_DIR)
|
||||
mkdir -p $(GENERATED_DIR)
|
||||
cd $(BUILD_DIR); cmake -DCMAKE_INSTALL_PREFIX=$INSTALL_PREFIX -DCMAKE_BUILD_TYPE=Debug ..
|
||||
$(MAKE) -C $(BUILD_DIR) --no-print-directory all
|
||||
|
||||
flash:
|
||||
picotool load $(BUILD_DIR)/i2c_adapter.bin
|
||||
picotool reboot
|
||||
|
||||
clean:
|
||||
rm -rf $(BUILD_DIR)
|
||||
rm -rf $(GENERATED_DIR)
|
||||
|
||||
install_rules:
|
||||
cp tools/99-pico.rules /etc/udev/rules.d/
|
||||
@echo "reload rules with:"
|
||||
@echo "\tudevadm control --reload-rules"
|
||||
@echo "\tudevadm trigger"
|
||||
|
||||
format:
|
||||
find . -iname '*.h' -o -iname '*.c' -o -iname '*.cpp' | grep -v '$(BUILD_DIR)' | xargs clang-format -i
|
||||
1
lib/tusb_gamepad
Submodule
1
lib/tusb_gamepad
Submodule
Submodule lib/tusb_gamepad added at 5e5ee00ee8
Submodule lib/tusb_xinput updated: 073d73c47a...b34398847a
@@ -1,62 +0,0 @@
|
||||
# This is a copy of <PICO_SDK_PATH>/external/pico_sdk_import.cmake
|
||||
|
||||
# This can be dropped into an external project to help locate this SDK
|
||||
# It should be include()ed prior to project()
|
||||
|
||||
if (DEFINED ENV{PICO_SDK_PATH} AND (NOT PICO_SDK_PATH))
|
||||
set(PICO_SDK_PATH $ENV{PICO_SDK_PATH})
|
||||
message("Using PICO_SDK_PATH from environment ('${PICO_SDK_PATH}')")
|
||||
endif ()
|
||||
|
||||
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT} AND (NOT PICO_SDK_FETCH_FROM_GIT))
|
||||
set(PICO_SDK_FETCH_FROM_GIT $ENV{PICO_SDK_FETCH_FROM_GIT})
|
||||
message("Using PICO_SDK_FETCH_FROM_GIT from environment ('${PICO_SDK_FETCH_FROM_GIT}')")
|
||||
endif ()
|
||||
|
||||
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_PATH} AND (NOT PICO_SDK_FETCH_FROM_GIT_PATH))
|
||||
set(PICO_SDK_FETCH_FROM_GIT_PATH $ENV{PICO_SDK_FETCH_FROM_GIT_PATH})
|
||||
message("Using PICO_SDK_FETCH_FROM_GIT_PATH from environment ('${PICO_SDK_FETCH_FROM_GIT_PATH}')")
|
||||
endif ()
|
||||
|
||||
set(PICO_SDK_PATH "${PICO_SDK_PATH}" CACHE PATH "Path to the Raspberry Pi Pico SDK")
|
||||
set(PICO_SDK_FETCH_FROM_GIT "${PICO_SDK_FETCH_FROM_GIT}" CACHE BOOL "Set to ON to fetch copy of SDK from git if not otherwise locatable")
|
||||
set(PICO_SDK_FETCH_FROM_GIT_PATH "${PICO_SDK_FETCH_FROM_GIT_PATH}" CACHE FILEPATH "location to download SDK")
|
||||
|
||||
if (NOT PICO_SDK_PATH)
|
||||
if (PICO_SDK_FETCH_FROM_GIT)
|
||||
include(FetchContent)
|
||||
set(FETCHCONTENT_BASE_DIR_SAVE ${FETCHCONTENT_BASE_DIR})
|
||||
if (PICO_SDK_FETCH_FROM_GIT_PATH)
|
||||
get_filename_component(FETCHCONTENT_BASE_DIR "${PICO_SDK_FETCH_FROM_GIT_PATH}" REALPATH BASE_DIR "${CMAKE_SOURCE_DIR}")
|
||||
endif ()
|
||||
FetchContent_Declare(
|
||||
pico_sdk
|
||||
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||
GIT_TAG master
|
||||
)
|
||||
if (NOT pico_sdk)
|
||||
message("Downloading Raspberry Pi Pico SDK")
|
||||
FetchContent_Populate(pico_sdk)
|
||||
set(PICO_SDK_PATH ${pico_sdk_SOURCE_DIR})
|
||||
endif ()
|
||||
set(FETCHCONTENT_BASE_DIR ${FETCHCONTENT_BASE_DIR_SAVE})
|
||||
else ()
|
||||
message(FATAL_ERROR
|
||||
"SDK location was not specified. Please set PICO_SDK_PATH or set PICO_SDK_FETCH_FROM_GIT to on to fetch from git."
|
||||
)
|
||||
endif ()
|
||||
endif ()
|
||||
|
||||
get_filename_component(PICO_SDK_PATH "${PICO_SDK_PATH}" REALPATH BASE_DIR "${CMAKE_BINARY_DIR}")
|
||||
if (NOT EXISTS ${PICO_SDK_PATH})
|
||||
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' not found")
|
||||
endif ()
|
||||
|
||||
set(PICO_SDK_INIT_CMAKE_FILE ${PICO_SDK_PATH}/pico_sdk_init.cmake)
|
||||
if (NOT EXISTS ${PICO_SDK_INIT_CMAKE_FILE})
|
||||
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' does not appear to contain the Raspberry Pi Pico SDK")
|
||||
endif ()
|
||||
|
||||
set(PICO_SDK_PATH ${PICO_SDK_PATH} CACHE PATH "Path to the Raspberry Pi Pico SDK" FORCE)
|
||||
|
||||
include(${PICO_SDK_INIT_CMAKE_FILE})
|
||||
@@ -1,39 +0,0 @@
|
||||
#include "Gamepad.h"
|
||||
#include "usbd/board_config.h"
|
||||
|
||||
void Gamepad::reset_pad()
|
||||
{
|
||||
buttons.up = buttons.down = buttons.left = buttons.right = false;
|
||||
buttons.a = buttons.b = buttons.x = buttons.y = false;
|
||||
buttons.l3 = buttons.r3 = buttons.back = buttons.start = false;
|
||||
buttons.rb = buttons.lb = buttons.sys = buttons.misc = false;
|
||||
|
||||
triggers.l = triggers.r = 0;
|
||||
|
||||
joysticks.lx = joysticks.ly = joysticks.rx = joysticks.ry = 0;
|
||||
}
|
||||
|
||||
void Gamepad::reset_rumble()
|
||||
{
|
||||
rumble.r = rumble.l = 0;
|
||||
}
|
||||
|
||||
void Gamepad::reset_hid_rumble()
|
||||
{
|
||||
if (rumble.l != UINT8_MAX)
|
||||
{
|
||||
rumble.l = 0;
|
||||
}
|
||||
|
||||
if (rumble.r != UINT8_MAX)
|
||||
{
|
||||
rumble.r = 0;
|
||||
}
|
||||
}
|
||||
|
||||
Gamepad& gamepad(int idx)
|
||||
{
|
||||
static Gamepad gamepad[MAX_GAMEPADS];
|
||||
|
||||
return gamepad[idx];
|
||||
}
|
||||
@@ -1,71 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#ifndef _GAMEPAD_H_
|
||||
#define _GAMEPAD_H_
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include <cstdint>
|
||||
|
||||
struct GamepadButtons
|
||||
{
|
||||
bool up {false};
|
||||
bool down {false};
|
||||
bool left {false};
|
||||
bool right {false};
|
||||
bool a {false};
|
||||
bool b {false};
|
||||
bool x {false};
|
||||
bool y {false};
|
||||
bool l3 {false};
|
||||
bool r3 {false};
|
||||
bool back {false};
|
||||
bool start {false};
|
||||
bool rb {false};
|
||||
bool lb {false};
|
||||
bool sys {false};
|
||||
bool misc {false};
|
||||
};
|
||||
|
||||
struct GamepadTriggers
|
||||
{
|
||||
uint8_t l {0};
|
||||
uint8_t r {0};
|
||||
};
|
||||
|
||||
struct GamepadJoysticks
|
||||
{
|
||||
int16_t lx {0};
|
||||
int16_t ly {0};
|
||||
int16_t rx {0};
|
||||
int16_t ry {0};
|
||||
};
|
||||
|
||||
struct GamepadRumble
|
||||
{
|
||||
uint8_t l {0};
|
||||
uint8_t r {0};
|
||||
};
|
||||
|
||||
class Gamepad
|
||||
{
|
||||
public:
|
||||
GamepadButtons buttons;
|
||||
GamepadTriggers triggers;
|
||||
GamepadJoysticks joysticks;
|
||||
GamepadRumble rumble;
|
||||
|
||||
void reset_pad();
|
||||
void reset_rumble();
|
||||
void reset_hid_rumble();
|
||||
};
|
||||
|
||||
Gamepad& gamepad(int idx);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif // _GAMEPAD_H_
|
||||
@@ -6,7 +6,6 @@
|
||||
|
||||
#include "tusb.h"
|
||||
|
||||
#include "usbd/board_config.h"
|
||||
#include "input_mode.h"
|
||||
|
||||
#define AIRCR_REG (*((volatile uint32_t *)(0xE000ED0C))) // Address of the AIRCR register
|
||||
@@ -16,6 +15,8 @@
|
||||
#define FLASH_TARGET_OFFSET (256 * 1024)
|
||||
#define FLASH_SIZE_BYTES (2 * 1024 * 1024)
|
||||
|
||||
InputMode current_input_mode;
|
||||
|
||||
void system_reset()
|
||||
{
|
||||
AIRCR_REG = AIRCR_VECTKEY | AIRCR_SYSRESETREQ;
|
||||
@@ -54,7 +55,7 @@ bool change_input_mode(GamepadButtons buttons)
|
||||
return false;
|
||||
}
|
||||
|
||||
InputMode new_mode;
|
||||
InputMode new_mode = current_input_mode;
|
||||
|
||||
if (buttons.up)
|
||||
{
|
||||
@@ -62,7 +63,7 @@ bool change_input_mode(GamepadButtons buttons)
|
||||
}
|
||||
else if (buttons.left)
|
||||
{
|
||||
new_mode = INPUT_MODE_HID;
|
||||
new_mode = INPUT_MODE_DINPUT;
|
||||
}
|
||||
else if (buttons.right)
|
||||
{
|
||||
@@ -104,22 +105,24 @@ enum InputMode get_input_mode()
|
||||
const uint8_t *stored_value = (const uint8_t *)(XIP_BASE + FLASH_SIZE_BYTES - FLASH_SECTOR_SIZE);
|
||||
|
||||
#if (MAX_GAMEPADS < 1)
|
||||
if ((*stored_value == INPUT_MODE_HID) || (*stored_value == INPUT_MODE_SWITCH))
|
||||
if ((*stored_value == INPUT_MODE_DINPUT) || (*stored_value == INPUT_MODE_SWITCH))
|
||||
{
|
||||
return(enum InputMode)*stored_value;
|
||||
current_input_mode = (enum InputMode)*stored_value;
|
||||
}
|
||||
else
|
||||
{
|
||||
return INPUT_MODE_HID;
|
||||
current_input_mode = INPUT_MODE_DINPUT;
|
||||
}
|
||||
#else
|
||||
if (*stored_value >= INPUT_MODE_XINPUT && *stored_value <= INPUT_MODE_XBOXORIGINAL)
|
||||
{
|
||||
return(enum InputMode)*stored_value;
|
||||
current_input_mode = (enum InputMode)*stored_value;
|
||||
}
|
||||
else
|
||||
{
|
||||
return INPUT_MODE_XBOXORIGINAL;
|
||||
current_input_mode = INPUT_MODE_XBOXORIGINAL;
|
||||
}
|
||||
#endif
|
||||
|
||||
return current_input_mode;
|
||||
}
|
||||
@@ -5,8 +5,7 @@
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include "Gamepad.h"
|
||||
#include "usbd/inputmodes.h"
|
||||
#include "tusb_gamepad.h"
|
||||
|
||||
enum InputMode get_input_mode();
|
||||
bool change_input_mode(GamepadButtons buttons);
|
||||
|
||||
17
src/main.cpp
17
src/main.cpp
@@ -6,13 +6,12 @@
|
||||
|
||||
#include "tusb.h"
|
||||
#include "bsp/board_api.h"
|
||||
#include "tusb_gamepad.h"
|
||||
#include "drivermanager.h"
|
||||
#include "drivers/gpdriver.h"
|
||||
|
||||
#include "usbh/tusb_host.h"
|
||||
#include "usbd/drivermanager.h"
|
||||
#include "usbd/drivers/gpdriver.h"
|
||||
#include "Gamepad.h"
|
||||
#include "input_mode.h"
|
||||
#include "usbd/board_config.h"
|
||||
|
||||
int main(void)
|
||||
{
|
||||
@@ -29,7 +28,7 @@ int main(void)
|
||||
multicore_reset_core1();
|
||||
multicore_launch_core1(usbh_main);
|
||||
|
||||
GamepadButtons prev_gamepad_buttons = gamepad(0).buttons;
|
||||
GamepadButtons prev_gamepad_buttons = gamepad(0)->buttons;
|
||||
absolute_time_t last_time_gamepad_changed = get_absolute_time();
|
||||
absolute_time_t last_time_gamepad_checked = get_absolute_time();
|
||||
|
||||
@@ -39,16 +38,16 @@ int main(void)
|
||||
{
|
||||
uint8_t outBuffer[64];
|
||||
GPDriver* driver = driverManager.getDriver();
|
||||
driver->process(i, &gamepad(i), outBuffer);
|
||||
driver->update_rumble(i, &gamepad(i));
|
||||
driver->process(i, gamepad(i), outBuffer);
|
||||
driver->update_rumble(i, gamepad(i));
|
||||
}
|
||||
|
||||
if (absolute_time_diff_us(last_time_gamepad_checked, get_absolute_time()) >= 500000)
|
||||
{
|
||||
// check if digital buttons have changed
|
||||
if (memcmp(&gamepad(0).buttons, &prev_gamepad_buttons, sizeof(GamepadButtons)) != 0)
|
||||
if (memcmp(&gamepad(0)->buttons, &prev_gamepad_buttons, sizeof(GamepadButtons)) != 0)
|
||||
{
|
||||
memcpy(&prev_gamepad_buttons, &gamepad(0).buttons, sizeof(GamepadButtons));
|
||||
memcpy(&prev_gamepad_buttons, &gamepad(0)->buttons, sizeof(GamepadButtons));
|
||||
last_time_gamepad_changed = get_absolute_time();
|
||||
}
|
||||
// haven't changed for 3 seconds
|
||||
|
||||
39
src/ogxm_config.h
Normal file
39
src/ogxm_config.h
Normal file
@@ -0,0 +1,39 @@
|
||||
#ifndef _OGXM_CONFIG_H_
|
||||
#define _OGXM_CONFIG_H_
|
||||
|
||||
#define ADAFRUIT_FEATHER_USBH 1
|
||||
#define PI_PICO 2
|
||||
#define RP2040_ZERO_INTERPOSER 3
|
||||
|
||||
// Options //
|
||||
#define OGXM_BOARD ADAFRUIT_FEATHER_USBH
|
||||
#define CDC_DEBUG 0
|
||||
// ------- //
|
||||
|
||||
#if OGXM_BOARD == ADAFRUIT_FEATHER_USBH
|
||||
#define PIO_USB_DP_PIN 16 // DM = 17
|
||||
#define LED_INDICATOR_PIN 13
|
||||
#define VCC_EN_PIN 18
|
||||
// #define NEOPIXEL_PWR_PIN 20
|
||||
// #define NEOPIXEL_CTRL_PIN 21
|
||||
|
||||
#elif OGXM_BOARD == PI_PICO
|
||||
#define PIO_USB_DP_PIN 0 // DM = 1
|
||||
#define LED_INDICATOR_PIN 25
|
||||
|
||||
#elif OGXM_BOARD == RP2040_ZERO_INTERPOSER
|
||||
#define PIO_USB_DP_PIN 10 // DM = 11
|
||||
#define LED_INDICATOR_PIN 13
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef OGXM_BOARD
|
||||
#error OGXM_BOARD must be defined in ogxm_config.h
|
||||
#endif
|
||||
|
||||
#ifndef CDC_DEBUG
|
||||
#define CDC_DEBUG 0
|
||||
#endif
|
||||
|
||||
|
||||
#endif // _OGXM_CONFIG_H_
|
||||
@@ -26,7 +26,9 @@
|
||||
#ifndef _TUSB_CONFIG_H_
|
||||
#define _TUSB_CONFIG_H_
|
||||
|
||||
#include "usbd/board_config.h"
|
||||
#include "board_config.h"
|
||||
|
||||
#define MAX_GAMEPADS 1
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
@@ -89,7 +91,7 @@
|
||||
#define CFG_TUD_ENABLED 1
|
||||
|
||||
// CFG_TUSB_DEBUG is defined by compiler in DEBUG build
|
||||
// #define CFG_TUSB_DEBUG 1
|
||||
#define CFG_TUSB_DEBUG 0
|
||||
|
||||
/* USB DMA on some MCUs can only access a specific SRAM region with restriction on alignment.
|
||||
* Tinyusb use follows macros to declare transferring memory so that they can be put
|
||||
@@ -128,7 +130,7 @@
|
||||
//--------------------------------------------------------------------
|
||||
|
||||
#ifndef CFG_TUD_ENDPOINT0_SIZE
|
||||
#define CFG_TUD_ENDPOINT0_SIZE 64
|
||||
#define CFG_TUD_ENDPOINT0_SIZE 64
|
||||
#endif
|
||||
|
||||
#define CFG_TUD_CDC_RX_BUFSIZE 256
|
||||
|
||||
1
src/usbd
1
src/usbd
Submodule src/usbd deleted from f7bdb97a37
@@ -1,15 +0,0 @@
|
||||
#ifndef USBD_CONFIG_H_
|
||||
#define USBD_CONFIG_H_
|
||||
|
||||
#include "usbd/usbd_boards.h"
|
||||
|
||||
// Boards
|
||||
// OGXM_PI_PICO
|
||||
// OGXM_ADA_FEATHER_USBH
|
||||
// OGXM_RPZERO_INTERPOSER
|
||||
|
||||
#define USBD_BOARD OGXM_RPZERO_INTERPOSER
|
||||
#define USBD_MAX_GAMEPADS 1 // This is set by idf.py menuconfig for wireless boards, number here is ignored in that case.
|
||||
#define CDC_DEBUG 0 // Set to 1 for CDC device, helpful for debugging USB host. Include utilities/log.h and use log() as you would printf()
|
||||
|
||||
#endif // USBD_CONFIG_H_
|
||||
@@ -3,19 +3,21 @@
|
||||
|
||||
#include <stdint.h>
|
||||
#include "host/usbh.h" // needed so xinput_host will build
|
||||
#include "xinput_host.h"
|
||||
#include "tusb_gamepad.h"
|
||||
|
||||
#include "usbh/shared/shared.h"
|
||||
#include "xinput_host.h"
|
||||
#include "Gamepad.h"
|
||||
|
||||
class GPHostDriver
|
||||
{
|
||||
public:
|
||||
virtual ~GPHostDriver() = default;
|
||||
|
||||
virtual void init(uint8_t player_id, uint8_t dev_addr, uint8_t instance) = 0;
|
||||
virtual void process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len) = 0;
|
||||
virtual void process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len) = 0;
|
||||
virtual void process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len) = 0;
|
||||
virtual void process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len) = 0;
|
||||
virtual void hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len) = 0;
|
||||
virtual bool send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance) = 0;
|
||||
virtual bool send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance) = 0;
|
||||
};
|
||||
|
||||
#endif // _GPHOSTDRIVER_H_
|
||||
@@ -11,64 +11,66 @@ void N64USB::init(uint8_t player_id, uint8_t dev_addr, uint8_t instance)
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void N64USB::update_gamepad(Gamepad& gamepad, const N64USBReport* n64_data)
|
||||
void N64USB::update_gamepad(Gamepad* gamepad, const N64USBReport* n64_data)
|
||||
{
|
||||
gamepad.reset_pad();
|
||||
gamepad->reset_pad(gamepad);
|
||||
|
||||
uint8_t n64_dpad = n64_data->buttons & N64_DPAD_MASK;
|
||||
|
||||
switch(n64_dpad)
|
||||
{
|
||||
case N64_DPAD_MASK_UP:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad->buttons.up = true;
|
||||
break;
|
||||
case N64_DPAD_MASK_UP_RIGHT:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.up = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case N64_DPAD_MASK_RIGHT:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case N64_DPAD_MASK_RIGHT_DOWN:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.right = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case N64_DPAD_MASK_DOWN:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case N64_DPAD_MASK_DOWN_LEFT:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.down = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case N64_DPAD_MASK_LEFT:
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case N64_DPAD_MASK_LEFT_UP:
|
||||
gamepad.buttons.left = true;
|
||||
gamepad.buttons.up = true;
|
||||
gamepad->buttons.left = true;
|
||||
gamepad->buttons.up = true;
|
||||
break;
|
||||
}
|
||||
|
||||
if (n64_data->buttons & N64_C_UP_MASK) gamepad.joysticks.ry = INT16_MAX;
|
||||
if (n64_data->buttons & N64_C_DOWN_MASK) gamepad.joysticks.ry = INT16_MIN;
|
||||
if (n64_data->buttons & N64_C_LEFT_MASK) gamepad.joysticks.rx = INT16_MIN;
|
||||
if (n64_data->buttons & N64_C_RIGHT_MASK) gamepad.joysticks.rx = INT16_MAX;
|
||||
if (n64_data->buttons & N64_C_UP_MASK) gamepad->joysticks.ry = INT16_MAX;
|
||||
if (n64_data->buttons & N64_C_DOWN_MASK) gamepad->joysticks.ry = INT16_MIN;
|
||||
if (n64_data->buttons & N64_C_LEFT_MASK) gamepad->joysticks.rx = INT16_MIN;
|
||||
if (n64_data->buttons & N64_C_RIGHT_MASK) gamepad->joysticks.rx = INT16_MAX;
|
||||
|
||||
if (n64_data->buttons & N64_A_MASK) gamepad.buttons.a = true;
|
||||
if (n64_data->buttons & N64_B_MASK) gamepad.buttons.b = true;
|
||||
if (n64_data->buttons & N64_START_MASK) gamepad.buttons.start = true;
|
||||
if (n64_data->buttons & N64_L_MASK) gamepad.buttons.lb = true;
|
||||
if (n64_data->buttons & N64_R_MASK) gamepad.buttons.rb = true;
|
||||
if (n64_data->buttons & N64_A_MASK) gamepad->buttons.a = true;
|
||||
if (n64_data->buttons & N64_B_MASK) gamepad->buttons.b = true;
|
||||
if (n64_data->buttons & N64_START_MASK) gamepad->buttons.start = true;
|
||||
if (n64_data->buttons & N64_L_MASK) gamepad->buttons.lb = true;
|
||||
if (n64_data->buttons & N64_R_MASK) gamepad->buttons.rb = true;
|
||||
|
||||
if (n64_data->buttons & N64_Z_MASK) gamepad.triggers.r = 0xFF;
|
||||
if (n64_data->buttons & N64_Z_MASK) gamepad->triggers.r = 0xFF;
|
||||
|
||||
gamepad.joysticks.ly = scale_uint8_to_int16(n64_data->y, true);
|
||||
gamepad.joysticks.lx = scale_uint8_to_int16(n64_data->x, false);
|
||||
gamepad->joysticks.ly = scale_uint8_to_int16(n64_data->y, true);
|
||||
gamepad->joysticks.lx = scale_uint8_to_int16(n64_data->x, false);
|
||||
}
|
||||
|
||||
void N64USB::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
void N64USB::process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
{
|
||||
static N64USBReport prev_report = { 0 };
|
||||
(void)len;
|
||||
|
||||
static N64USBReport prev_report = {};
|
||||
|
||||
N64USBReport n64_report;
|
||||
memcpy(&n64_report, report, sizeof(n64_report));
|
||||
@@ -83,11 +85,29 @@ void N64USB::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t inst
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void N64USB::process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len) {}
|
||||
|
||||
void N64USB::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len) {}
|
||||
|
||||
bool N64USB::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
void N64USB::process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
void N64USB::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report_id;
|
||||
(void)report_type;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
bool N64USB::send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -1,5 +1,3 @@
|
||||
#pragma once
|
||||
|
||||
#ifndef _N64USB_H_
|
||||
#define _N64USB_H_
|
||||
|
||||
@@ -54,14 +52,16 @@ struct N64USBState
|
||||
class N64USB: public GPHostDriver
|
||||
{
|
||||
public:
|
||||
~N64USB() override {}
|
||||
|
||||
virtual void init(uint8_t player_id, uint8_t dev_addr, uint8_t instance);
|
||||
virtual void process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len);
|
||||
virtual bool send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
virtual bool send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
private:
|
||||
N64USBState n64usb;
|
||||
void update_gamepad(Gamepad& gp, const N64USBReport* n64_data);
|
||||
void update_gamepad(Gamepad* gp, const N64USBReport* n64_data);
|
||||
};
|
||||
|
||||
#endif // _N64USB_H_
|
||||
@@ -13,84 +13,99 @@ void DInput::init(uint8_t player_id, uint8_t dev_addr, uint8_t instance)
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void DInput::update_gamepad(Gamepad& gamepad, const DInputReport* dinput_report)
|
||||
void DInput::update_gamepad(Gamepad* gamepad, const DInputReport* dinput_report)
|
||||
{
|
||||
gamepad.reset_pad();
|
||||
gamepad->reset_pad(gamepad);
|
||||
|
||||
switch (dinput_report->direction)
|
||||
{
|
||||
case DINPUT_HAT_UP:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad->buttons.up = true;
|
||||
break;
|
||||
case DINPUT_HAT_UPRIGHT:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.up = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case DINPUT_HAT_RIGHT:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case DINPUT_HAT_DOWNRIGHT:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.right = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case DINPUT_HAT_DOWN:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case DINPUT_HAT_DOWNLEFT:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.down = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case DINPUT_HAT_LEFT:
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case DINPUT_HAT_UPLEFT:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.up = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
}
|
||||
|
||||
if (dinput_report->square_btn) gamepad.buttons.x = true;
|
||||
if (dinput_report->triangle_btn) gamepad.buttons.y = true;
|
||||
if (dinput_report->cross_btn) gamepad.buttons.a = true;
|
||||
if (dinput_report->circle_btn) gamepad.buttons.b = true;
|
||||
if (dinput_report->square_btn) gamepad->buttons.x = true;
|
||||
if (dinput_report->triangle_btn) gamepad->buttons.y = true;
|
||||
if (dinput_report->cross_btn) gamepad->buttons.a = true;
|
||||
if (dinput_report->circle_btn) gamepad->buttons.b = true;
|
||||
|
||||
if (dinput_report->select_btn) gamepad.buttons.back = true;
|
||||
if (dinput_report->start_btn) gamepad.buttons.start = true;
|
||||
if (dinput_report->ps_btn) gamepad.buttons.sys = true;
|
||||
if (dinput_report->select_btn) gamepad->buttons.back = true;
|
||||
if (dinput_report->start_btn) gamepad->buttons.start = true;
|
||||
if (dinput_report->ps_btn) gamepad->buttons.sys = true;
|
||||
|
||||
if (dinput_report->l3_btn) gamepad.buttons.l3 = true;
|
||||
if (dinput_report->r3_btn) gamepad.buttons.r3 = true;
|
||||
if (dinput_report->l3_btn) gamepad->buttons.l3 = true;
|
||||
if (dinput_report->r3_btn) gamepad->buttons.r3 = true;
|
||||
|
||||
if (dinput_report->l1_btn) gamepad.buttons.lb = true;
|
||||
if (dinput_report->r1_btn) gamepad.buttons.rb = true;
|
||||
if (dinput_report->l1_btn) gamepad->buttons.lb = true;
|
||||
if (dinput_report->r1_btn) gamepad->buttons.rb = true;
|
||||
|
||||
if (dinput_report->l2_axis > 0)
|
||||
{
|
||||
gamepad.triggers.l = dinput_report->l2_axis;
|
||||
gamepad->triggers.l = dinput_report->l2_axis;
|
||||
}
|
||||
else if (dinput_report->l2_btn)
|
||||
{
|
||||
gamepad.triggers.l = 0xFF;
|
||||
gamepad->triggers.l = 0xFF;
|
||||
}
|
||||
|
||||
if (dinput_report->r2_axis > 0)
|
||||
if (dinput_report->r2_axis > 0)
|
||||
{
|
||||
gamepad.triggers.r = dinput_report->r2_axis;
|
||||
gamepad->triggers.r = dinput_report->r2_axis;
|
||||
}
|
||||
else if (dinput_report->r2_btn)
|
||||
{
|
||||
gamepad.triggers.r = 0xFF;
|
||||
gamepad->triggers.r = 0xFF;
|
||||
}
|
||||
|
||||
gamepad.joysticks.lx = scale_uint8_to_int16(dinput_report->l_x_axis, false);
|
||||
gamepad.joysticks.ly = scale_uint8_to_int16(dinput_report->l_y_axis, true);
|
||||
gamepad.joysticks.rx = scale_uint8_to_int16(dinput_report->r_x_axis, false);
|
||||
gamepad.joysticks.ry = scale_uint8_to_int16(dinput_report->r_y_axis, true);
|
||||
gamepad->analog_buttons.up = dinput_report->up_axis;
|
||||
gamepad->analog_buttons.down = dinput_report->down_axis;
|
||||
gamepad->analog_buttons.left = dinput_report->left_axis;
|
||||
gamepad->analog_buttons.right = dinput_report->right_axis;
|
||||
|
||||
gamepad->analog_buttons.x = dinput_report->square_axis;
|
||||
gamepad->analog_buttons.y = dinput_report->triangle_axis;
|
||||
gamepad->analog_buttons.a = dinput_report->cross_axis;
|
||||
gamepad->analog_buttons.b = dinput_report->circle_axis;
|
||||
|
||||
gamepad->analog_buttons.lb = dinput_report->l1_axis;
|
||||
gamepad->analog_buttons.rb = dinput_report->r1_axis;
|
||||
|
||||
gamepad->joysticks.lx = scale_uint8_to_int16(dinput_report->l_x_axis, false);
|
||||
gamepad->joysticks.ly = scale_uint8_to_int16(dinput_report->l_y_axis, true);
|
||||
gamepad->joysticks.rx = scale_uint8_to_int16(dinput_report->r_x_axis, false);
|
||||
gamepad->joysticks.ry = scale_uint8_to_int16(dinput_report->r_y_axis, true);
|
||||
}
|
||||
|
||||
void DInput::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
void DInput::process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
{
|
||||
static DInputReport prev_report = {0};
|
||||
(void)len;
|
||||
|
||||
static DInputReport prev_report = {};
|
||||
DInputReport dinput_report;
|
||||
memcpy(&dinput_report, report, sizeof(dinput_report));
|
||||
|
||||
@@ -103,11 +118,29 @@ void DInput::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t inst
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void DInput::process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len) {}
|
||||
|
||||
void DInput::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len) {}
|
||||
|
||||
bool DInput::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
void DInput::process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
void DInput::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report_id;
|
||||
(void)report_type;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
bool DInput::send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -2,9 +2,9 @@
|
||||
#define _DINPUT_H_
|
||||
|
||||
#include <stdint.h>
|
||||
#include "descriptors/DInputDescriptors.h"
|
||||
|
||||
#include "usbh/GPHostDriver.h"
|
||||
#include "usbd/descriptors/DInputDescriptors.h"
|
||||
|
||||
const usb_vid_pid_t dinput_devices[] =
|
||||
{
|
||||
@@ -23,14 +23,16 @@ struct DInputState
|
||||
class DInput : public GPHostDriver
|
||||
{
|
||||
public:
|
||||
~DInput() override {}
|
||||
|
||||
virtual void init(uint8_t player_id, uint8_t dev_addr, uint8_t instance);
|
||||
virtual void process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len);
|
||||
virtual bool send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
virtual bool send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
private:
|
||||
DInputState dinput;
|
||||
void update_gamepad(Gamepad& gp, const DInputReport* dinput_report);
|
||||
void update_gamepad(Gamepad* gp, const DInputReport* dinput_report);
|
||||
};
|
||||
|
||||
#endif // _DINPUT_H_
|
||||
@@ -4,7 +4,6 @@
|
||||
#include "class/hid/hid_host.h"
|
||||
|
||||
#include "usbh/ps3/Dualshock3.h"
|
||||
|
||||
#include "usbh/shared/scaling.h"
|
||||
|
||||
void Dualshock3::init(uint8_t player_id, uint8_t dev_addr, uint8_t instance)
|
||||
@@ -148,6 +147,11 @@ void Dualshock3::get_report_complete_cb(uint8_t dev_addr, uint8_t instance)
|
||||
|
||||
void Dualshock3::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report_id;
|
||||
(void)report_type;
|
||||
(void)len;
|
||||
// if (dualshock3.response_count == 0)
|
||||
// {
|
||||
// if (tuh_hid_get_report(dev_addr, instance, 0xF2, HID_REPORT_TYPE_FEATURE, &dualshock3.en_buffer, 17))
|
||||
@@ -209,42 +213,57 @@ void Dualshock3::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance,
|
||||
// }
|
||||
}
|
||||
|
||||
void Dualshock3::update_gamepad(Gamepad& gamepad, const Dualshock3Report* ds3_data)
|
||||
void Dualshock3::update_gamepad(Gamepad* gamepad, const Dualshock3Report* ds3_data)
|
||||
{
|
||||
gamepad.reset_pad();
|
||||
gamepad->reset_pad(gamepad);
|
||||
|
||||
if (ds3_data->up) gamepad.buttons.up =true;
|
||||
if (ds3_data->down) gamepad.buttons.down =true;
|
||||
if (ds3_data->left) gamepad.buttons.left =true;
|
||||
if (ds3_data->right) gamepad.buttons.right =true;
|
||||
if (ds3_data->up) gamepad->buttons.up =true;
|
||||
if (ds3_data->down) gamepad->buttons.down =true;
|
||||
if (ds3_data->left) gamepad->buttons.left =true;
|
||||
if (ds3_data->right) gamepad->buttons.right =true;
|
||||
|
||||
if (ds3_data->square) gamepad.buttons.x = true;
|
||||
if (ds3_data->triangle) gamepad.buttons.y = true;
|
||||
if (ds3_data->cross) gamepad.buttons.a = true;
|
||||
if (ds3_data->circle) gamepad.buttons.b = true;
|
||||
if (ds3_data->square) gamepad->buttons.x = true;
|
||||
if (ds3_data->triangle) gamepad->buttons.y = true;
|
||||
if (ds3_data->cross) gamepad->buttons.a = true;
|
||||
if (ds3_data->circle) gamepad->buttons.b = true;
|
||||
|
||||
if (ds3_data->select) gamepad.buttons.back = true;
|
||||
if (ds3_data->start) gamepad.buttons.start = true;
|
||||
if (ds3_data->ps) gamepad.buttons.sys = true;
|
||||
if (ds3_data->select) gamepad->buttons.back = true;
|
||||
if (ds3_data->start) gamepad->buttons.start = true;
|
||||
if (ds3_data->ps) gamepad->buttons.sys = true;
|
||||
|
||||
if (ds3_data->l3) gamepad.buttons.l3 = true;
|
||||
if (ds3_data->r3) gamepad.buttons.r3 = true;
|
||||
if (ds3_data->l3) gamepad->buttons.l3 = true;
|
||||
if (ds3_data->r3) gamepad->buttons.r3 = true;
|
||||
|
||||
if (ds3_data->l1) gamepad.buttons.lb = true;
|
||||
if (ds3_data->r1) gamepad.buttons.rb = true;
|
||||
if (ds3_data->l1) gamepad->buttons.lb = true;
|
||||
if (ds3_data->r1) gamepad->buttons.rb = true;
|
||||
|
||||
gamepad.triggers.l = ds3_data->l2_axis;
|
||||
gamepad.triggers.r = ds3_data->r2_axis;
|
||||
gamepad->analog_buttons.up = ds3_data->up_axis;
|
||||
gamepad->analog_buttons.down = ds3_data->down_axis;
|
||||
gamepad->analog_buttons.left = ds3_data->left_axis;
|
||||
gamepad->analog_buttons.right = ds3_data->right_axis;
|
||||
|
||||
gamepad.joysticks.lx = scale_uint8_to_int16(ds3_data->left_x, false);
|
||||
gamepad.joysticks.ly = scale_uint8_to_int16(ds3_data->left_y, true);
|
||||
gamepad.joysticks.rx = scale_uint8_to_int16(ds3_data->right_x, false);
|
||||
gamepad.joysticks.ry = scale_uint8_to_int16(ds3_data->right_y, true);
|
||||
gamepad->analog_buttons.x = ds3_data->square_axis;
|
||||
gamepad->analog_buttons.y = ds3_data->triangle_axis;
|
||||
gamepad->analog_buttons.a = ds3_data->cross_axis;
|
||||
gamepad->analog_buttons.b = ds3_data->circle_axis;
|
||||
|
||||
gamepad->analog_buttons.lb = ds3_data->l1_axis;
|
||||
gamepad->analog_buttons.rb = ds3_data->r1_axis;
|
||||
|
||||
gamepad->triggers.l = ds3_data->l2_axis;
|
||||
gamepad->triggers.r = ds3_data->r2_axis;
|
||||
|
||||
gamepad->joysticks.lx = scale_uint8_to_int16(ds3_data->left_x, false);
|
||||
gamepad->joysticks.ly = scale_uint8_to_int16(ds3_data->left_y, true);
|
||||
gamepad->joysticks.rx = scale_uint8_to_int16(ds3_data->right_x, false);
|
||||
gamepad->joysticks.ry = scale_uint8_to_int16(ds3_data->right_y, true);
|
||||
}
|
||||
|
||||
void Dualshock3::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
void Dualshock3::process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
{
|
||||
static Dualshock3Report prev_report = { 0 };
|
||||
(void)len;
|
||||
|
||||
static Dualshock3Report prev_report = {};
|
||||
Dualshock3Report ds3_report;
|
||||
memcpy(&ds3_report, report, sizeof(ds3_report));
|
||||
|
||||
@@ -257,10 +276,19 @@ void Dualshock3::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void Dualshock3::process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len) {}
|
||||
|
||||
bool Dualshock3::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
void Dualshock3::process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
bool Dualshock3::send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
(void)instance;
|
||||
|
||||
static absolute_time_t next_allowed_time = {0};
|
||||
absolute_time_t current_time = get_absolute_time();
|
||||
|
||||
@@ -269,13 +297,13 @@ bool Dualshock3::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t
|
||||
return false;
|
||||
}
|
||||
|
||||
dualshock3.out_report.rumble.right_duration = (gamepad.rumble.r > 0) ? 20: 0;
|
||||
dualshock3.out_report.rumble.right_motor_on = (gamepad.rumble.r > 0) ? 1 : 0;
|
||||
dualshock3.out_report.rumble.right_duration = (gamepad->rumble.r > 0) ? 20: 0;
|
||||
dualshock3.out_report.rumble.right_motor_on = (gamepad->rumble.r > 0) ? 1 : 0;
|
||||
|
||||
dualshock3.out_report.rumble.left_duration = (gamepad.rumble.l > 0) ? 20 : 0;
|
||||
dualshock3.out_report.rumble.left_motor_force = gamepad.rumble.l;
|
||||
dualshock3.out_report.rumble.left_duration = (gamepad->rumble.l > 0) ? 20 : 0;
|
||||
dualshock3.out_report.rumble.left_motor_force = gamepad->rumble.l;
|
||||
|
||||
if (gamepad.rumble.l > 0 || gamepad.rumble.r > 0 ||
|
||||
if (gamepad->rumble.l > 0 || gamepad->rumble.r > 0 ||
|
||||
absolute_time_diff_us(current_time, next_allowed_time) < 0)
|
||||
{
|
||||
tusb_control_request_t setup_packet =
|
||||
@@ -299,7 +327,7 @@ bool Dualshock3::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t
|
||||
|
||||
if (tuh_control_xfer(&transfer))
|
||||
{
|
||||
if (gamepad.rumble.l == 0 && gamepad.rumble.r == 0)
|
||||
if (gamepad->rumble.l == 0 && gamepad->rumble.r == 0)
|
||||
{
|
||||
next_allowed_time = delayed_by_us(get_absolute_time(), 500000);
|
||||
}
|
||||
|
||||
@@ -1,13 +1,10 @@
|
||||
#pragma once
|
||||
|
||||
#ifndef _DUALSHOCK3_H_
|
||||
#define _DUALSHOCK3_H_
|
||||
|
||||
#include <stdint.h>
|
||||
#include "descriptors/PS3Descriptors.h"
|
||||
|
||||
#include "usbh/GPHostDriver.h"
|
||||
#include "usbd/descriptors/PS3Descriptors.h"
|
||||
#include "usbd/descriptors/DInputDescriptors.h"
|
||||
|
||||
const usb_vid_pid_t ps3_devices[] =
|
||||
{
|
||||
@@ -26,14 +23,16 @@ struct Dualshock3State
|
||||
class Dualshock3 : public GPHostDriver
|
||||
{
|
||||
public:
|
||||
~Dualshock3() override {}
|
||||
|
||||
virtual void init(uint8_t player_id, uint8_t dev_addr, uint8_t instance);
|
||||
virtual void process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len);
|
||||
virtual bool send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
virtual bool send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
private:
|
||||
Dualshock3State dualshock3;
|
||||
void update_gamepad(Gamepad& gp, const Dualshock3Report* ds3_data);
|
||||
void update_gamepad(Gamepad* gp, const Dualshock3Report* ds3_data);
|
||||
void get_report_complete_cb(uint8_t dev_addr, uint8_t instance);
|
||||
};
|
||||
|
||||
|
||||
@@ -44,70 +44,72 @@ bool Dualshock4::set_leds(uint8_t dev_addr, uint8_t instance)
|
||||
return dualshock4.leds_set;
|
||||
}
|
||||
|
||||
void Dualshock4::update_gamepad(Gamepad& gamepad, const Dualshock4Report* ds4_data)
|
||||
void Dualshock4::update_gamepad(Gamepad* gamepad, const Dualshock4Report* ds4_data)
|
||||
{
|
||||
gamepad.reset_pad();
|
||||
gamepad->reset_pad(gamepad);
|
||||
|
||||
switch(ds4_data->dpad)
|
||||
{
|
||||
case PS4_DPAD_MASK_UP:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad->buttons.up = true;
|
||||
break;
|
||||
case PS4_DPAD_MASK_UP_RIGHT:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.up = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case PS4_DPAD_MASK_RIGHT:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case PS4_DPAD_MASK_RIGHT_DOWN:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.right = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case PS4_DPAD_MASK_DOWN:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case PS4_DPAD_MASK_DOWN_LEFT:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.down = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case PS4_DPAD_MASK_LEFT:
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case PS4_DPAD_MASK_LEFT_UP:
|
||||
gamepad.buttons.left = true;
|
||||
gamepad.buttons.up = true;
|
||||
gamepad->buttons.left = true;
|
||||
gamepad->buttons.up = true;
|
||||
break;
|
||||
}
|
||||
|
||||
if (ds4_data->square) gamepad.buttons.x = true;
|
||||
if (ds4_data->cross) gamepad.buttons.a = true;
|
||||
if (ds4_data->circle) gamepad.buttons.b = true;
|
||||
if (ds4_data->triangle) gamepad.buttons.y = true;
|
||||
if (ds4_data->square) gamepad->buttons.x = true;
|
||||
if (ds4_data->cross) gamepad->buttons.a = true;
|
||||
if (ds4_data->circle) gamepad->buttons.b = true;
|
||||
if (ds4_data->triangle) gamepad->buttons.y = true;
|
||||
|
||||
if (ds4_data->share) gamepad.buttons.back = true;
|
||||
if (ds4_data->option) gamepad.buttons.start = true;
|
||||
if (ds4_data->ps) gamepad.buttons.sys = true;
|
||||
if (ds4_data->tpad) gamepad.buttons.misc = true;
|
||||
if (ds4_data->share) gamepad->buttons.back = true;
|
||||
if (ds4_data->option) gamepad->buttons.start = true;
|
||||
if (ds4_data->ps) gamepad->buttons.sys = true;
|
||||
if (ds4_data->tpad) gamepad->buttons.misc = true;
|
||||
|
||||
if (ds4_data->l1) gamepad.buttons.lb = true;
|
||||
if (ds4_data->r1) gamepad.buttons.rb = true;
|
||||
if (ds4_data->l1) gamepad->buttons.lb = true;
|
||||
if (ds4_data->r1) gamepad->buttons.rb = true;
|
||||
|
||||
if (ds4_data->l3) gamepad.buttons.l3 = true;
|
||||
if (ds4_data->r3) gamepad.buttons.r3 = true;
|
||||
if (ds4_data->l3) gamepad->buttons.l3 = true;
|
||||
if (ds4_data->r3) gamepad->buttons.r3 = true;
|
||||
|
||||
gamepad.triggers.l = ds4_data->l2_trigger;
|
||||
gamepad.triggers.r = ds4_data->r2_trigger;
|
||||
gamepad->triggers.l = ds4_data->l2_trigger;
|
||||
gamepad->triggers.r = ds4_data->r2_trigger;
|
||||
|
||||
gamepad.joysticks.lx = scale_uint8_to_int16(ds4_data->lx, false);
|
||||
gamepad.joysticks.ly = scale_uint8_to_int16(ds4_data->ly, true);
|
||||
gamepad.joysticks.rx = scale_uint8_to_int16(ds4_data->rx, false);
|
||||
gamepad.joysticks.ry = scale_uint8_to_int16(ds4_data->ry, true);
|
||||
gamepad->joysticks.lx = scale_uint8_to_int16(ds4_data->lx, false);
|
||||
gamepad->joysticks.ly = scale_uint8_to_int16(ds4_data->ly, true);
|
||||
gamepad->joysticks.rx = scale_uint8_to_int16(ds4_data->rx, false);
|
||||
gamepad->joysticks.ry = scale_uint8_to_int16(ds4_data->ry, true);
|
||||
}
|
||||
|
||||
void Dualshock4::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
void Dualshock4::process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
{
|
||||
static Dualshock4Report prev_report = { 0 };
|
||||
(void)len;
|
||||
|
||||
static Dualshock4Report prev_report = {};
|
||||
Dualshock4Report ds4_report;
|
||||
memcpy(&ds4_report, report, sizeof(ds4_report));
|
||||
|
||||
@@ -121,16 +123,30 @@ void Dualshock4::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void Dualshock4::process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len) {}
|
||||
void Dualshock4::process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
void Dualshock4::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len) {}
|
||||
void Dualshock4::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report_id;
|
||||
(void)report_type;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
bool Dualshock4::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
bool Dualshock4::send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
Dualshock4OutReport out_report = {0};
|
||||
out_report.set_rumble = 1;
|
||||
out_report.motor_left = gamepad.rumble.l;
|
||||
out_report.motor_right = gamepad.rumble.r;
|
||||
out_report.motor_left = gamepad->rumble.l;
|
||||
out_report.motor_right = gamepad->rumble.r;
|
||||
|
||||
return tuh_hid_send_report(dev_addr, instance, 5, &out_report, sizeof(out_report));
|
||||
}
|
||||
@@ -1,5 +1,3 @@
|
||||
#pragma once
|
||||
|
||||
#ifndef _DUALSHOCK4_H_
|
||||
#define _DUALSHOCK4_H_
|
||||
|
||||
@@ -125,14 +123,16 @@ struct Dualshock4State
|
||||
class Dualshock4 : public GPHostDriver
|
||||
{
|
||||
public:
|
||||
~Dualshock4() override {}
|
||||
|
||||
virtual void init(uint8_t player_id, uint8_t dev_addr, uint8_t instance);
|
||||
virtual void process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len);
|
||||
virtual bool send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
virtual bool send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
private:
|
||||
Dualshock4State dualshock4;
|
||||
void update_gamepad(Gamepad& gp, const Dualshock4Report* ds4_data);
|
||||
void update_gamepad(Gamepad* gp, const Dualshock4Report* ds4_data);
|
||||
bool set_leds(uint8_t dev_addr, uint8_t instance);
|
||||
};
|
||||
|
||||
|
||||
@@ -3,7 +3,6 @@
|
||||
#include "tusb.h"
|
||||
|
||||
#include "usbh/ps5/Dualsense.h"
|
||||
|
||||
#include "usbh/shared/scaling.h"
|
||||
|
||||
void Dualsense::init(uint8_t player_id, uint8_t dev_addr, uint8_t instance)
|
||||
@@ -12,89 +11,105 @@ void Dualsense::init(uint8_t player_id, uint8_t dev_addr, uint8_t instance)
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void Dualsense::update_gamepad(Gamepad& gamepad, const DualsenseReport* ds_report)
|
||||
void Dualsense::update_gamepad(Gamepad* gamepad, const DualsenseReport* ds_report)
|
||||
{
|
||||
gamepad.reset_pad();
|
||||
gamepad->reset_pad(gamepad);
|
||||
|
||||
switch(ds_report->dpad)
|
||||
{
|
||||
case PS5_MASK_DPAD_UP:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad->buttons.up = true;
|
||||
break;
|
||||
case PS5_MASK_DPAD_UP_RIGHT:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.up = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case PS5_MASK_DPAD_RIGHT:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case PS5_MASK_DPAD_RIGHT_DOWN:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.right = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case PS5_MASK_DPAD_DOWN:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case PS5_MASK_DPAD_DOWN_LEFT:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.down = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case PS5_MASK_DPAD_LEFT:
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case PS5_MASK_DPAD_LEFT_UP:
|
||||
gamepad.buttons.left = true;
|
||||
gamepad.buttons.up = true;
|
||||
gamepad->buttons.left = true;
|
||||
gamepad->buttons.up = true;
|
||||
break;
|
||||
}
|
||||
|
||||
if (ds_report->square) gamepad.buttons.x = true;
|
||||
if (ds_report->cross) gamepad.buttons.a = true;
|
||||
if (ds_report->circle) gamepad.buttons.b = true;
|
||||
if (ds_report->triangle) gamepad.buttons.y = true;
|
||||
if (ds_report->square) gamepad->buttons.x = true;
|
||||
if (ds_report->cross) gamepad->buttons.a = true;
|
||||
if (ds_report->circle) gamepad->buttons.b = true;
|
||||
if (ds_report->triangle) gamepad->buttons.y = true;
|
||||
|
||||
if (ds_report->buttons[0] & PS5_MASK_L1) gamepad.buttons.lb = true;
|
||||
if (ds_report->buttons[0] & PS5_MASK_R1) gamepad.buttons.rb = true;
|
||||
if (ds_report->buttons[0] & PS5_MASK_L1) gamepad->buttons.lb = true;
|
||||
if (ds_report->buttons[0] & PS5_MASK_R1) gamepad->buttons.rb = true;
|
||||
|
||||
if (ds_report->buttons[0] & PS5_MASK_SHARE) gamepad.buttons.back = true;
|
||||
if (ds_report->buttons[0] & PS5_MASK_OPTIONS) gamepad.buttons.start = true;
|
||||
if (ds_report->buttons[0] & PS5_MASK_SHARE) gamepad->buttons.back = true;
|
||||
if (ds_report->buttons[0] & PS5_MASK_OPTIONS) gamepad->buttons.start = true;
|
||||
|
||||
if (ds_report->buttons[0] & PS5_MASK_L3) gamepad.buttons.l3 = true;
|
||||
if (ds_report->buttons[0] & PS5_MASK_R3) gamepad.buttons.r3 = true;
|
||||
if (ds_report->buttons[0] & PS5_MASK_L3) gamepad->buttons.l3 = true;
|
||||
if (ds_report->buttons[0] & PS5_MASK_R3) gamepad->buttons.r3 = true;
|
||||
|
||||
if (ds_report->buttons[1] & PS5_MASK_PS) gamepad.buttons.sys = true;
|
||||
if (ds_report->buttons[1] & PS5_MASK_MIC) gamepad.buttons.misc = true;
|
||||
if (ds_report->buttons[1] & PS5_MASK_PS) gamepad->buttons.sys = true;
|
||||
if (ds_report->buttons[1] & PS5_MASK_MIC) gamepad->buttons.misc = true;
|
||||
|
||||
gamepad.triggers.l = ds_report->lt;
|
||||
gamepad.triggers.r = ds_report->rt;
|
||||
gamepad->triggers.l = ds_report->lt;
|
||||
gamepad->triggers.r = ds_report->rt;
|
||||
|
||||
gamepad.joysticks.lx = scale_uint8_to_int16(ds_report->lx, false);
|
||||
gamepad.joysticks.ly = scale_uint8_to_int16(ds_report->ly, true);
|
||||
gamepad.joysticks.rx = scale_uint8_to_int16(ds_report->rx, false);
|
||||
gamepad.joysticks.ry = scale_uint8_to_int16(ds_report->ry, true);
|
||||
gamepad->joysticks.lx = scale_uint8_to_int16(ds_report->lx, false);
|
||||
gamepad->joysticks.ly = scale_uint8_to_int16(ds_report->ly, true);
|
||||
gamepad->joysticks.rx = scale_uint8_to_int16(ds_report->rx, false);
|
||||
gamepad->joysticks.ry = scale_uint8_to_int16(ds_report->ry, true);
|
||||
}
|
||||
|
||||
void Dualsense::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
void Dualsense::process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
{
|
||||
(void)len;
|
||||
|
||||
DualsenseReport ds_report;
|
||||
memcpy(&ds_report, report, sizeof(ds_report));
|
||||
update_gamepad(gamepad, &ds_report);
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void Dualsense::process_xinput_report(Gamepad& gp, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len) {}
|
||||
void Dualsense::process_xinput_report(Gamepad* gp, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len)
|
||||
{
|
||||
(void)gp;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
void Dualsense::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len) {}
|
||||
void Dualsense::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report_id;
|
||||
(void)report_type;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
bool Dualsense::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
bool Dualsense::send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
// need to figure out if the flags are necessary and how the LEDs work
|
||||
DualsenseOutReport out_report = {0};
|
||||
out_report.valid_flag0 = 0x02; // idk what this means
|
||||
out_report.valid_flag1 = 0x02; // this one either
|
||||
out_report.valid_flag2 = 0x04; // uhhhhh
|
||||
out_report.motor_left = gamepad.rumble.l;
|
||||
out_report.motor_right = gamepad.rumble.r;
|
||||
out_report.motor_left = gamepad->rumble.l;
|
||||
out_report.motor_right = gamepad->rumble.r;
|
||||
|
||||
return tuh_hid_send_report(dev_addr, instance, 5, &out_report, sizeof(out_report));
|
||||
}
|
||||
@@ -138,13 +138,13 @@ class Dualsense : public GPHostDriver
|
||||
{
|
||||
public:
|
||||
virtual void init(uint8_t player_id, uint8_t dev_addr, uint8_t instance);
|
||||
virtual void process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len);
|
||||
virtual bool send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
virtual bool send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
private:
|
||||
DualsenseState dualsense;
|
||||
void update_gamepad(Gamepad& gp, const DualsenseReport* ds_report);
|
||||
void update_gamepad(Gamepad* gp, const DualsenseReport* ds_report);
|
||||
};
|
||||
|
||||
#endif // _DUALSENSE_H_
|
||||
@@ -10,59 +10,61 @@ void PSClassic::init(uint8_t player_id, uint8_t dev_addr, uint8_t instance)
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void PSClassic::update_gamepad(Gamepad& gamepad, const PSClassicReport* psc_data)
|
||||
void PSClassic::update_gamepad(Gamepad* gamepad, const PSClassicReport* psc_data)
|
||||
{
|
||||
gamepad.reset_pad();
|
||||
gamepad->reset_pad(gamepad);
|
||||
|
||||
switch (psc_data->buttons & 0x3C00) {
|
||||
case PSCLASSIC_MASK_UP_LEFT:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.up = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case PSCLASSIC_MASK_UP:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad->buttons.up = true;
|
||||
break;
|
||||
case PSCLASSIC_MASK_UP_RIGHT:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.up = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case PSCLASSIC_MASK_LEFT:
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case PSCLASSIC_MASK_RIGHT:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case PSCLASSIC_MASK_DOWN_LEFT:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.down = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case PSCLASSIC_MASK_DOWN:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case PSCLASSIC_MASK_DOWN_RIGHT:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.down = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
}
|
||||
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_TRIANGLE) gamepad.buttons.y = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_CIRCLE) gamepad.buttons.b = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_CROSS) gamepad.buttons.a = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_SQUARE) gamepad.buttons.x = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_TRIANGLE) gamepad->buttons.y = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_CIRCLE) gamepad->buttons.b = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_CROSS) gamepad->buttons.a = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_SQUARE) gamepad->buttons.x = true;
|
||||
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_L2) gamepad.triggers.l = 0xFF;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_R2) gamepad.triggers.r = 0xFF;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_L2) gamepad->triggers.l = 0xFF;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_R2) gamepad->triggers.r = 0xFF;
|
||||
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_L1) gamepad.buttons.lb = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_R1) gamepad.buttons.rb = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_L1) gamepad->buttons.lb = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_R1) gamepad->buttons.rb = true;
|
||||
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_SELECT) gamepad.buttons.back = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_START) gamepad.buttons.start = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_SELECT) gamepad->buttons.back = true;
|
||||
if (psc_data->buttons & PSCLASSIC_MASK_START) gamepad->buttons.start = true;
|
||||
}
|
||||
|
||||
void PSClassic::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
void PSClassic::process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
{
|
||||
static PSClassicReport prev_report = { 0 };
|
||||
(void)len;
|
||||
|
||||
static PSClassicReport prev_report = {};
|
||||
|
||||
PSClassicReport psc_report;
|
||||
memcpy(&psc_report, report, sizeof(psc_report));
|
||||
@@ -77,11 +79,29 @@ void PSClassic::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t i
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void PSClassic::process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len) {}
|
||||
|
||||
void PSClassic::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len) {}
|
||||
|
||||
bool PSClassic::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
void PSClassic::process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
void PSClassic::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report_id;
|
||||
(void)report_type;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
bool PSClassic::send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -1,12 +1,10 @@
|
||||
#pragma once
|
||||
|
||||
#ifndef _PSCLASSIC_H_
|
||||
#define _PSCLASSIC_H_
|
||||
|
||||
#include <stdint.h>
|
||||
#include "descriptors/PSClassicDescriptors.h"
|
||||
|
||||
#include "usbh/GPHostDriver.h"
|
||||
#include "usbd/descriptors/PSClassicDescriptors.h"
|
||||
|
||||
const usb_vid_pid_t psc_devices[] =
|
||||
{
|
||||
@@ -21,14 +19,16 @@ struct PSClassicState
|
||||
class PSClassic : public GPHostDriver
|
||||
{
|
||||
public:
|
||||
~PSClassic() override {}
|
||||
|
||||
virtual void init(uint8_t player_id, uint8_t dev_addr, uint8_t instance);
|
||||
virtual void process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len);
|
||||
virtual bool send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
virtual bool send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
private:
|
||||
PSClassicState psclassic;
|
||||
void update_gamepad(Gamepad& gp, const PSClassicReport* psc_data);
|
||||
void update_gamepad(Gamepad* gp, const PSClassicReport* psc_data);
|
||||
};
|
||||
|
||||
#endif // _PSCLASSIC_H_
|
||||
@@ -7,12 +7,15 @@
|
||||
|
||||
void SwitchPro::init(uint8_t player_id, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
|
||||
switch_pro.player_id = player_id;
|
||||
}
|
||||
|
||||
void SwitchPro::send_handshake(uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
if (tuh_hid_send_ready)
|
||||
if (tuh_hid_send_ready(dev_addr, instance))
|
||||
{
|
||||
uint8_t handshake_command[2] = {CMD_HID, SUBCMD_HANDSHAKE};
|
||||
switch_pro.handshake_sent = tuh_hid_send_report(dev_addr, instance, 0, handshake_command, sizeof(handshake_command));
|
||||
@@ -31,15 +34,17 @@ uint8_t SwitchPro::get_output_sequence_counter()
|
||||
|
||||
void SwitchPro::disable_timeout(uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
if (tuh_hid_send_ready)
|
||||
if (tuh_hid_send_ready(dev_addr, instance))
|
||||
{
|
||||
uint8_t disable_timeout_cmd[2] = {CMD_HID, SUBCMD_DISABLE_TIMEOUT};
|
||||
switch_pro.timeout_disabled = tuh_hid_send_report(dev_addr, instance, 0, disable_timeout_cmd, sizeof(disable_timeout_cmd));
|
||||
}
|
||||
}
|
||||
|
||||
void SwitchPro::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
void SwitchPro::process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
{
|
||||
(void)len;
|
||||
|
||||
if (!switch_pro.handshake_sent)
|
||||
{
|
||||
return;
|
||||
@@ -51,7 +56,7 @@ void SwitchPro::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t i
|
||||
return;
|
||||
}
|
||||
|
||||
static SwitchProReport prev_report = {0};
|
||||
static SwitchProReport prev_report = {};
|
||||
|
||||
SwitchProReport switch_report;
|
||||
memcpy(&switch_report, report, sizeof(switch_report));
|
||||
@@ -86,45 +91,59 @@ int16_t SwitchPro::normalize_axes(uint16_t value)
|
||||
return (int16_t)normalized_value;
|
||||
}
|
||||
|
||||
void SwitchPro::update_gamepad(Gamepad& gamepad, const SwitchProReport* switch_report)
|
||||
void SwitchPro::update_gamepad(Gamepad* gamepad, const SwitchProReport* switch_report)
|
||||
{
|
||||
gamepad.reset_pad();
|
||||
gamepad->reset_pad(gamepad);
|
||||
|
||||
if (switch_report->up) gamepad.buttons.up =true;
|
||||
if (switch_report->down) gamepad.buttons.down =true;
|
||||
if (switch_report->left) gamepad.buttons.left =true;
|
||||
if (switch_report->right) gamepad.buttons.right =true;
|
||||
if (switch_report->up) gamepad->buttons.up =true;
|
||||
if (switch_report->down) gamepad->buttons.down =true;
|
||||
if (switch_report->left) gamepad->buttons.left =true;
|
||||
if (switch_report->right) gamepad->buttons.right =true;
|
||||
|
||||
if (switch_report->y) gamepad.buttons.x = true;
|
||||
if (switch_report->x) gamepad.buttons.y = true;
|
||||
if (switch_report->b) gamepad.buttons.a = true;
|
||||
if (switch_report->a) gamepad.buttons.b = true;
|
||||
if (switch_report->y) gamepad->buttons.x = true;
|
||||
if (switch_report->x) gamepad->buttons.y = true;
|
||||
if (switch_report->b) gamepad->buttons.a = true;
|
||||
if (switch_report->a) gamepad->buttons.b = true;
|
||||
|
||||
if (switch_report->minus) gamepad.buttons.back = true;
|
||||
if (switch_report->plus) gamepad.buttons.start = true;
|
||||
if (switch_report->home) gamepad.buttons.sys = true;
|
||||
if (switch_report->capture) gamepad.buttons.misc = true;
|
||||
if (switch_report->minus) gamepad->buttons.back = true;
|
||||
if (switch_report->plus) gamepad->buttons.start = true;
|
||||
if (switch_report->home) gamepad->buttons.sys = true;
|
||||
if (switch_report->capture) gamepad->buttons.misc = true;
|
||||
|
||||
if (switch_report->stickL) gamepad.buttons.l3 = true;
|
||||
if (switch_report->stickR) gamepad.buttons.r3 = true;
|
||||
if (switch_report->stickL) gamepad->buttons.l3 = true;
|
||||
if (switch_report->stickR) gamepad->buttons.r3 = true;
|
||||
|
||||
if (switch_report->l) gamepad.buttons.lb = true;
|
||||
if (switch_report->r) gamepad.buttons.rb = true;
|
||||
if (switch_report->l) gamepad->buttons.lb = true;
|
||||
if (switch_report->r) gamepad->buttons.rb = true;
|
||||
|
||||
if (switch_report->zl) gamepad.triggers.l = 0xFF;
|
||||
if (switch_report->zr) gamepad.triggers.r = 0xFF;
|
||||
if (switch_report->zl) gamepad->triggers.l = 0xFF;
|
||||
if (switch_report->zr) gamepad->triggers.r = 0xFF;
|
||||
|
||||
gamepad.joysticks.lx = normalize_axes(switch_report->leftX );
|
||||
gamepad.joysticks.ly = normalize_axes(switch_report->leftY );
|
||||
gamepad.joysticks.rx = normalize_axes(switch_report->rightX);
|
||||
gamepad.joysticks.ry = normalize_axes(switch_report->rightY);
|
||||
gamepad->joysticks.lx = normalize_axes(switch_report->leftX );
|
||||
gamepad->joysticks.ly = normalize_axes(switch_report->leftY );
|
||||
gamepad->joysticks.rx = normalize_axes(switch_report->rightX);
|
||||
gamepad->joysticks.ry = normalize_axes(switch_report->rightY);
|
||||
}
|
||||
|
||||
void SwitchPro::process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len) {}
|
||||
void SwitchPro::process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
void SwitchPro::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len) {}
|
||||
void SwitchPro::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report_id;
|
||||
(void)report_type;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
bool SwitchPro::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
bool SwitchPro::send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
if (!switch_pro.handshake_sent)
|
||||
{
|
||||
@@ -145,9 +164,9 @@ bool SwitchPro::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t i
|
||||
report.command = CMD_RUMBLE_ONLY;
|
||||
report.sequence_counter = get_output_sequence_counter();
|
||||
|
||||
if (gamepad.rumble.l > 0)
|
||||
if (gamepad->rumble.l > 0)
|
||||
{
|
||||
uint8_t amplitude_l = static_cast<uint8_t>(((gamepad.rumble.l / 255.0f) * 0.8f + 0.5f) * (0xC0 - 0x40) + 0x40);
|
||||
uint8_t amplitude_l = static_cast<uint8_t>(((gamepad->rumble.l / 255.0f) * 0.8f + 0.5f) * (0xC0 - 0x40) + 0x40);
|
||||
|
||||
report.rumble_l[0] = amplitude_l;
|
||||
report.rumble_l[1] = 0x88;
|
||||
@@ -162,9 +181,9 @@ bool SwitchPro::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t i
|
||||
report.rumble_l[3] = 0x40;
|
||||
}
|
||||
|
||||
if (gamepad.rumble.r > 0)
|
||||
if (gamepad->rumble.r > 0)
|
||||
{
|
||||
uint8_t amplitude_r = static_cast<uint8_t>(((gamepad.rumble.r / 255.0f) * 0.8f + 0.5f) * (0xC0 - 0x40) + 0x40);
|
||||
uint8_t amplitude_r = static_cast<uint8_t>(((gamepad->rumble.r / 255.0f) * 0.8f + 0.5f) * (0xC0 - 0x40) + 0x40);
|
||||
|
||||
report.rumble_r[0] = amplitude_r;
|
||||
report.rumble_r[1] = 0x88;
|
||||
|
||||
@@ -1,11 +1,9 @@
|
||||
#pragma once
|
||||
|
||||
#ifndef _SWITCHPRO_H_
|
||||
#define _SWITCHPRO_H_
|
||||
|
||||
#include <stdint.h>
|
||||
#include "descriptors/SwitchProDescriptors.h"
|
||||
|
||||
#include "usbd/descriptors/SwitchProDescriptors.h"
|
||||
#include "usbh/GPHostDriver.h"
|
||||
|
||||
const usb_vid_pid_t switch_pro_devices[] =
|
||||
@@ -29,18 +27,20 @@ struct SwitchProState
|
||||
class SwitchPro : public GPHostDriver
|
||||
{
|
||||
public:
|
||||
~SwitchPro() override {}
|
||||
|
||||
virtual void init(uint8_t player_id, uint8_t dev_addr, uint8_t instance);
|
||||
virtual void process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len);
|
||||
virtual bool send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
virtual bool send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
private:
|
||||
SwitchProState switch_pro;
|
||||
void send_handshake(uint8_t dev_addr, uint8_t instance);
|
||||
void disable_timeout(uint8_t dev_addr, uint8_t instance);
|
||||
uint8_t get_output_sequence_counter();
|
||||
int16_t normalize_axes(uint16_t value);
|
||||
void update_gamepad(Gamepad& gp, const SwitchProReport* switch_pro_data);
|
||||
void update_gamepad(Gamepad* gp, const SwitchProReport* switch_pro_data);
|
||||
};
|
||||
|
||||
#endif // _SWITCHPRO_H_
|
||||
@@ -2,11 +2,10 @@
|
||||
#include "pico/stdlib.h"
|
||||
#include "pico/time.h"
|
||||
#include "tusb.h"
|
||||
#include "descriptors/SwitchDescriptors.h"
|
||||
|
||||
#include "usbh/switch/SwitchWired.h"
|
||||
|
||||
#include "usbh/shared/scaling.h"
|
||||
#include "usbd/descriptors/SwitchDescriptors.h"
|
||||
|
||||
void SwitchWired::init(uint8_t player_id, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
@@ -14,9 +13,11 @@ void SwitchWired::init(uint8_t player_id, uint8_t dev_addr, uint8_t instance)
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void SwitchWired::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
void SwitchWired::process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
{
|
||||
static SwitchWiredReport prev_report = {0};
|
||||
(void)len;
|
||||
|
||||
static SwitchWiredReport prev_report = {};
|
||||
|
||||
SwitchWiredReport switch_report;
|
||||
memcpy(&switch_report, report, sizeof(switch_report));
|
||||
@@ -31,72 +32,90 @@ void SwitchWired::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t
|
||||
tuh_hid_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void SwitchWired::update_gamepad(Gamepad& gamepad, const SwitchWiredReport* switch_report)
|
||||
void SwitchWired::update_gamepad(Gamepad* gamepad, const SwitchWiredReport* switch_report)
|
||||
{
|
||||
gamepad.reset_pad();
|
||||
gamepad->reset_pad(gamepad);
|
||||
|
||||
switch (switch_report->dpad)
|
||||
{
|
||||
case SWITCH_HAT_UP:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad->buttons.up = true;
|
||||
break;
|
||||
case SWITCH_HAT_UPRIGHT:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.up = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case SWITCH_HAT_RIGHT:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad->buttons.right = true;
|
||||
break;
|
||||
case SWITCH_HAT_DOWNRIGHT:
|
||||
gamepad.buttons.right = true;
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.right = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case SWITCH_HAT_DOWN:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad->buttons.down = true;
|
||||
break;
|
||||
case SWITCH_HAT_DOWNLEFT:
|
||||
gamepad.buttons.down = true;
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.down = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case SWITCH_HAT_LEFT:
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
case SWITCH_HAT_UPLEFT:
|
||||
gamepad.buttons.up = true;
|
||||
gamepad.buttons.left = true;
|
||||
gamepad->buttons.up = true;
|
||||
gamepad->buttons.left = true;
|
||||
break;
|
||||
}
|
||||
|
||||
if (switch_report->b) gamepad.buttons.a = true;
|
||||
if (switch_report->a) gamepad.buttons.b = true;
|
||||
if (switch_report->y) gamepad.buttons.x = true;
|
||||
if (switch_report->x) gamepad.buttons.y = true;
|
||||
if (switch_report->b) gamepad->buttons.a = true;
|
||||
if (switch_report->a) gamepad->buttons.b = true;
|
||||
if (switch_report->y) gamepad->buttons.x = true;
|
||||
if (switch_report->x) gamepad->buttons.y = true;
|
||||
|
||||
if (switch_report->minus) gamepad.buttons.back = true;
|
||||
if (switch_report->plus) gamepad.buttons.start = true;
|
||||
if (switch_report->l3) gamepad.buttons.l3 = true;
|
||||
if (switch_report->r3) gamepad.buttons.r3 = true;
|
||||
if (switch_report->minus) gamepad->buttons.back = true;
|
||||
if (switch_report->plus) gamepad->buttons.start = true;
|
||||
if (switch_report->l3) gamepad->buttons.l3 = true;
|
||||
if (switch_report->r3) gamepad->buttons.r3 = true;
|
||||
|
||||
if(switch_report->home) gamepad.buttons.sys = true;
|
||||
if(switch_report->capture) gamepad.buttons.misc = true;
|
||||
if(switch_report->home) gamepad->buttons.sys = true;
|
||||
if(switch_report->capture) gamepad->buttons.misc = true;
|
||||
|
||||
if(switch_report->l) gamepad.buttons.lb = true;
|
||||
if(switch_report->r) gamepad.buttons.rb = true;
|
||||
if(switch_report->l) gamepad->buttons.lb = true;
|
||||
if(switch_report->r) gamepad->buttons.rb = true;
|
||||
|
||||
if(switch_report->lz) gamepad.triggers.l = 0xFF;
|
||||
if(switch_report->rz) gamepad.triggers.r = 0xFF;
|
||||
if(switch_report->lz) gamepad->triggers.l = 0xFF;
|
||||
if(switch_report->rz) gamepad->triggers.r = 0xFF;
|
||||
|
||||
gamepad.joysticks.lx = scale_uint8_to_int16(switch_report->lx, false);
|
||||
gamepad.joysticks.ly = scale_uint8_to_int16(switch_report->ly, true);
|
||||
gamepad.joysticks.rx = scale_uint8_to_int16(switch_report->rx, false);
|
||||
gamepad.joysticks.ry = scale_uint8_to_int16(switch_report->ry, true);
|
||||
gamepad->joysticks.lx = scale_uint8_to_int16(switch_report->lx, false);
|
||||
gamepad->joysticks.ly = scale_uint8_to_int16(switch_report->ly, true);
|
||||
gamepad->joysticks.rx = scale_uint8_to_int16(switch_report->rx, false);
|
||||
gamepad->joysticks.ry = scale_uint8_to_int16(switch_report->ry, true);
|
||||
}
|
||||
|
||||
void SwitchWired::process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len) {}
|
||||
|
||||
void SwitchWired::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len) {}
|
||||
|
||||
bool SwitchWired::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
void SwitchWired::process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
void SwitchWired::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report_id;
|
||||
(void)report_type;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
bool SwitchWired::send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
(void)gamepad;
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
|
||||
return true; // not aware of a wired switch gamepad with rumble
|
||||
}
|
||||
@@ -1,5 +1,3 @@
|
||||
#pragma once
|
||||
|
||||
#ifndef _SWITCHWIRED_H_
|
||||
#define _SWITCHWIRED_H_
|
||||
|
||||
@@ -54,14 +52,16 @@ struct SwitchWiredState
|
||||
class SwitchWired : public GPHostDriver
|
||||
{
|
||||
public:
|
||||
~SwitchWired() override {}
|
||||
|
||||
virtual void init(uint8_t player_id, uint8_t dev_addr, uint8_t instance);
|
||||
virtual void process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len);
|
||||
virtual bool send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
virtual bool send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
private:
|
||||
SwitchWiredState switch_wired;
|
||||
void update_gamepad(Gamepad& gp, const SwitchWiredReport* switch_pro_data);
|
||||
void update_gamepad(Gamepad* gp, const SwitchWiredReport* switch_pro_data);
|
||||
};
|
||||
|
||||
#endif // _SWITCHWIRED_H_
|
||||
@@ -7,13 +7,13 @@
|
||||
|
||||
#include "usbh/tusb_host.h"
|
||||
#include "usbh/tusb_host_manager.h"
|
||||
#include "usbd/board_config.h"
|
||||
#include "ogxm_config.h"
|
||||
|
||||
#define PIO_USB_CONFIG { PIO_USB_DP_PIN, PIO_USB_TX_DEFAULT, PIO_SM_USB_TX_DEFAULT, PIO_USB_DMA_TX_DEFAULT, PIO_USB_RX_DEFAULT, PIO_SM_USB_RX_DEFAULT, PIO_SM_USB_EOP_DEFAULT, NULL, PIO_USB_DEBUG_PIN_NONE, PIO_USB_DEBUG_PIN_NONE, false, PIO_USB_PINOUT_DPDM }
|
||||
|
||||
void board_setup()
|
||||
{
|
||||
#if USBD_BOARD == OGXM_ADA_FEATHER_USBH
|
||||
#if OGXM_BOARD == ADAFRUIT_FEATHER_USBH
|
||||
gpio_init(VCC_EN_PIN);
|
||||
gpio_set_dir(VCC_EN_PIN, GPIO_OUT);
|
||||
gpio_put(VCC_EN_PIN, 1);
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
#include "tusb.h"
|
||||
#include "host/usbh.h"
|
||||
#include "class/hid/hid_host.h"
|
||||
#include "tusb_gamepad.h"
|
||||
|
||||
#include "usbh/xinput/XInput.h"
|
||||
#include "usbh/n64usb/N64USB.h"
|
||||
@@ -16,20 +17,19 @@
|
||||
#include "usbh/shared/hid_class_driver.h"
|
||||
#include "usbh/tusb_host_manager.h"
|
||||
|
||||
#include "usbd/board_config.h"
|
||||
#include "Gamepad.h"
|
||||
#include "ogxm_config.h"
|
||||
|
||||
struct HostedDevice
|
||||
struct HostManager
|
||||
{
|
||||
bool hid_class = {false};
|
||||
bool class_mounted = {false};
|
||||
uint8_t class_address;
|
||||
uint8_t class_instance;
|
||||
bool hid = {false};
|
||||
bool mounted = {false};
|
||||
uint8_t address;
|
||||
uint8_t instance;
|
||||
const usbh_class_driver_t* class_driver = {&usbh_xinput_driver};
|
||||
GPHostDriver* gamepad_driver = {nullptr};
|
||||
GPHostDriver* gp_host_driver = {nullptr};
|
||||
};
|
||||
|
||||
HostedDevice hosted_device[MAX_GAMEPADS] = {};
|
||||
HostManager host_manager[MAX_GAMEPADS] = {};
|
||||
|
||||
typedef struct
|
||||
{
|
||||
@@ -55,7 +55,7 @@ void led_mounted_indicator(bool mounted)
|
||||
gpio_put(LED_INDICATOR_PIN, mounted ? 1 : 0);
|
||||
}
|
||||
|
||||
bool check_vid_pid(const usb_vid_pid_t* devices, size_t num_devices, HostMode check_mode, uint16_t vid, uint16_t pid)
|
||||
bool check_vid_pid(const usb_vid_pid_t* devices, size_t num_devices, uint16_t vid, uint16_t pid)
|
||||
{
|
||||
for (size_t i = 0; i < num_devices; i++)
|
||||
{
|
||||
@@ -68,42 +68,44 @@ bool check_vid_pid(const usb_vid_pid_t* devices, size_t num_devices, HostMode ch
|
||||
return false;
|
||||
}
|
||||
|
||||
void create_gamepad_driver(HostMode host_mode, int idx)
|
||||
void init_gp_host_driver(HostMode host_mode, int idx)
|
||||
{
|
||||
switch(host_mode)
|
||||
{
|
||||
case HOST_MODE_XINPUT:
|
||||
hosted_device[idx].gamepad_driver = new XInputHost();
|
||||
host_manager[idx].gp_host_driver = new XInputHost();
|
||||
break;
|
||||
case HOST_MODE_HID_PSCLASSIC:
|
||||
hosted_device[idx].gamepad_driver = new PSClassic();
|
||||
host_manager[idx].gp_host_driver = new PSClassic();
|
||||
break;
|
||||
case HOST_MODE_HID_DINPUT:
|
||||
hosted_device[idx].gamepad_driver = new DInput();
|
||||
host_manager[idx].gp_host_driver = new DInput();
|
||||
break;
|
||||
case HOST_MODE_HID_PS3:
|
||||
hosted_device[idx].gamepad_driver = new Dualshock3();
|
||||
host_manager[idx].gp_host_driver = new Dualshock3();
|
||||
break;
|
||||
case HOST_MODE_HID_PS4:
|
||||
hosted_device[idx].gamepad_driver = new Dualshock4();
|
||||
host_manager[idx].gp_host_driver = new Dualshock4();
|
||||
break;
|
||||
case HOST_MODE_HID_PS5:
|
||||
hosted_device[idx].gamepad_driver = new Dualsense();
|
||||
host_manager[idx].gp_host_driver = new Dualsense();
|
||||
break;
|
||||
case HOST_MODE_HID_SWITCH_PRO:
|
||||
hosted_device[idx].gamepad_driver = new SwitchPro();
|
||||
host_manager[idx].gp_host_driver = new SwitchPro();
|
||||
break;
|
||||
case HOST_MODE_HID_SWITCH_WIRED:
|
||||
hosted_device[idx].gamepad_driver = new SwitchWired();
|
||||
host_manager[idx].gp_host_driver = new SwitchWired();
|
||||
break;
|
||||
case HOST_MODE_HID_N64USB:
|
||||
hosted_device[idx].gamepad_driver = new N64USB();
|
||||
host_manager[idx].gp_host_driver = new N64USB();
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if (hosted_device[idx].gamepad_driver)
|
||||
if (host_manager[idx].gp_host_driver)
|
||||
{
|
||||
hosted_device[idx].gamepad_driver->init((uint8_t)idx + 1, hosted_device[idx].class_address, hosted_device[idx].class_instance);
|
||||
host_manager[idx].gp_host_driver->init((uint8_t)idx + 1, host_manager[idx].address, host_manager[idx].instance);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -111,9 +113,9 @@ int find_free_slot()
|
||||
{
|
||||
for (int i = 0; i < MAX_GAMEPADS; i++)
|
||||
{
|
||||
if (!hosted_device[i].class_mounted)
|
||||
if (!host_manager[i].mounted)
|
||||
{
|
||||
hosted_device[i].class_mounted = true;
|
||||
host_manager[i].mounted = true;
|
||||
return i;
|
||||
}
|
||||
}
|
||||
@@ -125,15 +127,19 @@ void unmount_gamepad(uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
for (int i = 0; i < MAX_GAMEPADS; i++)
|
||||
{
|
||||
if (hosted_device[i].class_mounted && hosted_device[i].class_address == dev_addr && hosted_device[i].class_instance == instance)
|
||||
if (host_manager[i].mounted &&
|
||||
host_manager[i].address == dev_addr &&
|
||||
host_manager[i].instance == instance)
|
||||
{
|
||||
hosted_device[i].class_mounted = false;
|
||||
gamepad(i).reset_pad();
|
||||
host_manager[i].mounted = false;
|
||||
|
||||
gamepad(i)->reset_pad(gamepad(i));
|
||||
gamepad(i)->enable_analog_buttons = false;
|
||||
|
||||
if (hosted_device[i].gamepad_driver)
|
||||
if (host_manager[i].gp_host_driver)
|
||||
{
|
||||
delete hosted_device[i].gamepad_driver;
|
||||
hosted_device[i].gamepad_driver = nullptr;
|
||||
delete host_manager[i].gp_host_driver;
|
||||
host_manager[i].gp_host_driver = nullptr;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -142,7 +148,7 @@ void unmount_gamepad(uint8_t dev_addr, uint8_t instance)
|
||||
|
||||
for (int i = 0; i < MAX_GAMEPADS; i++)
|
||||
{
|
||||
if (hosted_device[i].gamepad_driver != nullptr)
|
||||
if (host_manager[i].gp_host_driver != nullptr)
|
||||
{
|
||||
all_free = false;
|
||||
break;
|
||||
@@ -159,19 +165,21 @@ void unmount_gamepad(uint8_t dev_addr, uint8_t instance)
|
||||
|
||||
void tuh_mount_cb(uint8_t daddr)
|
||||
{
|
||||
(void)daddr;
|
||||
|
||||
led_mounted_indicator(true);
|
||||
}
|
||||
|
||||
void tuh_umount_cb(uint8_t daddr)
|
||||
{
|
||||
|
||||
(void)daddr;
|
||||
}
|
||||
|
||||
usbh_class_driver_t const* usbh_app_driver_get_cb(uint8_t* driver_count)
|
||||
{
|
||||
*driver_count = 1;
|
||||
|
||||
return hosted_device[0].class_driver;
|
||||
return host_manager[0].class_driver;
|
||||
}
|
||||
|
||||
/* ----------- HID ----------- */
|
||||
@@ -183,12 +191,11 @@ void tuh_hid_mount_cb(uint8_t dev_addr, uint8_t instance, uint8_t const* desc_re
|
||||
|
||||
int slot = find_free_slot();
|
||||
|
||||
if (slot < 0) return; // no available slots
|
||||
if (slot < 0) return; // no available slots, shouldn't happen
|
||||
|
||||
hosted_device[slot].class_address = dev_addr;
|
||||
hosted_device[slot].class_instance = instance;
|
||||
host_manager[slot].address = dev_addr;
|
||||
host_manager[slot].instance = instance;
|
||||
|
||||
HostMode host_mode;
|
||||
uint16_t vid, pid;
|
||||
|
||||
tuh_vid_pid_get(dev_addr, &vid, &pid);
|
||||
@@ -197,11 +204,18 @@ void tuh_hid_mount_cb(uint8_t dev_addr, uint8_t instance, uint8_t const* desc_re
|
||||
|
||||
for (size_t i = 0; i < num_device_types; i++)
|
||||
{
|
||||
if (check_vid_pid(device_types[i].devices, device_types[i].num_devices, device_types[i].check_mode, vid, pid))
|
||||
if (check_vid_pid(device_types[i].devices, device_types[i].num_devices, vid, pid))
|
||||
{
|
||||
hosted_device[slot].hid_class = true;
|
||||
host_mode = device_types[i].check_mode;
|
||||
create_gamepad_driver(host_mode, slot);
|
||||
host_manager[slot].hid = true;
|
||||
|
||||
init_gp_host_driver(device_types[i].check_mode, slot);
|
||||
|
||||
if (device_types[i].check_mode == HOST_MODE_HID_DINPUT ||
|
||||
device_types[i].check_mode == HOST_MODE_HID_PS3)
|
||||
{
|
||||
gamepad(slot)->enable_analog_buttons = true;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -218,13 +232,13 @@ void tuh_hid_report_received_cb(uint8_t dev_addr, uint8_t instance, uint8_t cons
|
||||
{
|
||||
for (int i = 0; i < MAX_GAMEPADS; i++)
|
||||
{
|
||||
if (hosted_device[i].class_mounted &&
|
||||
hosted_device[i].class_address == dev_addr &&
|
||||
hosted_device[i].class_instance == instance)
|
||||
if (host_manager[i].mounted &&
|
||||
host_manager[i].address == dev_addr &&
|
||||
host_manager[i].instance == instance)
|
||||
{
|
||||
if (hosted_device[i].gamepad_driver)
|
||||
if (host_manager[i].gp_host_driver)
|
||||
{
|
||||
hosted_device[i].gamepad_driver->process_hid_report(gamepad(i), dev_addr, instance, report, len);
|
||||
host_manager[i].gp_host_driver->process_hid_report(gamepad(i), dev_addr, instance, report, len);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -236,11 +250,11 @@ void tuh_hid_report_received_cb(uint8_t dev_addr, uint8_t instance, uint8_t cons
|
||||
// {
|
||||
// for (int i = 0; i < MAX_GAMEPADS; i++)
|
||||
// {
|
||||
// if (hosted_device[i].class_mounted &&
|
||||
// hosted_device[i].class_address == dev_addr &&
|
||||
// hosted_device[i].class_instance == instance)
|
||||
// if (host_manager[i].mounted &&
|
||||
// host_manager[i].address == dev_addr &&
|
||||
// host_manager[i].instance == instance)
|
||||
// {
|
||||
// hosted_device[i].gamepad_driver->hid_get_report_complete_cb(dev_addr, instance, report_id, report_type, len);
|
||||
// host_manager[i].gp_host_driver->hid_get_report_complete_cb(dev_addr, instance, report_id, report_type, len);
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
@@ -249,14 +263,21 @@ void tuh_hid_report_received_cb(uint8_t dev_addr, uint8_t instance, uint8_t cons
|
||||
|
||||
void tuh_xinput_mount_cb(uint8_t dev_addr, uint8_t instance, const xinputh_interface_t *xinput_itf)
|
||||
{
|
||||
(void)xinput_itf;
|
||||
|
||||
int slot = find_free_slot();
|
||||
|
||||
if (slot < 0) return; // no available slots
|
||||
|
||||
hosted_device[slot].class_address = dev_addr;
|
||||
hosted_device[slot].class_instance = instance;
|
||||
host_manager[slot].address = dev_addr;
|
||||
host_manager[slot].instance = instance;
|
||||
|
||||
create_gamepad_driver(HOST_MODE_XINPUT, slot);
|
||||
init_gp_host_driver(HOST_MODE_XINPUT, slot);
|
||||
|
||||
if (xinput_itf->type == XBOXOG)
|
||||
{
|
||||
gamepad(slot)->enable_analog_buttons = true;
|
||||
}
|
||||
|
||||
tuh_xinput_receive_report(dev_addr, instance);
|
||||
}
|
||||
@@ -270,11 +291,11 @@ void tuh_xinput_report_received_cb(uint8_t dev_addr, uint8_t instance, xinputh_i
|
||||
{
|
||||
for (int i = 0; i < MAX_GAMEPADS; i++)
|
||||
{
|
||||
if (hosted_device[i].class_mounted && hosted_device[i].class_address == dev_addr && hosted_device[i].class_instance == instance)
|
||||
if (host_manager[i].mounted && host_manager[i].address == dev_addr && host_manager[i].instance == instance)
|
||||
{
|
||||
if (hosted_device[i].gamepad_driver)
|
||||
if (host_manager[i].gp_host_driver)
|
||||
{
|
||||
hosted_device[i].gamepad_driver->process_xinput_report(gamepad(i), dev_addr, instance, report, len);
|
||||
host_manager[i].gp_host_driver->process_xinput_report(gamepad(i), dev_addr, instance, report, len);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -284,6 +305,19 @@ void tuh_xinput_report_received_cb(uint8_t dev_addr, uint8_t instance, xinputh_i
|
||||
|
||||
/* ----------- SEND FEEDBACK ----------- */
|
||||
|
||||
void reset_hid_rumble(Gamepad* gp)
|
||||
{
|
||||
if (gp->rumble.l != UINT8_MAX)
|
||||
{
|
||||
gp->rumble.l = 0;
|
||||
}
|
||||
|
||||
if (gp->rumble.r != UINT8_MAX)
|
||||
{
|
||||
gp->rumble.r = 0;
|
||||
}
|
||||
}
|
||||
|
||||
void send_fb_data_to_gamepad()
|
||||
{
|
||||
static const uint8_t fb_interval_ms = 100;
|
||||
@@ -291,19 +325,19 @@ void send_fb_data_to_gamepad()
|
||||
|
||||
for (int i = 0; i < MAX_GAMEPADS; i++)
|
||||
{
|
||||
if (!hosted_device[i].class_mounted || !hosted_device[i].gamepad_driver) break;
|
||||
if (!host_manager[i].mounted || !host_manager[i].gp_host_driver) break;
|
||||
|
||||
unsigned long current_time = to_ms_since_boot(get_absolute_time());
|
||||
|
||||
if (current_time - fb_sent_time[i] >= fb_interval_ms)
|
||||
{
|
||||
if (hosted_device[i].gamepad_driver->send_fb_data(gamepad(i), hosted_device[i].class_address, hosted_device[i].class_instance))
|
||||
if (host_manager[i].gp_host_driver->send_fb_data(gamepad(i), host_manager[i].address, host_manager[i].instance))
|
||||
{
|
||||
fb_sent_time[i] = current_time;
|
||||
|
||||
if (hosted_device[i].hid_class)
|
||||
if (host_manager[i].hid)
|
||||
{
|
||||
gamepad(i).reset_hid_rumble(); // reset rumble so it doesn't get stuck on
|
||||
reset_hid_rumble(gamepad(i));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -15,53 +15,84 @@ void XInputHost::set_leds(uint8_t dev_addr, uint8_t instance)
|
||||
xinput.leds_set = tuh_xinput_set_led(dev_addr, instance, xinput.player_id, true);
|
||||
}
|
||||
|
||||
void XInputHost::process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len)
|
||||
void XInputHost::process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len)
|
||||
{
|
||||
(void)len;
|
||||
|
||||
xinputh_interface_t *xid_itf = (xinputh_interface_t *)report;
|
||||
xinput_gamepad_t *xinput_data = &xid_itf->pad;
|
||||
|
||||
if (xid_itf->connected && xid_itf->new_pad_data)
|
||||
{
|
||||
gamepad.reset_pad();
|
||||
gamepad->reset_pad(gamepad);
|
||||
|
||||
gamepad.buttons.up = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_UP) != 0;
|
||||
gamepad.buttons.down = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_DOWN) != 0;
|
||||
gamepad.buttons.left = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_LEFT) != 0;
|
||||
gamepad.buttons.right = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_RIGHT) != 0;
|
||||
gamepad->buttons.up = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_UP) != 0;
|
||||
gamepad->buttons.down = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_DOWN) != 0;
|
||||
gamepad->buttons.left = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_LEFT) != 0;
|
||||
gamepad->buttons.right = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_RIGHT) != 0;
|
||||
|
||||
gamepad.buttons.a = (xinput_data->wButtons & XINPUT_GAMEPAD_A) != 0;
|
||||
gamepad.buttons.b = (xinput_data->wButtons & XINPUT_GAMEPAD_B) != 0;
|
||||
gamepad.buttons.x = (xinput_data->wButtons & XINPUT_GAMEPAD_X) != 0;
|
||||
gamepad.buttons.y = (xinput_data->wButtons & XINPUT_GAMEPAD_Y) != 0;
|
||||
gamepad->buttons.a = (xinput_data->wButtons & XINPUT_GAMEPAD_A) != 0;
|
||||
gamepad->buttons.b = (xinput_data->wButtons & XINPUT_GAMEPAD_B) != 0;
|
||||
gamepad->buttons.x = (xinput_data->wButtons & XINPUT_GAMEPAD_X) != 0;
|
||||
gamepad->buttons.y = (xinput_data->wButtons & XINPUT_GAMEPAD_Y) != 0;
|
||||
|
||||
gamepad.buttons.l3 = (xinput_data->wButtons & XINPUT_GAMEPAD_LEFT_THUMB) != 0;
|
||||
gamepad.buttons.r3 = (xinput_data->wButtons & XINPUT_GAMEPAD_RIGHT_THUMB) != 0;
|
||||
gamepad.buttons.back = (xinput_data->wButtons & XINPUT_GAMEPAD_BACK) != 0;
|
||||
gamepad.buttons.start = (xinput_data->wButtons & XINPUT_GAMEPAD_START) != 0;
|
||||
gamepad->buttons.l3 = (xinput_data->wButtons & XINPUT_GAMEPAD_LEFT_THUMB) != 0;
|
||||
gamepad->buttons.r3 = (xinput_data->wButtons & XINPUT_GAMEPAD_RIGHT_THUMB) != 0;
|
||||
gamepad->buttons.back = (xinput_data->wButtons & XINPUT_GAMEPAD_BACK) != 0;
|
||||
gamepad->buttons.start = (xinput_data->wButtons & XINPUT_GAMEPAD_START) != 0;
|
||||
|
||||
gamepad.buttons.rb = (xinput_data->wButtons & XINPUT_GAMEPAD_RIGHT_SHOULDER) != 0;
|
||||
gamepad.buttons.lb = (xinput_data->wButtons & XINPUT_GAMEPAD_LEFT_SHOULDER) != 0;
|
||||
gamepad.buttons.sys = (xinput_data->wButtons & XINPUT_GAMEPAD_GUIDE) != 0;
|
||||
gamepad.buttons.misc = (xinput_data->wButtons & XINPUT_GAMEPAD_SHARE) != 0;
|
||||
gamepad->buttons.rb = (xinput_data->wButtons & XINPUT_GAMEPAD_RIGHT_SHOULDER) != 0;
|
||||
gamepad->buttons.lb = (xinput_data->wButtons & XINPUT_GAMEPAD_LEFT_SHOULDER) != 0;
|
||||
gamepad->buttons.sys = (xinput_data->wButtons & XINPUT_GAMEPAD_GUIDE) != 0;
|
||||
gamepad->buttons.misc = (xinput_data->wButtons & XINPUT_GAMEPAD_SHARE) != 0;
|
||||
|
||||
gamepad.triggers.l = xinput_data->bLeftTrigger;
|
||||
gamepad.triggers.r = xinput_data->bRightTrigger;
|
||||
if (gamepad->enable_analog_buttons)
|
||||
{
|
||||
gamepad->analog_buttons.up = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_UP) ? UINT8_MAX : 0;
|
||||
gamepad->analog_buttons.down = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_DOWN) ? UINT8_MAX : 0;
|
||||
gamepad->analog_buttons.left = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_LEFT) ? UINT8_MAX : 0;
|
||||
gamepad->analog_buttons.right = (xinput_data->wButtons & XINPUT_GAMEPAD_DPAD_RIGHT) ? UINT8_MAX : 0;
|
||||
|
||||
gamepad.joysticks.lx = xinput_data->sThumbLX;
|
||||
gamepad.joysticks.ly = xinput_data->sThumbLY;
|
||||
gamepad->analog_buttons.a = xinput_data->analogButtons.a;
|
||||
gamepad->analog_buttons.b = xinput_data->analogButtons.b;
|
||||
gamepad->analog_buttons.x = xinput_data->analogButtons.x;
|
||||
gamepad->analog_buttons.y = xinput_data->analogButtons.y;
|
||||
|
||||
gamepad.joysticks.rx = xinput_data->sThumbRX;
|
||||
gamepad.joysticks.ry = xinput_data->sThumbRY;
|
||||
gamepad->analog_buttons.lb = xinput_data->analogButtons.white;
|
||||
gamepad->analog_buttons.rb = xinput_data->analogButtons.black;
|
||||
}
|
||||
|
||||
gamepad->triggers.l = xinput_data->bLeftTrigger;
|
||||
gamepad->triggers.r = xinput_data->bRightTrigger;
|
||||
|
||||
gamepad->joysticks.lx = xinput_data->sThumbLX;
|
||||
gamepad->joysticks.ly = xinput_data->sThumbLY;
|
||||
gamepad->joysticks.rx = xinput_data->sThumbRX;
|
||||
gamepad->joysticks.ry = xinput_data->sThumbRY;
|
||||
}
|
||||
|
||||
tuh_xinput_receive_report(dev_addr, instance);
|
||||
}
|
||||
|
||||
void XInputHost::process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len) {}
|
||||
void XInputHost::process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report;
|
||||
(void)len;
|
||||
(void)gamepad;
|
||||
}
|
||||
|
||||
void XInputHost::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len) {}
|
||||
void XInputHost::hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len)
|
||||
{
|
||||
(void)dev_addr;
|
||||
(void)instance;
|
||||
(void)report_id;
|
||||
(void)report_type;
|
||||
(void)len;
|
||||
}
|
||||
|
||||
bool XInputHost::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
bool XInputHost::send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance)
|
||||
{
|
||||
static int report_num = 0;
|
||||
|
||||
@@ -79,5 +110,5 @@ bool XInputHost::send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t
|
||||
report_num = 0;
|
||||
}
|
||||
|
||||
return tuh_xinput_set_rumble(dev_addr, instance, gamepad.rumble.l, gamepad.rumble.r, true);
|
||||
return tuh_xinput_set_rumble(dev_addr, instance, gamepad->rumble.l, gamepad->rumble.r, true);
|
||||
}
|
||||
@@ -17,11 +17,13 @@ struct XInputState
|
||||
class XInputHost : public GPHostDriver
|
||||
{
|
||||
public:
|
||||
~XInputHost() override {}
|
||||
|
||||
virtual void init(uint8_t player_id, uint8_t dev_addr, uint8_t instance);
|
||||
virtual void process_hid_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad& gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void process_hid_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, uint8_t const* report, uint16_t len);
|
||||
virtual void process_xinput_report(Gamepad* gamepad, uint8_t dev_addr, uint8_t instance, xinputh_interface_t const* report, uint16_t len);
|
||||
virtual void hid_get_report_complete_cb(uint8_t dev_addr, uint8_t instance, uint8_t report_id, uint8_t report_type, uint16_t len);
|
||||
virtual bool send_fb_data(const Gamepad& gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
virtual bool send_fb_data(const Gamepad* gamepad, uint8_t dev_addr, uint8_t instance);
|
||||
private:
|
||||
XInputState xinput;
|
||||
void set_leds(uint8_t dev_addr, uint8_t instance);
|
||||
|
||||
@@ -1,28 +0,0 @@
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <stdarg.h>
|
||||
|
||||
char stored_string[100];
|
||||
|
||||
void clear_log()
|
||||
{
|
||||
memset(stored_string, 0, sizeof(stored_string));
|
||||
}
|
||||
|
||||
void log(const char* format, ...)
|
||||
{
|
||||
va_list args;
|
||||
va_start(args, format);
|
||||
|
||||
clear_log();
|
||||
|
||||
vsnprintf(stored_string, sizeof(stored_string), format, args);
|
||||
strcat(stored_string, "\n");
|
||||
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
const char* get_log()
|
||||
{
|
||||
return stored_string;
|
||||
}
|
||||
@@ -1,8 +0,0 @@
|
||||
#ifndef _LOG_H_
|
||||
#define _LOG_H_
|
||||
|
||||
void log(const char* format, ...);
|
||||
void clear_log();
|
||||
const char* get_log();
|
||||
|
||||
#endif // _LOG_H_
|
||||
Reference in New Issue
Block a user