@tempoxyz/ds 0.3.10 → 0.3.11
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/dist/docs/AGENTS.md +9 -0
- package/dist/docs/components/accordion.md +489 -0
- package/dist/docs/components/address-card.md +147 -0
- package/dist/docs/components/agent-logo.md +194 -0
- package/dist/docs/components/alert-dialog.md +631 -0
- package/dist/docs/components/alert.md +448 -0
- package/dist/docs/components/amount-input.md +305 -0
- package/dist/docs/components/amount.md +794 -0
- package/dist/docs/components/app-shell.md +559 -0
- package/dist/docs/components/asset-chip.md +294 -0
- package/dist/docs/components/autocomplete.md +619 -0
- package/dist/docs/components/avatar.md +321 -0
- package/dist/docs/components/badge.md +339 -0
- package/dist/docs/components/badged-logo.md +116 -0
- package/dist/docs/components/banner.md +379 -0
- package/dist/docs/components/bar-chart.md +208 -0
- package/dist/docs/components/breadcrumbs.md +380 -0
- package/dist/docs/components/button-group.md +286 -0
- package/dist/docs/components/button.md +650 -0
- package/dist/docs/components/calendar.md +375 -0
- package/dist/docs/components/callout.md +96 -0
- package/dist/docs/components/checkbox-group.md +521 -0
- package/dist/docs/components/checkbox.md +467 -0
- package/dist/docs/components/choice-group.md +516 -0
- package/dist/docs/components/choicebox.md +641 -0
- package/dist/docs/components/code.md +100 -0
- package/dist/docs/components/combobox.md +939 -0
- package/dist/docs/components/container.md +257 -0
- package/dist/docs/components/copy-button.md +642 -0
- package/dist/docs/components/date-picker.md +514 -0
- package/dist/docs/components/dialog.md +1332 -0
- package/dist/docs/components/drawer.md +966 -0
- package/dist/docs/components/empty.md +340 -0
- package/dist/docs/components/field.md +570 -0
- package/dist/docs/components/fieldset.md +398 -0
- package/dist/docs/components/frame.md +434 -0
- package/dist/docs/components/gauge.md +299 -0
- package/dist/docs/components/get-started-visual.md +117 -0
- package/dist/docs/components/grid.md +288 -0
- package/dist/docs/components/hero-visual.md +155 -0
- package/dist/docs/components/hex.md +487 -0
- package/dist/docs/components/icon-tile.md +292 -0
- package/dist/docs/components/identicon.md +371 -0
- package/dist/docs/components/inline.md +233 -0
- package/dist/docs/components/inset.md +225 -0
- package/dist/docs/components/kbd.md +423 -0
- package/dist/docs/components/list-group.md +981 -0
- package/dist/docs/components/loading-dots.md +237 -0
- package/dist/docs/components/menu.md +934 -0
- package/dist/docs/components/native-select.md +204 -0
- package/dist/docs/components/network-logo.md +248 -0
- package/dist/docs/components/number-field.md +543 -0
- package/dist/docs/components/otp-field.md +616 -0
- package/dist/docs/components/pagination.md +516 -0
- package/dist/docs/components/popover.md +544 -0
- package/dist/docs/components/progress.md +388 -0
- package/dist/docs/components/qr.md +314 -0
- package/dist/docs/components/radio-group.md +528 -0
- package/dist/docs/components/secret-value.md +406 -0
- package/dist/docs/components/select.md +751 -0
- package/dist/docs/components/separator.md +379 -0
- package/dist/docs/components/sidebar-menu.md +922 -0
- package/dist/docs/components/skeleton.md +517 -0
- package/dist/docs/components/slider.md +539 -0
- package/dist/docs/components/snippet.md +424 -0
- package/dist/docs/components/spinner.md +216 -0
- package/dist/docs/components/split-bar.md +139 -0
- package/dist/docs/components/split-button.md +464 -0
- package/dist/docs/components/stack.md +299 -0
- package/dist/docs/components/status-chip.md +226 -0
- package/dist/docs/components/status-indicator.md +119 -0
- package/dist/docs/components/status-row.md +174 -0
- package/dist/docs/components/stepper.md +451 -0
- package/dist/docs/components/success-hero.md +157 -0
- package/dist/docs/components/surface.md +639 -0
- package/dist/docs/components/switch.md +472 -0
- package/dist/docs/components/table.md +967 -0
- package/dist/docs/components/tabs.md +627 -0
- package/dist/docs/components/tempo-logo.md +185 -0
- package/dist/docs/components/text-input.md +624 -0
- package/dist/docs/components/textarea.md +352 -0
- package/dist/docs/components/toast.md +535 -0
- package/dist/docs/components/token-logo.md +371 -0
- package/dist/docs/components/token.md +247 -0
- package/dist/docs/components/tooltip.md +490 -0
- package/dist/docs/components/verification-code.md +116 -0
- package/dist/docs/components/visual.md +249 -0
- package/dist/docs/components.md +203 -0
- package/dist/docs/foundations/accessibility.md +377 -0
- package/dist/docs/foundations/agents.md +150 -0
- package/dist/docs/foundations/color.md +522 -0
- package/dist/docs/foundations/content/tone.md +194 -0
- package/dist/docs/foundations/content/voice.md +194 -0
- package/dist/docs/foundations/content/writing-style.md +406 -0
- package/dist/docs/foundations/iconography.md +282 -0
- package/dist/docs/foundations/intent.md +360 -0
- package/dist/docs/foundations/layout.md +508 -0
- package/dist/docs/foundations/linter.md +296 -0
- package/dist/docs/foundations/motion.md +151 -0
- package/dist/docs/foundations/radius-and-padding.md +86 -0
- package/dist/docs/foundations/typography.md +266 -0
- package/dist/docs/index.md +137 -0
- package/dist/docs/introduction/faq.md +132 -0
- package/dist/docs/introduction/getting-started.md +377 -0
- package/dist/docs/patterns/blockchain-values.md +709 -0
- package/dist/docs/patterns/dashboards.md +638 -0
- package/dist/docs/patterns/destructive-actions.md +626 -0
- package/dist/docs/patterns/empty-states.md +612 -0
- package/dist/docs/patterns/errors-and-validation.md +808 -0
- package/dist/docs/patterns/feedback-and-status.md +518 -0
- package/dist/docs/patterns/forms.md +679 -0
- package/dist/docs/patterns/loading.md +630 -0
- package/dist/docs/patterns/navigation.md +397 -0
- package/dist/docs/patterns/payments.md +765 -0
- package/dist/docs/patterns/responsive-layout.md +997 -0
- package/dist/docs/patterns/tables-and-lists.md +964 -0
- package/dist/docs/products/tempo-console.md +671 -0
- package/dist/docs/products/tempo-performance.md +437 -0
- package/dist/docs/products/tempo-wallet.md +438 -0
- package/package.json +1 -1
|
@@ -0,0 +1,371 @@
|
|
|
1
|
+
# TokenLogo
|
|
2
|
+
|
|
3
|
+
Shows a token logo by contract address or symbol.
|
|
4
|
+
|
|
5
|
+
[View source and API](https://github.com/tempoxyz/ds/blob/main/src/web/components/TokenLogo.tsx)
|
|
6
|
+
|
|
7
|
+
Figma: [Elements/Logo](https://www.figma.com/design/yE96kcymnNR88PJp6G1sPs?node-id=5227-2546)
|
|
8
|
+
|
|
9
|
+
## Overview
|
|
10
|
+
|
|
11
|
+
A token logo renders a stablecoin's artwork, found by contract address or symbol, with its brand colors. Its `alt` is empty unless set, which suits a logo beside the token name.
|
|
12
|
+
|
|
13
|
+
## Examples
|
|
14
|
+
|
|
15
|
+
### Basic
|
|
16
|
+
|
|
17
|
+
```tsx
|
|
18
|
+
import { style, TokenLogo } from '@tempoxyz/ds'
|
|
19
|
+
|
|
20
|
+
export function Demo() {
|
|
21
|
+
return (
|
|
22
|
+
<TokenLogo.Provider>
|
|
23
|
+
<div {...styles.row()}>
|
|
24
|
+
<TokenLogo address="0x20c0000000000000000000000000000000000000" />
|
|
25
|
+
pathUSD
|
|
26
|
+
</div>
|
|
27
|
+
</TokenLogo.Provider>
|
|
28
|
+
)
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
namespace styles {
|
|
32
|
+
export const row = style({ alignItems: 'center', display: 'flex', gap: '12' })
|
|
33
|
+
}
|
|
34
|
+
```
|
|
35
|
+
|
|
36
|
+
[View example source](https://github.com/tempoxyz/ds/blob/main/docs/src/examples/demos/TokenLogo/Basic.tsx)
|
|
37
|
+
|
|
38
|
+
### Size
|
|
39
|
+
|
|
40
|
+
Set `size` to `small` (16px), `medium` (20px, default), or `large` (32px).
|
|
41
|
+
|
|
42
|
+
```tsx
|
|
43
|
+
import { style, TokenLogo } from '@tempoxyz/ds'
|
|
44
|
+
|
|
45
|
+
const tokens = [
|
|
46
|
+
['pathUSD', '0x20c0000000000000000000000000000000000000'],
|
|
47
|
+
['USDC.e', '0x20c000000000000000000000b9537d11c60e8b50'],
|
|
48
|
+
['EURC.e', '0x20c0000000000000000000001621e21f71cf12fb'],
|
|
49
|
+
['USDT0', '0x20c00000000000000000000014f22ca97301eb73'],
|
|
50
|
+
['frxUSD', '0x20c0000000000000000000003554d28269e0f3c2'],
|
|
51
|
+
] as const
|
|
52
|
+
|
|
53
|
+
export function Demo() {
|
|
54
|
+
return (
|
|
55
|
+
<TokenLogo.Provider>
|
|
56
|
+
<div {...styles.grid()}>
|
|
57
|
+
{tokens.map(([label, address]) => (
|
|
58
|
+
<div key={address} {...styles.row()}>
|
|
59
|
+
{(['small', 'medium', 'large'] as const).map((size) => (
|
|
60
|
+
<TokenLogo address={address} key={size} size={size} />
|
|
61
|
+
))}
|
|
62
|
+
{label}
|
|
63
|
+
</div>
|
|
64
|
+
))}
|
|
65
|
+
</div>
|
|
66
|
+
</TokenLogo.Provider>
|
|
67
|
+
)
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
namespace styles {
|
|
71
|
+
export const grid = style({ display: 'grid', gap: '12' })
|
|
72
|
+
|
|
73
|
+
export const row = style({ alignItems: 'center', display: 'flex', gap: '12' })
|
|
74
|
+
}
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
[View example source](https://github.com/tempoxyz/ds/blob/main/docs/src/examples/demos/TokenLogo/Size.tsx)
|
|
78
|
+
|
|
79
|
+
### Symbol
|
|
80
|
+
|
|
81
|
+
Pass `symbol` instead of `address` to resolve the token through the token list.
|
|
82
|
+
|
|
83
|
+
```tsx
|
|
84
|
+
import { style, TokenLogo } from '@tempoxyz/ds'
|
|
85
|
+
|
|
86
|
+
export function Demo() {
|
|
87
|
+
return (
|
|
88
|
+
<TokenLogo.Provider>
|
|
89
|
+
<div {...styles.row()}>
|
|
90
|
+
<TokenLogo size="large" symbol="pathUSD" />
|
|
91
|
+
By symbol: pathUSD
|
|
92
|
+
</div>
|
|
93
|
+
</TokenLogo.Provider>
|
|
94
|
+
)
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
namespace styles {
|
|
98
|
+
export const row = style({ alignItems: 'center', display: 'flex', gap: '12' })
|
|
99
|
+
}
|
|
100
|
+
```
|
|
101
|
+
|
|
102
|
+
[View example source](https://github.com/tempoxyz/ds/blob/main/docs/src/examples/demos/TokenLogo/Symbol.tsx)
|
|
103
|
+
|
|
104
|
+
### Fallback
|
|
105
|
+
|
|
106
|
+
An unknown address or symbol renders a placeholder.
|
|
107
|
+
|
|
108
|
+
```tsx
|
|
109
|
+
import { style, TokenLogo } from '@tempoxyz/ds'
|
|
110
|
+
|
|
111
|
+
export function Demo() {
|
|
112
|
+
return (
|
|
113
|
+
<TokenLogo.Provider>
|
|
114
|
+
<div {...styles.grid()}>
|
|
115
|
+
<div {...styles.row()}>
|
|
116
|
+
<TokenLogo address="0x0000000000000000000000000000000000000001" size="large" />
|
|
117
|
+
Unknown address (service placeholder)
|
|
118
|
+
</div>
|
|
119
|
+
<div {...styles.row()}>
|
|
120
|
+
<TokenLogo size="large" symbol="UNKNOWN" />
|
|
121
|
+
Unknown symbol (fallback)
|
|
122
|
+
</div>
|
|
123
|
+
</div>
|
|
124
|
+
</TokenLogo.Provider>
|
|
125
|
+
)
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
namespace styles {
|
|
129
|
+
export const grid = style({ display: 'grid', gap: '12' })
|
|
130
|
+
|
|
131
|
+
export const row = style({ alignItems: 'center', display: 'flex', gap: '12' })
|
|
132
|
+
}
|
|
133
|
+
```
|
|
134
|
+
|
|
135
|
+
[View example source](https://github.com/tempoxyz/ds/blob/main/docs/src/examples/demos/TokenLogo/Fallback.tsx)
|
|
136
|
+
|
|
137
|
+
## Anatomy
|
|
138
|
+
|
|
139
|
+
Import the component and assemble its parts.
|
|
140
|
+
|
|
141
|
+
```tsx
|
|
142
|
+
import { TokenLogo } from '@tempoxyz/ds'
|
|
143
|
+
|
|
144
|
+
<TokenLogo.Provider>
|
|
145
|
+
<TokenLogo />
|
|
146
|
+
</TokenLogo.Provider>
|
|
147
|
+
```
|
|
148
|
+
|
|
149
|
+
## Guidelines
|
|
150
|
+
|
|
151
|
+
### When to Use
|
|
152
|
+
|
|
153
|
+
* Show a token's logo beside its symbol in balance lists, token selectors, payment reviews, and activity rows.
|
|
154
|
+
|
|
155
|
+
### When Not to Use
|
|
156
|
+
|
|
157
|
+
* Use [Token](/docs/components/token) to show which token an amount is in, and to let a person change it.
|
|
158
|
+
* Use [Identicon](/docs/components/identicon) for an account address.
|
|
159
|
+
* Use [Avatar](/docs/components/avatar) for people and organizations.
|
|
160
|
+
* Use [IconTile](/docs/components/icon-tile) for a feature or category icon.
|
|
161
|
+
* Use [NetworkLogo](/docs/components/network-logo) for the chain a token lives on.
|
|
162
|
+
* Use [AssetChip](/docs/components/asset-chip) to list the assets a row supports.
|
|
163
|
+
|
|
164
|
+
### Pair the Icon With the Symbol
|
|
165
|
+
|
|
166
|
+
Many token icons look alike, and an unknown token can copy a well-known icon.
|
|
167
|
+
|
|
168
|
+
**Do:** Show the symbol beside each token icon.
|
|
169
|
+
|
|
170
|
+
```tsx
|
|
171
|
+
/**
|
|
172
|
+
* Do example for "Pair the Icon With the Symbol" on the TokenLogo page.
|
|
173
|
+
* Show the symbol beside each token icon.
|
|
174
|
+
* @module
|
|
175
|
+
*/
|
|
176
|
+
import { style, TokenLogo } from '@tempoxyz/ds'
|
|
177
|
+
|
|
178
|
+
const tokens = [
|
|
179
|
+
['pathUSD', '0x20c0000000000000000000000000000000000000'],
|
|
180
|
+
['USDC.e', '0x20c000000000000000000000b9537d11c60e8b50'],
|
|
181
|
+
['EURC.e', '0x20c0000000000000000000001621e21f71cf12fb'],
|
|
182
|
+
] as const
|
|
183
|
+
|
|
184
|
+
/** Renders the static preview, which the guideline card shows inert. */
|
|
185
|
+
export function Demo() {
|
|
186
|
+
return (
|
|
187
|
+
<TokenLogo.Provider>
|
|
188
|
+
<div {...styles.list()}>
|
|
189
|
+
{tokens.map(([symbol, address]) => (
|
|
190
|
+
<div key={address} {...styles.row()}>
|
|
191
|
+
<TokenLogo address={address} />
|
|
192
|
+
<span {...styles.symbol()}>{symbol}</span>
|
|
193
|
+
</div>
|
|
194
|
+
))}
|
|
195
|
+
</div>
|
|
196
|
+
</TokenLogo.Provider>
|
|
197
|
+
)
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
namespace styles {
|
|
201
|
+
export const list = style({ display: 'grid', gap: '12' })
|
|
202
|
+
|
|
203
|
+
export const row = style({ alignItems: 'center', display: 'flex', gap: '12' })
|
|
204
|
+
|
|
205
|
+
export const symbol = style({ color: 'content.primary', typography: 'body.b2Strong' })
|
|
206
|
+
}
|
|
207
|
+
```
|
|
208
|
+
|
|
209
|
+
**Don't:** Ask people to tell tokens apart by icon alone.
|
|
210
|
+
|
|
211
|
+
```tsx
|
|
212
|
+
/**
|
|
213
|
+
* Don't example for "Pair the Icon With the Symbol" on the TokenLogo page.
|
|
214
|
+
* Don't ask people to tell tokens apart by icon alone.
|
|
215
|
+
* @module
|
|
216
|
+
*/
|
|
217
|
+
import { style, TokenLogo } from '@tempoxyz/ds'
|
|
218
|
+
|
|
219
|
+
const addresses = [
|
|
220
|
+
'0x20c0000000000000000000000000000000000000',
|
|
221
|
+
'0x20c000000000000000000000b9537d11c60e8b50',
|
|
222
|
+
'0x20c0000000000000000000001621e21f71cf12fb',
|
|
223
|
+
] as const
|
|
224
|
+
|
|
225
|
+
/** Renders the static preview, which the guideline card shows inert. */
|
|
226
|
+
export function Demo() {
|
|
227
|
+
return (
|
|
228
|
+
<TokenLogo.Provider>
|
|
229
|
+
<div {...styles.row()}>
|
|
230
|
+
{addresses.map((address) => (
|
|
231
|
+
<TokenLogo address={address} key={address} />
|
|
232
|
+
))}
|
|
233
|
+
</div>
|
|
234
|
+
</TokenLogo.Provider>
|
|
235
|
+
)
|
|
236
|
+
}
|
|
237
|
+
|
|
238
|
+
namespace styles {
|
|
239
|
+
export const row = style({ alignItems: 'center', display: 'flex', gap: '12' })
|
|
240
|
+
}
|
|
241
|
+
```
|
|
242
|
+
|
|
243
|
+
### Prefer the Address
|
|
244
|
+
|
|
245
|
+
* **Address (address):** Use it when you have it. It loads the image directly and names one contract.
|
|
246
|
+
* **Symbol (symbol):** Resolves through the token list first, which adds a request. Different tokens can share a symbol.
|
|
247
|
+
* **Lists (TokenLogo.Provider):** Wrap lists so tokens share one lookup per symbol and a default `chainId`.
|
|
248
|
+
|
|
249
|
+
Pass `resolveSrc` or `resolveAddress` to `TokenLogo.Provider` to load icons or addresses from your own source.
|
|
250
|
+
|
|
251
|
+
### Show Unknown Tokens as Unknown
|
|
252
|
+
|
|
253
|
+
A gray circle renders while an icon loads or after it fails.
|
|
254
|
+
|
|
255
|
+
**Do:** Show the address in a [Hex](/docs/components/hex) beside the symbol of a token that isn't on the
|
|
256
|
+
list.
|
|
257
|
+
|
|
258
|
+
```tsx
|
|
259
|
+
/**
|
|
260
|
+
* Do example for "Show Unknown Tokens as Unknown" on the TokenLogo page.
|
|
261
|
+
* Show the address in a Hex beside the symbol of a token that isn't on the list.
|
|
262
|
+
* @module
|
|
263
|
+
*/
|
|
264
|
+
import { Hex, style, TokenLogo } from '@tempoxyz/ds'
|
|
265
|
+
|
|
266
|
+
const address = '0x20c00000000000000000000098a3f2c1e5d70b44'
|
|
267
|
+
|
|
268
|
+
/** Renders the static preview, which the guideline card shows inert. */
|
|
269
|
+
export function Demo() {
|
|
270
|
+
return (
|
|
271
|
+
<div {...styles.row()}>
|
|
272
|
+
<TokenLogo address={address} />
|
|
273
|
+
<div {...styles.text()}>
|
|
274
|
+
<span {...styles.symbol()}>USDC</span>
|
|
275
|
+
<Hex size="small" value={address} />
|
|
276
|
+
</div>
|
|
277
|
+
</div>
|
|
278
|
+
)
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
namespace styles {
|
|
282
|
+
export const row = style({ alignItems: 'center', display: 'flex', gap: '12', minWidth: '0' })
|
|
283
|
+
|
|
284
|
+
export const symbol = style({ color: 'content.primary', typography: 'body.b2Strong' })
|
|
285
|
+
|
|
286
|
+
export const text = style({ display: 'grid', gap: '4', minWidth: '0' })
|
|
287
|
+
}
|
|
288
|
+
```
|
|
289
|
+
|
|
290
|
+
**Don't:** Show only the symbol. Any token can claim it.
|
|
291
|
+
|
|
292
|
+
```tsx
|
|
293
|
+
/**
|
|
294
|
+
* Don't example for "Show Unknown Tokens as Unknown" on the TokenLogo page.
|
|
295
|
+
* Don't show only the symbol. Any token can claim it.
|
|
296
|
+
* @module
|
|
297
|
+
*/
|
|
298
|
+
import { style, TokenLogo } from '@tempoxyz/ds'
|
|
299
|
+
|
|
300
|
+
const address = '0x20c00000000000000000000098a3f2c1e5d70b44'
|
|
301
|
+
|
|
302
|
+
/** Renders the static preview, which the guideline card shows inert. */
|
|
303
|
+
export function Demo() {
|
|
304
|
+
return (
|
|
305
|
+
<div {...styles.row()}>
|
|
306
|
+
<TokenLogo address={address} />
|
|
307
|
+
<span {...styles.symbol()}>USDC</span>
|
|
308
|
+
</div>
|
|
309
|
+
)
|
|
310
|
+
}
|
|
311
|
+
|
|
312
|
+
namespace styles {
|
|
313
|
+
export const row = style({ alignItems: 'center', display: 'flex', gap: '12' })
|
|
314
|
+
|
|
315
|
+
export const symbol = style({ color: 'content.primary', typography: 'body.b2Strong' })
|
|
316
|
+
}
|
|
317
|
+
```
|
|
318
|
+
|
|
319
|
+
### Match Size to the Context
|
|
320
|
+
|
|
321
|
+
* **Small (16px):** Inline beside an amount.
|
|
322
|
+
* **Medium (20px):** The default, and the logo in a [Token](/docs/components/token).
|
|
323
|
+
* **Large (32px):** In asset rows and token pickers.
|
|
324
|
+
|
|
325
|
+
## Accessibility
|
|
326
|
+
|
|
327
|
+
A token logo renders a native `<img>`, decorative by default. It is not interactive and takes no focus.
|
|
328
|
+
|
|
329
|
+
### Semantics
|
|
330
|
+
|
|
331
|
+
* **Root (img):** Has empty alt text by default, so screen readers skip it beside a visible name.
|
|
332
|
+
* **Loading and Errors:** Renders a gray circle while loading or after an error. Text must identify the token.
|
|
333
|
+
* **Data Status (data-status):** Reports `loading`, `loaded`, or `error` for styling. Screen readers don't announce it.
|
|
334
|
+
|
|
335
|
+
### Your Responsibilities
|
|
336
|
+
|
|
337
|
+
* **Name a Standalone Icon (alt):** If the icon stands alone, such as in an icon-only selector, pass the token name.
|
|
338
|
+
|
|
339
|
+
## Related
|
|
340
|
+
|
|
341
|
+
[Amount](/docs/components/amount)
|
|
342
|
+
|
|
343
|
+
Use for token amounts.
|
|
344
|
+
|
|
345
|
+
[Token](/docs/components/token)
|
|
346
|
+
|
|
347
|
+
Use for a token pill that labels or picks a token.
|
|
348
|
+
|
|
349
|
+
[AssetChip](/docs/components/asset-chip)
|
|
350
|
+
|
|
351
|
+
Use for listing the assets a row supports.
|
|
352
|
+
|
|
353
|
+
[NetworkLogo](/docs/components/network-logo)
|
|
354
|
+
|
|
355
|
+
Use for the chain a token lives on.
|
|
356
|
+
|
|
357
|
+
[Identicon](/docs/components/identicon)
|
|
358
|
+
|
|
359
|
+
Use for account addresses.
|
|
360
|
+
|
|
361
|
+
[Avatar](/docs/components/avatar)
|
|
362
|
+
|
|
363
|
+
Use for people and organizations.
|
|
364
|
+
|
|
365
|
+
[Select](/docs/components/select)
|
|
366
|
+
|
|
367
|
+
Use for token selectors.
|
|
368
|
+
|
|
369
|
+
[Blockchain Values](/docs/patterns/blockchain-values)
|
|
370
|
+
|
|
371
|
+
Covers tokens and addresses.
|
|
@@ -0,0 +1,247 @@
|
|
|
1
|
+
# Token
|
|
2
|
+
|
|
3
|
+
Shows which token an amount is in, and opens a picker to change it.
|
|
4
|
+
|
|
5
|
+
[View source and API](https://github.com/tempoxyz/ds/blob/main/src/web/components/Token.tsx)
|
|
6
|
+
|
|
7
|
+
Figma: [Elements/Token](https://www.figma.com/design/yE96kcymnNR88PJp6G1sPs?node-id=5227-1266)
|
|
8
|
+
|
|
9
|
+
## Overview
|
|
10
|
+
|
|
11
|
+
A token renders a pill with a [TokenLogo](/docs/components/token-logo) and the token's symbol. By default it is a button with a chevron that opens a token picker. Set `readOnly` for a static pill.
|
|
12
|
+
|
|
13
|
+
## Examples
|
|
14
|
+
|
|
15
|
+
### Basic
|
|
16
|
+
|
|
17
|
+
```tsx
|
|
18
|
+
import { Token, TokenLogo } from '@tempoxyz/ds'
|
|
19
|
+
|
|
20
|
+
export function Demo() {
|
|
21
|
+
return (
|
|
22
|
+
<TokenLogo.Provider>
|
|
23
|
+
<Token address="0x20c0000000000000000000000000000000000000" symbol="pathUSD" />
|
|
24
|
+
</TokenLogo.Provider>
|
|
25
|
+
)
|
|
26
|
+
}
|
|
27
|
+
```
|
|
28
|
+
|
|
29
|
+
[View example source](https://github.com/tempoxyz/ds/blob/main/docs/src/examples/demos/Token/Basic.tsx)
|
|
30
|
+
|
|
31
|
+
### Read-Only
|
|
32
|
+
|
|
33
|
+
Set `readOnly` to render a span without the chevron, for reviews and receipts.
|
|
34
|
+
|
|
35
|
+
```tsx
|
|
36
|
+
import { Token, TokenLogo } from '@tempoxyz/ds'
|
|
37
|
+
|
|
38
|
+
export function Demo() {
|
|
39
|
+
return (
|
|
40
|
+
<TokenLogo.Provider>
|
|
41
|
+
<Token address="0x20c0000000000000000000000000000000000000" readOnly symbol="pathUSD" />
|
|
42
|
+
</TokenLogo.Provider>
|
|
43
|
+
)
|
|
44
|
+
}
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
[View example source](https://github.com/tempoxyz/ds/blob/main/docs/src/examples/demos/Token/ReadOnly.tsx)
|
|
48
|
+
|
|
49
|
+
### Picker
|
|
50
|
+
|
|
51
|
+
Pass the token to a trigger's `render`, such as a [Dialog](/docs/components/dialog) trigger, to open a token picker.
|
|
52
|
+
|
|
53
|
+
```tsx
|
|
54
|
+
import { Dialog, style, Token, TokenLogo } from '@tempoxyz/ds'
|
|
55
|
+
import { useState } from 'react'
|
|
56
|
+
|
|
57
|
+
const tokens = [
|
|
58
|
+
['pathUSD', '0x20c0000000000000000000000000000000000000'],
|
|
59
|
+
['USDC.e', '0x20c000000000000000000000b9537d11c60e8b50'],
|
|
60
|
+
['USDT0', '0x20c00000000000000000000014f22ca97301eb73'],
|
|
61
|
+
] as const
|
|
62
|
+
|
|
63
|
+
export function Demo() {
|
|
64
|
+
const [selected, setSelected] = useState<(typeof tokens)[number]>(tokens[0])
|
|
65
|
+
|
|
66
|
+
return (
|
|
67
|
+
<TokenLogo.Provider>
|
|
68
|
+
<Dialog.Root>
|
|
69
|
+
<Dialog.Trigger render={<Token address={selected[1]} symbol={selected[0]} />} />
|
|
70
|
+
<Dialog.Popup closeButton>
|
|
71
|
+
<Dialog.Header>
|
|
72
|
+
<Dialog.Title>Select token</Dialog.Title>
|
|
73
|
+
</Dialog.Header>
|
|
74
|
+
<Dialog.Body>
|
|
75
|
+
<div {...styles.list()}>
|
|
76
|
+
{tokens.map((token) => (
|
|
77
|
+
<Dialog.Close
|
|
78
|
+
key={token[1]}
|
|
79
|
+
onClick={() => setSelected(token)}
|
|
80
|
+
render={<button type="button" {...styles.option()} />}
|
|
81
|
+
>
|
|
82
|
+
<TokenLogo address={token[1]} size="large" />
|
|
83
|
+
{token[0]}
|
|
84
|
+
</Dialog.Close>
|
|
85
|
+
))}
|
|
86
|
+
</div>
|
|
87
|
+
</Dialog.Body>
|
|
88
|
+
</Dialog.Popup>
|
|
89
|
+
</Dialog.Root>
|
|
90
|
+
</TokenLogo.Provider>
|
|
91
|
+
)
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
namespace styles {
|
|
95
|
+
export const list = style({ display: 'grid', gap: '4' })
|
|
96
|
+
|
|
97
|
+
export const option = style({
|
|
98
|
+
alignItems: 'center',
|
|
99
|
+
backgroundColor: 'transparent !custom',
|
|
100
|
+
border: 'none !custom',
|
|
101
|
+
borderRadius: 'xs',
|
|
102
|
+
color: 'content.primary',
|
|
103
|
+
cursor: 'pointer',
|
|
104
|
+
display: 'flex',
|
|
105
|
+
gap: '12',
|
|
106
|
+
padding: '12',
|
|
107
|
+
textAlign: 'start',
|
|
108
|
+
typography: 'body.b2Strong',
|
|
109
|
+
selectors: { '&:hover': { backgroundColor: 'container.regular' } },
|
|
110
|
+
})
|
|
111
|
+
}
|
|
112
|
+
```
|
|
113
|
+
|
|
114
|
+
[View example source](https://github.com/tempoxyz/ds/blob/main/docs/src/examples/demos/Token/Picker.tsx)
|
|
115
|
+
|
|
116
|
+
## Anatomy
|
|
117
|
+
|
|
118
|
+
Import the component and assemble its parts.
|
|
119
|
+
|
|
120
|
+
```tsx
|
|
121
|
+
import { Token } from '@tempoxyz/ds'
|
|
122
|
+
|
|
123
|
+
<Token />
|
|
124
|
+
```
|
|
125
|
+
|
|
126
|
+
## Guidelines
|
|
127
|
+
|
|
128
|
+
### When to Use
|
|
129
|
+
|
|
130
|
+
* Name the token after the digits in an [AmountInput](/docs/components/amount-input), and let a person change it.
|
|
131
|
+
* Name a fixed token in a review or a receipt with `readOnly`.
|
|
132
|
+
|
|
133
|
+
### When Not to Use
|
|
134
|
+
|
|
135
|
+
* Use [TokenLogo](/docs/components/token-logo) for a logo beside a symbol in a list row.
|
|
136
|
+
* Use [AssetChip](/docs/components/asset-chip) to list the assets a row supports.
|
|
137
|
+
* Use [Select](/docs/components/select) to choose a token in a form field with a label.
|
|
138
|
+
|
|
139
|
+
### Show the Chevron Only on a Picker
|
|
140
|
+
|
|
141
|
+
The chevron tells people that the token opens a picker.
|
|
142
|
+
|
|
143
|
+
**Do:** Set `readOnly` in reviews and receipts, where the token can't change.
|
|
144
|
+
|
|
145
|
+
```tsx
|
|
146
|
+
/**
|
|
147
|
+
* Do example for "Show the Chevron Only on a Picker" on the Token page.
|
|
148
|
+
* Render a read-only pill where the token can't change.
|
|
149
|
+
* @module
|
|
150
|
+
*/
|
|
151
|
+
import { style, Token, TokenLogo } from '@tempoxyz/ds'
|
|
152
|
+
|
|
153
|
+
/** Renders the static preview, which the guideline card shows inert. */
|
|
154
|
+
export function Demo() {
|
|
155
|
+
return (
|
|
156
|
+
<TokenLogo.Provider>
|
|
157
|
+
<div {...styles.row()}>
|
|
158
|
+
<span {...styles.amount()}>25.00</span>
|
|
159
|
+
<Token address="0x20c0000000000000000000000000000000000000" readOnly symbol="pathUSD" />
|
|
160
|
+
</div>
|
|
161
|
+
</TokenLogo.Provider>
|
|
162
|
+
)
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
namespace styles {
|
|
166
|
+
export const amount = style({ color: 'content.primary', typography: 'heading.h2' })
|
|
167
|
+
|
|
168
|
+
export const row = style({ alignItems: 'center', display: 'flex', gap: '12' })
|
|
169
|
+
}
|
|
170
|
+
```
|
|
171
|
+
|
|
172
|
+
**Don't:** Show the chevron on a token that opens nothing.
|
|
173
|
+
|
|
174
|
+
```tsx
|
|
175
|
+
/**
|
|
176
|
+
* Don't example for "Show the Chevron Only on a Picker" on the Token page.
|
|
177
|
+
* A chevron on a token that can't change promises a picker that never opens.
|
|
178
|
+
* @module
|
|
179
|
+
*/
|
|
180
|
+
import { style, Token, TokenLogo } from '@tempoxyz/ds'
|
|
181
|
+
|
|
182
|
+
/** Renders the static preview, which the guideline card shows inert. */
|
|
183
|
+
export function Demo() {
|
|
184
|
+
return (
|
|
185
|
+
<TokenLogo.Provider>
|
|
186
|
+
<div {...styles.row()}>
|
|
187
|
+
<span {...styles.amount()}>25.00</span>
|
|
188
|
+
<Token address="0x20c0000000000000000000000000000000000000" symbol="pathUSD" />
|
|
189
|
+
</div>
|
|
190
|
+
</TokenLogo.Provider>
|
|
191
|
+
)
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
namespace styles {
|
|
195
|
+
export const amount = style({ color: 'content.primary', typography: 'heading.h2' })
|
|
196
|
+
|
|
197
|
+
export const row = style({ alignItems: 'center', display: 'flex', gap: '12' })
|
|
198
|
+
}
|
|
199
|
+
```
|
|
200
|
+
|
|
201
|
+
### Prefer the Address
|
|
202
|
+
|
|
203
|
+
* **Address (address):** Loads the logo directly. `symbol` still labels the pill.
|
|
204
|
+
* **Symbol (symbol):** Resolves the logo through the token list first.
|
|
205
|
+
|
|
206
|
+
## Content
|
|
207
|
+
|
|
208
|
+
### Use the Token's Symbol
|
|
209
|
+
|
|
210
|
+
Write the symbol as the token defines it, such as pathUSD or USDC.e. Keep amounts, network names, and verbs outside the pill.
|
|
211
|
+
|
|
212
|
+
## Accessibility
|
|
213
|
+
|
|
214
|
+
A token renders a native `<button>` built on Base UI Button, or a `<span>` when `readOnly`. The logo and the chevron are hidden from screen readers.
|
|
215
|
+
|
|
216
|
+
### Semantics
|
|
217
|
+
|
|
218
|
+
* **Root (button):** The symbol names the button. A picker trigger adds popup state.
|
|
219
|
+
* **Read-Only (readOnly):** Renders a span, so screen readers read the symbol as text.
|
|
220
|
+
|
|
221
|
+
### Keyboard
|
|
222
|
+
|
|
223
|
+
* **Move Focus to the Token (Tab):** Moves focus to the token.
|
|
224
|
+
* **Open the Picker (Enter or Space):** Opens the picker that the token triggers.
|
|
225
|
+
|
|
226
|
+
### Your Responsibilities
|
|
227
|
+
|
|
228
|
+
* **Open a Picker (render):** Pass the token to a picker trigger's `render`. If nothing opens, set `readOnly`.
|
|
229
|
+
* **Describe the Action (aria-label):** If the symbol alone doesn't say what the token does, add a label that keeps the symbol.
|
|
230
|
+
|
|
231
|
+
## Related
|
|
232
|
+
|
|
233
|
+
[TokenLogo](/docs/components/token-logo)
|
|
234
|
+
|
|
235
|
+
Use for token logos.
|
|
236
|
+
|
|
237
|
+
[AmountInput](/docs/components/amount-input)
|
|
238
|
+
|
|
239
|
+
Use for entering an amount beside a token.
|
|
240
|
+
|
|
241
|
+
[AssetChip](/docs/components/asset-chip)
|
|
242
|
+
|
|
243
|
+
Use for listing the assets a row supports.
|
|
244
|
+
|
|
245
|
+
[Dialog](/docs/components/dialog)
|
|
246
|
+
|
|
247
|
+
Use for a token picker.
|