← 返回提示词
UI 设计

界面加固:长文本、空状态、错误与重复操作

把界面从理想演示扩展到真实输入、失败和恢复情境,保护用户已完成的工作。

提示词发布于 2026-11-09更新于 2026-11-09浏览 0

部分附加信息、来源说明或示例仍显示原文。

来源:import:liubai_public_20261104 · https://github.com/Shanvision-star/liubai-prompt-library/blob/25f0137e36a8fae46aebace86b18cdfeff624a99/bundled-library/entries/PRM-0009/original.md · 授权:Apache License 2.0;原文来自对应上游项目,许可全文:http://promptlab.zhichow.com/licenses/apache-2.0.txt

适用说明

适用场景

原文来源:https://github.com/pbakaus/impeccable/blob/5cb95eea9c96479f57afe0732a45470d30183326/skill/reference/harden.md
效果未实测。

上游 NOTICE:
# Third-Party Notices

This project includes content derived from third-party work, used under the terms of its original license.

## Platform Design Skills

The `skill/reference/ios.md` and `skill/reference/android.md` platform reference files are distilled from ehmo's `platform-design-skills` (Apple Human Interface Guidelines and Material Design 3 rules), rewritten in Impeccable's voice.

**Original work:** https://github.com/ehmo/platform-design-skills
**Original license:** MIT
**Author:** ehmo

公开署名

pbakaus/impeccable 贡献者;留白素材库收录

EXAMPLE

使用示例

该主题的原文与优化版共用这份示例。

提示词示例输入

示例列表需要处理超长标题、没有记录、保存失败和用户重复点击保存四种情况;要求不丢失用户输入。

文字示意结果

以下结果为人工编写的示意,并非模型实测输出。

超长标题换行或截断并保留完整名称;无记录时显示清楚的空状态;保存失败时保留输入并提供重试;提交期间禁用重复保存并展示处理状态。逐项验证这些状态,而不是将示意当作已通过的测试。

实际生成时的文字输入

Create one original 2-by-2 sheet of FOUR equal landscape keyframes showing ordinary interface edge states, edge-to-edge without gutters or labels. Each tile shows the same blue and white browser panel with calm cream background and consistent framing. In order: a card with a very long abstract line wrapping cleanly onto three lines; an empty content area with a simple empty box icon; a small amber inline warning icon next to a blank field; a clear disabled duplicate-submit button with a single checkmark beside it. No text, words, numbers, people, logos or watermark. Soft flat editorial illustration with muted blue and teal, readable high-level visual hierarchy.
查看输入译文

译文仅供参考;实际生成时使用的是上方原文。

创建一张由 2 x 2 组成的、包含四个等大的横向关键帧的原创设计稿,展示普通的界面边界状态,边缘对边缘,无间距或标签。每个图块显示相同的蓝白浏览器面板,配有宁静的奶油色背景和一致的构图。顺序如下:一张带有非常长的抽象线条并整齐折行至三行的卡片;一个带有简单空白框图标的空白内容区域;一个位于空白字段旁的微小琥珀色内联警告图标;一个清晰的禁用状态重复提交按钮,旁边带有一个对勾。无文本、单词、数字、人物、徽标或水印。采用柔和的扁平化编辑插画风格,色调为柔和的蓝色和青色,具有清晰、易读的整体视觉层级。

图片与动图示意结果

四格依次示意长文本、空状态、提示和提交状态;具体交互仍需在真实界面验证。

静态图片由 imagegen 按上面的输入生成;动图由生成的四帧画面拼接而成,效果仅供参考。

界面长文本、空状态和提示的四格示意
生成的四格关键画面

THE PROMPT

提示词正文

仅在完美数据下运行的设计并不具备生产就绪性。针对真实用户可能输入的各种数据、错误、语言和网络状况,增强界面的鲁棒性。

## 评估加固需求

识别弱点和边缘情况:

