@transferwise/components 46.116.0 → 46.117.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 (71) hide show
  1. package/build/alert/Alert.js +2 -1
  2. package/build/alert/Alert.js.map +1 -1
  3. package/build/alert/Alert.mjs +2 -1
  4. package/build/alert/Alert.mjs.map +1 -1
  5. package/build/main.css +60 -139
  6. package/build/prompt/InlinePrompt/InlinePrompt.js +14 -8
  7. package/build/prompt/InlinePrompt/InlinePrompt.js.map +1 -1
  8. package/build/prompt/InlinePrompt/InlinePrompt.mjs +15 -9
  9. package/build/prompt/InlinePrompt/InlinePrompt.mjs.map +1 -1
  10. package/build/sentimentSurface/SentimentSurface.js +6 -5
  11. package/build/sentimentSurface/SentimentSurface.js.map +1 -1
  12. package/build/sentimentSurface/SentimentSurface.mjs +6 -5
  13. package/build/sentimentSurface/SentimentSurface.mjs.map +1 -1
  14. package/build/styles/button/Button.css +17 -17
  15. package/build/styles/button/Button.vars.css +16 -16
  16. package/build/styles/iconButton/IconButton.css +8 -8
  17. package/build/styles/inputs/Input.css +2 -4
  18. package/build/styles/inputs/TextArea.css +2 -4
  19. package/build/styles/link/Link.css +1 -0
  20. package/build/styles/main.css +60 -139
  21. package/build/styles/popover/Popover.css +2 -4
  22. package/build/styles/prompt/InlinePrompt/InlinePrompt.css +26 -105
  23. package/build/styles/sentimentSurface/SentimentSurface.css +4 -1
  24. package/build/types/alert/Alert.d.ts.map +1 -1
  25. package/build/types/prompt/InlinePrompt/InlinePrompt.d.ts +19 -3
  26. package/build/types/prompt/InlinePrompt/InlinePrompt.d.ts.map +1 -1
  27. package/build/types/sentimentSurface/SentimentSurface.d.ts +5 -4
  28. package/build/types/sentimentSurface/SentimentSurface.d.ts.map +1 -1
  29. package/build/types/sentimentSurface/SentimentSurface.types.d.ts +4 -16
  30. package/build/types/sentimentSurface/SentimentSurface.types.d.ts.map +1 -1
  31. package/build/types/test-utils/story-config.d.ts +24 -0
  32. package/build/types/test-utils/story-config.d.ts.map +1 -1
  33. package/package.json +13 -12
  34. package/src/alert/Alert.tsx +3 -1
  35. package/src/button/Button.css +17 -17
  36. package/src/button/Button.less +1 -1
  37. package/src/button/Button.story.tsx +75 -110
  38. package/src/button/Button.tests.story.tsx +189 -0
  39. package/src/button/Button.vars.css +16 -16
  40. package/src/button/Button.vars.less +58 -18
  41. package/src/iconButton/IconButton.css +8 -8
  42. package/src/iconButton/IconButton.less +35 -4
  43. package/src/iconButton/IconButton.story.tsx +72 -3
  44. package/src/inputs/Input.css +2 -4
  45. package/src/inputs/TextArea.css +2 -4
  46. package/src/link/Link.css +1 -0
  47. package/src/link/Link.less +1 -0
  48. package/src/link/Link.story.tsx +28 -0
  49. package/src/main.css +60 -139
  50. package/src/popover/Popover.css +2 -4
  51. package/src/prompt/InlinePrompt/InlinePrompt.css +26 -105
  52. package/src/prompt/InlinePrompt/InlinePrompt.less +31 -119
  53. package/src/prompt/InlinePrompt/InlinePrompt.spec.tsx +87 -29
  54. package/src/prompt/InlinePrompt/InlinePrompt.story.tsx +223 -31
  55. package/src/prompt/InlinePrompt/InlinePrompt.tsx +42 -11
  56. package/src/sentimentSurface/SentimentSurface.css +4 -1
  57. package/src/sentimentSurface/SentimentSurface.docs.mdx +37 -478
  58. package/src/sentimentSurface/SentimentSurface.less +118 -114
  59. package/src/sentimentSurface/SentimentSurface.spec.tsx +31 -11
  60. package/src/sentimentSurface/SentimentSurface.story.tsx +325 -147
  61. package/src/sentimentSurface/SentimentSurface.tests.story.tsx +85 -86
  62. package/src/sentimentSurface/SentimentSurface.tsx +16 -9
  63. package/src/sentimentSurface/SentimentSurface.types.ts +5 -20
  64. package/src/test-utils/story-config.ts +0 -1
  65. package/build/sentimentSurface/classMap.js +0 -17
  66. package/build/sentimentSurface/classMap.js.map +0 -1
  67. package/build/sentimentSurface/classMap.mjs +0 -14
  68. package/build/sentimentSurface/classMap.mjs.map +0 -1
  69. package/build/types/sentimentSurface/classMap.d.ts +0 -4
  70. package/build/types/sentimentSurface/classMap.d.ts.map +0 -1
  71. package/src/sentimentSurface/classMap.ts +0 -15
