跳到主要内容

客户端插件说明(electricclawplugin-hmi)

开发环境​

环境工具链
WindowsQt 5.15.2、MSVC 2015 64-bit
linux X86GNU Compiler Collection 9.4
linux aarch64gcc-linaro-6.3.1-2017.05-x86_64_aarch64-linux-gnu

项目结构​

代码文件夹包含 include 和 lib 文件夹,用于提供插件环境支持和必要的工具,在 Qt Creator 中打开 .pro 工程即可看到如下项目结构。

HMI 项目结构

各部分说明:

组成说明
配置文件(.pro)Qt 编译配置文件(可理解为 Qt 版的 CMake),核心配置见下文
界面文件(.ui)Qt Designer 可视化布局文件,构建后生成 ui_*.h 用于 UI 组件绑定
代码文件(.cpp/.h)界面类、业务逻辑类、插件入口类的声明与实现
资源文件(.qrc/.ts)控件文字翻译相关文件

.pro 核心配置​

pro 配置文件

电爪项目 .pro 中与插件开发相关的关键配置:

TEMPLATE = lib                          # 构建为共享库(.dll/.so)
DEFINES += ELECTRICCLAWPLUGIN_LIBRARY # 控制导出/导入符号
DEFINES += PLUGIN_NAME=\\\"OnrobotPlugin\\\" # 插件注册名,用于完成插件注册
LIBS += -L$$PWD/lib/windows -lxplugin # 链接插件 SDK(xplugin)
INCLUDEPATH += $$PWD/include # SDK 头文件搜索路径

QT += widgets、CONFIG += c++11、FORMS、TRANSLATIONS、RESOURCES 等通用 qmake 配置说明见 制作一个简单的 HMI 插件。

代码文件组成​

文件/模块职责
OnrobotPlugin.h/.cpp插件入口类 ElectricClawPlugin:插件注册、工艺包界面创建、RL 指令注册
OnrobotWidget.h/.cpp/.ui工艺包主界面类 ElectricClawWidget:界面生成、信号槽绑定、初始化/运行/停止控制
StatusPoller.h/.cpp状态轮询类:在子线程中以 200ms 周期查询电爪状态并通知界面刷新
JsonWorker.h/.cppJSON 指令工作类:在线程池中异步发送插件指令,避免阻塞界面
rl/RLStartWidget、RLStopWidget、RLStatusWidgetRL 指令界面类:根据窗口内单元的数据生成具体 RL 脚本
OnrobotPlugin_global.h导出符号宏定义(ELECTRICCLAWPLUGIN_EXPORT)

代码核心逻辑​

插件注册​

在 OnrobotPlugin.cpp 中通过宏声明实现插件的注册(PLUGIN_NAME 即 .pro 中定义的 OnrobotPlugin),插件加载时自动初始化插件类,并依次执行插件初始化函数 init() 和 afterInit():

XPLUGIN_REGISTER(PLUGIN_NAME, ElectricClawPlugin)

插件入口与界面注册​

插件入口

init() 中创建工艺包主界面 ElectricClawWidget,并通过 CreateCenterWidget 注册为中心控件:

void xplugin::ElectricClawPlugin::init()
{
m_widget = new ElectricClawWidget;
xplugin::CreateCenterWidget(PLUGIN_NAME, m_widget);
}

工艺包界面(ElectricClawWidget)​

ElectricClawWidget 构造函数中完成信号槽绑定并启动状态监听:

  1. 创建 QThread 子线程,将 StatusPoller 移入其中,线程启动后开始 200ms 周期的状态轮询;
  2. 轮询结果 statusUpdated 信号以 队列连接(Qt::QueuedConnection)方式绑到界面刷新槽函数,更新状态、力度、内宽、外宽四个显示框;
  3. 为各输入框设置 QIntValidator 范围限制(设备 ID 0255、力度 0140、速度 20100、宽度 160685)。

界面按钮的点击逻辑:

按钮逻辑
初始化先钳制输入值,再向设备发送一次 stop 指令作为"握手"校验;成功后记录设备 ID、使能运行/停止按钮及各参数输入框,失败则禁用并清空状态显示
运行钳制输入值后,按界面参数(模式、宽度、力度、速度)组包发送 start 指令
停止钳制输入值后,组包发送 stop 指令

