基于视觉的机械臂分拣(一)
最近做了一个基于视觉的五轴机械臂分拣的项目,功能基本完成,现在抽点时间出来做一个总结,算是自己做机械臂的一个记录,在做这个项目之前,你需要先学习一下机械臂的基础知识(运动学),以及摄像头方面的知识和坐标之间的一个变换的使用。
首先说一下我项目用到的材料:openmv摄像头,SD卡,五轴机械臂,舵机驱动板,6v输出的开关电源,以及部分架子,整体如下图
首先我们来介绍一下机械臂,因为我的机械臂的驱动器用的是舵机,那么我们先来介绍一下舵机。
舵机又称之为伺服电机,伺服电机是一种可以控制旋转角度或者是旋转角速度的电机。一般舵机有90度舵机、180度舵机、270度舵机、360度舵机。
注意的一点:360度舵机,我们无法控制其旋转特定的角度,只能控制其以特定的角速度旋转。
舵机分类
舵机一般分为模拟舵机与数码舵机两种,他们的区别在与舵机内部有无mcu(单片机),有单片机控制的是数码舵机,没有单片机控制的是模拟舵机。
比如传统模拟舵机和数字比例舵机都称之为模拟舵机,数码舵机的电子电路中带有mcu微控制器,跟模拟舵机相比,数码舵机反应速度更快,无反应去范围小,定位精度高,抗干扰性强。
注意区分数字舵机与数码舵机之间的区别,数字比例舵机属于模拟舵机,数码舵机要贵一些,一般售价在两百多,而普通的模拟舵机一般在十几到几十,买那种舵机看个人的经济情况,如果刚刚入门,用低成本的模拟舵机就可以了。
接来下讲讲重点了,舵机的标定(如果舵机不进行标定的话,误差会比较大,到时候抓取的时候,会偏离较大)
我用的是线性回归的方法,尽可能的修正舵机的角度误差
第一步 做一个标定板
这个标定板的话要看大家的舵机角度,我的舵机都是180度,所以我做的标定板是这个样子的,比较简陋。
第二步
你应该知道当我们设置占空比,舵机会转到一个角度,而占空比的取值范围和驱动板有一定关系,我用的驱动板的分辨率是12位的,对应的有效取值(0,4095)。
因为舵机的有效脉宽是0.5ms~2.5ms,脉宽对应的占空比范围是:
但是这个是理想情况,与实际上还是有一定误差的。
标定程序如下
''' 测试机械臂的安装 舵机角度标定,记录占空比与角度之间的映射关系 duty reference range 102 511 ''' from machine import Pin, I2C from easy_pca9685 import PCA9685 from configs import config i2c = I2C(scl=Pin(config['I2C_SCL']), sda=Pin(config['I2C_SDA'])) #,freq=config['I2C_FREQUENCY']) # 初始化PCA9685对象 pca9685 = PCA9685(i2c, config['PCA9685_ADDRESS']) pca9685.freq(50) # Joint:1 # degree: 180 # range: 0 - #------------------ # RADIUS | DUTY #------------------ # -pi/2 | 145 # -pi/4 | 230 # 0 | 307 # pi/4 | 400 # pi/2 | 468 pca9685.duty(0, 307) # Joint:2 * # degree: 180 #------------------ # RADIUS | DUTY #------------------ # -pi | 530 # -3pi/4 | 420 # -pi/2 | 332 # -pi/4 | 220 # 0 | 110 pca9685.duty(1, 327) # Joint:3 degree: 180* #------------------ # RADIUS | DUTY #------------------ # -pi/6 | 128 # 0 | 172 # pi / 4 | 230 # pi/2 | 305 # 3*pi/4 | 390 pca9685.duty(2, 175) # Joint:4 # degree: 180 # range: 0 - #------------------ # RADIUS | DUTY #------------------ # -pi/2 | 530 # -pi/4 | 425 # 0 | 318 # pi/4 | 208 # pi/2 | 110 pca9685.duty(3, 318) # Joint 5 #------------------ # RADIUS | DUTY #------------------ # -pi/2 | 505 # -pi/4 | 406 # 0 | 307 # pi/4 | 218 # pi/2 | 130 pca9685.duty(4, 307) # 40 OpenS # 80 Grab Box # Grapper #------------------ # WIDTH | DUTY #------------------ # 0 | 300 # 0.02 | 280 # 0.035 | 250 # 0.05 | 200 pca9685.duty(5, 280)
线性拟合程序如下
#-*- coding:utf_8 -*- import numpy as np import matplotlib.pyplot as plt from sklearn.linear_model import LinearRegression ''' data = [ [64,500], [74,600], [85,700], [93,800], [103,900], [112,1000], [120,1100], [128,1200], [135,1300], [144,1400], [154,1500], [160,1600], [168,1700], [172,1800], [186,1900], [195,2000], [203,2100], [210,2200], [222,2300], [230,2400], [240,2500]] ''' data = [ [-1.57,545], [-1.047,478], [-0.785,445], [-0.523,407], [0,333], [0.523,260], [0.785,222], [1.047,184], [1.57,124] ] data = np.array(data) angles = data[:,0] pws = data[:,1] plt.scatter(angles,pws) x = angles.reshape(len(angles), 1) y = pws.reshape(len(pws), 1) model = LinearRegression() model.fit(x,y) k = model.coef_[0][0] b = model.intercept_[0] print('拟合后的直线 y = {} * x + {}'.format(k,b))
标定结果如下
机械臂组装时,我们标定一个舵机,安装一个,安装舵机尽量以0度或90度安装,并且转转范围要在你需要的范围内。
到这里机械臂部分基本安装完成了。