# CMVR Control Station CMVR Control Station 是一个基于 Qt 5 的桌面控制站,用于连接 CMVR 机器人边缘服务。应用通过 gRPC 调用系统、机械臂、相机、AGV、音频、灵巧手和仿生头等服务,并提供视频预览、音频收发、URDF 模型查看、配置编辑和 QUIC 边缘节点测试服务。 ## 主要功能 - 连接真实 gRPC 服务或使用内置 Demo 模式离线体验界面 - 系统状态、机械臂、AGV、相机及其他设备服务控制 - H.264/H.265 视频解码和 OpenGL 视频渲染 - 麦克风采集、扬声器播放和流式音频 - 内置 AUBO、Elfin、小研及自定义 URDF 模型选择与 Qt3D 显示 - Protobuf 配置查看、校验和编辑 - 可选的 MsQuic/TLS 测试服务器 ## 设备管理 左侧进入 `gRPC > 设备管理` 后,默认打开“设备总览”: - 主 gRPC 通道连接成功时自动调用 `GetSystemInfo` 和 `GetSystemStatus`。 - `GetSystemInfo` 用于显示边缘端系统名与版本;`GetSystemStatus.device_list` 用于展示在线设备 ID、设备大类、厂商和运行时驱动,并随系统状态轮询自动更新。 - 设备按 AGV、电池、相机、灵巧手、夹爪、麦克风、机械臂和扬声器分类, 支持按设备 ID 或类型搜索。 - 点击只读状态下的设备卡片会进入对应控制页面,并自动填写该设备的 `device_id`。 - 点击“修改”会从 ConfigurationService 加载 `manager/device_manager.pb.txt` 及 `devices/*/*.pb.txt`:可以修改设备 ID、类型和品牌/驱动,展开“配置参数” 后按 Protobuf 字段逐项编辑,也可以使用卡片右上角删除按钮或末尾的“+”卡片 增删设备。 - 点击“完成”会先写入各设备配置,再写入 DeviceManager 配置;保存使用远端 revision 做并发版本校验。当前只上传配置文件,不会自动重启或重载 cmvr-es。 - “配置管理”页签保留远端 Protobuf 配置的读取、字段编辑、校验和保存能力; 配置服务默认端口为 `50053`,与主控制 gRPC 通道独立连接。 `GetSystemStatus` 的设备条目包含 `device_type`、稳定的 `device_kind`、 `driver_type` 和 `vendor`。上位机优先使用 `device_kind` 判断设备大类,避免 AUBO、 华沿等具体机械臂驱动被错误归类为 AGV;设备卡片副标题会显示如 `AUBO · AuboARM` 的厂商与驱动信息。“在线”仍表示设备存在于边缘端 本次返回的 `device_list` 中。 ## 机械臂自动识别与切换 机械臂页面的顶部选单来自 `GetSystemStatus` 返回的全部在线机械臂,不再使用 固定的“左臂/右臂”选项。选择设备管理中的机械臂卡片,或直接切换该选单后, 上位机会以相同的 `device_id` 调用 `ArmService.GetArmInfo` 和 `ArmService.getRobotState`: - `GetArmInfo` 返回厂商、SDK 检测到的精确型号/子型号、自由度、关节名以及默认 Base/TCP 坐标系。AUBO 使用 `getRobotType/getRobotSubType`,华沿使用 `HRIF_ReadRobotModel`;SDK 查询失败时边缘端回退到配置文件中的型号。 - 关节点动区、零位标定关节列表和实时关节表按返回的自由度与关节名动态生成, 不再假定机械臂固定为 7 轴。 - 上位机按厂商、型号和子型号自动选择内置 URDF。驱动关节名与 URDF 关节名不一致 时,按 SDK/URDF 的关节顺序映射实时姿态和示教姿态。 - `getRobotState` 一次返回运行模式、安全状态、使能/故障状态、关节状态和 TCP 位姿,切换设备时响应会按 `device_id` 校验,避免旧设备的在途响应覆盖新设备。 上述功能需要 cmvr-es `061bfc50` 或更高版本。 ### 机械臂点动与实时状态 “模型与控制”页将 URDF 模型、速度点动和只读遥测放在同一工作区: - “关节速度”按实时自由度生成每个关节的当前位置与 `−/+` 按钮。每条位置条 使用当前精确 URDF 的关节上下限映射实时位置;按住按钮时调用 `speedJ`,速度 为左侧 SpeedJ 最大速度乘以速度倍率,松开按钮立即调用 `stopMotion`。 - “笛卡尔速度”显示当前 X/Y/Z、RX/RY/RZ,并使用相同的按住点动交互调用 `speedL`。SpeedL 使用独立的笛卡尔速度(m/s)和加速度(m/s²)限制,不再 复用 SpeedJ 的关节单位参数。基座坐标和工具坐标名称通过 `ListBaseFrame`、`ListTCPFrame` 自动 获取;选择变化后,遥测通过 `getPose(base_link, ee_link)` 显示对应坐标对的 末端位姿。 - 当前 cmvr-es 的 `speedL` 协议只接受 Base/Tool 类型,不接受命名坐标系。 因此点动命令按 Base 语义发送,坐标名称用于选定实时位姿的参考基座和 TCP; 后续若需要在任意命名坐标系轴向点动,需要扩展 `SpeedL.Request` 及边缘端驱动。 - 下方“实时状态”只读显示关节位置、速度、由连续速度采样计算的加速度,以及 当前坐标对下的末端位置姿态;关节与末端两个状态区域等宽显示,不再提供 MoveJ/MoveL 目标输入和示教按钮。 ## 技术栈和目录 项目使用 C++14、Qt 5、gRPC/Protobuf、FFmpeg、urdfdom 和可选的 MsQuic。 ```text src/ 应用、服务客户端、音视频和三维显示源码 ui/ Qt Designer 界面文件和辅助控件 protos/ CMVR gRPC、配置和 QUIC 协议定义 models/ 内置机械臂 URDF、网格资源与来源说明 certs/ QUIC 测试 CA;本机 PFX 证书不提交到 Git include/, lib/ Windows MinGW 预编译依赖 tools/ Windows protoc 和 grpc_cpp_plugin scripts/ Windows 依赖、构建脚本和 Linux 构建入口 ``` CMake 是 Windows 和 Linux 的统一构建入口。`CmvrControlStation.pro` 继续保留,用于现有 Windows Qt Creator/qmake 工作流。 ## Linux 编译 ### 1. 安装依赖 Debian/Ubuntu 示例: ```bash sudo apt update sudo apt install \ build-essential cmake ninja-build pkg-config \ qtbase5-dev qtmultimedia5-dev qt3d5-dev qt3d-assimpsceneimport-plugin \ libprotobuf-dev protobuf-compiler protobuf-compiler-grpc \ libgrpc++-dev \ libavcodec-dev libavutil-dev libswscale-dev \ liburdfdom-dev libtinyxml-dev libassimp-dev libgl1-mesa-dev ``` 不同发行版的包名可能不同,但需要提供以下 CMake/pkg-config 组件: - Qt 5.12 或更高版本:Core、Gui、Widgets、Multimedia、3DCore、3DRender、3DExtras、3DInput - Protobuf 和 `protoc` - gRPC C++ 和 `grpc_cpp_plugin` - FFmpeg:libavcodec、libavutil、libswscale - urdfdom、Assimp 和 OpenGL ### 2. 编译默认版本 Linux 默认关闭内置 MsQuic 服务,其余功能可正常编译: ```bash bash scripts/build_demo.sh Release ``` 等价的手动命令: ```bash cmake -S . -B build/linux-release -G Ninja \ -DCMAKE_BUILD_TYPE=Release \ -DCMVR_WITH_MSQUIC=OFF cmake --build build/linux-release --parallel ``` 输出程序: ```text bin/release/CmvrControlStation ``` Debug 构建: ```bash bash scripts/build_demo.sh Debug ``` ### 3. 启用 Linux MsQuic 安装包含 `msquic.h`、`msquic_posix.h` 和 `libmsquic.so` 的 Linux MsQuic 开发包,然后配置: ```bash cmake -S . -B build/linux-release -G Ninja \ -DCMAKE_BUILD_TYPE=Release \ -DCMVR_WITH_MSQUIC=ON \ -DCMVR_MSQUIC_ROOT=/opt/msquic cmake --build build/linux-release --parallel ``` 如果 MsQuic 安装在系统标准目录,可以省略 `CMVR_MSQUIC_ROOT`。运行时动态链接器必须能够找到 `libmsquic.so`。 QUIC 服务使用 PKCS#12 证书。将 `quic-test-server.pfx` 放入 `certs/` 后重新构建,CMake 会把它复制到程序目录。默认测试密码为 `cmvr-test`。 ### 4. 运行 ```bash ./bin/release/CmvrControlStation ``` 如果使用非系统 Qt 或其他自定义依赖前缀,通过 `CMAKE_PREFIX_PATH` 指定: ```bash cmake -S . -B build/linux-release -G Ninja \ -DCMAKE_BUILD_TYPE=Release \ -DCMAKE_PREFIX_PATH="/opt/qt5;/opt/grpc;/opt/urdfdom" ``` Qt Multimedia 在 Linux 上依赖系统音频/媒体后端;如果音频文件不能解码,请安装发行版提供的 GStreamer 插件。URDF 中的外部网格由 Qt3D Assimp scene parser 加载。 ## Windows 编译 Windows 仓库内的静态库使用固定 ABI: - Qt 5.12.4 MinGW 64-bit - MinGW 7.3 64-bit - gRPC 1.48.4 / Protobuf 3.19.5 - FFmpeg 4.4.5 - MsQuic 2.5.9 OpenSSL x64 - urdfdom 4.0.3 不要混用 MSVC、32 位 Qt 或其他 MinGW ABI。详细依赖说明见 [NATIVE_DEPS.md](NATIVE_DEPS.md)。 ### 1. 准备 Qt 和证书 默认目录: ```text C:\Qt\Qt5.12.4\5.12.4\mingw73_64 C:\Qt\Qt5.12.4\Tools\mingw730_64 ``` `certs/quic-test-server.pfx` 含有私钥,因此被 Git 忽略。可以从开发环境安全复制,或生成新的测试证书: ```powershell powershell -ExecutionPolicy Bypass ` -File .\scripts\install_msquic.ps1 ` -ServerIp 192.168.0.118 Copy-Item ` .\third_party\install\msquic\certs\quic-test-server.pfx ` .\certs\ Copy-Item ` .\third_party\install\msquic\certs\quic-test-ca.crt ` .\certs\ ` -Force ``` 将示例 IP 替换为运行控制站电脑的地址。 ### 2. 使用 CMake 编译 在 PowerShell 中: ```powershell $QtRoot = "C:\Qt\Qt5.12.4" $env:Path = "$QtRoot\5.12.4\mingw73_64\bin;$QtRoot\Tools\mingw730_64\bin;$env:Path" cmake -S . -B build\windows-release -G "MinGW Makefiles" ` -DCMAKE_BUILD_TYPE=Release ` -DCMAKE_PREFIX_PATH="$QtRoot\5.12.4\mingw73_64" ` -DCMVR_WITH_MSQUIC=ON cmake --build build\windows-release --parallel 4 ``` 输出程序: ```text bin\release\CmvrControlStation.exe ``` CMake 会复制仓库 `lib/` 中的运行时 DLL、现有证书和完整 `models/` 模型目录。制作独立安装包时,仍需执行 Qt 的 `windeployqt` 复制 Qt DLL 和插件。 ### 3. 使用现有 qmake 脚本 ```powershell powershell -ExecutionPolicy Bypass ` -File .\scripts\build_demo.ps1 ` -Configuration release ``` Debug: ```powershell powershell -ExecutionPolicy Bypass ` -File .\scripts\build_demo.ps1 ` -Configuration debug ``` 也可以在 Qt Creator 中打开 `CmvrControlStation.pro`,选择 `Desktop Qt 5.12.4 MinGW 64-bit` Kit,运行 qmake 后构建。 ## CMake 选项 | 选项 | Windows 默认值 | Linux 默认值 | 说明 | | --- | --- | --- | --- | | `CMVR_WITH_MSQUIC` | `ON` | `OFF` | 编译内置 QUIC 测试服务器 | | `CMVR_MSQUIC_ROOT` | 空 | 空 | Linux MsQuic 的安装前缀 | | `CMVR_CXX_RUNTIME` | 空 | 自动探测 | 非系统依赖前缀配套的 `libstdc++.so.6` | | `CMVR_ASSIMP_SCENE_PARSER` | 自动探测 | 自动探测 | Qt3D Assimp 场景解析插件文件;用于加载 STL、DAE 和 3DS 网格 | | `CMAKE_BUILD_TYPE` | `Release`(教程) | `Release`(教程) | `Debug` 或 `Release` | 未启用 MsQuic 时,QUIC 页面仍会显示,但启动服务会给出明确提示,不影响 gRPC、Demo、音视频和 URDF 功能。 ## 开发与排错 - CMake 配置找不到 Qt:设置 `CMAKE_PREFIX_PATH` 指向 Qt 安装前缀。 - 找不到 gRPC 插件:确认安装了 `grpc_cpp_plugin`,并且 gRPC CMake 包与运行库来自同一前缀。 - Proto 编译或链接版本错误:`protoc`、Protobuf 头文件和 Protobuf 库必须来自同一套安装。 - 出现 `GLIBCXX_* not found`:不要混用不兼容的编译器和 C++ 运行库。CMake 会优先链接 gRPC/Qt 前缀内配套的 `libstdc++.so.6`;特殊环境可通过 `-DCMVR_CXX_RUNTIME=/path/to/libstdc++.so.6` 显式指定。 - 只有 `演示 · demo_arm` 能显示,AUBO、Elfin、小研模型为空:`demo_arm` 仅使用 Qt3D 内置几何体,其他模型需要 Assimp 场景解析插件加载 STL、DAE 和 3DS 网格。在 Debian/Ubuntu 上执行 `sudo apt install qt3d-assimpsceneimport-plugin`,然后重新运行 CMake 和构建。 CMake 会检测插件并将其复制到程序目录的 `sceneparsers/`;如果使用自定义 Qt,可通过 `-DCMVR_ASSIMP_SCENE_PARSER=/path/to/libassimpsceneimport.so` 指定插件。 构建后应存在 `bin/release/sceneparsers/libassimpsceneimport.so`(Windows 对应 `assimpsceneimport.dll`)。如果插件存在但仍加载失败,查看应用日志中的 `Qt3D 无法加载网格` 信息,并确认插件与所用 Qt 版本及架构一致。 - Linux 没有声音:检查 Qt Multimedia 后端、系统音频服务和 GStreamer 插件。 - QUIC 无法启动:检查 MsQuic 动态库搜索路径、PFX 文件、密码、监听地址和防火墙。 Proto 约定和目录说明见 [protos/README.md](protos/README.md)。