ankidroid / ankidroid/Anki-Android

[Bug] JavaScript can't detect gamepads

Open
#21,395 2 comments 0 reactions 1 assignee Claimed by @BrayanDSO View on GitHub
Needs Triage
Dominant language
Kotlin
Stars
11.8k
Forks
2.9k
Avg merge
2d 3h
Merged PRs (30d)
171

Description

### Checked for duplicates?

- [x] This issue is not a duplicate

### Does it also happen in the desktop version?

- [x] This bug does not occur in the latest version of Anki Desktop

### What are the steps to reproduce this bug?

1. Connect a gamepad to an Android device.
2. Connect the Android device to a desktop Chromium-based browser via USB or wireless debugging.
3. Open a card in AnkiDroid.
4. Inspect that card with the browser dev tools.
5. Press a button on the gamepad ([per this forum comment](https://forums.ankiweb.net/t/does-anyone-know-how-to-use-a-gamepad-javascript-with-android/38398/8)).
6. Execute `navigator.getGamepads()` in the browser console. (Or add it to a script tag on a card or template.)

### Expected behaviour

The console should show an array containing a Gamepad object. Instead it shows an array of null values:

```js
// expected
[Gamepad, null, null, null]

// actual
[null, null, null, null]
```

### Debug info

```text
AnkiDroid
2.24.0
May 2, 2026
(anki 25.09.2 / 3890e12c)
(FSRS 6)
```

- Android device: Google Pixel 7
- Android version: 16
- Gamepad: 8BitDo Micro
- This device has three modes: S (emulates Nintendo Switch controller), D (DirectInput), K (keyboard). The behavior described above is the same in both S and D modes.
- When `navigator.getGamepads()` is run in a desktop browser with the gamepad paired in D mode, the controller appears as a `Gamepad` object with `id`: `8BitDo Micro gamepad (Vendor: 2dc8 Product: 9020)`. (S mode doesn't work on desktop either.)
- Desktop OS: macOS Tahoe 26.3.1
- Desktop browser: Brave 1.92.134 (Chromium: 150.0.7871.63) (Official Build) (arm64)

### (Optional) Anything else you want to share?

### More details

- This was previously reported in #14974 and reported as fixed by #14983 (in 2023). I'm not sure if there was a regression, this never worked, it was removed because gamepad buttons can be mapped to actions in the app settings, or I'm doing something wrong.
- Settings that don't affect the behavior:
- Whether any controller buttons are mapped to actions in Settings > Controls
- Advanced > Type answer into the card (reported to affect handling of gamepad input in #20872, but for app-level button mappings, not JavaScript)
- The gamepad is successfully paired to the mobile device. Some of the buttons trigger OS or AnkiDroid actions, but the gamepad and its events and state aren't accessible to JavaScript running on the card.
- I assume this is supposed to work based on the previous report and [code like](https://github.com/ankidroid/Anki-Android/blob/main/AnkiDroid/src/main/java/com/ichi2/anki/AbstractFlashcardViewer.kt#L689) `if (webView.handledGamepadKeyDown(keyCode, event))`.

### Some notes about the use case

- #12425, which has been open since 2022, requests settings that permit mapping double-taps, long presses, and simultaneous presses of multiple gamepad buttons to actions. Exposing gamepads to the webview would (a) allow users to implement all of these with JavaScript in advance (or lieu) of official AnkiDroid support, and (b) shift the development and maintenance burden for those features onto deck/template developers and end users rather than the AnkiDroid team.
- While DirectInput is officially deprecated, I believe it's the most standard mode offered by the 8BitDo Micro, which is popular for use with Anki(Droid). Anyway, I don't think the input type affects the issue at all; it's just that the webview can't see gamepads at all.
- **Keyboard events** are also not received by JavaScript on cards. (Maybe this should be a separate issue, but mentioning it here because it's basically the same issue so it might be simpler to address both in one PR.)
- If there's concern about interaction between JavaScript handling of keyboard (or gamepad) input and webview-external handling, it could be a setting that's off by default, something like "Pass [keyboard/gamepad] events to webview", description "This allows JavaScript in cards to handle [keyboard/gamepad] input, but may *blah blah blah*. Support is not available for issues caused by enabling this."
- [This forum comment](https://forums.ankiweb.net/t/does-anyone-know-how-to-use-a-gamepad-javascript-with-android/38398/3) from 2023 when this was first being implemented partially lays out the rationale: "I want to have the ability to trigger a specific function that is not provided in the default action list....In other words, the ability to write a customized mapping to any javascript function would give users the freedom to play with their cards."
- Although we do now have the ability to map buttons to JavaScript functions (user actions), "the freedom to play with their cards" is still limited. With JS access to gamepad and keyboard events, no effort from AnkiDroid would be required for users to implement mappings for more than 9 functions, support all the options mentioned by #12425 (admittedly, two of them could probably be done with JS already), set their own thresholds for what qualifies as a long press, or anything else not specifically foreseen and implemented within AnkiDroid itself. I currently have...11 functions I'd like to map 🙂
- For me personally, having a single setup entrypoint for all my Anki-related JS—dropping a single script tag into all my templates—is preferable to setting up 10 mappings in settings, matching my code up to them, and making sure nothing gets out of sync.

### Research

- [x] I have checked the [manual](https://docs.ankidroid.org/) and the [FAQ](https://github.com/ankidroid/Anki-Android/wiki/FAQ) and could not find a solution to my issue
- [ ] (Optional) I have confirmed the issue is not resolved in the latest alpha release ([instructions](https://docs.ankidroid.org/manual.html#betaTesting))

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.