1. **使用极端输入进行测试**:
   - 非常长的文本(姓名、描述、标题)
   - 非常短的文本(空值、单个字符)
   - 特殊字符(表情符号、从右向左阅读的文本、重音符号)
   - 大数字(百万、十亿)
   - 大量项目(1000+ 列表项,50+ 选项)
   - 无数据(空状态)

2. **测试错误场景**:
   - 网络故障(离线、缓慢、超时)
   - API 错误(400, 401, 403, 404, 500)
   - 验证错误
   - 权限错误
   - 速率限制
   - 并发操作

3. **测试国际化**:
   - 较长的翻译(德语通常比英语长 30%)
   - 从右向左阅读的语言(阿拉伯语、希伯来语)
   - 字符集(中文、日语、韩语、表情符号)
   - 日期/时间格式
   - 数字格式(1,000 对比 1.000)
   - 货币符号

仅在完美数据下运行的设计并不具备生产就绪性。

## 加固维度

系统性地提高韧性:

### 文本溢出与换行

**长文本处理**:
```css
/* Single line with ellipsis */
.truncate {
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

/* Multi-line with clamp */
.line-clamp {
  display: -webkit-box;
  -webkit-line-clamp: 3;
  -webkit-box-orient: vertical;
  overflow: hidden;
}

/* Allow wrapping */
.wrap {
  word-wrap: break-word;
  overflow-wrap: break-word;
  hyphens: auto;
}
```

**Flex/Grid 溢出**:
```css
/* Prevent flex items from overflowing */
.flex-item {
  min-width: 0; /* Allow shrinking below content size */
  overflow: hidden;
}

/* Prevent grid items from overflowing */
.grid-item {
  min-width: 0;
  min-height: 0;
}
```

**响应式文本大小**:
- 使用 `clamp()` 实现流体排版
- 设置最小可读尺寸(移动端正文为 16px,即排版指南设定的底线;14px 仅用于真正的次要文本。iOS Safari 会对小于 16px 的聚焦输入框进行强制缩放,这会破坏表单布局)
- 测试文本缩放(缩放到 200%)
- 确保容器随文本扩展

### 国际化 (i18n)

**文本扩展**:
- 为翻译预留 30-40% 的空间预算
- 使用能适应内容的 flexbox/grid
- 使用最长的语言进行测试(通常是德语)
- 避免在文本容器上使用固定宽度

```jsx
// ❌ Bad: Assumes short English text
<button className="w-24">Submit</button>

// ✅ Good: Adapts to content
<button className="px-4 py-2">Submit</button>
```

**RTL(从右至左)支持**:
```css
/* Use logical properties */
margin-inline-start: 1rem; /* Not margin-left */
padding-inline: 1rem; /* Not padding-left/right */
border-inline-end: 1px solid; /* Not border-right */

/* Or use dir attribute */
[dir="rtl"] .arrow { transform: scaleX(-1); }
```

**阿拉伯语系特性**(阿拉伯语、波斯语、乌尔都语、帕什图语、库尔德语):
- 保留零宽非连接符 (U+200C)。波斯语和库尔德语在复合词部分之间使用 ZWNJ,以在保持单词完整性的同时打破连写。如果过滤器或清理程序将其删除,会改变含义。切勿在规范化时将其删除。
- 处理 Yeh 和 Kaf 的变体。波斯语使用 ی (U+06CC) 和 ک (U+06A9),而阿拉伯语使用 ي (U+064A) 和 ك (U+0643)。在存储时保留原始形式。对于搜索和验证,将相应的字母视为等效,以便阿拉伯语键盘输入能匹配波斯语文本。拒绝其中一种变体会导致使用另一种键盘的用户无法使用。
- 支持区域感知数字。波斯语 (`fa-IR`) 和阿拉伯语区域使用东阿拉伯-印度数字 (۰-۹ 和 ٠-٩)。使用带有正确区域设置的 `Intl.NumberFormat`,而不是硬编码西文数字。

