Skip to content

fix(web): make the inline rail resizable via touch and stylus - #4781

Closed
btli wants to merge 11 commits into
omnigent-ai:mainfrom
btli:pollux/touch-p0-resize-inline
Closed

fix(web): make the inline rail resizable via touch and stylus#4781
btli wants to merge 11 commits into
omnigent-ai:mainfrom
btli:pollux/touch-p0-resize-inline

Conversation

@btli

@btli btli commented Aug 14, 2026

Copy link
Copy Markdown
Contributor

Part of #4790

Related issue

Implements TR-6 / TR-7 / TR-9 of the touch interaction spec (the touch-interaction spec (see #4790)) for the always-visible inline rail. No standalone issue to close.

Summary

The right-rail resize handle only listened for mouse events on a 1px target, so touch and stylus drags lost the pointer as soon as they left the handle (or crossed the HTML-preview iframe).

  • Migrate useResizableInlinePanel from mouse to pointer events: onPointerDown + setPointerCapture, with move/up on the captured element.
  • Abort cleanly on pointercancel and lostpointercapture (last applied size, no persist, listeners gone). First pointer wins until that drag ends. Unmount still drops the iframe overlay.
  • Touch affordances live only on returned handleProps: touch-action: none plus 20px content-box padding each side (44px hit target on the existing w-1 handle). WorkspacePanel / AppShell still spread handleProps unchanged. Width gating is untouched.

ELI5

The right-rail divider still looks like a thin line. The invisible grab area around it is now finger-sized, and once you start dragging, that finger owns the resize until you lift it (or the browser cancels).

sequenceDiagram
  participant Finger
  participant Handle
  Finger->>Handle: pointerdown
  Handle->>Handle: setPointerCapture
  loop while captured
    Finger->>Handle: pointermove (even off-handle / over iframe)
    Handle->>Handle: update live width
  end
  alt pointerup
    Finger->>Handle: persist width
  else pointercancel / lostpointercapture
    Finger->>Handle: abort, keep last applied, no persist
  end
Loading

Test Plan

  • npx pnpm install --frozen-lockfile at worktree root (Node 22)
  • web/node_modules/.bin/vitest run src/hooks/useResizableInlinePanel.test.tsx — 22 passed
  • web/node_modules/.bin/vitest run src/shell/WorkspacePanel.test.tsx — 41 passed
  • web/node_modules/.bin/vitest run src/shell/AppShell.test.tsx — 102 passed
  • web/node_modules/.bin/tsc -b — clean
  • Mutation-check: revert the hook to mouse events; the new capture / pointercancel / capture-loss / first-pointer-wins / affordance tests fail; restore and they pass
  • Manual: on a touch or stylus device, drag the right-rail divider, continue the drag off the handle and over the HTML preview, lift — width should follow and persist. A second finger during the drag should be ignored. Browser gesture cancel should stop the drag without a stuck overlay.

Demo

Inline seam touch-drag validated live — foldable, tablet. Adjacent transcript scroll never resizes; gutter clears the scrollbar thumb band.

Type of change

  • Bug fix
  • Feature
  • UI / frontend change
  • Refactor / chore
  • Docs
  • Test / CI
  • Breaking change

Test coverage

  • Unit tests added / updated
  • Integration tests added / updated
  • E2E tests added / updated
  • Manual verification completed
  • Existing tests cover this change
  • Not applicable

Coverage notes

Hook unit tests cover pointer capture, pointercancel abort, lostpointercapture abort, first-pointer-wins, 44px hit-target style, iframe overlay mount/unmount, and existing keyboard / reserved-width / persistence behavior. End-to-end touch demo is deferred to the consolidated validation phase.

Changelog

The right rail can be resized with touch and stylus, not just a mouse.

The 1px handle only listened for mouse events, so touch/stylus drags
lost the pointer as soon as they left the handle. Pointer capture plus
a 44px hit target on handleProps keep the stream without changing
consumers.

Signed-off-by: Bryan Li <bryan.li@gmail.com>
@github-actions github-actions Bot added the size/L Pull request size: L label Aug 14, 2026
btli added 2 commits August 13, 2026 19:18
Signed-off-by: Bryan Li <bryan.li@gmail.com>
Signed-off-by: Bryan Li <bryan.li@gmail.com>
github-actions Bot pushed a commit to btli/omnigent that referenced this pull request Aug 14, 2026
Signed-off-by: Bryan Li <bryan.li@gmail.com>
@github-actions github-actions Bot added size/XL Pull request size: XL and removed size/L Pull request size: L labels Aug 14, 2026
github-actions Bot pushed a commit to btli/omnigent that referenced this pull request Aug 14, 2026
github-actions Bot pushed a commit to btli/omnigent that referenced this pull request Aug 14, 2026
github-actions Bot pushed a commit to btli/omnigent that referenced this pull request Aug 14, 2026
btli pushed a commit to btli/omnigent that referenced this pull request Aug 14, 2026
Signed-off-by: Bryan Li <bryan.li@gmail.com>
btli pushed a commit to btli/omnigent that referenced this pull request Aug 14, 2026
btli added 2 commits August 14, 2026 04:35
Signed-off-by: Bryan Li <bryan.li@gmail.com>
Signed-off-by: Bryan Li <bryan.li@gmail.com>
Signed-off-by: Bryan Li <bryan.li@gmail.com>
@btli

btli commented Aug 14, 2026

Copy link
Copy Markdown
Contributor Author

Tribunal attestation (automated multi-engine review): CLEAN

Both blocking engines (codex + claude_code) attested head df3cf67b2. 3 review rounds on the production change plus re-attestations for the snapshot-baseline refresh and a test-only viewport pin (fixes a latent cross-PR interaction with #4785 found by integration validation: the AppShell separator test's 375px default fixture now correctly renders mobile layout under the new capability semantics, so the test pins 1024px). All findings fixed, none dismissed. Full record in .pollux/review-ledger.md.

btli added 3 commits August 14, 2026 09:00
Signed-off-by: Bryan Li <bryan.li@gmail.com>
Signed-off-by: Bryan Li <bryan.li@gmail.com>
Signed-off-by: Bryan Li <bryan.li@gmail.com>
@btli
btli marked this pull request as draft August 15, 2026 14:15
@btli btli closed this Aug 15, 2026
@github-actions

Copy link
Copy Markdown
Contributor

Closed. If you want to pick this back up, comment /reopen. GitHub only lets maintainers press the Reopen button, so this command does it for you. It needs the source branch to still exist.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

size/XL Pull request size: XL waiting-for-review

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants