COLORCAST — tap the watch, paint the phone (Xiaomi Watch S4 + Android)
Watch app + Android companion: tap the watch screen and the companion's screen changes color, over Bluetooth LE. Colors cycle RED → GREEN → BLUE → YELLOW.
Status: BUILT, UNTESTED ON HARDWARE. The BLE code follows the official Vela docs exactly, but whether the S4 firmware exposes BLE to quick apps under AstroBox is unverified (same unknown class as the crown API).
How it works
WATCH (GATT client) PHONE (GATT server, ColorCompanion)
┌──────────────────────┐ ┌────────────────────────────┐
│ createScanner │ BLE advertise │ advertises ILIAS-COLOR │
│ subscribeBLEDeviceFind│ ◄──────────── │ service 0000fee7-… │
│ createGattClientDevice│ │ char 0000fee8-… (WRITE) │
│ connect │ │ │
│ writeCharacteristic │ ── 3B RGB ───► │ paint screen (r,g,b) │
└──────────────────────┘ └────────────────────────────┘
- Watch:
com.ilias.colorcast, BLE flow insrc/pages/index/index.ux(scan → subscribe → connect → write), color cycle insrc/common/colorcast.js - Phone: standard Android GATT server; no Xiaomi signature coupling (that's why
BLE instead of the official
@system.interconnect, which requires matching package names + re-signing with the Android app's key) - The S4 41mm has no WiFi, so the HTTP/fetch route was ruled out entirely
Watch app
src/
├── app.ux, manifest.json # com.ilias.colorcast, feature system.bluetooth.ble
├── common/colorcast.js # color cycle + payload (3-byte RGB) + UUIDs
└── pages/index/index.ux # scan/connect UI, tap-to-cast, status text
tests/colorcast.cjs # cycle/payload/UUID tests (node tests/colorcast.cjs)
Build: npm ci && npm run release → dist/com.ilias.colorcast.release.0.1.rpk
Android companion (built on the Arch PC)
Project: ~/android-build/colorcompanion on iliasmouhcine@192.168.1.30
(rsynced from /tmp/colorcompanion). Plain Java, no Android Studio needed.
cd ~/android-build/colorcompanion
export JAVA_HOME=$HOME/android-build/jdk21 # system JDK 26 breaks AGP 8.5.2
export ANDROID_HOME=$HOME/android-build/android-sdk
~/android-build/gradle-8.9/bin/gradle assembleDebug --no-daemon
# → app/build/outputs/apk/debug/app-debug.apk
On first launch it requests Bluetooth/Advertise/Connect + Location permissions,
then advertises as ILIAS-COLOR. Tap the phone screen to hide the status text.
Protocol: watch writes 3 bytes (R, G, B) to char 0000fee8-0000-1000-8000-00805f9b34fb
under service 0000fee7-0000-1000-8000-00805f9b34fb.
Install & test
- Phone: install
ColorCompanion-0.1.apk, open, grant permissions - Watch: side-load the .rpk via AstroBox, open — it scans, auto-connects, and casts RED on first contact
- Tap the watch disc to cycle colors
If the watch shows "BLE unavailable" or never finds the phone, the firmware doesn't expose BLE to quick apps — report the on-screen status text.
Releases: https://gitea.oimcloud.myaddr.tools/codex-bot/vela-colorcast (both the .rpk and the APK are attached to v0.1)