@puredesktop/puredesktop-ui-bridge 2.1.4 → 2.1.7

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.
Files changed (183) hide show
  1. package/package.json +19 -1
  2. package/src/agents/runtime/mapAgentSnapshot.test.ts +1 -3
  3. package/src/agents/runtime/mapAgentSnapshot.ts +8 -4
  4. package/src/agents/runtime/mergeUsageTurn.ts +1 -2
  5. package/src/agents/runtime/pendingToolCalls.test.ts +1 -3
  6. package/src/agents/runtime/unresolvedToolCalls.ts +1 -2
  7. package/src/bridge/agentModelTiers.ts +9 -4
  8. package/src/bridge/agents.mjs +3 -1
  9. package/src/bridge/calendarDraftIntent.ts +12 -4
  10. package/src/bridge/calendarInviteIntent.ts +18 -5
  11. package/src/bridge/client.mjs +45 -45
  12. package/src/bridge/dialog.d.mts +8 -8
  13. package/src/bridge/dialog.mjs +40 -40
  14. package/src/bridge/dialog.test.ts +73 -73
  15. package/src/bridge/fs.d.mts +41 -41
  16. package/src/bridge/fs.mjs +56 -56
  17. package/src/bridge/fs.test.ts +83 -83
  18. package/src/bridge/fs.ts +28 -28
  19. package/src/bridge/googleAuth.ts +3 -1
  20. package/src/bridge/methods.d.mts +6 -0
  21. package/src/bridge/methods.mjs +7 -0
  22. package/src/bridge/network.d.mts +17 -17
  23. package/src/bridge/network.mjs +22 -22
  24. package/src/bridge/pureRender/base.css +324 -76
  25. package/src/bridge/pureRender/compiler.ts +1 -1
  26. package/src/bridge/pureRender/document.test.ts +2 -2
  27. package/src/bridge/pureRender/extraction.test.ts +24 -12
  28. package/src/bridge/pureRender/extraction.ts +10 -7
  29. package/src/bridge/pureRender/flow.css +17 -3
  30. package/src/bridge/pureRender/normalize.ts +28 -26
  31. package/src/bridge/pureRender/presets.ts +7 -7
  32. package/src/bridge/pureRender/profiles/book.css +122 -19
  33. package/src/bridge/pureRender/profiles/manuscript.css +57 -11
  34. package/src/bridge/pureRender/profiles/writer.css +48 -10
  35. package/src/bridge/pureRender/reset.css +20 -5
  36. package/src/bridge/pureRender/theme.ts +37 -9
  37. package/src/bridge/pureRender/tokens/default.css +45 -33
  38. package/src/bridge/react/usePlatformAgentRunLiveState.tsx +4 -1
  39. package/src/bridge/react/usePlatformAgentSessionDrive.tsx +13 -4
  40. package/src/bridge/screenAnnotation.test.ts +4 -1
  41. package/src/bridge/screenAnnotation.ts +6 -2
  42. package/src/bridge/storage.d.mts +26 -24
  43. package/src/bridge/storage.mjs +18 -18
  44. package/src/bridge/storage.test.ts +45 -45
  45. package/src/bridge/types.ts +62 -58
  46. package/src/bridge/window.d.mts +3 -1
  47. package/src/bridge/workspace.d.mts +7 -0
  48. package/src/bridge/workspace.mjs +8 -0
  49. package/src/bridge/workspace.ts +1 -0
  50. package/src/commitments/commitments.test.ts +10 -3
  51. package/src/commitments/commitments.ts +18 -4
  52. package/src/components/accessibility/AccessibilityReviewDialog.tsx +7 -2
  53. package/src/components/accessibility/accessibilityReview.test.ts +11 -4
  54. package/src/components/accessibility/accessibilityReview.ts +18 -10
  55. package/src/components/agent-feedback/ScreenAnnotationAgentDialog.tsx +9 -2
  56. package/src/components/agents/AgentContextUsageBar.tsx +5 -3
  57. package/src/components/agents/AgentDrawerPanel.test.tsx +15 -3
  58. package/src/components/agents/AgentMessageBubble.tsx +1 -3
  59. package/src/components/agents/AgentQuestionPromptList.tsx +3 -3
  60. package/src/components/agents/AgentToolApprovalActions.tsx +1 -3
  61. package/src/components/agents/agentPanelStyles.ts +1 -3
  62. package/src/components/agents/agentToolDisplay.ts +4 -1
  63. package/src/components/assets/asset-library/AssetLibraryDialog.tsx +2 -0
  64. package/src/components/assets/asset-library/AssetLibraryWorkspace.tsx +2 -0
  65. package/src/components/assets/asset-library/detail/AssetLibraryDetailHeader.test.tsx +40 -0
  66. package/src/components/assets/asset-library/detail/AssetLibraryDetailHeader.tsx +7 -3
  67. package/src/components/assets/asset-library/detail/AssetLibraryDetailPreview.tsx +8 -8
  68. package/src/components/assets/asset-library/hooks/useAssetLibraryDialog.ts +13 -2
  69. package/src/components/assets/asset-library/hooks/useAssetLibraryMutations.ts +18 -1
  70. package/src/components/assets/asset-library/sidebar/AssetLibraryListRow.tsx +9 -6
  71. package/src/components/assets/asset-library/sidebar/AssetLibrarySidebarToolbar.tsx +3 -1
  72. package/src/components/assets/asset-library/sidebar/AssetListThumbnail.tsx +1 -1
  73. package/src/components/assets/asset-library/types.ts +6 -0
  74. package/src/components/chrome/OverlayActionCapsule.tsx +2 -2
  75. package/src/components/chrome/PanelTabStrip.tsx +3 -2
  76. package/src/components/chrome/PureAppWordmark.tsx +15 -15
  77. package/src/components/chrome/WorkspaceTabStrip.tsx +19 -14
  78. package/src/components/chrome/documentChromePolicy.test.ts +34 -0
  79. package/src/components/chrome/documentChromePolicy.ts +15 -0
  80. package/src/components/chrome/index.ts +4 -0
  81. package/src/components/chrome/workspaceTabTypes.ts +2 -0
  82. package/src/components/common/buttons/Button.tsx +60 -10
  83. package/src/components/common/buttons/ChoiceChip.tsx +2 -2
  84. package/src/components/common/buttons/IconButton.tsx +26 -0
  85. package/src/components/common/buttons/SegmentedControl.tsx +23 -7
  86. package/src/components/common/canvas/CanvasElementFrame.tsx +37 -28
  87. package/src/components/common/canvas/canvasGeometry.test.ts +4 -5
  88. package/src/components/common/canvas/canvasGeometry.ts +1 -4
  89. package/src/components/common/canvas/useCanvasDragResize.test.tsx +10 -10
  90. package/src/components/common/canvas/useCanvasDragResize.ts +1 -4
  91. package/src/components/common/cards/OpenReviewCard.tsx +6 -6
  92. package/src/components/common/chat/ChatBox.test.tsx +9 -1
  93. package/src/components/common/chat/ChatBox.tsx +3 -4
  94. package/src/components/common/chat/ChatMarkdown.tsx +1 -1
  95. package/src/components/common/chat/ChatModelMenu.tsx +1 -1
  96. package/src/components/common/chat/ChatThinkingIndicator.tsx +1 -1
  97. package/src/components/common/chat/ChatThread.tsx +2 -1
  98. package/src/components/common/chat/ChatToolRow.tsx +2 -2
  99. package/src/components/common/chat/ChatUserBubble.tsx +1 -1
  100. package/src/components/common/connections/ConnectionSetup.tsx +6 -6
  101. package/src/components/common/containers/AppFrame.test.tsx +37 -36
  102. package/src/components/common/containers/AppFrame.tsx +15 -0
  103. package/src/components/common/containers/AppHeader.tsx +6 -3
  104. package/src/components/common/containers/SurfacePanel.tsx +1 -0
  105. package/src/components/common/containers/useOpacityPresence.ts +10 -15
  106. package/src/components/common/context/ContextSelector.tsx +10 -10
  107. package/src/components/common/desk/CreationDesk.tsx +23 -11
  108. package/src/components/common/desk/DailyBrief.tsx +18 -7
  109. package/src/components/common/desk/DeskCard.tsx +11 -6
  110. package/src/components/common/dropdown/MenuButtonDropdown.tsx +58 -6
  111. package/src/components/common/dropdown/MenuDropdownItem.tsx +23 -3
  112. package/src/components/common/dropdown/MenuPanel.tsx +8 -8
  113. package/src/components/common/dropdown/SelectMenu.tsx +8 -3
  114. package/src/components/common/dropdown/menuTypes.ts +2 -1
  115. package/src/components/common/evidence/StructuredEvidenceView.tsx +9 -5
  116. package/src/components/common/feedback/Badge.tsx +19 -5
  117. package/src/components/common/feedback/CapabilityPills.tsx +1 -1
  118. package/src/components/common/feedback/InfoHint.tsx +2 -2
  119. package/src/components/common/feedback/PlatformChip.tsx +9 -9
  120. package/src/components/common/feedback/QuietPill.tsx +5 -8
  121. package/src/components/common/feedback/WorkProgressPanel.tsx +14 -14
  122. package/src/components/common/files/FileTable.tsx +8 -2
  123. package/src/components/common/inputs/Checkbox.tsx +1 -1
  124. package/src/components/common/inputs/EditableSecretField.tsx +1 -3
  125. package/src/components/common/inputs/InlineComposer.tsx +2 -2
  126. package/src/components/common/inputs/PaletteDropdown.tsx +33 -23
  127. package/src/components/common/inputs/SurfacePalettePicker.tsx +1 -1
  128. package/src/components/common/inputs/ToggleSwitch.tsx +2 -2
  129. package/src/components/common/inputs/WorkspacePicker.tsx +3 -3
  130. package/src/components/common/lists/listRowStyles.ts +4 -2
  131. package/src/components/common/lists/quiet-ledger/index.ts +1 -4
  132. package/src/components/common/lists/reorderable/DragHandle.tsx +1 -1
  133. package/src/components/common/lists/reorderable/ReorderableSections.tsx +2 -1
  134. package/src/components/common/media/ImageReferencePicker.tsx +22 -14
  135. package/src/components/common/narrative/NarrativeMention.tsx +15 -9
  136. package/src/components/common/navigation/NavigationCardRow.tsx +2 -2
  137. package/src/components/common/navigation/UnderlineTabs.tsx +1 -0
  138. package/src/components/common/overlays/Modal.tsx +52 -3
  139. package/src/components/common/overlays/ObjectActionStrip.tsx +2 -2
  140. package/src/components/common/people/AutoUpdateReviewList.tsx +2 -2
  141. package/src/components/common/people/EntityList.tsx +7 -3
  142. package/src/components/common/people/EntityPortrait.tsx +6 -1
  143. package/src/components/common/people/LinkedDossierList.tsx +3 -1
  144. package/src/components/common/people/RelationshipMap.tsx +3 -9
  145. package/src/components/common/research/EvidenceDossier.tsx +24 -20
  146. package/src/components/common/tiles/CatalogCard.tsx +1 -1
  147. package/src/components/credentials/CredentialsPanel.tsx +2 -6
  148. package/src/components/data/DataChart.tsx +119 -94
  149. package/src/components/data/dataTable.ts +4 -1
  150. package/src/components/editor/DocumentAppChrome.tsx +172 -0
  151. package/src/components/editor/EditorCommentPromptDialog.tsx +1 -1
  152. package/src/components/editor/EditorLinkPromptDialog.tsx +1 -1
  153. package/src/components/print-design/PrintDesignPanel.test.tsx +8 -6
  154. package/src/components/print-design/PrintDesignPanel.tsx +18 -25
  155. package/src/components/proofing/PagedProofDialog.tsx +17 -4
  156. package/src/editor/EditorViewModeToggle.tsx +6 -2
  157. package/src/editor/index.ts +6 -0
  158. package/src/theme/ThemeProvider.tsx +5 -2
  159. package/src/theme/appAccents.test.ts +51 -0
  160. package/src/theme/appAccents.ts +151 -88
  161. package/src/theme/appIdentityCss.mjs +256 -0
  162. package/src/theme/appIdentityCss.ts +256 -0
  163. package/src/theme/composePlatformTheme.test.ts +43 -14
  164. package/src/theme/platformFont.d.mts +2 -2
  165. package/src/theme/platformFont.mjs +4 -3
  166. package/src/theme/reportsShellChromeSelectors.ts +14 -132
  167. package/src/theme/surfaceCss.mjs +37 -0
  168. package/src/theme/surfaceCss.ts +37 -0
  169. package/src/theme/surfacePalettes.ts +120 -79
  170. package/src/theme/surfaceRoleSelectors.ts +135 -71
  171. package/src/theme/themes/dark.ts +44 -43
  172. package/src/theme/themes/light.ts +40 -38
  173. package/src/theme/themes/palette.ts +32 -30
  174. package/src/theme/themes/shared.ts +17 -17
  175. package/src/theme/utils/GlobalStyles.ts +10 -6
  176. package/src/theme/utils/appFrameDocumentStyles.mjs +6 -1
  177. package/src/theme/utils/cssVariables.ts +169 -0
  178. package/src/writing/DraftAssistantDialog.tsx +85 -85
  179. package/src/writing/WritingStyleManager.tsx +6 -3
  180. package/src/writing/draftTextWithAgent.ts +47 -50
  181. package/src/writing/styleStore.ts +4 -3
  182. package/src/writing/writingStyle.test.ts +8 -2
  183. package/src/writing/writingStyle.ts +19 -8
@@ -0,0 +1,256 @@
1
+ export const appIdentityCss = `
2
+ /*
3
+ * Pure app identity layer.
4
+ *
5
+ * Identity owns only chrome: wordmark name, active tab marker, primary button,
6
+ * and one live/selected region. Theme/status colors remain separate. Hues are
7
+ * perceptually spaced and lightness-staggered so neighbouring apps differ by
8
+ * value as well as hue.
9
+ */
10
+ :root,
11
+ :where([data-app]) {
12
+ --pure-identity-default: #1f9d57;
13
+ --pure-identity-default-bg: #eef7f1;
14
+ --pure-identity-default-tx: #15703f;
15
+ --pure-identity-default-block: #235240;
16
+ --app-acc: var(--pure-identity-default);
17
+ --app-bg: var(--pure-identity-default-bg);
18
+ --app-text: var(--pure-identity-default-tx);
19
+ --app-block: var(--pure-identity-default-block);
20
+ --app-primary-fill: var(--app-acc);
21
+ }
22
+
23
+ [data-app='teams'],
24
+ [data-app='pureteams'] {
25
+ --app-acc: oklch(0.58 0.13 8);
26
+ --app-bg: oklch(0.955 0.03 8);
27
+ --app-text: oklch(0.40 0.12 8);
28
+ --app-block: oklch(0.40 0.06 8);
29
+ }
30
+
31
+ [data-app='vibes'],
32
+ [data-app='purevibes'] {
33
+ --app-acc: oklch(0.50 0.14 26);
34
+ --app-bg: oklch(0.955 0.03 26);
35
+ --app-text: oklch(0.40 0.12 26);
36
+ --app-block: oklch(0.40 0.06 26);
37
+ }
38
+
39
+ [data-app='mail'],
40
+ [data-app='puremail'] {
41
+ --app-acc: oklch(0.60 0.12 44);
42
+ --app-bg: oklch(0.93 0.05 44);
43
+ --app-text: oklch(0.40 0.12 44);
44
+ --app-block: oklch(0.40 0.06 44);
45
+ }
46
+
47
+ [data-app='files'],
48
+ [data-app='purefiles'] {
49
+ --app-acc: oklch(0.50 0.13 64);
50
+ --app-bg: oklch(0.955 0.03 64);
51
+ --app-text: oklch(0.40 0.12 64);
52
+ --app-block: oklch(0.40 0.06 64);
53
+ }
54
+
55
+ [data-app='slides'],
56
+ [data-app='pureslides'] {
57
+ --app-acc: oklch(0.61 0.11 84);
58
+ --app-bg: oklch(0.955 0.03 84);
59
+ --app-text: oklch(0.40 0.11 84);
60
+ --app-block: oklch(0.40 0.06 84);
61
+ }
62
+
63
+ [data-app='writer'],
64
+ [data-app='purewriter'] {
65
+ --app-acc: oklch(0.50 0.12 102);
66
+ --app-bg: oklch(0.955 0.03 102);
67
+ --app-text: oklch(0.40 0.12 102);
68
+ --app-block: oklch(0.40 0.06 102);
69
+ }
70
+
71
+ [data-app='manuscript'],
72
+ [data-app='puremanuscript'] {
73
+ --app-acc: oklch(0.61 0.12 124);
74
+ --app-bg: oklch(0.955 0.03 124);
75
+ --app-text: oklch(0.40 0.12 124);
76
+ --app-block: oklch(0.40 0.06 124);
77
+ }
78
+
79
+ [data-app='book'],
80
+ [data-app='purebook'] {
81
+ --app-acc: oklch(0.48 0.14 148);
82
+ --app-bg: oklch(0.955 0.03 148);
83
+ --app-text: oklch(0.40 0.12 148);
84
+ --app-block: oklch(0.40 0.06 148);
85
+ }
86
+
87
+ [data-app='reports'],
88
+ [data-app='purereports'] {
89
+ --app-acc: oklch(0.61 0.12 166);
90
+ --app-bg: oklch(0.955 0.03 166);
91
+ --app-text: oklch(0.40 0.12 166);
92
+ --app-block: oklch(0.40 0.06 166);
93
+ }
94
+
95
+ [data-app='chart'],
96
+ [data-app='purechart'] {
97
+ --app-acc: oklch(0.48 0.13 184);
98
+ --app-bg: oklch(0.955 0.03 184);
99
+ --app-text: oklch(0.40 0.12 184);
100
+ --app-block: oklch(0.40 0.06 184);
101
+ }
102
+
103
+ [data-app='knowledge'],
104
+ [data-app='pureknowledge'] {
105
+ --app-acc: oklch(0.46 0.11 198);
106
+ --app-bg: oklch(0.955 0.03 198);
107
+ --app-text: oklch(0.40 0.11 198);
108
+ --app-block: oklch(0.40 0.06 198);
109
+ }
110
+
111
+ [data-app='research'],
112
+ [data-app='pureresearch'] {
113
+ --app-acc: oklch(0.63 0.12 222);
114
+ --app-bg: oklch(0.955 0.03 222);
115
+ --app-text: oklch(0.40 0.12 222);
116
+ --app-block: oklch(0.40 0.06 222);
117
+ }
118
+
119
+ [data-app='sheets'],
120
+ [data-app='puresheets'] {
121
+ --app-acc: oklch(0.50 0.13 244);
122
+ --app-bg: oklch(0.955 0.03 244);
123
+ --app-text: oklch(0.40 0.12 244);
124
+ --app-block: oklch(0.40 0.06 244);
125
+ }
126
+
127
+ [data-app='calendar'],
128
+ [data-app='purecalendar'] {
129
+ --app-acc: oklch(0.63 0.13 258);
130
+ --app-bg: oklch(0.955 0.03 258);
131
+ --app-text: oklch(0.40 0.12 258);
132
+ --app-block: oklch(0.40 0.06 258);
133
+ }
134
+
135
+ [data-app='desktop'],
136
+ [data-app='puredesktop'] {
137
+ --app-acc: oklch(0.48 0.13 274);
138
+ --app-bg: oklch(0.955 0.03 274);
139
+ --app-text: oklch(0.40 0.12 274);
140
+ --app-block: oklch(0.40 0.06 274);
141
+ }
142
+
143
+ [data-app='plan'],
144
+ [data-app='pureplan'] {
145
+ --app-acc: oklch(0.61 0.14 290);
146
+ --app-bg: oklch(0.955 0.03 290);
147
+ --app-text: oklch(0.40 0.12 290);
148
+ --app-block: oklch(0.40 0.06 290);
149
+ }
150
+
151
+ [data-app='review'],
152
+ [data-app='purereview'] {
153
+ --app-acc: oklch(0.50 0.15 308);
154
+ --app-bg: oklch(0.955 0.03 308);
155
+ --app-text: oklch(0.40 0.12 308);
156
+ --app-block: oklch(0.40 0.06 308);
157
+ }
158
+
159
+ [data-app='tasks'],
160
+ [data-app='puretasks'] {
161
+ --app-acc: oklch(0.63 0.15 324);
162
+ --app-bg: oklch(0.955 0.03 324);
163
+ --app-text: oklch(0.40 0.12 324);
164
+ --app-block: oklch(0.40 0.06 324);
165
+ }
166
+
167
+ [data-app='assistant'],
168
+ [data-app='pureassistant'] {
169
+ --app-acc: oklch(0.50 0.15 340);
170
+ --app-bg: oklch(0.955 0.03 340);
171
+ --app-text: oklch(0.40 0.12 340);
172
+ --app-block: oklch(0.40 0.06 340);
173
+ }
174
+
175
+ [data-app='people'],
176
+ [data-app='purepeople'] {
177
+ --app-acc: oklch(0.61 0.14 356);
178
+ --app-bg: oklch(0.955 0.03 356);
179
+ --app-text: oklch(0.40 0.12 356);
180
+ --app-block: oklch(0.40 0.06 356);
181
+ }
182
+
183
+ [data-app='slides'],
184
+ [data-app='pureslides'],
185
+ [data-app='manuscript'],
186
+ [data-app='puremanuscript'],
187
+ [data-app='reports'],
188
+ [data-app='purereports'],
189
+ [data-app='research'],
190
+ [data-app='pureresearch'],
191
+ [data-app='calendar'],
192
+ [data-app='purecalendar'],
193
+ [data-app='plan'],
194
+ [data-app='pureplan'],
195
+ [data-app='tasks'],
196
+ [data-app='puretasks'],
197
+ [data-app='people'],
198
+ [data-app='purepeople'] {
199
+ --app-primary-fill: var(--app-block);
200
+ }
201
+
202
+ .pure-wordmark__prefix {
203
+ color: var(--platform-colors-text-tertiary, #9a9aa0);
204
+ }
205
+
206
+ .pure-wordmark__name {
207
+ color: var(--app-acc, var(--platform-colors-text));
208
+ font-weight: 700;
209
+ }
210
+
211
+ .pure-tab.is-active {
212
+ box-shadow: inset 0 -2px 0 0 var(--app-acc, var(--platform-colors-text));
213
+ }
214
+
215
+ .pure-viewtab.is-active {
216
+ border-bottom-color: var(--app-acc, var(--platform-colors-text));
217
+ }
218
+
219
+ .pure-btn--primary {
220
+ background: var(--app-primary-fill, var(--app-acc, var(--platform-colors-text)));
221
+ border-color: var(--app-primary-fill, var(--app-acc, var(--platform-colors-text)));
222
+ color: #fff;
223
+ }
224
+
225
+ .pure-btn--primary.is-light {
226
+ background: var(--app-block, var(--platform-colors-text));
227
+ border-color: var(--app-block, var(--platform-colors-text));
228
+ }
229
+
230
+ .pure-btn--bordered {
231
+ background: var(--platform-colors-surface, #fff);
232
+ border-color: var(--app-acc, var(--platform-colors-text));
233
+ color: var(--app-text, var(--platform-colors-text));
234
+ }
235
+
236
+ .pure-selected {
237
+ border-left-color: var(--app-acc, var(--platform-colors-accent));
238
+ background: var(--platform-colors-surface, #fff);
239
+ }
240
+
241
+ .pure-selected--chip {
242
+ background: var(--app-bg, var(--platform-colors-surface-muted));
243
+ }
244
+
245
+ .pure-active-col {
246
+ border-color: var(--app-acc, var(--platform-colors-accent));
247
+ border-top-color: var(--app-acc, var(--platform-colors-accent));
248
+ border-radius: 0;
249
+ background: var(--platform-colors-surface, #fff);
250
+ }
251
+
252
+ .pure-block {
253
+ background: var(--app-block, var(--platform-colors-text));
254
+ color: #fff;
255
+ }
256
+ `
@@ -0,0 +1,256 @@
1
+ export const appIdentityCss = `
2
+ /*
3
+ * Pure app identity layer.
4
+ *
5
+ * Identity owns only chrome: wordmark name, active tab marker, primary button,
6
+ * and one live/selected region. Theme/status colors remain separate. Hues are
7
+ * perceptually spaced and lightness-staggered so neighbouring apps differ by
8
+ * value as well as hue.
9
+ */
10
+ :root,
11
+ :where([data-app]) {
12
+ --pure-identity-default: #1f9d57;
13
+ --pure-identity-default-bg: #eef7f1;
14
+ --pure-identity-default-tx: #15703f;
15
+ --pure-identity-default-block: #235240;
16
+ --app-acc: var(--pure-identity-default);
17
+ --app-bg: var(--pure-identity-default-bg);
18
+ --app-text: var(--pure-identity-default-tx);
19
+ --app-block: var(--pure-identity-default-block);
20
+ --app-primary-fill: var(--app-acc);
21
+ }
22
+
23
+ [data-app='teams'],
24
+ [data-app='pureteams'] {
25
+ --app-acc: oklch(0.58 0.13 8);
26
+ --app-bg: oklch(0.955 0.03 8);
27
+ --app-text: oklch(0.40 0.12 8);
28
+ --app-block: oklch(0.40 0.06 8);
29
+ }
30
+
31
+ [data-app='vibes'],
32
+ [data-app='purevibes'] {
33
+ --app-acc: oklch(0.50 0.14 26);
34
+ --app-bg: oklch(0.955 0.03 26);
35
+ --app-text: oklch(0.40 0.12 26);
36
+ --app-block: oklch(0.40 0.06 26);
37
+ }
38
+
39
+ [data-app='mail'],
40
+ [data-app='puremail'] {
41
+ --app-acc: oklch(0.60 0.12 44);
42
+ --app-bg: oklch(0.93 0.05 44);
43
+ --app-text: oklch(0.40 0.12 44);
44
+ --app-block: oklch(0.40 0.06 44);
45
+ }
46
+
47
+ [data-app='files'],
48
+ [data-app='purefiles'] {
49
+ --app-acc: oklch(0.50 0.13 64);
50
+ --app-bg: oklch(0.955 0.03 64);
51
+ --app-text: oklch(0.40 0.12 64);
52
+ --app-block: oklch(0.40 0.06 64);
53
+ }
54
+
55
+ [data-app='slides'],
56
+ [data-app='pureslides'] {
57
+ --app-acc: oklch(0.61 0.11 84);
58
+ --app-bg: oklch(0.955 0.03 84);
59
+ --app-text: oklch(0.40 0.11 84);
60
+ --app-block: oklch(0.40 0.06 84);
61
+ }
62
+
63
+ [data-app='writer'],
64
+ [data-app='purewriter'] {
65
+ --app-acc: oklch(0.50 0.12 102);
66
+ --app-bg: oklch(0.955 0.03 102);
67
+ --app-text: oklch(0.40 0.12 102);
68
+ --app-block: oklch(0.40 0.06 102);
69
+ }
70
+
71
+ [data-app='manuscript'],
72
+ [data-app='puremanuscript'] {
73
+ --app-acc: oklch(0.61 0.12 124);
74
+ --app-bg: oklch(0.955 0.03 124);
75
+ --app-text: oklch(0.40 0.12 124);
76
+ --app-block: oklch(0.40 0.06 124);
77
+ }
78
+
79
+ [data-app='book'],
80
+ [data-app='purebook'] {
81
+ --app-acc: oklch(0.48 0.14 148);
82
+ --app-bg: oklch(0.955 0.03 148);
83
+ --app-text: oklch(0.40 0.12 148);
84
+ --app-block: oklch(0.40 0.06 148);
85
+ }
86
+
87
+ [data-app='reports'],
88
+ [data-app='purereports'] {
89
+ --app-acc: oklch(0.61 0.12 166);
90
+ --app-bg: oklch(0.955 0.03 166);
91
+ --app-text: oklch(0.40 0.12 166);
92
+ --app-block: oklch(0.40 0.06 166);
93
+ }
94
+
95
+ [data-app='chart'],
96
+ [data-app='purechart'] {
97
+ --app-acc: oklch(0.48 0.13 184);
98
+ --app-bg: oklch(0.955 0.03 184);
99
+ --app-text: oklch(0.40 0.12 184);
100
+ --app-block: oklch(0.40 0.06 184);
101
+ }
102
+
103
+ [data-app='knowledge'],
104
+ [data-app='pureknowledge'] {
105
+ --app-acc: oklch(0.46 0.11 198);
106
+ --app-bg: oklch(0.955 0.03 198);
107
+ --app-text: oklch(0.40 0.11 198);
108
+ --app-block: oklch(0.40 0.06 198);
109
+ }
110
+
111
+ [data-app='research'],
112
+ [data-app='pureresearch'] {
113
+ --app-acc: oklch(0.63 0.12 222);
114
+ --app-bg: oklch(0.955 0.03 222);
115
+ --app-text: oklch(0.40 0.12 222);
116
+ --app-block: oklch(0.40 0.06 222);
117
+ }
118
+
119
+ [data-app='sheets'],
120
+ [data-app='puresheets'] {
121
+ --app-acc: oklch(0.50 0.13 244);
122
+ --app-bg: oklch(0.955 0.03 244);
123
+ --app-text: oklch(0.40 0.12 244);
124
+ --app-block: oklch(0.40 0.06 244);
125
+ }
126
+
127
+ [data-app='calendar'],
128
+ [data-app='purecalendar'] {
129
+ --app-acc: oklch(0.63 0.13 258);
130
+ --app-bg: oklch(0.955 0.03 258);
131
+ --app-text: oklch(0.40 0.12 258);
132
+ --app-block: oklch(0.40 0.06 258);
133
+ }
134
+
135
+ [data-app='desktop'],
136
+ [data-app='puredesktop'] {
137
+ --app-acc: oklch(0.48 0.13 274);
138
+ --app-bg: oklch(0.955 0.03 274);
139
+ --app-text: oklch(0.40 0.12 274);
140
+ --app-block: oklch(0.40 0.06 274);
141
+ }
142
+
143
+ [data-app='plan'],
144
+ [data-app='pureplan'] {
145
+ --app-acc: oklch(0.61 0.14 290);
146
+ --app-bg: oklch(0.955 0.03 290);
147
+ --app-text: oklch(0.40 0.12 290);
148
+ --app-block: oklch(0.40 0.06 290);
149
+ }
150
+
151
+ [data-app='review'],
152
+ [data-app='purereview'] {
153
+ --app-acc: oklch(0.50 0.15 308);
154
+ --app-bg: oklch(0.955 0.03 308);
155
+ --app-text: oklch(0.40 0.12 308);
156
+ --app-block: oklch(0.40 0.06 308);
157
+ }
158
+
159
+ [data-app='tasks'],
160
+ [data-app='puretasks'] {
161
+ --app-acc: oklch(0.63 0.15 324);
162
+ --app-bg: oklch(0.955 0.03 324);
163
+ --app-text: oklch(0.40 0.12 324);
164
+ --app-block: oklch(0.40 0.06 324);
165
+ }
166
+
167
+ [data-app='assistant'],
168
+ [data-app='pureassistant'] {
169
+ --app-acc: oklch(0.50 0.15 340);
170
+ --app-bg: oklch(0.955 0.03 340);
171
+ --app-text: oklch(0.40 0.12 340);
172
+ --app-block: oklch(0.40 0.06 340);
173
+ }
174
+
175
+ [data-app='people'],
176
+ [data-app='purepeople'] {
177
+ --app-acc: oklch(0.61 0.14 356);
178
+ --app-bg: oklch(0.955 0.03 356);
179
+ --app-text: oklch(0.40 0.12 356);
180
+ --app-block: oklch(0.40 0.06 356);
181
+ }
182
+
183
+ [data-app='slides'],
184
+ [data-app='pureslides'],
185
+ [data-app='manuscript'],
186
+ [data-app='puremanuscript'],
187
+ [data-app='reports'],
188
+ [data-app='purereports'],
189
+ [data-app='research'],
190
+ [data-app='pureresearch'],
191
+ [data-app='calendar'],
192
+ [data-app='purecalendar'],
193
+ [data-app='plan'],
194
+ [data-app='pureplan'],
195
+ [data-app='tasks'],
196
+ [data-app='puretasks'],
197
+ [data-app='people'],
198
+ [data-app='purepeople'] {
199
+ --app-primary-fill: var(--app-block);
200
+ }
201
+
202
+ .pure-wordmark__prefix {
203
+ color: var(--platform-colors-text-tertiary, #9a9aa0);
204
+ }
205
+
206
+ .pure-wordmark__name {
207
+ color: var(--app-acc, var(--platform-colors-text));
208
+ font-weight: 700;
209
+ }
210
+
211
+ .pure-tab.is-active {
212
+ box-shadow: inset 0 -2px 0 0 var(--app-acc, var(--platform-colors-text));
213
+ }
214
+
215
+ .pure-viewtab.is-active {
216
+ border-bottom-color: var(--app-acc, var(--platform-colors-text));
217
+ }
218
+
219
+ .pure-btn--primary {
220
+ background: var(--app-primary-fill, var(--app-acc, var(--platform-colors-text)));
221
+ border-color: var(--app-primary-fill, var(--app-acc, var(--platform-colors-text)));
222
+ color: #fff;
223
+ }
224
+
225
+ .pure-btn--primary.is-light {
226
+ background: var(--app-block, var(--platform-colors-text));
227
+ border-color: var(--app-block, var(--platform-colors-text));
228
+ }
229
+
230
+ .pure-btn--bordered {
231
+ background: var(--platform-colors-surface, #fff);
232
+ border-color: var(--app-acc, var(--platform-colors-text));
233
+ color: var(--app-text, var(--platform-colors-text));
234
+ }
235
+
236
+ .pure-selected {
237
+ border-left-color: var(--app-acc, var(--platform-colors-accent));
238
+ background: var(--platform-colors-surface, #fff);
239
+ }
240
+
241
+ .pure-selected--chip {
242
+ background: var(--app-bg, var(--platform-colors-surface-muted));
243
+ }
244
+
245
+ .pure-active-col {
246
+ border-color: var(--app-acc, var(--platform-colors-accent));
247
+ border-top-color: var(--app-acc, var(--platform-colors-accent));
248
+ border-radius: 0;
249
+ background: var(--platform-colors-surface, #fff);
250
+ }
251
+
252
+ .pure-block {
253
+ background: var(--app-block, var(--platform-colors-text));
254
+ color: #fff;
255
+ }
256
+ `
@@ -4,14 +4,17 @@ import { darkTheme } from './themes/dark.js'
4
4
  import { lightTheme } from './themes/light.js'
