]> git.r.bdr.sh - rbdr/sumo/blobdiff - lib/systems/control_mapper.js
Merge branch 'feature/rbdr-gitlab-pipeline' into 'develop'
[rbdr/sumo] / lib / systems / control_mapper.js
index e91ecc6c05bc4dba532fb675c4b12623587b7380..c39aea3c8fe44ba48fcc90fd0f408b0a256eb53c 100644 (file)
@@ -2,9 +2,11 @@ import { System } from '@serpentity/serpentity';
 
 import ControllableNode from '../nodes/controllable';
 
-/* global window */
+/* global navigator window */
 
 const internals = {
+  gamepadState: {
+  },
   keyboardState: {
   }
 };
@@ -32,6 +34,7 @@ export default class ControlMapperSystem extends System {
     this.controllables = null;
 
     this._initializeKeyboard();
+    this._initializeGamepad();
   }
 
   /**
@@ -71,11 +74,21 @@ export default class ControlMapperSystem extends System {
    */
   update(currentFrameDuration) {
 
+    this._updateGamepads();
+
     for (const controllable of this.controllables) {
       for (const map of controllable.controlMap.map) {
         if (map.source.type === 'keyboard') {
           this._setValue(controllable.entity, map.target, !!internals.keyboardState[map.source.index]);
         }
+
+        if (map.source.type === 'gamepad') {
+          const gamepad = internals.gamepadState[map.source.gamepadNumber];
+          if (gamepad) {
+            const source = gamepad[map.source.gamepadInputSource];
+            source && this._setValue(controllable.entity, map.target, source[map.source.index]);
+          }
+        }
       }
     }
   }
@@ -95,6 +108,32 @@ export default class ControlMapperSystem extends System {
     });
   }
 
+  // Requests gamepad access and binds to the events
+
+  _initializeGamepad() {
+
+    window.addEventListener('gamepadconnected', (event) => {
+
+      internals.gamepadState[event.gamepad.index] = event.gamepad;
+      window.gamepad = event.gamepad;
+    });
+
+    window.addEventListener('gamepaddisconnected', (event) => {
+
+      delete internals.gamepadState[event.gamepad.index];
+    });
+  }
+
+  // Update Gamepad
+
+  _updateGamepads() {
+
+    const gamepads = navigator.getGamepads();
+    for (const index of Object.keys(internals.gamepadState)) {
+      internals.gamepadState[index] = gamepads[index];
+    }
+  }
+
   // Sets the value to a target
 
   _setValue(entity, target, value) {