Skip to content

Releases: Dylanmurzello/zed-android-port

Zdroid 0.3.2

05 Jun 21:34

Choose a tag to compare

Install

Download Zdroid-0.3.2.apk, open it, allow "install from unknown sources".

adb install -r Zdroid-0.3.2.apk for dev iteration. In-place upgrade over v0.2.x / v0.3.x.

What's new

  • Fixed Bluetooth mouse under pointer capture
  • Added vim mode on the soft keyboard
  • Fixed the soft-keyboard Enter key
  • Added Shift to the programming keys row
  • Added invert-scroll option for trackpad and wheel
  • Smoother terminal scrollback scrolling
  • Synced with upstream Zed
  • Fixed chroot terminal losing /proc after reboot (zdroid-spawnd v1.1.7)

Verification

  • APK SHA-256: 2425cb6e81ab7796c5a2b5e8eee5f3f3226dba87d9eca5d38e071bd04406b356
  • Built from commit 89e8070f15
  • versionCode 17, versionName "0.3.2"
  • Cert: same as v0.2.x / v0.3.x

Zdroid 0.3.1.1

20 May 21:16

Choose a tag to compare

Install

Download Zdroid-0.3.1.1.apk, open it, allow "install from unknown sources".

adb install -r Zdroid-0.3.1.1.apk for dev iteration. In-place upgrade over v0.2.x / v0.3.x.

Fixes

  • Gboard no longer auto-shows when a HW keyboard is connected. ImeHostView was returning a valid InputConnection on focus regardless of the user setting; Android starts the IME the moment that happens. Now returns null when either on_screen_keyboard = false or any device with KEYBOARD_TYPE_ALPHABETIC is in InputManager.inputDeviceIds (BT and USB both register here; Configuration.keyboard alone is unreliable on tablets).
  • Programming Keys Row no longer flashes on launch with the setting off. Kotlin field defaulted to true and lost the boot-time race against the Rust→Kotlin push.
  • Picking ExternalTermux no longer bricks the install. lib.rs now tests environment_root() writability and falls back to the bare app data dir instead of panicking on PermissionDenied.

Changes

  • All three Android Input toggles (Soft Keyboard, Programming Keys Row, Virtual Trackpad) default to off.
  • Restart-required prompt after an adapter switch is now an inline themed banner, not a native AlertDialog.

Verification

  • APK SHA-256: 8dfea934fbba1a419a4a472e725af70db11a35d82bc83168a34b8797dc8a3916
  • Built from commit 00cde3a76b
  • versionCode 12, versionName "0.3.1.1"
  • Cert: same as v0.2.x / v0.3.x

v0.3.1.1-diag.3 (fix candidate: Tab S11 captured-pointer)

22 May 03:00

Choose a tag to compare

Install

Download Zdroid-0.3.1.1-diag.3.apk, open it, allow "install from unknown sources". In-place upgrade over v0.3.1.1 / v0.3.1.1-diag.2. Pre-release; not promoted as Latest.

Convention

v0.3.1.1-diag.2 and v0.3.1.1-diag.3 serve different purposes:

  • diag.2 is the data-gathering build. Install it when I ask you to send a diagnostic dump. Probes-only, no behavior changes.
  • diag.3 is the fix-candidate build. Install it to test if a specific issue is fixed for you.

What this build fixes (candidate)

Tab S11 (Samsung SM-X7xx, One UI 8, Android 16, MediaTek) Bluetooth/USB mouse: cursor stays stuck after pairing, even though the system cursor correctly hides when Zdroid takes capture.

Root cause confirmed via the diag.2 probe dump: framework grants requestPointerCapture but no motion events reach Activity.onGenericMotionEvent. The Samsung legacy bubble-up path that works on Tab S9 / One UI 7 is not honored on One UI 8 + Android 16. Canonical AOSP routes captured events through View.dispatchCapturedPointerEvent on the focused View instead.

Fix: install View.OnCapturedPointerListener on the GameActivity SurfaceView. No focus-state manipulation (sidesteps the previous tint regression).

Use this if

You hit the "BT/USB mouse pairs but doesn't move the cursor" bug on Tab S11 or any non-Samsung Android 14+ device. Install diag.3, pair your mouse, the cursor should now follow motion. If it still doesn't, fall back to diag.2 and send me the dump.

