forked from chromium/chromium
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathgamepad_provider.h
174 lines (132 loc) · 6.01 KB
/
gamepad_provider.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
// Copyright (c) 2012 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef DEVICE_GAMEPAD_GAMEPAD_PROVIDER_H_
#define DEVICE_GAMEPAD_GAMEPAD_PROVIDER_H_
#include <memory>
#include <utility>
#include <vector>
#include "base/callback_forward.h"
#include "base/macros.h"
#include "base/memory/ref_counted.h"
#include "base/memory/shared_memory.h"
#include "base/synchronization/lock.h"
#include "base/system_monitor/system_monitor.h"
#include "device/gamepad/gamepad_export.h"
#include "device/gamepad/gamepad_pad_state_provider.h"
#include "device/gamepad/gamepad_shared_buffer.h"
#include "device/gamepad/public/cpp/gamepads.h"
#include "device/gamepad/public/interfaces/gamepad.mojom.h"
#include "mojo/public/cpp/system/buffer.h"
namespace base {
class SingleThreadTaskRunner;
class Thread;
}
namespace device {
class GamepadDataFetcher;
class DEVICE_GAMEPAD_EXPORT GamepadConnectionChangeClient {
public:
virtual void OnGamepadConnectionChange(bool connected,
int index,
const Gamepad& pad) = 0;
};
class DEVICE_GAMEPAD_EXPORT GamepadProvider
: public GamepadPadStateProvider,
public base::SystemMonitor::DevicesChangedObserver {
public:
explicit GamepadProvider(
GamepadConnectionChangeClient* connection_change_client);
// Manually specifies the data fetcher. Used for testing.
explicit GamepadProvider(
GamepadConnectionChangeClient* connection_change_client,
std::unique_ptr<GamepadDataFetcher> fetcher);
~GamepadProvider() override;
// Returns a duplicate of the shared memory handle of the gamepad data.
base::SharedMemoryHandle DuplicateSharedMemoryHandle();
// Returns a new mojo::ScopedSharedBufferHandle of the gamepad data.
mojo::ScopedSharedBufferHandle GetSharedBufferHandle();
void GetCurrentGamepadData(Gamepads* data);
void PlayVibrationEffectOnce(
int pad_index,
mojom::GamepadHapticEffectType,
mojom::GamepadEffectParametersPtr,
mojom::GamepadHapticsManager::PlayVibrationEffectOnceCallback);
void ResetVibrationActuator(
int pad_index,
mojom::GamepadHapticsManager::ResetVibrationActuatorCallback);
// Pause and resume the background polling thread. Can be called from any
// thread.
void Pause();
void Resume();
// Registers the given closure for calling when the user has interacted with
// the device. This callback will only be issued once.
void RegisterForUserGesture(const base::Closure& closure);
// base::SystemMonitor::DevicesChangedObserver implementation.
void OnDevicesChanged(base::SystemMonitor::DeviceType type) override;
// Add a gamepad data fetcher. Takes ownership of |fetcher|.
void AddGamepadDataFetcher(std::unique_ptr<GamepadDataFetcher> fetcher);
// Remove gamepad data fetchers with the given source.
void RemoveSourceGamepadDataFetcher(GamepadSource source);
void SetSanitizationEnabled(bool sanitize) { sanitize_ = sanitize; }
private:
void Initialize(std::unique_ptr<GamepadDataFetcher> fetcher);
// Method for setting up the platform-specific data fetcher. Takes ownership
// of |fetcher|.
void DoAddGamepadDataFetcher(std::unique_ptr<GamepadDataFetcher> fetcher);
void DoRemoveSourceGamepadDataFetcher(GamepadSource source);
GamepadDataFetcher* GetSourceGamepadDataFetcher(GamepadSource source);
// Method for sending pause hints to the low-level data fetcher. Runs on
// polling_thread_.
void SendPauseHint(bool paused);
// Method for polling a GamepadDataFetcher. Runs on the polling_thread_.
void DoPoll();
void ScheduleDoPoll();
void OnGamepadConnectionChange(bool connected, int index, const Gamepad& pad);
// Checks the gamepad state to see if the user has interacted with it.
void CheckForUserGesture();
enum { kDesiredSamplingIntervalMs = 16 };
// Keeps track of when the background thread is paused. Access to is_paused_
// must be guarded by is_paused_lock_.
base::Lock is_paused_lock_;
bool is_paused_;
// Keep track of when a polling task is schedlued, so as to prevent us from
// accidentally scheduling more than one at any time, when rapidly toggling
// |is_paused_|.
bool have_scheduled_do_poll_;
// Lists all observers registered for user gestures, and the thread which
// to issue the callbacks on. Since we always issue the callback on the
// thread which the registration happened, and this class lives on the I/O
// thread, the message loop proxies will normally just be the I/O thread.
// However, this will be the main thread for unit testing.
base::Lock user_gesture_lock_;
struct ClosureAndThread {
ClosureAndThread(const base::Closure& c,
const scoped_refptr<base::SingleThreadTaskRunner>& m);
ClosureAndThread(const ClosureAndThread& other);
~ClosureAndThread();
base::Closure closure;
scoped_refptr<base::SingleThreadTaskRunner> task_runner;
};
using UserGestureObserverVector = std::vector<ClosureAndThread>;
UserGestureObserverVector user_gesture_observers_;
// Updated based on notification from SystemMonitor when the system devices
// have been updated, and this notification is passed on to the data fetcher
// to enable it to avoid redundant (and possibly expensive) is-connected
// tests. Access to devices_changed_ must be guarded by
// devices_changed_lock_.
base::Lock devices_changed_lock_;
bool devices_changed_;
bool ever_had_user_gesture_;
bool sanitize_;
// Only used on the polling thread.
using GamepadFetcherVector = std::vector<std::unique_ptr<GamepadDataFetcher>>;
GamepadFetcherVector data_fetchers_;
base::Lock shared_memory_lock_;
std::unique_ptr<GamepadSharedBuffer> gamepad_shared_buffer_;
// Polling is done on this background thread.
std::unique_ptr<base::Thread> polling_thread_;
GamepadConnectionChangeClient* connection_change_client_;
DISALLOW_COPY_AND_ASSIGN(GamepadProvider);
};
} // namespace device
#endif // DEVICE_GAMEPAD_GAMEPAD_PROVIDER_H_