@@ -26,7 +26,18 @@ export class Button extends EventTarget {
2626 #name = null ;
2727 #index = null ;
2828 #debug = false ;
29+ #angle = 0 ;
30+ #distance = 0 ;
31+ #proportion = 0 ;
32+ #touched = false ;
33+ #value = 0 ;
34+ #lastValue = 0 ;
2935
36+ /**
37+ *
38+ * @param {string } name
39+ * @param {Number } index
40+ */
3041 constructor ( name , index ) {
3142 super ( )
3243 this . #name = name ;
@@ -48,18 +59,75 @@ export class Button extends EventTarget {
4859 this . #debug = v ;
4960 }
5061
62+ /**
63+ * angle in radians
64+ * This is done by GamepadJS, you don't have to set it.
65+ */
66+ get angle ( ) {
67+ return this . #angle;
68+ }
69+
70+
71+ /**
72+ * distance from the center of the joystick
73+ */
74+ get distance ( ) {
75+ return this . #distance;
76+ }
77+
78+ get proportion ( ) {
79+ return this . #proportion;
80+ }
81+
82+ get touched ( ) {
83+ return this . #touched;
84+ }
85+
86+ get value ( ) {
87+ return this . #value
88+ }
89+
90+ /**
91+ * only used for Firefox fix
92+ */
93+ set value ( v ) {
94+ this . #lastValue = this . #value;
95+ this . #value = v ;
96+ this . #touched = - .9 < v ;
97+ // to solve a bug if the value starts in zero (Firefox)
98+ if ( this . #lastValue === this . #value && this . #value === 0 ) {
99+ this . #touched = false ;
100+ }
101+ if ( this . #touched) {
102+ this . #value = ( this . #value + 1 ) * .5 ;
103+ }
104+ this . #dispatchEventIfPushed( ) ;
105+ }
106+
51107 /**
52108 * To copy properties from the Gamepad API button
53109 * @param {Object } v
54110 */
55- setProperties ( v ) {
56- for ( let p in v ) {
57- this [ p ] = v [ p ]
111+ setProperties ( { pressed, touched, value, x, y } ) {
112+ this . pressed = pressed
113+ this . #touched = touched
114+ this . x = x ;
115+ this . y = y ;
116+ this . #value = value ;
117+ if ( this . x && this . y ) {
118+ const { x, y } = this ; // TODO replace with #x and #y
119+ this . #distance = Math . sqrt ( x * x + y * y ) ;
120+ this . #angle = Math . atan2 ( - y , x ) ;
121+ this . #proportion = this . #angle / TAU ;
122+ if ( this . #angle < 0 ) this . #angle += TAU ;
123+
124+ this . #touched = ( Math . abs ( x ) > .1 ) || ( Math . abs ( y ) > .1 ) ;
58125 }
126+ this . #dispatchEventIfPushed( ) ;
59127 }
60128
61- dispatchEventIfPushed ( ) {
62- if ( this . touched && ! this . #pushed) {
129+ # dispatchEventIfPushed( ) {
130+ if ( this . # touched && ! this . #pushed) {
63131 this . dispatchEvent ( new Event ( Button . PUSHED ) ) ;
64132 this . #pushed = true ;
65133 this . #released = false ;
@@ -72,7 +140,7 @@ export class Button extends EventTarget {
72140 console . log ( `Button PUSHED: Name: ${ this . #name} , Index: ${ index } ` ) ;
73141 }
74142 }
75- if ( ! this . touched && ! this . #released) {
143+ if ( ! this . # touched && ! this . #released) {
76144 this . dispatchEvent ( new Event ( Button . RELEASED ) ) ;
77145 this . #pushed = false ;
78146 this . #released = true ;
@@ -148,6 +216,15 @@ export class Control extends EventTarget {
148216 } ) ;
149217 }
150218
219+ /**
220+ * Add an button with alias `name`
221+ * @param {string } name Name the button will be called on later
222+ * @param {Number } index button index from the Gamepad API
223+ */
224+ addButton ( name , index ) {
225+ this . #buttons[ name ] = new Button ( name , index ) ;
226+ }
227+
151228 get hasVibrationActuator ( ) {
152229 return ! ! this . #gamepad. vibrationActuator ;
153230 }
@@ -207,11 +284,10 @@ export class GamepadJS extends EventTarget {
207284 console . log ( gamepad . mapping ) ;
208285
209286 for ( let buttonName in this . #mapping. buttons ) {
210- // TODO controls.addButton method
211- control . buttons [ buttonName ] = new Button ( buttonName , this . #mapping. buttons [ buttonName ] ) ;
287+ control . addButton ( buttonName , this . #mapping. buttons [ buttonName ] ) ;
212288 }
213289 for ( let buttonName in this . #mapping. axes ) {
214- control . buttons [ buttonName ] = new Button ( buttonName , this . #mapping. axes [ buttonName ] ) ;
290+ control . addButton ( buttonName , this . #mapping. axes [ buttonName ] ) ;
215291 }
216292
217293 this . dispatchEvent ( new CustomEvent ( GamepadJS . CONNECTED , { detail : control } ) ) ;
@@ -245,7 +321,7 @@ export class GamepadJS extends EventTarget {
245321
246322 #isObject = v => typeof v === 'object' && v !== null ;
247323
248- #distance = ( x , y ) => Math . sqrt ( x * x + y * y ) ;
324+ // #distance = (x, y) => Math.sqrt(x * x + y * y);
249325
250326 /**
251327 * To be called in the `requestAnimationFrame`
@@ -262,7 +338,7 @@ export class GamepadJS extends EventTarget {
262338 continue ;
263339 }
264340
265- if ( ! control . hasVibrationActuator ) {
341+ if ( ! control . hasVibrationActuator ) {
266342 control . gamepad = gamepad ;
267343 }
268344
@@ -272,38 +348,22 @@ export class GamepadJS extends EventTarget {
272348 const button = control . buttons [ buttonName ] ;
273349 const gamepadButton = gamepad . buttons [ button . index ] ;
274350 button . debug = this . #debug;
275- button . setProperties ( gamepadButton )
276- button . dispatchEventIfPushed ( ) ;
351+ button . setProperties ( gamepadButton ) ;
277352 }
278353
279354 for ( let buttonName in mapping . axes ) {
280355 const mappingButton = mapping . axes [ buttonName ] ;
281356 const isObject = this . #isObject( mappingButton ) ;
282357
283- let button = control . buttons [ buttonName ] ;
358+ const button = control . buttons [ buttonName ] ;
359+ button . debug = this . #debug;
284360
285361 if ( isObject ) {
286- button = control . buttons [ buttonName ] ;
287- button . debug = this . #debug;
288362 button . setProperties ( { x : gamepad . axes [ mappingButton . x ] , y : gamepad . axes [ mappingButton . y ] } )
289- button . touched = ( Math . abs ( button . x ) > .1 ) || ( Math . abs ( button . y ) > .1 ) ;
290- button . angle = Math . atan2 ( - button . y , button . x ) ;
291- button . proportion = button . angle / TAU ; // TODO move to Button class
292- if ( button . angle < 0 ) button . angle += TAU ;
293- button . distance = this . #distance( button . x , button . y ) ;
294363 } else {
295- const value = gamepad . axes [ mappingButton ] ;
296- button = control . buttons [ buttonName ] ;
297- button . debug = this . #debug;
298- button . lastValue = button . value ;
299- button . value = value ;
300- button . touched = - .9 < value ;
301- // to solve a bug if the value starts in zero
302- if ( button . lastValue == button . value && button . value == 0 ) {
303- button . touched = false ;
304- }
364+ // Firefox fix
365+ button . value = gamepad . axes [ mappingButton ]
305366 }
306- button . dispatchEventIfPushed ( ) ;
307367 }
308368 }
309369
0 commit comments