Verification

  • APK SHA-256: 98b9c7c3f1285498e36d3e7697459f99f315fc4282c5a78344589c727937af91
  • Built from commit f614d8b23d (debug branch)
  • versionCode 16, versionName 0.3.1.1-diag.3
  • Cert: same as v0.2.x / v0.3.x (in-place upgrade compatible)
  • Tab S9 Ultra regression verified: 576 captured events still flow through the legacy Activity path with the new View listener installed alongside.

v0.3.1.1-diag.2 (diagnostic pre-release)

20 May 22:24

Choose a tag to compare

Install

Download Zdroid-0.3.1.1-diag.2.apk, open it, allow "install from unknown sources". In-place upgrade over v0.3.x. Pre-release; not promoted as Latest.

What this build does

v0.3.1.1 plus an in-app diagnostic exporter wired with layered input-event probes. Tap Zdroid menu > Export Diagnostic. A file is saved to Downloads/Zdroid/zdroid-diag-<stamp>.txt containing:

  • Device manufacturer, model, Android release, SDK level
  • Build fingerprint with carrier/region tail stripped
  • Every input device InputManager sees (vendor/product IDs, source bits with class names, keyboard type, isVirtual/isExternal). External devices (paired BT mouse, USB keyboard) have their literal name redacted to a prefix***suffix[hash] shape so reports are safe to post publicly; internal kernel devices (vendor=0 product=0) keep their driver name.
  • Rust-side env (PATH, SHELL, ZED_RELEASE_CHANNEL, etc.) plus a 2000-line ring buffer of every captured-pointer event seen at the Rust JNI sink (cap.disp lines).
  • Kotlin-side ring buffer covering Activity-level dispatchGenericMotionEvent arrivals (M/disp.gen), Activity-level onGenericMotionEvent arrivals (M/act.gen), and binary state transitions for window focus, pointer-capture grant/revoke, and Activity lifecycle (T/).

Use this if

You hit a bug like "Bluetooth or USB mouse pairs but the cursor doesn't move" on a non-Samsung device. Open Files app, navigate to Downloads/Zdroid/, attach the file to your GitHub issue. No PC + ADB required. The redaction means you do not need to scrub the dump before posting.

Verification

  • APK SHA-256: b9b33c60bcb41e0ca8cdde953cc6b99cfe7b24df428770c51a1f84b040232655
  • Built from commit e725613219 (debug branch)
  • versionCode 15, versionName 0.3.1.1-diag.2
  • Cert: same as v0.2.x / v0.3.x (in-place upgrade compatible)
  • Reference baseline (Tab S9 Ultra, One UI 8, Android 16): docs/diagnostic-baselines/tab-s9-ultra-oneui8-android16.txt on the debug branch

Zdroid 0.3.1

19 May 00:58

Choose a tag to compare

Install

Download Zdroid-0.3.1.apk below and open it on your Android device. Allow "install from unknown sources" when prompted, then tap the Zdroid icon.

For dev iteration: adb install -r Zdroid-0.3.1.apk.

In-place upgrade over v0.2.x and v0.3.0 (same signing cert). Auto-update from a working v0.3.0 build (the one currently on this releases page) will pull this version automatically. If your v0.3.0 install was the very first build that shipped on 2026-05-18, its updater has the FileProvider path bug and can't reach this release. Sideload Zdroid-0.3.1.apk once; subsequent updates will be auto.

What's new

  • Android Input onboarding section. The first-run onboarding now exposes a dedicated row for the three touch-input toggles (Soft Keyboard, Programming Keys Row, Virtual Trackpad), each rendered as an icon + label + on/off switch. Replaces the Zed AI agent setup row on Android, which surfaced sign-in buttons for a feature path the port doesn't support yet. The Settings panel still has the full Android Input page; this is purely a discoverability surface so new users see the touch-mode controls during setup.

