# leopard-formula **Repository Path**: shuiyebuai/leopard-formula ## Basic Information - **Project Name**: leopard-formula - **Description**: 适用于低代码平台公式编辑器,公式解析执行器 - **Primary Language**: JavaScript - **License**: MIT - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 2 - **Created**: 2024-08-20 - **Last Updated**: 2024-09-01 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README ## 公式编辑器&公式引擎 ### 运行截图 ![img.png](docs/image/img.png) ### 公式编辑器 #### 创建编辑器 > `FormulaEditor` 基于 `codemirror/EditorView` 扩展 ```typescript const containerRef = shallowRef(); const instance = new FormulaEditor(containerRef, { extensions: createExtensions({ /** 自定义关键字 */ keywords: [], /** 自定义函数名 */ functions: ['SUM'], /** 自定义变量 value:字段全路径 */ variables: [ {label: '用户', value: 'user', type: 'object', category: 'field'}, {label: '用户.名称', value: 'user.name', type: 'string', category: 'field'}, {label: '用户.年龄', value: 'user.age', type: 'number', category: 'field'}, {label: '用户.组织', value: 'user.org', type: 'number', category: 'field'}, {label: '用户.组织.名称', value: 'user.org.name', type: 'text', category: 'field'}, ], /** 自定义提示 默认的变量匹配规则是{},所以value必须包含在{}中 */ hints: [ {label: '用户', value: '{user}', type: 'variable', detail: '用户', children: [ {label: '名称', value: '{user.name}', type: 'text', detail: '用户的名称'}, {label: '年龄', value: '{user.age}', type: 'variable', detail: '用户的年龄, number类型'}, {label: '组织', value: '{user.org}', type: 'class', detail: '用户的组件', children: [ {label: '名称', value: '{user.org.name}', type: 'text', detail: '组件名称'}, ] }, ] }, ] }) }); ``` #### 编辑器实例方法 | 名称 | 类型 | 说明 | |:----------------|:---------------------------------------|:---------------------------------| | getValue | `()` | 获取编辑器内容 | | setValue | `(value: string)` | 设置编辑器内容,会覆盖原内容 | | insertValue | `(value: string, isTemplate: boolean)` | 插入内容, `isTemplate`插入的内容是否需要按模板解析 | | setDisabled | `(disabled: boolean)` | 禁用编辑器 | | setPlaceholder | `(placeholder: string)` | 设置占位文本 | | setStyle | `(style: object)` | 设置编辑器样式 | | reloadExtension | `(extension: Extension)` | 刷新插件 | | focus | `()` | 编辑器获取焦点 | | dispose | `()` | 销毁编辑器 | #### 自定义变量匹配规则 > 通过 `createVariablePlugin(variables, regexp)` 方法创建自定义匹配规则 ```typescript /** 定义成 {{ }} 匹配变量 */ const variableExtension = createVariablePlugin( [ {label: '用户', value: 'user', type: 'object', category: 'field'}, {label: '用户.名称', value: 'user.name', type: 'string', category: 'field'}, {label: '用户.年龄', value: 'user.age', type: 'number', category: 'field'}, {label: '用户.组织', value: 'user.org', type: 'number', category: 'field'}, {label: '用户.组织.名称', value: 'user.org.name', type: 'text', category: 'field'}, ], /{{(.+?)\}\}/g ); const containerRef = shallowRef(); const instance = new FormulaEditor(containerRef, { extensions: [variableExtension] }) ``` ### 公式引擎 #### 创建解析引擎 ```typescript const formulaEngine = new FormulaEngine({ /** 注入自定义函数 key为函数名 */ functions: { 'GETUSERNAME': function(users) { if(!users || !Array.isArray(users)) return '' return users.map(user=> user.name).join(',') }, }, /** 全局变量 */ scopeData: {}, }); /** 执行公式 */ const res = formulaEngine.exec(formulaStr, variableData); ``` #### 自定义变量匹配规则 > 覆盖 `variableToken`。 name 固定为 `VARIABLE` ```typescript const formulaEngine = new FormulaEngine({ functions: { 'GETUSERNAME': function(users) { if(!users || !Array.isArray(users)) return '' return users.map(user=> user.name).join(',') }, }, scopeData: {}, variableToken: { name: "VARIABLE", pattern: /{{.*?\}\}/, } }); ``` #### 解析引擎实例方法 | 名称 | 类型 | 说明 | |:------------------|:----------------------------------------------------------------|:-----------------------------------------------------------------------| | registerFunctions | `(fus: Record)` | 注册自定义函数 | | exec | `(expression: string, scopeData?: object, autoMerge?: boolean)` | 执行公式,`expression`为公式字符串,`scopeData`为变量数据,`autoMerge`是否和全局变量合并,否则覆盖全局变量 | | dispose | `()` | 销毁重置 | #### 解析引擎内置函数 * 日期函数 | 名称 | 类型 | 说明 | 使用示例 | |:------|:-----|:--------|:----------| | TODAY | `()` | 返回当前时间戳 | `TODAY()` | * 逻辑函数 | 名称 | 类型 | 说明 | 使用示例 | |:------|:------------------|:------------------------|:------------------------------| | AND | `(...args)` | 并且,每一项参数为真则返回真,有一项为假返回假 | `AND(3>2, 2>1, 1>1) => false` | | OR | `(...args)` | 或者,有一项为真则返回真,全部为假返回假 | `OR(3>2, 1>2, 1>1) => true` | | FALSE | `()` | 总是返回假 | `FALSE()` | | TRUE | `()` | 总是返回真 | `TRUE()` | | IF | `(logic, p1, p2)` | 条件判断,为真返回`p1`,否则返回`p2` | `IF(3>4, 1, 2) => 2` | | NOT | `(logic)` | 结果取反 | `NOT(3>4) => true` | | XOR | `(...args)` | 异或,每一项都相同返回假,有一项不同则返回真 | `XOR(a>10,b>10)` | * 数学函数 | 名称 | 类型 | 说明 | 使用示例 | |:----|:-----------|:--------------|:---------------------------| | ADD | `(a,b,n?)` | 两数相加,`为保留小数位` | `ADD(1.5, 2.41, 1) => 3.9` | * 文本函数 | 名称 | 类型 | 说明 | 使用示例 | |:-----|:-------------------|:---------------------------|:---------------------------------------| | JOIN | `(arr, separator)` | 数组拼接成字符串, `separator`为拼接符号 | `JOIN(['a','b', 'c'], '-') => 'a-b-c'` |