19f02e61debb7.png

来源:第四届3D视觉创新应用竞赛 | 河南工业大学 | 作者:王俊超 源代码:https://github.com/3DCVdeveloper/RobotV_Sorting-and-Testing 相机SDK:奥比中光 Orbbec SDK


一、项目背景:工业4.0时代的痛点与机遇

1.1 行业痛点

在工业生产中,工件尺寸不达标是影响产品质量和使用寿命的关键问题。传统解决方案依赖人工检测,存在以下缺陷:

  • ❌ 效率低下:人工检测速度慢,无法满足高速生产线的需求
  • ❌ 成本高昂:大量人力投入,生产成本居高不下
  • ❌ 精度不稳:人工检测受主观因素影响,测量结果不稳定

1.2 技术机遇

随着机器视觉技术和机器人技术的快速发展,智能分拣与检测系统成为可能:

  • ✅ 机器视觉:比人工检测更精准、更高效
  • ✅ 机器人技术:灵活多变、抓取效率高、系统柔性化
  • ✅ 深度学习:缺陷检测精度不断提升

二、系统概述:一站式智能分拣检测方案

2.1 核心功能

当不同种类的工件从传送带上经过时,系统会:

  1. 通过深度相机获取工件的种类和距离相机的深度
  1. 机械臂末端相机获取工件坐标和种类
  1. 根据工件特性分为 2D检测 和 3D检测 两个种类
  1. 机械臂抓取工件,放置到对应的检测系统上

2.2 硬件配置一览

image.png
组件 型号 作用
🎥 深度相机 奥比中光 Gemini 2 工件识别、深度测量
📷 工业相机 大华 A3B00MG000 2D检测(5472×3648分辨率)
📸 3D相机 IDS相机 三维重建
🤖 机械臂 越疆 Dobot 四自由度 工件抓取与分拣
🧠 计算平台 NVIDIA Jetson Orin Nano 深度学习推理、图像处理
🎛️ 控制器 STM32F407 传送带、旋转台控制
🛞 传送系统 步进电机驱动 工件输送

三、工作流程:智能化分拣全解析

3.1 整体流程

19f02da74b8b1.png

四、核心算法:技术实现深度解析

4.1 工件定位识别算法

工件定位识别算法流程图:【需要插入】

工件定位是整个系统的第一步,主要分为以下五个步骤:

4.1.1 图像预处理

// 高斯模糊 - 降噪处理
GaussianBlur(srcImage, blurred, Size(5, 5), 1.5);

// 二值化 - 分离前景背景
threshold(grayImage, binary, 0, 255, THRESH_BINARY | THRESH_OTSU);

// 形态学操作 - 改善形状结构
Mat kernel = getStructuringElement(MORPH_RECT, Size(3, 3));
morphologyEx(binary, processed, MORPH_OPEN, kernel);

技术要点:

  • 高斯模糊:使用 5×5 卷积核,有效减少图像噪声
  • OTSU算法:自适应阈值分割,无需手动设置阈值
  • 形态学开运算:消除小斑点,平滑边缘

4.1.2 轮廓查找与筛选

// 查找所有外部轮廓
vector<vector<Point>> contours;
findContours(processed, contours, hierarchy,
             RETR_EXTERNAL, CHAIN_APPROX_SIMPLE);

// 筛选条件
for (auto& contour : contours) {
    // 排除点数过少的轮廓(噪声)
    if (contour.size() < MIN_CONTOUR_POINTS) continue;

    // 计算轮廓面积
    double area = contourArea(contour);
    if (area < MIN_AREA) continue;
}

4.1.3 形状拟合

// 椭圆拟合 - 用于圆形工件
RotatedRect ellipse = fitEllipse(contour);
float axisRatio = ellipse.size.width / ellipse.size.height;

// 矩形拟合 - 用于方形工件
RotatedRect rect = minAreaRect(contour);
float widthRatio = rect.size.width / rect.size.height;

识别效果示意:【需要插入矩形工件和圆形工件的识别效果图】


4.2 2D检测系统:亚像素精度测量

2D检测系统流程图:【需要插入】

2D检测系统采用高精度工业相机,配合亚像素边缘检测算法,实现微米级测量精度。

