@felloinnovations/brand-kit 0.4.0 → 0.5.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENTS.md +198 -24
- package/CHANGELOG.md +221 -0
- package/README.md +38 -9
- package/design-system/01-how-claude-decides.md +26 -17
- package/design-system/02-principles.md +11 -6
- package/design-system/03-colour.md +135 -47
- package/design-system/04-type.md +45 -23
- package/design-system/05-space-and-layout.md +175 -52
- package/design-system/06-sizing-profiles.md +4 -4
- package/design-system/07-scrolling.md +66 -20
- package/design-system/08-choosing-components.md +50 -22
- package/design-system/09-charts.md +71 -28
- package/design-system/10-patterns.md +33 -10
- package/design-system/11-page-recipes.md +110 -23
- package/design-system/12-content.md +2 -1
- package/design-system/13-motion.md +330 -47
- package/design-system/14-accessibility.md +47 -24
- package/design-system/15-ai-experiences.md +11 -6
- package/design-system/16-creativity.md +1 -1
- package/design-system/17-decisions.md +367 -1
- package/design-system/18-checklist.md +79 -16
- package/design-system/19-public-pages.md +6 -4
- package/design-system/20-palettes.md +275 -0
- package/design-system/README.md +30 -17
- package/design-system/components/ActionList/README.md +96 -10
- package/design-system/components/ActionList/preview.html +52 -7
- package/design-system/components/ActionList/style.css +64 -0
- package/design-system/components/ActivityGrid/README.md +38 -2
- package/design-system/components/ActivityGrid/preview.html +1 -1
- package/design-system/components/ActivityGrid/style.css +35 -0
- package/design-system/components/AppShell/README.md +205 -75
- package/design-system/components/AppShell/preview.html +339 -58
- package/design-system/components/AppShell/style.css +154 -0
- package/design-system/components/Avatar/README.md +37 -10
- package/design-system/components/Avatar/preview.html +13 -4
- package/design-system/components/Avatar/style.css +14 -0
- package/design-system/components/Badge/README.md +41 -19
- package/design-system/components/Badge/preview.html +13 -10
- package/design-system/components/Badge/style.css +23 -0
- package/design-system/components/Banner/README.md +30 -9
- package/design-system/components/Banner/preview.html +1 -1
- package/design-system/components/Banner/style.css +19 -0
- package/design-system/components/Breadcrumb/README.md +58 -46
- package/design-system/components/Breadcrumb/preview.html +16 -16
- package/design-system/components/Breadcrumb/style.css +17 -0
- package/design-system/components/Button/README.md +113 -55
- package/design-system/components/Button/preview.html +98 -25
- package/design-system/components/Button/style.css +86 -0
- package/design-system/components/Card/README.md +158 -49
- package/design-system/components/Card/preview.html +141 -19
- package/design-system/components/Card/style.css +115 -0
- package/design-system/components/CardBoard/README.md +58 -37
- package/design-system/components/CardBoard/preview.html +26 -29
- package/design-system/components/ChatCard/README.md +115 -29
- package/design-system/components/ChatCard/preview.html +149 -32
- package/design-system/components/ChatCard/style.css +49 -0
- package/design-system/components/ChatShell/README.md +116 -0
- package/design-system/components/ChatShell/preview.html +201 -0
- package/design-system/components/ChatShell/style.css +86 -0
- package/design-system/components/ChatTurn/README.md +78 -35
- package/design-system/components/ChatTurn/preview.html +60 -28
- package/design-system/components/ChatTurn/style.css +50 -0
- package/design-system/components/CheckRow/README.md +141 -0
- package/design-system/components/CheckRow/preview.html +140 -0
- package/design-system/components/CheckRow/style.css +88 -0
- package/design-system/components/Checkbox/README.md +58 -22
- package/design-system/components/Checkbox/preview.html +112 -50
- package/design-system/components/Checkbox/style.css +45 -0
- package/design-system/components/Chip/README.md +78 -47
- package/design-system/components/Chip/preview.html +29 -4
- package/design-system/components/Chip/style.css +17 -0
- package/design-system/components/Combobox/README.md +44 -11
- package/design-system/components/Combobox/preview.html +35 -12
- package/design-system/components/Combobox/style.css +54 -0
- package/design-system/components/Composer/README.md +137 -35
- package/design-system/components/Composer/preview.html +115 -40
- package/design-system/components/Composer/style.css +81 -0
- package/design-system/components/ConfirmDialog/README.md +73 -52
- package/design-system/components/ConfirmDialog/preview.html +70 -26
- package/design-system/components/ConfirmDialog/style.css +5 -0
- package/design-system/components/Cover/preview.html +3 -3
- package/design-system/components/Cover/style.css +19 -0
- package/design-system/components/DateInput/README.md +77 -12
- package/design-system/components/DateInput/preview.html +27 -12
- package/design-system/components/DateInput/style.css +38 -0
- package/design-system/components/Dialog/README.md +112 -44
- package/design-system/components/Dialog/preview.html +141 -18
- package/design-system/components/Dialog/style.css +74 -0
- package/design-system/components/EmptyState/README.md +42 -12
- package/design-system/components/EmptyState/preview.html +11 -11
- package/design-system/components/EmptyState/style.css +9 -0
- package/design-system/components/EntryShell/README.md +73 -48
- package/design-system/components/EntryShell/preview.html +60 -27
- package/design-system/components/EntryShell/style.css +19 -0
- package/design-system/components/FeatureGrid/README.md +61 -39
- package/design-system/components/FeatureGrid/preview.html +2 -2
- package/design-system/components/FeatureGrid/style.css +20 -0
- package/design-system/components/FileUpload/README.md +33 -3
- package/design-system/components/FileUpload/preview.html +18 -4
- package/design-system/components/FileUpload/style.css +23 -0
- package/design-system/components/FilterBar/README.md +114 -0
- package/design-system/components/FilterBar/preview.html +82 -0
- package/design-system/components/FilterBar/style.css +22 -0
- package/design-system/components/Fold/README.md +84 -26
- package/design-system/components/Fold/preview.html +77 -34
- package/design-system/components/Fold/style.css +48 -0
- package/design-system/components/Footer/README.md +62 -39
- package/design-system/components/Footer/preview.html +5 -5
- package/design-system/components/Footer/style.css +30 -0
- package/design-system/components/FunnelBars/README.md +24 -3
- package/design-system/components/FunnelBars/preview.html +5 -5
- package/design-system/components/FunnelBars/style.css +13 -0
- package/design-system/components/GoalBars/README.md +54 -10
- package/design-system/components/GoalBars/preview.html +69 -28
- package/design-system/components/GoalBars/style.css +51 -0
- package/design-system/components/GoalTicks/README.md +74 -58
- package/design-system/components/GoalTicks/preview.html +41 -118
- package/design-system/components/GoalTicks/style.css +37 -0
- package/design-system/components/GoalTubes/README.md +29 -3
- package/design-system/components/GoalTubes/preview.html +6 -6
- package/design-system/components/GoalTubes/style.css +23 -0
- package/design-system/components/Heatmap/README.md +133 -0
- package/design-system/components/Heatmap/preview.html +168 -0
- package/design-system/components/Heatmap/style.css +119 -0
- package/design-system/components/Hero/README.md +58 -40
- package/design-system/components/Hero/preview.html +1 -1
- package/design-system/components/Hero/style.css +19 -0
- package/design-system/components/HoverCard/README.md +114 -0
- package/design-system/components/HoverCard/preview.html +107 -0
- package/design-system/components/HoverCard/style.css +59 -0
- package/design-system/components/IconButton/README.md +69 -38
- package/design-system/components/IconButton/preview.html +77 -43
- package/design-system/components/IconButton/style.css +45 -0
- package/design-system/components/Input/README.md +36 -11
- package/design-system/components/Input/preview.html +1 -1
- package/design-system/components/Input/style.css +23 -0
- package/design-system/components/KanbanBoard/README.md +93 -45
- package/design-system/components/KanbanBoard/preview.html +159 -43
- package/design-system/components/KanbanBoard/style.css +53 -0
- package/design-system/components/Kbd/README.md +25 -9
- package/design-system/components/Kbd/preview.html +6 -2
- package/design-system/components/Kbd/style.css +9 -0
- package/design-system/components/KitButton/README.md +81 -47
- package/design-system/components/KitButton/preview.html +35 -13
- package/design-system/components/KitButton/style.css +46 -0
- package/design-system/components/KitCard/README.md +75 -44
- package/design-system/components/KitCard/preview.html +18 -10
- package/design-system/components/KitCard/style.css +15 -0
- package/design-system/components/KitInput/README.md +54 -39
- package/design-system/components/KitInput/preview.html +7 -7
- package/design-system/components/KitInput/style.css +23 -0
- package/design-system/components/Leaderboard/README.md +76 -49
- package/design-system/components/Leaderboard/preview.html +61 -26
- package/design-system/components/Leaderboard/style.css +44 -0
- package/design-system/components/ListDetail/README.md +222 -0
- package/design-system/components/ListDetail/preview.html +213 -0
- package/design-system/components/ListDetail/style.css +148 -0
- package/design-system/components/LoadBar/README.md +79 -0
- package/design-system/components/LoadBar/preview.html +40 -0
- package/design-system/components/LoadBar/style.css +17 -0
- package/design-system/components/MarketingNav/README.md +76 -42
- package/design-system/components/MarketingNav/preview.html +37 -8
- package/design-system/components/MarketingNav/style.css +45 -0
- package/design-system/components/Matrix/README.md +129 -0
- package/design-system/components/Matrix/preview.html +99 -0
- package/design-system/components/Matrix/style.css +84 -0
- package/design-system/components/Menu/README.md +117 -41
- package/design-system/components/Menu/preview.html +85 -23
- package/design-system/components/Menu/style.css +61 -0
- package/design-system/components/Meter/README.md +39 -4
- package/design-system/components/Meter/preview.html +18 -1
- package/design-system/components/Meter/style.css +23 -0
- package/design-system/components/MetricTile/README.md +237 -0
- package/design-system/components/MetricTile/preview.html +241 -0
- package/design-system/components/MetricTile/style.css +129 -0
- package/design-system/components/Morph/README.md +106 -0
- package/design-system/components/Morph/preview.html +103 -0
- package/design-system/components/Morph/style.css +31 -0
- package/design-system/components/Motion/README.md +164 -0
- package/design-system/components/Motion/preview.html +2537 -0
- package/design-system/components/NumberInput/README.md +27 -8
- package/design-system/components/NumberInput/preview.html +21 -5
- package/design-system/components/NumberInput/style.css +34 -0
- package/design-system/components/PaceBar/README.md +75 -0
- package/design-system/components/PaceBar/preview.html +67 -0
- package/design-system/components/PaceBar/style.css +25 -0
- package/design-system/components/Page/README.md +57 -18
- package/design-system/components/Page/preview.html +15 -17
- package/design-system/components/Page/style.css +7 -0
- package/design-system/components/PageBar/README.md +90 -34
- package/design-system/components/PageBar/preview.html +60 -19
- package/design-system/components/PageBar/style.css +35 -0
- package/design-system/components/PageHero/README.md +87 -51
- package/design-system/components/PageHero/preview.html +35 -6
- package/design-system/components/PageHero/style.css +31 -0
- package/design-system/components/Pagination/README.md +70 -49
- package/design-system/components/Pagination/preview.html +24 -15
- package/design-system/components/Pagination/style.css +12 -0
- package/design-system/components/Panel/README.md +109 -51
- package/design-system/components/Panel/preview.html +118 -20
- package/design-system/components/Panel/style.css +51 -0
- package/design-system/components/PasswordInput/README.md +50 -18
- package/design-system/components/PasswordInput/preview.html +71 -21
- package/design-system/components/PasswordInput/style.css +31 -0
- package/design-system/components/Plate/README.md +75 -17
- package/design-system/components/Plate/preview.html +40 -7
- package/design-system/components/Plate/style.css +37 -0
- package/design-system/components/Popover/README.md +70 -49
- package/design-system/components/Popover/preview.html +44 -22
- package/design-system/components/Popover/style.css +41 -0
- package/design-system/components/PricingTable/README.md +69 -49
- package/design-system/components/PricingTable/preview.html +21 -21
- package/design-system/components/PricingTable/style.css +21 -0
- package/design-system/components/ProgressPetals/README.md +31 -3
- package/design-system/components/ProgressPetals/preview.html +14 -15
- package/design-system/components/ProgressPetals/style.css +27 -0
- package/design-system/components/README.md +151 -0
- package/design-system/components/Radio/README.md +40 -17
- package/design-system/components/Radio/preview.html +16 -1
- package/design-system/components/Radio/style.css +21 -0
- package/design-system/components/RankBar/README.md +29 -2
- package/design-system/components/RankBar/preview.html +14 -12
- package/design-system/components/RankBar/style.css +18 -0
- package/design-system/components/Ring/README.md +61 -11
- package/design-system/components/Ring/preview.html +55 -10
- package/design-system/components/Ring/style.css +49 -0
- package/design-system/components/ScoreHero/README.md +91 -0
- package/design-system/components/ScoreHero/preview.html +104 -0
- package/design-system/components/ScoreHero/style.css +32 -0
- package/design-system/components/Section/README.md +72 -33
- package/design-system/components/Section/preview.html +46 -16
- package/design-system/components/Section/style.css +18 -0
- package/design-system/components/Segmented/README.md +100 -55
- package/design-system/components/Segmented/preview.html +107 -26
- package/design-system/components/Segmented/style.css +94 -0
- package/design-system/components/SegmentedProgress/README.md +64 -0
- package/design-system/components/SegmentedProgress/preview.html +69 -0
- package/design-system/components/SegmentedProgress/style.css +11 -0
- package/design-system/components/Select/README.md +47 -12
- package/design-system/components/Select/preview.html +28 -2
- package/design-system/components/Select/style.css +22 -0
- package/design-system/components/ShareBar/README.md +69 -0
- package/design-system/components/ShareBar/preview.html +72 -0
- package/design-system/components/ShareBar/style.css +25 -0
- package/design-system/components/SideList/README.md +147 -0
- package/design-system/components/SideList/preview.html +139 -0
- package/design-system/components/SideList/style.css +94 -0
- package/design-system/components/Skeleton/README.md +53 -16
- package/design-system/components/Skeleton/preview.html +35 -23
- package/design-system/components/Skeleton/style.css +17 -0
- package/design-system/components/Slider/README.md +95 -0
- package/design-system/components/Slider/preview.html +49 -0
- package/design-system/components/Slider/style.css +13 -0
- package/design-system/components/Split/README.md +112 -0
- package/design-system/components/Split/preview.html +105 -0
- package/design-system/components/Split/style.css +30 -0
- package/design-system/components/Starter/README.md +21 -9
- package/design-system/components/Starter/preview.html +5 -5
- package/design-system/components/Stat/README.md +64 -43
- package/design-system/components/Stat/preview.html +3 -3
- package/design-system/components/Stat/style.css +15 -0
- package/design-system/components/StatTiles/README.md +88 -44
- package/design-system/components/StatTiles/preview.html +142 -71
- package/design-system/components/StatTiles/style.css +64 -0
- package/design-system/components/StatusLine/README.md +85 -0
- package/design-system/components/StatusLine/preview.html +49 -0
- package/design-system/components/StatusLine/style.css +14 -0
- package/design-system/components/StatusScreen/README.md +49 -35
- package/design-system/components/StatusScreen/preview.html +20 -5
- package/design-system/components/StatusScreen/style.css +9 -0
- package/design-system/components/StepLine/README.md +97 -0
- package/design-system/components/StepLine/preview.html +108 -0
- package/design-system/components/StepLine/style.css +62 -0
- package/design-system/components/Stepper/README.md +35 -13
- package/design-system/components/Stepper/style.css +13 -0
- package/design-system/components/StreakCalendar/README.md +22 -1
- package/design-system/components/StreakCalendar/preview.html +10 -10
- package/design-system/components/StreakCalendar/style.css +12 -0
- package/design-system/components/SuggestionChip/README.md +87 -0
- package/design-system/components/SuggestionChip/preview.html +42 -0
- package/design-system/components/SuggestionChip/style.css +20 -0
- package/design-system/components/Switch/README.md +44 -24
- package/design-system/components/Switch/preview.html +23 -8
- package/design-system/components/Switch/style.css +31 -0
- package/design-system/components/Table/README.md +129 -58
- package/design-system/components/Table/preview.html +106 -72
- package/design-system/components/Table/style.css +104 -0
- package/design-system/components/Tabs/README.md +71 -46
- package/design-system/components/Tabs/preview.html +56 -24
- package/design-system/components/Tabs/style.css +44 -0
- package/design-system/components/Testimonial/README.md +48 -32
- package/design-system/components/Testimonial/preview.html +14 -14
- package/design-system/components/Testimonial/style.css +12 -0
- package/design-system/components/TextArea/README.md +27 -11
- package/design-system/components/TextArea/preview.html +8 -2
- package/design-system/components/TextArea/style.css +12 -0
- package/design-system/components/ThemeSwitch/README.md +116 -0
- package/design-system/components/ThemeSwitch/preview.html +57 -0
- package/design-system/components/ThemeSwitch/style.css +6 -0
- package/design-system/components/TickRow/README.md +52 -36
- package/design-system/components/TickRow/preview.html +64 -41
- package/design-system/components/TickRow/style.css +23 -0
- package/design-system/components/TickStrip/README.md +95 -0
- package/design-system/components/TickStrip/preview.html +88 -0
- package/design-system/components/TickStrip/style.css +42 -0
- package/design-system/components/Tile/README.md +79 -18
- package/design-system/components/Tile/preview.html +91 -40
- package/design-system/components/Tile/style.css +36 -0
- package/design-system/components/Timeline/README.md +68 -48
- package/design-system/components/Timeline/preview.html +27 -15
- package/design-system/components/Timeline/style.css +25 -0
- package/design-system/components/Toast/README.md +70 -38
- package/design-system/components/Toast/preview.html +43 -8
- package/design-system/components/Toast/style.css +25 -0
- package/design-system/components/Tooltip/README.md +93 -35
- package/design-system/components/Tooltip/preview.html +69 -15
- package/design-system/components/Tooltip/style.css +78 -0
- package/design-system/components/TopBar/README.md +67 -53
- package/design-system/components/TopBar/preview.html +14 -27
- package/design-system/components/TopBar/style.css +35 -0
- package/design-system/components/TopicRail/README.md +108 -0
- package/design-system/components/TopicRail/preview.html +58 -0
- package/design-system/components/TopicRail/style.css +48 -0
- package/design-system/components/TrendBars/README.md +52 -14
- package/design-system/components/TrendBars/preview.html +65 -32
- package/design-system/components/TrendBars/style.css +25 -0
- package/design-system/components/TrendLine/README.md +164 -0
- package/design-system/components/TrendLine/preview.html +373 -0
- package/design-system/components/TrendLine/style.css +155 -0
- package/design-system/components/Well/README.md +64 -22
- package/design-system/components/Well/preview.html +14 -14
- package/design-system/components/Well/style.css +22 -0
- package/design-system/components/_house.css +324 -0
- package/design-system/components/bundle.css +4086 -744
- package/design-system/tokens.json +1310 -124
- package/dist/fello-core.css +2 -2
- package/dist/fello.css +6 -1369
- package/dist/fello.scoped.css +7 -0
- package/dist/index.d.ts +109 -10
- package/dist/index.js +781 -96
- package/dist/palettes.d.ts +464 -0
- package/dist/palettes.js +497 -0
- package/dist/scoped.d.ts +3 -0
- package/dist/scoped.js +16 -0
- package/dist/toast.d.ts +14 -0
- package/dist/toast.js +33 -29
- package/dist/tokens.d.ts +1686 -62
- package/dist/tokens.js +1668 -61
- package/package.json +20 -4
- package/scripts/check-palette.mjs +295 -0
- package/scripts/token-model.mjs +552 -0
- package/tokens/_dark.css +173 -0
- package/tokens/_palettes.css +46 -0
- package/tokens/_product.css +266 -53
- package/tokens/_source.hubl.css +39 -19
- package/tokens/design-tokens.json +319 -0
- package/tokens/palettes.ts +504 -0
- package/tokens/shadcn-compat.css +19 -19
- package/tokens/shadcn-compat.hsl.css +76 -0
- package/tokens/tokens.css +1287 -62
- package/tokens/tokens.md +587 -61
- package/tokens/tokens.root.css +1293 -62
- package/tokens/tokens.ts +1677 -64
|
@@ -0,0 +1,201 @@
|
|
|
1
|
+
<!-- @dsCard group="Chat" height=1472 -->
|
|
2
|
+
<!doctype html>
|
|
3
|
+
<html>
|
|
4
|
+
<head>
|
|
5
|
+
<meta charset="utf-8">
|
|
6
|
+
<title>ChatShell</title>
|
|
7
|
+
<link rel="stylesheet" href="../../tokens.css">
|
|
8
|
+
<link rel="stylesheet" href="../bundle.css">
|
|
9
|
+
</head>
|
|
10
|
+
<body>
|
|
11
|
+
<div class="ws-stage ws-stage--column" style="background: var(--ws-frame);">
|
|
12
|
+
|
|
13
|
+
<div class="ws-stack">
|
|
14
|
+
<span class="ws-muted">Docked: the chat a column beside the page, the nav folded to its rail, a handle to resize it</span>
|
|
15
|
+
<div class="ws-chat-dock" style="height: 560px;">
|
|
16
|
+
<nav class="ws-app-shell__rail" aria-label="Main">
|
|
17
|
+
<span class="ws-app-shell__mark ws-app-shell__mark--wordmark">F</span>
|
|
18
|
+
<span class="ws-app-shell__mark ws-app-shell__mark--current" aria-current="page" aria-label="Pipeline">
|
|
19
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><path d="M2.5 3.5h11M4.5 8h7M6.5 12.5h3" stroke="currentColor" stroke-width="1.5" stroke-linecap="round"/></svg>
|
|
20
|
+
</span>
|
|
21
|
+
</nav>
|
|
22
|
+
<aside class="ws-chat-shell ws-chat-shell--dock" aria-label="Chat with Coach">
|
|
23
|
+
<header class="ws-chat-shell__head">
|
|
24
|
+
<h2 class="ws-section">Coach</h2>
|
|
25
|
+
<span class="ws-muted ws-chat-shell__where" title="On Pipeline">On Pipeline</span>
|
|
26
|
+
<span class="ws-chat-shell__tools">
|
|
27
|
+
<button type="button" class="ws-icon-btn ws-icon-btn--sm" aria-label="Full screen" title="Full screen">
|
|
28
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><path d="M9.5 2.5h4v4M6.5 13.5h-4v-4M13.5 2.5L9 7M2.5 13.5L7 9" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/></svg>
|
|
29
|
+
</button>
|
|
30
|
+
<button type="button" class="ws-icon-btn ws-icon-btn--sm" aria-label="Close the chat" title="Close">
|
|
31
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><path d="M4 4l8 8M12 4l-8 8" stroke="currentColor" stroke-width="1.5" stroke-linecap="round"/></svg>
|
|
32
|
+
</button>
|
|
33
|
+
</span>
|
|
34
|
+
</header>
|
|
35
|
+
<ol class="ws-chat-shell__thread" aria-label="Messages">
|
|
36
|
+
<li class="ws-chat-turn ws-chat-turn--person"><p class="ws-chat-turn__bubble">Who should I call first today?</p></li>
|
|
37
|
+
<li class="ws-chat-turn ws-chat-turn--agent">
|
|
38
|
+
<p class="ws-chat-turn__words">Priya Nair. Her offer runs out tonight and she asked for an answer by five.</p>
|
|
39
|
+
<div class="ws-suggestions ws-suggestions--chat" aria-label="Ask next">
|
|
40
|
+
<button type="button" class="ws-suggestion-chip ws-suggestion-chip--chat"><span>Call her now</span></button>
|
|
41
|
+
<button type="button" class="ws-suggestion-chip ws-suggestion-chip--chat"><span>Who is next?</span></button>
|
|
42
|
+
</div>
|
|
43
|
+
</li>
|
|
44
|
+
</ol>
|
|
45
|
+
<div class="ws-chat-shell__compose">
|
|
46
|
+
<div class="ws-composer">
|
|
47
|
+
<label class="ws-sr" for="dock-words">Message Coach</label>
|
|
48
|
+
<textarea id="dock-words" class="ws-composer__words" rows="1" placeholder="Message Coach"></textarea>
|
|
49
|
+
<div class="ws-composer__trail">
|
|
50
|
+
<button type="button" class="ws-icon-btn ws-icon-btn--lg" aria-label="Add a file"><svg viewBox="0 0 16 16" fill="none" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" aria-hidden="true"><path d="M8 3v10M3 8h10"/></svg></button>
|
|
51
|
+
<button type="button" class="ws-icon-btn ws-icon-btn--primary ws-icon-btn--lg" aria-label="Talk with Coach"><svg viewBox="0 0 16 16" fill="none" stroke="currentColor" stroke-width="1.6" stroke-linecap="round" aria-hidden="true"><path d="M3 6.5v3M5.5 4.5v7M8 2.5v11M10.5 4.5v7M13 6.5v3"/></svg></button>
|
|
52
|
+
</div>
|
|
53
|
+
</div>
|
|
54
|
+
</div>
|
|
55
|
+
<button type="button" class="ws-chat-shell__resize" role="separator" aria-orientation="vertical" aria-label="Resize the chat" aria-valuemin="340" aria-valuemax="560" aria-valuenow="420"></button>
|
|
56
|
+
</aside>
|
|
57
|
+
<main class="ws-card ws-card--pad-md ws-stack">
|
|
58
|
+
<h2 class="ws-title">Pipeline</h2>
|
|
59
|
+
<p class="ws-body">The page steps aside for the chat; on a phone the chat takes the whole screen.</p>
|
|
60
|
+
</main>
|
|
61
|
+
</div>
|
|
62
|
+
</div>
|
|
63
|
+
|
|
64
|
+
<div class="ws-stack">
|
|
65
|
+
<span class="ws-muted">Full screen: the page card's frame, one centred reading column; empty, it says who it is</span>
|
|
66
|
+
<div class="ws-chat-shell ws-chat-shell--full" style="height: 460px;">
|
|
67
|
+
<header class="ws-chat-shell__head">
|
|
68
|
+
<h2 class="ws-section">Coach</h2>
|
|
69
|
+
<span class="ws-chat-shell__tools">
|
|
70
|
+
<button type="button" class="ws-icon-btn ws-icon-btn--sm" aria-label="Dock the chat" title="Dock">
|
|
71
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><rect x="2.5" y="2.5" width="11" height="11" rx="1.5" stroke="currentColor" stroke-width="1.5"/><path d="M7 2.5v11" stroke="currentColor" stroke-width="1.5"/></svg>
|
|
72
|
+
</button>
|
|
73
|
+
</span>
|
|
74
|
+
</header>
|
|
75
|
+
<div class="ws-chat-shell__thread">
|
|
76
|
+
<div class="ws-chat-shell__empty">
|
|
77
|
+
<h3 class="ws-chat-shell__empty-title">What should we work on?</h3>
|
|
78
|
+
<p class="ws-body">Coach knows your calls, your pipeline and your goal for October.</p>
|
|
79
|
+
<div class="ws-suggestions ws-suggestions--chat" aria-label="Start with">
|
|
80
|
+
<button type="button" class="ws-suggestion-chip ws-suggestion-chip--chat"><span>Plan my day</span></button>
|
|
81
|
+
<button type="button" class="ws-suggestion-chip ws-suggestion-chip--chat"><span>Who needs a nudge?</span></button>
|
|
82
|
+
<button type="button" class="ws-suggestion-chip ws-suggestion-chip--chat"><span>Practice a call</span></button>
|
|
83
|
+
</div>
|
|
84
|
+
</div>
|
|
85
|
+
</div>
|
|
86
|
+
<div class="ws-chat-shell__compose">
|
|
87
|
+
<div class="ws-composer">
|
|
88
|
+
<label class="ws-sr" for="full-words">Message Coach</label>
|
|
89
|
+
<textarea id="full-words" class="ws-composer__words" rows="1" placeholder="Message Coach"></textarea>
|
|
90
|
+
<div class="ws-composer__trail">
|
|
91
|
+
<button type="button" class="ws-icon-btn ws-icon-btn--primary ws-icon-btn--lg" aria-label="Talk with Coach"><svg viewBox="0 0 16 16" fill="none" stroke="currentColor" stroke-width="1.6" stroke-linecap="round" aria-hidden="true"><path d="M3 6.5v3M5.5 4.5v7M8 2.5v11M10.5 4.5v7M13 6.5v3"/></svg></button>
|
|
92
|
+
</div>
|
|
93
|
+
</div>
|
|
94
|
+
</div>
|
|
95
|
+
</div>
|
|
96
|
+
</div>
|
|
97
|
+
|
|
98
|
+
<div class="ws-stack">
|
|
99
|
+
<span class="ws-muted">Bar: only the field and its starters, over a veil that blurs the page</span>
|
|
100
|
+
<div style="position: relative; height: 300px; overflow: hidden; border-radius: var(--ws-radius-panel);">
|
|
101
|
+
<div class="ws-card ws-card--pad-md ws-stack" style="height: 100%;">
|
|
102
|
+
<h2 class="ws-title">Pipeline</h2>
|
|
103
|
+
<p class="ws-body">Nine leads, two of them waiting on you.</p>
|
|
104
|
+
</div>
|
|
105
|
+
<div class="ws-chat-veil" aria-hidden="true"></div>
|
|
106
|
+
<div class="ws-chat-shell ws-chat-shell--bar" style="position: absolute; top: var(--space-xl); left: 50%; translate: -50% 0; width: min(560px, calc(100% - var(--space-xl)));">
|
|
107
|
+
<div class="ws-chat-shell__compose">
|
|
108
|
+
<div class="ws-composer">
|
|
109
|
+
<label class="ws-sr" for="bar-words">Ask Coach</label>
|
|
110
|
+
<textarea id="bar-words" class="ws-composer__words" rows="1" placeholder="Ask Coach"></textarea>
|
|
111
|
+
<div class="ws-composer__trail">
|
|
112
|
+
<button type="button" class="ws-icon-btn ws-icon-btn--primary ws-icon-btn--lg" aria-label="Talk with Coach"><svg viewBox="0 0 16 16" fill="none" stroke="currentColor" stroke-width="1.6" stroke-linecap="round" aria-hidden="true"><path d="M3 6.5v3M5.5 4.5v7M8 2.5v11M10.5 4.5v7M13 6.5v3"/></svg></button>
|
|
113
|
+
</div>
|
|
114
|
+
</div>
|
|
115
|
+
<div class="ws-suggestions" aria-label="Ask about">
|
|
116
|
+
<button type="button" class="ws-suggestion-chip"><span>Why did calls drop?</span></button>
|
|
117
|
+
<button type="button" class="ws-suggestion-chip"><span>Who needs a nudge?</span></button>
|
|
118
|
+
</div>
|
|
119
|
+
</div>
|
|
120
|
+
</div>
|
|
121
|
+
</div>
|
|
122
|
+
</div>
|
|
123
|
+
|
|
124
|
+
<div class="ws-stack" data-live>
|
|
125
|
+
<span class="ws-muted">Live: Full screen and Dock move the chat between its modes as itself, over .55 s on the shift curve (morph); Close sends it off over .16 s, and Open grows it back out of its edge on the panel spring, its head fading in after it</span>
|
|
126
|
+
<div class="ws-chat-dock" id="chat-live" style="height: 480px;">
|
|
127
|
+
<aside class="ws-chat-shell ws-chat-shell--dock" aria-label="Chat with Coach">
|
|
128
|
+
<header class="ws-chat-shell__head">
|
|
129
|
+
<h2 class="ws-section">Coach</h2>
|
|
130
|
+
<span class="ws-muted ws-chat-shell__where" title="On Pipeline">On Pipeline</span>
|
|
131
|
+
<span class="ws-chat-shell__tools">
|
|
132
|
+
<button type="button" class="ws-icon-btn ws-icon-btn--sm" aria-label="Full screen" title="Full screen" data-mode>
|
|
133
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><path d="M9.5 2.5h4v4M6.5 13.5h-4v-4M13.5 2.5L9 7M2.5 13.5L7 9" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/></svg>
|
|
134
|
+
</button>
|
|
135
|
+
<button type="button" class="ws-icon-btn ws-icon-btn--sm" aria-label="Close the chat" title="Close" data-close>
|
|
136
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><path d="M4 4l8 8M12 4l-8 8" stroke="currentColor" stroke-width="1.5" stroke-linecap="round"/></svg>
|
|
137
|
+
</button>
|
|
138
|
+
</span>
|
|
139
|
+
</header>
|
|
140
|
+
<ol class="ws-chat-shell__thread" aria-label="Messages">
|
|
141
|
+
<li class="ws-chat-turn ws-chat-turn--person"><p class="ws-chat-turn__bubble">Who should I call first today?</p></li>
|
|
142
|
+
<li class="ws-chat-turn ws-chat-turn--agent"><p class="ws-chat-turn__words">Priya Nair. Her offer runs out tonight and she asked for an answer by five.</p></li>
|
|
143
|
+
</ol>
|
|
144
|
+
<div class="ws-chat-shell__compose">
|
|
145
|
+
<div class="ws-composer">
|
|
146
|
+
<label class="ws-sr" for="live-words">Message Coach</label>
|
|
147
|
+
<textarea id="live-words" class="ws-composer__words" rows="1" placeholder="Message Coach"></textarea>
|
|
148
|
+
</div>
|
|
149
|
+
</div>
|
|
150
|
+
</aside>
|
|
151
|
+
<main class="ws-card ws-card--pad-md ws-stack">
|
|
152
|
+
<h2 class="ws-title">Pipeline</h2>
|
|
153
|
+
<p class="ws-body">The page steps aside for the chat.</p>
|
|
154
|
+
<button type="button" class="ws-btn ws-btn--secondary" style="align-self: flex-start; display: none;" data-open>Open the chat</button>
|
|
155
|
+
</main>
|
|
156
|
+
</div>
|
|
157
|
+
</div>
|
|
158
|
+
<script>
|
|
159
|
+
(() => {
|
|
160
|
+
// A copy of morph() from @felloinnovations/brand-kit (src/lib/motion.ts): a preview cannot import the package.
|
|
161
|
+
const morph = (update, { as = 'full', el } = {}) => {
|
|
162
|
+
if (!document.startViewTransition || matchMedia('(prefers-reduced-motion: reduce)').matches) { update(); return Promise.resolve(); }
|
|
163
|
+
const root = document.documentElement;
|
|
164
|
+
if (el) {
|
|
165
|
+
const s = getComputedStyle(el);
|
|
166
|
+
root.style.setProperty('--ws-morph-ground', s.backgroundColor);
|
|
167
|
+
root.style.setProperty('--ws-morph-radius', s.borderRadius);
|
|
168
|
+
root.style.setProperty('--ws-morph-backdrop', s.backdropFilter || 'none');
|
|
169
|
+
el.style.viewTransitionName = 'ws-morph';
|
|
170
|
+
}
|
|
171
|
+
root.dataset.wsMorph = as;
|
|
172
|
+
const move = document.startViewTransition(update);
|
|
173
|
+
move.ready.catch(() => {});
|
|
174
|
+
return move.finished.finally(() => { if (el) el.style.viewTransitionName = ''; delete root.dataset.wsMorph; });
|
|
175
|
+
};
|
|
176
|
+
const dock = document.getElementById('chat-live');
|
|
177
|
+
const shell = dock.querySelector('.ws-chat-shell'), page = dock.querySelector('main'), mode = shell.querySelector('[data-mode]'), open = page.querySelector('[data-open]');
|
|
178
|
+
mode.addEventListener('click', () => morph(() => {
|
|
179
|
+
const full = shell.classList.toggle('ws-chat-shell--full');
|
|
180
|
+
shell.classList.toggle('ws-chat-shell--dock', !full);
|
|
181
|
+
shell.style.flex = full ? '1' : '';
|
|
182
|
+
page.style.display = full ? 'none' : '';
|
|
183
|
+
mode.setAttribute('aria-label', full ? 'Dock the chat' : 'Full screen');
|
|
184
|
+
mode.title = full ? 'Dock' : 'Full screen';
|
|
185
|
+
}, { as: 'shift', el: shell }));
|
|
186
|
+
shell.querySelector('[data-close]').addEventListener('click', () => {
|
|
187
|
+
shell.setAttribute('data-leaving', '');
|
|
188
|
+
setTimeout(() => {
|
|
189
|
+
shell.removeAttribute('data-leaving');
|
|
190
|
+
shell.style.display = 'none';
|
|
191
|
+
page.style.display = '';
|
|
192
|
+
open.style.display = '';
|
|
193
|
+
}, 160);
|
|
194
|
+
});
|
|
195
|
+
open.addEventListener('click', () => { open.style.display = 'none'; shell.style.display = ''; });
|
|
196
|
+
})();
|
|
197
|
+
</script>
|
|
198
|
+
|
|
199
|
+
</div>
|
|
200
|
+
</body>
|
|
201
|
+
</html>
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
/* ---- ChatShell: the chat's frame (North's) in three modes: a bar (the field over a veiled page), a docked column beside the page, the full screen ---- */
|
|
2
|
+
/* The shell: North's glass card (white at 59 % blurred 28 px, 1 px stage edge, 16 px corners), a column of a 52 px
|
|
3
|
+
head, the thread that scrolls and the composer area. Not clipped: its parts are inset, so a menu inside still shows.
|
|
4
|
+
It opens growing from its mode's side out of an 8 px blur (North's panel spring as a curve). */
|
|
5
|
+
.ws-chat-shell { --ws-chat-col: calc(var(--space-9xl) * 3 + var(--space-8xl)); --ws-chat-dock-w: calc(var(--space-9xl) * 2 + var(--ws-card-inset)); position: relative; display: flex; flex-direction: column; min-width: 0; min-height: 0; border: var(--ws-line) solid var(--ws-edge-stage); border-radius: var(--ws-radius-panel); background: var(--ws-glass); -webkit-backdrop-filter: blur(var(--ws-glass-blur-chat)) saturate(1.4); backdrop-filter: blur(var(--ws-glass-blur-chat)) saturate(1.4); }
|
|
6
|
+
.ws-chat-shell > * { flex-shrink: 0; }
|
|
7
|
+
/* The head: 52 tall, 20 in on the left (the thread's edge) and 12 on the right (the composer's), 8 apart: the title
|
|
8
|
+
(ws-section), where it is (muted, cut with a title), then the mode buttons at the end; a 0.5 px navy rule under it. */
|
|
9
|
+
.ws-chat-shell__head { display: flex; align-items: center; gap: var(--space-xs); min-height: calc(var(--space-3xl) + var(--space-xxs)); padding: 0 var(--space-sm) 0 var(--ws-card-inset); border-bottom: var(--ws-hairline) solid color-mix(in srgb, var(--ws-ink) 8%, transparent); }
|
|
10
|
+
.ws-chat-shell__where { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
|
|
11
|
+
.ws-chat-shell__tools { display: flex; flex-shrink: 0; align-items: center; gap: var(--space-3xs); margin-left: auto; }
|
|
12
|
+
/* On touch the small tools' 40 px hit areas would overlap 2 apart: 12 apart they meet and never overlap. */
|
|
13
|
+
@media (pointer: coarse) { .ws-chat-shell__tools { gap: var(--space-sm); } }
|
|
14
|
+
/* The thread: the one scroller, 20 down and 20 in (North's docked thread, on the head's edge), 64 of room under the
|
|
15
|
+
last item so it can scroll up clear of the composer (North's 72, a one-off, snapped to the scale: D4). */
|
|
16
|
+
.ws-chat-shell__thread { position: relative; display: flex; flex: 1; flex-direction: column; min-height: 0; overflow-y: auto; overscroll-behavior: contain; padding: var(--ws-card-inset) var(--ws-card-inset) var(--space-4xl); scrollbar-width: thin; }
|
|
17
|
+
.ws-chat-shell__thread > * { flex-shrink: 0; }
|
|
18
|
+
/* The empty chat: a 26 / 32 title and one 14 / 20 line 8 under it, sitting low in the thread, the starters 16 under.
|
|
19
|
+
The title balances its lines, so a narrow column never leaves its last word alone. */
|
|
20
|
+
.ws-chat-shell__empty { display: flex; flex-direction: column; gap: var(--space-xs); margin-top: auto; padding-bottom: var(--space-xl); }
|
|
21
|
+
.ws-chat-shell__empty-title { font-size: var(--font-size-2xl); line-height: var(--space-xl); font-weight: 600; letter-spacing: var(--ws-tracking-title); color: var(--color-text-heading); text-wrap: balance; }
|
|
22
|
+
.ws-chat-shell__empty > .ws-suggestions { margin-top: var(--space-xs); }
|
|
23
|
+
/* The composer area: 8 / 12 / 12 round the field. */
|
|
24
|
+
.ws-chat-shell__compose { padding: var(--space-xs) var(--space-sm) var(--space-sm); }
|
|
25
|
+
.ws-chat-shell .ws-chat-turn__bubble { background: var(--color-surface); }
|
|
26
|
+
/* Docked: a column beside the page, 420 wide (the person drags it from 340 to 560 by its handle, which sets
|
|
27
|
+
--ws-chat-dock-w), no shadow, the page stepping aside. AppShell folds its nav to the rail beside it. */
|
|
28
|
+
.ws-chat-dock { display: flex; gap: var(--space-sm); min-height: 0; }
|
|
29
|
+
.ws-chat-dock > :not(.ws-chat-shell) { min-width: 0; }
|
|
30
|
+
.ws-chat-dock > :last-child:not(.ws-chat-shell) { flex: 1; }
|
|
31
|
+
.ws-chat-shell--dock { flex-shrink: 0; width: clamp(calc(var(--space-9xl) + var(--space-7xl) + var(--ws-card-inset)), var(--ws-chat-dock-w), calc(var(--space-9xl) * 2 + var(--space-8xl))); }
|
|
32
|
+
/* The resize handle: the 12 px gap at the column's right edge, a 3 x 40 grip at its middle, a col-resize pointer; a
|
|
33
|
+
real separator a keyboard can move (arrow keys, in the app). */
|
|
34
|
+
.ws-chat-shell__resize { position: absolute; top: 0; bottom: 0; left: 100%; width: var(--space-sm); padding: 0; border: 0; background: none; cursor: col-resize; }
|
|
35
|
+
.ws-chat-shell__resize::after { content: ""; position: absolute; top: 50%; left: 50%; width: var(--ws-halo); height: var(--space-2xl); border-radius: var(--ws-radius-chip); background: color-mix(in srgb, var(--ws-ink) 18%, transparent); translate: -50% -50%; transition: background-color var(--ws-duration-hover) var(--ws-ease-soft); }
|
|
36
|
+
/* Under the pointer and while dragged the grip darkens, so the handle shows it can be taken. */
|
|
37
|
+
@media (hover: hover) { .ws-chat-shell__resize:hover::after { background: color-mix(in srgb, var(--ws-ink) 36%, transparent); } }
|
|
38
|
+
.ws-chat-shell--resizing .ws-chat-shell__resize::after { background: color-mix(in srgb, var(--ws-ink) 36%, transparent); }
|
|
39
|
+
/* Full screen: the page card's frame, white at 94 %, one centred reading column at most 760 wide, 28 in at the least,
|
|
40
|
+
items 24 apart and 120 of room under the last; the composer spans the same column. The person's bubble takes a navy
|
|
41
|
+
tint since the ground is white. */
|
|
42
|
+
.ws-chat-shell--full { background: color-mix(in srgb, var(--color-surface) 94%, transparent); }
|
|
43
|
+
.ws-chat-shell--full .ws-chat-shell__thread { padding: calc(var(--space-lg) + var(--space-xxs)) calc(var(--space-lg) + var(--space-xxs)) var(--space-7xl); }
|
|
44
|
+
.ws-chat-shell--full .ws-chat-shell__compose { padding: var(--space-xs) calc(var(--space-lg) + var(--space-xxs)) calc(var(--space-md) + var(--space-xxs)); }
|
|
45
|
+
.ws-chat-shell--full :is(.ws-chat-shell__thread, .ws-chat-shell__compose) > * { width: 100%; max-width: var(--ws-chat-col); margin-inline: auto; }
|
|
46
|
+
.ws-chat-shell--full .ws-chat-turn + .ws-chat-turn { margin-top: var(--space-lg); }
|
|
47
|
+
.ws-chat-shell--full .ws-chat-turn__bubble { background: var(--ws-hover); }
|
|
48
|
+
/* The bar: only the field (60 tall, 8 px corners, the chat bar's drop in the floating family, ws-shadow-bar) and the starters 14
|
|
49
|
+
under it, over a veil that blurs the page. */
|
|
50
|
+
.ws-chat-shell--bar { border-color: transparent; background: none; -webkit-backdrop-filter: none; backdrop-filter: none; }
|
|
51
|
+
.ws-chat-shell--bar .ws-chat-shell__compose { padding: 0; }
|
|
52
|
+
.ws-chat-shell--bar .ws-composer { min-height: calc(var(--space-4xl) - var(--space-xxs)); padding-block: var(--space-sm); border-radius: var(--ws-radius-card); box-shadow: var(--ws-shadow-bar); }
|
|
53
|
+
/* A live call in the bar keeps the composer's ring (the bar's drop alone outranked it). */
|
|
54
|
+
.ws-chat-shell--bar .ws-composer--live { box-shadow: var(--ws-ring-selected), var(--ws-shadow-bar); }
|
|
55
|
+
.ws-chat-shell--bar .ws-suggestions { margin-top: var(--space-sm-plus); }
|
|
56
|
+
.ws-chat-veil { position: absolute; inset: 0; background: var(--ws-veil); -webkit-backdrop-filter: blur(var(--ws-blur-panel)); backdrop-filter: blur(var(--ws-blur-panel)); }
|
|
57
|
+
/* Motion (D7, North's chat, js@647700 to 675000): it opens from its mode's side (the bar from its top, the docked column
|
|
58
|
+
from its left edge, the full screen from 40 % down), growing out of .97 on the panel spring (.42 / .12, "Opens / moves
|
|
59
|
+
/ docks"), fading in over .2 s and out of an 8 px blur over .24 s; its head fades in .25 s, .12 s after it. A change of
|
|
60
|
+
mode goes through morph() (Morph, `as: 'shift'`): the shell moves to its new place and size as itself over .55 s on
|
|
61
|
+
the shift curve ("Chat moves between full screen, dock and pop-out"). data-leaving closes it over .16 s (opacity 0,
|
|
62
|
+
.97, a 6 px blur), faster. The docked width shifts on the same curve, never while the handle is dragged (North
|
|
63
|
+
css:789). Reduced motion: every mode is simply there. */
|
|
64
|
+
.ws-chat-shell { --ws-chat-out: 160ms; /* raw: North's chat exit .16 s */ --ws-chat-unblur: 240ms; /* raw: North's .24 s blur in */ --ws-chat-head-after: 120ms; /* raw: North's head waits .12 s */ }
|
|
65
|
+
.ws-chat-shell--bar { transform-origin: 50% 0; }
|
|
66
|
+
.ws-chat-shell--dock { transform-origin: 0 50%; }
|
|
67
|
+
.ws-chat-shell--full { transform-origin: 50% 40%; }
|
|
68
|
+
@keyframes ws-chat-fade { from { opacity: 0; } }
|
|
69
|
+
@keyframes ws-chat-grow { from { scale: var(--ws-open-scale); } }
|
|
70
|
+
@keyframes ws-chat-unblur { from { filter: blur(var(--ws-blur-panel)); } }
|
|
71
|
+
@keyframes ws-chat-out { to { opacity: 0; scale: var(--ws-open-scale); filter: blur(calc(var(--ws-blur-arrive) * 2)); } }
|
|
72
|
+
@media (prefers-reduced-motion: no-preference) {
|
|
73
|
+
.ws-chat-shell { animation: ws-chat-fade var(--ws-duration-hover) var(--ws-ease-soft) backwards, ws-chat-grow var(--ws-spring-panel-duration) var(--ws-spring-panel) backwards, ws-chat-unblur var(--ws-chat-unblur) var(--ws-ease-soft) backwards; }
|
|
74
|
+
.ws-chat-shell__head { animation: ws-chat-fade var(--ws-duration-text) var(--ws-ease-soft) var(--ws-chat-head-after) backwards; }
|
|
75
|
+
.ws-chat-shell[data-leaving] { animation: ws-chat-out var(--ws-chat-out) var(--ws-ease-exit) forwards; pointer-events: none; }
|
|
76
|
+
.ws-chat-shell--dock { transition: width var(--ws-duration-shift) var(--ws-ease-shift); }
|
|
77
|
+
.ws-chat-shell--resizing { transition: none; }
|
|
78
|
+
.ws-chat-veil { animation: ws-chat-veil var(--ws-duration-settle) var(--ws-ease-soft) backwards; }
|
|
79
|
+
}
|
|
80
|
+
@keyframes ws-chat-veil { from { opacity: 0; } }
|
|
81
|
+
/* A phone or a narrow window (60rem, North's 960): the docked chat takes the whole width and the page waits behind it. */
|
|
82
|
+
@media (max-width: 60rem) {
|
|
83
|
+
.ws-chat-dock > :not(.ws-chat-shell) { display: none; }
|
|
84
|
+
.ws-chat-shell--dock { width: 100%; }
|
|
85
|
+
.ws-chat-shell__resize { display: none; }
|
|
86
|
+
}
|
|
@@ -1,11 +1,11 @@
|
|
|
1
|
-
One turn of a product's chat: the person's
|
|
2
|
-
|
|
1
|
+
One turn of a product's chat (North's thread): the person's question in a white bubble at the right, the answer full
|
|
2
|
+
width as plain words with no orb, its acts on one line under it, and the quiet receipt of what it did.
|
|
3
3
|
|
|
4
4
|
## Use it when
|
|
5
5
|
|
|
6
6
|
- Drawing the back and forth of a chat with an app's assistant or agent.
|
|
7
7
|
- Showing what an agent did as a result of a reply, as a short receipt line under its words.
|
|
8
|
-
- Showing an agent is still working on a reply, before its words arrive.
|
|
8
|
+
- Showing an agent is still working on a reply, before its words arrive (a `StatusLine` at the top of the turn).
|
|
9
9
|
|
|
10
10
|
## Not for
|
|
11
11
|
|
|
@@ -16,46 +16,57 @@ and the quiet act line that says what it did, all in one centred column.
|
|
|
16
16
|
|
|
17
17
|
## Anatomy
|
|
18
18
|
|
|
19
|
-
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
(
|
|
19
|
+
- Thread: the turns sit in the chat's thread (`ChatShell`: 20 px in, or a centred 760 px column full screen), 28 px
|
|
20
|
+
apart (24 full screen).
|
|
21
|
+
- The person's bubble (`ws-chat-turn__bubble`): 14 / 20 medium navy, at most 78 % of the thread, 10 / 14 inside,
|
|
22
|
+
corners 14 with a 4 px tail at the bottom right. White (`--color-surface`) on the chat's glass; navy at 5 %
|
|
23
|
+
(`--ws-hover`) on the full screen's white; the sunk cream on a bare page, so it always shows.
|
|
24
|
+
- A reference in the bubble (`ws-chat-turn__ref`): what the question points at (a chart, a card), one 13 / 18 medium
|
|
25
|
+
muted line above the words with a 12 px mark, cut with an ellipsis (give it a title).
|
|
26
|
+
- The answer (`ws-chat-turn__words`): full width, no bubble and no orb; 15 / 22 medium in the answer ink (North's
|
|
27
|
+
#3D3D3D, built from `--color-text-body` and `--ws-field-ink` so it follows the theme); its own line breaks kept. The
|
|
28
|
+
answer's parts (words, a card, acts) are 12 px apart; a card in it is at most 556 px.
|
|
29
|
+
- The acts (`ws-chat-turn__acts`): icons on one line, 2 px apart, each 28 px tall (40 on touch), 32 px wide at
|
|
30
|
+
least, 8 px at the sides, 6 px corners, a 16 px icon in `--color-text-body`; the label (13 / 18 semibold) slides out
|
|
31
|
+
of the icon on hover, on keyboard focus and while its menu is open. A touch screen shows every label.
|
|
32
|
+
- The receipt (`ws-chat-turn__act`): a 16 px teal check, 13 / 18 words in `--color-text-body` hanging 8 px off it (a
|
|
33
|
+
long receipt wraps on the words' edge, never under the check), and a door under the words on the same edge ("Open
|
|
34
|
+
in the app", navy medium, 24 px tall).
|
|
35
|
+
- Typing (`ws-chat-turn__working`): three 6 px dots (`ws-chat-turn__dots`, three empty `span`s) in
|
|
36
|
+
`--color-text-muted`, then who is typing in muted words, the dots one after another on the working beat
|
|
37
|
+
(`--ws-loop`, 1 s), for a person writing in a handoff. An answer at work says what it is doing instead
|
|
38
|
+
(`StatusLine`).
|
|
29
39
|
|
|
30
40
|
## Variants and sizes
|
|
31
41
|
|
|
32
|
-
| Variant | Ground |
|
|
42
|
+
| Variant | Ground | Words | Width |
|
|
33
43
|
| --- | --- | --- | --- |
|
|
34
|
-
|
|
|
35
|
-
|
|
|
36
|
-
|
|
|
37
|
-
|
|
|
44
|
+
| Person turn | White bubble (navy 5 % full screen; sunk cream on a bare page) | 14 / 20 medium navy | At most 78 % |
|
|
45
|
+
| Agent turn | None | 15 / 22 medium, the answer ink | Full width |
|
|
46
|
+
| Acts | None, navy 6 % under the pointer | 13 / 18 semibold body grey | One line |
|
|
47
|
+
| Receipt | None | 13 / 18 body grey, teal check | Full width |
|
|
38
48
|
|
|
39
49
|
## States
|
|
40
50
|
|
|
41
|
-
- **Default**:
|
|
42
|
-
- **Working**:
|
|
43
|
-
- **Act
|
|
44
|
-
- **Act
|
|
45
|
-
- **
|
|
46
|
-
|
|
47
|
-
- **
|
|
48
|
-
|
|
51
|
+
- **Default**: as above.
|
|
52
|
+
- **Working**: a `StatusLine` at the top of the agent turn says what it is doing; the answer lands under it.
|
|
53
|
+
- **Act hover / focus / open**: the act takes the navy 6 % wash (`--ws-hover-strong`) and its label slides out.
|
|
54
|
+
- **Act pressed**: the same wash at once, so a tap answers on a touch screen.
|
|
55
|
+
- **Act done**: the check and its words; a door when the act made something to open.
|
|
56
|
+
- **Long words**: a long word or address wraps (`overflow-wrap: anywhere`); a long reference is cut with a title.
|
|
57
|
+
- **Long reply**: more than three paragraphs folds behind "Show more"; the newest reply starts folded too.
|
|
58
|
+
- **Empty**: a turn with no words (an act only, or a card only) draws no bubble or words, just its act or card.
|
|
59
|
+
- **Dark**: the bubble, the answer ink and the acts follow the theme. On the navy ground the answer ink mixes toward
|
|
60
|
+
the ground's heading instead (the field ink is navy there), so it stays AA on the glass and the full screen.
|
|
49
61
|
|
|
50
62
|
## Behaviour
|
|
51
63
|
|
|
52
64
|
- Keyboard and pointer: hovering or focusing a turn can light the cards it made elsewhere on the screen
|
|
53
65
|
(`onLight`); the turn itself carries no click of its own.
|
|
54
|
-
- Motion: a new agent turn
|
|
55
|
-
person's own turn comes up from the composer,
|
|
56
|
-
|
|
57
|
-
- Touch: the
|
|
58
|
-
floor on a touch screen.
|
|
66
|
+
- Motion: a new agent turn settles in (`ws-settle`: 6 px, out of a 3 px blur, `--ws-duration-settle`); its words arrive
|
|
67
|
+
in order. The person's own turn comes up from the composer, growing from its bottom-right corner. An act's label
|
|
68
|
+
grows out over `--ws-duration-settle` on `--ws-ease-grow`. Reduced motion: everything appears in place.
|
|
69
|
+
- Touch: the acts are 40 px tall and show their labels; the door and "Show more" are 24 px tall.
|
|
59
70
|
|
|
60
71
|
## Content
|
|
61
72
|
|
|
@@ -78,13 +89,45 @@ and the quiet act line that says what it did, all in one centred column.
|
|
|
78
89
|
|
|
79
90
|
## Rules
|
|
80
91
|
|
|
81
|
-
- **The agent's words are plain text, no bubble; the person's sit in a
|
|
82
|
-
13 Oct 2026).
|
|
92
|
+
- **The agent's words are plain text, full width, no bubble and no orb; the person's sit in a white bubble** (North,
|
|
93
|
+
Figma 752:334990, which replaces the light grey bubble of 13 Oct 2026).
|
|
83
94
|
- **One voice per reply**: words, plus at most one card, never both saying the same thing; acts are short receipt
|
|
84
95
|
lines, never echoing a question already asked (the system's rule).
|
|
85
96
|
- **No em dashes anywhere the person reads**, including what a model writes (the system's rule).
|
|
86
97
|
|
|
87
98
|
## Source
|
|
88
99
|
|
|
89
|
-
**Derived from**:
|
|
90
|
-
|
|
100
|
+
**Derived from**: North's chat formatting (Figma 752:334990 "Chat · docked column"; style1.css:644, :652, :1362-1374,
|
|
101
|
+
:1406, :1703-1715: the white bubble 14 / 20 medium, 78 %, the 4 px tail; the answer full width with no orb; 28 between
|
|
102
|
+
items; the acts whose labels slide out) and the system's receipt line. **Precedent**: the first product built on the
|
|
103
|
+
system.
|
|
104
|
+
|
|
105
|
+
## Markup
|
|
106
|
+
|
|
107
|
+
```html
|
|
108
|
+
<ol class="ws-chat-shell__thread" aria-label="Chat">
|
|
109
|
+
<li class="ws-chat-turn ws-chat-turn--person">
|
|
110
|
+
<p class="ws-chat-turn__bubble">Who should I call first today?</p>
|
|
111
|
+
</li>
|
|
112
|
+
<li class="ws-chat-turn ws-chat-turn--agent">
|
|
113
|
+
<p class="ws-chat-turn__words">Priya Nair. Her offer runs out tonight.</p>
|
|
114
|
+
<span class="ws-chat-turn__act">
|
|
115
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><path d="M3.5 8.4l3 3 6-6.6" stroke="currentColor" stroke-width="1.6" stroke-linecap="round" stroke-linejoin="round"/></svg>
|
|
116
|
+
Reminded Priya about the Oak Street follow-up
|
|
117
|
+
<a class="ws-chat-turn__door" href="/leads/priya">Open in the app</a>
|
|
118
|
+
</span>
|
|
119
|
+
<div class="ws-chat-turn__acts">
|
|
120
|
+
<button type="button" class="ws-chat-turn__action" aria-label="Copy">
|
|
121
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><!-- a 16 px icon --></svg>
|
|
122
|
+
<span class="ws-chat-turn__action-label">Copy</span>
|
|
123
|
+
</button>
|
|
124
|
+
</div>
|
|
125
|
+
</li>
|
|
126
|
+
</ol>
|
|
127
|
+
```
|
|
128
|
+
|
|
129
|
+
## Styles
|
|
130
|
+
|
|
131
|
+
`ChatTurn/style.css`; the thread's insets and the full-screen bubble are `ChatShell`'s. Tokens: `--ws-text-body`,
|
|
132
|
+
`--ws-text-message`, `--ws-leading-section`, `--ws-radius-bubble`, `--ws-radius-control`, `--ws-radius-row`,
|
|
133
|
+
`--color-surface`, `--ws-surface-sunk`, `--ws-hover-strong`, `--ws-field-ink`, `--color-text-body`, `--ws-chart-card-w`.
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
<!-- @dsCard group="Chat" height=
|
|
1
|
+
<!-- @dsCard group="Chat" height=536 -->
|
|
2
2
|
<!doctype html>
|
|
3
3
|
<html>
|
|
4
4
|
<head>
|
|
@@ -8,34 +8,66 @@
|
|
|
8
8
|
<link rel="stylesheet" href="../bundle.css">
|
|
9
9
|
</head>
|
|
10
10
|
<body>
|
|
11
|
-
<div class="ws-stage" style="
|
|
12
|
-
<
|
|
11
|
+
<div class="ws-stage" style="background: var(--ws-frame);">
|
|
12
|
+
<div class="ws-stack" style="width: 440px;">
|
|
13
|
+
<span class="ws-muted">In the chat: your question in a white bubble, the answer full width, its acts under it</span>
|
|
14
|
+
<div class="ws-chat-shell">
|
|
15
|
+
<ol class="ws-chat-shell__thread" aria-label="Chat">
|
|
16
|
+
<li class="ws-chat-turn ws-chat-turn--person">
|
|
17
|
+
<p class="ws-chat-turn__bubble">Priya hasn’t followed up with the Oak Street sellers this week. Can you remind her?</p>
|
|
18
|
+
</li>
|
|
19
|
+
<li class="ws-chat-turn ws-chat-turn--agent">
|
|
20
|
+
<p class="ws-chat-turn__words">On it. I’ll message her before the end of the day and flag it again if she doesn’t reply.</p>
|
|
21
|
+
<span class="ws-chat-turn__act">
|
|
22
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><path d="M3.5 8.4l3 3 6-6.6" stroke="currentColor" stroke-width="1.6" stroke-linecap="round" stroke-linejoin="round"/></svg>
|
|
23
|
+
Reminded Priya about the Oak Street follow-up
|
|
24
|
+
<a class="ws-chat-turn__door" href="#" onclick="return false;">Open in the app</a>
|
|
25
|
+
</span>
|
|
26
|
+
<div class="ws-chat-turn__acts">
|
|
27
|
+
<button type="button" class="ws-chat-turn__action" aria-label="Copy">
|
|
28
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><rect x="5.5" y="5.5" width="8" height="8" rx="1.5" stroke="currentColor" stroke-width="1.5"/><path d="M10.5 3.5v-.5A1.5 1.5 0 0 0 9 1.5H4A1.5 1.5 0 0 0 2.5 3v5A1.5 1.5 0 0 0 4 9.5h.5" stroke="currentColor" stroke-width="1.5" stroke-linecap="round"/></svg>
|
|
29
|
+
<span class="ws-chat-turn__action-label">Copy</span>
|
|
30
|
+
</button>
|
|
31
|
+
<button type="button" class="ws-chat-turn__action" aria-label="Send to Google Chat">
|
|
32
|
+
<svg viewBox="0 0 16 16" fill="none" aria-hidden="true"><path d="M2.5 8l11-5-4 11-2-4.5z" stroke="currentColor" stroke-width="1.5" stroke-linejoin="round"/></svg>
|
|
33
|
+
<span class="ws-chat-turn__action-label">Send to Google Chat</span>
|
|
34
|
+
</button>
|
|
35
|
+
</div>
|
|
36
|
+
</li>
|
|
37
|
+
<li class="ws-chat-turn ws-chat-turn--person">
|
|
38
|
+
<p class="ws-chat-turn__bubble">
|
|
39
|
+
<span class="ws-chat-turn__ref" title="Calls this week, by agent">
|
|
40
|
+
<svg viewBox="0 0 12 12" fill="none" aria-hidden="true"><path d="M1.5 10.5h9M3 8V5.5M6 8V3M9 8V6" stroke="currentColor" stroke-width="1.25" stroke-linecap="round"/></svg>
|
|
41
|
+
<span>Calls this week, by agent</span>
|
|
42
|
+
</span>
|
|
43
|
+
Why is Sam so far behind?
|
|
44
|
+
</p>
|
|
45
|
+
</li>
|
|
46
|
+
<li class="ws-chat-turn ws-chat-turn--agent">
|
|
47
|
+
<p class="ws-status-line" role="status" title="Coach: reading Sam's calls, 12 of 40">
|
|
48
|
+
<b class="ws-status-line__who">Coach</b>
|
|
49
|
+
<span class="ws-status-line__doing">Reading Sam’s calls</span>
|
|
50
|
+
<span class="ws-status-line__step">12 of 40</span>
|
|
51
|
+
</p>
|
|
52
|
+
</li>
|
|
53
|
+
</ol>
|
|
54
|
+
</div>
|
|
55
|
+
</div>
|
|
13
56
|
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
<
|
|
21
|
-
<
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
<p class="ws-chat-turn__bubble">Also pull together a report on last week’s cold calls.</p>
|
|
29
|
-
</li>
|
|
30
|
-
|
|
31
|
-
<li class="ws-chat-turn ws-chat-turn--agent">
|
|
32
|
-
<p class="ws-chat-turn__working" role="status" aria-label="The assistant is working">
|
|
33
|
-
<span class="ws-chat-turn__dots" aria-hidden="true"><span></span><span></span><span></span></span>
|
|
34
|
-
<span class="ws-muted">Building the report…</span>
|
|
35
|
-
</p>
|
|
36
|
-
</li>
|
|
37
|
-
|
|
38
|
-
</ol>
|
|
57
|
+
<div class="ws-stack" style="width: 340px;">
|
|
58
|
+
<span class="ws-muted">On a bare page the bubble falls back to the sunk cream; a long word wraps</span>
|
|
59
|
+
<ol aria-label="Chat" style="padding: var(--space-md); background: var(--color-bg-page); border-radius: var(--ws-radius-panel);">
|
|
60
|
+
<li class="ws-chat-turn ws-chat-turn--person">
|
|
61
|
+
<p class="ws-chat-turn__bubble">Send this to priya.nair@northpointrealty.example</p>
|
|
62
|
+
</li>
|
|
63
|
+
<li class="ws-chat-turn ws-chat-turn--agent">
|
|
64
|
+
<p class="ws-chat-turn__working" role="status" aria-label="Priya is typing">
|
|
65
|
+
<span class="ws-chat-turn__dots" aria-hidden="true"><span></span><span></span><span></span></span>
|
|
66
|
+
<span class="ws-muted">Priya is typing</span>
|
|
67
|
+
</p>
|
|
68
|
+
</li>
|
|
69
|
+
</ol>
|
|
70
|
+
</div>
|
|
39
71
|
</div>
|
|
40
72
|
</body>
|
|
41
73
|
</html>
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
/* ---- ChatTurn: one turn in the chat (North's thread): the person's question in a white bubble at the right, the answer full width with no orb ---- */
|
|
2
|
+
/* The answer's ink is North's #3D3D3D (--ws-word-answer), a step darker than the body grey, with its own dark steps. */
|
|
3
|
+
.ws-chat-turn { display: flex; flex-direction: column; gap: var(--space-xxs-plus); }
|
|
4
|
+
/* Items 28 apart (North's docked thread); a full-screen thread sets 24 (ChatShell). */
|
|
5
|
+
.ws-chat-turn + .ws-chat-turn { margin-top: var(--ws-gap-turn); }
|
|
6
|
+
.ws-chat-turn--person { align-items: flex-end; }
|
|
7
|
+
.ws-chat-turn--agent { align-items: stretch; gap: var(--space-sm); }
|
|
8
|
+
/* The person's bubble: 14 / 20 medium navy, at most 78 % wide, 10 / 14 inside, corners 14 with a 4 px tail at the
|
|
9
|
+
bottom right. White on the chat's glass (ChatShell); on a bare cream page it falls back to the sunk cream so it still shows. */
|
|
10
|
+
.ws-chat-turn__bubble { display: flex; flex-direction: column; align-items: flex-start; gap: var(--space-3xs); max-width: 78%; padding: var(--space-xs-plus) var(--space-sm-plus); border-radius: calc(var(--ws-radius-bubble) + var(--ws-radius-chip)) calc(var(--ws-radius-bubble) + var(--ws-radius-chip)) var(--ws-radius-control) calc(var(--ws-radius-bubble) + var(--ws-radius-chip)); background: var(--ws-surface-sunk); font-size: var(--ws-text-body); line-height: calc(var(--space-md) + var(--space-xxs)); font-weight: 500; color: var(--color-text-heading); overflow-wrap: anywhere; }
|
|
11
|
+
/* What a question points at (a chart, a card): one quiet line inside the bubble, above the words. */
|
|
12
|
+
.ws-chat-turn__ref { display: inline-flex; align-items: center; gap: var(--space-xxs-plus); max-width: 100%; font-size: var(--ws-text-control); line-height: var(--ws-leading-control); font-weight: 500; color: var(--color-text-muted); }
|
|
13
|
+
.ws-chat-turn__ref > span { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
|
|
14
|
+
.ws-chat-turn__ref > svg { flex-shrink: 0; width: var(--ws-icon-sm); height: var(--ws-icon-sm); }
|
|
15
|
+
/* The answer: full width, no bubble, no orb; 15 / 22 medium in the answer ink, its line breaks kept. */
|
|
16
|
+
.ws-chat-turn__words { font-size: var(--ws-text-message); line-height: var(--ws-leading-section); font-weight: 500; color: var(--ws-word-answer); white-space: pre-line; text-wrap: pretty; overflow-wrap: anywhere; }
|
|
17
|
+
/* A card the answer brings sits at most 556 wide (North's chat chart card). */
|
|
18
|
+
.ws-chat-turn--agent > .ws-card, .ws-chat-turn--agent > .ws-chat-card { max-width: var(--ws-chart-card-w); }
|
|
19
|
+
/* The answer's acts: icons on one line, 2 apart, 28 tall, 6 px corners; the label slides out of the icon on hover, on
|
|
20
|
+
keyboard focus and while its menu is open. A touch screen shows every label. */
|
|
21
|
+
.ws-chat-turn__acts { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-3xs); }
|
|
22
|
+
.ws-chat-turn__action { display: inline-flex; align-items: center; justify-content: center; min-width: var(--ws-control-h); height: var(--ws-control-h-sm); padding: 0 var(--space-xs); border: 0; border-radius: var(--ws-radius-row); background: none; font-size: var(--ws-text-control); line-height: var(--ws-leading-control); font-weight: 600; color: var(--color-text-body); cursor: pointer; transition: background-color var(--ws-duration-hover) var(--ws-ease-soft), color var(--ws-duration-hover) var(--ws-ease-soft); }
|
|
23
|
+
.ws-chat-turn__action > svg { flex-shrink: 0; width: var(--ws-icon); height: var(--ws-icon); }
|
|
24
|
+
.ws-chat-turn__action-label { margin-left: var(--space-xxs-plus); white-space: nowrap; }
|
|
25
|
+
.ws-chat-turn__action:active { background-color: var(--ws-hover-strong); color: var(--color-text-heading); transition-duration: var(--ws-duration-instant); }
|
|
26
|
+
.ws-chat-turn__action[aria-expanded="true"], .ws-chat-turn__action[aria-pressed="true"] { background-color: var(--ws-hover-strong); color: var(--color-text-heading); }
|
|
27
|
+
@media (hover: hover) {
|
|
28
|
+
.ws-chat-turn__action:hover { background-color: var(--ws-hover-strong); color: var(--color-text-heading); }
|
|
29
|
+
.ws-chat-turn__action { interpolate-size: allow-keywords; }
|
|
30
|
+
.ws-chat-turn__action-label { width: 0; margin-left: 0; overflow: hidden; opacity: 0; transition: width var(--ws-duration-settle) var(--ws-ease-grow), margin-left var(--ws-duration-settle) var(--ws-ease-grow), opacity var(--ws-duration-exit) var(--ws-ease-soft); }
|
|
31
|
+
.ws-chat-turn__action:is(:hover, :focus-visible, [aria-expanded="true"]) .ws-chat-turn__action-label { width: auto; margin-left: var(--space-xxs-plus); opacity: 1; transition-duration: var(--ws-duration-settle), var(--ws-duration-settle), var(--ws-duration-hover); transition-delay: 0s, 0s, var(--ws-stagger-row); }
|
|
32
|
+
}
|
|
33
|
+
@media (pointer: coarse) { .ws-chat-turn__action { height: var(--ws-touch); } }
|
|
34
|
+
/* What the agent did, as a receipt line: a teal check, 13 / 18 words and a door to open what it made. The words hang
|
|
35
|
+
8 off the check, so a long receipt wraps on the words' edge (a wrapping row left the check alone on its line), and
|
|
36
|
+
the door sits under them on that same edge. */
|
|
37
|
+
.ws-chat-turn__act { position: relative; display: block; padding-left: calc(var(--ws-icon) + var(--space-xs)); font-size: var(--ws-text-control); line-height: var(--ws-leading-control); color: var(--color-text-body); }
|
|
38
|
+
.ws-chat-turn__act svg { position: absolute; top: calc((var(--ws-leading-control) - var(--ws-icon)) / 2); left: 0; width: var(--ws-icon); height: var(--ws-icon); color: var(--color-stat-positive); }
|
|
39
|
+
.ws-chat-turn__door { display: flex; width: fit-content; align-items: center; min-height: var(--space-lg); font-weight: 500; color: var(--color-text-heading); text-decoration: none; }
|
|
40
|
+
@media (hover: hover) { .ws-chat-turn__door:hover { text-decoration: underline; } }
|
|
41
|
+
/* Typing (a person writing in a handoff): three 6 px dots, one after another on the working beat. An answer at work
|
|
42
|
+
says what it is doing instead (StatusLine). */
|
|
43
|
+
.ws-chat-turn__working { display: flex; align-items: center; gap: var(--space-xs); min-height: var(--space-lg); }
|
|
44
|
+
.ws-chat-turn__dots { display: flex; gap: var(--space-xxs); }
|
|
45
|
+
.ws-chat-turn__dots span { width: var(--space-xxs-plus); height: var(--space-xxs-plus); border-radius: var(--radius-full); background: var(--color-text-muted); }
|
|
46
|
+
@media (prefers-reduced-motion: no-preference) {
|
|
47
|
+
.ws-chat-turn__dots span { animation: ws-pulse var(--ws-loop) var(--ws-ease-loop) infinite; }
|
|
48
|
+
.ws-chat-turn__dots span:nth-child(2) { animation-delay: calc(var(--ws-loop) / 8); }
|
|
49
|
+
.ws-chat-turn__dots span:nth-child(3) { animation-delay: calc(var(--ws-loop) / 4); }
|
|
50
|
+
}
|