Fixes

  • CursorSurfaceControl release race. setStyle(STYLE_ARROW) schedules an 80 ms debounced runnable to suppress the Arrow flicker that gpui's cursor_style emits during clicks. If pointer capture was lost during those 80 ms (settings window opening, focus change), MainActivity.onPointerCaptureChanged would call CursorSurfaceControl.release(), tearing down the underlying SurfaceControl. The 80 ms timer then fired its deferred move(), which threw IllegalStateException: Invalid usage after release of Surface(name=zdroid_cursor_overlay) and crashed the main thread. Repro was reliable on the S9 Ultra during onboarding navigation. Fix: a released flag now guards every public mutator (move, setStyle, setVisible) plus the debounced runnable body, and release() calls Handler.removeCallbacks on any pending Arrow transition before tearing the SurfaceControl down. Two layers of protection because a late JNI dispatch from gpui after release could still race the cancel.

  • Virtual trackpad cursor accumulated ghost travel past window edges. The Rust trackpad state machine in touch.rs updated self.cursor.x / self.cursor.y unbounded on every swipe; Kotlin's setTrackpadCursorPosition clamped the displayed sprite to [0, width-1] but Rust's internal state kept growing past width. Result: pushing the cursor past the right edge banked overshoot inside Rust, and you had to swipe back the exact same overshoot distance before the sprite visibly moved off the edge. Asymmetric visual look (sprite "vanishes" off the right but "hugs" the left) was the Arrow cursor's top-left hot-spot: at the right edge, the sprite body extends ~sprite_size past the screen and gets clipped by SurfaceFlinger; at the left edge, the body extends into the visible region so the cursor stays fully drawn. Fix: clamp self.cursor to [0, bounds] in logical pixels after every delta, with bounds piped through from AndroidWindowState.bounds.size via the dispatch wrappers.

Caveats

  • First install (or after a clean uninstall) needs you to grant "Install unknown apps" for Zdroid in Android Settings so the in-app updater can hand future APKs to the system installer.
  • Floating-mode Gboard support is unfinished: the programming keys row stays anchored at the screen bottom and won't follow a detached IME. Toggle android_input.programming_extras_row off if you use floating mode.
  • The "Please update Zed to Collaborate" badge in the title bar calls auto_update::check directly instead of dispatching the action, so it still surfaces upstream's package-manager prompt. Use the Zdroid menu's Check for Updates entry.

Verification

  • APK SHA-256: f18f6cb5434d18dae033034484dc44b97e09067e0b7b11d95c11ac3a4c9b5216
  • Signing cert SHA-256: 25:68:A2:A3:81:2D:8B:C3:A4:E8:E7:56:68:5C:5C:F7:25:40:EA:A2:94:37:F4:C1:25:8A:0C:81:73:BF:AB:4E (same as v0.2.x / v0.3.0)
  • Built from commit 2e11ed91ca
  • versionCode 11, versionName "0.3.1"
  • Bootstrap: bootstrap-2026.05.06-r2

Zdroid 0.3.0

18 May 22:34

Choose a tag to compare

Install

Download Zdroid-0.3.0.apk below and open it on your Android device. Allow "install from unknown sources" when prompted, then tap the Zdroid icon.

For dev iteration: adb install -r Zdroid-0.3.0.apk.

This is an in-place upgrade over v0.2.x, same signing cert and your existing data dir is preserved. Users on v0.1.x still need to uninstall before installing (different cert from the 0.1 line).

Notice for early v0.3.0 installs

The original v0.3.0 build (commit 4ce680200b) had a broken in-app updater: APKs were written to <filesDir>/cache/updater/ while the FileProvider XML declared <cache-path> (a different directory), so the system installer refused every hand-off with Failed to find configured root that contains .... The APK at this release has been re-uploaded with the fix (commit 3402b3174f). If you already had v0.3.0 installed, your in-app updater can't reach this build because of that same bug, so this is a one-time manual sideload. Future versions auto-update cleanly.

What's new

  • Multi-window IME. Settings, runtime picker, and any other spawned window now gets its own soft keyboard. The Rust side carries window_id end-to-end on every IME event so commits route to the right PlatformInputHandler; per-tick IME state moved from app-global to per-AndroidWindowState; the reconcile loop iterates every open window independently. Before this, focusing a text input in any non-main window did nothing.

  • Programming keys row. Termux-style row above the soft keyboard with Esc, Tab, Ctrl, Alt, and arrow keys. Ctrl and Alt are sticky modifiers (tap once for next key, double-tap to lock until untapped). Press-and-hold on arrows auto-repeats at the system key-repeat cadence so cursor navigation matches desktop. Ctrl+letter combos with soft-keyboard input intercept Gboard's commitText and re-fire as a real KeyEvent with the modifier, so Ctrl+C in the terminal sends ^C the same as a hardware keyboard. New android_input.programming_extras_row setting (default on, exposed in Android Input settings page).

  • Virtual trackpad mode. VNC-style touch trackpad: drag moves an on-screen cursor, tap clicks, two-finger tap is right-click, two-finger drag scrolls. Replaces direct touch while active. New tab-bar toggle (crosshair icon) and android_input.trackpad_mode setting (default off). Hold-to-drag for text selection works through the virtual mouse.

  • 120Hz fix. ANativeWindow_setFrameRate(0.0, DEFAULT) was previously interpreted as "I'm inactive" by Samsung's adaptive panel, dropping the display to 30Hz and producing visible stutter on scroll / resize. Switched to passing a positive target (120Hz). Compositor downgrades transparently on panels that can't deliver, so the value is safe across the device matrix. Measured: vsync_interval p50 went from 33ms to 8.33ms.

  • Pixel-smooth dock drag. Terminal panel resize splitter no longer ticks by row height during the drag. Snap-to-row policy now applies only on mouse-up so the gesture feels smooth, then the dock settles to the nearest row boundary at rest.

  • Cursor coherence. Hardware-pointer cursor sprite hides on direct touch / keyboard input and reappears on the next pointer activity (process-wide modality flag). Sprite is focus-gated so only the foreground window draws it (no more duplicate sprites with settings open). Style changes (IBeam, Hand, etc.) fan out to every Activity so a focused ExtraWindowActivity gets the same updates as the main window. Hot-spot offset is re-anchored on style swaps so the pointing tip stays put across Hand/IBeam transitions. The Arrow flicker that gpui's cursor_style produces during click events is debounced (80ms) so rapidly tapping a button no longer flashes the cursor shape.

