教育场景中的自动化分拣系统!基于大象机器人UltraArm P340机械臂和传送带的实现

引言

今天我们将展示一个高度自动化的模拟场景,展示多个机械臂与传送带协同工作的高效分拣系统。在这个场景中,机械臂通过视觉识别技术对物体进行分类,并通过精确的机械操作将它们放置在指定的位置。这一系统不仅提高了分拣的速度和准确性,还展示了现代自动化技术在工业领域的巨大潜力。无论是处理大量的日常物品,还是在复杂的工业流程中应用,这种自动化分拣解决方案都体现出了极高的灵活性和效率。

场景描述

在这个高度自动化的分拣场景中,主要设备包括两个机械臂和一条800mm的传送带。右侧的上料机器人负责识别和抓取标记物,并将它们放置到传送带上。传送带将标记物运输到左侧的下料机器人工作范围内。下料机器人则根据分类要求识别标记物,并将它们有序地放置在指定区域。

放个视频gif

接下来我们简要介绍产品的相关参数

产品

NAME

QUANTITY

UltraArm P340

2

USB Camera 2D

2

Conveyor belt

1

Conveyor Controller

1

Vertical suction pump

2

Quick-change servos

2

Kit base Plate

1

列表中是几个主要的产品。

UltraArm P340

ultraArm 是4自由度的机械臂,全身采用经典金属设计结构,本体占用体积只有A4纸张的一半,搭载高性能的步进电机,能够实现±0.1mm重复定位精度和高稳定性。

高性能的步进电机能够进行7*24的工作时长,且保持性能良好,也是比较适合高度自动化这一场景的选择。

Conveyor belt

这个也是步进电机来进行驱动的传送带,需要用到Arduino mega 2560开发板来作为控制器,给物体提供运输的一个设备。

USB Camera 2D

摄像头作为机器视觉必不可少的一部分,是获取标记物的重要设备,usb 摄像头,能够提供画面,通过各种机器视觉的算法来确定标记物的具体位置,坐标来反馈给机械臂去执行抓取。

工作原理

整个项目的被分为以下几个功能模块,以实现整个自动化分拣场景。

我们具体看看各个功能模块的功能是如何在代码当中实现的。

Visual recognition module

本次项目用的标记物是Aruco码,是一种广泛使用的二进制方形标记,主要用于增强现实和机器人导航等场景中,Aruco码的设计使得它们在图像中易于检测和识别,有以下几个特点。

1易于检测和识别:Aruco码的设计使得它们在图像中易于检测和识别

2 唯一性和抗误识别:每个Aruco码都有一个唯一的ID,具有一定的纠错能力

3姿态估计:Aruco码不仅可以用于识别和定位,还可以用于估计相机相对于标记的姿态(位置和方向)。

4开源和易于使用:OpenCV库提供了对Aruco码的完整支持,包括生成、检测和解码。

5灵活性和多样性:Aruco码可以生成各种尺寸和复杂度的码,以适应不同的应用需求。

6低成本:生成和使用Aruco码的成本非常低。它们可以简单地打印在纸上,或者制作在物体表面,不需要昂贵的硬件设备。

#导入库
import cv2.aruco as aruco#加载字典
aruco_dict = aruco.Dictionary_get(aruco.DICT_6X6_250)
parameters = aruco.DetectorParameters_create()#灰度处理并且识别
gray = cv.cvtColor(img, cv.COLOR_BGR2GRAY)   corners, ids, rejectImaPoint = cv.aruco.detectMarkers(gray, self.aruco_dict, parameters=self.aruco_params)#检测Aruco码
if len(corners) > 0:if ids is not None:id = int(ids[0][0])

姿态估计,确定Aruco码的姿态位置,对于抓取是非常重要的,为控制算法提供反馈,调整机器人的动作。姿态估计后再进行数据的转换和补偿,计算和调整角度最终反馈位置和姿态角度。