4.2.1 亚像素边缘检测核心算法(DeVernay)

// DeVernay 亚像素边缘检测算法实现
void devernay(
    double** x, double** y,           // 输出:边缘点坐标
    int* N, int** curve_limits, int* M, // 输出:点数、曲线限制、曲线数
    uchar* pSrc, uchar* pDst,         // 输入:原始图像、处理后图像
    int iWidth, int iHeight,          // 图像尺寸
    double S, double H, double L      // 参数:平滑系数、高阈值、低阈值
) {
    // 1. 高斯平滑
    gaussian_smooth(pSrc, pDst, iWidth, iHeight, S);

    // 2. 计算梯度
    image_gradient(pDst, gradMag, gradDir, iWidth, iHeight);

    // 3. 非极大值抑制
    non_maximum_suppression(gradMag, gradDir, iWidth, iHeight, H, L);

    // 4. 边缘连接与亚像素精化
    edge_linking(x, y, N, curve_limits, M, iWidth, iHeight);
}

4.2.2 RANSAC直线拟合

// RANSAC 鲁棒直线拟合
void Calculator::fitLineRansac(
    const vector<Point2f>& points,  // 输入点集
    vector<Point2f>& finalPoints,   // 输出:内点
    Vec4f& line,                    // 输出:直线参数 (dx, dy, x0, y0)
    int iterations,                 // 迭代次数
    double sigma,                   // 内点阈值
    double k_min, double k_max      // 斜率范围
) {
    cv::RNG rng;
    double bestScore = -1;

    for (int k = 0; k < iterations; k++) {
        // 随机选取两个点
        int i1 = rng(points.size());
        int i2 = rng(points.size());
        const Point2f& p1 = points[i1];
        const Point2f& p2 = points[i2];

        // 计算方向向量
        Point2f dp = p2 - p1;
        dp *= 1.0 / norm(dp);

        // 统计内点数量
        double score = 0;
        vector<Point2f> inliers;
        for (const auto& pt : points) {
            Point2f v = pt - p1;
            // 计算点到直线的距离(叉积)
            double d = fabs(v.y * dp.x - v.x * dp.y);
            if (d < sigma) {
                score++;
                inliers.push_back(pt);
            }
        }

        // 更新最佳模型
        if (score > bestScore) {
            bestScore = score;
            finalPoints = inliers;
            line = Vec4f(dp.x, dp.y, p1.x, p1.y);
        }
    }
}

4.2.3 算法对比

拟合方法 精度 抗噪性 计算效率
多项式拟合 ★★★ ★★ ★★★★★
Zernike矩 ★★★★ ★★★ ★★★
改进算法 ★★★★★ ★★★★ ★★★★

算法对比效果:【需要插入多项式拟合 vs Zernike矩 vs 改进算法的对比图】


4.3 3D检测系统:光结构三维重建

3D检测系统流程图:【需要插入】

4.3.1 算法流程

相机标定 → 光平面标定 → 旋转轴标定 → 拍摄采集 → 三维重建

4.3.2 光条中心提取算法

// 光条中心提取流程
Mat lightStripeCenterExtraction(Mat& srcImage) {
    // 步骤1:减运算得到光条区域
    Mat diffImage;
    absdiff(srcImage, backgroundImage, diffImage);

    // 步骤2:开运算去噪
    Mat opened;
    morphologyEx(diffImage, opened, MORPH_OPEN, kernel);

    // 步骤3:阈值处理
    Mat thresholded;
    threshold(opened, thresholded, THRESH_OTSU);

    // 步骤4:腐蚀操作细化
    Mat eroded;
    erode(thresholded, eroded, kernel, Point(-1,-1), 2);

    // 步骤5:Steger算法提取中心
    vector<Point> centerLine;
    steger(eroded, centerLine);

    return centerLine;
}

光条处理效果:【需要插入光条中心提取各步骤效果图:(a)减运算 (b)开运算 (c)阈值处理 (d)腐蚀操作】

4.3.3 SMD-ARM机械臂控制

// 机械臂控制核心逻辑
class DobotController {
public:
    // 关节角度控制
    void setJointAngle(int joint, double angle) {
        sendCommand(CMD_SET_ANGLE, joint, angle);
    }

