Skip to content

Commit c8a5023

Browse files
authored
GamePad/Keyboard/Mouse updated for GameInput v3 (#353)
1 parent 019d900 commit c8a5023

File tree

6 files changed

+126
-30
lines changed

6 files changed

+126
-30
lines changed

Inc/GamePad.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@
2828

2929
#ifdef USING_GAMEINPUT
3030
#include <GameInput.h>
31-
#if !defined(_GAMING_XBOX) && defined(_MSC_VER)
31+
#if defined(_MSC_VER) && (defined(_GAMING_XBOX) || defined(GAMEINPUT_API_VERSION))
3232
#pragma comment(lib,"gameinput.lib")
3333
#endif
3434

@@ -335,6 +335,8 @@ namespace DirectX
335335
using GameInputDevice_t = GameInput::v1::IGameInputDevice;
336336
#elif defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 2)
337337
using GameInputDevice_t = GameInput::v2::IGameInputDevice;
338+
#elif defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 3)
339+
using GameInputDevice_t = GameInput::v3::IGameInputDevice;
338340
#else
339341
using GameInputDevice_t = ::IGameInputDevice;
340342
#endif

Inc/Keyboard.h

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,12 @@
2424

2525
#endif // !USING_XINPUT && !USING_GAMEINPUT && !USING_WINDOWS_GAMING_INPUT
2626

27-
#if defined(USING_GAMEINPUT) && !defined(_GAMING_XBOX) && defined(_MSC_VER)
27+
#ifdef USING_GAMEINPUT
28+
#include <GameInput.h>
29+
#if defined(_MSC_VER) && (defined(_GAMING_XBOX) || defined(GAMEINPUT_API_VERSION))
2830
#pragma comment(lib,"gameinput.lib")
2931
#endif
32+
#endif
3033

3134
#include <cstdint>
3235
#include <memory>

Inc/Mouse.h

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,12 @@
2424

2525
#endif // !USING_XINPUT && !USING_GAMEINPUT && !USING_WINDOWS_GAMING_INPUT
2626

27-
#if defined(USING_GAMEINPUT) && !defined(_GAMING_XBOX) && defined(_MSC_VER)
27+
#ifdef USING_GAMEINPUT
28+
#include <GameInput.h>
29+
#if defined(_MSC_VER) && (defined(_GAMING_XBOX) || defined(GAMEINPUT_API_VERSION))
2830
#pragma comment(lib,"gameinput.lib")
2931
#endif
32+
#endif
3033

3134
#include <cstdint>
3235
#include <memory>

Src/GamePad.cpp

Lines changed: 39 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -84,15 +84,19 @@ namespace
8484
#pragma region Implementations
8585
#ifdef USING_GAMEINPUT
8686

87+
//======================================================================================
88+
// GameInput
89+
//======================================================================================
90+
8791
#if defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 1)
8892
using namespace GameInput::v1;
8993
#elif defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 2)
9094
using namespace GameInput::v2;
95+
#elif defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 3)
96+
using namespace GameInput::v3;
9197
#endif
9298

93-
//======================================================================================
94-
// GameInput
95-
//======================================================================================
99+
using GameInputCreateFn = HRESULT(*)(IGameInput**);
96100

97101
class GamePad::Impl
98102
{
@@ -110,7 +114,26 @@ class GamePad::Impl
110114

111115
s_gamePad = this;
112116

117+
#if defined(_GAMING_XBOX) || defined(GAMEINPUT_API_VERSION)
113118
HRESULT hr = GameInputCreate(mGameInput.GetAddressOf());
119+
#else
120+
if (!s_gameInputCreate)
121+
{
122+
s_gameInputModule = LoadLibraryExW(L"GameInput.dll", nullptr, LOAD_LIBRARY_SEARCH_SYSTEM32);
123+
if (s_gameInputModule)
124+
{
125+
s_gameInputCreate = reinterpret_cast<GameInputCreateFn>(static_cast<void*>(GetProcAddress(s_gameInputModule, "GameInputCreate")));
126+
}
127+
128+
if (!s_gameInputCreate)
129+
{
130+
DebugTrace("ERROR: GetProcAddress GameInputCreate failed\n");
131+
throw std::runtime_error("GameInput.dll is not installed on this system");
132+
}
133+
}
134+
135+
HRESULT hr = s_gameInputCreate(mGameInput.GetAddressOf());
136+
#endif
114137
if (SUCCEEDED(hr))
115138
{
116139
ThrowIfFailed(mGameInput->RegisterDeviceCallback(
@@ -126,10 +149,10 @@ class GamePad::Impl
126149
{
127150
DebugTrace("ERROR: GameInputCreate [gamepad] failed with %08X\n", static_cast<unsigned int>(hr));
128151
#ifdef _GAMING_XBOX
129-
ThrowIfFailed(hr);
130-
#elif defined(_DEBUG)
152+
throw com_exception(hr);
153+
#else
131154
DebugTrace(
132-
"\t**** Check that the 'GameInput Service' is running on this system. ****\n"
155+
"\t**** Install the latest GameInputRedist package on this system. ****\n"
133156
"\t**** NOTE: All calls to GetState will be reported as 'not connected'. ****\n");
134157
#endif
135158
}
@@ -417,10 +440,20 @@ class GamePad::Impl
417440
SetEvent(impl->mCtrlChanged);
418441
}
419442
}
443+
444+
#if !defined(_GAMING_XBOX) && !defined(GAMEINPUT_API_VERSION)
445+
static HMODULE s_gameInputModule;
446+
static GameInputCreateFn s_gameInputCreate;
447+
#endif
420448
};
421449

422450
GamePad::Impl* GamePad::Impl::s_gamePad = nullptr;
423451

452+
#if !defined(_GAMING_XBOX) && !defined(GAMEINPUT_API_VERSION)
453+
HMODULE GamePad::Impl::s_gameInputModule = nullptr;
454+
GameInputCreateFn GamePad::Impl::s_gameInputCreate = nullptr;
455+
#endif
456+
424457
void GamePad::RegisterEvents(HANDLE ctrlChanged) noexcept
425458
{
426459
pImpl->mCtrlChanged = (!ctrlChanged) ? INVALID_HANDLE_VALUE : ctrlChanged;

Src/Keyboard.cpp

Lines changed: 38 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -51,18 +51,19 @@ namespace
5151
#pragma region Implementations
5252
#ifdef USING_GAMEINPUT
5353

54-
#include <GameInput.h>
54+
//======================================================================================
55+
// GameInput
56+
//======================================================================================
5557

5658
#if defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 1)
5759
using namespace GameInput::v1;
5860
#elif defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 2)
5961
using namespace GameInput::v2;
62+
#elif defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 3)
63+
using namespace GameInput::v3;
6064
#endif
6165

62-
63-
//======================================================================================
64-
// GameInput
65-
//======================================================================================
66+
using GameInputCreateFn = HRESULT(*)(IGameInput**);
6667

6768
class Keyboard::Impl
6869
{
@@ -80,7 +81,26 @@ class Keyboard::Impl
8081

8182
s_keyboard = this;
8283

84+
#if defined(_GAMING_XBOX) || defined(GAMEINPUT_API_VERSION)
8385
HRESULT hr = GameInputCreate(mGameInput.GetAddressOf());
86+
#else
87+
if (!s_gameInputCreate)
88+
{
89+
s_gameInputModule = LoadLibraryExW(L"GameInput.dll", nullptr, LOAD_LIBRARY_SEARCH_SYSTEM32);
90+
if (s_gameInputModule)
91+
{
92+
s_gameInputCreate = reinterpret_cast<GameInputCreateFn>(static_cast<void*>(GetProcAddress(s_gameInputModule, "GameInputCreate")));
93+
}
94+
95+
if (!s_gameInputCreate)
96+
{
97+
DebugTrace("ERROR: GetProcAddress GameInputCreate failed\n");
98+
throw std::runtime_error("GameInput.dll is not installed on this system");
99+
}
100+
}
101+
102+
HRESULT hr = s_gameInputCreate(mGameInput.GetAddressOf());
103+
#endif
84104
if (SUCCEEDED(hr))
85105
{
86106
ThrowIfFailed(mGameInput->RegisterDeviceCallback(
@@ -96,12 +116,11 @@ class Keyboard::Impl
96116
{
97117
DebugTrace("ERROR: GameInputCreate [keyboard] failed with %08X\n", static_cast<unsigned int>(hr));
98118
#ifdef _GAMING_XBOX
99-
ThrowIfFailed(hr);
100-
#elif defined(_DEBUG)
119+
throw com_exception(hr);
120+
#else
101121
DebugTrace(
102-
"\t**** Check that the 'GameInput Service' is running on this system. ****\n"
103-
"\t**** NOTE: No keys will be returned and IsConnected will return false. ****\n"
104-
);
122+
"\t**** Install the latest GameInputRedist package on this system. ****\n"
123+
"\t**** NOTE: All calls to GetState will be reported as 'not connected'. ****\n");
105124
#endif
106125
}
107126
}
@@ -208,11 +227,19 @@ class Keyboard::Impl
208227
--impl->mConnected;
209228
}
210229
}
211-
};
212230

231+
#if !defined(_GAMING_XBOX) && !defined(GAMEINPUT_API_VERSION)
232+
static HMODULE s_gameInputModule;
233+
static GameInputCreateFn s_gameInputCreate;
234+
#endif
235+
};
213236

214237
Keyboard::Impl* Keyboard::Impl::s_keyboard = nullptr;
215238

239+
#if !defined(_GAMING_XBOX) && !defined(GAMEINPUT_API_VERSION)
240+
HMODULE Keyboard::Impl::s_gameInputModule = nullptr;
241+
GameInputCreateFn Keyboard::Impl::s_gameInputCreate = nullptr;
242+
#endif
216243

217244
void Keyboard::ProcessMessage(UINT, WPARAM, LPARAM) noexcept
218245
{

Src/Mouse.cpp

Lines changed: 38 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -19,17 +19,19 @@ using Microsoft::WRL::ComPtr;
1919
#pragma region Implementations
2020
#ifdef USING_GAMEINPUT
2121

22-
#include <GameInput.h>
22+
//======================================================================================
23+
// Win32 + GameInput implementation
24+
//======================================================================================
2325

2426
#if defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 1)
2527
using namespace GameInput::v1;
2628
#elif defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 2)
2729
using namespace GameInput::v2;
30+
#elif defined(GAMEINPUT_API_VERSION) && (GAMEINPUT_API_VERSION == 3)
31+
using namespace GameInput::v3;
2832
#endif
2933

30-
//======================================================================================
31-
// Win32 + GameInput implementation
32-
//======================================================================================
34+
using GameInputCreateFn = HRESULT(*)(IGameInput**);
3335

3436
//
3537
// Call this static function from your Window Message Procedure
@@ -83,7 +85,26 @@ class Mouse::Impl
8385

8486
s_mouse = this;
8587

88+
#if defined(_GAMING_XBOX) || defined(GAMEINPUT_API_VERSION)
8689
HRESULT hr = GameInputCreate(mGameInput.GetAddressOf());
90+
#else
91+
if (!s_gameInputCreate)
92+
{
93+
s_gameInputModule = LoadLibraryExW(L"GameInput.dll", nullptr, LOAD_LIBRARY_SEARCH_SYSTEM32);
94+
if (s_gameInputModule)
95+
{
96+
s_gameInputCreate = reinterpret_cast<GameInputCreateFn>(static_cast<void*>(GetProcAddress(s_gameInputModule, "GameInputCreate")));
97+
}
98+
99+
if (!s_gameInputCreate)
100+
{
101+
DebugTrace("ERROR: GetProcAddress GameInputCreate failed\n");
102+
throw std::runtime_error("GameInput.dll is not installed on this system");
103+
}
104+
}
105+
106+
HRESULT hr = s_gameInputCreate(mGameInput.GetAddressOf());
107+
#endif
87108
if (SUCCEEDED(hr))
88109
{
89110
ThrowIfFailed(mGameInput->RegisterDeviceCallback(
@@ -99,12 +120,11 @@ class Mouse::Impl
99120
{
100121
DebugTrace("ERROR: GameInputCreate [mouse] failed with %08X\n", static_cast<unsigned int>(hr));
101122
#ifdef _GAMING_XBOX
102-
ThrowIfFailed(hr);
103-
#elif defined(_DEBUG)
123+
throw com_exception(hr);
124+
#else
104125
DebugTrace(
105-
"\t**** Check that the 'GameInput Service' is running on this system. ****\n"
106-
"\t**** NOTE: No relative movement be returned and IsConnected will return false. ****\n"
107-
);
126+
"\t**** Install the latest GameInputRedist package on this system. ****\n"
127+
"\t**** NOTE: All calls to GetState will be reported as 'not connected'. ****\n");
108128
#endif
109129
}
110130

@@ -367,12 +387,20 @@ class Mouse::Impl
367387
ClipCursor(&rect);
368388
#endif
369389
}
390+
391+
#if !defined(_GAMING_XBOX) && !defined(GAMEINPUT_API_VERSION)
392+
static HMODULE s_gameInputModule;
393+
static GameInputCreateFn s_gameInputCreate;
394+
#endif
370395
};
371396

397+
#if !defined(_GAMING_XBOX) && !defined(GAMEINPUT_API_VERSION)
398+
HMODULE Mouse::Impl::s_gameInputModule = nullptr;
399+
GameInputCreateFn Mouse::Impl::s_gameInputCreate = nullptr;
400+
#endif
372401

373402
Mouse::Impl* Mouse::Impl::s_mouse = nullptr;
374403

375-
376404
void Mouse::ProcessMessage(UINT message, WPARAM wParam, LPARAM lParam)
377405
{
378406
auto pImpl = Impl::s_mouse;

0 commit comments

Comments
 (0)