Skip to content

Ship tiling pane redesign#10

Merged
max4c merged 26 commits intomainfrom
dev
Apr 3, 2026
Merged

Ship tiling pane redesign#10
max4c merged 26 commits intomainfrom
dev

Conversation

@max4c
Copy link
Copy Markdown
Owner

@max4c max4c commented Apr 3, 2026

Summary

  • Every pane redesigned from full-window views to tile-native (400-600px)
  • Mail: message list + filter tabs, no sidebar/preview
  • Calendar: width-adaptive day/week, transcript badges on events with meeting notes
  • Meetings: quick-draw recorder with notes/transcript toggle
  • Home: launcher with pinned databases, stripped mini calendar/inbox
  • Chat: suggestion chips empty state, no centered logo void
  • Terminal: added to sidebar navigation
  • Keyboard shortcut overlay (⌘/), layout auto-save indicator, resize grip dots, pane drag-to-swap
  • Design spec: design/pane-tiles.html (visual) + design/interactions.html (interaction model)

Test plan

  • Build passes: swift build
  • Mail pane shows filter tabs (All/Unread/Starred/Sent), no sidebar rail
  • Calendar defaults to day view at narrow widths, week view when wide
  • Calendar events with linked pages show waveform badge
  • Meetings pane shows "Start recording" button, not a browsable list
  • During recording: Notes/Transcript toggle works, waveform animates
  • Terminal appears in sidebar, clicking opens terminal pane
  • ⌘/ opens keyboard shortcut overlay with Workflows section
  • Resize dividers show grip dots on hover
  • Drag ☰ handle from one pane onto another swaps their content
  • "Saved" indicator appears briefly in tab bar after layout changes
  • Home pane shows pinned databases, no mini calendar/inbox

🤖 Generated with Claude Code

Every pane redesigned from full-window views to tile-native:

- Mail: stripped three-column layout to message list + filter tabs (All/Unread/Starred/Sent)
- Calendar: width-adaptive day/week switching (day at ≤700px), transcript badges on events
- Meetings: rewritten as quick-draw recorder with notes/transcript toggle, saves via MeetingNoteService
- Home: stripped mini calendar/inbox widgets, kept launcher + pinned databases
- Chat: replaced centered empty state with left-aligned suggestion chips
- Terminal: added to sidebar navigation

Pane system improvements:
- Keyboard shortcut overlay (⌘/) with primary/secondary sections + composed workflows
- Layout auto-save indicator ("Saved" dot in tab bar, 1.5s fade)
- Resize divider: 2px idle line + grip dots on hover
- Drag-to-swap: ☰ handle in hover bar, drop target highlight, swapPaneContents()

Design assets:
- design/pane-tiles.html — full workspace mockup (Comms layout, Meetings recorder, Home)
- design/interactions.html — interaction spec (shortcuts, operations, in-pane nav, roster, persistence, open questions)

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Copy link
Copy Markdown

@chatgpt-codex-connector chatgpt-codex-connector bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 20cf4af8c6

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".


