From 029d933892bbcc7c061aff999da351e83422d37c Mon Sep 17 00:00:00 2001 From: GCWing Date: Fri, 18 Sep 2026 11:41:39 +0800 Subject: [PATCH 1/2] refactor(ui): align interactive surfaces with shared contracts --- design-system/packages/ui/README.md | 18 +- .../src/components/ActionCard/ActionCard.tsx | 2 +- .../src/components/ActionItem/ActionItem.tsx | 2 +- .../components/ActivityItem/ActivityItem.tsx | 2 +- .../ui/src/components/Avatar/Avatar.tsx | 2 +- .../ui/src/components/Button/Button.tsx | 4 +- .../ui/src/components/Combobox/Combobox.tsx | 4 +- .../ConfirmDialog/ConfirmDialog.tsx | 1 + .../ui/src/components/Empty/Empty.tsx | 1 + .../src/components/IconButton/IconButton.tsx | 2 +- .../ui/src/components/Input/Input.tsx | 4 +- .../ui/src/components/KeyHint/KeyHint.tsx | 2 +- .../LauncherButton/LauncherButton.tsx | 2 +- .../ui/src/components/Listbox/Listbox.tsx | 4 +- .../ui/src/components/Menu/MenuPopover.tsx | 2 +- .../components/SearchField/SearchField.tsx | 2 +- .../SegmentedControl/SegmentedControl.tsx | 2 +- .../ui/src/components/Select/Select.tsx | 4 +- .../src/components/StatusPill/StatusPill.tsx | 2 +- .../ui/src/components/TabGroup/TabGroup.tsx | 2 +- .../VoiceCallPanel/VoiceCallPanel.meta.ts | 3 + .../VoiceCallPanel/VoiceCallPanel.module.css | 26 + .../VoiceCallPanel/VoiceCallTranscript.tsx | 5 +- design-system/packages/ui/src/index.ts | 3 + .../packages/ui/src/overlay/usePresence.ts | 19 +- .../packages/ui/src/styles/layers.css | 12 + .../packages/ui/tests/icon-slots.test.mjs | 58 + .../packages/ui/tests/overlay-kernel.test.mjs | 2 + .../review-platform/ReviewPlatformPanel.scss | 1647 ++--------------- .../ReviewPlatformPanel.test.tsx | 156 +- .../ReviewPlatformPanel.trust.test.tsx | 12 - .../review-platform/ReviewPlatformPanel.tsx | 1400 +++++++------- .../panels/review-platform/appearance.ts | 12 +- .../src/app/layout/FloatingMiniChat.scss | 37 +- .../src/app/layout/FloatingMiniChat.tsx | 2 +- .../layout/floatingMiniChatActivity.test.ts | 2 + src/web-ui/src/app/styles/motion.scss | 5 +- src/web-ui/src/app/styles/motion.test.ts | 38 + .../ChatInputWorkspaceStrip.test.tsx | 2 +- .../components/ChatInputWorkspaceStrip.tsx | 9 +- .../modern/FLOWCHAT_VIRTUALIZATION.md | 10 +- .../components/modern/UserMessageItem.scss | 38 +- .../components/modern/UserMessageItem.tsx | 4 +- .../modern/UserMessageItemActions.test.ts | 10 +- .../components/voice/ControlConversation.tsx | 2 +- .../voice/ConversationModeSurface.scss | 13 +- .../voice/ConversationModeSurface.test.tsx | 26 +- .../voice/ConversationModeSurface.tsx | 8 +- .../compiler/AppearanceCompiler.test.ts | 2 +- src/web-ui/src/shared/ui/Dialog.test.tsx | 4 + src/web-ui/src/shared/ui/MenuPopover.test.tsx | 9 +- src/web-ui/src/shared/ui/usePresence.test.tsx | 67 + .../utils/useAnchoredPopoverPosition.ts | 17 +- .../git/components/BranchQuickSwitch.scss | 39 +- .../git/components/BranchQuickSwitch.test.tsx | 190 +- .../git/components/BranchQuickSwitch.tsx | 125 +- 56 files changed, 1547 insertions(+), 2531 deletions(-) create mode 100644 src/web-ui/src/app/styles/motion.test.ts create mode 100644 src/web-ui/src/shared/ui/usePresence.test.tsx diff --git a/design-system/packages/ui/README.md b/design-system/packages/ui/README.md index e85cc700e7..594df3d207 100644 --- a/design-system/packages/ui/README.md +++ b/design-system/packages/ui/README.md @@ -45,6 +45,11 @@ and `data-scrolled` when records have moved below their starting position. Hosts can layer compact controls above that viewport without creating another scroller. Each entry may supply `activity` beneath its message; the host owns its real processing state, localized accessible label, and completion lifecycle. +Its `presentation="chat"` variant uses FlowChat's `type.flow.control` text size +and weight, `type.flow.body` font stack and leading, `color.content.primary` +text, and `color.action.quiet.hover` user-bubble fill. `compact` controls spacing +independently. The default `presentation="voice"` retains the call typography +and inverse colors; hosts can switch presentation on the existing viewport. `VoiceParticleLogo` is also exported independently. Its `readAudio` callback reads `{ user, assistant, assistantSpeaking }` once per animation frame. The @@ -330,7 +335,10 @@ Sized icon slots in buttons, tabs, menu items and fields own their glyph geometr Pass catalog `Icon` nodes through `leadingIcon`, `trailingIcon`, `icon` or the matching component slot, just as for SVG icons. These slots constrain catalog icons to the component's size; a standalone `Icon` retains its explicit size -(24px by default). Do not shrink the catalog globally to correct a slot mismatch. +(24px by default). They also normalize a direct Lucide glyph that still has +Lucide's default 2px stroke to the shared 1.6 line weight and inherit the slot's +color. Explicit non-default strokes and non-Lucid SVG artwork remain unchanged. +Do not shrink the catalog globally to correct a slot mismatch. `IconButton` defaults to `quiet`: its resting surface is transparent, hover and pressed states use shared action feedback, and keyboard focus keeps a visible @@ -456,6 +464,14 @@ they must forward all props and refs and retain public component ownership. `useSubmenuIntent` is available for product popovers that need the same pointer corridor behavior. +Custom composed menus reuse `useDismissibleLayer` and the public `usePresence` +hook. Keep the positioned/measured layer separate from its animated surface, +retain geometry until presence unmounts it, and make exiting content inert. +Presence cancels a pending exit when reopened and honors reduced motion. +The host should opt a presence-owned surface out of its fallback animations; +outside-pointer dismissal leaves the clicked control's focus alone, while +Escape and menu actions restore the trigger before handing off to another UI. + ## FlowChat tool cards diff --git a/design-system/packages/ui/src/components/ActionCard/ActionCard.tsx b/design-system/packages/ui/src/components/ActionCard/ActionCard.tsx index 48a8beac64..ffdc1d6296 100644 --- a/design-system/packages/ui/src/components/ActionCard/ActionCard.tsx +++ b/design-system/packages/ui/src/components/ActionCard/ActionCard.tsx @@ -67,7 +67,7 @@ export const ActionCard = forwardRef( type={type} > {leading !== undefined && leading !== null && ( -