@@ -1,527 +1,86 @@
1
- import { Meta, Source, ArgTypes } from '@storybook/addon-docs/blocks';
2
- import * as SentimentSurfaceStories from './SentimentSurface.story';
1
+ import { Meta, Source, Canvas } from '@storybook/addon-docs/blocks';
2
+ import * as stories from './SentimentSurface.story';
3
3
 
4
4
  <Meta title="Content/SentimentSurface/Developer Guide" />
5
5
 
6
- # SentimentSurface Developer Guide
6
+ # Developer Guide
7
7
 
8
- `SentimentSurface` is a polymorphic container component that applies contextual background colours and text styling based on sentiment types. It's designed to visually communicate the nature or importance of content through colour and establish a semantic colour context for nested interactive components.
8
+ SentimentSurface is a polymorphic container component that exposes and, optionally, applies contextual colour tokens
9
+ as CSS custom properties, based on sentiment types (`negative`, `warning`, `neutral`, `success`, `proposition`).
9
10
 
10
- ## Basic Usage
11
-
12
- Import and use the component with a required `sentiment` prop:
13
-
14
- <Source dark code={`
15
- import { SentimentSurface } from '@transferwise/components';
16
-
17
- <SentimentSurface sentiment="negative">Your payment has failed</SentimentSurface>
18
- `} />
19
-
20
- ### Props
21
-
22
- <ArgTypes of={SentimentSurfaceStories} />
23
-
24
- ## Sentiment Types
25
-
26
- The component supports five sentiment types (`negative`, `warning`, `neutral`, `proposition` and `success`), each communicating different types of information:
27
-
28
- ```tsx
29
- <SentimentSurface sentiment="negative">
30
- Your payment has failed. Please try again.
31
- </SentimentSurface>
32
-
33
- <SentimentSurface sentiment="warning">
34
- Action required: Please verify your email address.
35
- </SentimentSurface>
36
-
37
- <SentimentSurface sentiment="neutral">
38
- Your account is up to date.
39
- </SentimentSurface>
40
-
41
- <SentimentSurface sentiment="proposition">
42
- Try our new feature and save time on transfers.
43
- </SentimentSurface>
44
-
45
- <SentimentSurface sentiment="success">
46
- Your payment was successful!
47
- </SentimentSurface>
48
- ```
49
-
50
- ---
51
-
52
- ## Emphasis Levels
53
-
54
- Each sentiment type supports two emphasis levels to provide different levels of visual prominence (`base`, `elevated`):
55
-
56
- ```tsx
57
- <SentimentSurface sentiment="success" emphasis="base">
58
- Base emphasis - subtle background
59
- </SentimentSurface>
60
-
61
- <SentimentSurface sentiment="success" emphasis="elevated">
62
- Elevated emphasis - strong background
63
- </SentimentSurface>
64
- ```
65
-
66
- **When to use:**
67
-
68
- - **Base**: For inline notifications, subtle callouts, or when sentiment needs to be communicated without drawing too much attention
69
- - **Elevated**: For prominent banners, critical alerts, or when the sentiment should be immediately noticeable
70
-
71
- ---
72
-
73
- ## Polymorphic Rendering
74
-
75
- The component is fully polymorphic, meaning it can render as any HTML element using the `as` prop while maintaining full type safety.
76
-
77
- ### Basic Examples
78
-
79
- ```tsx
80
- // Render as div (default)
81
- <SentimentSurface sentiment="neutral">
82
- Default div element
83
- </SentimentSurface>
84
-
85
- // Render as section
86
- <SentimentSurface sentiment="negative" as="section">
87
- Semantic section element
88
- </SentimentSurface>
89
-
90
- // Render as article
91
- <SentimentSurface sentiment="success" as="article">
92
- Article element for standalone content
93
- </SentimentSurface>
94
- ```
95
-
96
- ### With HTML Attributes
97
-
98
- The component accepts all valid HTML attributes for the rendered element:
99
-
100
- ```tsx
101
- // Section with ARIA attributes
102
- <SentimentSurface
103
- sentiment="negative"
104
- as="section"
105
- role="alert"
106
- aria-live="polite"
107
- aria-atomic="true"
108
- >
109
- Critical error message
110
- </SentimentSurface>
111
-
112
- // Article with data attributes
113
- <SentimentSurface
114
- sentiment="proposition"
115
- as="article"
116
- data-tracking-id="promo-banner"
117
- data-position="top"
118
- >
119
- Promotional content
120
- </SentimentSurface>
121
- ```
122
-
123
- ### Type Safety
124
-
125
- TypeScript provides full type checking for HTML attributes based on the `as` prop:
126
-
127
- ```tsx
128
- // ✅ Valid - section supports these attributes
129
- <SentimentSurface as="section" role="region" aria-labelledby="heading">
130
- Content
131
- </SentimentSurface>
132
-
133
- // ❌ TypeScript error - 'href' is not valid for 'div'
134
- <SentimentSurface as="div" href="/link">
135
- Content
136
- </SentimentSurface>
137
- ```
138
-
139
- ---
140
-
141
- ## Nesting Sentiment Surfaces
142
-
143
- Sentiment surfaces can be nested to create layered contexts. Each nested surface establishes its own colour context through CSS custom properties.
144
-
145
- ### Basic Nesting
146
-
147
- ```tsx
148
- <SentimentSurface sentiment="negative" emphasis="base">
149
- <Title size="large">Payment Failed</Title>
150
- <Body>There was an issue processing your payment.</Body>
151
-
152
- <SentimentSurface sentiment="neutral" emphasis="elevated">
153
- <Title size="small">What happened?</Title>
154
- <Body>Your card was declined by your bank.</Body>
155
- </SentimentSurface>
156
- </SentimentSurface>
157
- ```
158
-
159
- ### Multi-Level Nesting
160
-
161
- ```tsx
162
- <SentimentSurface sentiment="success" emphasis="base">
163
- Outer: Payment successful
164
- <SentimentSurface sentiment="neutral" emphasis="elevated">
165
- Inner: Transaction details
166
- <SentimentSurface sentiment="warning" emphasis="base">
167
- Deepest: Additional fees may apply
168
- </SentimentSurface>
169
- </SentimentSurface>
170
- </SentimentSurface>
171
- ```
172
-
173
- ### Nesting with Different Elements
174
-
175
- ```tsx
176
- <SentimentSurface sentiment="negative" as="section">
177
- <Title size="large">Error Section</Title>
178
-
179
- <SentimentSurface sentiment="neutral" as="article">
180
- <Title size="small">Details</Title>
181
- <Body>More information about the error.</Body>
182
- </SentimentSurface>
183
-
184
- <SentimentSurface sentiment="proposition" as="aside">
185
- <Body>Need help? Contact support.</Body>
186
- </SentimentSurface>
187
- </SentimentSurface>
188
- ```
189
-
190
- ---
191
-
192
- ## CSS Custom Properties (Tokens)
193
-
194
- The component sets CSS custom properties (CSS variables) that child components can use to adapt their styling to the sentiment context. This enables a powerful theming system where nested components automatically adjust their appearance.
195
-
196
- ### Available Tokens
11
+ ## Available Tokens
197
12
 
