一、项目结构

开发过程中涉及的主要目录及用途如下;

  • tests 测试用例,其内部目录结构与src文件夹保持一致
  • docs 文档
  • examples 网站示例
  • src 开发目录

二、规范

1. 命名

文件夹与文件

名称全部使用小写,单词或分隔使用 - 符号,测试文件需要添加 -spec 标识
示例:

  • index.ts
  • basic-slider.ts
  • number-spec.ts 测试文件

变量

首字母小写的驼峰命名法
示例

  • lowercaseVaribaleName

常量

字母全部大写,单词之间使用下划线_分隔
示例

  • CONSTANT_NAME

类型与接口

驼峰命名法
示例

  • TypeName

类名

驼峰命名法
示例

  • ClassName

2. 编码

整体编码规范见 JavaScript 编码规范

三、开发流程

1. 开发设计文档

正式组件开发之前,需要进行充分调研,包括但不限于 1. 参考现有组件缺点 2. 吸取同类组件优点 3. 创新性特性。最终形成开发设计【文档】, 文档需包括:

  • 组件简介与描述
  • 设计草图
  • 引用方式
  • 配置项
    • 配置项名称
    • 类型
    • 默认值(若有)
    • 描述
  • 事件
    • 事件名称
    • 事件参数
  • API
    • 接口名称
    • 参数列表及类型
    • 返回值类型
  • 交互

2. 评审

形成文档后,通知专家进行评审,评审考察点包括但不限于:

  • 组件必要性、可用性
  • 配置项、事件、API的完整性、必要性、命名合理性
  • 交互设计的可用性

待评审通过后方可进入编码阶段

3. 编码

开发组件代码位于src/ui/目录,组件需根据其名称单独创建文件夹,内部至少包含入口文件index.ts,类型定义types.ts,可根据项目需要添加常量文件constant.ts,组件工具方法文件utils.ts以及子组件文件。
示例:(Slider)

  • index.ts
  • types.ts
  • handle.ts 子组件

类型定义

首先根据开发设计文档中的配置项在types.ts中完成类型定义,常用的类型引用

  1. // 图形配置项
  2. import {
  3. ShapeAttrs, // 基本图形配置项类型
  4. DisplayObject, // 图形基类类型
  5. DisplayObjectConfig, // 图形配置项类型
  6. CircleProps, // 圆型配置项类型
  7. EllipseProps, // 椭圆配置项类型
  8. RectProps, // 矩形配置项类型
  9. ImageProps, // 图片配置项类型
  10. LineProps, // 线条配置项类型
  11. PathProps, // 路径配置项类型
  12. PolylineProps, // 多边形配置项类型
  13. TextProps, // 文本配置项类型
  14. Group, // 分组配置项类型
  15. } from "../../types";

对于某些在不同状态下具有不同样式的图形,使用MixAttrs<>来定义其样式属性

  1. // 带状态的文本样式
  2. textStyle: MixAttrs<Partial<TextProps>>;
  3. // 带状态的矩形样式
  4. rectStyle?: MixAttrs<Partial<RectProps>>;
  5. // 使用
  6. textStyle:{
  7. default: {} // 默认状态
  8. active: {} // hover状态
  9. disable: {} // 禁用状态
  10. selected: {} // 选择状态
  11. }

对于一个组件,其配置项包括两个部分

  • 参数配置项 以【组件名Cfg】形式命名,其需要具有基本的图形属性。需要注释各配置项的作用
  • 初始化配置项 以【组件名Options】命名,并使用参数配置项作为DisplayObjectConfig的泛型 ```typescript // Button types export type ButtonCfg = { x: number; y: number; // …配置项 }

// or // export interface ButtonCfg {}

export type ButtonOptions = DisplayObject

// Legend types export type LegendBaseCfg = ShapeAttrs & { // …配置项 } export type LegendBaseOptions = DisplayObjectConfig;

  1. <a name="HJZro"></a>
  2. #### 组件
  3. 绘制组件所使用的子组件、图形按需引入,[@antv/g](http://g-next.antv.vision/zh/docs/api/basic/display-object)提供了基本图形,也可以先自行封装然后引入。<br />组件类需继承自GUI类,且包含**组件tag**,**配置项默认值**、**构造方法**、**初始化方法、更新方法、事件绑定,**用到的子组件需定义为**类成员变量**
  4. ![](https://intranetproxy.alipay.com/skylark/lark/0/2021/jpeg/20156471/1629976260169-e8c64d37-4519-4109-b333-2e8d60416d42.jpeg)
  5. > 为了方便组件更新,建议使用 getter 的方式来计算出绘制每个子图形、组件的属性,然后通过subShape.attr(cfg) 的形式应用属性
  6. ```typescript
  7. // 以 Button 组件为例
  8. export class Button extends GUI<Required<ButtonCfg>>{
  9. public static tag = 'button'; // tag 名称全小写,单词使用 - 分隔
  10. public static defaultOptions = {
  11. type: Button.tag,
  12. style:{
  13. // 配置项默认值
  14. }
  15. }
  16. private textShape!: Text;
  17. private backgroundShape!: Rect;
  18. private get textCfg() {} // 得到 textShape 配置项的 getter
  19. private get backgroundCfg() {} // 得到 backgroundShape 配置项的 getter
  20. constructor(options: ButtonOptions){
  21. super(deepMix({}, Button.defaultOptions, options));
  22. // do something others
  23. }
  24. // 初始化方法
  25. public init() {}
  26. // 更新方法
  27. public update(cfg: Partial<ButtonCfg>){
  28. // 根据需要使用 cfg
  29. // this.attr(deepMix({}, this.attributes, cfg));
  30. }
  31. // 清理方法
  32. public clear() {}
  33. // 销毁方法
  34. public destory() {
  35. /**
  36. * 1. 子组件销毁 可使用 this.removeChildren(true); 方法
  37. */
  38. }
  39. private initShape(){
  40. // 初始化 textShape backgroundShape
  41. }
  42. // 事件回调方法
  43. private eventCallback = (event) => {}
  44. // 绑定事件
  45. private bindEvents() {}
  46. }

常用库方法

  1. import {
  2. clone, // 深度拷贝
  3. clamp,
  4. deepMix, // 递归合并两个Object
  5. pick, // 从Object中根据name挑选值
  6. throttle, // 节流
  7. get, // 从Object中根据name获得值
  8. min,
  9. max,
  10. minBy,
  11. maxBy,
  12. isArray,
  13. isElement,
  14. isFunction,
  15. isNumber,
  16. isString,
  17. isUndefined,
  18. } from "@antv/util";

3. 测试

使用jest框架进行单元测试,测试范围包括但不限于

  • 子组件位置是否正确
  • 样式是否生效
  • 交互是否正常
  • 事件能否触发
  • 生命周期流程是否正常
  • 方法输出是否正确

4. 使用文档

使用文档需包含

  • 组件名称及介绍
  • 引用方法
  • 配置项名称、描述、类型及默认值

5. 网站示例

创建美观的组件示例,尽可能展现组件的各个形态与能力

6. 提交代码

提交代码前需通过ci,具体操作

  1. npm run ci