改造铁路道口的项目,我前两年接过一个。甲方要求把原来靠人工摇把子的栏木改成自动控制系统,同时值班室要能看到现场状态,最好还能远程操作。当时我选的方案就是西门子 S7-200 PLC 加组态王。这套组合在小型工控项目里算是经典搭档:PLC 负责逻辑控制,组态王负责上位机监控,资料多、成本压得住,现场电工维护起来也不抓瞎。
整个项目从需求梳理、硬件选型、控制程序设计,到组态画面跑通、通信联调,前后折腾了一个多月,中间踩了不少坑,也总结了不少经验。这篇文章就把这个项目的完整设计过程复盘一遍,重点讲清楚几个关键问题:S7-200 这一侧的控制逻辑怎么搭才安全可靠,组态王的数据词典和画面动画怎么规划才不乱,以及 S7-200 与组态王之间通信中断、协议组件加载失败这类问题到底怎么排查。如果你也在做类似的道口控制、车站监测或者需要 PLC 加组态王联动的项目,这篇应该能帮你省下不少弯路。
1. 需求拆分:道口控制系统真正要管住的四件事
1.1 现场工况与原始痛点
先说项目背景。这是单线非电气化铁路上的一个有人看守道口,每天大概有二十来趟客货列车通过。改造前是纯人工操作:火车快要来的时候,值班员听到电话通知或者看到来车方向有信号,就跑去手动放下栏木,等列车通过后再手动抬起来。
听起来简单,但实际用起来问题不少。最典型的是夜间和恶劣天气,值班员视线差,经常出现栏木放下不及时的情况;再一个就是栏木放下后有没有真正压到位,没有反馈信号,光靠人眼判断不可靠;还有就是所有操作都没有记录,万一出了事情,事后没法追溯,责任划分也扯不清。
所以甲方提的要求很直接:第一,系统要能自动感应列车的到来,不用人盯着;第二,栏木升降要有位置反馈,系统要能确认动作真的完成了;第三,值班室要能看到整个道口的状态,操作要有记录;第四,出了故障要能报警,不能带病运行。
1.2 功能清单:不只是"自动落杆"这么简单
很多人一听"火车道口智能控制",第一反应就是"自动落杆"。真做起来才发现,核心其实是安全联锁,而不是简单的自动化动作。
我把整个系统的功能拆成四个层面:
第一层,列车接近检测。系统需要在列车到达道口之前足够远的地方就发现它,提前给出预告信号。这个"提前多少时间"很关键,直接决定后续声光报警和栏木动作的时序。
第二层,顺序联锁控制。整个动作链是固定的:先声光报警,再落杆,确认落杆到位,等待列车通过,确认列车已经离开,最后抬杆。每一步都要确认上一步已经完成,不能跳步,不能同时动作。
第三层,远程监控与记录。组态王要实时显示道口状态、栏木位置、信号灯情况,要能查历史动作记录和报警记录,还要支持远程手动干预。
第四层,故障安全与自诊断。传感器断线、栏木卡死、通信中断、超时未到位,这些异常都要能被检测到,并且系统要自动回到安全状态。什么算安全状态?对于道口来说,宁可让栏木放下来拦着路,也不能在列车即将通过的时候抬杆放行。
1.3 "智能"体现在哪里
说句实在话,这套系统里的"智能"不是那种高大上的人工智能,而是体现在三个地方:一是能自动识别列车行驶方向,避免反向的列车误触发;二是有一套完整的状态机,让系统知道当前处于哪个阶段、下一步该干什么;三是故障时能按安全优先的原则自动处理,而不是停在原地"死机"。
理清楚需求之后,后面的选型和程序设计就顺理成章了。
2. 硬件选型与 I/O 分配:这套系统的物理链路
2.1 控制器选型:为什么是 S7-200 CPU226
控制器选型这块,我先排除了两个方案。一个是用单片机自己搭控制板,成本确实低,但可靠性存疑,而且现场电工修不了,坏了只能寄回去返厂;另一个是用 S7-1200,性能更好,但价格上去了,组态王驱动也需要额外确认,对这么个小项目来说有点浪费。
最后定的是 S7-200 CPU226 AC/DC/RLY,具体型号 6ES7 216-2BD23-0XB8。选它的理由很直接:CPU226 自带 24 路数字量输入和 16 路数字量输出,对这个项目的 I/O 点数来说余量充足,不需要扩展模块;继电器输出型可以直接驱动中间继电器,控制 220V 的接触器、信号灯都很顺手;另外 S7-200 在国内存量很大,组态王对它的驱动支持非常成熟,老工程师基本都会用,现场维护门槛低。
2.2 传感器与执行机构:磁钢、限位开关、电动栏木
列车接近检测这块,我对比过轨道电路、光电对射和磁钢传感器三种方案。轨道电路最可靠,但工程量大,要在钢轨上做绝缘节,适合正规站点;光电对射容易受灰尘、树叶遮挡,铁路现场环境太脏,不建议用;磁钢传感器是铁路系统里最常用的方案,结构简单,装到钢轨内侧,车轮碾压时产生脉冲信号,抗干扰能力也不错,成本还低。
我的方案是在距道口约 400 米处装一组预告磁钢,在距道口约 100 米处装一组接近磁钢,道口另一侧装一组离开磁钢,每组由两只磁钢组成,间距 1 米,通过脉冲顺序判断列车行驶方向。列车速度按 60 到 80 公里每小时算,400 米距离对应的提前量大概 18 到 24 秒,足够完成声光报警和落杆动作。
执行机构采用标准的电动道口栏木,单相 220V 电机,带减速机构,两个限位开关分别检测栏木的上限位和下限位。信号灯是道口两侧的红绿警示灯,再加一套语音播报和红色闪光报警器。
2.3 I/O 分配表
数字量输入输出分配如下表:
| PLC 地址 | 信号名称 | 功能说明 | 信号类型 |
|---|---|---|---|
| I0.0 | 手动/自动选择开关 | 就地切换工作模式 | 开关量输入 |
| I0.1 | 预告磁钢 A1 | 列车经过预告点,产生脉冲 | 开关量输入 |
| I0.2 | 预告磁钢 A2 | 与 A1 配合判断方向 | 开关量输入 |
| I0.3 | 接近磁钢 B1 | 列车接近道口 | 开关量输入 |
| I0.4 | 接近磁钢 B2 | 与 B1 配合判断方向 | 开关量输入 |
| I0.5 | 离开磁钢 C1 | 列车驶离道口 | 开关量输入 |
| I0.6 | 离开磁钢 C2 | 与 C1 配合判断方向 | 开关量输入 |
| I0.7 | 栏木上限位 | 栏木完全抬起 | 开关量输入 |
| I1.0 | 栏木下限位 | 栏木完全放下 | 开关量输入 |
| I1.1 | 报警复位按钮 | 就地复位故障报警 | 开关量输入 |
| Q0.0 | 栏木电机正转 | 栏木放下 | 继电器输出 |
| Q0.1 | 栏木电机反转 | 栏木抬起 | 继电器输出 |
| Q0.2 | 红灯控制 | 道口禁行信号 | 继电器输出 |
| Q0.3 | 绿灯控制 | 道口通行信号 | 继电器输出 |
| Q0.4 | 语音播报 | 列车接近预告 | 继电器输出 |
| Q0.5 | 闪光报警器 | 故障及异常报警 | 继电器输出 |
| Q0.6 | 远程模式指示灯 | 指示组态王远程控制有效 | 继电器输出 |
2.4 电气接线几个容易忽视的点
接线这块有几个细节,虽然是老生常谈,但现场真的容易出事。
第一,PLC 的 24V 传感器电源容量有限。CPU226 自带的 24V 电源大概能提供几百毫安电流,带磁钢传感器和限位开关勉强够用,但如果传感器数量多,建议单独配一个 24V 开关电源,避免 PLC 自带电源过载。
第二,继电器输出点不能直接驱动接触器线圈。Q0.0 到 Q0.6 这些输出点接的是中间继电器线圈,再由中间继电器触点去控制接触器和信号灯,这样 PLC 输出点不会因为感性负载拉弧而损坏。
第三,信号线和动力线必须分开走线。磁钢传感器的信号线用屏蔽双绞线,屏蔽层单端接地,绝对不能和 220V 动力线穿同一根管,否则干扰问题会搞得你怀疑人生。
第四,道口栏木电机要有过载保护和热继电器。栏杆被汽车撞了或者卡住的时候,电机电流会飙升,没有保护的话很容易烧电机。
3. S7-200 侧的控制逻辑:状态机、联锁与故障安全设计
3.1 主状态机:待命、预告、落杆、锁定、抬杆
控制程序我没有按传统的"一段一段顺序逻辑"写,而是用一个状态字驱动的主状态机。状态字放在 VW0 里,程序每隔几十毫秒扫描一次当前状态,根据输入条件和联锁条件决定是否迁移到下一个状态。
整个系统的状态流转是:
S0 待命状态:栏木在上限位,绿灯亮,红灯熄灭。系统等待预告磁钢被触发。
S1 预告状态:预告磁钢检测到列车驶向道口,系统立即启动语音播报和红灯闪烁,同时开始落杆倒计时。这个阶段保持大约 3 秒,给行人车辆一个反应时间,然后才允许落杆动作。
S2 落杆状态:栏木电机正转,栏木放下。到达下限位后,电机停止,系统记录落杆到位时间。如果超出设定时间(比如 15 秒)还没到位,立即进入故障状态。
S3 锁定状态:栏木已经压到位,红灯常亮,道路完全封闭。系统等待接近磁钢触发,确认列车到达道口,再等待离开磁钢触发,确认列车已经驶离。
S4 抬杆状态:列车离开后延时 2 到 5 秒,绿灯亮,电机反转抬杆。到达上限位后停止,系统回到 S0 待命状态。
3.2 双磁钢方向判断逻辑
磁钢传感器方向判断是这套系统里比较关键的一个逻辑。单只磁钢只能检测"有车轮经过",判断不了方向,所以每组都要装两只,间距 1 米。当两只磁钢都触发时,根据触发的先后顺序确定列车的行驶方向。
比如预告点 A1 和 A2,如果 A1 先触发、A2 后触发,说明列车是驶向道口的;反过来 A2 先触发、A1 后触发,说明列车是离开道口方向的,就不应该触发落杆流程。我用边沿脉冲加中间状态位来实现这个判断,核心思路是:当 A1 的上升沿到来时,如果 A2 还没有动作,就设置一个"方向身份"位;等 A2 也触发后,根据方向位决定是否进入预告状态。
3.3 故障安全策略:宁可停着,不能乱动
这套系统在安全策略上有一条硬性原则:任何故障导致的默认结果,必须是让道口处于封闭状态,而不是开放状态。也就是说,栏木要么保持放下,要么在失电时自动放下,绝不允许因为 PLC 死机或者通信断了而出现"栏杆抬着、绿灯亮着"的情况。
具体做了四层防护:
第一层,机械断电落杆。选用的电动栏木带有弹簧储能机构,断电时弹簧自动把栏木压到水平位置。这样即使供电完全丢失,道口也是封闭的。
第二层,程序联锁。抬杆操作必须同时满足三个条件:列车已经离开、栏木没有故障、系统处于待命或者抬杆状态。任何条件不满足,抬杆输出都不会动作。
第三层,超时检测。落杆动作发出后,如果 15 秒内没有收到下限位信号,程序把故障字 VW4 的 BIT0 置位,系统进入故障封锁状态,组态王同时弹出报警。故障封锁状态下,除非人工复位,否则系统不会自动恢复。
第四层,传感器断线检测。磁钢传感器的 24V 信号线如果断了或者被老鼠咬了,输入点会一直保持高电平或者一直保持低电平。程序里用定时中断扫描这些输入点,如果一个周期内没有任何传感器变化,就认为传感器线路异常,报警提示维护。
3.4 关键程序片段示例
落杆联锁的关键逻辑用 STL 指令写出来大致是这样:
Network 1 预告触发:A1 先到、A2 后到,且系统处于待命状态 LD I0.1 // A1 上升沿 EU AN M0.0 // 方向标志未设置 AN M20.0 // 预告状态已激活 S M0.0, 1 // 设置方向标志:列车驶向道口 LD I0.2 // A2 触发 A M0.0 // 方向标志成立 AN M20.0 // 预告状态未激活 AN VW0, 0 // 比较当前状态为待命 S M20.0, 1 // 激活预告状态 Network 2 落杆超时检测 LD M20.1 // 落杆状态激活 TON T37, 150 // 15 秒定时器 LD T37 S M50.0, 1 // 故障字节 BIT0:落杆超时 Network 3 状态字写入,集中赋值 LD M20.0 MOVW 1, VW0 // 预告状态 LD M20.1 MOVW 2, VW0 // 落杆状态这里有个很重要的写法:状态字 VW0 的赋值一定要集中在程序最后统一处理,不要在中间每个网络里都写 MOVW 指令。我一开始图省事,在每个状态分支里都直接写 VW0,结果程序扫描周期内同一变量被多次改写,组态王读到的状态值经常跳变,画面上栏木的状态显示乱闪。
3.5 与组态王交互的变量区规划
PLC 和组态王之间的数据交互,全靠 V 区和 M 区。我在程序里做了一个统一规划,让组态王那边建变量的时候有据可查:
| 寄存器 | 数据类型 | 方向 | 说明 |
|---|---|---|---|
| VW0 | 整数 | PLC 到组态王 | 状态字:0 待命,1 预告,2 落杆,3 锁定,4 抬杆,50 故障封锁 |
| VW2 | 整数 | 组态王到 PLC | 远程控制字:BIT0 远程自动,BIT1 远程落杆,BIT2 远程抬杆,BIT3 报警复位 |
| VW4 | 整数 | PLC 到组态王 | 故障字:BIT0 落杆超时,BIT1 传感器异常,BIT2 通信丢失 |
| VW6 | 整数 | PLC 到组态王 | 列车通过次数累计 |
| VW100 | 整数 | PLC 到组态王 | 心跳计数,每秒加一,组态王用来判断通信是否正常 |
规划好这个变量区,后面组态王建数据词典就快多了,不会出现"这个数据该读哪个地址"的纠结。
4. 组态王上位机开发:数据词典、画面动画与报警记录
4.1 数据词典规划:先建变量,再画画面
组态王的开发流程,我的习惯永远是先在数据词典里把变量建好,再去做画面。不然画面画到一半发现变量没有,来回切窗口特别低效。
数据词典里对应 PLC 这侧的变量建了这些:
| 变量名 | 连接设备 | 寄存器 | 数据类型 | 初始值 |
|---|---|---|---|---|
| 当前状态 | S7-200 | VW0 | 整数 | 0 |
| 远程控制字 | S7-200 | VW2 | 整数 | 0 |
| 故障字 | S7-200 | VW4 | 整数 | 0 |
| 通过次数 | S7-200 | VW6 | 整数 | 0 |
| 心跳值 | S7-200 | VW100 | 整数 | 0 |
| 上次心跳值 | 内存变量 | 内存 | 整数 | 0 |
| 通信状态 | 内存变量 | 内存 | 整数 | 0 |
| 栏木角度 | 内存变量 | 内存 | 整数 | 90 |
这里有一个细节:栏木的角度不是 PLC 直接传过来的,因为系统拿的是限位开关信号,只有上限位和下限位两个点,中间过程的角度要么在组态王里用动画连接模拟,要么靠程序插值。我采用的是在组态王里写脚本,根据状态字和栏木限位反馈,在画面里用一定速度旋转栏木图案,这样的视觉效果比"开关量直接跳变"好很多。
4.2 主监控画面:静态构图与动画连接
主监控画面的布局,我按"上铁路、中道口、下控制"的逻辑来排。画面顶部画两条铁路线,标注预告磁钢、接近磁钢、离开磁钢的位置;中间是道口,画栏木、信号灯、行人通道;底部是状态栏,显示当前状态、通信状态、故障信息和通过次数。
动画连接是画面组态的重点。栏木图案设置旋转动画,连接"栏木角度"变量;红灯和绿灯设置填充闪烁动画,连接对应变量;磁钢位置设置数值显示,触发时变成红色。
需要说明的是,组态王里动画连接的表达式是用变量名直接写的,比如栏木旋转角度连接的是"\本站点\栏木角度",信号灯颜色连接的是"\本站点\红灯状态"。写脚本的时候,访问变量也要带上"\本站点"前缀,这个别漏了。
4.3 脚本:心跳检测、远程操作与报警弹窗
组态王的命令语言是这套上位机的"大脑"。我写了三段核心脚本:
第一段是心跳检测脚本,放在应用程序命令语言的"每秒钟执行"里:
\\本站点\上次心跳值 = \\本站点\心跳值; \\本站点\心跳值 = \\本站点\心跳值; if (\\本站点\心跳值 != \\本站点\上次心跳值) { \\本站点\通信状态 = 1; } else { \\本站点\通信状态 = 0; }这段脚本的原理很简单:PLC 里 VW100 每秒自动加一,组态王每次扫描时对比上一次的值,如果变了说明 PLC 还活着,如果连续多次不变就报通信故障。心跳检测比单纯靠通信状态位靠谱,因为组态王自带的状态有时不够灵敏。
第二段是远程操作脚本,放在按钮的事件里。远程落杆按钮按下时,先弹确认对话框,再把远程控制字 VW2 的 BIT1 置位:
if (\\本站点\当前状态 == 0 || \\本站点\当前状态 == 1) { \本站点\远程控制字 = \本站点\远程控制字 | 2; } else { ShowPicture("操作无效提示"); }第三段是报警处理,利用组态王的数据改变命令语言。当故障字 VW4 发生变化时,自动弹报警窗口并记录:
if (\\本站点\故障字 != 0) { \\本站点\报警触发 = 1; }4.4 报警与历史曲线配置
组态王的报警窗口控件要单独在一个画面里做。我把报警分成三类:通信报警、设备故障报警、状态异常报警。通信报警属于系统级,优先级别设为最高;设备故障报警包括落杆超时、传感器异常;状态异常报警包括列车滞留时间过长、手动模式下长时间无人操作等。
报警要记录的内容包括:报警时间、恢复时间、报警变量、报警描述、操作员姓名。这里提醒一下,组态王的报警记录默认只保存在内存里,重启之后就没有了,一定要配置报警数据库或者把报警事件写入历史记录的 ODBC 数据库,否则甲方让你调三个月前的记录,你什么都拿不出来。
历史曲线这块,我记录了栏木角度、状态字、通过次数这三个量。曲线控件配置时,一个常见问题是时间轴显示不对,注意组态王的系统时间要跟现场电脑同步,否则曲线上的时间点和实际动作时间差一大截,后期翻记录会很痛苦。
5. S7-200 与组态王的通信细节及"协议组件失败"排查
5.1 PPI 和以太网两种通信方案怎么选
S7-200 和组态王通信,最传统的方式是 PPI 串口通信,也就是用编程电缆把 PLC 的编程口和电脑的串口连起来。组态王设备配置时选择"PLC → 西门子 → S7-200 系列(PPI)",然后设置串口参数和 PLC 站地址(S7-200 默认站地址为 2)。
PPI 方式的优点是成本低,一条 USB-PPI 电缆几十块钱到一两百块钱不等,不用新增硬件;缺点是通信速率慢(通常 9.6kbps 或者 19.2kbps),抗干扰能力一般,而且如果用的是国产兼容电缆,驱动稳定性可能不理想。
如果项目现场干扰强、上位机离 PLC 比较远,我建议用以太网方案。给 S7-200 加一个 CP243-1 以太网模块,组态王设备配置时选择"PLC → 西门子 → S7-200 系列(TCP)",填上模块的 IP 地址就可以。以太网通信速率高,传输距离远,后期和维护下载程序也方便。
我在这个项目里一开始用的是 PPI 加国产 USB-PPI 电缆,后来通信时不时掉线,实在受不了,就加了一块 CP243-1 改用以太网,问题直接消失。
5.2 组态王通信参数的几个坑
如果你用的是 PPI 方案,有几个参数必须对上,否则就是明明线插着,通信就是不通:
第一,波特率。组态王侧的波特率必须和 S7-200 里 Micro/WIN 设置的 PPI 波特率一致。默认是 9.6kbps,但有些现场为了速度改成 19.2kbps,组态王那边没改,通信就会报错。
第二,PLC 站地址。组态王设备配置里的站地址要和 S7-200 系统块里的站地址一致,默认是 2,这个一般不会改,但改过的人就容易踩坑。
第三,串口号。USB-PPI 电缆插上之后,在设备管理器里看到的串口号可能是 COM3、COM5 甚至更高,组态王里必须选择正确的那个,选错了连不上。
第四,通信超时和重试次数。现场干扰较强的时候,可以把组态王的通信超时调大一点,比如默认 3 秒改成 5 秒,重试次数从默认 1 次改成 3 次,能减少偶发性的通信失败报警。
5.3 "创建协议组件失败"是怎么回事
组态王用久了的人大概率都遇到过"创建协议组件失败"这个报错。任务栏里弹出来一个对话框,说协议组件创建失败,然后整个设备驱动加载不了,画面上所有变量全部变成坏值。
我遇到过两次,一次是更换了上位机电脑之后,另一次是现场杀毒软件自动更新之后。排查思路是这样的:
第一个原因,杀毒软件拦截。组态王的驱动文件属于比较底层的进程间通信组件,很多杀毒软件会把它误判为可疑程序,拦截加载。处理方法是把组态王安装目录加入杀毒软件的信任列表,同时把组态王运行相关进程全部加入白名单。如果已经拦截了,先恢复被隔离的文件,再添加白名单。
第二个原因,安装路径问题。组态王别装在中文路径或者带空格的路径下,有些驱动组件对路径解析比较敏感,装在 D:\Program Files\ 这种路径下容易出幺蛾子。我后来的习惯是统一装在 D:\KingView 这种纯英文无空格的目录下。
第三个原因,安装不完整。非完整版组态王安装包可能缺少驱动组件,尤其是加密狗驱动和协议转换器组件。重装时选择完全安装,或者补装"设备驱动"和"网络通信"组件。
第四个原因,Windows 账户权限。组态王运行时最好右键选择"以管理员身份运行",特别是 Windows 7 和 Windows 10 系统,UAC 权限不够会导致协议组件写不了注册表,加载失败。
排查顺序我从实际经验来说应该是:先看杀毒软件隔离记录,再看安装路径,然后用管理员身份运行,最后考虑重装。按这个顺序能解决掉九成以上的问题。
5.4 通信稳定性优化
通信稳定这块,除了把 PPI 换成以太网之外,还有两个小技巧效果很好。
一是在组态王里做一个通信状态指示。就是前面说的心跳检测,把心跳值的变化情况显示在画面上,通信一断就能立刻看到,不用等变量变成坏值才发现。
二是在 PLC 里加一个"通信守护"逻辑。PLC 每收到组态王的任何写操作,就刷新一个定时器,如果长时间没有收到上位机指令,PLC 就判定通信中断,把系统切换到就地自动模式,同时点亮通信故障灯。这样哪怕组态王歇菜了,PLC 也能独立完成道口控制,不至于整个系统瘫痪。
6. 现场调试的抗干扰处理与两类典型故障复盘
6.1 一次性解决电磁干扰问题的三个措施
调试阶段最让人头疼的不是逻辑写不对,而是设备动作偶尔抽风。有一阵子,栏木电机一启动,磁钢传感器信号就乱跳,本来没有火车经过,系统却误报"列车接近",警报喇叭突然响起来,值班员都被吓过好几次。
排查到最后,干扰源是栏木电机的动力线,它在启动的瞬间产生很强的电磁脉冲,感应到了旁边的传感器信号线上。解决措施做了三个:
第一,信号线全部换成屏蔽双绞线,屏蔽层在 PLC 柜内单端接地,传感器侧不接地。这样能挡住大部分空间辐射干扰。
第二,信号线和动力线彻底分开敷设。现场原来的线缆都挤在同一个线槽里,后来把传感器信号线单独走了一根镀锌管,和动力线距离拉开到 500 毫米以上。
第三,PLC 电源进线加装滤波器,同时在电机接触器线圈两端并联 RC 吸收回路。电机启停的瞬间,接触器线圈会产生很高的反电动势,这个尖峰通过电源线窜进 PLC 供电回路,装上吸收回路之后好了很多。
6.2 调试验收时抓到的两个实际 bug
第一个 bug 是组态王画面上栏木角度显示乱跳。PLC 侧限位信号明明是好的,程序逻辑也看不出问题,但组态王读到的状态字 VW0 总是不稳定,一会显示"落杆中",一会显示"待命"。
后来用 Micro/WIN 在线监控 VW0 才发现,问题出在程序里有多个网络都对 VW0 做了赋值操作。我最初写状态字赋值时,在每个状态分支里都直接写 MOVW 指令,程序扫描到不同网络时,VW0 的值会被连续改写,组态王采样的时候正好抓到中间值,就出现了跳变。
修复方法很粗暴有效:把状态字赋值指令全部集中到程序末尾的同一个网络里,前面所有网络只操作中间状态位 M 地址,最后一个网络根据 M 地址统一计算 VW0 的值。这样每个扫描周期 VW0 只在固定位置被写一次,组态王读到的就是稳定值。
第二个 bug 是远程透传通道偶发失效。组态王上点"远程落杆"按钮,PLC 有时候响应,有时候不响应。排查过程比较绕,后来打开 Micro/WIN 的状态表,发现是 VW2 的高字节被程序里的一个网络覆盖了,因为远程控制字我用的是整数 VW2,但程序里有个地方用了 V3.0 这个位地址,正好和 VW2 的高字节重叠。
这个属于典型的地址重叠问题。VW2 和 VB3、V3.0 这类地址在物理上是同一个存储区域,程序里 VW2 的低字节是 VB2,高字节是 VB3。组态王通过 VW2 写入的数据,如果程序里不小心又操作了 VB3,两个逻辑就会互相干扰。修复办法是重新规划地址分配,把远程控制字用 VW100 区间内的地址,和状态字、故障字之间留出足够的间隔。
6.3 从单道口到多道口联网扩展
这套系统做完之后,甲方后来又提了一个新需求:沿线还有两个类似的道口,能不能都接到同一个值班室来监控。
扩展方案其实不难。每个道口保留一套 S7-200 和就地控制箱,上位机换成组态王网络版,通过以太网连接三个道口的 CP243-1 模块,每套 PLC 一个 IP 地址。组态王里建三个设备,分别对应三套 PLC,在数据词典里给每套 PLC 的变量加上不同的前缀(比如 1 号道口状态、2 号道口状态),画面里也能做多标签页切换。
这里要注意一个问题:组态王默认的驱动并发连接数有限制,网络版虽然支持多设备,但连接数多了之后驱动资源占用会上升,画面刷新率可能下降。连接三四个道口问题不大,如果道口数量超过十个,就得考虑改用服务器中间件做数据汇聚了。
6.4 项目收尾的个人体会
整个项目做完,我最深的体会是:这类控制系统的价值不在"自动"本身,而在于把"安全状态确认"做成了一个闭环。自动落杆很简单,难的是系统要知道自己什么时候该落杆、什么时候可以抬杆、出了问题怎么办,并且每一步都有据可查、有迹可循。
最后分享一个我自己摸索出来的小技巧:调试阶段一定要在组态王里做一个"模拟运行"画面。我在 PLC 程序里加了一个模拟模式切换点,用内部定时器代替磁钢传感器的输入信号,这样不用等着真的火车来,就能在白天把整个状态流程完整跑一遍。从待命到预告、落杆、锁定、抬杆,每一步的时序、报警、远程操作都能验证到位。等模拟运行没有任何问题了,再切换到现场模式,这样实际联调的时间能压缩一大半。这个做法放到其他类似的 PLC 上位机项目里也一样适用。