此外,界面通过重写 showEvent/hideEvent 在工艺包页面 显示时开启轮询定时器、隐藏时关闭,避免后台空转。

clampLineEdit() 负责将输入框数值钳制到合法区间:非数字输入重置为最小值,超出上下限则钳到边界值。

JSON 指令收发(JsonWorker)​

界面的所有请求都经 sendRequest() 发出:构造一个 JsonWorker(继承 QObject + QRunnable)投入全局线程池异步执行,完成后通过 finished 信号以队列连接回调界面,避免阻塞 UI 线程:

void JsonWorker::run()
{
QJsonArray result = xplugin::xPluginInterface().commandCustomData(nullptr, m_json);
emit finished(result);
}

发送的 JSON 协议与控制器插件注册的插件指令一一对应(见 控制器插件说明):

操作发送的 JSON响应
停止/初始化握手{"ElectricClawPlugin":{"stop":{"slave_id":1}}}{"return":true}
启动{"ElectricClawPlugin":{"start":{"slave_id":1,"mode":1,"width":400,"force":50,"speed":50}}}{"return":true}
状态轮询{"ElectricClawPlugin":{"get_status":{"slave_id":1}}}{"status":...,"external_width":...,"internal_width":...,"force":...,"return":true}

状态轮询(StatusPoller)​

StatusPoller 在子线程中运行,startPolling() 创建 QTimer 并以 200ms 周期触发 pollStatus():

  • 设备未初始化(m_is_init == false)时直接返回,不发送请求;
  • 组包 get_status 指令调用 commandCustomData 查询,解析返回数组中 ElectricClawPlugin → get_status 节点,通过 statusUpdated 信号抛给界面线程刷新显示。

RL 指令注册​

RL 指令注册

RL 指令注册

在 afterInit() 中通过 RLManager 注册 RL 编辑器指令(OnrobotMove、OnrobotStop、OnrobotStatus)。每条指令需注册五项内容:

m_rlManager->createTypeKey("OnrobotMove");                 // 指令类型标识
m_rlManager->createSkeleton("OnrobotMove", "OnrobotMove"); // 指令骨架
m_rlManager->createInsDescribe("OnrobotMove", tr("...")); // 指令描述
m_rlManager->createPattern("OnrobotMove", "^\\s*...$"); // 匹配正则
m_rlManager->createInsertWidget("OnrobotMove", [](){ // 插入时的编辑控件
return new xplugin::RLStartWidget("OnrobotMove");
});

最后通过 createTypeToGroup 将三条指令归入 OnrobotPlugin 分组,并以 createGroups 设置分组显示标题。

备注

这里注册的只是辅助编程的简化 RL 编写逻辑,不具备 RL 执行逻辑;RL 执行逻辑在控制器插件中实现,见 控制器插件说明。

RL 指令界面类​

RL 指令界面类继承 RLContentBase,需实现三个接口:

接口作用
ToString()将界面控件参数转换为指令字符串(生成 RL 脚本时调用)
FillWith(str)用指令字符串反向填充界面(本示例仅打印调试日志,未做解析)
CheckInsert()判断是否允许作为插入值(本示例固定返回 true)

RLStartWidget::ToString() 示例——读取各控件值并拼接为 指令名 参数1,参数2,... 形式:

三个界面类的输出形式:

界面类对应指令ToString 输出示例
RLStartWidgetOnrobotMoveOnrobotMove 1,1,400,50,50(ID、模式、宽度、力度、速度)
RLStopWidgetOnrobotStopOnrobotStop 1(ID)
RLStatusWidgetOnrobotStatusOnrobotStatus 1,s,e,i,f(ID + 4 个下拉框文本)

编译打包​

  1. 打开 Qt Creator,选择构建类型(推荐 Release 用于发布)。
  2. 编译流程:qmake 解析 .pro 生成 Makefile → jom/make 执行编译 → 生成动态库(.dll)。

编译流程

  1. 构建完成后在构建目录下即可找到生成的动态库。

构建产物

打包规范与通用流程见 插件包制作,可直接使用 PluginPackage 打包脚本。