利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计

这篇具有很好参考价值的文章主要介绍了利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

前言:

        博主是在上一篇博文的基础上作的研究和总结,希望这篇文章可以对诸君有用,同时博主也对鱼香ROS、小鱼大佬、以及其他相关创作者的支持表示由衷的感谢,本文章内容也将继续公开且代码开源。

        文章将讲述usb_cam(usb相机内参标定)、handeye-calib(手眼标定)、aruco_ros(AR码的追踪和位姿检测)的下载、编译以及使用和配置、librviz在Qt中的配置和使用以及图片话题的显示。

        可以参考手眼标定和AR码的追踪和位姿检测。

正文:

板块一:手眼标定

一、使用usb_cam来进行usb相机内参标定

        下载usb_cam:

# 下载对应版本 我这里是noetic版本
sudo apt-get install ros-noetic-usb-cam

        运行:

        1、修改参数

roscd usb_cam/
sudo gedit launch/usb_cam-test.launch
<launch>
  <node name="usb_cam" pkg="usb_cam" type="usb_cam_node" output="screen" >
    <!-- 相机驱动设备位置用ls /dev/video* 查看 -->
    <param name="video_device" value="/dev/video0" />
    <!-- 图片的宽度和高度 这个看相机参数了 -->
    <param name="image_width" value="1280" />
    <param name="image_height" value="720" />

    <param name="pixel_format" value="yuyv" />
    <param name="color_format" value="yuv422p" />

<!-- 相机的tf名称,最好默认 影响最后的图片话题 -->
    <param name="camera_frame_id" value="usb_cam" />
    <param name="io_method" value="mmap"/>

<!-- 内参标定结果文件保存位置 -->
    <param name="camera_info_url" type="string" value="file:///home/dev/.ros/camera_info/head_camera.yaml"/>
  </node>
<!-- 显示图片节点 -->
  <node name="image_view" pkg="image_view" type="image_view" respawn="false" output="screen">
    <remap from="image" to="/usb_cam/image_raw"/>
    <param name="autosize" value="true" />
  </node>
</launch>

        2、下载标定板

        进入Camera Calibration Pattern Generator – calib.io

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        3、开始标定

# 开启相机流
roslaunch usb_cam usb_cam-test.launch
# 新开终端运行内参标定程序 size 为网格角点数 square 是格子边长数 (参数就是上面图片中的说明)
rosrun camera_calibration cameracalibrator.py --size 11x15 --square 0.015 image:=/usb_cam/image_raw camera:=/usb_cam

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        注意:

        这里标定内参的结果会存在你usb_cam-test.launch文件中的位置,这个位置很重要,他是后面ArUco使用时用usb_cam来启动相机的参数之一。

二、handeye-calib(手眼标定)的下载、编译和使用

说明:

       1、 该源码内容由小鱼大佬提供,所以吃水不忘挖井人,感谢。

       2、该源码编译环境为安装好了ROS且最好没有Anaconda等虚拟环境的干扰(至少博主就是因为安装了Anaconda的开发环境导致python的版本不对,最后导致编译不通过和运行错误等问题)。

       3、该功能包编译是有几个依赖文件需要下载和安装。

下载和编译:

        1、创建工作目录并进入开始下载源码。

mkdir ~/hand_eye
cd ~/hand_eye
git clone https://gitee.com/ohhuo/handeye-calib.git

       2、编译源码

cd handeye-calib/
catkin_make

        注意:

        如果编译报错且提示是因为缺少包,那么你需要下载安装就好啦。一般就缺失transforms3d和tabulate两个包,安装就好了,如果还不行就缺啥安啥方法一样。

pip install transforms3d
pip install tabulate

        如果有其他一些关于pip的问题,可以看下面:

# pip安装过慢,可以尝试换清华源
 # 临时使用:
 pip install -i https://pypi.tuna.tsinghua.edu.cn/simple 包名
 # 设为默认:
 pip config set global.index-url https://pypi.tuna.tsinghua.edu.cn/simple

# 没有pip的话可以安装
 sudo apt-get install pip

  学习并使用:

        该内容将以功能包中README.md文件教程为主。

        1、准备工作:

        当我们在用到一个新的功能包或库时可以先阅读它的readme文件,当然小鱼大佬也提供了这么一个文件-----README.md,不过用记事本打开的话不怎么好看,所以我推荐安装一个Markdown编辑器,我这里有一个我总结好的离线安装版本Typora。

