aboutsummaryrefslogtreecommitdiffstats
path: root/components/script/dom/navigator.rs
diff options
context:
space:
mode:
Diffstat (limited to 'components/script/dom/navigator.rs')
-rw-r--r--components/script/dom/navigator.rs56
1 files changed, 48 insertions, 8 deletions
diff --git a/components/script/dom/navigator.rs b/components/script/dom/navigator.rs
index 3732a1face7..d6901ee802a 100644
--- a/components/script/dom/navigator.rs
+++ b/components/script/dom/navigator.rs
@@ -9,6 +9,7 @@ use dom_struct::dom_struct;
use js::jsval::JSVal;
use lazy_static::lazy_static;
+use crate::dom::bindings::cell::DomRefCell;
use crate::dom::bindings::codegen::Bindings::NavigatorBinding::NavigatorMethods;
use crate::dom::bindings::codegen::Bindings::WindowBinding::Window_Binding::WindowMethods;
use crate::dom::bindings::reflector::{reflect_dom_object, DomObject, Reflector};
@@ -17,7 +18,7 @@ use crate::dom::bindings::str::DOMString;
use crate::dom::bindings::utils::to_frozen_array;
use crate::dom::bluetooth::Bluetooth;
use crate::dom::gamepad::Gamepad;
-use crate::dom::gamepadlist::GamepadList;
+use crate::dom::gamepadevent::GamepadEventType;
use crate::dom::gpu::GPU;
use crate::dom::mediadevices::MediaDevices;
use crate::dom::mediasession::MediaSession;
@@ -47,7 +48,7 @@ pub struct Navigator {
xr: MutNullableDom<XRSystem>,
mediadevices: MutNullableDom<MediaDevices>,
/// <https://www.w3.org/TR/gamepad/#dfn-gamepads>
- gamepads: MutNullableDom<GamepadList>,
+ gamepads: DomRefCell<Vec<MutNullableDom<Gamepad>>>,
permissions: MutNullableDom<Permissions>,
mediasession: MutNullableDom<MediaSession>,
gpu: MutNullableDom<GPU>,
@@ -81,9 +82,50 @@ impl Navigator {
self.xr.get()
}
- pub fn gamepads(&self) -> DomRoot<GamepadList> {
- self.gamepads
- .or_init(|| GamepadList::new(&self.global(), &[]))
+ pub fn get_gamepad(&self, index: usize) -> Option<DomRoot<Gamepad>> {
+ self.gamepads.borrow().get(index).and_then(|g| g.get())
+ }
+
+ pub fn set_gamepad(&self, index: usize, gamepad: &Gamepad) {
+ if let Some(gamepad_to_set) = self.gamepads.borrow().get(index) {
+ gamepad_to_set.set(Some(gamepad));
+ }
+ if self.has_gamepad_gesture.get() {
+ gamepad.set_exposed(true);
+ if self.global().as_window().Document().is_fully_active() {
+ gamepad.notify_event(GamepadEventType::Connected);
+ }
+ }
+ }
+
+ pub fn remove_gamepad(&self, index: usize) {
+ if let Some(gamepad_to_remove) = self.gamepads.borrow_mut().get(index) {
+ gamepad_to_remove.set(None);
+ }
+ self.shrink_gamepads_list();
+ }
+
+ /// <https://www.w3.org/TR/gamepad/#dfn-selecting-an-unused-gamepad-index>
+ pub fn select_gamepad_index(&self) -> u32 {
+ let mut gamepad_list = self.gamepads.borrow_mut();
+ if let Some(index) = gamepad_list.iter().position(|g| g.get().is_none()) {
+ index as u32
+ } else {
+ let len = gamepad_list.len();
+ gamepad_list.resize_with(len + 1, Default::default);
+ len as u32
+ }
+ }
+
+ fn shrink_gamepads_list(&self) {
+ let mut gamepad_list = self.gamepads.borrow_mut();
+ for i in (0..gamepad_list.len()).rev() {
+ if gamepad_list.get(i as usize).is_none() {
+ gamepad_list.remove(i as usize);
+ } else {
+ break;
+ }
+ }
}
pub fn has_gamepad_gesture(&self) -> bool {
@@ -200,9 +242,7 @@ impl NavigatorMethods for Navigator {
return Vec::new();
}
- let root = self.gamepads.or_init(|| GamepadList::new(&global, &[]));
-
- root.list()
+ self.gamepads.borrow().iter().map(|g| g.get()).collect()
}
// https://w3c.github.io/permissions/#navigator-and-workernavigator-extension
fn Permissions(&self) -> DomRoot<Permissions> {