#姿态估计
ret = cv.aruco.estimatePoseSingleMarkers(corners, 0.022, self.camera_matrix, self.dist_coeffs
)
(rvec, tvec) = (ret[0], ret[1])#位置计算
xyz = tvec[0, 0, :]
xyz = [round(xyz[0]*1000 + self.pump_x, 2), round(xyz[1]*1000 + self.pump_y, 2), round(xyz[2]*1000, 2)]#旋转向量处理
try:rvec = np.reshape(rvec, (3, 1))
except ValueError as e:print("reshape错误:", e)print("rvec1=", rvec)rvec = np.array([[[-2.86279729, -0.00687534, -0.05316529]]])print("rvec2=", rvec)#计算旋转矩阵和欧拉角
rotation_matrix, _ = cv.Rodrigues(rvec)
euler_angles = cv.RQDecomp3x3(rotation_matrix)[0]
yaw_angle = int(euler_angles[2])#返回结果
for i in range(rvec.shape[0]):cv.aruco.drawDetectedMarkers(img, corners, ids)if num < 100:num += 1elif num == 100:cv.destroyAllWindows()print("final_x:", xyz[0])print("final_y:", xyz[1])print("final_yaw_angle=", -yaw_angle)return xyz[0], xyz[1], -yaw_angle, id

在此之前需要进行手眼标定,标定的目前是确定相机与机器人末端执行器的相对位置和姿态关系。

Robotic arm control module

ultraArm有一个python的控制库pymycobot,安装好环境之后即可使用,一下是简单控制的使用

from pymycobot.ultraArm import ultraArm#创建实例,com为机械臂的串口号
ua = ultraArm(COM)# 角度控制
ua.send_angles([angle_list],speed)
# 坐标控制mode,控制走直线还是非直线
ua.send_coords([coords_list),speed,mode)#吸泵的使用1-open ;0-close
def pub_pump(self, flag):if flag:self.ua.set_gpio_state(0)else:self.ua.set_gpio_state(1)
ua.pub_pump(state)

机械臂的运动控制很简单,只需要简单的调用就好了,但是需要注意的是,在机械臂运动的过程中需要设计运动轨迹,不能撞到一些物体,以及根据获取到标记吗的坐标后的点位,比如说起始点位,待抓取点位等等。

Conveyor control module

传送带配备的步进电机通常需要通过微控制器(Arduino Mega 2560)来进行输出控制,mega为此提供了足够的I/O引脚和处理能力,能够精确控制步进电机的步进和方向,从而实现传送带的启动、停止、速度调节和方向控制。

#初始化设置
self.serial = serial.Serial(port, baudrate, timeout=1)#写入命令
def write_command(self, command):self.serial.write(command.encode())#设置传送带的方向
def set_direction(self, direction):command = f'DIR {direction}\n'self.write_command(command)#设置速度
def set_speed(self, speed):command = f'SPD {speed}\n'self.write_command(command)#启动和停止
def start(self):self.write_command('START\n')def stop(self):self.write_command('STOP\n')

Data processing and communication module

在这个自动化分拣系统项目中,数据处理和通信是关键部分,为了让他们互相知道彼此在干什么,将整体连贯起来,只要有一个地方出错就会停止程序。

第一步-上料机器人的视觉检测,如果发现检测的物体不复合要求(摆满),将不会执行后续的程序。

第二步-上下料机器人协作好,上料机器人先进行拆码垛工作,搬运到传送带上。

第三步-传送带将物体运输到下料机器人的摄像头识别范围和机械臂工作半径内。

第四步-下料机器人将物体的姿态进行识别,下料机器人得到反馈的姿态进行调整后抓去物体放置在指定区域。第五步-每当完成六次物体的抓取后,会重新再进行一次上料机器人的视觉检测,如果在此期间上料机器人的物体有所变化会导致抓取失败。(这是逻辑上的设定,可自行更改)

  while robot2.count<18:data=obj.detect()while len(data)<6:print("二维码检测数目不对,请确保二维码在相机范围内并且能正确识别")time.sleep(1)data=obj.detect()          for i in range(len(data)):robot.move(data[i][2],data[i][1]) conveyer.open_conveyor(100)time.sleep(5.2)conveyer.close_conveyor()for i in range(3):try:print("i=",i)                                pose=cam.detect()if pose is not None: breakexcept Exception as e:if i==2:message()                temp=obj.exception_handling()robot.Special_handling(temp[0][2],temp[0][1],temp[0][3])conveyer.open_conveyor(100)time.sleep(5.2)conveyer.close_conveyor()id=robot2.move(pose[0],pose[1],pose[2],pose[3])                   robot2.judge(id)  

