Skip to content

[Feature] Responsive mobile-friendly layout for the dashboard web UI #601

@b-client-vm

Description

@b-client-vm

Goal

Make the spacebot dashboard usable on phones and small tablets. The full experience (agents, workers, channels, OpenCode workbench) should be reachable from mobile, not a stripped-down view.

Library readiness

  • spaceui is mobile-ready. Built on Radix UI + Headless UI (both touch-aware out of the box), styled with Tailwind v4. Small upstream nits:
    • packages/ai/src/ChatComposer.tsx has hardcoded w-[210px] / w-[180px] / w-[76px] fragments that won't shrink
    • packages/primitives/src/Dialog.tsx has min-w-[300px] — can clip ≤320px
    • Resizable.tsx is desktop-only — consumers should swap to tabs/stacks below md rather than asking spaceui to change
  • OpenCode embed is mobile-aware but we're disabling it (see below)

OpenCode embed plan (load-bearing)

The vendored OpenCode SPA already has mobile support that interface/src/components/OpenCodeEmbed.tsx actively turns off. Tasks:

  • Stop force-hiding [data-component="sidebar-nav-mobile"] in the embed's override CSS (lines 268–271), OR replace it with a spacebot-owned mobile nav surface
  • Make the pre-seeded session: {width: 600} layout (line 234) conditional on viewport ≥ md, or drop it and let OpenCode's own defaults run
  • Verify the [data-component="prompt-input"] !important overrides don't clip on narrow viewports
  • Test Kobalte portal elements (dropdowns, dialogs, toasts) on touch — they render outside the Shadow DOM into document.body
  • Verify contain: "strict" on the embed host (line 374) doesn't break the mobile layout's height calculations

Important context: Tailwind md: classes inside the embed DO work despite the Shadow DOM because they resolve to viewport media queries.

Sidebar pattern

Replace the persistent side-by-side sidebars (Sidebar, ConversationsSidebar, WorkbenchSidebar, ConfigSidebar, SkillsSidebar) with a single drawer/sheet pattern below md. Open via a hamburger / nav button in a top bar. Persist open/closed state per #586.

Scope (routes needing a pass)

  • Dashboard shell
  • Agent routes: Chat, Channels, Config, Cortex, Cron, Detail, Ingest, Memories, Projects, Skills, Tasks, Workers
  • Workbench / OpenCode embed
  • ChannelDetail, GlobalTasks, Settings, Wiki, Overview

Likely approach

  • Mobile-first Tailwind breakpoints across existing components — no parallel mobile route tree
  • Agent detail tabs → horizontally scrollable tab bar or bottom nav below md
  • Workbench worker columns → tabs instead of side-by-side scroll on mobile (intersects with OpenCode embed exposure: chat→workbench link, resizable+full-width worker columns #596)
  • Touch targets ≥44px; no hover-only affordances on critical paths
  • Drawer-based primary nav with persistent state

Related

Out of scope

  • Native iOS/Android app
  • A separate mobile client consuming the API (rejected: OpenCode embed is Shadow-DOM-mounted same-origin via src/api/opencode_proxy.rs; re-implementing it elsewhere isn't worth it)

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions