@appsolutely-io/waypoint 0.0.0-stage → 0.1.1-next.0

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 (161) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +260 -2
  3. package/dist/block-reply-DN4RiLL0.d.cts +169 -0
  4. package/dist/block-reply-Dtof9ild.d.ts +169 -0
  5. package/dist/blocks-25YOJ5SS.cjs +1 -0
  6. package/dist/blocks-UJ7GUJHD.js +1 -0
  7. package/dist/chunk-3KV7TDDR.cjs +3 -0
  8. package/dist/chunk-4BWV3SEL.cjs +1 -0
  9. package/dist/chunk-4ZGW4HM4.cjs +1 -0
  10. package/dist/chunk-5TBO732O.js +1 -0
  11. package/dist/chunk-6OZSKCPT.cjs +1 -0
  12. package/dist/chunk-C3VS33WJ.js +1 -0
  13. package/dist/chunk-D2EGPBCX.cjs +1 -0
  14. package/dist/chunk-FBADWFRR.cjs +1 -0
  15. package/dist/chunk-FQSWQLRW.js +1 -0
  16. package/dist/chunk-GT6PI4CT.cjs +1 -0
  17. package/dist/chunk-II26UWZM.cjs +1 -0
  18. package/dist/chunk-JFMVVGGB.js +1 -0
  19. package/dist/chunk-K73VV7KA.js +1 -0
  20. package/dist/chunk-L4PFFRDE.js +3 -0
  21. package/dist/chunk-LLPGVQUT.cjs +1 -0
  22. package/dist/chunk-M3UENQ6L.cjs +1 -0
  23. package/dist/chunk-M63QOANE.js +1 -0
  24. package/dist/chunk-MEKDQDSV.js +1 -0
  25. package/dist/chunk-OEPKPDLD.js +1 -0
  26. package/dist/chunk-OWT55N6J.js +3 -0
  27. package/dist/chunk-PFR2J5BV.js +1 -0
  28. package/dist/chunk-Q6BD2YL3.cjs +1 -0
  29. package/dist/chunk-Q7BULGQG.cjs +1 -0
  30. package/dist/chunk-QS3MKZOY.cjs +3 -0
  31. package/dist/chunk-RHBDQGD4.js +1 -0
  32. package/dist/chunk-RZZDQWC2.js +1 -0
  33. package/dist/chunk-S73WZWDP.js +1 -0
  34. package/dist/chunk-SD2KAIVE.js +1 -0
  35. package/dist/chunk-T5XF2R74.js +1 -0
  36. package/dist/chunk-TCFCSGQ3.js +1 -0
  37. package/dist/chunk-TGL3DR2K.js +1 -0
  38. package/dist/chunk-TODYQ3SG.cjs +1 -0
  39. package/dist/chunk-TVSQHTK2.cjs +1 -0
  40. package/dist/chunk-UYR3UEIW.cjs +1 -0
  41. package/dist/chunk-VGGJGRNK.cjs +1 -0
  42. package/dist/chunk-W6Y7H56X.js +1 -0
  43. package/dist/chunk-XSHOLIC7.cjs +1 -0
  44. package/dist/chunk-XWDB2LS3.cjs +1 -0
  45. package/dist/cli.js +3 -0
  46. package/dist/confirmation-view-CICNJJIO.js +1 -0
  47. package/dist/confirmation-view-OMWHUYVC.cjs +1 -0
  48. package/dist/conformance.cjs +1 -0
  49. package/dist/conformance.d.cts +10 -0
  50. package/dist/conformance.d.ts +10 -0
  51. package/dist/conformance.js +1 -0
  52. package/dist/flow-parser.cjs +1 -0
  53. package/dist/flow-parser.d.cts +3 -0
  54. package/dist/flow-parser.d.ts +3 -0
  55. package/dist/flow-parser.js +1 -0
  56. package/dist/flows-panel-AIULKYOS.cjs +1 -0
  57. package/dist/flows-panel-YEJ36RTY.js +1 -0
  58. package/dist/form-extras-QYE32TUY.cjs +1 -0
  59. package/dist/form-extras-SBBOMJS2.js +1 -0
  60. package/dist/form-fill-C32AHxSr.d.cts +653 -0
  61. package/dist/form-fill-Dp3ut1_Y.d.ts +653 -0
  62. package/dist/form-session.cjs +1 -0
  63. package/dist/form-session.d.cts +7 -0
  64. package/dist/form-session.d.ts +7 -0
  65. package/dist/form-session.js +1 -0
  66. package/dist/frame-decoder.cjs +3 -0
  67. package/dist/frame-decoder.d.cts +5 -0
  68. package/dist/frame-decoder.d.ts +5 -0
  69. package/dist/frame-decoder.js +3 -0
  70. package/dist/generated-C9tbjwK0.d.cts +797 -0
  71. package/dist/generated-C9tbjwK0.d.ts +797 -0
  72. package/dist/hooks/index.cjs +1 -0
  73. package/dist/hooks/index.d.cts +48 -0
  74. package/dist/hooks/index.d.ts +48 -0
  75. package/dist/hooks/index.js +1 -0
  76. package/dist/i18n-DPNfYTMG.d.cts +148 -0
  77. package/dist/i18n-DPNfYTMG.d.ts +148 -0
  78. package/dist/index-B5idIFTx.d.cts +34 -0
  79. package/dist/index-DPzoKXCK.d.ts +34 -0
  80. package/dist/index.cjs +3 -0
  81. package/dist/index.d.cts +38 -0
  82. package/dist/index.d.ts +38 -0
  83. package/dist/index.js +3 -0
  84. package/dist/intent-BQPPows1.d.cts +154 -0
  85. package/dist/intent-BuvqEU3Q.d.ts +154 -0
  86. package/dist/intent.cjs +1 -0
  87. package/dist/intent.d.cts +2 -0
  88. package/dist/intent.d.ts +2 -0
  89. package/dist/intent.js +1 -0
  90. package/dist/markdown-BSRKJFFE.cjs +17 -0
  91. package/dist/markdown-ETLB66BK.js +17 -0
  92. package/dist/message-actions-3HGE6VTS.js +1 -0
  93. package/dist/message-actions-F6SPLTT7.cjs +1 -0
  94. package/dist/messages/en/index.cjs +1 -0
  95. package/dist/messages/en/index.d.cts +3 -0
  96. package/dist/messages/en/index.d.ts +3 -0
  97. package/dist/messages/en/index.js +1 -0
  98. package/dist/messages/index.cjs +1 -0
  99. package/dist/messages/index.d.cts +14 -0
  100. package/dist/messages/index.d.ts +14 -0
  101. package/dist/messages/index.js +1 -0
  102. package/dist/messages/zh-Hans/index.cjs +1 -0
  103. package/dist/messages/zh-Hans/index.d.cts +3 -0
  104. package/dist/messages/zh-Hans/index.d.ts +3 -0
  105. package/dist/messages/zh-Hans/index.js +1 -0
  106. package/dist/on-demand.cjs +1 -0
  107. package/dist/on-demand.d.cts +56 -0
  108. package/dist/on-demand.d.ts +56 -0
  109. package/dist/on-demand.js +1 -0
  110. package/dist/problem-messages-THONMXFZ.cjs +1 -0
  111. package/dist/problem-messages-Z5QGO6RE.js +1 -0
  112. package/dist/react/index.cjs +1 -0
  113. package/dist/react/index.d.cts +419 -0
  114. package/dist/react/index.d.ts +419 -0
  115. package/dist/react/index.js +1 -0
  116. package/dist/reads-Bk84x_rt.d.ts +38 -0
  117. package/dist/reads-DlpCt8dE.d.cts +38 -0
  118. package/dist/recovery-panel-OWY2CWOH.cjs +3 -0
  119. package/dist/recovery-panel-VOKVDDZD.js +3 -0
  120. package/dist/reply-controls-5CWIAKIG.js +1 -0
  121. package/dist/reply-controls-CPWB4VBK.cjs +1 -0
  122. package/dist/run-XBABOEXK.js +1 -0
  123. package/dist/schema.json +2900 -0
  124. package/dist/skin-antd/index.cjs +1 -0
  125. package/dist/skin-antd/index.d.cts +30 -0
  126. package/dist/skin-antd/index.d.ts +30 -0
  127. package/dist/skin-antd/index.js +1 -0
  128. package/dist/skin-default/index.cjs +1 -0
  129. package/dist/skin-default/index.d.cts +42 -0
  130. package/dist/skin-default/index.d.ts +42 -0
  131. package/dist/skin-default/index.js +1 -0
  132. package/dist/step-name-3hQ6CCGr.d.cts +19 -0
  133. package/dist/step-name-BdkYnb5g.d.ts +19 -0
  134. package/dist/storage-commit.cjs +1 -0
  135. package/dist/storage-commit.d.cts +17 -0
  136. package/dist/storage-commit.d.ts +17 -0
  137. package/dist/storage-commit.js +1 -0
  138. package/dist/stream-reads.cjs +1 -0
  139. package/dist/stream-reads.d.cts +22 -0
  140. package/dist/stream-reads.d.ts +22 -0
  141. package/dist/stream-reads.js +1 -0
  142. package/dist/styles.css +796 -0
  143. package/dist/testing/index.cjs +1 -0
  144. package/dist/testing/index.d.cts +57 -0
  145. package/dist/testing/index.d.ts +57 -0
  146. package/dist/testing/index.js +1 -0
  147. package/docs/examples/message-versions.tsx +74 -0
  148. package/docs/form-fill-protocol.md +83 -0
  149. package/docs/message-versions.md +64 -0
  150. package/docs/plan-protocol.md +83 -0
  151. package/docs/reply-protocol.md +75 -0
  152. package/etc/hooks.api.md +2385 -0
  153. package/etc/index.api.md +2159 -0
  154. package/etc/messages-en.api.md +13 -0
  155. package/etc/messages-zh-Hans.api.md +13 -0
  156. package/etc/messages.api.md +183 -0
  157. package/etc/react.api.md +2968 -0
  158. package/etc/skin-antd.api.md +2989 -0
  159. package/etc/skin-default.api.md +61 -0
  160. package/etc/testing.api.md +3034 -0
  161. package/package.json +168 -4
@@ -0,0 +1,796 @@
1
+ .waypoint {
2
+ /* Its padding and border count inside its width, so it is never wider
3
+ than its container (WCAG 1.4.10). */
4
+ box-sizing: border-box;
5
+ max-inline-size: 100%;
6
+ container-type: inline-size;
7
+ color: var(--wp-foreground);
8
+ background: var(--wp-background);
9
+ font-family: var(--wp-font-family);
10
+ font-size: var(--wp-font-size);
11
+ border: 1px solid var(--wp-border);
12
+ border-radius: var(--wp-radius);
13
+ padding: var(--wp-space);
14
+ box-shadow: var(--wp-shadow);
15
+ }
16
+ .waypoint * {
17
+ box-sizing: border-box;
18
+ }
19
+ .waypoint .wp-shell {
20
+ display: grid;
21
+ grid-template-columns: minmax(8rem, 1fr) minmax(0, 3fr);
22
+ gap: var(--wp-space);
23
+ }
24
+ /* The plan column only while a plan is shown. */
25
+ .waypoint .wp-shell[data-has-aside] {
26
+ grid-template-columns: minmax(8rem, 1fr) minmax(0, 3fr) minmax(0, 1fr);
27
+ }
28
+ /* No rail column without a conversation list (or a host's own rail). */
29
+ .waypoint .wp-shell:not([data-has-rail]) {
30
+ grid-template-columns: minmax(0, 1fr);
31
+ }
32
+ .waypoint .wp-shell:not([data-has-rail])[data-has-aside] {
33
+ grid-template-columns: minmax(0, 3fr) minmax(0, 1fr);
34
+ }
35
+ .waypoint .wp-shell:not([data-has-rail]) > [data-part="rail"] {
36
+ display: none;
37
+ }
38
+ .waypoint main {
39
+ min-inline-size: 0;
40
+ }
41
+ /* In the conversation (narrow), the plan stands apart from what follows. */
42
+ .waypoint main > [data-plan] {
43
+ margin-block-end: var(--wp-space);
44
+ }
45
+ .waypoint [data-part] {
46
+ color: var(--wp-foreground);
47
+ transition: color var(--wp-motion) var(--wp-easing);
48
+ }
49
+ /* A visible focus ring, 3:1 against what is around it (WCAG 1.4.11). */
50
+ .waypoint :focus-visible {
51
+ outline: 2px solid var(--wp-focus-ring);
52
+ outline-offset: 2px;
53
+ }
54
+ /* Status by tone; the text always says it too. */
55
+ .waypoint [data-reply-state="writing"] {
56
+ color: var(--wp-muted);
57
+ }
58
+ .waypoint [data-reply-state="overdue"],
59
+ .waypoint [data-tone="warning"] {
60
+ color: var(--wp-warning);
61
+ }
62
+ .waypoint [data-reply-state="failed"],
63
+ .waypoint [data-reply-state="unavailable"],
64
+ .waypoint [data-reply-ended],
65
+ .waypoint [data-tone="danger"] {
66
+ color: var(--wp-danger);
67
+ }
68
+ .waypoint [data-tone="success"] {
69
+ color: var(--wp-success);
70
+ }
71
+ .waypoint [data-body-unavailable] [data-part="bubble"] {
72
+ display: none;
73
+ }
74
+ /* A bubble's text and its blocks are spaced like Markdown blocks. */
75
+ .waypoint [data-part="bubble"] > * + * {
76
+ margin-block-start: var(--wp-space);
77
+ }
78
+ .waypoint [data-part="bubble"] {
79
+ padding: var(--wp-space);
80
+ border-radius: var(--wp-radius);
81
+ background: var(--wp-surface);
82
+ margin-block-end: var(--wp-space);
83
+ }
84
+ /* Who wrote a message, first in its bubble and close to what it says. */
85
+ .waypoint [data-sender] {
86
+ display: block;
87
+ color: var(--wp-muted);
88
+ font-size: var(--wp-font-size-sm);
89
+ font-weight: 600;
90
+ }
91
+ .waypoint [data-sender] + * {
92
+ margin-block-start: var(--wp-space1);
93
+ }
94
+ /* The user's messages sit at the inline end on an accent-tinted surface,
95
+ the assistant's at the start on the surface. The tint is 16% in dark,
96
+ where the surfaces are closer, so the two read as far apart as in light.
97
+ It is used only where its colours are checked: waypoint's tokens, and a
98
+ host antd theme whose colours the antd skin can read (it checks or
99
+ adjusts them there). Under a `theme` prop, whose colours are not
100
+ checked, or colours the skin cannot read (the skin sets the same two
101
+ properties), the bubble keeps the plain surface, where those colours
102
+ already hold, with an accent start edge. */
103
+ /* Set on every chat, so an outer chat's or a host's values never leak in. */
104
+ .waypoint {
105
+ --wp-user-tint: 12%;
106
+ --wp-user-edge: 0px;
107
+ }
108
+ .waypoint[data-color-scheme="dark"] {
109
+ --wp-user-tint: 16%;
110
+ }
111
+ .waypoint[data-custom-theme] {
112
+ --wp-user-tint: 0%;
113
+ --wp-user-edge: 3px;
114
+ }
115
+ .waypoint article:is([data-role="user"], [data-role="pending"]) {
116
+ display: flex;
117
+ flex-direction: column;
118
+ align-items: flex-end;
119
+ }
120
+ .waypoint
121
+ article:is([data-role="user"], [data-role="pending"])
122
+ > [data-part="bubble"] {
123
+ max-inline-size: 85%;
124
+ background: color-mix(
125
+ in srgb,
126
+ var(--wp-accent) var(--wp-user-tint),
127
+ var(--wp-surface)
128
+ );
129
+ border-inline-start: var(--wp-user-edge) solid var(--wp-accent);
130
+ }
131
+ .waypoint .wp-outline {
132
+ margin-block-end: var(--wp-space);
133
+ }
134
+ .waypoint .wp-outline ol {
135
+ list-style: none;
136
+ /* Apart from the toggle, with a visible edge whatever the platform's
137
+ scrollbars do. */
138
+ margin: var(--wp-space1) 0 0;
139
+ padding: var(--wp-space1);
140
+ max-block-size: 12rem;
141
+ overflow: auto;
142
+ border-block: 1px solid var(--wp-border);
143
+ }
144
+ /* Drawn inside the link, so the scroller never clips it; an outline, not a
145
+ shadow, so it stays under forced colors. */
146
+ .waypoint .wp-outline a:focus-visible {
147
+ outline: 2px solid var(--wp-focus-ring);
148
+ outline-offset: -2px;
149
+ }
150
+ .waypoint .wp-outline a {
151
+ /* A target of at least 24 by 24 px with room between (WCAG 2.5.8). */
152
+ display: block;
153
+ min-block-size: 24px;
154
+ min-inline-size: 24px;
155
+ padding-block: 2px;
156
+ margin-block: 2px;
157
+ }
158
+ .waypoint .wp-transcript {
159
+ overflow: auto;
160
+ max-block-size: 32rem;
161
+ overflow-anchor: none;
162
+ }
163
+ .waypoint [data-back-to-latest] {
164
+ flex-shrink: 0;
165
+ margin-block-start: var(--wp-space);
166
+ }
167
+ .waypoint textarea {
168
+ inline-size: 100%;
169
+ min-block-size: 3rem;
170
+ resize: vertical;
171
+ color: inherit;
172
+ background: var(--wp-background);
173
+ /* An input's boundary must be seen (3:1); the decorative border is not. */
174
+ border: 1px solid var(--wp-control-border);
175
+ border-radius: var(--wp-radius);
176
+ padding-inline: var(--wp-space);
177
+ }
178
+ .waypoint input:not([type="checkbox"], [type="radio"]),
179
+ .waypoint select {
180
+ border: 1px solid var(--wp-control-border);
181
+ }
182
+ /* Fields typed into (text, numbers, dates and any later such type) and
183
+ selects take the chat's colours, as the textarea does, not the user
184
+ agent's for the scheme; antd draws its own, and file, range and colour
185
+ inputs keep the platform's. */
186
+ .waypoint
187
+ input:not(
188
+ [type="file"],
189
+ [type="range"],
190
+ [type="color"],
191
+ [type="hidden"],
192
+ [type="checkbox"],
193
+ [type="radio"],
194
+ .ant-input,
195
+ .ant-picker *
196
+ ),
197
+ .waypoint select {
198
+ color: inherit;
199
+ background: var(--wp-background);
200
+ }
201
+ /* The selected tab is marked by a thick accent edge, a cue that is not
202
+ colour alone, drawn inside it so selecting a tab moves nothing. */
203
+ .waypoint [role="tab"][aria-selected="true"] {
204
+ box-shadow: inset 0 -3px 0 var(--wp-accent);
205
+ }
206
+ .waypoint button,
207
+ .waypoint input {
208
+ font: inherit;
209
+ }
210
+ .waypoint button {
211
+ cursor: pointer;
212
+ margin-inline-end: var(--wp-space);
213
+ }
214
+ /* The space is between buttons: the last one in a group ends at the
215
+ group's edge, so a group aligned to the end lines up with what is above. */
216
+ .waypoint button:last-child,
217
+ .waypoint button:not(:has(~ button)) {
218
+ margin-inline-end: 0;
219
+ }
220
+ /* An empty status after a group's buttons (it says Copied, or Loading)
221
+ takes no place in the row, so the row ends at its last button; it stays
222
+ in the page, so what it says later is still announced. */
223
+ .waypoint [role="group"] > [role="status"]:empty {
224
+ position: absolute;
225
+ }
226
+ /* Neutral buttons are drawn from the tokens, so an unavailable one can
227
+ look different from an available one. */
228
+ .waypoint button:not(.ant-btn) {
229
+ color: var(--wp-foreground);
230
+ background: var(--wp-surface);
231
+ border: 1px solid var(--wp-control-border);
232
+ border-radius: var(--wp-radius);
233
+ padding: var(--wp-space1) var(--wp-space2);
234
+ }
235
+ .waypoint button:not(.ant-btn) {
236
+ transition: border-color var(--wp-motion-fast) var(--wp-easing);
237
+ }
238
+ .waypoint button:not(.ant-btn):hover:not(:disabled, [aria-disabled="true"]) {
239
+ border-color: var(--wp-accent);
240
+ }
241
+ /* An unavailable action: muted (still 4.5:1), no hover change, and still
242
+ focusable so its reason can be reached. */
243
+ .waypoint button:not(.ant-btn):is(:disabled, [aria-disabled="true"]),
244
+ .waypoint .ant-btn.ant-btn[aria-disabled="true"],
245
+ .waypoint .ant-btn.ant-btn[aria-disabled="true"]:hover {
246
+ color: var(--wp-muted);
247
+ cursor: not-allowed;
248
+ }
249
+ /* The conversation list has no bullets, wherever it is shown. */
250
+ .waypoint .wp-rail ul {
251
+ list-style: none;
252
+ margin: 0;
253
+ padding-inline-start: 0;
254
+ }
255
+ .waypoint .wp-rail li + li {
256
+ margin-block-start: var(--wp-space1);
257
+ }
258
+ .waypoint .wp-rail ul ul {
259
+ padding-inline-start: var(--wp-space);
260
+ }
261
+ .waypoint a {
262
+ color: var(--wp-accent);
263
+ }
264
+ .waypoint [role="alert"] {
265
+ color: var(--wp-danger);
266
+ }
267
+ /* A reply still streaming in says so under its text, with a dot that
268
+ pulses (still under reduced motion); the reply row says it once. */
269
+ .waypoint [data-writing] {
270
+ display: block;
271
+ color: var(--wp-muted);
272
+ font-size: var(--wp-font-size-sm);
273
+ }
274
+ .waypoint [data-writing]::before {
275
+ content: "";
276
+ display: inline-block;
277
+ inline-size: 0.5em;
278
+ block-size: 0.5em;
279
+ margin-inline-end: var(--wp-space1);
280
+ border-radius: 50%;
281
+ background: var(--wp-accent);
282
+ animation: wp-writing calc(var(--wp-motion-slow) * 4) var(--wp-easing)
283
+ infinite alternate;
284
+ }
285
+ @keyframes wp-writing {
286
+ to {
287
+ opacity: 0.25;
288
+ }
289
+ }
290
+ /* A message still being sent, or not sent, says so under its bubble. */
291
+ .waypoint [data-pending-status] {
292
+ margin-block: 0 var(--wp-space1);
293
+ color: var(--wp-muted);
294
+ font-size: var(--wp-font-size-sm);
295
+ }
296
+ .waypoint [data-pending-status="failed"] {
297
+ color: var(--wp-danger);
298
+ }
299
+ /* A message's problem, its action and its details sit at the message's
300
+ side, like "Not sent": an action that wraps stays there, and opening the
301
+ details moves nothing. */
302
+ .waypoint article > [role="alert"] {
303
+ justify-content: flex-end;
304
+ }
305
+ .waypoint article > [data-problem-details] {
306
+ align-self: stretch;
307
+ text-align: end;
308
+ }
309
+ /* A field's validation when it is invalid: the danger tone, with the word
310
+ "Invalid" in front as the cue that is not colour. */
311
+ .waypoint .wp-invalid {
312
+ color: var(--wp-danger);
313
+ }
314
+ /* A text field's label sits above it, at every width. */
315
+ .waypoint label > input:not([type="checkbox"], [type="radio"]) {
316
+ display: block;
317
+ }
318
+ .waypoint .wp-attachments,
319
+ .waypoint [role="tabpanel"] > ul {
320
+ padding-inline-start: 0;
321
+ list-style-type: none;
322
+ }
323
+ .waypoint .wp-attachments > li,
324
+ .waypoint [role="tabpanel"] > ul > li {
325
+ display: flex;
326
+ flex-wrap: wrap;
327
+ align-items: center;
328
+ gap: var(--wp-space1);
329
+ margin-block-end: var(--wp-space1);
330
+ }
331
+ /* A fill's suggestion for an edited field reads as one aside: a small
332
+ label over its value, its validation under it, its answers in a row. */
333
+ .waypoint [data-suggestion] {
334
+ display: grid;
335
+ gap: var(--wp-space1);
336
+ margin-block: var(--wp-space1);
337
+ padding-inline-start: var(--wp-space1);
338
+ border-inline-start: 3px solid var(--wp-accent);
339
+ }
340
+ .waypoint [data-suggestion] p {
341
+ margin: 0;
342
+ }
343
+ .waypoint [data-suggestion] > p:first-child {
344
+ color: var(--wp-muted);
345
+ font-size: var(--wp-font-size-sm);
346
+ font-weight: 600;
347
+ }
348
+ /* "Invalid" leads its first message on one line. */
349
+ .waypoint .wp-invalid > strong {
350
+ margin-inline-end: var(--wp-space1);
351
+ }
352
+ .waypoint .wp-invalid > strong + p {
353
+ display: inline;
354
+ }
355
+ /* A row of answers or actions; a reason wraps under them. */
356
+ .waypoint .wp-actions {
357
+ display: flex;
358
+ flex-wrap: wrap;
359
+ align-items: center;
360
+ gap: var(--wp-space1);
361
+ }
362
+ .waypoint .wp-actions > [data-reason] {
363
+ order: 1;
364
+ flex-basis: 100%;
365
+ }
366
+ /* A flow's parameters, one per line, with Run and its reason after them. */
367
+ .waypoint .wp-flow-form {
368
+ display: flex;
369
+ flex-direction: column;
370
+ align-items: start;
371
+ gap: var(--wp-space1);
372
+ }
373
+ /* An alert's action reads as its own control, not part of the sentence;
374
+ when it wraps, it lines up with the sentence's start. */
375
+ .waypoint [role="alert"]:has(> button) {
376
+ display: flex;
377
+ flex-wrap: wrap;
378
+ align-items: baseline;
379
+ gap: var(--wp-space1);
380
+ }
381
+ .waypoint [role="alert"] > button {
382
+ margin-inline: 0;
383
+ }
384
+ /* A plan step's facts (risk, undo, status): one row of separate items. */
385
+ .waypoint .wp-step-facts {
386
+ list-style: none;
387
+ margin: var(--wp-space1) 0 0;
388
+ padding: 0;
389
+ display: flex;
390
+ flex-wrap: wrap;
391
+ gap: var(--wp-space1) var(--wp-space);
392
+ }
393
+ /* Table columns stay apart at any font size. */
394
+ .waypoint table th,
395
+ .waypoint table td {
396
+ padding-inline: var(--wp-space1);
397
+ }
398
+ /* The toggle and the title share the top row; a long title wraps. */
399
+ .waypoint [data-part="topBar"] {
400
+ display: flex;
401
+ align-items: center;
402
+ gap: var(--wp-space1);
403
+ margin-block-end: var(--wp-space2);
404
+ }
405
+ .waypoint [data-part="topBar"] h2 {
406
+ margin-block: 0;
407
+ min-inline-size: 0;
408
+ overflow-wrap: anywhere;
409
+ }
410
+ .waypoint [data-rail-toggle] [aria-expanded="true"] {
411
+ box-shadow: inset 0 -2px 0 var(--wp-accent);
412
+ }
413
+ /* A drawer is a sheet over the chat and the page: it never moves the
414
+ chat, is at most the viewport tall, and its content scrolls inside it. */
415
+ .waypoint .wp-drawer {
416
+ position: fixed;
417
+ inset-block: 0;
418
+ inset-inline-end: 0;
419
+ z-index: 1000;
420
+ inline-size: min(24rem, 100%);
421
+ max-block-size: 100dvh;
422
+ display: flex;
423
+ flex-direction: column;
424
+ gap: var(--wp-space1);
425
+ padding: var(--wp-space);
426
+ color: var(--wp-foreground);
427
+ background: var(--wp-surface);
428
+ border-inline-start: 1px solid var(--wp-border);
429
+ box-shadow: var(--wp-shadow);
430
+ }
431
+ /* The sheet can be as wide as the viewport: its own ring is drawn inside,
432
+ in either skin. */
433
+ .waypoint .wp-drawer:focus-visible,
434
+ .waypoint .ant-drawer-content:focus-visible,
435
+ .waypoint :is(.wp-drawer, .ant-drawer-content) .wp-rail summary:focus-visible {
436
+ outline-offset: -2px;
437
+ }
438
+ .waypoint :is(.wp-drawer, .ant-drawer-content) .wp-rail summary {
439
+ margin-block: var(--wp-space1);
440
+ padding-inline: var(--wp-space1);
441
+ }
442
+ .waypoint .wp-drawer-header {
443
+ display: flex;
444
+ align-items: center;
445
+ justify-content: space-between;
446
+ gap: var(--wp-space1);
447
+ }
448
+ .waypoint .wp-drawer-header h2 {
449
+ margin: 0;
450
+ font-size: var(--wp-font-size-lg);
451
+ }
452
+ .waypoint .wp-drawer-header button {
453
+ margin-inline-end: 0;
454
+ }
455
+ .waypoint .wp-drawer-body {
456
+ flex: 1;
457
+ min-block-size: 0;
458
+ overflow-y: auto;
459
+ }
460
+ /* antd's drawer renders in place; over the viewport like the neutral one,
461
+ so its height is the viewport's and its body scrolls. */
462
+ .waypoint .ant-drawer-inline {
463
+ position: fixed;
464
+ }
465
+ .waypoint .wp-markdown {
466
+ overflow-wrap: anywhere;
467
+ }
468
+ /* Blocks are spaced by the token, not by the newlines between them; a soft
469
+ line break inside a paragraph or cell still breaks, and code keeps its
470
+ own whitespace. */
471
+ .waypoint .wp-markdown :is(p, td, th) {
472
+ white-space: pre-wrap;
473
+ }
474
+ .waypoint .wp-markdown > * {
475
+ margin-block: 0;
476
+ }
477
+ .waypoint .wp-markdown > * + * {
478
+ margin-block-start: var(--wp-space);
479
+ }
480
+ /* Table cells keep their words whole: a table wider than the bubble
481
+ scrolls inside its own region instead. */
482
+ .waypoint .wp-markdown :is(td, th) {
483
+ overflow-wrap: normal;
484
+ }
485
+ /* A task list shows its boxes, not bullets as well; the box is drawn from
486
+ the tokens so done and open read apart (the engine fades disabled
487
+ boxes), and an open box's edge keeps 3:1 against the bubble (WCAG
488
+ 1.4.11), as the muted text colour does. */
489
+ .waypoint .wp-markdown .task-list-item {
490
+ list-style: none;
491
+ }
492
+ .waypoint .wp-markdown .task-list-item input[type="checkbox"] {
493
+ appearance: none;
494
+ inline-size: 1em;
495
+ block-size: 1em;
496
+ margin: 0 var(--wp-space1) 0 0;
497
+ vertical-align: -0.125em;
498
+ border: 1px solid var(--wp-muted);
499
+ border-radius: 2px;
500
+ background: var(--wp-background);
501
+ opacity: 1;
502
+ }
503
+ .waypoint .wp-markdown .task-list-item input[type="checkbox"]:checked {
504
+ background: var(--wp-foreground);
505
+ box-shadow: inset 0 0 0 2px var(--wp-background);
506
+ }
507
+ /* Forced colours drop backgrounds and shadows: bubbles keep a border and
508
+ the open toggle and the current row a visible edge. After the rules it
509
+ overrides, so it wins at equal specificity. */
510
+ @media (forced-colors: active) {
511
+ .waypoint [data-part="bubble"] {
512
+ border: 1px solid CanvasText;
513
+ }
514
+ .waypoint [data-rail-toggle] [aria-expanded="true"],
515
+ .waypoint [aria-current="page"] {
516
+ border-block-end: 2px solid Highlight;
517
+ }
518
+ /* The selected tab's inset edge is dropped with shadows: an outline,
519
+ which takes no space, marks it instead. */
520
+ .waypoint [role="tab"][aria-selected="true"] {
521
+ outline: 2px solid Highlight;
522
+ outline-offset: -2px;
523
+ }
524
+ /* An unavailable action in the system's unavailable colour. */
525
+ .waypoint button:not(.ant-btn):is(:disabled, [aria-disabled="true"]),
526
+ .waypoint .ant-btn.ant-btn[aria-disabled="true"] {
527
+ color: GrayText;
528
+ border-color: GrayText;
529
+ }
530
+ /* The token fill that marks a done task box would become the canvas;
531
+ drawn in the system's colours, it stays. */
532
+ .waypoint .wp-markdown .task-list-item input[type="checkbox"] {
533
+ border-color: CanvasText;
534
+ background: Canvas;
535
+ }
536
+ .waypoint .wp-markdown .task-list-item input[type="checkbox"]:checked {
537
+ background: CanvasText;
538
+ }
539
+ }
540
+ /* A block quote is set in by the token behind a start border, not by the
541
+ engine's wide margins, so what it quotes fits a narrow bubble. */
542
+ .waypoint .wp-markdown blockquote {
543
+ margin-inline: 0;
544
+ padding-inline-start: var(--wp-space);
545
+ border-inline-start: 3px solid var(--wp-muted);
546
+ }
547
+ .waypoint .wp-markdown blockquote > * {
548
+ margin-block: 0;
549
+ }
550
+ .waypoint .wp-markdown blockquote > * + * {
551
+ margin-block-start: var(--wp-space);
552
+ }
553
+ /* An image never exceeds its bubble. */
554
+ .waypoint .wp-markdown img {
555
+ max-inline-size: 100%;
556
+ block-size: auto;
557
+ }
558
+ /* Code blocks and tables scroll inside themselves, never the transcript. */
559
+ .waypoint [data-scroll-region] {
560
+ max-inline-size: 100%;
561
+ overflow-x: auto;
562
+ }
563
+ /* Every control is a target of at least 24 by 24 px (WCAG 2.5.8), and 44
564
+ by 44 on a coarse pointer; inline links in message text are exempt. */
565
+ .waypoint button,
566
+ .waypoint select,
567
+ .waypoint summary,
568
+ .waypoint nav a,
569
+ .waypoint li > a,
570
+ .waypoint .wp-check,
571
+ .waypoint .ant-checkbox-wrapper,
572
+ .waypoint .ant-btn,
573
+ .waypoint .ant-input,
574
+ .waypoint .ant-picker {
575
+ min-block-size: 24px;
576
+ min-inline-size: 24px;
577
+ }
578
+ .waypoint nav a,
579
+ .waypoint li > a,
580
+ .waypoint .wp-check,
581
+ .waypoint .ant-checkbox-wrapper {
582
+ display: inline-flex;
583
+ align-items: center;
584
+ }
585
+ /* A checkbox's label is its target; the box itself takes the accent. */
586
+ .waypoint .wp-check {
587
+ gap: var(--wp-space1);
588
+ }
589
+ .waypoint input[type="checkbox"] {
590
+ accent-color: var(--wp-accent);
591
+ }
592
+ /* antd keeps button labels on one line at a fixed height; with enlarged
593
+ text that pushes the chat sideways, so labels wrap inside the chat. The
594
+ fixed height stays as the minimum: the skin passes antd's control height
595
+ (in px, unitless), the small and large sizes are 0.75 and 1.25 of it as
596
+ antd derives them, and a target is never under 24px (44px for a coarse
597
+ pointer, below). */
598
+ .waypoint .ant-btn {
599
+ --wp-target: 24px;
600
+ max-inline-size: 100%;
601
+ block-size: auto;
602
+ min-block-size: max(var(--wp-target), var(--wp-btn, 0) * 1px);
603
+ white-space: normal;
604
+ }
605
+ .waypoint .ant-btn-sm {
606
+ min-block-size: max(var(--wp-target), var(--wp-btn, 0) * 0.75px);
607
+ }
608
+ .waypoint .ant-btn-lg {
609
+ min-block-size: max(var(--wp-target), var(--wp-btn, 0) * 1.25px);
610
+ }
611
+ @media (pointer: coarse) {
612
+ .waypoint button,
613
+ .waypoint select,
614
+ .waypoint summary,
615
+ .waypoint nav a,
616
+ .waypoint li > a,
617
+ .waypoint .wp-check,
618
+ .waypoint .ant-checkbox-wrapper,
619
+ .waypoint .ant-btn,
620
+ .waypoint input:not([type="checkbox"], [type="radio"], [type="hidden"]),
621
+ .waypoint .ant-input,
622
+ .waypoint .ant-picker {
623
+ min-block-size: 44px;
624
+ min-inline-size: 44px;
625
+ }
626
+ .waypoint .ant-btn {
627
+ --wp-target: 44px;
628
+ }
629
+ /* An inline citation is a few characters wide: its touch area grows to
630
+ 44 by 44 around it, and the text it sits in does not move. */
631
+ .waypoint a[data-wp-cite] {
632
+ position: relative;
633
+ }
634
+ .waypoint a[data-wp-cite]::after {
635
+ content: "";
636
+ position: absolute;
637
+ inset-block-start: 50%;
638
+ inset-inline-start: 50%;
639
+ inline-size: max(100%, 44px);
640
+ block-size: max(100%, 44px);
641
+ transform: translate(-50%, -50%);
642
+ }
643
+ }
644
+ .waypoint .wp-sr {
645
+ position: absolute;
646
+ inline-size: 1px;
647
+ block-size: 1px;
648
+ overflow: hidden;
649
+ clip-path: inset(50%);
650
+ }
651
+ @container (max-width: 40rem) {
652
+ .waypoint .wp-shell,
653
+ .waypoint .wp-shell[data-has-aside],
654
+ .waypoint .wp-shell:not([data-has-rail])[data-has-aside] {
655
+ grid-template-columns: minmax(0, 1fr);
656
+ }
657
+ .waypoint [data-part="rail"] {
658
+ order: 2;
659
+ }
660
+ }
661
+ .waypoint[data-layout="panel"] {
662
+ position: relative;
663
+ inline-size: 100%;
664
+ }
665
+ /* The page layout fills the page: the transcript takes the height left,
666
+ and the composer sits at the bottom. Other layouts keep the transcript's
667
+ cap, since their host decides their height. */
668
+ .waypoint[data-layout="page"] {
669
+ display: flex;
670
+ flex-direction: column;
671
+ }
672
+ .waypoint[data-layout="page"] > .wp-shell {
673
+ flex: 1;
674
+ min-block-size: 0;
675
+ }
676
+ /* Without a conversation list, the page's chat stays a readable width,
677
+ centred, instead of running lines across a wide screen. */
678
+ .waypoint[data-layout="page"] > .wp-shell:not([data-has-rail]) {
679
+ inline-size: 100%;
680
+ max-inline-size: 60rem;
681
+ margin-inline: auto;
682
+ }
683
+ .waypoint[data-layout="page"] main,
684
+ .waypoint[data-layout="page"] main > [data-part="transcript"],
685
+ .waypoint[data-layout="page"] main > [data-part="transcript"] > div {
686
+ display: flex;
687
+ flex-direction: column;
688
+ min-block-size: 0;
689
+ }
690
+ .waypoint[data-layout="page"] main > [data-part="transcript"],
691
+ .waypoint[data-layout="page"] main > [data-part="transcript"] > div,
692
+ .waypoint[data-layout="page"] .wp-transcript {
693
+ flex: 1;
694
+ }
695
+ .waypoint[data-layout="page"] .wp-transcript {
696
+ max-block-size: none;
697
+ }
698
+ .waypoint[data-layout="page"] {
699
+ inline-size: 100%;
700
+ min-block-size: 100dvh;
701
+ border: 0;
702
+ border-radius: 0;
703
+ }
704
+ .waypoint[data-layout="floating"] {
705
+ position: fixed;
706
+ inset-inline-end: var(--wp-space);
707
+ inset-block-end: var(--wp-space);
708
+ inline-size: min(32rem, calc(100% - 2 * var(--wp-space)));
709
+ max-block-size: calc(100dvh - 2 * var(--wp-space));
710
+ overflow: auto;
711
+ }
712
+ .waypoint[data-layout="sheet"] {
713
+ position: fixed;
714
+ inset-inline: 0;
715
+ inset-block-end: 0;
716
+ inline-size: 100%;
717
+ max-block-size: 80dvh;
718
+ overflow: auto;
719
+ border-end-start-radius: 0;
720
+ border-end-end-radius: 0;
721
+ }
722
+
723
+ /* The adornment takes its own column beside the field instead of lying
724
+ over it, so the field's end (where long text and the caret go) is never
725
+ covered; the field narrows only while the adornment is shown. */
726
+ .wp-field-parent {
727
+ display: grid;
728
+ grid-template-columns: minmax(0, 1fr) auto;
729
+ column-gap: 0.25rem;
730
+ align-items: start;
731
+ }
732
+ .wp-field-parent > * {
733
+ grid-column: 1;
734
+ }
735
+ .wp-field-parent > .wp-field-adornment {
736
+ grid-column: 2;
737
+ grid-row: 1;
738
+ }
739
+ /* A suggestion spans the adornment's column too, so its answers fit on
740
+ one row at narrow widths. */
741
+ .wp-field-parent > :has(> [data-suggestion]) {
742
+ grid-column: 1 / -1;
743
+ }
744
+ .wp-sr-only {
745
+ position: absolute;
746
+ width: 1px;
747
+ height: 1px;
748
+ padding: 0;
749
+ overflow: hidden;
750
+ clip-path: inset(50%);
751
+ white-space: nowrap;
752
+ }
753
+ /* Under reduced motion a reply being written fades in rather than typing
754
+ out: a change of opacity only, nothing moves. */
755
+ @keyframes wp-fade-in {
756
+ from {
757
+ opacity: 0.4;
758
+ }
759
+ }
760
+ /* A message's actions and the reply's controls sit in one wrapping row. */
761
+ .waypoint [data-part="messageActions"] [role="group"],
762
+ .waypoint [data-version-walk],
763
+ .waypoint [data-reply-controls] {
764
+ display: flex;
765
+ flex-wrap: wrap;
766
+ align-items: center;
767
+ gap: var(--wp-space1);
768
+ }
769
+ /* What ends a message (its actions, a failed message's controls and its
770
+ problem's details) and the reply's controls end with the chat's spacing,
771
+ as a bubble does, so they never touch the next message or the row
772
+ below. */
773
+ .waypoint [data-part="messageActions"] [role="group"],
774
+ .waypoint [data-part="failedSendControls"]:not(:empty),
775
+ .waypoint article > [data-problem-details],
776
+ .waypoint [data-reply-controls] {
777
+ margin-block-end: var(--wp-space);
778
+ }
779
+ /* Previous points the way the reading goes back. */
780
+ .waypoint[dir="rtl"] [data-version-walk] > button {
781
+ transform: scaleX(-1);
782
+ }
783
+ /* Reduced motion: nothing inside the chat animates, generated effects such
784
+ as a skin's click wave included; state still changes, at once. */
785
+ @media (prefers-reduced-motion: reduce) {
786
+ .waypoint *,
787
+ .waypoint *::before,
788
+ .waypoint *::after {
789
+ transition-duration: 0s !important;
790
+ animation-duration: 0s !important;
791
+ animation-iteration-count: 1 !important;
792
+ }
793
+ .waypoint .wp-markdown[data-fade] {
794
+ animation: wp-fade-in 240ms ease-out !important;
795
+ }
796
+ }