总结

本项目展示了一个基于UltraArm P340机械臂和传送带的自动化分拣系统,主要应用于教育场景,旨在教学和演示自动化分拣技术。系统结合计算机视觉、步进电机控制、手眼标定和机械臂运动控制,实现了高效的自动化分拣流程。

如果你觉得该项目有什么可以改进的地方欢迎在下方留下评论,你的留言和支持是对我们更新最大的鼓励。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/39826.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

PTrade怎么获取KDJ随机指标?想做量化策略怎么申请PTrade量化软件?

get_KDJ - 随机指标 get_KDJ(high, low, close, n9, m13, m23) 使用场景 该函数仅在回测、交易模块可用 接口说明 获取随机指标KDJ指标的计算结果 PTrade是恒生公司开发的一款专业量化软件&#xff0c;部分合作券商可提供&#xff0c;↑↑↑&#xff01; 参数 high&…

什么是分库分表?它有哪些实现类型?

假如你正在使用关系型数据库开发一款健康类系统。业务发展很好&#xff0c;系统有很多活跃的新老用户&#xff0c;这些用户会和平台的医生团队进行交互&#xff0c;每天可能会生成数万甚至数十万级别的业务数据。这样的话&#xff0c;随着数据量越来越大&#xff0c;系统中的某…

被⽹络罪犯利⽤的5⼤ChatGPT越狱提⽰

⾃ChatGPT发布的近18个月以来&#xff0c;⽹络罪犯们已经能够利⽤⽣成式AI进⾏攻击。OpenAI在其内容政策中制定了限制措施&#xff0c;以阻⽌⽣成恶意内容。作为回应&#xff0c;攻击者们创建了⾃⼰的⽣成式AI平台&#xff0c;如 WormGPT和FraudGPT&#xff0c;并且他们还分享了…

IP地址定位中多源数据融合的应用

IP地址定位如今在诸如网络安全、地理信息服务、智能交通等领域发挥着关键作用。然而&#xff0c;传统的基于单一数据源&#xff08;如IP数据库&#xff09;的定位方法往往存在精度有限、可靠性不足等问题。多源数据融合技术的出现为解决这些问题提供了新的思路和方法。今天我们…

石墨烯分散液制备方法众多 应用领域广泛

石墨烯分散液制备方法众多 应用领域广泛 石墨烯分散液指将石墨烯纳米片均匀分散在特定溶剂中制成的溶液。石墨烯分散液具有化学稳定性好、生物相容性好、热稳定性好等优势&#xff0c;未来有望在涂料、纤维制品、电池制造、油墨等领域获得广泛应用。 石墨烯分散液以石墨…

绝区零卡顿严重、延迟高的解决方法提前看

绝区零这款游戏背后是一个错综复杂的架空世界&#xff0c;仿佛一幅波澜壮阔的史诗画卷缓缓展开。在这个世界中&#xff0c;神秘莫测的“空洞”灾害如影随形&#xff0c;给大地带来了无尽的破坏和混沌。经过米哈游团队的精心雕琢&#xff0c;无论是画面UI的细腻呈现&#xff0c;…

灌区量测水管理系统是如何实现灌区节水?

随着全球水资源日益紧张&#xff0c;节水已成为农业生产中不可忽视的一环。在灌区管理中&#xff0c;量测水管理系统以其精准的数据监测和科学的灌溉管理&#xff0c;为实现灌区节水提供了强有力的技术支持。 灌区量测水管理系统是一套集成了自动化监测、数据传输、数据分析和…

Springboot交流论坛网站00304

Springboot交流论坛网站 摘要 随着信息技术在管理上越来越深入而广泛的应用&#xff0c;管理信息系统的实施在技术上已逐步成熟。本文介绍了交流论坛网站的开发全过程。通过分析交流论坛网站管理的不足&#xff0c;创建了一个计算机管理交流论坛网站的方案。文章介绍了交流论坛…

elementui中table组件合并行(看就懂)

做一个动态合并的table表格, 如下图 1.首先定义需要合并的字段及合并后的对象 data(){return {mergeFields: [name, amount3],mergeObj: {}} }2.分配合并项函数, data为数据源 //获取合并序号getSpanArr(data []) {this.mergeFields.forEach(key > {// 用来记录合并行的起…

