01 B.C. 设计系统 界面预览 在电子邮件和电话之间切换并保留输入,然后验证并查看本地联系方式偏好。
原生 @bcgov/design-system-react-components 0.8.1、设计令牌 5.0.0 和 BC Sans 2.1.2。·
实现参考 原生 @bcgov/design-system-react-components 0.8.1、设计令牌 5.0.0 和 BC Sans 2.1.2。
名称 / 规则 值 / 配置 用途 --surface-color-primary-button-default#013366 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --surface-color-primary-button-hover#1e5189 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --surface-color-primary-button-disabled#edebe9 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --surface-color-background-white#ffffff 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --surface-color-background-light-gray#faf9f8 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --surface-color-background-light-blue#f1f8fe 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --surface-color-border-default#d8d8d8 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --surface-color-border-medium#898785 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --surface-color-border-active#2e5dd7 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-color-primary#2d2d2d 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-color-secondary#474543 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-color-link#255a90 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-color-danger#ce3e39 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-color-primary-invert#ffffff 已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。
名称 / 规则 值 / 配置 用途 --layout-padding-hair0.125rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-padding-xsmall0.25rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-padding-small0.5rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-padding-medium1rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-padding-large1.5rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-padding-xlarge2rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-margin-medium1rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-margin-large1.5rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-margin-xlarge2rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-margin-xxxlarge3rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-border-radius-small2px已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-border-radius-medium4px已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --layout-border-radius-large6px已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。
名称 / 规则 值 / 配置 用途 --typography-font-size-small-body0.875rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-font-size-body1rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-font-size-large-body1.125rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-font-size-h51.25rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-font-size-h41.5rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-font-size-h31.75rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-font-size-h22rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-font-size-h12.25rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。 --typography-font-size-display3rem已发布的 B.C. 角色;应按用途使用,而不是替换成原始颜色或尺寸值。
03 B.C. 设计系统 完整指南 实用指南,介绍如何为真实界面选择、应用和评审此系统。
DESIGN-british-columbia.md 完整指导、实现起点和源代码链接。
下载指南 B.C. 设计系统 当前 React 库与设计令牌 选择受维护的实现 当前的 B.C. Design System 提供基于 React Aria 构建的组件。此示例固定使用 react-components 0.8.1 及其依赖 design-tokens 5.0.0。较早的 B.C. Web Components 仓库是独立的旧版实现;导入它并不能复现当前的 React 库。复制示例前,请先确认实现与文档相符。
导入实际字体 这些组件使用带空格的 BC Sans 字体系列名称。2.1.2 版本提供 css/BC_Sans.css;旧版 BCSans.css 条目已标记为弃用,且声明了不同的字体系列名称。如果开发人员的电脑上已安装 BC Sans,可能会掩盖字体未导入的问题。此示例内置了已发布的字体,因此显示效果不依赖本地安装。
B.C. 设计系统语义颜色与间距角色 先看角色,再选择对应值 主按钮使用深蓝色主按钮填充色,辅助内容使用 typography-color-secondary,错误消息使用 typography-color-danger。表格列出了当前 CSS 的导出名称;即使未来主题更改底层值,名称表达的用途仍保持稳定。请勿将非活动控件颜色与普通辅助文本颜色混淆。
有意识地规划布局尺寸 表单字段之间相距 24px,主要任务与辅助说明之间则留出更宽的 48px 间距。这些数值与库的间距节奏相符,而整体双栏布局是为此示例单独设计的。在移动端,布局会合并为单栏,同时保留表单标签的字号,也不会将说明文字变成工具提示。
B.C. 设计系统 React Aria 组件约定 使用受控值和文档规定的处理器 TextField 接收 value 和 onChange;RadioGroup 接收 value 和 onChange;Checkbox 使用 isSelected 和 onChange。这些处理器接收文档规定的值,而不是必须通过 event.target 读取的浏览器事件对象。Button 使用 type=submit,并依靠原生表单的提交事件,使键盘提交也遵循相同的验证流程。
让审核反馈保持同步 实现说明 偏好审核区域会根据所选联系方式显示本地摘要。任何更改都会清除旧结果,并重置已提交的错误状态。此示例不会声称已发送电子邮件或安排提醒。若要发送真实通知,必须先另行明确同意、数据持久化和发送机制,才能作出此类说明。
B.C. 设计系统 无障碍名称与响应式布局 确保标签、说明和错误提示彼此关联 原生组件提供 React Aria 对标签、帮助文本和错误消息的关联支持。应用仍须提供有意义的标签、清晰的分组说明和易于理解的验证文本。测试时应点击可见的单选项标签并使用键盘操作;内部视觉隐藏的输入框不是可见的交互目标。
将辅助说明与表单分开 旁边的说明框解释了本地操作流程,并使用原生 details 展示实现背景。在窄屏布局中,它会按阅读顺序排在表单之后。信息图标仅作装饰,含义由标题表达。研究这些组件无需使用 B.C. 官方标志,也不必声称这是政府服务。
B.C. 设计系统 完整的 React 实现 复现经验证的源代码 创建 Vite React 项目,并安装固定版本的组件、令牌和字体包。使用提供的 main.jsx 和 bc.css,并添加根挂载元素。此代码包包含原生单选框、字段、复选框和按钮行为,以及完整的本地验证和状态转换。无需私有的 API 或凭据。
安装固定版本的软件包,并导入 css/BC_Sans.css。 保存 main.jsx 和 bc.css,并保留根挂载元素。 提交空表单,然后修正可见字段中的内容。 切换联系方式,并确认先前输入的值仍然保留。 让条件验证与所选联系方式保持一致 RadioGroup 和 TextField 的 onChange 处理器接收值,Checkbox 的 onChange 处理器则接收所选布尔值。直接存储这些值,不要对所有组件一概使用通用的 event.target.value 处理器。即使 React Aria 在视觉上隐藏了原生输入框,可见标签仍是交互目标。
更改联系方式时,保留两项草稿值,但清除旧的审核结果,并且只验证当前选中的方式。提交后,将焦点移至第一个可见的无效控件。这样一来,用户可以比较不同联系方式,而不会丢失电子邮件地址,也不会被隐藏的电话字段阻挡。示例中的十位数字电话规则仅适用于本地场景,应替换为服务实际要求的国际电话号码规则。
仅验证所选的联系方式字段。 更改任一选项都会清除旧的审核反馈。 结果不会声称已安排提醒。 B.C. 设计系统组件示例 main.jsx — 完整可运行示例 选择并审核一种联系方式。以下源代码是完整的 React 入口文件,包含全部状态和验证逻辑。
jsx 复制代码
import React, { useState, useRef } from "react";
import { createRoot } from "react-dom/client";
import {
Button,
Radio,
RadioGroup,
TextField,
Checkbox,
} from "@bcgov/design-system-react-components";
import "@bcgov/bc-sans/css/BC_Sans.css";
import "./bc.css";
function App() {
const [method, setMethod] = useState("email"),
[email, setEmail] = useState(""),
[phone, setPhone] = useState(""),
[consent, setConsent] = useState(false),
[submitted, setSubmitted] = useState(false),
[result, setResult] = useState("");
const panel = useRef(null);
const invalidEmail = !/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(email),
invalidPhone = phone.replace(/\D/g, "").length < 10;
function change(fn, value) {
fn(value);
setResult("");
setSubmitted(false);
}
function review(e) {
e.preventDefault();
setSubmitted(true);
if ((method === "email" ? invalidEmail : invalidPhone) || !consent) {
requestAnimationFrame(() =>
panel.current
.querySelector(
'[aria-invalid="true"] input,input[aria-invalid="true"],input[type=checkbox]:not(:checked)',
)
?.focus(),
);
return;
}
setResult(
`Local preference ready: ${method === "email" ? "Email to " + email : "Phone call to " + phone}. No reminder has been scheduled.`,
);
}
return (
<main>
<header>
<div className="eyebrow">
SERVICE REMINDER / ORIGINAL APPLICATION STUDY
</div>
<h1>Choose how to hear from us</h1>
<p>
Set a sample reminder preference. Use fictional contact details in
this local example.
</p>
</header>
<div className="columns">
<form onSubmit={review} noValidate ref={panel}>
<RadioGroup
label="Contact method"
value={method}
onChange={(v) => change(setMethod, v)}
description="Choose one way to receive a reminder."
>
<Radio value="email">Email</Radio>
<Radio value="phone">Phone call</Radio>
</RadioGroup>
<div className="field">
{method === "email" ? (
<TextField
label="Email address"
type="email"
value={email}
onChange={(v) => change(setEmail, v)}
isRequired
isInvalid={submitted && invalidEmail}
errorMessage="Enter an email address in the format [email protected] ."
description="Use a sample address, such as [email protected] ."
/>
) : (
<TextField
label="Phone number"
type="tel"
value={phone}
onChange={(v) => change(setPhone, v)}
isRequired
isInvalid={submitted && invalidPhone}
errorMessage="Enter a phone number with at least 10 digits."
description="Sample validation only; a real service needs a jurisdiction-aware phone rule."
/>
)}
</div>
<div className="field">
<Checkbox
isSelected={consent}
onChange={(v) => change(setConsent, v)}
isInvalid={submitted && !consent}
>
I agree to use these details for this sample reminder
</Checkbox>
{submitted && !consent && (
<p className="error" role="alert">
Confirm the reminder preference before continuing.
</p>
)}
</div>
<Button type="submit" variant="primary">
Review preference
</Button>
<p className="result" role="status">
{result}
</p>
</form>
<aside>
<div className="status-mark" aria-hidden="true">
i
</div>
<h2>What happens next</h2>
<ol>
<li>Choose a contact method.</li>
<li>Review the sample details.</li>
<li>Connect a real notification service before scheduling.</li>
</ol>
<p>
This example keeps both fields while switching methods, but only
reviews the selected method.
</p>
<details>
<summary>About this specimen</summary>
<p>
Native B.C. React Aria components with BC Sans. The form is
original and is not an official government service.
</p>
</details>
</aside>
</div>
</main>
);
}
createRoot(document.getElementById("root")).render(<App />);
代码参考
创建 Vite React 项目,保留 <div id="root"></div>,并将以下内容保存为 src/main.jsx。 bc.css — 原始响应式布局 围绕原生组件构建的应用布局。
css 复制代码
* {
box-sizing: border-box;
}
body {
margin: 0;
font:
16px/1.5 "BC Sans",
sans-serif;
color: var(--typography-color-primary, #2d2d2d);
background: white;
}
main {
padding: 32px;
}
header {
border-top: 6px solid #fcba19;
border-bottom: 1px solid #d8d8d8;
padding: 24px 0;
margin-bottom: 32px;
}
.eyebrow {
font-size: 13px;
color: #474543;
}
h1 {
font-size: 32px;
line-height: 1.25;
margin: 8px 0 16px;
}
h2 {
font-size: 24px;
margin: 0 0 16px;
}
p {
margin: 8px 0 16px;
}
.columns {
display: grid;
grid-template-columns: 1.4fr 1fr;
gap: 48px;
}
form {
max-width: 620px;
}
.field {
margin: 24px 0;
}
aside {
padding: 24px;
background: #f1f8fe;
border-left: 4px solid #1a5a96;
align-self: start;
}
.status-mark {
background: #1a5a96;
color: white;
border-radius: 50%;
width: 32px;
height: 32px;
display: grid;
place-items: center;
font-weight: bold;
margin-bottom: 16px;
}
ol {
padding-left: 24px;
}
li {
padding-left: 4px;
margin: 12px 0;
}
.error {
color: #ce3e39;
font-size: 14px;
}
.result {
margin-top: 24px;
color: #24613b;
}
summary {
cursor: pointer;
text-decoration: underline;
color: #1a5a96;
}
details {
margin-top: 24px;
}
details p {
font-size: 14px;
}
@media (max-width: 767px) {
main {
padding: 16px;
}
.columns {
grid-template-columns: 1fr;
gap: 24px;
}
h1 {
font-size: 28px;
}
aside {
padding: 16px;
}
}
代码参考
将其保存在 main.jsx 旁边。这些自定义组合规则有别于库的设计令牌参考。 实现起点 已打包固定的原生示例,并在本地浏览器中完成检查。该示例仅使用本地应用状态。
sh 复制示例
npm create vite@latest bc-reminder -- --template react
cd bc-reminder
npm install
npm install @bcgov/[email protected] @bcgov/[email protected] @bcgov/[email protected]
# Replace src/main.jsx and add src/bc.css using the complete examples.
npm run dev 适用于你项目的提示词 Agent 提示词 复制提示词
使用 B.C. React components 0.8.1 和 BC Sans 2.1.2 构建提醒表单。保留条件验证、已保留的输入内容、可见错误以及过期结果清除功能。使用当前设计令牌名称和正确的带空格字体系列。尚无正式通知约定前,请将示例保留在本地。 基于当前公开的 B.C. React 库进行的 OpenDesign 应用研究。这是原创的本地表单,并非官方政府服务;请使用虚构的联系信息。