1 | //************************************ bs::framework - Copyright 2018 Marko Pintera **************************************// |
2 | //*********** Licensed under the MIT license. See LICENSE.md for full terms. This notice is not to be removed. ***********// |
3 | #pragma once |
4 | |
5 | #include "BsPrerequisites.h" |
6 | #include "Input/BsInputFwd.h" |
7 | |
8 | namespace bs |
9 | { |
10 | /** @addtogroup Input-Engine |
11 | * @{ |
12 | */ |
13 | |
14 | /** |
15 | * Describes a virtual button. Virtual buttons allow you to map custom actions without needing to know about what |
16 | * physical buttons trigger those actions. |
17 | */ |
18 | struct BS_EXPORT VIRTUAL_BUTTON_DESC |
19 | { |
20 | VIRTUAL_BUTTON_DESC() = default; |
21 | |
22 | /** |
23 | * Constructs a virtual button descriptor. |
24 | * |
25 | * @param[in] buttonCode Physical button the virtual button is triggered by. |
26 | * @param[in] modifiers Modifiers required to be pressed with the physical button to trigger the virtual button. |
27 | * @param[in] repeatable If true, the virtual button events will be sent continually while the physical button |
28 | * is being held. |
29 | */ |
30 | VIRTUAL_BUTTON_DESC(ButtonCode buttonCode, ButtonModifier modifiers = ButtonModifier::None, bool repeatable = false); |
31 | |
32 | ButtonCode buttonCode = BC_0; |
33 | ButtonModifier modifiers = ButtonModifier::None; |
34 | bool repeatable = false; |
35 | }; |
36 | |
37 | /** |
38 | * Describes a virtual axis. Virtual axes allow you to map custom axes without needing to know the actual physical |
39 | * device handling those axes. |
40 | */ |
41 | struct BS_EXPORT VIRTUAL_AXIS_DESC |
42 | { |
43 | VIRTUAL_AXIS_DESC() = default; |
44 | |
45 | /** |
46 | * Constructs a new virtual axis descriptor. |
47 | * |
48 | * @param[in] type @copydoc VIRTUAL_AXIS_DESC::type |
49 | */ |
50 | VIRTUAL_AXIS_DESC(UINT32 type); |
51 | |
52 | /** Type of physical axis to map to. See InputAxis type for common types, but you are not limited to those values. */ |
53 | UINT32 type = (UINT32)InputAxis::MouseX; |
54 | |
55 | /** Value below which to ignore axis value and consider it 0. */ |
56 | float deadZone = 0.0001f; |
57 | |
58 | /** Higher sensitivity means the axis will more easily reach its maximum values. */ |
59 | float sensitivity = 1.0f; |
60 | |
61 | /** Should the axis be inverted. */ |
62 | bool invert = false; |
63 | |
64 | /** |
65 | * If enabled, axis values will be normalized to [-1, 1] range. Most axes already come in normalized form and this |
66 | * value will not affect such axes. Some axes, like mouse movement are not normalized by default and will instead |
67 | * report relative movement. By enabling this you will normalize such axes to [-1, 1] range. |
68 | */ |
69 | bool normalize = false; |
70 | }; |
71 | |
72 | /** |
73 | * Identifier for a virtual button. |
74 | * |
75 | * Primary purpose of this class is to avoid expensive string compare, and instead use a unique button identifier for |
76 | * compare. Generally you want to create one of these using the button name, and then store it for later use. |
77 | * |
78 | * @note |
79 | * This class is not thread safe and should only be used on the sim thread. |
80 | * |
81 | * @see VIRTUAL_BUTTON_DESC |
82 | */ |
83 | class BS_EXPORT VirtualButton |
84 | { |
85 | public: |
86 | VirtualButton() = default; |
87 | VirtualButton(const String& name); |
88 | |
89 | bool operator== (const VirtualButton& rhs) const |
90 | { |
91 | return (buttonIdentifier == rhs.buttonIdentifier); |
92 | } |
93 | |
94 | UINT32 buttonIdentifier = 0; |
95 | private: |
96 | /** Returns a static map of all virtual button identifiers and their buttons. */ |
97 | static Map<String, UINT32>& getUniqueButtonIds(); |
98 | |
99 | static UINT32 NextButtonId; |
100 | }; |
101 | |
102 | /** |
103 | * Identifier for a virtual axis. |
104 | * |
105 | * Primary purpose of this class is to avoid expensive string compare (axis names), and instead use a unique axis |
106 | * identifier for compare. Generally you want to create one of these using the axis name, and then store it for later |
107 | * use. |
108 | * |
109 | * @note |
110 | * This class is not thread safe and should only be used on the sim thread. |
111 | * |
112 | * @see VIRTUAL_AXIS_DESC |
113 | */ |
114 | class BS_EXPORT VirtualAxis |
115 | { |
116 | public: |
117 | VirtualAxis() = default; |
118 | VirtualAxis(const String& name); |
119 | |
120 | UINT32 axisIdentifier = 0; |
121 | |
122 | bool operator== (const VirtualAxis& rhs) const |
123 | { |
124 | return (axisIdentifier == rhs.axisIdentifier); |
125 | } |
126 | |
127 | private: |
128 | static Map<String, UINT32> UniqueAxisIds; |
129 | static UINT32 NextAxisId; |
130 | }; |
131 | |
132 | /** Contains virtual <-> physical key mappings. */ |
133 | class BS_EXPORT InputConfiguration |
134 | { |
135 | static const int MAX_NUM_DEVICES_PER_TYPE = 8; |
136 | static const int MAX_NUM_DEVICES = (UINT32)InputDevice::Count * MAX_NUM_DEVICES_PER_TYPE; |
137 | |
138 | /** Internal virtual button data container. */ |
139 | struct VirtualButtonData |
140 | { |
141 | String name; |
142 | VirtualButton button; |
143 | VIRTUAL_BUTTON_DESC desc; |
144 | }; |
145 | |
146 | /** Internal virtual axis data container. */ |
147 | struct VirtualAxisData |
148 | { |
149 | String name; |
150 | VirtualAxis axis; |
151 | VIRTUAL_AXIS_DESC desc; |
152 | }; |
153 | |
154 | /** Internal container for holding axis data for all devices. */ |
155 | struct DeviceAxisData |
156 | { |
157 | VirtualAxisData axes[(UINT32)InputAxis::Count]; |
158 | }; |
159 | |
160 | public: |
161 | InputConfiguration() = default; |
162 | |
163 | /** |
164 | * Registers a new virtual button. |
165 | * |
166 | * @param[in] name Unique name used to access the virtual button. |
167 | * @param[in] buttonCode Physical button the virtual button is triggered by. |
168 | * @param[in] modifiers Modifiers required to be pressed with the physical button to trigger the virtual button. |
169 | * @param[in] repeatable If true, the virtual button events will be sent continually while the physical button |
170 | * is being held. |
171 | */ |
172 | void registerButton(const String& name, ButtonCode buttonCode, ButtonModifier modifiers = ButtonModifier::None, bool repeatable = false); |
173 | |
174 | /** Unregisters a virtual button with the specified name. Events will no longer be generated for that button. */ |
175 | void unregisterButton(const String& name); |
176 | |
177 | /** |
178 | * Registers a new virtual axis. |
179 | * |
180 | * @param[in] name Unique name used to access the axis. |
181 | * @param[in] desc Descriptor structure containing virtual axis creation parameters. |
182 | */ |
183 | void registerAxis(const String& name, const VIRTUAL_AXIS_DESC& desc); |
184 | |
185 | /** |
186 | * Unregisters a virtual axis with the specified name. You will no longer be able to retrieve valid values for that |
187 | * axis. |
188 | */ |
189 | void unregisterAxis(const String& name); |
190 | |
191 | /** |
192 | * Sets repeat interval for held virtual buttons. Buttons will be continously triggered in interval increments as |
193 | * long as they button is being held. |
194 | */ |
195 | void setRepeatInterval(UINT64 milliseconds) { mRepeatInterval = milliseconds; } |
196 | |
197 | /** Gets the currently set repeat interval for held virtual buttons. */ |
198 | UINT64 getRepeatInterval() const { return mRepeatInterval; } |
199 | |
200 | /** @name Internal |
201 | * @{ |
202 | */ |
203 | |
204 | /** |
205 | * Returns data about virtual buttons that are triggered by the specified physical button code and modifier flags. |
206 | */ |
207 | bool _getButtons(ButtonCode code, UINT32 modifiers, Vector<VirtualButton>& btns, Vector<VIRTUAL_BUTTON_DESC>& btnDescs) const; |
208 | |
209 | /** Retrieves virtual axis descriptor for the provided axis. */ |
210 | bool _getAxis(const VirtualAxis& axis, VIRTUAL_AXIS_DESC& axisDesc) const; |
211 | |
212 | /** @} */ |
213 | |
214 | private: |
215 | Vector<VirtualButtonData> mButtons[BC_Count]; |
216 | Vector<VirtualAxisData> mAxes; |
217 | |
218 | UINT64 mRepeatInterval = 300; |
219 | }; |
220 | |
221 | /** @} */ |
222 | } |