相机应用
1. 通讯介绍
目前机械臂和视觉通讯的有两种方式:
- 视觉和相机直接连接,一般采用的通讯方式都是TCP/IP。通过在程序里面需要拍照的地方插入运行脚本,这里面也有两种坐标偏移 ;
(1)机械臂直接获取需要的目标点位----绝对坐标;
(2)机械臂获取需要偏移的距离----相对坐标;
- 视觉通过PLC通过Modbus、Profinet等通讯方式进行连接, 拍照后由PLC把需要偏移的数值发给机械臂,根据相对位置进行X 、Y、RZ的偏移。
2. ARCS中相机通讯的方式
ARCS中可以使用socket通信来实现机器人与相机的TCP/IP通讯,在AUBO开发者官网中提供了相关示例

-- 示例相机使用TCP/IP方式进行通讯,进行拍照接收和发送数据
-- 导入socket库,用于实现网络通信功能
local socket = require("socket.core")
-- 相对于模板的旋转角度,初始化为0
offset_rz = 0
-- 相对于模板在x轴方向的偏移量,初始化为0
offset_x = 0
-- 相对于模板在y轴方向的偏移量,初始化为0
offset_y = 0
-- 创建一个TCP连接,用于与服务器进行通信
local tcp = socket.tcp()
-- 设置主机地址,该地址为要连接的服务器的IP地址
local host = '192.168.1.66'
-- 设置端口号,该端口号为服务器监听的端口
local port = '8000'
-- 定义拍照结果的标志位:识别成功为1,2,3,4,未识别为5
flag = "0"
-- 存储VisionMaster发送的数据,初始化为nil
str1 = nil
-- 自定义函数,用于将字符串按指定分隔符进行分割
-- 参数str:要分割的字符串
-- 参数delimiter:分隔符
function string.split(str , delimiter)
-- 检查输入的字符串是否为nil、空字符串或者分隔符是否为nil
if str == nil or str ==' ' or delimiter == nil then
-- 如果条件满足,返回nil
return nil
end
-- 用于存储分割后的结果
local result = {}
-- 使用gmatch函数按分隔符对字符串进行匹配分割
for match in (str..delimiter):gmatch("(.-)"..delimiter) do
-- 将匹配到的子字符串插入到结果表中
table.insert(result, match)
end
-- 返回分割后的结果表
return result
end
-- 定义拍照函数,用于控制相机拍照并处理返回结果
function photo1()
-- 尝试连接相机控制器
local clicon = tcp:connect(host,port)
-- 如果连接成功
if(clicon) then
-- 打印连接成功的消息
print('connect '..host..' ok!')
-- 如果连接失败
else
-- 打印连接错误的消息
print('connect error')
end
-- 定义拍照的触发字符
take_photo = "photo1"
-- 设置TCP连接的超时时间为2秒
tcp:settimeout(2)
-- 无限循环,直到有条件退出
while (true) do
-- 如果TCP连接的状态为关闭
if status == "closed" then
-- 打印服务器关闭的消息
print("server is closed!")
-- 退出循环
break
end
-- 如果str1不为nil
if str1 ~= nil then
-- 取str1的第一个字符赋值给flag
flag = string.sub(str1,1,1)
-- 将flag转换为数字类型
TPresult = tonumber(flag)
end
-- 如果flag不是1也不是5
if (flag ~= "1") and (flag ~= "5") then
-- 发送拍照的触发字符
tcp:send(take_photo)
-- 等待1秒
sleep(1)
-- 从TCP连接接收数据,读取到换行符(\n)为止,并存储到str1中
s, status, str1 = tcp:receive()
-- 打印接收到的数据
print("if str1: ", str1)
-- 如果flag是1(表示识别成功)
else
-- 使用逗号作为分隔符分割str1字符串
table1 = string.split(str1 ,",")
-- 将分割结果中的第二个元素转换为数字,并将单位从毫米转换为米
offset_x = tonumber(table1[2])/1000
-- 将分割结果中的第三个元素转换为数字,并将单位从毫米转换为米
offset_y = tonumber(table1[3])/1000
-- 将分割结果中的第四个元素转换为数字
offset_rz = tonumber(table1[4])
-- 打印offset_x的值
print("offset_x= ", offset_x)
-- 打印offset_y的值
print("offset_y= ", offset_y)
-- 打印offset_rz的值
print("offset_rz= ", offset_rz)
-- 退出循环
break
end
-- 等待0.2秒后继续循环
sleep(0.2)
end
-- 关闭TCP连接
tcp:close()
-- 重置标志位
falg = "0"
-- 重置接收到的数据
str1 = nil
end
Modbus主站通讯,通过plc做为数据的中转站,将数据发送给plc,或收到PLC发送的数据
Modbus通讯参考:29 ARCS Modbus使用说明 · AUBO 应用笔记
--示例modbodbus主站读写浮点数 function writeModbusFloat(value, lowSignalName, highSignalName) local word = math.float2words(value) local low_word = word[1] local high_word = word[2] modbusSetOutputSignal(highSignalName, high_word) modbusSetOutputSignal(lowSignalName, low_word) end function readModbusFloat(lowSignalName, highSignalName) return math.words2float(modbusGetSignalStatus(lowSignalName), modbusGetSignalStatus(highSignalName)) end --示例modbus主站读取寄存器地址Modbus_0,Modbus_14的值,并赋值给变量P1,注意浮点数的读写需要占用两个寄存器地址 P1 = readModbusFloat("Modbus_0", "Modbus_1") --示例modbus主站寄寄存器地址Modbus_0,Modbus_1写入-3.14,注意浮点数的读写需要占用两个寄存器地址 writeModbusFloat(-3.14, "Modbus_0", "Modbus_1")
使用从站通讯(modbus从站与Profinet从站都可用),通过plc做为数据的中转站,将数据发送给plc,或收到PLC发送的数据
--从站通用寄存器读写浮点数 function writeModbusFloat(value, low, high) local word= math.float2words(value) local high_word=word[1] local low_word=word[2] setInt16Register(high, high_word) setInt16Register(low, low_word) end function readModbusFloat(low, high) return math.words2float(getInt16Register(high), getInt16Register(low)) end --示例从站往通用寄存器地址300,301写入-3.14,注意浮点数的读写需要占用两个通用寄存器地址 writeModbusFloat(-3.14, 0, 1) --示例从站读取通用寄存器地址300,301的值,注意浮点数的读写需要占用两个通用寄存器地址 P1=readModbusFloat(0, 1)
3. 偏移实现
通过自定义坐标系实现偏移
通过方向-直达节点实现偏移
0.31分支版本相对于变量或路点实现偏移