pixijs-input-devices 0.5.8 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +155 -161
- package/dist/index.cjs +1 -1
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +92 -86
- package/dist/index.mjs +1 -1
- package/dist/index.mjs.map +1 -1
- package/package.json +9 -12
package/README.md
CHANGED
|
@@ -4,10 +4,10 @@
|
|
|
4
4
|
|
|
5
5
|
| | |
|
|
6
6
|
| ------ | ------ |
|
|
7
|
-
| 🎮
|
|
8
|
-
| ⚡
|
|
9
|
-
| 🔮 Highly configurable |
|
|
10
|
-
| ✅ Cross-platform & mobile-friendly <sup>[[1]](https://caniuse.com/mdn-api_keyboardlayoutmap) [[2]](https://caniuse.com/mdn-api_gamepad_vibrationactuator) [[3]](https://chromestatus.com/feature/5989275208253440)</sup> |
|
|
7
|
+
| 🎮 Handle [keyboard](#keyboarddevice), [gamepads](#gamepaddevice), and [more](#custom-devices)! | 🚀 [Real-time](#real-time) & [event-driven](#keyboarddevice-events) APIs |
|
|
8
|
+
| ⚡ Highly-optimized for [performance](https://web.dev/articles/inp) | 🧭 Built-in [UI navigation](#uinavigation-api) |
|
|
9
|
+
| 🔮 Highly configurable (with sensible defaults) | 🪄 Supports [input binding](#named-binds) |
|
|
10
|
+
| ✅ Cross-platform & mobile-friendly <sup>[[1]](https://caniuse.com/mdn-api_keyboardlayoutmap) [[2]](https://caniuse.com/mdn-api_gamepad_vibrationactuator) [[3]](https://chromestatus.com/feature/5989275208253440)</sup> | 🌐 Automatic [Intl layouts](#keyboard-layout---detection) detection |
|
|
11
11
|
| 🍃 Zero dependencies & tree-shakeable | ✨ Supports PixiJS v8, v7, v6.3+ |
|
|
12
12
|
|
|
13
13
|
|
|
@@ -16,29 +16,28 @@
|
|
|
16
16
|
*Handle device inputs with ease.*
|
|
17
17
|
|
|
18
18
|
```ts
|
|
19
|
-
import { InputDevice, GamepadDevice } from "pixijs-input-devices"
|
|
19
|
+
import { InputDevice, GamepadDevice } from "pixijs-input-devices"
|
|
20
20
|
|
|
21
21
|
|
|
22
22
|
// Set named binds
|
|
23
|
-
KeyboardDevice.global.configureBinds({
|
|
24
|
-
jump: [ "Space" ]
|
|
25
|
-
})
|
|
26
|
-
|
|
27
23
|
GamepadDevice.configureDefaultBinds({
|
|
28
|
-
jump: [ "
|
|
24
|
+
jump: [ "Face1" ]
|
|
25
|
+
})
|
|
26
|
+
InputDevice.keyboard.configureBinds({
|
|
27
|
+
jump: [ "ArrowUp", "Space" ]
|
|
29
28
|
})
|
|
30
29
|
|
|
31
30
|
// Use binds
|
|
32
|
-
for (
|
|
33
|
-
if (
|
|
31
|
+
for (const device of InputDevice.devices) {
|
|
32
|
+
if (device.bindDown("jump")) // ...
|
|
34
33
|
}
|
|
35
34
|
|
|
36
35
|
// Event-driven
|
|
37
|
-
InputDevice.
|
|
38
|
-
if (
|
|
36
|
+
InputDevice.onBindDown("jump", ({ device }) => {
|
|
37
|
+
if (device.type === "gamepad") {
|
|
39
38
|
device.playVibration({ duration: 50 })
|
|
40
39
|
}
|
|
41
|
-
})
|
|
40
|
+
})
|
|
42
41
|
```
|
|
43
42
|
|
|
44
43
|
## Getting Started with PixiJS Input Devices
|
|
@@ -76,10 +75,11 @@ yarn add pixijs-input-devices --dev
|
|
|
76
75
|
**2.** Register the update loop:
|
|
77
76
|
|
|
78
77
|
```ts
|
|
79
|
-
import { Ticker } from 'pixi.js'
|
|
80
|
-
import { InputDevice } from 'pixijs-input-devices'
|
|
78
|
+
import { Ticker } from 'pixi.js'
|
|
79
|
+
import { InputDevice } from 'pixijs-input-devices'
|
|
81
80
|
|
|
82
|
-
|
|
81
|
+
|
|
82
|
+
Ticker.shared.add(() => InputDevice.update())
|
|
83
83
|
```
|
|
84
84
|
|
|
85
85
|
> [!TIP]
|
|
@@ -88,14 +88,15 @@ Ticker.shared.add(ticker => InputDevice.update());
|
|
|
88
88
|
**3.** (Optional) enable the UINavigation API
|
|
89
89
|
|
|
90
90
|
```ts
|
|
91
|
-
import * as PIXI from 'pixi.js'
|
|
92
|
-
import { UINavigation, registerPixiJSNavigationMixin } from 'pixijs-input-devices'
|
|
91
|
+
import * as PIXI from 'pixi.js'
|
|
92
|
+
import { UINavigation, registerPixiJSNavigationMixin } from 'pixijs-input-devices'
|
|
93
|
+
|
|
93
94
|
|
|
94
95
|
const app = new PIXI.Application(/*…*/)
|
|
95
96
|
|
|
96
97
|
// enable the navigation API
|
|
97
|
-
UINavigation.configureWithRoot(
|
|
98
|
-
registerPixiJSNavigationMixin(
|
|
98
|
+
UINavigation.configureWithRoot(app.stage)
|
|
99
|
+
registerPixiJSNavigationMixin(PIXI.Container)
|
|
99
100
|
```
|
|
100
101
|
|
|
101
102
|
✨ You are now ready to use inputs!
|
|
@@ -108,46 +109,65 @@ The `InputDevice` singleton controls all device discovery.
|
|
|
108
109
|
|
|
109
110
|
```ts
|
|
110
111
|
InputDevice.keyboard // KeyboardDevice
|
|
111
|
-
InputDevice.gamepads //
|
|
112
|
-
InputDevice.custom //
|
|
112
|
+
InputDevice.gamepads // GamepadDevice[]
|
|
113
|
+
InputDevice.custom // Device[]
|
|
113
114
|
```
|
|
114
115
|
|
|
115
116
|
You can access all **active/connected** devices using `.devices`:
|
|
116
117
|
|
|
117
118
|
```ts
|
|
118
|
-
for (
|
|
119
|
+
for (const device of InputDevice.devices) { // …
|
|
119
120
|
```
|
|
120
121
|
|
|
121
122
|
#### InputDevice - properties
|
|
122
123
|
|
|
124
|
+
The `InputDevice` manager provides the following **context capability** properties:
|
|
125
|
+
|
|
123
126
|
| Property | Type | Description |
|
|
124
127
|
|---|---|---|
|
|
125
|
-
| `InputDevice.
|
|
126
|
-
| `InputDevice.
|
|
128
|
+
| `InputDevice.hasMouseLikePointer` | `boolean` | Whether the context has a mouse/trackpad. |
|
|
129
|
+
| `InputDevice.isMobile` | `boolean` | Whether the context is mobile capable. |
|
|
130
|
+
| `InputDevice.isTouchCapable` | `boolean` | Whether the context is touchscreen capable. |
|
|
131
|
+
|
|
132
|
+
As well as shortcuts to **connected devices**:
|
|
133
|
+
|
|
134
|
+
| Accessor | Type | Description |
|
|
135
|
+
|---|---|---|
|
|
127
136
|
| `InputDevice.lastInteractedDevice` | `Device?` | The most recently interacted device (or first if multiple). |
|
|
128
137
|
| `InputDevice.devices` | `Device[]` | All active, connected devices. |
|
|
129
138
|
| `InputDevice.keyboard` | `KeyboardDevice` | The global keyboard. |
|
|
130
139
|
| `InputDevice.gamepads` | `GamepadDevice[]` | Connected gamepads. |
|
|
131
|
-
| `InputDevice.custom` | `CustomDevice[]` |
|
|
140
|
+
| `InputDevice.custom` | `CustomDevice[]` | Any custom devices. |
|
|
132
141
|
|
|
133
142
|
#### InputDevice - on() Events
|
|
134
143
|
|
|
135
144
|
Access global events directly through the manager:
|
|
136
145
|
|
|
137
146
|
```ts
|
|
138
|
-
InputDevice.on(
|
|
139
|
-
//
|
|
147
|
+
InputDevice.on("deviceadded", ({ device }) => {
|
|
148
|
+
// new device was connected or became available
|
|
140
149
|
// do additional setup here, show a dialog, etc.
|
|
141
150
|
})
|
|
142
151
|
|
|
143
|
-
InputDevice.off(
|
|
152
|
+
InputDevice.off("deviceadded") // stop listening
|
|
144
153
|
```
|
|
145
154
|
|
|
146
155
|
| Event | Description | Payload |
|
|
147
156
|
|---|---|---|
|
|
148
157
|
| `"deviceadded"` | `{device}` | A device has been added. |
|
|
149
158
|
| `"deviceremoved"` | `{device}` | A device has been removed. |
|
|
159
|
+
| `"lastdevicechanged"` | `{device}` | The _last interacted device_ has changed. |
|
|
160
|
+
|
|
161
|
+
|
|
162
|
+
#### InputDevice - onBindDown() Events
|
|
150
163
|
|
|
164
|
+
You may also subscribe globally to **named bind** events:
|
|
165
|
+
|
|
166
|
+
```ts
|
|
167
|
+
InputDevice.onBindDown("my_custom_bind", (event) => {
|
|
168
|
+
// a bound input waas triggered
|
|
169
|
+
})
|
|
170
|
+
```
|
|
151
171
|
|
|
152
172
|
### KeyboardDevice
|
|
153
173
|
|
|
@@ -156,7 +176,7 @@ Unlike gamepads & custom devices, there is a single global keyboard device.
|
|
|
156
176
|
```ts
|
|
157
177
|
let keyboard = InputDevice.keyboard
|
|
158
178
|
|
|
159
|
-
if (
|
|
179
|
+
if (keyboard.key.ControlLeft) { // …
|
|
160
180
|
```
|
|
161
181
|
|
|
162
182
|
> [!NOTE]
|
|
@@ -168,7 +188,7 @@ if ( keyboard.key.ControlLeft ) { // …
|
|
|
168
188
|
```ts
|
|
169
189
|
keyboard.layout // "AZERTY" | "JCUKEN" | "QWERTY" | "QWERTZ"
|
|
170
190
|
|
|
171
|
-
keyboard.getKeyLabel(
|
|
191
|
+
keyboard.getKeyLabel("KeyZ") // Я
|
|
172
192
|
```
|
|
173
193
|
|
|
174
194
|
> [!NOTE]
|
|
@@ -176,7 +196,7 @@ keyboard.getKeyLabel( "KeyZ" ) // Я
|
|
|
176
196
|
> Almost every keyboard is one of these four (or a regional derivative – e.g. Hangeul,
|
|
177
197
|
> Kana). There is no built-in detection for specialist or esoteric layouts (e.g. Dvorak, Colemak, BÉPO).
|
|
178
198
|
>
|
|
179
|
-
> The `keyboard.getKeyLabel(
|
|
199
|
+
> The `keyboard.getKeyLabel(key)` uses the [KeyboardLayoutMap API](https://caniuse.com/mdn-api_keyboardlayoutmap)
|
|
180
200
|
> when available, before falling back to default AZERTY, JCUKEN, QWERTY or QWERTZ key values.
|
|
181
201
|
|
|
182
202
|
The keyboard layout is automatically detected from (in order):
|
|
@@ -191,7 +211,7 @@ You can also manually force the layout:
|
|
|
191
211
|
// force layout
|
|
192
212
|
InputDevice.keyboard.layout = "JCUKEN"
|
|
193
213
|
|
|
194
|
-
InputDevice.keyboard.getKeyLabel(
|
|
214
|
+
InputDevice.keyboard.getKeyLabel("KeyW") // "Ц"
|
|
195
215
|
InputDevice.keyboard.layoutSource // "manual"
|
|
196
216
|
```
|
|
197
217
|
|
|
@@ -200,7 +220,7 @@ InputDevice.keyboard.layoutSource // "manual"
|
|
|
200
220
|
| Event | Description | Payload |
|
|
201
221
|
|---|---|---|
|
|
202
222
|
| `"layoutdetected"` | `{layout,layoutSource,device}` | The keyboard layout (`"QWERTY"`, `"QWERTZ"`, `"AZERTY"`, or `"JCUKEN"`) has been detected, either from the native API or from keypresses. |
|
|
203
|
-
| `"
|
|
223
|
+
| `"binddown"` | `{name,event,keyCode,keyLabel,device}` | A **named bind** key was pressed. |
|
|
204
224
|
| **Key presses:** | | |
|
|
205
225
|
| `"KeyA"` | `{event,keyCode,keyLabel,device}` | The `"KeyA"` was pressed. |
|
|
206
226
|
| `"KeyB"` | `{event,keyCode,keyLabel,device}` | The `"KeyB"` was pressed. |
|
|
@@ -215,11 +235,22 @@ Gamepads are automatically detected via the browser API when first interacted wi
|
|
|
215
235
|
Gamepad accessors are modelled around the "Standard Controller Layout":
|
|
216
236
|
|
|
217
237
|
```ts
|
|
218
|
-
|
|
238
|
+
const gamepad = InputDevice.gamepads[0];
|
|
239
|
+
|
|
240
|
+
if (gamepad.button.DpadDown)
|
|
241
|
+
{
|
|
242
|
+
// button pressed
|
|
243
|
+
}
|
|
219
244
|
|
|
220
|
-
if (
|
|
221
|
-
|
|
222
|
-
|
|
245
|
+
if (gamepad.leftTrigger > 0.25)
|
|
246
|
+
{
|
|
247
|
+
// trigger pulled
|
|
248
|
+
}
|
|
249
|
+
|
|
250
|
+
if (gamepad.leftJoystick.x < -0.33)
|
|
251
|
+
{
|
|
252
|
+
// joystick moved
|
|
253
|
+
}
|
|
223
254
|
```
|
|
224
255
|
|
|
225
256
|
> [!TIP]
|
|
@@ -243,24 +274,24 @@ gamepad.playVibration({
|
|
|
243
274
|
|
|
244
275
|
The gamepad buttons reference **Standard Controller Layout**:
|
|
245
276
|
|
|
246
|
-
| Button
|
|
277
|
+
| Button # | GamepadCode | Description | Xbox Series X | Playstation 5 DualSense® | Nintendo Switch™ Pro |
|
|
247
278
|
|:---:|:---|:---|:---:|:---:|:---:|
|
|
248
|
-
| `0` | `"
|
|
249
|
-
| `1` | `"
|
|
250
|
-
| `2` | `"
|
|
251
|
-
| `3` | `"
|
|
279
|
+
| `0` | `"Face1"` | **Face Button 1** | A | Cross | B |
|
|
280
|
+
| `1` | `"Face2"` | **Face Button 2** | B | Circle | A |
|
|
281
|
+
| `2` | `"Face3"` | **Face Button 3** | X | Square | Y |
|
|
282
|
+
| `3` | `"Face4"` | **Face Button 4** | Y | Triangle | X |
|
|
252
283
|
| `4` | `"LeftShoulder"` | **Left Shoulder** | LB | L1 | L |
|
|
253
284
|
| `5` | `"RightShoulder"` | **Right Shoulder** | RB | R1 | R |
|
|
254
285
|
| `6` | `"LeftTrigger"` | **Left Trigger** | LT | L2 | ZL |
|
|
255
286
|
| `7` | `"RightTrigger"` | **Right Trigger** | RT | R2 | ZR |
|
|
256
|
-
| `8` | `"Back"` | **Back** |
|
|
257
|
-
| `9` | `"Start"` | **Start** |
|
|
258
|
-
| `10` | `"LeftStickClick"` | **Left Stick Click** | LSB | L3 | L3 |
|
|
259
|
-
| `11` | `"RightStickClick"` | **Right Stick Click** | RSB | R3 | R3 |
|
|
260
|
-
| `12` | `"
|
|
261
|
-
| `13` | `"
|
|
262
|
-
| `14` | `"
|
|
263
|
-
| `15` | `"
|
|
287
|
+
| `8` | `"Back"` | **Back** | View | Options | Minus |
|
|
288
|
+
| `9` | `"Start"` | **Start** | Menu | Select | Plus |
|
|
289
|
+
| `10` | `"LeftStickClick"` | **Left Stick (Click)** | LSB | L3 | L3 |
|
|
290
|
+
| `11` | `"RightStickClick"` | **Right Stick (Click)** | RSB | R3 | R3 |
|
|
291
|
+
| `12` | `"DpadUp"` | **D-Pad Up** | ⬆️ | ⬆️ | ⬆️ |
|
|
292
|
+
| `13` | `"DpadDown"` | **D-Pad Down** | ⬇️ | ⬇️ | ⬇️ |
|
|
293
|
+
| `14` | `"DpadLeft"` | **D-Pad Left** | ⬅️ | ⬅️ | ⬅️ |
|
|
294
|
+
| `15` | `"DpadRight"` | **D-Pad Right** | ➡️ | ➡️ | ➡️ |
|
|
264
295
|
|
|
265
296
|
#### Gamepad Axis Codes
|
|
266
297
|
|
|
@@ -268,71 +299,32 @@ Bindable helpers are available for the joysticks too:
|
|
|
268
299
|
|
|
269
300
|
| Axis # | GamepadCode | Standard | Layout
|
|
270
301
|
|:---:|:---:|:---:|:---:|
|
|
271
|
-
| `0` | `"LeftStickLeft"`<br/>`"LeftStickRight"` | **Left Stick (
|
|
272
|
-
| `1` | `"LeftStickUp"`<br/>`"LeftStickDown"` | **Left Stick (
|
|
273
|
-
| `2` | `"RightStickLeft"`<br/>`"RightStickRight"` | **Right Stick (
|
|
274
|
-
| `3` | `"RightStickUp"`<br/>`"RightStickDown"` | **Right Stick (
|
|
302
|
+
| `0` | `"LeftStickLeft"`<br/>`"LeftStickRight"` | **Left Stick (X-Axis)** | ⬅️➡️ |
|
|
303
|
+
| `1` | `"LeftStickUp"`<br/>`"LeftStickDown"` | **Left Stick (Y-Axis)** | ⬆️⬇️ |
|
|
304
|
+
| `2` | `"RightStickLeft"`<br/>`"RightStickRight"` | **Right Stick (X-Axis)** | ⬅️➡️ |
|
|
305
|
+
| `3` | `"RightStickUp"`<br/>`"RightStickDown"` | **Right Stick (Y-Axis)** | ⬆️⬇️ |
|
|
275
306
|
|
|
276
307
|
> [!TIP]
|
|
277
|
-
> Set the `joystick.
|
|
308
|
+
> Set the `joystick.pressThreshold` option in `GamepadDevice.defaultOptions` to adjust event sensitivity.
|
|
278
309
|
|
|
279
310
|
#### Gamepad Layouts
|
|
280
311
|
|
|
281
312
|
```ts
|
|
282
|
-
gamepad.layout
|
|
313
|
+
gamepad.layout // "xbox_one"
|
|
283
314
|
```
|
|
284
315
|
|
|
285
|
-
|
|
286
|
-
improvements (e.
|
|
287
|
-
|
|
288
|
-
There is some limited layout remapping support built-in for Nintendo controllers, which appear to be the
|
|
289
|
-
only major brand controller that deviates from the standard.
|
|
290
|
-
|
|
291
|
-
##### Gamepad - Nintendo Layout Remapping
|
|
292
|
-
|
|
293
|
-
> [!CAUTION]
|
|
294
|
-
> ***Nintendo:** Both the labels and physical positions of the A,B,X,Y buttons are different
|
|
295
|
-
> on Nintendo controllers.
|
|
296
|
-
>
|
|
297
|
-
> Set `GamepadDevice.defaultOptions.nintendoRemapMode` to apply the remapping as required.
|
|
298
|
-
>
|
|
299
|
-
> - `"physical"` _**(default)**_ – The A,B,X,Y button codes will refer the standard face button positions (Left=X, Top=Y, Bottom=A, Right=B).
|
|
300
|
-
> - `"accurate"` – The A,B,X,Y button codes will refer to the exact Nintendo labels (Left=Y, Top=X, Bottom=B, Right=A).
|
|
301
|
-
> - `"none"` – The A,B,X,Y button codes mapping stay at the default indices (Left=Y, Top=B, Bottom=X, Right=A).
|
|
302
|
-
>
|
|
303
|
-
> ```
|
|
304
|
-
> standard nintendo nintendo nintendo
|
|
305
|
-
> layout "physical" "accurate" "none"
|
|
306
|
-
> reference (default)
|
|
307
|
-
>
|
|
308
|
-
> Y Y X B
|
|
309
|
-
> X B X B Y A Y A
|
|
310
|
-
> A A B X
|
|
311
|
-
>
|
|
312
|
-
> 3 3 2 1
|
|
313
|
-
> 2 1 2 1 3 0 3 0
|
|
314
|
-
> 0 0 1 2
|
|
315
|
-
> ```
|
|
316
|
-
|
|
317
|
-
You can manually override this per-gamepad, or for all gamepads:
|
|
318
|
-
|
|
319
|
-
```ts
|
|
320
|
-
// set default
|
|
321
|
-
GamepadDevice.defaultOptions.nintendoRemapMode = "none"
|
|
322
|
-
|
|
323
|
-
// set for a single gamepad
|
|
324
|
-
gamepad.options.nintendoRemapMode = "accurate"
|
|
325
|
-
```
|
|
316
|
+
Gamepad device layout reporting is a non-standard API, and should only be used for aesthetic
|
|
317
|
+
enhancements improvements (i.e. [display layout-specific icons](https://thoseawesomeguys.com/prompts/)).
|
|
326
318
|
|
|
327
319
|
#### GamepadDevice Events
|
|
328
320
|
|
|
329
321
|
| Event | Description | Payload |
|
|
330
322
|
|---|---|---|
|
|
331
|
-
| `"
|
|
323
|
+
| `"binddown"` | `{name,button,buttonCode,device}` | A **named bind** button was pressed. |
|
|
332
324
|
| **Button presses:** | | |
|
|
333
|
-
| `"
|
|
334
|
-
| `"
|
|
335
|
-
| `"
|
|
325
|
+
| `"Face1"` | `{button,buttonCode,device}` | Standard layout button `"Face1"` was pressed. Equivalent to `0`. |
|
|
326
|
+
| `"Face2"` | `{button,buttonCode,device}` | Standard layout button `"Face2"` was pressed. Equivalent to `1`. |
|
|
327
|
+
| `"Face3"` | `{button,buttonCode,device}` | Standard layout button `"Face3"` was pressed. Equivalent to `2`. |
|
|
336
328
|
| … | … | … |
|
|
337
329
|
| **Button presses (no label):** | | |
|
|
338
330
|
| `0` or `Button.A` | `{button,buttonCode,device}` | Button at offset `0` was pressed. |
|
|
@@ -347,17 +339,16 @@ You can add custom devices to the device manager so it will be polled togehter a
|
|
|
347
339
|
```ts
|
|
348
340
|
import { type CustomDevice, InputDevice } from "pixijs-input-devices"
|
|
349
341
|
|
|
350
|
-
export const
|
|
351
|
-
id: "on-screen-buttons",
|
|
342
|
+
export const onScreenButtonsDevice: CustomDevice = {
|
|
352
343
|
type: "custom",
|
|
344
|
+
id: "OnScreen",
|
|
353
345
|
meta: {},
|
|
354
|
-
|
|
355
|
-
update: ( now: number ) => {
|
|
346
|
+
update: (now: number) => {
|
|
356
347
|
// polling update
|
|
357
348
|
}
|
|
358
|
-
}
|
|
349
|
+
};
|
|
359
350
|
|
|
360
|
-
InputDevice.add(
|
|
351
|
+
InputDevice.add(onScreenButtonsDevice);
|
|
361
352
|
```
|
|
362
353
|
|
|
363
354
|
## Named Binds
|
|
@@ -376,8 +367,8 @@ InputDevice.keyboard.configureBinds({
|
|
|
376
367
|
|
|
377
368
|
// all gamepads:
|
|
378
369
|
GamepadDevice.configureDefaultBinds({
|
|
379
|
-
jump: [ "
|
|
380
|
-
crouch: [ "
|
|
370
|
+
jump: [ "Face1", "LeftStickUp" ],
|
|
371
|
+
crouch: [ "Face2", "Face3", "RightTrigger" ],
|
|
381
372
|
toggleGraphics: [ "RightStickUp", "RightStickDown" ],
|
|
382
373
|
})
|
|
383
374
|
```
|
|
@@ -388,11 +379,11 @@ These can then be used with either the real-time and event-based APIs.
|
|
|
388
379
|
|
|
389
380
|
```ts
|
|
390
381
|
// listen to all devices:
|
|
391
|
-
InputDevice.
|
|
382
|
+
InputDevice.onBindDown("toggleGraphics", (e) => toggleGraphics())
|
|
392
383
|
|
|
393
384
|
// listen to specific devices:
|
|
394
|
-
InputDevice.keyboard.
|
|
395
|
-
InputDevice.gamepads[0].
|
|
385
|
+
InputDevice.keyboard.onBindDown("jump", (e) => doJump())
|
|
386
|
+
InputDevice.gamepads[0].onBindDown("jump", (e) => doJump())
|
|
396
387
|
```
|
|
397
388
|
|
|
398
389
|
#### Real-time:
|
|
@@ -401,19 +392,19 @@ InputDevice.gamepads[0].onBind( "jump", ( e ) => doJump() )
|
|
|
401
392
|
let jump = false, crouch = false, moveX = 0
|
|
402
393
|
|
|
403
394
|
const keyboard = InputDevice.keyboard
|
|
404
|
-
if (
|
|
405
|
-
if (
|
|
406
|
-
if (
|
|
407
|
-
else if (
|
|
395
|
+
if (keyboard.bindDown("jump")) jump = true
|
|
396
|
+
if (keyboard.bindDown("crouch")) crouch = true
|
|
397
|
+
if (keyboard.key.ArrowLeft) moveX = -1
|
|
398
|
+
else if (keyboard.key.ArrowRight) moveX = 1
|
|
408
399
|
|
|
409
|
-
for (
|
|
410
|
-
if (
|
|
411
|
-
if (
|
|
400
|
+
for (const gamepad of InputDevice.gamepads) {
|
|
401
|
+
if (gamepad.bindDown("jump")) jump = true
|
|
402
|
+
if (gamepad.bindDown("crouch")) crouch = true
|
|
412
403
|
|
|
413
404
|
// gamepads have additional analog inputs
|
|
414
405
|
// we're going to apply these only if touched
|
|
415
|
-
if (
|
|
416
|
-
if (
|
|
406
|
+
if (gamepad.leftJoystick.x != 0) moveX = gamepad.leftJoystick.x
|
|
407
|
+
if (gamepad.leftTrigger > 0) moveX *= (1 - gamepad.leftTrigger)
|
|
417
408
|
}
|
|
418
409
|
```
|
|
419
410
|
|
|
@@ -426,8 +417,8 @@ _Traverse a UI using input devices._
|
|
|
426
417
|
Set up navigation once using:
|
|
427
418
|
|
|
428
419
|
```ts
|
|
429
|
-
UINavigation.configureWithRoot(
|
|
430
|
-
registerPixiJSNavigationMixin(
|
|
420
|
+
UINavigation.configureWithRoot(app.stage) // any root container
|
|
421
|
+
registerPixiJSNavigationMixin(PIXI.Container)
|
|
431
422
|
```
|
|
432
423
|
|
|
433
424
|
Navigation should now work automatically if your buttons handle these events:
|
|
@@ -494,7 +485,7 @@ Containers are extended with a few properties/accessors:
|
|
|
494
485
|
> [!WARNING]
|
|
495
486
|
> **Fallback Hover Effect:** If there is no `"pointerover"` or `"mouseover"` handler detected on a container, `UINavigation`
|
|
496
487
|
> will apply abasic alpha effect to the selected item to indicate which container is currently the navigation target. This
|
|
497
|
-
> can be disabled by setting `UINavigation.options.
|
|
488
|
+
> can be disabled by setting `UINavigation.options.enableFallbackOverEffect` to `false`.
|
|
498
489
|
|
|
499
490
|
### Default Binds
|
|
500
491
|
|
|
@@ -502,12 +493,12 @@ The keyboard and gamepad devices are preconfigured with the following binds, fee
|
|
|
502
493
|
|
|
503
494
|
Navigation Intent Bind | Keyboard | Gamepad
|
|
504
495
|
---|---|---
|
|
505
|
-
`"navigate.left"` | "ArrowLeft", "KeyA" | "
|
|
506
|
-
`"navigate.right"` | "ArrowRight", "KeyD" | "
|
|
507
|
-
`"navigate.up"` | "ArrowUp", "KeyW" | "
|
|
508
|
-
`"navigate.down"` | "ArrowDown", "KeyS" | "
|
|
509
|
-
`"navigate.trigger"` | "Enter", "Space" | "
|
|
510
|
-
`"navigate.back"` | "Escape", "Backspace" | "
|
|
496
|
+
`"navigate.left"` | "ArrowLeft", "KeyA" | "DpadLeft", "LeftStickLeft"
|
|
497
|
+
`"navigate.right"` | "ArrowRight", "KeyD" | "DpadRight", "LeftStickRight"
|
|
498
|
+
`"navigate.up"` | "ArrowUp", "KeyW" | "DpadUp", "LeftStickUp"
|
|
499
|
+
`"navigate.down"` | "ArrowDown", "KeyS" | "DpadDown", "LeftStickDown"
|
|
500
|
+
`"navigate.trigger"` | "Enter", "Space" | "Face1"
|
|
501
|
+
`"navigate.back"` | "Escape", "Backspace" | "Face2", "Back"
|
|
511
502
|
|
|
512
503
|
### Manual control for submenus & modal views
|
|
513
504
|
|
|
@@ -515,7 +506,7 @@ You can manually take control of navigation using:
|
|
|
515
506
|
|
|
516
507
|
```ts
|
|
517
508
|
// take control
|
|
518
|
-
UINavigation.pushResponder(
|
|
509
|
+
UINavigation.pushResponder(myModalView)
|
|
519
510
|
|
|
520
511
|
// relinquish control
|
|
521
512
|
UINavigation.popResponder()
|
|
@@ -535,9 +526,9 @@ InputDevice.on("deviceconnected", ({ device }) =>
|
|
|
535
526
|
device.meta.localPlayerId = 123
|
|
536
527
|
)
|
|
537
528
|
|
|
538
|
-
for (
|
|
529
|
+
for (const device of InputDevice.devices)
|
|
539
530
|
{
|
|
540
|
-
if (
|
|
531
|
+
if (device.meta.localPlayerId === 123)
|
|
541
532
|
{
|
|
542
533
|
// use assigned input device!
|
|
543
534
|
}
|
|
@@ -550,26 +541,29 @@ You can easily map an on-screen input device using the `CustomDevice` interface.
|
|
|
550
541
|
|
|
551
542
|
```ts
|
|
552
543
|
export class OnScreenInputContainer extends Container implements CustomDevice {
|
|
553
|
-
id = "onscreen"
|
|
554
|
-
type = "custom" as const
|
|
555
|
-
meta: Record<string, any> = {}
|
|
544
|
+
id = "onscreen"
|
|
545
|
+
type = "custom" as const
|
|
546
|
+
meta: Record<string, any> = {}
|
|
556
547
|
|
|
557
548
|
inputs = {
|
|
558
549
|
moveX: 0.0
|
|
559
550
|
jump: false,
|
|
560
551
|
}
|
|
561
552
|
|
|
562
|
-
update(
|
|
553
|
+
update(now)
|
|
563
554
|
{
|
|
564
|
-
this.moveX = this._virtualJoystick.x
|
|
565
|
-
this.jump = this._jumpButton.isTouching()
|
|
555
|
+
this.inputs.moveX = this._virtualJoystick.x
|
|
556
|
+
this.inputs.jump = this._jumpButton.isTouching()
|
|
566
557
|
}
|
|
558
|
+
|
|
559
|
+
// e.g. disable named binds for onscreen joysticks:
|
|
560
|
+
bindDown(name){ return false }
|
|
567
561
|
}
|
|
568
562
|
|
|
569
|
-
const onscreen = new OnScreenInputContainer()
|
|
563
|
+
const onscreen = new OnScreenInputContainer()
|
|
570
564
|
|
|
571
|
-
InputDevice.add(
|
|
572
|
-
InputDevice.remove(
|
|
565
|
+
InputDevice.add(onscreen)
|
|
566
|
+
InputDevice.remove(onscreen)
|
|
573
567
|
```
|
|
574
568
|
|
|
575
569
|
### Two Users; One Keyboard
|
|
@@ -591,32 +585,32 @@ InputDevice.keyboard.configureBinds({
|
|
|
591
585
|
p2_jump: [ "ArrowUp" ],
|
|
592
586
|
p2_defend: [ "ArrowDown" ],
|
|
593
587
|
p2_left: [ "ArrowLeft" ],
|
|
594
|
-
p2_right: [ "ArrowRight" ]
|
|
588
|
+
p2_right: [ "ArrowRight" ]
|
|
595
589
|
})
|
|
596
590
|
```
|
|
597
591
|
|
|
598
592
|
and then switch groups depending on the mode:
|
|
599
593
|
|
|
600
594
|
```ts
|
|
601
|
-
if (
|
|
595
|
+
if (gameMode === "multiplayer")
|
|
602
596
|
{
|
|
603
|
-
player1.jump = device.
|
|
604
|
-
player1.defend = device.
|
|
605
|
-
player1.moveX += device.
|
|
606
|
-
player1.moveX += device.
|
|
607
|
-
|
|
608
|
-
player2.jump = device.
|
|
609
|
-
player2.defend = device.
|
|
610
|
-
player2.moveX += device.
|
|
611
|
-
player2.moveX += device.
|
|
597
|
+
player1.jump = device.bindDown("p1_jump")
|
|
598
|
+
player1.defend = device.bindDown("p1_defend")
|
|
599
|
+
player1.moveX += device.bindDown("p1_left") ? -1 : 0
|
|
600
|
+
player1.moveX += device.bindDown("p1_right") ? 1 : 0
|
|
601
|
+
|
|
602
|
+
player2.jump = device.bindDown("p2_jump")
|
|
603
|
+
player2.defend = device.bindDown("p2_defend")
|
|
604
|
+
player2.moveX += device.bindDown("p2_left") ? -1 : 0
|
|
605
|
+
player2.moveX += device.bindDown("p2_right") ? 1 : 0
|
|
612
606
|
}
|
|
613
607
|
else
|
|
614
608
|
{
|
|
615
|
-
player1.jump = device.
|
|
616
|
-
player1.defend = device.
|
|
617
|
-
player1.moveX += device.
|
|
618
|
-
player1.moveX += device.
|
|
609
|
+
player1.jump = device.bindDown("jump")
|
|
610
|
+
player1.defend = device.bindDown("defend")
|
|
611
|
+
player1.moveX += device.bindDown("left") ? -1 : 0
|
|
612
|
+
player1.moveX += device.bindDown("right") ? 1 : 0
|
|
619
613
|
|
|
620
|
-
updateComputerPlayerInput(
|
|
614
|
+
updateComputerPlayerInput(player2)
|
|
621
615
|
}
|
|
622
616
|
```
|