    // 吸盘控制
    void setSuctionCup(bool on) {
        sendCommand(CMD_SUCTION, on ? 1 : 0);
    }

    // 运动到目标位置(带深度补偿)
    void moveToWithDepth(double x, double y, double z, double depth) {
        // 深度补偿公式:实际Z = 目标Z - 测量深度
        double compensatedZ = z - depth * DEPTH_SCALE_FACTOR;
        moveTo(x, y, compensatedZ);
    }
};

五、通信架构:多协议协同工作

系统通信拓扑:【需要插入通信架构图】

5.1 系统通信拓扑

19f02e01e8abf.png

5.2 Modbus通信协议

STM32与上位机采用Modbus RTU协议通信,具有高可靠性和多设备支持能力:

// Modbus 数据帧格式

// 传送带转动
uint8_t conveyorFrame[] = {0x02, 0x10, 0x00, 0x00, 0x00, 0x01, 0x63, 0xBA};

// 激光控制
uint8_t laserFrame[] = {0x02, 0x10, 0x00, 0x01, 0x00, 0x01, 0x5E, 0x7A};

// 光源控制
uint8_t lightFrame[] = {0x02, 0x10, 0x00, 0x02, 0x00, 0x01, 0x1A, 0x7A};

Modbus协议优势:

  • ✅ CRC校验确保数据完整性
  • ✅ 多从机支持(多路复用)
  • ✅ 从机主动上报功能

5.3 Socket局域网通信

// Jetson Orin Nano 端 - Socket服务器
class SocketServer {
private:
    int server_fd;
    struct sockaddr_in address;

public:
    bool init(int port) {
        server_fd = socket(AF_INET, SOCK_STREAM, 0);
        address.sin_family = AF_INET;
        address.sin_port = htons(port);
        address.sin_addr.s_addr = INADDR_ANY;
        bind(server_fd, (struct sockaddr*)&address, sizeof(address));
        listen(server_fd, 5);
    }

    // 发送工件信息到上位机
    void sendWorkpieceInfo(int type, double depth) {
        char buffer[BUFFER_SIZE];
        sprintf(buffer, "TYPE:%d,DEPTH:%.2f", type, depth);
        send(client_fd, buffer, strlen(buffer), 0);
    }
};

六、系统UI:人性化交互设计

系统UI界面截图:【需要插入】

系统UI分为三大区域:

区域 功能 说明
🖼️ 左侧2D区 图像显示 展示相机采集的2D图像,支持ROI选取
📦 右侧3D区 模型显示 实时显示3D重建结果
⚙️ 下方控制区 硬件控制 传送带、光源、检测参数设置

核心功能模块:

  • 📁 工件库管理:存储工件模板和检测参数
  • 📏 测量工具:点-点、点-线、线-线、角度、圆弧测量
  • 📋 结果显示:检测值、公差、合格/不合格判定
  • 📝 日志系统:操作记录、异常报警

七、项目优势与未来展望

7.1 核心技术创新

技术亮点 实现方式 达到效果
🔬 双目+深度融合 Gemini 2 结构光 高精度3D感知
📐 亚像素边缘检测 DeVernay + RANSAC 微米级测量精度
🌀 多协议协同 Modbus + Socket 实时稳定通信
⚡ 智能分拣 颜色+形状识别 分类准确率 > 95%

7.2 优化方向

模块 当前问题 优化方案
识别算法 光照敏感、背景干扰 迁移学习、背景分割
机械臂 双相机资源浪费 单相机方案
三维重建 非白色物体重建变形 MVS多视角重建
系统UI 功能单一、偶发卡顿 全新架构重构

八、技术栈总结

类别 技术选型
🎥 深度视觉 奥比中光 Orbbec SDK
🖼️ 工业视觉 大华 GenICam SDK
🧠 边缘计算 NVIDIA Jetson Orin Nano
🎛️ 实时控制 STM32F407 + FreeRTOS
📐 图像处理 OpenCV + 自研算法
🖥️ UI开发 Qt5
🗄️ 数据存储 MySQL
🤖 机械臂 越疆 Dobot API

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注