```javascript
// ✅ Locale-aware digit formatting
new Intl.NumberFormat('fa-IR').format(1234); // ۱٬۲۳۴
new Intl.NumberFormat('ar-SA').format(1234); // ١٬٢٣٤
```

- 尊重历法系统。波斯语用户期望使用伊朗太阳历 (Jalali);许多阿拉伯语用户期望使用希吉拉历 (伊斯兰历)。使用带有适当区域设置或历法参数的 `Intl.DateTimeFormat`。

```javascript
// ✅ Locale-appropriate calendar
new Intl.DateTimeFormat('fa-IR').format(new Date());
new Intl.DateTimeFormat('ar-SA-u-ca-islamic').format(new Date());
```

**字符集支持**:
- 在所有地方使用 UTF-8 编码
- 使用中/日/韩 (CJK) 字符进行测试
- 使用 emoji 进行测试(它们可能是 2-4 字节)
- 处理不同的脚本(拉丁字母、西里尔字母、阿拉伯字母等)

**日期/时间格式化**:
```javascript
// ✅ Use Intl API for proper formatting
new Intl.DateTimeFormat('en-US').format(date); // 1/15/2024
new Intl.DateTimeFormat('de-DE').format(date); // 15.1.2024

new Intl.NumberFormat('en-US', { 
  style: 'currency', 
  currency: 'USD' 
}).format(1234.56); // $1,234.56
```

**复数形式**:
```javascript
// ❌ Bad: Assumes English pluralization
`${count} item${count !== 1 ? 's' : ''}`

// ✅ Good: Use proper i18n library
t('items', { count }) // Handles complex plural rules
```

### 错误处理

**网络错误**:
- 显示清晰的错误信息
- 提供重试按钮
- 解释发生了什么
- 提供离线模式(如果适用)
- 处理超时场景

```jsx
// Error states with recovery
{error && (
  <ErrorMessage>
    <p>Failed to load data. {error.message}</p>
    <button onClick={retry}>Try again</button>
  </ErrorMessage>
)}
```

**表单验证错误**:
- 字段附近的内联错误
- 清晰、具体的提示
- 建议更正方案
- 不要不必要地阻断提交
- 在出错时保留用户输入

**API 错误**:
- 适当地处理每个状态码
  - 400: 显示验证错误
  - 401: 重定向至登录
  - 403: 显示权限错误
  - 404: 显示未找到状态
  - 429: 显示速率限制消息
  - 500: 显示通用错误,提供支持

**优雅降级**:
- 在没有 JavaScript 的情况下核心功能仍可运行
- 图片具有替代文本
- 渐进式增强
- 不受支持功能的备选方案

### 边缘情况与边界条件

**空状态**:
- 列表中无项目
- 无搜索结果
- 无通知
- 无数据可显示
- 提供明确的下一步操作

**加载状态**:
- 初始加载
- 分页加载
- 刷新
- 显示正在加载的内容(“正在加载您的项目...”)
- 长时操作的时间预估

**大数据集**:
- 分页或虚拟滚动
- 搜索/筛选功能
- 性能优化
- 不要一次性加载所有 10,000 项目

**并发操作**:
- 防止重复提交(加载时禁用按钮)
- 处理竞态条件
- 带有回滚机制的乐观更新
- 冲突解决

**中断的手势**(自定义滑块、拖拽表面、可滚动控制条):
- 第二根手指或指针在拖拽过程中落下:第一次拖拽保持其指针或干净地结束,绝不跳转到新指针
- 浏览器为滚动而取消手势 (`pointercancel`)、捕获丢失 (`lostpointercapture`)、指针在控件外部释放,或窗口在拖拽过程中失去焦点 (`blur`):清除拖拽状态并释放捕获
- 在上述每种情况之后,下一次点击或拖拽均可正常工作,无需重新加载