198
13
  Each `SentimentSurface` sets tokens for content, interactive elements, and background surfaces. See the [Tokens story](?path=/story/content-sentimentsurface--tokens) for a visual demonstration of all tokens across sentiments and emphasis levels:
199
14
 
200
- #### Content Tokens
201
-
202
- ```css
203
- --color-sentiment-content-primary
204
- --color-sentiment-content-primary-hover
205
- --color-sentiment-content-primary-active
206
- ```
15
+ <Source dark language="html" code={`
16
+ --color-sentiment-content-primary
17
+ --color-sentiment-content-primary-hover
18
+ --color-sentiment-content-primary-active
207
19
 
208
- #### Interactive Primary Tokens
209
-
210
- ```css
211
20
  --color-sentiment-interactive-primary
212
21
  --color-sentiment-interactive-primary-hover
213
22
  --color-sentiment-interactive-primary-active
214
- ```
215
-
216
- #### Interactive Secondary Tokens
217
23
 
218
- ```css
219
24
  --color-sentiment-interactive-secondary
220
25
  --color-sentiment-interactive-secondary-hover
221
26
  --color-sentiment-interactive-secondary-active
222
- ```
223
27
 
224
- #### Interactive Secondary Neutral Tokens
225
-
226
- ```css
227
28
  --color-sentiment-interactive-secondary-neutral
228
29
  --color-sentiment-interactive-secondary-neutral-hover
229
30
  --color-sentiment-interactive-secondary-neutral-active
230
- ```
231
-
232
- #### Interactive Control Tokens
233
31
 
234
- ```css
235
32
  --color-sentiment-interactive-control
236
33
  --color-sentiment-interactive-control-hover
237
34
  --color-sentiment-interactive-control-active
238
- ```
239
35
 
240
- #### Background Surface Tokens
241
-
242
- ```css
243
36
  --color-sentiment-background-surface
244
37
  --color-sentiment-background-surface-hover
245
38
  --color-sentiment-background-surface-active
246
- ```
247
-
248
- ### Using Tokens in Component Styles
249
-
250
- Components can reference these tokens with fallbacks to maintain functionality outside of a `SentimentSurface`:
39
+ `} />
251
40
 