链接 提取码: xs66,下载完成后:直接下面命令,就安装好Typora了。

sudo bash install.sh

把功能包的README.md拖入Typora就可以阅读查看了。那么,你可以详细阅读README.md文件来学习和了解使用这个功能包。

        2、开始使用(README.md文件中的基础标定): 

        快读体验(眼在手上为例子)

        使用小鱼提供好的数据,可以快速体验手眼标定。

        参数配置

        找到程序中的src/handeye-calib/launch/base/base_hand_on_eye_calib.launch文件,文件中有两个可配置参数

  • base_handeye_data参数为从位姿文件所在的目录,默认config/base_hand_on_eye_test_data.csv

  • base_handeye_result 参数为结果存储文件目录,默认为config/result/base_hand_on_eye_result.txt

<launch>
    <!-- 需要输入两个参数 -->
    <arg   name="base_handeye_data"   default="$(find handeye-calib)/config/base_hand_on_eye_test_data.csv" />
    <arg   name="base_handeye_result"   default="$(find handeye-calib)/config/result/base_hand_on_eye_result.txt" />
​
    <node pkg="handeye-calib" type="base_hand_on_eye_calib.py" name="base_hand_on_eye_calib" output="screen" >
         <param name="base_handeye_data" value="$(arg base_handeye_data)" />
         <param name="base_handeye_result" value="$(arg base_handeye_result)" />
    </node>
</launch>

        运行程序

source devel/setup.bash
roslaunch handeye-calib base_hand_on_eye_calib.launch

        查看结果

程序会根据配置文件中的坐标进行计算,最终输出如下数据。数据包含不同算法下计算结果,以及计算结果的标准差和方差等数据。

眼在手上最终结果应取:end_link->marker之间关系。

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        3、在线标定:

        在线标定即实时从话题读取姿态信息进行计算,会在 四、标定结果(转换矩阵)的获取中再次提到。

        输入内容:

        1、机械臂位姿:可以通过话题、tf、机械臂的SDK、moveit节点等获取。

        2、标定板位姿:可以通过ArUco工具(下文会讲到它的安装、配置和使用)获取。

        输出内容:

        通过启动不同的launch文件可以得到:(眼在手上)机械臂末端与相机之间的位姿关系或者(眼在手外)机械臂基座与相机之间的位姿态关系。

    三、ArUco的安装和使用

        该功能包一共有两种安装方式:二进制文件安装和源码安装。 

        下载和安装:

         1、二进制安装

# 版本名称为ros的版本 
  sudo apt-get install ros-版本名称-aruco*

        2、源码下载安装

cd ~/hand_eye/handeye-calib/src
# 注意noetic-devel是ros对应版本 需要更改
git clone -b  https://github.com/pal-robotics/aruco_ros
# 回到工作空间
cd ..
catkin_make

        至此,你就将ArUco就安装好了,不同的是一个(二进制安装)是在系统ROS环境下,一个(源码安装)在你建立的ROS环境(工作空间handeye-calib)下。

        参数说明:

        该部分内容,可以仿照aruco_ros(功能包)/aruco_ros/launch中的 single.launch文件来了解,但是我这里就结合小鱼的handeye-calib 功能包中的aruco_start_usb_cam.launch来说明,它的位置在 handeye-calib(功能包)/launch/aruco下,其中标定板的下载和打印,我会在下面说明。

<launch>
<!-- 相机内参标定文件位置 一般为file:///home/用户名/.ros/camera_info/head_camera.yaml -->
    <arg name="camera_info_url"  default="file:///home/ros/.ros/camera_info/head_camera.yaml"/>
<!-- usb相机参数 -->
    <!-- 相机驱动设备位置用ls /dev/video* 查看 -->
    <arg name="video_device"     default="/dev/video0"/>
    <!-- 图片宽度和高度 -->
    <arg name="image_width"      default="640"/>
    <arg name="image_height"     default="480"/>