**权限状态**:
- 无查看权限
- 无编辑权限
- 只读模式
- 明确的解释原因

**浏览器兼容性**:
- 现代功能的 Polyfills
- 不受支持的 CSS 的回退方案
- 特性检测(而非浏览器检测)
- 在目标浏览器中进行测试

### 输入验证与清理

**客户端验证**:
- 必填字段
- 格式验证(电子邮件、电话、URL)
- 长度限制
- 模式匹配
- 自定义验证规则

**服务端验证**(始终执行):
- 绝不仅信任客户端
- 验证并清理所有输入
- 防范注入攻击
- 速率限制

**约束处理**:
```html
<!-- Set clear constraints -->
<input 
  type="text"
  maxlength="100"
  pattern="[A-Za-z0-9]+"
  required
  aria-describedby="username-hint"
/>
<small id="username-hint">
  Letters and numbers only, up to 100 characters
</small>
```

### 无障碍韧性

**键盘导航**:
- 所有功能均可通过键盘访问
- 逻辑标签顺序
- 模态框中的焦点管理
- 长内容的跳过链接

**屏幕阅读器支持**:
- 适当的 ARIA 标签
- 宣布动态变化(实时区域)
- 描述性的替代文本
- 语义化 HTML

**高对比度模式**:
- 在 Windows 高对比度模式下进行测试
- 不要仅依赖颜色
- 提供替代视觉提示

### 性能韧性

**慢速连接**:
- 渐进式图像加载
- 骨架屏
- 乐观 UI 更新
- 离线支持 (Service Workers)

**内存泄漏**:
- 清理事件监听器
- 取消订阅
- 清除定时器/间隔
- 在卸载时中止待处理的请求

**节流与防抖**:
```javascript
// Debounce search input
const debouncedSearch = debounce(handleSearch, 300);

// Throttle scroll handler
const throttledScroll = throttle(handleScroll, 100);
```

## 测试策略

**手动测试**:
- 使用极端数据进行测试(非常长、非常短、空数据)
- 使用不同语言进行测试
- 离线测试
- 慢速连接测试(节流至 3G)
- 使用屏幕阅读器进行测试
- 仅使用键盘导航进行测试
- 在旧版浏览器上进行测试

**自动化测试**:
- 针对边缘情况的单元测试
- 针对错误场景的集成测试
- 针对关键路径的 E2E 测试
- 对于每个已确认修复的手势,当项目的测试运行器可以驱动输入时,进行行为回归测试
- 视觉回归测试
- 无障碍测试 (axe, WAVE)

**避免**:
- 假设输入是完美的(验证一切)
- 忽略国际化(为全球化设计)
- 留下通用的错误信息(“发生错误”)
- 忘记离线场景
- 仅信任客户端验证
- 为文本使用固定宽度
- 假设文本长度与英文一致
- 当单个组件出错时阻塞整个界面

## 验证加固

使用边缘情况进行彻底测试:

- **长文本**:尝试包含 100+ 个字符的名称
- **Emoji**:在所有文本字段中使用 emoji
- **RTL**:使用阿拉伯语或希伯来语进行测试
- **CJK**:使用中文/日语/韩语进行测试
- **网络问题**:禁用互联网,限制连接速度
- **大数据集**:使用 1000+ 个项目进行测试
- **并发操作**:快速点击提交 10 次
- **中断手势**:在拖动过程中添加第二根手指、跨越控件滚动、在控件外释放、在拖动过程中切换窗口;然后再次拖动
- **错误**:强制 API 错误,测试所有错误状态
- **空状态**:移除所有数据,测试空状态

对于手势,请说明产生证据的方式(模拟视口、合成触摸、哪个引擎、物理设备)并列出未测试的内容。

当边缘情况得到覆盖后,移交给 `{{command_prefix}}impeccable polish` 进行最终审核。

提示词仅供参考,请结合实际场景调整,并核实 AI 生成结果。