为什么我感觉 C 语言在 Linux 下执行效率比 Windows 快得多?

在开始前刚好我有一些资料&#xff0c;是我根据网友给的问题精心整理了一份「Linux的资料从专业入门到高级教程」&#xff0c; 点个关注在评论区回复“888”之后私信回复“888”&#xff0c;全部无偿共享给大家&#xff01;&#xff01;&#xff01;Windows的终端或者叫控制台…

时间12小时和24时转换方法

24小时时间转为12小时制 function convertTo12Hour(time24h){let [hours, minutes] time24h.split(:);let modifier 上午;if (parseInt(hours, 10) > 12) {modifier 下午;hours (parseInt(hours, 10) - 12).toString();}if (parseInt(hours, 10) 12) {modifier 下午;}…

新手入门:无服务器函数和FaaS简介

无服务器&#xff08;Serverless&#xff09;架构的价值在于其成本效益、弹性和扩展性、简化的开发和部署流程、高可用性和可靠性以及使开发者能够专注于业务逻辑。通过自动化资源调配和按需计费&#xff0c;无服务器架构能够降低成本并适应流量变化&#xff0c;同时简化开发流…

《昇思25天学习打卡营第01天|sun65535》

开始 昇思25天打卡训练营&#xff0c;让我第一次了解了华为昇思的平台&#xff0c;之前也有自己本地使用4060训练了一些“小模型”&#xff0c;但是都是比较皮毛的知识&#xff0c;只是根据教程去搭建。很少了解到具体的过程。昇思25天打卡训练营给了一个比较全面的训练课程。…

大数据基础知识【大数据导论】

各位大佬好 &#xff0c;这里是阿川的博客&#xff0c;祝您变得更强 个人主页&#xff1a;在线OJ的阿川 大佬的支持和鼓励&#xff0c;将是我成长路上最大的动力 阿川水平有限&#xff0c;如有错误&#xff0c;欢迎大佬指正 大数据基础知识前 必看 【大数据导论】—大数据序言…

Golang | Leetcode Golang题解之第206题反转链表

题目&#xff1a; 题解&#xff1a; func reverseList(head *ListNode) *ListNode {if head nil || head.Next nil {return head}newHead : reverseList(head.Next)head.Next.Next headhead.Next nilreturn newHead }

【1.1】动态规划求解不同的子序列

一、题目 给定一个字符串s和一个字符串t&#xff0c;计算在s的子序列中t出现的个数。 字符串的一个子序列是指&#xff0c;通过删除一些&#xff08;也可以不删除&#xff09;字符且不干扰剩余字符相对位置 所组成的新字符串。&#xff08;例如&#xff0c;"ACE"是…

6.2、函数的定义

代码 #include <iostream> using namespace std; #include <string>//函数定义//语法&#xff1a;//返回值类型 函数名(参数列表) {函数体语句 return表达式}//加法函数 int add(int num1, int num2) {int sum num1 num2;return sum; } int main() {cout <&l…

聊聊Redis持久化策略RDB

写在文章开头 为避免服务器宕机着情况导致redis内存数据库数据丢失&#xff0c;redis默认出通过rdb保证可靠性&#xff0c;本文将从源码的角度带读者了解rdb读写时机和写入流程。 Hi&#xff0c;我是 sharkChili &#xff0c;是个不断在硬核技术上作死的 java coder &#xff…

刷代码随想录有感(124):动态规划——最长公共子序列

题干&#xff1a; 代码&#xff1a; class Solution { public:int findLength(vector<int>& nums1, vector<int>& nums2) {vector<vector<int>>dp(nums1.size() 1, vector<int>(nums2.size() 1, 0));int res 0;for(int i 1; i <…

数据集采样策略对模型性能的影响问题

数据集采样策略对模型性能的影响问题&#xff0c;需要具体代码示例 随着机器学习和深度学习的快速发展&#xff0c;数据集的质量和规模对于模型性能的影响变得越来越重要。在实际应用中&#xff0c;我们往往面临着数据集规模过大、样本类别不平衡、样本噪声等问题。这时&#…