<!-- 标定板参数 -->
    <!-- markerId: 标定板编号,就是你所用的标定板的id,可以通过`在线生成标定板:https://chev.me/arucogen/进行生成并打印 markerSize:标定板的宽度 单位m -->
    <arg name="markerId"        default="0"/>
    <arg name="markerSize"      default="0.107"/> 
<!-- 剩下的默认就好 -->   
    <arg name="eye"             default="left"/>
    <arg name="marker_frame"    default="aruco_marker_frame"/>
    <arg name="ref_frame"       default=""/>  
    <arg name="corner_refinement" default="LINES" />
 
<!-- 传入参数启动相机 -->
    <node name="usb_cam" pkg="usb_cam" type="usb_cam_node" output="screen" >
        <param name="camera_info_url" type="string" value="$(arg camera_info_url)"/>
        <param name="video_device" value="$(arg video_device)" />
        <param name="image_width" value="$(arg image_width)" />
        <param name="image_height" value="$(arg image_height)" />
        <param name="pixel_format" value="yuyv" />
        <param name="camera_frame_id" value="usb_cam" />
        <param name="io_method" value="mmap"/>
    </node>

<!-- 传入参数启动aruco_ros识别标定板位姿 -->
    <node pkg="aruco_ros" type="single" name="aruco_single">
        <remap from="/camera_info" to="/usb_cam/camera_info" />
        <remap from="/image" to="/usb_cam/image_raw" />
        <param name="image_is_rectified" value="True"/>
        <param name="marker_size"        value="$(arg markerSize)"/>
        <param name="marker_id"          value="$(arg markerId)"/>
        <param name="reference_frame"    value="$(arg ref_frame)"/> 
        <param name="camera_frame"       value="camera_frame"/>
        <param name="marker_frame"       value="$(arg marker_frame)" />
        <param name="corner_refinement"  value="$(arg corner_refinement)" />
    </node> 

<!-- 启动image_view显示识别结果 -->
    <node name="image_view" pkg="image_view" type="image_view" respawn="false" output="screen">
        <remap from="image" to="/aruco_single/result"/>
        <param name="autosize" value="true" />
    </node>


</launch>

        标定板下载和打印:

        下载网站:Online ArUco markers generator        利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉     利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        运行结果:

        当你把参数修改好后,可以开始运行一下。

roslaunch handeye-calib aruco_start_usb_cam.launch

就可以有这个结果辣

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

这个时候,你可以查看你的话题列表就可以找到该标定板的位姿话题(/aruco_single/pose),那么我们把他和handeye-calib功能包中需要的标定板位姿话题统一起来不就有一个输入了吗,至于另一个机器人位姿输入就需要各位仁兄根据自己的实际情况来设计和获取了。

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

四、标定结果(转换矩阵)的获取

        说明:

        这一部分其实际上在 二、handeye-calib(手眼标定)的下载、编译和使用中有提到,其实阅读README.md文件,一步步来就OK了很详细的。

        运行:

        只要你把你的机器人位姿和handeye-calib中的话题和类型统一(建议先看下文参数,更改后再运行)。

# 眼在手
roslaunch handeye-calib online_hand_on_eye_calib.launch

# 眼到手
roslaunch handeye-calib online_hand_to_eye_calib.launch 

        变换机器人位置,以拍到并识别到AR码为准记录数据,多保记录几组后可以计算完成后就可保存。

r  rocord    记录一组手眼数据(当记录的数据大于程序计算所需的数据量之后会进行自动计算)
c  calculate 计算当前数据
s  save      保存数据
p  print     打印当前数据到屏幕上(格式为 type,x,y,z,rx,ry,rz 角度制)
q  quit      退出标定程序

        参数:

        其中,关于两个launch文件的参数说明:

<launch>
    <!-- ArUco获得的标定板位姿话题 类型 geometry_msgs::Pose-->
    <arg   name="camera_pose_topic"   default="/aruco_single/pose" />
    <!-- 机械臂位姿话题 类型 geometry_msgs::Pose-->
    <arg   name="arm_pose_topic"   default="/arm_pose" />

    <arg   name="base_link"   default="/base_link" />
    <arg   name="end_link"   default="/link7" />

    <node pkg="handeye-calib" type="online_hand_on_eye_calib.py" name="online_hand_on_eye_calib" output="screen" >
         <param name="arm_pose_topic" value="$(arg arm_pose_topic)" />
         <param name="camera_pose_topic" value="$(arg camera_pose_topic)" />
    </node>
    
    <node pkg="handeye-calib" type="tf_to_pose.py" name="tf_to_pose" output="screen" >
         <param name="arm_pose_topic" value="$(arg arm_pose_topic)" />
         <param name="base_link" value="$(arg base_link)" />
         <param name="end_link" value="$(arg end_link)" />
    </node>
    
</launch>

        运行结果:

        可参考基于ROS的手眼标定程序解决方案|支持眼在手外/上_ros手眼标定-CSDN博客

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

板块二:Qt上rviz+图片话题显示的UI设计

一、rviz的使用和介绍

        说明:

        1、该部分内容旨在学习和了解rviz的功能和基本操作方法,如果你对这个很熟悉,可以选择跳过。

          2、RViz(Robot Visualization)是一个用于可视化机器人系统的开源工具,用于显示和调试机器人的传感器数据、状态信息和运动规划等。它是ROS(Robot Operating System)的一部分,是ROS中最常用的可视化工具之一。RViz提供了丰富的功能和可定制的界面,使用户能够以三维方式查看机器人模型、传感器数据和环境地图等。它支持多种类型的可视化对象,包括点云、网格模型、标记、路径、激光扫描和相机图像等。

        使用:

        打开两个终端

# 一个终端输入
roscore

# 另一个输入
rviz

        这里,对该窗口作简单介绍

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        添加选项

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        我们拿添加image为例

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

         那我们打开usb_cam,就可以有图像话题产生了,然后就可以看到啦

roslaunch usb_cam usb_cam-test.launch

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        那么,我们对rviz的了解就可以结束了,感兴趣的小伙伴可以自己再研究研究。

二、librviz和Qt的UI结合

        说明:

        该部分意在将我们上面的rviz的可裁减功能融入我们自己设计的UI界面中,比如我们可以做一个显示机器人模型和我们相机识别AR码结果显示的一个自定义UI。那么开始,我建议读者可以先阅读本博主上一篇博客的第四个模块,他讲述了将ROS和Qt结合的一个基础,以及第五个模块,讲述了第三方库和Qt结合开发的一些知识。Ubuntu下基于ROS开发QT人机交互界面和PCL点云处理软件_ros qt pcl-CSDN博客文章浏览阅读889次,点赞22次,收藏27次。仁兄加油吧,活到老,学到老。持续关注博主,将会更新PCL的滤波、平滑、拟合(贪婪三角化)等点云操作方法。_ros qt pclhttps://blog.csdn.net/qq_60640693/article/details/134811948?spm=1001.2014.3001.5501        当然的当,你也可以不看,其实我只是想增加我的浏览量.....哈哈哈哈;不过通过上篇文章确实可以学到东西,但是只看本篇也是可以的了。

        开发步骤:

        1、前言

        首先说明一下,我已有的文件结构

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        那么实际上,我们只需要封装一个qt+rviz的包就好了。

        2、创建框架

        创建工作空间

mkdir -p cam_ui/src
cd cam_ui/
catkin_make

        创建qrviz功能包

cd src/
catkin_create_pkg qrviz roscpp

        用QtCreator打开该工作空间并对该功能包编写

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉        利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        这个时候,就可以用QtCreator再创建一个界面项目,并把他的main.cpp、ui文件和widget.h、widget.cpp文件移到我们功能包下(该部分在上篇文章中 模块四:Qt制作ROS人机交互界面 有提及)。

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        这是移动后效果

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        接下来双击widget.ui文件设计界面

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        然后回到编辑源码页面,修改CMakeLists.txt文件和增加rosnode(前两个部分我在上一片有提及)和Qrviz类(这部分看下面图片的注意事项),这部分直接将我开源的代码复制过去研究就好了。

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        把这些对应的cpp和h、hpp文件移到src和include文件夹下,然后就可以双击CMakeLists.txt修改了,修改完成后,就可以编译了。

        3、源码文件

        CMakeLists.txt文件

#设置cmake版本号
cmake_minimum_required(VERSION 3.0.2)
#设置项目名称
project(qrviz)

#寻找ros包 赋予catkin
find_package(catkin REQUIRED COMPONENTS
  roscpp
  rviz
  std_msgs
  sensor_msgs
  image_transport
  cv_bridge
  )

#声明联合编译为ros包 不然roslaunch和rosrun调不起
catkin_package()

#打开QT moc(自定义信号和槽函数生成功能生成信号的moc_xxx.cpp文件) RCC(qrc资源文件) UIC(负责处理ui文件,生成对应的ui_xxxx.h文件)
set(CMAKE_AUTOMOC ON)
set(CMAKE_AUTORCC ON)
set(CMAKE_AUTOUIC ON)


#寻找QT包 有QT6就是6 没有就是QT5
find_package(Qt5 COMPONENTS Widgets Core Gui REQUIRED)



#########################################  源码、ui文件和头文件  ################################################
set(SOURCES
    src/widget.ui
    src/widget.cpp
    src/main.cpp
    src/qrviz.cpp
    src/rosnode.cpp
)
#这里可以不设置这个 直接把这两个放在src下编译 也行
set(HEADERS
   include/widget.h
   include/qrviz.hpp
   include/rosnode.h
)

###############################################################################################################

#加载头文件到环境中
include_directories(
    include #当前目录的include
    ${catkin_INCLUDE_DIRS} #ros头文件
)

#源码编译为
add_executable(ui ${SOURCES} ${HEADERS}
)

#链接所有动态链接库
target_link_libraries(ui Qt5::Widgets Qt5::Core Qt5::Gui ${catkin_LIBRARIES})

        main.cpp文件

#include "widget.h"

#include <QApplication>
#include <rosnode.h>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    ros::init(argc,argv,"ui");
    Widget w;
    Rosnode n; //实例化一个rosnode对象(该类和方法在rosnode.h和rosnode.cpp中实现)
    QObject::connect(&n,&Rosnode::pubimage,&w,&Widget::getimage); //绑定对象信号和槽函数
    QObject::connect(&n,&Rosnode::pubparam,&w,&Widget::getparam);
    QObject::connect(&w,&Widget::startgetparam,&n,&Rosnode::startpubparam);
    w.startrviz();
    w.show();
    return a.exec();
}

        widget.h文件

#ifndef WIDGET_H
#define WIDGET_H

#include <QWidget>
#include <QImage>
#include <QMap>

#include <qrviz.hpp>

QT_BEGIN_NAMESPACE
namespace Ui {
class Widget;
}
QT_END_NAMESPACE

class Widget : public QWidget
{
    Q_OBJECT

public:
    Widget(QWidget *parent = nullptr);
    void startrviz();
    ~Widget();

private:
    Ui::Widget *ui;
    Qrviz *my_rviz;

    QMap<QString,QString> param; //接收参数map
signals:
    void startgetparam();
public slots:
    void getimage(QImage im);
    void getparam(QMap<QString,QString>pa);
};
#endif // WIDGET_H

        widget.cpp

#include "widget.h"
#include "ui_widget.h"

Widget::Widget(QWidget *parent)
    : QWidget(parent)
    , ui(new Ui::Widget)
{
    ui->setupUi(this);
}

void Widget::startrviz()
{
    emit startgetparam(); //开始获得参数
    my_rviz=new Qrviz(ui->verticalLayout);
    my_rviz->display_grid();
    my_rviz->set_fixedframe(param["fixed_frame"]); //传递参数给qrviz
    my_rviz->display_model(param["robot_model"]);
    //my_rviz->display_imag(param["image_topic"]);
}

Widget::~Widget()
{
    delete ui;
}

void Widget::getimage(QImage im)
{
    ui->label->setPixmap(QPixmap::fromImage(im));
}

void Widget::getparam(QMap<QString, QString> pa)
{
    param.unite(pa); //得到参数存到param中
}

        rosnode.h

#ifndef ROSNODE_H
#define ROSNODE_H

#include <QThread>
#include <QImage>
#include <QMap>

#include <sensor_msgs/Image.h>
#include <cv_bridge/cv_bridge.h>
#include <ros/ros.h>

// 子线程类
class Rosnode : public QThread //继承QThread(线程类)
{
    Q_OBJECT

public:
    void run() override; //重写run函数
    Rosnode();
    void sub_callback(const sensor_msgs::Image::ConstPtr &msg_); //图片消息回调函数
    void getparam(QString paramName); //ros得到参数文件并存储到一个Qmap中
    QImage cvMat2QImage(const cv::Mat &mat); //把图片转化为Qimage

    ros::NodeHandle nh; //定义一个ros节点句柄,用于操作ros方法
    ros::Publisher pub; //话题发布器
    ros::Subscriber sub; //话题订阅器

    QMap<QString,QString> param; //参数存储map

signals:
    void pubimage(QImage im); //发布图片信号给UI页面接收
    void pubparam(QMap<QString,QString> pa); //发布参数map给qrviz对象控制

public slots:
    void startpubparam(); //靠UI页面来控制是否开始传递读取参数

};

#endif // ROSNODE_H

        rosnode.cpp

#include "rosnode.h"

void Rosnode::run()
{

}

Rosnode::Rosnode()
{
    /*读取三个参数文件参数*/
    getparam("fixed_frame");
    getparam("image_topic");
    getparam("robot_model");
    sub=nh.subscribe(param["image_topic"].toStdString(),1,&Rosnode::sub_callback,this); //绑定消息回调函数
}

/*有图片消息过来就以信号抛出给UI了*/
void Rosnode::sub_callback(const sensor_msgs::Image::ConstPtr &msg_)
{
    cv_bridge::CvImagePtr cv_ptr;
    try
    {
        cv_ptr = cv_bridge::toCvCopy(msg_,msg_->encoding);
        QImage im = cvMat2QImage(cv_ptr->image);
        emit pubimage(im);
    }
    catch (cv_bridge::Exception&e)
    {
        ROS_ERROR(e.what());
        return;
    }


}

void Rosnode::getparam(QString paramName)
{
    std::string vale_s;
    nh.getParam(paramName.toStdString(),vale_s);
    QString vale(vale_s.data());
    param[paramName]=vale;
}
void Rosnode::startpubparam()
{
    emit pubparam(param);
}
QImage Rosnode::cvMat2QImage(const cv::Mat &mat)
{
    QImage image;
    switch(mat.type())
    {
    case CV_8UC1:
        // QImage构造:数据,宽度,高度,每行多少字节,存储结构
        image = QImage((const unsigned char*)mat.data, mat.cols, mat.rows, mat.step, QImage::Format_Grayscale8);
        break;
    case CV_8UC3:
        image = QImage((const unsigned char*)mat.data, mat.cols, mat.rows, mat.step, QImage::Format_RGB888);
        //image = image.rgbSwapped(); // BRG转为RGB(颜色变成灰色)
        //Qt5.14增加了Format_BGR888
        //image = QImage((const unsigned char*)mat.data, mat.cols, mat.rows, mat.cols * 3, QImage::Format_BGR888);
        break;
    case CV_8UC4:
        image = QImage((const unsigned char*)mat.data, mat.cols, mat.rows, mat.step, QImage::Format_ARGB32);
        break;
    case CV_16UC4:
        image = QImage((const unsigned char*)mat.data, mat.cols, mat.rows, mat.step, QImage::Format_RGBA64);
        image = image.rgbSwapped(); // BRG转为RGB
        break;
    }
    return image;
}

        qrviz.hpp文件

#ifndef QRVIZ_HPP
#define QRVIZ_HPP

#include <QObject>

#include <ros/ros.h>

#include <rviz/visualization_manager.h>
#include <rviz/render_panel.h>
#include <rviz/display.h>
#include <rviz/tool_manager.h>
#include<rviz/tool.h>
#include <rviz/default_plugin/view_controllers/orbit_view_controller.h>
#include <rviz/view_manager.h>

#include <QVBoxLayout>

class Qrviz
{
public:
    Qrviz(QVBoxLayout *layout); //重写构造函数传入一个布局地址
    void display_grid(); //展示网格
    void set_fixedframe(QString frame); //设置相机坐标系
    void display_imag(QString topic); //设置图片话题
    void display_model(QString model); //设置机器人模型


private:
    rviz::RenderPanel *render_panel_; //rviz显示容器
    rviz::VisualizationManager* manager_; //rviz控制器
};

#endif // QRVIZ_HPP

        qrviz.cpp

#include "qrviz.hpp"

Qrviz::Qrviz(QVBoxLayout *layout)
{
    render_panel_=new rviz::RenderPanel();  //创建rviz显示容器,其本质是继承QWidget类,因此可将其看成一个窗口控件
    layout->addWidget(render_panel_); //将rviz显示容器加入传入的布局器中
    manager_=new rviz::VisualizationManager(render_panel_); //获取可视化rviz的控制对象,后面直接操作这个
    /*前三步把Qt窗口的布局器和rviz的显示窗口绑定,并绑定了一个供操作rviz的接口manager_*/

    render_panel_->initialize(manager_->getSceneManager(),manager_);  //绑定交互信号(初始化camera ,实现放大 缩小 平移等操作)

    manager_->initialize();//初始化
    manager_->removeAllDisplays();//删除所有图层
    manager_->startUpdate();//更新所有图层
}


void Qrviz::display_grid()//添加网格
{
    /*
     * Display* createDisplay( const QString& class_lookup_name, const QString& name, bool enabled );
     * 创建图层函数,其中class_lookup_name:还可以取“rviz/PointCloud2”,“rviz/RobotModel”,"rviz/TF"等:
       图层创建好之后要设置图层的各个属性值,属性值也可以根据rviz图形界面右侧来设置:
       subProp( QString propertyName )->setValue(Qvariant value)(键值对);
     */
    rviz::Display* grid_ =manager_->createDisplay("rviz/Grid","adjustable grid",true);
    grid_->subProp("Line Style")->setValue("Billboards");
    grid_->subProp("Color")->setValue(QColor(125,125,125));
}

void Qrviz::set_fixedframe(QString frame)
{
    manager_->setFixedFrame(frame);
}

void Qrviz::display_imag(QString topic)
{
    rviz::Display* imag_ =manager_->createDisplay("rviz/Image","xs image",true);
    imag_->subProp("Image Topic")->setValue(topic);
}

void Qrviz::display_model(QString model)
{
    rviz::Display* model_=manager_->createDisplay("rviz/RobotModel","robot",true);
    model_->setDescription(model);
}

        那么,到此为止我们就搞定了最重要的一个环节;但是由于我代码采用的参数是由外部文件来提供的,所以我们需要一个param的文件夹下的qrviz.yaml文件和对应的launch文件。

        qrviz.yaml

# 设置qrviz的参数
# fixed_frame 相机所在坐标系名称
# image_topic 图像显示订阅话题
# robot_model 机器人模型名

fixed_frame: /base_link
image_topic: /aruco_single/result
robot_model: robot_description

        qrviz.launch

<launch>
<!-- 加载参数文件的参数 -->
    <rosparam file="$(find qrviz)/param/qrviz.yaml" command="load"/>
    <node name="ui" pkg="qrviz" type="ui" output="screen" required="true"/>
</launch>

        这里,我提供我的项目文件 链接 ,提取码: xs66,其中包括aruco_ros、handeye-calib、krp_description(我自己的机器人模型)、qrviz、bringup(启动功能包);下载、编译可以

# 注意/handeye-calib/launch/aruco/aruco_start_usb_cam.launch里面的摄像头驱动号
# <arg name="video_device"     default="/dev/video2"/> 可能是其他号
roslaunch bringup bringup.launch

        运行效果

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

        注意:

        如果出现下述问题

利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计,机器人,qt,linux,计算机视觉

总结:

        博主说:

        虽然这个过程曲折且艰辛,但是不经历风雨,如何见彩虹啊;诸位仁兄,还得学习啊,每日三省吾身......哈哈哈哈哈哈。

        废话少说,后面我会继续更新PCL、Qt、ROS以及机械臂相关知识的,知识点杂,大家挑有用的看吧。文章来源地址https://www.toymoban.com/news/detail-834015.html

到了这里,关于利用ROS做机器人手眼标定和Qt+rviz+图片话题显示的UI设计的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 【ROS 2 基础-常用工具】-7 Rviz仿真机器人

     所有内容请查看:博客学习目录_Howe_xixi的博客-CSDN博客

    2024年02月08日
    浏览(51)
  • 【ROS2机器人入门到实战】通过JointStates控制RVIZ2关节

    当前平台文章汇总地址:ROS2机器人从入门到实战 获取完整教程及配套资料代码,请关注公众号鱼香ROS获取 教程配套机器人开发平台:两驱版| 四驱版 为方便交流,搭建了机器人技术问答社区:地址 fishros.org.cn 我是小鱼,本节我们来看看如何手动的发送 joint_states 来控制机器人

    2024年02月02日
    浏览(69)
  • kuka示教器嵌套UR界面操作ros中rviz的UR机器人

    本例展示了用QT增加一个网页视图,背景是kuka示教器界面,中间增加UR的VNC网页界面显示。本人博客中一起有写过ros2运行UR的操作。         ros2 UR10仿真包运行_基于ros的ur仿真-CSDN博客       效果如下:     背景的增加,参考这篇文件。  qt for python创建UI界面-CSDN博客   主要

    2024年02月21日
    浏览(55)
  • ROS2下使用TurtleBot3-->SLAM导航(仿真)RVIZ加载不出机器人模型

    在使用台式机进行仿真时,大部分例程很顺利,但在SLAM导航时,在RVIZ中却一直加载不出机器人模型,点击Navigation2 Goal选择目标点进行导航时,无响应。 启动后在RVIZ2和终端看到一个错误 按照官网的指令试了多次,一直无法加载,在网上赵的解决方案都是修改RVIZ里的各种设

    2024年02月09日
    浏览(53)
  • GPS学习(一):在ROS2中将GPS经纬度数据转换为机器人ENU坐标系,在RVIZ中显示坐标轨迹

    本文记录在Ubuntu22.04-Humbel中使用NMEA协议GPS模块的过程,使用国产ROS开发板鲁班猫(LubanCat )进行调试。 在淘宝找了款性价比较高的轮趣科技GPS北斗双模定位模块作为入门学习使用,支持GNSS系统(北斗、GPS、GLONASS、日本的QZSS以及卫星增强系统SBAS),定位精度在2.5m左右,属于民用

    2024年02月03日
    浏览(69)
  • 如何利用蓝桥云课提升学习ROS机器人的效率

    合适再深入学习,不合适一个网页简单使用也能了解其中大部分功能,免除繁琐配置的时间成本。 如果学习和试用一下ROS机器人(ROS1为例)最方便的办法就是打开如下网页: 课程编号854,已经学习人数超过1.6万。 可以通过蓝桥云课上的ROS机器人相关课程学习,结合实践操

    2023年04月09日
    浏览(48)
  • 利用qt实现机器人可视化界面,并在界面上控制机器人各个关节运动

     本工程借助于clion配置的qt环境,同时依赖eigen tinyxml2等开源库,也借鉴了博客上一些文章,具体哪些忘记了,十分抱歉。本工程仅供参考。机械臂模型为史陶比尔官网的TX2-60L-HB。可以去那下载对应的stp文件。 最终图:  通过鼠标中键控制旋转 缩放,配合ctrl进行平移。加载

    2024年02月11日
    浏览(58)
  • rviz上不显示机器人模型(模型只有白色)

    文档中的是base_footprint,需要根据自己所设的坐标系更改,我的改为base_link 如何查看自己设的坐标系: 这些parent父坐标系就是 同时打开rviz后需要更改成base_link

    2024年04月17日
    浏览(33)
  • 读取机器人移动轨迹并在RVIZ界面中显示

    机器人在巡检过程中需要沿着固定路线执行任务,因此可以先把机器人的移动轨迹录制并保存下来,之后读取轨迹,方便后续操作。 巡检导航过程中,机器人需要确定好坐标系,以便进行定位与导航,在gazebo仿真下可以选择world坐标系,在实际使用中通常使用的是map坐标系,

    2024年02月04日
    浏览(40)
  • RViz成功显示多个机器人模型以及解决显示的模型没有左右轮

    在RViz中显示多个机器人模型需要设置好几个关键的参数 首先点击Add,找到RobotModel,添加进来 Fixed Frame:选择TF树最上层的坐标系,一般是世界坐标系,即固定不动的全局坐标系 Robot Description:/robot1/robot_description,要在robot_description前加上对应的命名空间 TF Prefix:robot1,机器

    2024年01月18日
    浏览(56)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包