252
- ```css
253
- .wds-Button {
254
- /* Primary button uses interactive primary tokens */
255
- --Button-background: var(--color-sentiment-interactive-primary, var(--color-interactive-accent));
256
- --Button-background-hover: var(
257
- --color-sentiment-interactive-primary-hover,
258
- var(--color-interactive-accent-hover)
259
- );
260
- --Button-background-active: var(
261
- --color-sentiment-interactive-primary-active,
262
- var(--color-interactive-accent-active)
263
- );
41
+ ## Using Tokens in Components
264
42
 
265
- /* Button text color uses control tokens */
266
- --Button-color: var(--color-sentiment-interactive-control, var(--color-interactive-control));
267
- --Button-color-hover: var(
268
- --color-sentiment-interactive-control-hover,
269
- var(--color-interactive-control-hover)
270
- );
271
- --Button-color-active: var(
272
- --color-sentiment-interactive-control-active,
273
- var(--color-interactive-control-active)
274
- );
275
- }
43
+ When building `SentimentSurface`-aware components, the exposed tokens should be [referenced with fallbacks](https://developer.mozilla.org/en-US/docs/Web/CSS/Guides/Cascading_variables/Using_custom_properties#custom_property_fallback_values) to maintain functionality outside a said surfaces.
276
44
 
277
- .wds-Button--secondary {
278
- /* Secondary button uses secondary tokens */
279
- --Button-background: var(
280
- --color-sentiment-interactive-secondary,
281
- var(--color-interactive-neutral)
282
- );
283
- --Button-background-hover: var(
284
- --color-sentiment-interactive-secondary-hover,
285
- var(--color-interactive-neutral-hover)
286
- );
287
- --Button-color: var(--color-sentiment-interactive-primary, var(--color-interactive-primary));
288
- }
289
- ```
45
+ <Canvas of={stories.CustomComponents} />
290
46
 
291
- ### Example: Button in Sentiment Context
47
+ ## Polymorphic Rendering
292
48
 
