如果你问我哪个项目最适合工控新人完完整整做一遍,三轴码垛绝对排在我推荐列表的第一位。原因很直白:它不像PID那样一开始就跟你谈算法推导,也不像总线通讯那样上来就是报文和诊断,它本质上是一套“顺序控制”的标准容器,把传感器、执行器、步进逻辑、安全联锁、手动/自动切换这些日常调试每天都要碰的东西全装进去了。这次我直接用FactoryIO搭了一个立体仓库场景,配合博图V16(TIA Portal V16)编写PLC程序,把取料、搬运、码垛的完整流程跑通。整个过程非常适合刚接触PLC、想学运动控制,或者准备往自动化设备调试方向走的人照着练一遍。下面我把这次项目的完整思路、程序框架和踩坑点全部摊开讲。
1. 为什么三轴码垛是工控入门绕不开的练手项目
1.1 它把自动化最常遇见的几种控制一次练完
很多新人学PLC容易走进一个误区:今天看视频学计数器,明天找资料看定时器,后天又去翻通讯教程,结果单个指令都认识,一碰到整机设备就不知道代码从哪里写起。三轴码垛正好把这个问题治了——它逼着你去思考“整个流程怎么拆”。
以一个典型码垛动作为例:夹爪移动到取料位上方,Z轴下降,夹紧工件,Z轴上升,X/Y轴联动到货架目标格,Z轴下降,放松工件,Z轴上升回到安全高度。这中间涉及到数字量输入(传感器检测到位)、数字量输出(电机正反转、夹具电磁阀)、顺序控制(步号推进)、位置计量(行/列/层计数)、安全保护(限位、回原点顺序)。这套东西做完一遍,你对PLC程序的理解会从“会写指令”上升到“会写设备”。
更关键的是,码垛设备的控制逻辑在工厂里太常见了。上下料机、装配线搬运、立体仓库堆垛机、成品下线码垛,底层思路几乎都是这一套“取-搬-放”的状态切换。练好这一个项目,等于把后面可能遇到的很多设备逻辑提前打了个底。
1.2 仿真平台让“动手”这件事的门槛降了下来
没有真机是很多自学者最大的痛点,但FactoryIO刚好补上了这块拼图。它提供3D物理场景、传感器和执行器模型,你写好的PLC程序通过博图V16下载到仿真PLC里,就能直接驱动场景里的设备动起来。
这种“虚拟调试”的方式特别适合验证逻辑,因为你可以随时查看输入输出状态,可以反复回原点重新跑,不用心疼设备磨损,也不用担心撞机。工厂里的真实调试通常要等机械装配、电气接线全部完成才能开始,而在仿真环境里,你只需要把程序逻辑理顺,就能提前发现大部分控制问题。这也是为什么现在很多设备厂家在出厂前都会做数字样机联调。
对初学者来说,FactoryIO还有一层额外价值:它把抽象的“I/O映射”变成了看得见的东西。你在场景里看到挡块碰到了限位开关,再去PLC变量表里监控那个输入点,立刻就能理解物理信号是怎么进到程序里的。
2. 先把场景搭对:FactoryIO立体仓库的坐标规划与IO映射
2.1 场景布局与坐标系的建立
打开FactoryIO之后,第一件事不是急着写程序,而是把场景布局规划清楚。这一次的目标是立体仓库场景,我建议直接从场景库里选择带货架、流水线和码垛机械手的模板,再根据实际需求调整位置。
场景里几个关键元素要提前放好:
- 料台:来料工件固定的取料位置,机械手每次从同一个地方取货。
- 货架:目标存放位置,需要留出多行多列的格子,方便后面验证码垛计数。
- 机械手本体:三轴模组的基座位置,决定了X/Y/Z轴的行程方向。
- 托盘/传送带:如果要做连续循环,可以加一条出料线,码完一盘后把托盘送走。
布局确定之后,建立一个坐标系非常重要。我习惯把坐标系原点设在机械手回零位,也就是X/Y/Z三轴都在原点位置。然后定义取料点、货架基准格、各轴安全高度这几个关键坐标。这里不需要编程序,只需要在纸上或者表格里先算清楚,后面写坐标计算逻辑时直接用。
2.2 传感器、执行器和IO表怎么定
很多新手拿到项目第一件事就写梯形图,这是最容易被坑的做法。正确顺序是先画IO拓扑,再建变量表,最后才动手写程序。
这次项目我规划的IO清单大致如下:
| 类型 | 名称 | 说明 |
|---|---|---|
| 输入 | X原点 | X轴回零到位信号 |
| 输入 | X正限位/Y负限位 | X轴行程边界保护 |
| 输入 | Y原点 | Y轴回零到位信号 |
| 输入 | Y正限位/Y负限位 | Y轴行程边界保护 |
| 输入 | Z上极限/Z下极限 | Z轴升降边界保护 |
| 输入 | 夹爪夹紧检测 | 确认工件已夹住 |
| 输入 | 料台有料检测 | 确认当前取料位有工件 |
| 输入 | 托盘到位检测 | 确认码垛托盘就位 |
| 输出 | X正转/X反转 | X轴电机方向控制 |
| 输出 | Y正转/Y反转 | Y轴电机方向控制 |
| 输出 | Z上升/Z下降 | Z轴电机方向控制 |
| 输出 | 夹爪夹紧/夹爪松开 | 气动夹具电磁阀 |
| 输出 | 运行指示/报警指示 | 状态灯显示 |
在FactoryIO里面,每个传感器和执行器都会对应一个可配置的IO地址,最省事的做法是直接使用它默认的字节位,比如I0.0、Q0.0。后面在博图V16里建PLC变量表时,名称和FactoryIO里的元素保持一致,地址一一对应,这样联调时你盯着变量表就能知道哪个信号是从场景里来的。
2.3 建立坐标参数表,让码垛逻辑后面好写
三轴码垛最核心的就是坐标换算,所以场景搭好后先建立一张点位参数表。我这次用的是一组相对好算的参数,方便演示:
- 取料点:X=100,Y=0,Z=80(夹爪需要下降到的取料高度)
- 安全高度:Z=180(移动时Z轴必须抬到这个高度以上)
- 货架基准格:第一行第一列坐标 X=300,Y=200
- 箱宽方向间距:DX=80
- 箱深方向间距:DY=80
- 箱高方向间距:DZ=60
这张表建好之后,货架第m行第n列第k层的目标坐标就是:
- X目标 = 货架基准X + (m-1) * DX
- Y目标 = 货架基准Y + (n-1) * DY
- Z目标 = 货架基准Z + (k-1) * DZ
后面写程序时,它就是一个现成的计算公式。这样设计的好处是,真机调试时如果某列间距跟设计不一致,你只需要改一个参数,不用改整段逻辑。
3. 博图V16端的事前准备:PLC选型与通信通道
3.1 为什么这次选S7-1200
博图V16(TIA Portal V16)里可选的主流PLC有S7-1200和S7-1500两个系列。做三轴码垛仿真,S7-1200完全够用,像CPU 1214C DC/DC/DC这种型号,数字量输入输出点数足够覆盖这次项目的IO,而且它支持FB/FC、DB、SCL等现代编程方式,能写的程序结构比老式S7-200要清晰得多。
选S7-1200还有一个隐蔽优势:它的仿真支持在博图V16里非常成熟,和FactoryIO的驱动兼容性比较稳定。S7-1500当然也可以,但对于新手来说配置相对复杂,而且仿真资源占用更大,没必要。
有人会问为什么不用S7-200 SMART这种老平台。我只能说,S7-1200/1500的程序组织方式(OB、FB、FC、DB)更接近现代工业软件工程,而且FactoryIO的Siemens驱动面向的主要就是S7-1200/1500这条产品线。既然目标是练手,那就直接练一套能迁移到实际项目里的方法。
3.2 让PLCSIM和FactoryIO连上
博图V16写完程序后,要验证逻辑有两种方式:一种是用博图自带的S7-PLCSIM仿真PLC,另一种是接真机。在这个项目里必须用S7-PLCSIM,因为FactoryIO无法直接跟博图里的普通仿真环境通信,需要先把程序下载到PLCSIM里,再在FactoryIO端选择对应的Siemens驱动。
操作流程大概是:
- 在博图V16中建好工程,写完程序后点击“下载到设备”,目标选择S7-PLCSIM。
- 下载完成后把仿真PLC切到RUN状态。
- 打开FactoryIO,在顶部菜单选择外部PLC驱动,选Siemens S7-PLCSIM对应的项。
- 在驱动配置里确认连接参数,一般默认地址需要用S7-1200的PLC地址段。
- 启动FactoryIO仿真,此时场景里的传感器信号会通过驱动刷新到PLCSIM,PLC的输出也会回写到场景里。
这里最容易出的问题是PLCSIM和博图版本不一致,比如你装了V16的TIA Portal但PLCSIM是旧版组件,FactoryIO这边就会找不到连接。装博图V16时一定要把对应的S7-PLCSIM组件选上,版本不匹配时会出现各种莫名其妙连不上的现象。
3.3 下载程序前值得花两分钟检查的事
我每次下载前都会做一轮固定检查,这轮检查帮我省掉了大量联调时间:
- 检查PLC变量表的地址和FactoryIO里的实际地址是否一一对应,不要只看名字,要核对字节位。
- 检查程序里是否有OB1之外的组织块被遗漏,下载时确保所有相关块都包含在内。
- 检查PLCSIM是否处于可下载状态,如果之前跑过别的程序,建议先复位再下载。
- 检查驱动窗口是否显示“已连接”,FactoryIO连接成功后通常会有状态提示。
在虚拟机里装博图的情况稍微特殊一点,不少人会遇到PLC仿真和FactoryIO之间网络不通的问题,这个时候优先检查虚拟机的网络模式设置,根据驱动要求选择桥接或者NAT,一般都能解决。我不建议在这个环节死磕太久,如果发现网络不通,先看驱动类型,再看虚拟网卡配置,这两处是最常见的根因。
4. 码垛程序的核心骨架:步进状态机才是调试不乱的根
4.1 程序整体架构:三个模式先分开
三轴码垛程序如果全部堆在一起写,后期调试会非常痛苦。我这次采用的结构是:OB1作为主程序,只负责调用三个功能块,手动模式FB、回原点FB、自动模式FB,三个功能块之间通过模式选择互锁。
为什么必须分模式?
手动模式是调试和示教的基础。码垛位置怎么定出来的?不是程序算出来的,而是手动模式下用点动按钮把夹爪挪到目标位置,看坐标值记录下来,再填到参数表里。自动模式跑不动的时候,也要切回手动模式把轴挪到安全位置。
自动模式是正常运行时的逻辑,负责自动取料、搬运、码垛循环。
回原点是启动自动运行前的必备动作。设备上电后你不知道三轴在什么位置,贸然跑自动模式很容易撞货架,必须先回一次原点建立坐标基准。
三个模式不能同时生效,所以我做了一个模式字变量,比如0=停止,1=手动,2=回原点,3=自动,程序里先判断当前模式,再去执行对应逻辑。
4.2 自动模式步进状态机设计
自动模式的核心就是“步进状态机”。我会用一个整型变量叫step,每一个step代表一个动作阶段,条件满足就切换。
这次项目的步号设计大致如下:
| 步号 | 动作 | 切换条件 |
|---|---|---|
| 0 | 等待启动 | 启动按钮 & 托盘到位 & 料台有料 |
| 10 | 移动到取料点上方 | 到位确认 |
| 20 | Z轴下降到取料高度 | 取料高度到位 |
| 30 | 夹爪夹紧并延时 | 夹紧检测到位 |
| 40 | Z轴上升到安全高度 | 安全高度到位 |
| 50 | 移动到目标货位上方 | 目标坐标到位 |
| 60 | Z轴下降到放料高度 | 放料高度到位 |
| 70 | 夹爪松开并延时 | 松开检测到位 |
| 80 | Z轴上升到安全高度 | 安全高度到位 |
| 90 | 更新码垛计数,判断下一格 | 计数正常更新 |
| 100 | 判断是否继续循环或满盘停止 | 条件分支判断 |
每个step内部其实只有三件事:给对应输出发指令、等反馈条件、条件满足就跳下一个step。这种写法的最大好处是逻辑完全可视,程序跑到哪一步,你打开监控表看一眼step的值就知道。真机调试时如果设备停住不动,第一件事永远是看step停在哪个值,再分析为什么这个step的切换条件没满足。
下面是一个简化版的SCL片段,展示步进状态机的写法:
CASE step OF 20: // 移动到取料点上方 IF xPosOK AND yPosOK THEN step := 20; END_IF; 20: // Z轴下降到取料高度 zDown := TRUE; IF zAtPickPos THEN step := 30; END_IF; 30: // 夹紧工件 gripperClose := TRUE; IF gripperClamped THEN step := 40; END_IF; 40: // 抬升到安全高度 zUp := TRUE; IF zAtSafeHeight THEN step := 50; END_IF; END_CASE;注意这里有个细节:切换条件不要用时间,要用传感器反馈。虽然时间触发在仿真里看起来很顺,但真机上一旦工件卡住或者气压不足,你的程序还按时间继续往下走,就会出大问题。步进状态机一定要建立在“动作完成确认”的基础上。
4.3 可复用的动作封装思路
项目做完后你会发现,三轴码垛的过程本质上就是“移动到某点→爪子动作→移动到某点→爪子动作”的循环。所以进阶做法是把“取料”和“放料”封装成两个FB(函数块),每个FB内部又是一个小的子状态机。
比如取料FB的输入参数:取料点X坐标、取料点Y坐标、取料高度、安全高度、超时时间。外部调用时只需要填参数,不需要关心它内部是下降、夹紧还是抬升。这样的话,自动模式的状态机就只剩下“选目标位置→调用取料FB→调用放料FB→更新计数”,代码结构会变得很干净。
这个封装思维非常重要。以后你换一台不同的码垛设备,只要IO映射和坐标参数变了,FB内部逻辑几乎不用改,只改调用参数就能适配。
5. 三个轴各司其职:运行控制、限位保护与码垛坐标计算
5.1 轴运动控制的两种主流做法
三轴码垛的轴运动控制在写代码时有两条路线。
第一种是直接数字量控制:输出正转、反转信号,靠传感器或者坐标信号停止。这适合简单搬运、结构精度要求不高的场景,也是仿真里最容易实现的方式。本次项目就是这种做法,在FactoryIO里电机正转、反转就像是开关量,真正停止靠的是程序里判断“目标到达”的标志位。
第二种是用运动控制工艺对象:在博图里组态轴,使用Motion Control指令(如MC_MoveAbsolute、MC_MoveRelative)进行定位,带加减速、方向、超时报警。这种方式对应真实工程项目里的伺服/步进控制系统,定位精度高、运行平稳,但配置也复杂得多。
对仿真项目来说,先用第一种方式把逻辑跑通,再尝试把某一个轴改成运动控制对象,会让学习曲线平滑很多。我见过很多人一上来就搞伺服组态,结果轴配置、报文、闭环参数一起涌过来,最后连基础码垛逻辑都没跑顺。建议分阶段走,先逻辑后运动控制。
5.2 三轴坐标计算和码垛计数
码垛坐标计算是整个程序里最需要动脑的一部分,也是体现程序通用性的地方。
我在前面提到了坐标参数表,具体计算逻辑如下:
- 目标位置 = 货架基准格 + 行偏移 + 列偏移 + 层偏移。
- 每放完一件货,行数+1,当一行放满,行数归1,列数+1。
- 当一层放满,列数归1,层数+1。
- 当最高层也放满,输出满盘信号,停止自动循环。
在SCL里可以这么写:
xTarget := rackBaseX + (row - 1) * dx; yTarget := rackBaseY + (col - 1) * dy; zTarget := rackBaseZ + (layer - 1) * dz;计算的核心是一开始那张坐标参数表。参数表里有一个值特别容易写错,就是行距/列距的方向。如果现场设备的轴方向和场景坐标系方向相反,计算出来的位置会直接飞出边界。所以我在参数表里会专门标注“X正方向对应场景里的哪个方向”,联调前先手动点动确认方向,再填参数。
5.3 码垛计数与换层策略
计数逻辑并不复杂,但要注意“什么时候更新计数”。常见错误是程序刚进放料步就计数,结果放料失败也照样+1。正确做法是:计数更新的时机放在放料完成后、判定“夹爪松开到位”之后。
这样即使放料失败,程序可以停下来报警,而不是继续往下一格放,导致后面全部错位。
换层策略也要考虑是“顺序换层”还是“先满一层再换层”。我这次采用的是先铺满一层再升层,也就是常规的逐层码垛。如果你要写交叠式码垛(第二层压在第一层缝隙上),坐标计算公式就会变成“奇偶层使用不同的基准X偏移”,这个可以在练习完基础码垛后自己试着加。
5.4 安全互锁,这是必须写进程序里的
很多新手程序能跑通就觉得自己会了,但真机调试最怕的就是没有安全逻辑。这次仿真项目里我特意加了几个互锁,强烈建议你也保留:
- 三轴不同时动作:码垛动作是分时执行的,程序里通过状态机天然保证同一时刻只有一个轴在动。手动模式下则需要额外加互锁,禁止X和Z同时输出,防止夹爪撞到货架。
- 限位信号硬保护:每个轴的正反转输出除了由状态机决定,还要串联限位触点。也就是即使逻辑出错了,一旦轴碰到限位,输出也必须被切断。
- 回原点顺序:先Z抬升到最高,再Y回原点,最后X回原点。这个顺序的核心目的,是避免回原点时夹爪处在低位撞上货架或者料台。在FactoryIO里同样要遵守,因为物理碰撞也是仿真的一部分。
限位保护的思路可以简单理解成:程序正常运行时靠坐标计算来停止,程序异常时靠限位开关来兜底。两者缺一不可,少了限位保护,调试中分分钟把机械结构干报废。
6. 联调现场最容易翻车的几个环节与排查方式
6.1 连不上PLCSIM,先按这个顺序查
我这次联调就栽过一次跟头:FactoryIO里选了Siemens驱动,但一直提示连不上。排查顺序是我自认为最有价值的经验:
- 查版本:TIA Portal V16必须配V16的S7-PLCSIM,版本跨了基本连不上。
- 查PLCSIM状态:确认程序已经下载进去,且PLC处于RUN状态,RUN灯亮着。
- 查驱动配置:FactoryIO里的连接地址要和PLCSIM的地址对应,地址填错会一直握手失败。
- 查虚拟机网络:如果博图装在虚拟机里,检查网卡模式,必要时改用桥接模式。
正常情况下按这个顺序走能解决九成以上的连接问题。不要一开始就去重装软件,先确认自己卡在哪一层。
6.2 步号不推进或者乱跳,先怀疑反馈条件
联调时最常见的现象是:程序启动后没有任何动作,或者动作做了一半就停住。我建议先做两步操作:打开博图的变量监控表,同时把step变量加进去;再看FactoryIO当前的传感器状态。
很多时候是传感器位置没被物理触发。FactoryIO里传感器的作用范围和位置是可以在场景里调整的,如果感应块离传感器太远,信号就永远为0,step等不到切换条件,自然卡住。
另一种情况是条件给错了,比如我在调试时曾经把“Z轴在取料高度”的反馈接到“Z轴在安全高度”上,结果Z轴还没降到位就提前执行夹紧,夹了个空气。解决办法是把每个反馈信号的含义写清楚,变量监控表里挨个核对实际触发的传感器。
6.3 回原点失灵,多半是顺序和信号抖动问题
回原点逻辑看起来简单,实际坑也不少。有一种非常典型的故障:按下回原点按钮,三个轴同时往原点跑,结果在FactoryIO里看到机械手撞到货架。原因就在于没有先抬Z轴。
回原点的标准顺序必须是:Z先升到最高位,Y回到原点,X回到原点。因为Y/X回原点时Z轴如果处于低位,机械手会扫过货架区域直接撞上去。
另外,原点开关的信号抖动也很值得注意。在FactoryIO里传感器信号切换是瞬间的,但如果以后接真机,机械抖动会产生连续脉冲,程序里最好对原点信号做滤波或者连续确认若干周期再判定到位,这一点仿真里看不见,但真机一定会遇到。
6.4 夹具夹不住、放不下,先验证IO输出和到位反馈
夹具逻辑看起来简单,但联调时最容易出两种问题。
一种是夹爪已经收到输出命令,但FactoryIO里没有动作。这种基本就是地址映射反了,输出点没写到位。另一种是夹爪动了但工件没被夹住,或者夹爪松开了但工件没放下来,这种一般是夹持确认时间太短,我给夹紧和松开都加了200毫秒左右的延时,并等待夹紧/松开检测信号,而不是输出命令一给就立刻切换下一步。
气动夹爪在真机里还有气压不够、掉件等额外问题,而这些在仿真里体现不出来,所以写程序时预留好延时和反馈确认,能最大程度降低后续迁移到真机时的改动量。
6.5 一张联调排错参考表
为了方便你快速定位问题,我把这次遇到的主要问题整理成一张表:
| 现象 | 可能原因 | 排查方法 |
|---|---|---|
| 连接失败 | 版本不匹配、驱动地址错 | 核对TIA/PLCSIM版本,检查FactoryIO驱动参数 |
| 场景不动 | 程序没下载、PLC没RUN | 看PLCSIM状态,看变量表输出是否变化 |
| 只有单轴动 | 状态机停在某一步 | 查看step值,核对卡住的切换条件 |
| 位置偏差大 | 坐标参数填错、单位不一致 | 核对参数表,检查毫米/米换算 |
| 夹具无动作 | IO映射错误 | 手动强制输出,反向验证地址 |
| 工件掉落 | 夹持确认不足 | 增加延时,等待夹紧反馈信号 |
| 撞货架 | 回原点顺序错、Z未抬升 | 先升Z再回Y/X,限位保护串联 |
这张表不是万能的,但能帮你把大多数“看着像程序问题”的故障缩小到具体范围,剩下的再通过变量监控细化。
7. 一点经验之谈:从仿真到真机的差距在哪里
7.1 仿真帮你练的是逻辑,不是工艺
三轴码垛仿真做完,我最大的体会是:FactoryIO帮你解决的是控制逻辑验证问题,但它不会帮你解决机械和工艺问题。
仿真里没有惯性,电机正转指令给出后,坐标瞬间到达目标位置;真机则需要考虑加减速时间、刹车距离、超程误差。仿真里传感器信号是理想的,到了真机会有抖动、有延迟、有安装位置偏差。仿真里工件质量是不变的,真机码垛可能需要考虑重心偏移、层间压伤、节拍时间。
所以做完这个项目,你应该把收获定位在“程序架构”和“调试方法”上,而不是觉得这也算完整复刻了真机。真正去现场调试时你会发现,程序逻辑写得好只是基础,和机械配合、跟电工对点、跟工艺人员讨论动作节拍,这些才是调试工作的大头。
7.2 示教加偏移的思想一定要提前养好
这次程序里我用了直接厘米级坐标计算,但在真实项目里,码垛位置往往不是纯计算出来的,而是先通过手动示教确定几个关键点位,然后用偏移量公式去推算其他点位。
比如,手动示教出第一行第一列的货位坐标,然后通过箱宽、箱深、箱高算出整面货架所有格子的坐标。这样即使现场基准点有误差,只需要重新示教一次基准坐标,就能让整条逻辑重新生效。这个设计思路在仿真项目里用手动模式按钮就能模拟,强烈建议你在写完自动模式之后再回过来练一遍手动示教法。
7.3 立体仓库项目的下一步可以往哪走
三轴码垛只是立体仓库的一个运动核心,再往后你看这类系统,通常还会带这些外围设备:供料传送带、AGV小车、机器视觉定位、MES/WMS系统下发任务。每一块都是在三轴运动的基础上叠加的新模块。
比如你可以试着给场景加上视觉识别:通过相机识别箱子上的二维码或者颜色标签,PLC根据识别结果决定箱子放到哪个货位。也可以试着加上任务队列:程序启动时先接收一批目标货位数据,然后按顺序完成取放。甚至可以写一个“动态码垛配方”,货位间距根据工件型号自动切换。
这些扩展方向的核心控制逻辑,仍然是你在这个三轴码垛项目里练出来的状态机加坐标换算。骨架不变,往上加功能只是时间问题。这也是我为什么一直强调,第一个项目一定要把状态机扎扎实实吃透,它后面能带动的东西比你想的要多得多。
最后说一个我自己比较受用的习惯:每次在仿真平台上练项目,都会专门留一张纸画步号流程图,把每个步号的触发条件、输出状态、异常分支写清楚。没画清楚之前不写代码,画清楚之后写SCL或者梯形图都快很多。三轴码垛这个项目做完,这套方法基本就长在身上了,后面再去做搬运设备、装配设备,你会发现底层的逻辑都是相通的。