# muxplex

Web-based tmux session dashboard and terminal multiplexer. Pure vanilla JS frontend (no frameworks, no build step), FastAPI backend, xterm.js terminals via ttyd WebSocket proxy.

## Repository

- **Upstream**: https://github.com/bkrabach/muxplex
- **Fork (primary working repo)**: git@git.ampbox.io:ken/muxplex.git
- **Branch strategy**: Work on `main` directly in the fork. PR upstream when ready.

## Architecture

- `muxplex/frontend/app.js` (~4,600 lines) -- dashboard, sidebar, settings, views, mobile UX
- `muxplex/frontend/terminal.js` (~700 lines) -- xterm.js terminal, WebSocket, mobile toolbar
- `muxplex/frontend/style.css` (~2,600 lines) -- dark theme, responsive breakpoints
- `muxplex/frontend/index.html` -- SPA shell
- `muxplex/frontend/vendor/` -- vendored xterm.js + addons (fit, search, web-links, image)
- `muxplex/main.py` -- FastAPI app, API endpoints, WebSocket proxy, poll loop
- `muxplex/sessions.py` -- tmux session enumeration, caching, snapshots
- `muxplex/ttyd.py` -- ttyd process lifecycle management
- `muxplex/tests/` -- 1300+ tests (Python + frontend structure/behavior tests)

## Key patterns

- No build step. JS/CSS served as-is with version-busting query suffixes.
- Icons are inline SVGs (replaced unicode entities), stored in `_icons` object in app.js.
- Mobile detection: `MOBILE_THRESHOLD = 600`, `isMobile()` function.
- Touch devices get a bottom toolbar with Ctrl/Alt modifier toggles.
- xterm.js handles touch scrolling natively -- do NOT add custom touch scroll handlers.
- Session names can contain spaces -- always use `shlex.quote()` when interpolating into shell commands.
- The running service is an editable install from this directory: `systemctl --user restart muxplex` to apply changes.

## Testing

```bash
.venv/bin/python -m pytest muxplex/tests/ -x -q --timeout=30
```

The CSS test suite enforces that `@media (max-width: 959px)` is the last `@media` block in style.css. Place new `@media` blocks above it.

---

# UX Improvement Roadmap

Prioritized improvements for a power user on desktop + Android phone + Android tablet.

## P0 -- High Impact (Grid "catches you off guard")

### Search/filter bar on dashboard grid
With 10+ sessions, there's no way to quickly find one. Add a sticky search input at the top of the grid that filters tiles by name as you type. Critical on mobile where the list view requires scrolling through all sessions linearly.

### Visual hierarchy for tiles
All tiles look identical -- no distinction between a session used 30 seconds ago and one idle for 3 days. Add subtle visual cues: accent border on recently active sessions, dimmed styling for idle ones. Give the user's eyes an anchor point.

### Readable tile previews
Terminal snapshot text is 11px in a 300px tile -- it's decoration, not information. Either make it large enough to read (fewer lines, bigger font), or add a readable "last command" / "working directory" summary line beneath the session name.

### Default session / quick-resume
Auto-open the last-used or default session on page load. The `default_session` setting exists but may not be fully wired. At minimum, put a prominent "Resume" action for the most recently used session.

## P1 -- High Impact (Mobile Phone)

### Tap-to-open too easy to trigger accidentally
On mobile list view, any tap anywhere on the tile opens the terminal. Need to distinguish scroll gestures from taps, and make the tap target the header area rather than the entire tile body.

### Session pill is too subtle
In expanded terminal view on mobile, the floating pill (75% opacity, 13px, bottom-right) is the only session switcher. Make it more prominent -- persistent thin bar at bottom, or a swipe-to-switch gesture.

### Swipe gestures
- Swipe from left edge to open sidebar (Android convention)
- Swipe down on bottom sheet to dismiss
- Swipe left/right on session pill to switch sessions

### Scroll-to-bottom indicator
When scrolled up in the terminal buffer, there's no visual cue and no quick way to jump back to live output. Add a floating "Jump to bottom" button that appears when scrolled up.

## P2 -- Medium Impact (Tablet)

### Tablet grid wastes space
At 600-899px (tablet portrait), grid collapses to a single column with 200px tiles. Too conservative. Use a two-column grid with shorter tiles to show more sessions.

### Compact sidebar for tablet
Tablets have room for a mini session list alongside the terminal. Add a compact sidebar mode (just session names, no preview tiles) that works as a side panel rather than a full overlay.

## P3 -- Medium Impact (General UX)

### Keyboard shortcut cheat sheet
Shortcuts exist (`,` settings, `` ` `` view dropdown, `1-9` views, `Escape` close) but are undiscoverable. Add `?` shortcut to show a cheat sheet overlay.

### Quick session creation
The current flow requires typing a name. Add "Quick new" that auto-generates a name (e.g. `session-4`) and opens immediately. Name prompt becomes optional.

### Inline session rename
No rename exists today -- typo means kill and recreate. Add long-press (mobile) / double-click (desktop) on tile header to rename. Backend: `tmux rename-session`.

### Pull-to-refresh on mobile dashboard
The 2s poll handles updates, but users expect pull-to-refresh on mobile. Even a triggered immediate poll gives a sense of control.

### Confirmation before killing sessions
Verify the delete confirmation step is present in the mobile bottom sheet (not just desktop flyout). Accidentally killing a session with running work is catastrophic.

## P4 -- Polish

### Fix tile metadata fade on hover
Timestamp and device badge fade to transparent on hover -- exactly when you're looking at it. Invert: show more detail on hover, not less.

### Reduce grid flicker on poll
The 2s poll rebuilds DOM for all tiles. Diff the DOM instead (only update changed tiles) to eliminate subtle flicker.

### Long-press context menu on mobile tiles
The kebab button is small on mobile. Long-press on the tile itself should open the same action menu -- standard Android convention.

### Better toast positioning on mobile
Toast at `bottom: 80px` may be occluded by the mobile toolbar or FAB. Position above any floating elements.

## Future Ideas

- **Session pinning** -- pin 1-3 sessions to always show at top of grid
- **Session tags/colors** -- color-code sessions by project
- **Command palette** -- `Ctrl+K` / `Cmd+K` to search sessions, switch views, open settings
- **Notification badges on tiles** -- "3 new lines" counter on idle tiles
- **Multi-select on grid** -- select multiple sessions for bulk kill or bulk-add to view
- **Dim vs deep dark toggle** -- for outdoor tablet use in bright light
