title: 泛微 E9 前端开发速查表 (JS/CheatSheet) created: 2026-04-21 updated: 2026-04-21 type: reference tags: [weaver, e9, js, wfform, ecode, dev] related: [oa/ecode-guide.md, oa/development-standards.md]
泛微 E9 前端开发速查表
本文档汇总了泛微 E9 流程表单开发中常用的 WfForm API、常见场景代码模板及最佳实践。适用于 Ecode 开发与表单自定义 JS 代码块。
1. 核心基础
1.1 环境准备与对象获取
E9 表单中,所有操作均基于 WfForm 对象。
jQuery(document).ready(function() {
// 获取 WfForm 对象(兼容 Ecode 和传统代码块)
const form = window.WfForm || window.parent.WfForm;
// 获取表单基础信息(节点ID、请求ID、workflowId 等)
// const baseInfo = WfForm.getBaseInfo();
});
1.2 最佳实践红线
- 严禁直接操作 DOM:如
document.getElementById或jQuery('#fieldxxx')获取值。必须使用WfFormAPI,否则在 E9 新版表单引擎或 Ecode 模式下可能失效。 - 变量声明:严禁使用
var。优先使用const(即便在回调中,也是独立快照),仅在需要重新赋值时使用let。 - ID 动态映射:使用
WfForm.convertFieldNameToId('name', 'detail_x')获取真实 Field ID,避免硬编码field123。
2. 常用 API 速查
2.1 主表字段操作
// 获取字段值 (返回字符串)
const value = form.getFieldValue('field1234');
// 设置字段值
form.setFieldValue('field1234', 'New Value');
// 绑定字段值变化事件
// id 是字段ID,value 是新值
form.bindFieldChangeEvent('field1234', function(obj, id, value){
console.log('字段值变为:', value);
});
``### 2.2 明细表操作 (Detail Table)
明细表字段 ID 格式通常为fieldID_rowIndex(如field1234_0`)。
// 获取明细表所有行索引字符串 (例如 "0,1,2")
// 注意:空行时可能返回 ""
const rowStr = form.getDetailAllRowIndexStr('detail_1');
const rows = rowStr ? rowStr.split(',') : [];
// 遍历明细表
rows.forEach(rowIndex => {
const val = form.getFieldValue(`field1234_${rowIndex}`);
// do something...
});
// 绑定明细字段变化事件
form.bindDetailFieldChangeEvent('field1234', function(id, rowIndex, value) {
console.log(`明细表行 ${rowIndex} 的值变为: ${value}`);
});
2.3 字段显示/隐藏与必填控制
// 显示字段
form.showField('field1234');
// 隐藏字段 (自动取消必填)
form.hideField('field1234');
// 设置/取消必填标记 (红星)
// 注意:仅设置 UI 标记,不改变后端校验配置。
form.setFieldRequiredMark('field1234', true);
form.setFieldRequiredMark('field1234', false);
2.4 常用工具函数
// 日期范围控制 (endDate >= startDate)
// 字段 change 时触发
WfForm.controlDateRange('startDateField', 'endDateField');
// 浏览按钮过滤条件
// 过滤出部门 ID 为 123 的人员
form.setBrowserCondition('hrmField', "departmentid='123'");
3. 高频场景代码模板
部门 ID 为 123 的人员 form.setBrowserCondition('hrmField', "departmentid='123'");
---
## 3. 高频场景代码模板### 3.1 场景:字段联动(显示/隐藏 + 必填联动)
**需求**:当字段 A 选择"是"时,显示字段 B 并设为必填;否则隐藏并清空。
```javascript
jQuery(document).ready(function() {
const FIELD_A = 'field100'; // 触发字段
const FIELD_B = 'field101'; // 目标字段
const form = window.WfForm;
function toggleField() {
const valA = form.getFieldValue(FIELD_A);
if (valA === '1') { // 假设 '1' 代表是
form.showField(FIELD_B);
form.setFieldRequiredMark(FIELD_B, true);
} else {
form.hideField(FIELD_B);
form.setFieldRequiredMark(FIELD_B, false);
form.setFieldValue(FIELD_B, ''); // 隐藏时清空值,防止提交校验报错
}
}
// 绑定变化事件
form.bindFieldChangeEvent(FIELD_A, function(obj, id, value){
toggleField();
});
// 页面加载初始化 (使用 setTimeout 防止表单未加载完)
setTimeout(toggleField, 500);
});
// 页面加载初始化 (使用 setTimeout 防止表单未加载完)
setTimeout(toggleField, 500);
}); ```### 3.2 场景:明细表数据校验(提交拦截) 需求:提交时检查明细表中字段 A 不能为空。
jQuery(document).ready(function() {
const form = window.WfForm;
const FIELD_A = 'field200';
// 注册提交前检查事件 (支持保存、提交、提交确认)
form.registerCheckEvent(WfForm.OPER_SAVE + ',' + WfForm.OPER_SUBMIT, function(callback){
let errorMsg = '';
const rows = form.getDetailAllRowIndexStr('detail_1').split(',');
for (let i = 0; i < rows.length; i++) {
const row = rows[i];
const val = form.getFieldValue(`${FIELD_A}_${row}`);
if (!val || val.trim() === '') {
errorMsg += `第 ${parseInt(row)+1} 行 [字段A] 不能为空。\n`;
}
}
if (errorMsg) {
WfForm.showConfirm(errorMsg, function(){ /* 点击确定后无操作 */ });
return; // 阻断提交
}
callback(); // 校验通过,继续提交流程
});
});
callback(); // 校验通过,继续提交流程
});
}); ```### 3.3 场景:明细表数值汇总到主表 需求:明细表金额变化时,自动汇总到主表“总金额”。
jQuery(document).ready(function() {
const form = window.WfForm;
const DETAIL_FIELD = 'field300'; // 明细金额
const MAIN_TOTAL = 'field301'; // 主表总额
const DETAIL_TABLE = 'detail_1';
function calcTotal() {
let sum = 0;
const rows = form.getDetailAllRowIndexStr(DETAIL_TABLE).split(',');
rows.forEach(idx => {
let val = parseFloat(form.getFieldValue(`${DETAIL_FIELD}_${idx}`));
if (!isNaN(val)) sum += val;
});
form.setFieldValue(MAIN_TOTAL, sum.toFixed(2));
}
// 绑定明细字段变化
form.bindDetailFieldChangeEvent(DETAIL_FIELD, calcTotal);
// 绑定明细行增删事件
form.bindFieldAction('click', `addDetail${DETAIL_TABLE}`, calcTotal);
form.bindFieldAction('click', `delDetail${DETAIL_TABLE}`, calcTotal); // 需确认删除按钮ID格式
});
4. 避坑指南
| 坑点现象 | 原因分析 | 解决方案 |
|---|---|---|
WfForm is not defined |
脚本在 WfForm 加载前执行 | 放在 jQuery(document).ready 中;Ecode 中使用 onRender 或 setInterval 轮询直到 WfForm 存在。 |
| 隐藏字段后提交报错 | 字段设为必填,隐藏后清空了值 | 隐藏时务必调用 form.setFieldRequiredMark(id, false) 取消必填。 |
明细表取值 undefined |
索引拼接错误 | 确保格式为 fieldID + '_' + rowIndex。注意 rowIndex 是从 0 开始的字符串。 |
bindFieldChangeEvent 不触发 |
字段 ID 错误或被覆盖 | 检查字段是否被其他脚本覆盖;确认 ID 是后端真实 ID 而非 Name。 |