Fixes

  • Auto-updater FileProvider path. Pre-fix the updater wrote downloaded APKs to <filesDir>/cache/updater/zdroid-X.Y.Z.apk but res/xml/updater_file_paths.xml maps <cache-path> to <cacheDir>/updater/ (a sibling directory, not a child of files). FileProvider.getUriForFile failed with "Failed to find configured root" and MainActivity.launchPackageInstaller returned false on every update attempt. Cache dir is now resolved via JNI through Context.getCacheDir(), matching the FileProvider declaration. One-time cleanup wipes the old wrong directory on first run so the 225 MB stale APK doesn't sit on disk.

  • Auto-updater asset-name candidate walk. Updater now tries Zdroid-X.Y.Z.apk first and falls back to app-release.apk on 404 so future asset-name conventions don't silently break the download. This release publishes the APK under both names for compatibility with older clients.

  • Settings window duplication. Two rapid OpenSettings dispatches both passed the existing-window check before either's cx.defer opened a window, spawning duplicates in Recents. Re-check inside the deferred closure too.

  • Pane toggle visibility on welcome screen. Bottom-dock terminal panel uses its own custom tab-bar render that bypassed the editor pane's default, so the keyboard/crosshair toggles never appeared before opening a project. Inlined the same buttons into TerminalPanel.

  • android_input.on_screen_keyboard gate during onboarding. Setting was previously mirrored from workspace::pane render only. With no Pane visible during onboarding the gate atomic stayed at its true default; toggling the setting off had no effect until you opened a project. Now mirrored via a SettingsStore observer so the gate stays current regardless of which window is up.

  • Trackpad icon clarity. Pane tab-bar trackpad-mode button was ArrowUpRight (read as expand). Swapped to Crosshair so the precision-pointer intent is unambiguous.

  • Cursor on direct touch. Desktop convention: hardware-pointer cursor hides while the user is touch-typing. Now does.

Caveats

  • First install (or after a clean uninstall) needs you to grant "Install unknown apps" for Zdroid in Android Settings so the in-app updater can hand future APKs to the system installer.
  • Floating-mode Gboard support is unfinished: the programming keys row stays anchored at the screen bottom and won't follow a detached IME. Toggle android_input.programming_extras_row off if you use floating mode.
  • The "Please update Zed to Collaborate" badge in the title bar calls auto_update::check directly instead of dispatching the action, so it still surfaces upstream's package-manager prompt. Use the Zdroid menu's Check for Updates entry.

Verification

  • APK SHA-256: 66d3103f7da27deb05d047fa426075d35366022ca64c2fe3b777c10b1c7c1492
  • Signing cert SHA-256: 25:68:A2:A3:81:2D:8B:C3:A4:E8:E7:56:68:5C:5C:F7:25:40:EA:A2:94:37:F4:C1:25:8A:0C:81:73:BF:AB:4E (same as v0.2.x)
  • Built from commit 3402b3174f
  • versionCode 10, versionName "0.3.0"
  • Bootstrap: bootstrap-2026.05.06-r2

Zdroid 0.2.3

15 May 13:42

Choose a tag to compare

Install

Download Zdroid-0.2.3.apk below and open it on your Android device. Allow "install from unknown sources" when prompted, then tap the Zdroid icon.

