This skill should be used when creating a new TDesign React component. It provides a complete SOP for scaffolding components in the packages/components or packages/pro-components directories, including file structure, code patterns, and registration steps.
本技能提供 TDesign React 新组件开发的完整 SOP 流程。
当用户需要执行以下任务时使用此技能:
根据组件性质选择目标位置:
| 组件类型 | 目录 | 说明 |
|---|---|---|
| 基础组件 | packages/components/ | 通用 UI 组件(button, input, select 等) |
| 高阶组件 | packages/pro-components/ | 业务/AIGC 组件(chat, copilot 等) |
以组件名 example-component(PascalCase: ExampleComponent)为例:
packages/components/example-component/
├── index.ts # 组件入口
├── ExampleComponent.tsx # 组件主文件
├── type.ts # 类型定义(由 API 平台生成)
├── defaultProps.ts # 默认属性(由 API 平台生成)
├── example-component.md # 中文文档
├── example-component.en-US.md # 英文文档
├── style/
│ ├── index.js # Less 样式入口
│ └── css.js # CSS 样式入口
├── _example/
│ └── base.tsx # 基础示例
├── _usage/ # Live Demo 配置(可选)
│ └── props.json
└── __tests__/
└── vitest-example-component.test.tsx
import _ExampleComponent from './ExampleComponent';
import './style/index.js';
export type { ExampleComponentProps } from './ExampleComponent';
export * from './type';
export const ExampleComponent = _ExampleComponent;
export default ExampleComponent;
使用 forwardRef + useDefaultProps 标准模式:
import React, { forwardRef } from 'react';
import classNames from 'classnames';
import useConfig from '../hooks/useConfig';
import useDefaultProps from '../hooks/useDefaultProps';
import { TdExampleComponentProps } from './type';
import { exampleComponentDefaultProps } from './defaultProps';
export interface ExampleComponentProps extends TdExampleComponentProps {
// 扩展属性(如原生 HTML 属性)
}
const ExampleComponent = forwardRef<HTMLDivElement, ExampleComponentProps>(
(originProps, ref) => {
// 1. 合并默认属性
const props = useDefaultProps(originProps, exampleComponentDefaultProps);
const { className, style, ...restProps } = props;
// 2. 获取前缀配置
const { classPrefix } = useConfig();
const componentClass = `${classPrefix}-example-component`;
// 3. 计算类名
const rootClassName = classNames(componentClass, className);
// 4. 渲染
return (
<div ref={ref} className={rootClassName} style={style}>
{/* 组件内容 */}
</div>
);
}
);
ExampleComponent.displayName = 'ExampleComponent';
export default ExampleComponent;
⚠️ 重要:此文件由 API 平台生成,不应手动编辑。
临时开发时可以先写一个简化版本,后续由 API 平台覆盖:
/* eslint-disable */
/**
* 该文件为脚本自动生成文件,请勿随意修改。如需修改请联系 PMC
* */
import { TNode, StyledProps } from '../common';
export interface TdExampleComponentProps extends StyledProps {
/**
* 组件内容
*/
children?: TNode;
/**
* 是否禁用
* @default false
*/
disabled?: boolean;
}
⚠️ 重要:此文件由 API 平台生成,不应手动编辑。
/**
* 该文件为脚本自动生成文件,请勿随意修改。如需修改请联系 PMC
* */
import { TdExampleComponentProps } from './type';
export const exampleComponentDefaultProps: TdExampleComponentProps = {
disabled: false,
};
style/index.js(引用 Less 源文件):
import '../../_common/style/web/components/example-component/index.less';
style/css.js(引用编译后 CSS):
import '../../_common/style/web/components/example-component/index.css';
import React from 'react';
import { ExampleComponent } from 'tdesign-react';
export default function ExampleComponentBase() {
return <ExampleComponent>基础用法</ExampleComponent>;
}
位置: __tests__/vitest-example-component.test.tsx
import { render } from '@testing-library/react';
import ExampleComponent from '../ExampleComponent';
describe('ExampleComponent', () => {
it('renders correctly', () => {
const { container } = render(<ExampleComponent />);
expect(container.firstChild).toHaveClass('t-example-component');
});
it('supports disabled state', () => {
const { container } = render(<ExampleComponent disabled />);
expect(container.firstChild).toHaveClass('t-is-disabled');
});
});
编辑 packages/components/index.ts,添加导出:
// 在文件末尾添加
export * from './example-component';
编辑 packages/tdesign-react/site/site.config.mjs:
{
title: '基础组件',
type: 'component',
children: [
// ... 其他组件
{
title: 'ExampleComponent 示例组件',
name: 'example-component',
path: '/react/components/example-component',
component: () => import('tdesign-react/example-component/example-component.md'),
},
],
}
组件文档采用 Markdown + {{ xxx }} 占位符 机制,占位符会在站点构建时自动解析为 _example/xxx.tsx 中导出的 React 组件。
基础组件 使用双层拼接:
packages/common/docs/web/api/<component>.md — 包含使用说明文本和 {{ xxx }} 示例占位符,这是文档的核心内容packages/components/<component>/<component>.md — 以 :: BASE_DOC :: 开头自动引入上层文档主体,后面追加 React 特有的 API 表格⚠️ 当
<component>.md以:: BASE_DOC ::开头时,文档的使用说明和示例占位符不在这个文件中,而是在packages/common/docs/web/api/<component>.md里。
映射规则:每个 {{ xxx }} 对应 _example/xxx.tsx,文件必须默认导出一个 React 组件。
---