293
- ```tsx
294
- import { Button, Body } from '@transferwise/components';
49
+ The component is fully polymorphic, meaning it can render as any HTML element using the `as` prop while maintaining full type safety, accepting all valid HTML attributes for the rendered element:
50
+
51
+ <Source dark language="tsx" code={`
52
+ // ✅ Renders as HTML 'section' with valid HTML attributes
53
+ <SentimentSurface
54
+ sentiment="negative"
55
+ as="section"
56
+ role="alert"
57
+ aria-live="polite"
58
+ data-position="top"
59
+ >
60
+ Critical error message
61
+ </SentimentSurface>
295
62
 
296
- // Button automatically adapts to the sentiment context
297
- <SentimentSurface sentiment="success">
298
- <Body>Your payment was successful!</Body>
299
- <Button v2 priority="primary">View Receipt</Button>
300
- <Button v2 priority="secondary">Send Another</Button>
301
- </SentimentSurface>
63
+ // TypeScript error - 'href' is not a valid attribute for a 'div'
302
64
 
303
- // Same buttons in different sentiment context
304
- <SentimentSurface sentiment="negative">
305
- <Body>Payment failed</Body>
306
- <Button v2 priority="primary">Try Again</Button>
307
- <Button v2 priority="secondary">Cancel</Button>
65
+ <SentimentSurface as="div" href="/link">
66
+ Content
308
67
  </SentimentSurface>
309
- ```
310
-
311
- The buttons will automatically use appropriate colours based on the sentiment context.
312
-
313
- ### Creating Custom Components with Sentiment Tokens
314
-
315
- You can create your own components that respect sentiment context:
316
-
317
- ```tsx
318
- // CustomCard.css
319
- .custom-card {
320
- background-color: var(
321
- --color-sentiment-background-surface,
322
- var(--color-background-surface)
323
- );
324
- color: var(
325
- --color-sentiment-content-primary,
326
- var(--color-content-primary)
327
- );
328
- border: 1px solid var(
329
- --color-sentiment-interactive-secondary,
330
- var(--color-border-neutral)
331
- );
332
- }
333
-
334
- .custom-card:hover {
335
- background-color: var(
336
- --color-sentiment-background-surface-hover,
337
- var(--color-background-surface-hover)
338
- );
339
- }
340
-
341
- .custom-card-link {
342
- color: var(
343
- --color-sentiment-interactive-primary,
344
- var(--color-interactive-primary)
345
- );
346
- }
347
-
348
- .custom-card-link:hover {
349
- color: var(
350
- --color-sentiment-interactive-primary-hover,
351
- var(--color-interactive-primary-hover)
352
- );
353
- }
354
- ```
355
-
356
- ```tsx
357
- // CustomCard.tsx
358
- function CustomCard({ children }) {
359
- return (
360
- <div className="custom-card">
361
- {children}
362
- <a href="#" className="custom-card-link">
363
- Learn more
364
- </a>
365
- </div>
366
- );
367
- }
368
-
369
- // Usage
370
- <SentimentSurface sentiment="warning">
371
- <CustomCard>This card adapts to the warning sentiment</CustomCard>
372
- </SentimentSurface>;
373
- ```
374
-
375
- ---
68
+ `} />
376
69
 
377
70
  ## Accessibility Considerations
378
71
 
379
- ### Semantic HTML
72
+ The tokens provided by the component are designed with WCAG AA contrast ratios in mind:
380
73
 