For dev iteration: adb install -r Zdroid-0.2.3.apk.

This is an in-place upgrade over v0.2.2, same signing cert and your existing data dir is preserved.

Fixes

  • Zdroid menu "Check for Updates" actually checks for updates. v0.2.1 shipped an in-app updater (GitHub Releases fetch + APK download + system installer handoff), but a gpui action-dispatch ordering bug meant the menu entry was being intercepted by upstream Zed's auto-update handler first. With ZED_UPDATE_EXPLANATION set (which Zdroid uses to suppress upstream's polling self-installer because Android distribution is APK reinstall, not in-place binary swap), upstream's handler shows a "Zed was installed via a package manager" prompt and stops. Bubble-phase action dispatch auto-stops after the first handler, so our updater handler never ran. Fix is the same dispatch-ordering pattern that landed for the OpenSettings deep-link in v0.2.2: register our handler ahead of auto_update::init so it lands at workspace_actions[0] and runs first.

Caveats

  • First install (or after a clean uninstall) needs you to grant "Install unknown apps" for Zdroid in Android Settings so the in-app updater can hand future APKs to the system installer.
  • Upgrading from v0.1.x or earlier needs an uninstall first because of signing-cert changes between the 0.1.x line and 0.2.x.
  • The "Please update Zed to Collaborate" badge in the title bar (visible when you sign in for collab and your client is out of date) calls auto_update::check directly instead of dispatching the action, so it still surfaces upstream's package-manager prompt. Use the Zdroid menu's Check for Updates entry for the working flow.

Verification

  • APK SHA-256: a3b979c01097aede225fd8916ed7216a49758af8f93299917e96c2e54c74b718
  • Signing cert SHA-256: 25:68:A2:A3:81:2D:8B:C3:A4:E8:E7:56:68:5C:5C:F7:25:40:EA:A2:94:37:F4:C1:25:8A:0C:81:73:BF:AB:4E
  • Built from commit 24812df05f
  • Bootstrap: bootstrap-2026.05.06-r2

Zdroid 0.2.2

15 May 12:58

Choose a tag to compare

Install

Download Zdroid-0.2.2.apk below and open it on your Android device. Allow "install from unknown sources" when prompted, then tap the Zdroid icon.

For dev iteration: adb install -r Zdroid-0.2.2.apk.

This is an in-place upgrade over v0.2.1, same signing cert and your existing data dir is preserved.

Fixes

  • "Edit Settings" on terminal failure now opens the runtime picker. When the Android runtime is not yet configured, opening the integrated terminal surfaces "Failed to spawn terminal" with an Edit Settings button. That button used to dispatch the generic OpenSettings action and drop the user into settings.json with no obvious way forward. It now routes straight to the runtime picker when ~/usr/etc/zd-runtime.toml is missing, so the configure-a-runtime path is one tap away. After a runtime is configured, the button falls through to the normal settings editor.
  • Runtime picker window opens tall enough for all three adapter cards. Default height was clipping the Bootstrap card on first open, forcing the user to drag-resize before they could pick it. Default is now 800 DP (up from 560) with a 560 DP minimum so the three cards always fit.

Caveats

  • First install (or after a clean uninstall) needs you to grant "Install unknown apps" for Zdroid in Android Settings so the in-app updater can hand future APKs to the system installer.
  • Upgrading from v0.1.x or earlier needs an uninstall first because of signing-cert changes between the 0.1.x line and 0.2.x.

Verification

  • APK SHA-256: 1dcb0a0ddad2f44e334ae0aca22ae85f02987f07aaa01fd072a96324178f9d72
  • Signing cert SHA-256: 25:68:A2:A3:81:2D:8B:C3:A4:E8:E7:56:68:5C:5C:F7:25:40:EA:A2:94:37:F4:C1:25:8A:0C:81:73:BF:AB:4E
  • Built from commit 2eba0724c3
  • Bootstrap: bootstrap-2026.05.06-r2

Zdroid 0.2.1

15 May 11:48

Choose a tag to compare

Highlights

In-app updater

Zdroid menu now has Check for Updates that pulls newer releases from GitHub and hands them to Android's system installer. One menu click runs through: github.com/Dylanmurzello/zed-android-port/releases/latest → version compare → user prompt → APK download to app cache → ACTION_VIEW via FileProvider so the system package installer takes over. Works with the signed release.keystore APKs, so reinstalls upgrade in place. Adds the REQUEST_INSTALL_PACKAGES permission; first run will need you to grant "Install unknown apps" for Zdroid in Android Settings.

