]> Shamusworld >> Repos - virtualjaguar/blob - src/gui/gamepad.cpp
More gamepad work.
[virtualjaguar] / src / gui / gamepad.cpp
1 //
2 // gamepad.cpp - Host joystick handling (using SDL)
3 //
4 // by James Hammons
5 // (C) 2013 Underground Software
6 //
7 // JLH = James Hammons <jlhamm@acm.org>
8 //
9 // Who  When        What
10 // ---  ----------  -------------------------------------------------------------
11 // JLH  01/05/2013  Created this file
12 //
13
14 #include "gamepad.h"
15 #include "log.h"
16
17
18 // Class member initialization
19 /*static*/ int Gamepad::numJoysticks = 0;
20 /*static*/ SDL_Joystick * Gamepad::pad[8];
21 /*static*/ int Gamepad::numButtons[8];
22 /*static*/ int Gamepad::numHats[8];
23 /*static*/ bool Gamepad::button[8][256];
24 /*static*/ uint8_t Gamepad::hat[8][32];
25
26
27 Gamepad::Gamepad(void)//: numJoysticks(0)
28 {
29         AllocateJoysticks();
30 }
31
32
33 Gamepad::~Gamepad(void)
34 {
35         DeallocateJoysticks();
36 }
37
38
39 void Gamepad::AllocateJoysticks(void)
40 {
41 //      DeallocateJoysticks();
42         numJoysticks = SDL_NumJoysticks();
43
44         // Sanity check
45         if (numJoysticks > 8)
46                 numJoysticks = 8;
47
48         for(int i=0; i<numJoysticks; i++)
49         {
50                 pad[i] = SDL_JoystickOpen(i);
51                 numButtons[i] = numHats[i] = 0;
52
53                 if (pad[i])
54                 {
55                         numButtons[i] = SDL_JoystickNumButtons(pad[i]);
56                         numHats[i] = SDL_JoystickNumHats(pad[i]);
57                 }
58         }
59
60         WriteLog("Gamepad: Found %u joystick%s.\n", numJoysticks, (numJoysticks == 1 ? "" : "s"));
61 }
62
63
64 void Gamepad::DeallocateJoysticks(void)
65 {
66         for(int i=0; i<numJoysticks; i++)
67                 SDL_JoystickClose(pad[i]);
68 }
69
70
71 bool Gamepad::GetState(int joystickID, int buttonID)
72 {
73         uint8_t hatMask[8] = { 1, 2, 4, 8, 16, 32, 64, 128 };
74
75         if (buttonID & JOY_BUTTON)
76         {
77                 // Handle SDL button
78                 int buttonNum = (buttonID & JOY_BUTTON_MASK);
79 //              SDL_JoystickGetButton(pad[joystickID]);
80                 return button[joystickID][buttonNum];
81         }
82         else if (buttonID & JOY_HAT)
83         {
84                 // Handle SDL hats
85                 int hatNumber = (buttonID & JOY_HATNUM_MASK) >> 3;
86                 uint8_t hatDirection = hatMask[buttonID & JOY_HATBUT_MASK];
87 //              uint8 direction = SDL_JoystickGetHat(pad[joystickID], hatNumber);
88 //              return (
89                 return (hat[joystickID][hatNumber] & hatDirection ? true : false);
90         }
91
92         // Default == failure
93         return false;
94 }
95
96
97 int Gamepad::CheckButtonPressed(void)
98 {
99         // This translates the hat direction to a mask index.
100         int hatNum[16] = { -1, 0, 1, -1, 2, -1, -1, -1,
101                 3, -1, -1, -1, -1, -1, -1, -1 };
102
103         // Return single button ID being pressed (if any)
104         for(int i=0; i<numJoysticks; i++)
105         {
106                 for(int j=0; j<numButtons[i]; j++)
107                 {
108                         if (button[i][j])
109                                 return (JOY_BUTTON | j);
110                 }
111
112                 for(int j=0; j<numHats[i]; j++)
113                 {
114                         if (hat[i][j])
115                                 return (JOY_HAT | hatNum[hat[i][j]]);
116                 }
117         }
118
119         return -1;
120 }
121
122
123 int Gamepad::GetButtonID(void)
124 {
125         // Return single button ID being pressed (if any)
126         return -1;
127 }
128
129
130 int Gamepad::GetJoystickID(void)
131 {
132         // Return joystick ID of button being pressed (if any)
133         return -1;
134 }
135
136
137 void Gamepad::Update(void)
138 {
139 //      SDL_PollEvent(&event);
140         SDL_JoystickUpdate();
141
142         for(int i=0; i<numJoysticks; i++)
143         {
144                 for(int j=0; j<numButtons[i]; j++)
145                         button[i][j] = SDL_JoystickGetButton(pad[i], j);
146
147                 for(int j=0; j<numHats[i]; j++)
148                         hat[i][j] = SDL_JoystickGetHat(pad[i], j);
149         }
150 }
151
152
153 #if 0
154 // Need to test this. It may be that the only time joysticks are detected is
155 // when the program is first run. That would suck.
156 void Gamepad::CheckConsistency(void)
157 {
158         int currentNumJoysticks = SDL_NumJoysticks();
159
160         // Check to see if the # of joysticks reported by SDL changed
161         if (currentNumJoysticks == numJoysticks)
162                 return;
163
164         // Either one or more joysticks were plugged in, or removed. Fix up our
165         // internal states to reflect this.
166
167         
168 }
169 #endif
170