381
- Use appropriate HTML elements via the `as` prop to ensure proper document structure:
382
-
383
- ```tsx
384
- // ✅ Good - semantic HTML for alerts
385
- <SentimentSurface
386
- sentiment="negative"
387
- as="section"
388
- role="alert"
389
- aria-live="assertive"
390
- >
391
- Critical error: Payment failed
392
- </SentimentSurface>
393
-
394
- // ✅ Good - article for standalone content
395
- <SentimentSurface sentiment="proposition" as="article">
396
- <Title size="large">New Feature Available</Title>
397
- <Body>Try our new instant transfer feature...</Body>
398
- </SentimentSurface>
399
- ```
400
-
401
- ### ARIA Attributes
402
-
403
- Add appropriate ARIA attributes for screen readers:
404
-
405
- ```tsx
406
- // For errors or critical warnings
407
- <SentimentSurface
408
- sentiment="negative"
409
- role="alert"
410
- aria-live="assertive"
411
- aria-atomic="true"
412
- >
413
- Error: Your session has expired
414
- </SentimentSurface>
415
-
416
- // For important but not critical information
417
- <SentimentSurface
418
- sentiment="warning"
419
- role="status"
420
- aria-live="polite"
421
- >
422
- Please verify your email address
423
- </SentimentSurface>
424
-
425
- // For regions with headings
426
- <SentimentSurface
427
- sentiment="success"
428
- as="section"
429
- role="region"
430
- aria-labelledby="success-heading"
431
- >
432
- <Title id="success-heading" size="large">Payment Successful</Title>
433
- <Body>Your payment has been processed.</Body>
434
- </SentimentSurface>
435
- ```
436
-
437
- ### Color Contrast
438
-
439
- The component is designed with WCAG AA contrast ratios in mind:
440
-
441
- - **Base emphasis**: Provides sufficient contrast for body text
442
- - **Elevated emphasis**: Provides higher contrast, often with inverted colours
74
+ - **Base emphasis**: Tokens provide sufficient contrast for body text
75
+ - **Elevated emphasis**: Tokens provide higher contrast, often with inverted colours
443
76
 
444
77
  Always test your content for contrast compliance, especially when:
445
78
 
446
- - Adding custom text colours via `style` or `className`
79
+ - Applying tokens via `style` or `className`
447
80
  - Using small text sizes
448
81
  - Displaying important information
449
82
 
450
- ### Don't Rely on Color Alone
451
-
452
- Sentiment should not be conveyed through colour alone. Always include:
453
-
454
- ```tsx
455
- // ✅ Good - includes text and icons
456
- <SentimentSurface sentiment="negative">
457
- <ErrorIcon aria-hidden="true" />
458
- <strong>Error:</strong> Payment failed
459
- </SentimentSurface>
460
-
461
- // ❌ Bad - relies only on colour
462
- <SentimentSurface sentiment="negative">
463
- Payment failed
464
- </SentimentSurface>
465
- ```
466
-
467
- ### Focus Management
468
-
469
- When using for alerts, consider focus management:
470
-
471
- ```tsx
472
- function ErrorBanner({ error }) {
473
- const errorRef = useRef<HTMLElement>(null);
474
-
475
- useEffect(() => {
476
- if (error && errorRef.current) {
477
- errorRef.current.focus();
478
- }
479
- }, [error]);
480
-
481
- if (!error) return null;
482
-
483
- return (
484
- <SentimentSurface
485
- ref={errorRef}
486
- sentiment="negative"
487
- as="section"
488
- role="alert"
489
- tabIndex={-1}
490
- aria-live="assertive"
491
- >
492
- {error.message}
493
- </SentimentSurface>
494
- );
495
- }
496
- ```
497
-
498
- ---
499
-
500
- ## Best Practices
501
-
502
- ### Do's
503
-
504
- ✅ Use semantic HTML elements via the `as` prop
505
- ✅ Include ARIA attributes for screen readers
506
- ✅ Combine colour with icons and text for clarity
507
- ✅ Use appropriate sentiment types for the content
508
- ✅ Leverage CSS tokens for consistent theming
509
- ✅ Test contrast ratios for accessibility
510
- ✅ Provide focus management for critical alerts
511
-
512
- ### Don'ts
513
-
514
- ❌ Don't rely solely on colour to convey meaning
515
- ❌ Don't nest too many levels (3+ levels can be confusing)
516
- ❌ Don't override sentiment tokens without good reason
517
- ❌ Don't use `sentiment="negative"` for informational content
518
- ❌ Don't forget to test with screen readers
519
-
520
- ---
521
-
522
- ## Further Reading
83
+ ### Further Reading
523
84
 
524
- - [Component Source Code](./SentimentSurface.tsx)
525
- - [Storybook Examples](?path=/docs/content-sentimentsurface--docs)
526
85
  - [WCAG Color Contrast Guidelines](https://www.w3.org/WAI/WCAG21/Understanding/contrast-minimum.html)
527
86
  - [ARIA Live Regions](https://www.w3.org/WAI/WCAG21/Understanding/status-messages.html)