PLC 配置页面原始功能详细规格
基于原工程 libplc C 引擎 + Reclose_logic.xml 完整分析
分析日期: 2026-07-10
目标: 重构前端 PLC Config 页面,做到比原工程更好
一、PLC 系统架构
┌─────────────────────────────────────────────────────────────────┐
│ RTU 运行时 │
│ │
│ config/PLC/Reclose_logic.xml ──→ pls.cpp parse_reclose_logic │
│ (mtime 文件变化检测, stat) │ │
│ ↓ │
│ LogicGraph[] (最多4个) │
│ │ │
│ EV_TIMER3 (1s) │
│ ↓ │
│ PLC_Logic() 执行: │
│ 1. 读取 datacenter input 信号 │
│ 2. Kahn 拓扑排序 │
│ 3. 按拓扑序执行各门逻辑 │
│ 4. 写入 datacenter output 信号 │
└─────────────────────────────────────────────────────────────────┘
二、XML 格式完全规格 (Reclose_logic.xml)
顶层结构
<?xml version="1.0" encoding="UTF-8"?>
<PLCConfig name="PLC Logic" key="1783070862205" checksum="3486BE04">
<Chain gates="N" inputs="N" outputs="N">
<!-- 简单 Chain 无 Comb: Inputs → Gates → Outputs 顺序 -->
<Inputs> <Signal no="ID" x="X" y="Y"/> ... </Inputs>
<Gate type="TYPE" id="N" x="X" y="Y" [delayMs="MS"] [S="src"] [R="src"]/>
...
<!-- 含 Comb 的 Chain: Comb 可嵌套, 位置不固定 -->
<Comb id="N">
<Inputs> ... </Inputs>
<Gate .../>
<Comb id="N"> <!-- 嵌套 Comb -->
<Inputs> ... </Inputs>
<Gate .../>
<Outputs> ... </Outputs>
</Comb>
<Gate .../>
<Outputs> ... </Outputs>
</Comb>
<Outputs> <Signal no="ID" x="X" y="Y"/> ... </Outputs>
</Chain>
<Chain ...> ... </Chain>
</PLCConfig>
关键节点类型 (10 种)
| type |
Name |
功能 |
参数 |
输入引脚 |
输出引脚 |
| 0 |
INPUT |
硬件输入, 从 datacenter 读取值 |
no=信号ID |
0 |
1 |
| 1 |
OUTPUT |
硬件输出, 写入 datacenter |
no=信号ID |
1 |
0 |
| 2 |
OR |
或门, 任意输入=1→输出1 |
id=门ID |
2 |
1 |
| 3 |
AND |
与门, 全部输入=1→输出1 |
id=门ID |
2 |
1 |
| 4 |
NOT |
非门, 取反 |
id=门ID |
1 |
1 |
| 5 |
T62P |
延时导通 (IN=1 等待 delayMs ms 后 OUT=1) |
id, delayMs |
1 |
1 |
| 6 |
T62D |
延时关断 (IN=0 等待 delayMs ms 后 OUT=0) |
id, delayMs |
1 |
1 |
| 7 |
RISING |
上升沿检测 (0→1 产生一周期脉冲) |
id |
1 |
1 |
| 8 |
SR |
SR 触发器 (S优先: S=1置位, R=1& S=0复位) |
id, S, R |
2 (S=0, R=1) |
1 |
| 9 |
RS |
RS 触发器 (R优先: R=1复位, S=1& R=0置位) |
id, S, R |
2 (S=0, R=1) |
1 |
| 10 |
FALLING |
下降沿检测 (1→0 产生一周期脉冲) |
id |
1 |
1 |
Comb 的 C 引擎自动检测逻辑
parse_xml_comb(comb_el, graph):
1. 遍历 comb_el 的子元素 (<Inputs>, <Gate>, <Comb>, <Outputs>)
2. 遇到子 <Comb> → 递归调用 parse_xml_comb() ← 这就是嵌套自动检测
3. 子 Comb 的 Gate 输出 → 父 Comb 的 Gate 输入 (自动连线)
4. 遇到 <Inputs> → 创建 HW_INPUT 节点 → 连线到同层 Gate
5. 遇到 <Gate> → 创建门节点 + 解析 R/S 属性
- R="Comb#N" → 查找子 Comb 中对应 Gate 的输出
- S="Comb#N" → 同上
- R="Input#N" / S="Input#N" → 创建对应 Input 节点
6. 遇到 <Outputs> → 创建 HW_OUTPUT 节点 → 连线从同层 Gate
链级别 Comb 处理 (第二遍布线):
1. Comb 的 Gate 输出 → 链级 Gate 输入
2. 链级 Input → 链级 Gate
3. 链级 Gate → 链级 Output
核心结论: Comb 是 XML 中天然存在的嵌套结构,C 引擎自动递归解析。前端应该:
- 加载 XML 时自动识别 Comb 嵌套关系
- 渲染为视觉分组容器 (矩形框)
- 允许用户通过拖拽节点入框来创建 Comb
- 不允许手动添加空 Comb
三、原工程 PLC Config 前端功能详细清单
3.1 导航与入口
- Hash 路由:
#plc_config
- 导航标签: "PLC 配置" / "PLC Config"
- 导航图标: 原工程用 emoji 🧩, 当前用 SVG cpu
3.2 多 Chain 管理
| 功能 |
描述 |
实现方式 |
| Chain 标签切换 |
顶部标签栏,每个 Chain 一个标签 |
点击切换当前编辑的 Chain |
| Chain 标签内容 |
显示 "Chain N (节点数)" |
实时更新 |
| 添加 Chain |
+Chain 按钮 |
创建空 Chain, 自动切换 |
| 删除 Chain |
-Chain 按钮 |
删除当前 Chain (≥2个时可用) |
3.3 节点类型工具栏
每种节点类型一个按钮,点击后在 Canvas 随机位置添加:
[+INPUT] [+OUTPUT] [+OR] [+AND] [+NOT] [+T62P] [+T62D] [+RISING] [+SR] [+RS] [+FALLING]
3.4 Canvas 画布编辑器
| 功能 |
描述 |
交互 |
| 节点渲染 |
圆角矩形 + 类型名 + ID号 + 颜色区分 |
11种颜色方案 |
| 引脚圆点 |
输入引脚(左, 彩色), 输出引脚(右, 绿色) |
5px 半径 |
| 连线渲染 |
节点间实线, 从输出引脚→输入引脚 |
深灰 #2c3e50 |
| 拖拽节点 |
按住节点拖动 |
20px 网格吸附 |
| 连线操作 |
从输出引脚拖出虚线→目标输入引脚释放 |
红色虚线 |
| 选中节点 |
单击节点高亮 |
白色填充 + 红色边框 |
| 删除节点 |
选中 + 删除按钮 |
同时删除关联连线 + 重编号 Gate ID |
| 平移画布 |
拖拽空白区域 |
平移 |
| 缩放 |
滚轮缩放 0.5x-2.0x |
缩放栏显示百分比 |
| 缩放栏 |
[放大] [缩小] [适应] 100% |
适应 = zoom=1, pan=0 |
| 双击编辑 |
双击节点弹出属性 Modal |
编辑 saddr/desc/delayMs/spin/rpin |
3.5 Comb 组合块
| 功能 |
描述 |
| 自动识别 |
加载 XML 时自动解析 Comb 嵌套结构 |
| 视觉渲染 |
虚线圆角矩形,标签 "Comb #N" |
| 嵌套 Comb |
视觉上子 Comb 在父 Comb 内部 |
| 节点归属 |
Comb 内节点在视觉上位于 Comb 矩形内 |
| 创建 Comb |
选中多个节点 → "成组为 Comb" 创建 |
| 解散 Comb |
选中 Comb → "解散 Comb" → 节点回到链级别 |
3.6 XML 查看与持久化
| 功能 |
描述 |
| XML 实时预览 |
只读 <pre> 标签, 随编辑实时更新 |
| 加载 XML |
从 RTU 读取 cat config/PLC/Reclose_logic.xml |
| 保存 XML |
通过 WS set_file 写回 RTU |
| checksum |
根节点自动计算 XOR checksum |
3.7 操作按钮栏
[加载 XML] [保存 XML] [清空] [删除选中节点]
四、原工程 UI 设计参考
4.1 设计风格
| 参数 |
原设计值 |
当前值 |
| 风格 |
暗色工业主题 (Dark Industrial Dashboard) |
暗色工业主题 |
| 主色调 |
Cyan/Teal (#00E5FF / #1DE9B6) |
Teal (#00d4aa) |
| 背景 |
#0F1923 (deep navy) |
#0a0f16 (更深) |
| 卡片背景 |
#1A2332 |
#111922 |
| 字体 |
Inter + JetBrains Mono |
同 |
| 图标 |
Emoji (原工程) → SVG Lucide (重构目标) |
SVG 内联 Lucide |
| Canvas 背景 |
浅色网格 (#f0f2f5) |
同 |
4.2 导航图标规格
| 页面 |
原 Emoji |
Lucide SVG 图标名 |
说明 |
| 仪表盘 |
📊 |
dashboard |
四象限网格 |
| 开出信号 |
📡 |
signal |
信号波形 |
| 开入信号 |
🔗 |
link |
链接 |
| 遥控信号 |
⚡ |
zap |
闪电 |
| 参数设置 |
🎚️ |
sliders |
滑块 |
| 定值管理 |
⚙️ |
settings |
齿轮 |
| 数据中心 |
📋 |
database |
数据库 |
| PLC 调试 |
🔌 |
bug |
Bug/调试 |
| PLC 配置 |
🧩 |
cpu |
CPU/芯片 |
| 实时监控 |
📈 |
activity |
心电图 |
| 命令终端 |
💻 |
terminal |
终端 |
五、重构目标与要求
5.1 必须保留/增强的功能
5.2 必须修复的问题
5.3 必须优于原工程的新功能
六、Comb 自动检测算法 (前端)
// 加载 XML 时的 Comb 自动检测伪代码
function detectCombsFromXml(xmlDoc):
for each <Chain> in <PLCConfig>:
chain.nodes = [] // 扁平存储所有节点
chain.combs = [] // 存储 Comb 容器定义
chain.links = [] // 存储连线
// 1. 解析顶层元素
parseChainElements(chainEl, chain, parentId=-1)
function parseChainElements(parentEl, chain, parentId):
for each child in parentEl.children:
if child.tag == 'Inputs' or 'Outputs':
parseSignals(child, chain)
if child.tag == 'Gate':
parseGate(child, chain)
if child.tag == 'Comb':
combId = child.getAttribute('id')
// 创建 Comb 容器 (位置由内部节点包围盒计算)
comb = { id: combId, parentId: parentId }
chain.combs.push(comb)
// 递归解析 Comb 内部元素
parseChainElements(child, chain, combId)
// 2. Comb 位置自动计算 (后处理)
for each comb in chain.combs:
var nodesInComb = chain.nodes.filter(n => 位于 comb 区域)
// 包围盒 = min/max of nodesInComb 的 x,y
comb.x = minX - margin
comb.y = minY - margin
comb.w = maxX - minX + 2*margin
comb.h = maxY - minY + 2*margin
Comb 归属判断
节点属于哪个 Comb 由以下规则确定:
- 来自 内 // → 属于该 Comb
- 来自 内子 的元素 → 属于子 Comb (嵌套)
- 来自 顶层元素 → 不属于任何 Comb (parentId=-1)
七、节点样式与颜色方案
| 节点 |
填充色 |
描边色 |
尺寸 |
| INPUT |
#e8f5e9 浅绿 |
#27ae60 绿 |
110×34 |
| OUTPUT |
#fce4ec 浅粉 |
#e74c3c 红 |
110×34 |
| OR |
#fff3e0 浅橙 |
#e67e22 橙 |
76×46 |
| AND |
#e3f2fd 浅蓝 |
#2980b9 蓝 |
76×46 |
| NOT |
#f3e5f5 浅紫 |
#8e44ad 紫 |
76×46 |
| T62P |
#fce4ec 浅粉 |
#c0392b 深红 |
86×46 |
| T62D |
#fff3e0 浅橙 |
#d35400 深橙 |
86×46 |
| RISING |
#e8f5e9 浅绿 |
#1abc9c 青绿 |
86×46 |
| SR |
#e3f2fd 浅蓝 |
#3498db 亮蓝 |
86×52 |
| RS |
#fce4ec 浅粉 |
#9b59b6 紫 |
86×52 |
| FALLING |
#fff3e0 浅橙 |
#16a085 青 |
86×46 |
引脚颜色: 输入=同节点描边色, 输出=#27ae60 绿
Comb 视觉
- 描边: #95a5a6 灰色虚线 (8px dash, 4px gap)
- 填充: rgba(149,165,166,0.05) 极浅灰
- 标签: 左上角 "Comb #N"
- 圆角: 6px
八、文件结构
web/js/pages/plc.js ← PLC Debug + PLC Config (重构目标)
web/css/style.css ← PLC 相关 CSS (.chain-tabs, .plc-canvas-wrap, etc.)
web/js/i18n.js ← PLC 相关翻译 key
config/PLC/Reclose_logic.xml ← XML 配置文件 (数据源)