5
5
 
6
6
  describe('composePlatformTheme', () => {
7
- it('applies writer accent and ink surface palette in light mode', () => {
7
+ it('applies ink surface palette in light mode without changing identity chrome', () => {
8
8
  const theme = composePlatformTheme(lightTheme, {
9
9
  appSlug: 'writer',
10
10
  surfacePaletteId: 'ink',
11
11
  })
12
- expect(theme.colors.appViewport).toBe('#f5f3ef')
13
- expect(theme.colors.text).toBe('#2e3338')
14
- expect(theme.colors.accent).toBe('#525a65')
12
+ expect(theme.colors.appViewport).toBe('#eef2f7')
13
+ expect(theme.colors.surface).toBe('#fcfdfe')
14
+ expect(theme.colors.text).toBe('#171b21')
15
+ expect(theme.colors.textSecondary).toBe('#48515c')
16
+ expect(theme.colors.accent).toBe('#34506f')
17
+ expect(theme.colors.accentMuted).toBe('#dde7f1')
15
18
  })
16
19
 
17
20
  it('applies surface palette roles in dark mode', () => {
@@ -19,26 +22,52 @@ describe('composePlatformTheme', () => {
19
22
  appSlug: 'writer',
20
23
  surfacePaletteId: 'sepia',
21
24
  })
22
- expect(theme.colors.appViewport).toBe('#1a1814')
23
- expect(theme.colors.text).toBe('#ece6dc')
24
- expect(theme.colors.surface).toBe('#242019')
25
- expect(theme.colors.textInverse).toBe('#1a1814')
25
+ expect(theme.colors.appViewport).toBe('#1b1b1e')
26
+ expect(theme.colors.text).toBe('#eaeaee')
27
+ expect(theme.colors.surface).toBe('#26262a')
28
+ expect(theme.colors.textInverse).toBe('#1b1b1e')
26
29
  })
27
30
 
28
- it('darkens warm app accent fills in dark mode', () => {
31
+ it('applies pushed named theme values in light mode', () => {
32
+ const sepia = composePlatformTheme(lightTheme, {
33
+ surfacePaletteId: 'sepia',
34
+ })
35
+ expect(sepia.colors.text).toBe('#33260f')
36
+ expect(sepia.colors.textSecondary).toBe('#675135')
37
+ expect(sepia.colors.divider).toBe('#e7dcc4')
38
+ expect(sepia.colors.surface).toBe('#fcf8ef')
39
+ expect(sepia.colors.appViewport).toBe('#f4ecd8')
40
+ expect(sepia.colors.accent).toBe('#a25c00')
41
+ expect(sepia.colors.accentMuted).toBe('#ecd49b')
42
+ expect(sepia.colors.semanticGreenText).toBe('#6e4400')
43
+
44
+ const plum = composePlatformTheme(lightTheme, {
45
+ surfacePaletteId: 'plum',
46
+ })
47
+ expect(plum.colors.text).toBe('#261426')
48
+ expect(plum.colors.textSecondary).toBe('#554656')
49
+ expect(plum.colors.divider).toBe('#e6dbeb')
50
+ expect(plum.colors.surface).toBe('#fdfafd')
51
+ expect(plum.colors.appViewport).toBe('#f3ecf6')
52
+ expect(plum.colors.accent).toBe('#8a2ba6')
53
+ expect(plum.colors.accentMuted).toBe('#e9d0f3')
54
+ expect(plum.colors.semanticGreenText).toBe('#622970')
55
+ })
56
+
57
+ it('keeps neutral app identity out of the dark platform theme accent', () => {
29
58
  const theme = composePlatformTheme(darkTheme, {
30
59
  appSlug: 'book',
31
60
  })
32
- expect(theme.colors.accent).toBe('hsl(150, 48%, 30%)')
33
- expect(theme.colors.accentMuted).toBe('hsl(150, 34%, 22%)')
61
+ expect(theme.colors.accent).toBe(darkTheme.colors.accent)
62
+ expect(theme.colors.accentMuted).toBe(darkTheme.colors.accentMuted)
34
63
  })
35
64
 
36
- it('darkens cyan app accent fills in dark mode', () => {
65
+ it('keeps hue app identity separate from the dark platform theme accent', () => {
37
66
  const theme = composePlatformTheme(darkTheme, {
38
67
  appSlug: 'teams',
39
68
  })
40
- expect(theme.colors.accent).toBe('hsl(188, 48%, 30%)')
41
- expect(theme.colors.accentMuted).toBe('hsl(188, 34%, 22%)')
69
+ expect(theme.colors.accent).toBe(darkTheme.colors.accent)
70
+ expect(theme.colors.accentMuted).toBe(darkTheme.colors.accentMuted)
42
71
  })
43
72
 
44
73
  it('returns base theme when composition is empty', () => {
@@ -1,6 +1,6 @@
1
- export declare const PLATFORM_FONT_FAMILY: '"Schibsted Grotesk", sans-serif'
1
+ export declare const PLATFORM_FONT_FAMILY: '"Archivo", system-ui, -apple-system, "Segoe UI", sans-serif'
2
2
 
3
- export declare const PLATFORM_FONT_STYLESHEET_ID: 'platform-font-schibsted-grotesk'
3
+ export declare const PLATFORM_FONT_STYLESHEET_ID: 'platform-font-suite'
4
4
 
5
5
  export declare const PLATFORM_FONT_STYLESHEET_URL: string
6
6
 
@@ -1,10 +1,11 @@
1
1
  /** Shared platform UI font — loaded in shell ThemeProvider and AppFrame iframe apps. */
2
- export const PLATFORM_FONT_FAMILY = '"Schibsted Grotesk", sans-serif'
2
+ export const PLATFORM_FONT_FAMILY =
3
+ '"Archivo", system-ui, -apple-system, "Segoe UI", sans-serif'
3
4
 
4
- export const PLATFORM_FONT_STYLESHEET_ID = 'platform-font-schibsted-grotesk'
5
+ export const PLATFORM_FONT_STYLESHEET_ID = 'platform-font-suite'
5
6
 
6
7
  export const PLATFORM_FONT_STYLESHEET_URL =
7
- 'https://fonts.googleapis.com/css2?family=Schibsted+Grotesk:ital,wght@0,400..900;1,400..900&display=swap'
8
+ 'https://fonts.googleapis.com/css2?family=Archivo:wght@400;500;600;700&family=Source+Serif+4:opsz,wght@8..60,400;8..60,600;8..60,700&family=JetBrains+Mono:wght@400;500;600&display=swap'
8
9
 
9
10
  /**
10
11
  * @param {Document} [doc]