The Bluetooth HID protocol is one of the more useful things in the wireless stack. It is what makes your wireless mouse, keyboard, and game controller plug-and-play across every modern operating system without driver installs. ESP32-S3 supports BLE HID natively — the firmware advertises itself as a generic HID device, the OS recognises it, and from then on your custom hardware is indistinguishable from a brand-name gamepad.
This project builds a wireless game controller from scratch: an ESP32-S3, a thumbstick, eight buttons, and a small battery, in a 3D-printed case. About $25 in parts, fits in your hand, works with PC, Mac, iOS, Android, and any console that accepts generic Bluetooth controllers.
What we are building
2x potentiometers] --> ADC[ESP32-S3 ADC] Buttons[8 momentary buttons
A B X Y LB RB Start Select] --> GPIO[ESP32-S3 GPIO] ADC --> CPU[CPU
build HID report] GPIO --> CPU CPU -->|BLE HID| Radio[Bluetooth radio] end Radio -.->|BLE GATT| Host[Phone, PC, Mac, console] Host --> Game[Game / app]
The controller polls its inputs at 100–500 Hz, packages them into a HID report, and broadcasts. The host's Bluetooth stack decodes them as a standard gamepad.
Hardware
- ESP32-S3 DevKit (any variant — Seeed XIAO ESP32-S3 is compact) — $10
- 2-axis analog thumbstick (PSP-style with click) — $3
- 8 × momentary push buttons — $4
- 500–1000 mAh LiPo cell — $5
- TP4056 charger module — $2
- 3D-printed case (designs on Printables / Thingiverse) — $3
- Optional: 2 × analog triggers (linear hall sensor or pot) — $4
Total around $25.
Why ESP32-S3, specifically
The ESP32 classic and ESP32-C3 also support BLE HID, but with quirks: the classic has older Bluetooth 4.2, and the C3's BLE HID library support is thinner. The ESP32-S3 is the sweet spot — Bluetooth 5 LE, mature library support via Arduino's BleGamepad, dual-core for separate radio and input handling, and USB-OTG so you can also use it as a wired controller.
Calibration matters
The single thing that separates a good DIY controller from a bad one is thumbstick calibration. Cheap thumbsticks have asymmetric centre points, non-linear response, and dead-zone variance from unit to unit. Plug-and-play won't feel right.
Calibration steps:
- Read the centre value with the stick at rest. This is your zero.
- Push the stick fully to each direction. Record max X, min X, max Y, min Y.
- In firmware, normalise readings against centre and scale per axis.
- Apply a small dead zone (~5% of full scale) around centre.
- Optionally apply a non-linear curve (e.g. squaring with sign preservation) to give finer control near centre.
Save calibration to NVS flash so it persists across reboots. Add a button combo to recalibrate (e.g., hold Start+Select for 5 seconds).
What goes wrong
- Connection drops mid-game. Usually a power issue — the battery sags under load.
- OS sees the controller but games don't. Game uses XInput (Xbox-only), DirectInput (older Windows), or platform-specific protocols. BleGamepad's default is DirectInput; for XInput-only games on Windows, you may need a wrapper like x360ce.
- Latency feels off. BLE adds 5–15 ms of inherent latency on top of polling. For competitive games, that matters; for casual play, it doesn't.
- Stick drift. Cheap thumbsticks develop centre drift after months of use.
Frequently Asked Questions
Will this work with my Switch / PS5 / Xbox?
Switch and Steam Deck: yes, both accept generic Bluetooth controllers natively. PS5 and Xbox: no, both lock to first-party controllers.
How does this compare to an 8BitDo controller?
8BitDo controllers ($30–60) have better build quality and platform-specific firmware modes. The DIY version is cheaper, fully customisable (custom button layouts, macros, profiles), and a learning project. Different tradeoffs.
Does this work as a keyboard or mouse too?
Yes. The same BLE HID library can present as a keyboard or mouse instead of (or in addition to) a gamepad.
What's the latency for FPS / fighting games?
End-to-end measures about 25–40 ms over BLE. Pro-grade wired controllers run 5–10 ms. For most genres unnoticeable; for fighting games and competitive shooters, prefer wired.
Get the complete project package
The article above shows the core firmware and the principles behind it. The complete project package — assembled, tested, and ready to flash — is available by email request. We send it manually, and we read every request.
- Complete Arduino sketch (.ino) with full error handling
- List of required libraries with version numbers
- Printable wiring diagram (PDF)
- Bill of materials with current part numbers
- Build guide and troubleshooting tips
- Configuration template (WiFi, MQTT, etc.)
Share your thoughts
Worked with this in production and have a story to share, or disagree with a tradeoff? Email us at support@mybytenest.com — we read everything.