Settings/secondary windows no longer tint

ExtraWindowActivity (the activity that hosts Settings, secondary editor windows) was setting its SurfaceHolder pixel format to RGBA_8888, which flipped Android's compositor into alpha-aware mode and let anti-aliased text edges + scrim regions bleed the windowBackground through as a faint white tint. Switching to PixelFormat.OPAQUE makes the compositor treat the surface as opaque from creation onward, so settings/other secondary windows render with the same indigo as the main editor.

Cursor reappears after SAF picker

The hardware-composited cursor SurfaceControl could get orphaned when another activity (SAF picker from "Open Project" in onboarding, etc.) destroyed and recreated MainActivity's surface. Now release + rebuild the overlay on every onPointerCaptureChanged regain so it always anchors to the current SurfaceView.

Zdroid menu Quit closes the app

Quit was wired into the menu but no handler responded. Added the action handler in lib.rs and made AndroidPlatform::quit actually exit the process so MainActivity.onDestroy runs and the OS returns to the launcher.

Termux subprocess HOME parity

Zed-spawned subprocesses (git, LSPs) were inheriting HOME=/data/data/com.zdroid/files (Termux ROOTFS) while integrated terminal had HOME=/data/data/com.zdroid/files/home (Termux HOME). Result: git commit didn't see ~/.gitconfig even though terminal git did. Aligned the Zed-process HOME with what Termux's profile.d sets for shells.

Install

Download app-release.apk below. Signed; reinstalls upgrade in place. If you're upgrading from v0.1.x or earlier, you may need to uninstall first because of signing-key changes.

Zdroid 0.2.0

15 May 09:24

Choose a tag to compare

Highlights

Animated cold-start splash

The launcher → editor transition is no longer a "brick then upper-punch". An animated Zdroid sigil (counter-rotating ripple rings + breathing orb) covers the entire boot path from app tap through gpui's first paint, fading out into the editor with a ripple-dissipates exit. Built as a sibling-View overlay above the GameActivity SurfaceView; safe against the prior cursor white-tint regression because the wgpu surface now clears to opaque brand indigo on every frame.

Hardware-composited cursor via SurfaceControl

Replaces the disabled View-based cursor with a child SurfaceControl of the editor SurfaceView. SurfaceFlinger composites the sprite over the main surface via HWC2 — same hardware overlay path the OS uses for the system pointer on devices with a cursor plane. Cursor moves are Transaction.setPosition().apply() with zero gpui paint and zero wgpu work per move. API 29+ only; older devices keep trackpad gestures without a visible sprite.

Trackpad gestures

  • libinput-style drag-lock for tap-tap-drag
  • Hold-and-drag selection cursor follows the dragging finger
  • Multi-window capture parity — spawned ExtraWindowActivity instances inherit the same gesture state machine
  • Touchpad ACTION_BUTTON_PRESS firmware noise filtered out
  • Click-storm fixed during sustained drags
  • AXIS_RELATIVE_X/AXIS_RELATIVE_Y historical samples summed so fast finger motion doesn't lose ~80% of its travel

Runtime adapter command-bridge fix

The env-root → zd-exec rewrite in util::command::new_command was unconditional, breaking every absolute-path subprocess spawn for bootstrap-mode users (rust-analyzer, gopls, bash, every LSP). Now gated on RuntimeProvider::needs_command_bridge(): chroot adapter opts in, bootstrap and external-Termux let execve run the binary directly. Apt-installed LSPs work without any zd-exec hop.

External-storage CWD fallback

Command::current_dir on Android rewrites /storage/emulated/0/* and other FUSE-emulated prefixes to $HOME to avoid the chdir-ENOENT-in-forked-subprocess gate. LSP servers still receive the real project path via workspaceFolders in LSP initialize so rust-analyzer / pyright / etc. locate the project root correctly.

Vim mode wiring

VimModeSetting (and HelixModeSetting) now correctly load VIM_KEYMAP_PATH on init and on settings change, with a SettingsStore observer for live reload.

Misc

  • Android rust-analyzer asset name points at upstream unknown-linux-gnu (was malformed unknown-linux).
  • WgpuRenderer::set_clear_color lets embedders override the main-pass clear (default stays transparent for desktop compositors).
  • Gitignored the Kotlin incremental cache.

Install

Download app-release.apk below. APK is signed; reinstalls upgrade in place. Tab S9 Ultra / Android 14 is the primary tested target.