OXYGENHUB
◆ main enhanced-x16-emulator / src / joystick.h
3.4 KiB · Objective-C · last changed chore(): initial commit 25 days ago source blame history raw
9120e874 Andy McCall 1
#pragma once
2
#ifndef JOYSTICK_H
3
#define JOYSTICK_H
4
5
#include <stdint.h>
6
#include <stdbool.h>
7
8
#ifdef __cplusplus
9
extern "C" {
10
#endif
11
12
#define JOY_LATCH_MASK 0x04
13
#define JOY_CLK_MASK 0x08
14
15
#define NUM_JOYSTICKS 4
16
17
// ─── Button bit layout (button_mask, 16 bits, 0=pressed) ────────────────────
18
// Derived from the button_map[] table in joystick.c. The ImGui panel uses
19
// these defines to label each bit in the mask display.
20
#define JOY_BIT_A             (1 << 0)   // A button
21
#define JOY_BIT_X             (1 << 1)   // X button
22
#define JOY_BIT_SELECT        (1 << 2)   // Back / Select
23
#define JOY_BIT_START         (1 << 3)   // Start
24
#define JOY_BIT_DPAD_UP       (1 << 4)   // D-Pad Up
25
#define JOY_BIT_DPAD_DOWN     (1 << 5)   // D-Pad Down
26
#define JOY_BIT_DPAD_LEFT     (1 << 6)   // D-Pad Left
27
#define JOY_BIT_DPAD_RIGHT    (1 << 7)   // D-Pad Right
28
#define JOY_BIT_B             (1 << 8)   // B button
29
#define JOY_BIT_Y             (1 << 9)   // Y button
30
#define JOY_BIT_LEFT_SHOULDER (1 << 10)  // Left shoulder / L
31
#define JOY_BIT_RIGHT_SHOULDER (1 << 11) // Right shoulder / R
32
// Bits 12-15 are forced to 1 when the latch is loaded (0xF000 mask applied).
33
34
extern uint8_t Joystick_data;
35
extern bool Joystick_slots_enabled[NUM_JOYSTICKS];
36
37
bool joystick_init(void); //initialize SDL controllers
38
void joystick_add(int index);
39
void joystick_remove(int index);
40
41
void joystick_button_down(int instance_id, uint8_t button);
42
void joystick_button_up(int instance_id, uint8_t button);
43
44
void joystick_set_latch(bool value);
45
void joystick_set_clock(bool value);
46
47
// ─── Virtual joysticks ───────────────────────────────────────────────────────
48
// A synthetic input source that needs no SDL controller, so automation (the DAP
49
// x16/joystick request) can drive the SNES ports on a headless machine with no
50
// gamepad attached. While a slot's virtual joystick is active it overrides any
51
// physical controller bound to that slot; clearing it hands the slot back.
52
//
53
// mask is the same active-low layout as the debug snapshot's button_mask: a 0
54
// bit means pressed. See JOY_BIT_* above. Bits 12-15 are ignored -- the latch
55
// forces them to 1, as the hardware does.
56
57
void joystick_set_virtual(int slot, uint16_t button_mask);
58
void joystick_clear_virtual(int slot);
59
bool joystick_virtual_active(int slot);
60
61
// ─── Debugger accessor ───────────────────────────────────────────────────────
62
// Side-effect-free snapshot of joystick state. Safe to call every frame from
63
// the debugger while the emulation is running.
64
65
typedef struct {
66
	bool     enabled;          // slot is enabled (Joystick_slots_enabled[i])
67
	bool     controller_bound; // a real SDL controller is mapped to this slot
68
	bool     virtual_active;   // a virtual joystick is driving this slot
69
	uint16_t button_mask;      // current button state (0=pressed, see JOY_BIT_*)
70
	uint16_t shift_mask;       // current shift register value being clocked out
71
} joystick_slot_debug_t;
72
73
typedef struct {
74
	joystick_slot_debug_t slots[NUM_JOYSTICKS];
75
	bool    latch;             // current latch line state
76
	uint8_t data;              // current Joystick_data byte
77
} joystick_debug_state_t;
78
79
void joystick_debug_get_state(joystick_debug_state_t *out);
80
81
#ifdef __cplusplus
82
}
83
#endif
84
85
#endif