var mailbox: MailMailbox {
switch self {
case .all, .unread: return .inbox
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Apply unread filter instead of reusing inbox mailbox

The new Unread tab is wired to MailMailbox.inbox, so selecting it loads the same thread set as All and still includes read messages. In this view, MailService.visibleThreads only reflects the selected mailbox, so this mapping makes the unread filter non-functional for users trying to triage unread mail.

Useful? React with 👍 / 👎.

Comment on lines +274 to +275
isRecording = true
appState.isRecording = true
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Set recording state only after capture actually starts

startRecording() marks the UI/global state as recording before TranscriptionService.startRecording() succeeds. If mic/speech permission is denied (or startup fails), the service never enters recording, but the pane still shows active recording and appState.isRecording stays true until the user manually presses Stop, which is a misleading broken state transition.

Useful? React with 👍 / 👎.

max4c and others added 25 commits April 3, 2026 00:43
- Add paste(_:) responder to GhosttySurfaceHostView for Cmd+V support
- Implement read_clipboard_cb and confirm_read_clipboard_cb with active
  surface tracking via _activeSurface global
- Load user's Ghostty config (~/.config/ghostty/config) via
  ghostty_config_load_default_files before app init
- Pass empty args to ghostty_init(0, nil) to prevent libghostty from
  manipulating the parent terminal's TTY state

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Removed the 3px left accent border. Now uses rounded gray background
with subtle stroke border matching the outline/TOC block exactly.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Removed circle bullets from TOC entries. Now renders as plain grey
text links with indentation by heading level. Click still scrolls
to the heading.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Removed the per-row gripDotsColumn from TableBlockView — BlockCellView
already provides the block-level drag handle. Table grid is now flush
with the editor content area. Row reorder still available via context
menu.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Changed kebab from Text+onTapGesture to a proper Button for tap
priority over the row gesture. Increased hit area to 28x28pt. Edit
popover now appears to the side (arrowEdge: .trailing) instead of
overlapping the options list.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Renamed "Ask AI" to "Chat" in menu bar, sidebar panel header, slash
  commands, command palette, and keyboard shortcut overlay
- Removed X close button from full-page NotesChatView
- Cmd+I now toggles the sidebar chat panel instead of opening full page

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Added parseMention to AttributedStringConverter that detects @[[...]]
patterns and renders the page name with accent color and underline,
hiding the @[[ ]] delimiters. Round-trips correctly via markdownSourceKey.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…saction

Previous approaches using @State + .onChange failed because the state
change was swallowed during the command palette dismissal transaction.
Now calls navigateToEntryInPane via DispatchQueue.main.async, which
defers to the next run loop iteration after the palette is dismissed.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Uses .task with async loop — SwiftUI cancels automatically when the
mail pane disappears. Only polls when Google is connected.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Removed minHeight: geo.size.height from the table frame modifier.
The table now shrinks to just group headers when all groups are
collapsed, instead of always filling the full container height.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Added toggleBlockExpanded in BlockDocument for Cmd+Shift+Enter to
  expand/collapse toggle and headingToggle blocks
- Added autoNestIntoHeadingToggle that absorbs subsequent sibling
  blocks into a heading toggle until hitting an equal-or-larger heading
- Added keyboard shortcut in BlockTextView (Cmd+Shift+Return)

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Callout: normal weight text instead of semibold
- TOC: underline heading links
- Gateway tab renamed to "Home"
- Slash command: "Ask AI" kept separate from "Chat" sidebar label
- Cmd+I: opens full chat window, not sidebar panel
- Meeting block: more bottom padding in notes section
- Grouped table: 40pt bottom padding so "+ New page" isn't clipped
- Regenerated xcodeproj via xcodegen

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
… table fix

- TOC: strip markdown formatting from heading text (fixes **bold** showing raw)
- Cmd+I: back to toggling sidebar panel (sidebar Chat click opens full window)
- Tab icons: Home (house), Mail (envelope), Meetings (waveform) now show in tab bar
- Grouped table: removed oversized 40pt bottom padding, removed maxHeight: .infinity
  that was causing the giant blank space

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…b, grouped table fix

- Sidebar "Chat" click now posts .openFullChat → opens full chat window
- Cmd+I stays as sidebar panel toggle (separate .openAIPanel notification)
- Chat full-page view now shows "Chat" with icon in the tab bar
- TOC: skip H1 page title, use relative indentation from shallowest heading
- Grouped table: restored maxHeight: .infinity to prevent "+ New page" clipping
- Added TabKind.chat for proper chat pane support

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…vel, fix grouped table

- Chat full window: tab bar now renders above NotesChatView showing
  "Chat" with bubble icon, matching other full-page views
- TOC: indent by block tree nesting depth, not heading level number.
  Top-level H2s are all flush; only headings inside toggles/callouts
  get indented. H1 page title still excluded.
- Grouped table: removed GeometryReader wrapper that forced full-height
  layout. ScrollView now sizes to content naturally — no blank space
  when groups are collapsed, no clipping of "+ New page".

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- TOC links now highlight on hover (grey → primary color)
- Grouped table: removed maxHeight: .infinity from the PARENT frame
  (line 85) that was forcing the entire viewContent to fill available
  space. The ScrollView now sizes to content naturally. This was the
  actual source of the blank space — the inner table frame was already
  fixed in prior commits but the parent was still expanding.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Grouped table blank space fix (attempt 5 — structural change):
- Wrapped header + tabs + divider + table in a single outer ScrollView(.vertical)
- Table's own ScrollView is now horizontal-only
- Content naturally hugs its height — no blank space when groups are collapsed
- Header scrolls with content instead of being pinned (trade-off)

TOC/callout/code block coloring:
- Block row background color now skips blocks that have their own container
  (outline, callout, codeBlock) via blockHasOwnContainer flag
- Setting a block background color on these blocks no longer colors the
  entire row — only the inner container is affected

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Title is hidden in the titlebar (titleVisibility = .hidden) but macOS
still shows window.title in Mission Control, making it easy to find
Bugbook among other windows.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Prevents "+ New page" from being clipped by the pane bottom edge.
The padding is inside the ScrollView content so it scrolls with
the table and doesn't create permanent blank space.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
OutlineBlockView now accepts the block and uses its backgroundColor
when set, falling back to the default grey. The blockHasOwnContainer
flag in BlockCellView prevents the row-level background from applying,
while the container itself now picks up the color.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Pinned header/tabs/divider at top (not scrollable). viewContent gets
maxHeight: .infinity to fill remaining pane space. Table uses its own
[horizontal, vertical] ScrollView within that space. Short content
still shows empty scroll area but it reads as an empty table area
rather than a broken layout gap.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- MailHTMLView: guard updateNSView against redundant loadHTMLString
  calls — only reload when content actually changes (prevents flash
  and wasted work on every SwiftUI state change)
- Terminal clipboard callbacks: dispatch to main thread when not
  already on it — NSPasteboard and _activeSurface access must happen
  on main to avoid data races

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@max4c max4c merged commit c1039af into main Apr 3, 2026
1 check failed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant