缩略图 · Thumbnail
缩略图用于内容展示场景。下面的官方示例展示原生用法与状态,属性名保持上游 API。
安装与前置条件
npm install @astryxdesign/core@0.7.1 @astryxdesign/theme-neutral@0.7.1 @stylexjs/stylex@0.19.0
需要 React 19+,按顺序导入基础 CSS 和主题,并设置 Theme Provider。参见开始使用。
示例与使用方式
- 缩略图 · 综合展示 1:首先体验这个示例,再查看代码理解组件的组合方式。
- 缩略图 · 禁用状态 2:可交互查看这一用法的行为,复制代码时保留它实际使用的属性与导入。
- 缩略图 · 交互示例 3:可交互查看这一用法的行为,复制代码时保留它实际使用的属性与导入。
- 缩略图 · 交互示例 4:可交互查看这一用法的行为,复制代码时保留它实际使用的属性与导入。
- 缩略图 · 多种状态 5:可交互查看这一用法的行为,复制代码时保留它实际使用的属性与导入。
API 与上游详细参考
优先使用 0.7.1 官方中文说明;上游尚未提供中文的条目保留英文。属性名、类型及默认值保持原生 API,不把示例状态名称当成组件属性。
Thumbnail
Thumbnail 是图片附件的方形预览卡片。上传时显示骨架屏动画,成功后显示图片,未设置源时显示占位图标。用于聊天编辑器、文件上传列表或任何需要紧凑图片预览的场景。
| 属性 | 类型 | 默认值 | 说明 |
|---|---|---|---|
| src | string | 图片源 URL。 | |
| alt | string | 图片的替代文本。省略时图片会被显式标记为装饰性(alt=""、role="presentation"、aria-hidden)并对屏幕阅读器隐藏;若 alt 和 label 均未设置,开发环境会发出警告。 | |
| label | string | 无障碍标签(如文件名)。悬停时以提示工具显示。 | |
| onRemove | (e: React.MouseEvent) => void | 覆盖层移除按钮的回调。 | |
| onClick | (e: React.MouseEvent) => void | 点击处理器。添加按钮语义和悬停覆盖层。 | |
| isLoading | boolean | false | 显示骨架屏(无 src)或上传覆盖层(有 src)。 |
| isDisabled | boolean | false | 是否禁用缩略图。 |
| showRemoveOn | 'always' | 'hover' | 'hover' | 何时显示移除按钮:hover(默认,悬停时以及键盘聚焦时显示,触摸设备上保持可见)| always(始终显示)。仅在设置 onRemove 时生效。 |
| xstyle | StyleXStyles | 用于布局自定义的 StyleX 样式。必须是 stylex.create() 的值,而非内联样式对象。 | |
| className | string | 根元素的 CSS 类名。建议使用 xstyle。 | |
| style | CSSProperties | 根元素的内联样式。建议使用 xstyle。 | |
| data-testid | string | 用于自动化测试框架的测试选择器。 |
使用建议
- 始终提供 label 属性并填写文件名,以便屏幕阅读器能够识别缩略图及其移除按钮,并在悬停时显示提示。
- 上传初期使用不带 src 的 isLoading 显示骨架屏;获得预览 URL 后使用带 src 的 isLoading 显示旋转加载覆盖层。
- 将 onClick 与灯箱或详情视图配对,以便用户查看完整图片——组件会自动添加按钮语义和悬停覆盖层。
- 避免:对 PDF 或电子表格等非图片文件类型使用 Thumbnail——应使用带有相应图标的文件附件组件。
- 避免:提供 src 时省略 alt 文本——屏幕阅读器需要图片内容的描述,而不仅是 label 中的文件名。
主题 API
{
"targets": [
{
"className": "astryx-thumbnail"
}
],
"vars": [
{
"name": "--_thumbnail-hit-inset",
"description": "Outset of the remove button's invisible hit area, applied to a ::after overlay. 0 on a fine pointer; negative on a coarse one, which grows the 20px button to the 24px touch target without changing what is drawn.",
"default": "0px",
"private": true
},
{
"name": "--_press-overlay",
"description": "Fill of the ::after interaction overlay: transparent at rest, the hover overlay token on hover (hover-capable pointers), the pressed overlay token while pressed (`:active` on a mouse; `data-astryx-press=\"on\"` written by the touch press controller under a finger) and the hover token for the release fade. Set on the card element by its own interaction arms.",
"default": "transparent",
"private": true
},
{
"name": "--_press-overlay-transition",
"description": "Duration of the overlay's background-color transition: the fast duration token, except 0s while a believed touch press paints so it lands on the first frame.",
"default": "var(--duration-fast)",
"private": true
}
]
}
组件结构
- Image: The preview image, displayed as a square with cover fit.
- Placeholder: An image silhouette icon shown when no src is provided.
- Remove button: An overlaid close button in the top-right corner. Appears when onRemove is set. Sits on a fixed --color-overlay scrim with an --color-on-dark icon to stay visible on any image.
- Upload overlay: A semi-transparent overlay with a spinner, shown when isLoading is true and a src preview is available.
- Skeleton: A shimmer animation shown when isLoading is true and no src is set.