Add Clumsy plugins and dual-vehicle fleet sync demo.
Restructure into DiffWheel/MultiWheel folders, add DiffWheelC and MultiWheelC with MovementTests, FleetRemote multi-vehicle manual sync, deploy templates, and documentation. Update dependency paths to D:\MDCS\Release and mirror motor feedback in MotorRoutine for simulation. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -0,0 +1,103 @@
|
||||
# 多车联动(MultiVehicleSync)算法原理
|
||||
|
||||
本文说明 **MDCSToolBox** 中 N 车联动的架构与几何原理。Tutorial `MultiWheelC` 与产品 `StandardMultiWheelLifterC` 均继承 `MultiWheelPilotDefinition`,调用 `InitMultiVehicleCoordination()` 启用同步。
|
||||
|
||||
## 1. 总体架构
|
||||
|
||||
每台 AGV 运行 **Detour + Medulla (M) + Clumsy (C)**:
|
||||
|
||||
| 实例 | Detour `shareObjectTag` | Medulla/Clumsy `soTag` | Clumsy 角色 | `MultiVehicleMasterEndpoint` | Clumsy `port` | Detour HTTP | `CarNum` |
|
||||
|------|-------------------------|------------------------|-------------|------------------------------|---------------|-------------|----------|
|
||||
| AGV1 | `Multi1` | `Multi1` | 主车 master | `/` | 8008 | 4321 | 1 |
|
||||
| AGV2 | `Multi2` | `Multi2` | 从车 slave | `127.0.0.1:8008` | 8009 | 4421 | 2 |
|
||||
|
||||
Medulla web API(与 Clumsy 车队同步端口无关):AGV1 **8007**,AGV2 **8108**(单机部署时 Medulla #2 不可占用 8008,该端口留给 Clumsy 主车)。
|
||||
|
||||
**同机隔离(Core 层)**
|
||||
|
||||
- Detour 写入 `DObject("DetourPos{shareObjectTag}")`;Clumsy 读取 `DObject("DetourPos{soTag}")`,tag 必须一致。
|
||||
- Clumsy 通过 `detourHost`/`detourPort`(`clumsyconsole.json` 或 `clumsy.json`)访问对应 Detour HTTP 端口(4321/4421)。
|
||||
- 每台 Clumsy 绑定独立 `WebAPI.port`(8008/8009),register/notify 使用 `VehicleSyncInfo.Port` 寻址。
|
||||
|
||||
M 与 C 通过 `CartActivator` 共享 DObject(`MedullaCartUpperIO{tag}`),不直接 DLL 调用。
|
||||
|
||||
```text
|
||||
从车 --GET /multi-vehicle-register--> 主车:8008 (上报本车位姿、layout、Port)
|
||||
主车 --GET /multi-vehicle-notify----> 从车:8009 (广播车队中心、fleet 命令、完整 fleet 状态)
|
||||
```
|
||||
|
||||
## 2. 数据模型
|
||||
|
||||
定义于 `MDCSToolBox/Clumsy/Pilot/MultiWheel/VehicleSyncModels.cs`。
|
||||
|
||||
### 2.1 VehicleSyncInfo(从车 → 主车)
|
||||
|
||||
| 字段 | 含义 |
|
||||
|------|------|
|
||||
| `Master` | 是否主车 |
|
||||
| `Ip` / `Port` | 本车同步端点(notify 寻址) |
|
||||
| `PosAvailable` | 本车 Detour/SLAM 是否有效 |
|
||||
| `X/Y/Th` | 本车世界位姿(mm, deg) |
|
||||
| `LayoutX/Y/Th` | 本车在车队坐标系下的 **固定 slot** |
|
||||
| `Aligned` | 本车互识别/精度是否满足(见 §4) |
|
||||
|
||||
### 2.2 VehicleSyncNotification(主车 → 从车)
|
||||
|
||||
除原 fleet 命令外,主车广播 `CenterX/Y/Th`(世界系车队中心)、`SyncTh/SyncDistance`、完整 `Fleet` 快照等。
|
||||
|
||||
## 3. 编队几何与车队中心
|
||||
|
||||
### 3.1 编队布局(双车)
|
||||
|
||||
布局由 `TestCarSyncDistance` 与 `TestCarSyncTh` 唯一确定(不再有独立 slot 表):每车相对车队中心沿编队方向对称分布于 ±`TestCarSyncDistance/2`,从车朝向额外翻转 180°。实现见 `GetLayoutPose`。`TestCarSyncDistance` 同时是检测环(`detectDistance = TestCarSyncDistance - DeltaDetectCenter`)与 SLAM 位姿环的唯一间距来源,二者据此自洽。
|
||||
|
||||
### 3.2 车队中心反推(非位姿平均)
|
||||
|
||||
世界系中心 **不是** 对各车 X/Y/Th 取平均,而是由 **当前 `PosAvailable==true` 的车** 按固定 slot 反推:
|
||||
|
||||
```text
|
||||
Transform2D(fleetCenter, layoutSlot) = carWorldPose
|
||||
⇒ fleetCenter = Transform2D(carWorld, -layoutSlot) // 实现见 InferFleetCenterFromCar
|
||||
```
|
||||
|
||||
- 多台有效车:对各车反推的中心取平均(理论上应一致,差异可作互检)。
|
||||
- 零台有效车:无世界系中心 → **手动模式**仍可通过互识别保持编队;**自动模式**门控拒绝(见 §5)。
|
||||
|
||||
## 4. 互识别接口(插件实现)
|
||||
|
||||
基类 `MultiWheelPilotDefinition` 提供虚方法:
|
||||
|
||||
```csharp
|
||||
protected virtual (bool Valid, float Dx, float Dy, float Dth) DetectNeighborBias(float detectDistance);
|
||||
```
|
||||
|
||||
- 基类:`MultiVehicleUseDetect` 门控 → 计算 `Aligned` → `SendMotion(localCompensate*)`。
|
||||
- **具体检测**(雷达名、两腿/反光板等)由车体插件重写。
|
||||
- 产品:`StandardMultiWheelLifterC` → `VehicleMoverHelper.GetSyncBias`
|
||||
- Tutorial:默认 `Valid=false`(无检测硬件时可纯靠手动+SLAM)
|
||||
|
||||
## 5. 手动 / 自动门控
|
||||
|
||||
| 模式 | 条件 |
|
||||
|------|------|
|
||||
| 手动 | 始终可用;可无 Detour,靠 `DetectNeighborBias` 纠正 |
|
||||
| 自动 | 主车要求 fleet 中 **至少 1 台** `PosAvailable`;否则 toast 拒绝并清零 `MultiVehicleAutoEnabled` |
|
||||
|
||||
## 6. 主循环(默认 50ms)
|
||||
|
||||
逻辑位于 `MultiWheelPilotDefinition.MultiVehicle.cs` 的 `TickMultiVehicle`:
|
||||
|
||||
1. 判断 master/slave、手动/自动是否启用
|
||||
2. 读取本车 SLAM(若 `PosAvailable`)
|
||||
3. 主车:计算 fleet 命令;从 notification 同步
|
||||
4. `GetLayoutPose` → 本车布局位姿(由 `TestCarSyncDistance`/`TestCarSyncTh` 推导)
|
||||
5. `DetectNeighborBias`(可选)→ 互识别补偿
|
||||
6. 有有效中心时 SLAM `posBias` 补偿
|
||||
7. `SendMotion(fleetVx, FrontTh, RearTh, localCompensate*)`
|
||||
8. master:register 汇总 + notify 各从车(按 `Ip:Port`,跳过自身 `CarNum`)
|
||||
|
||||
## 7. 配置文件
|
||||
|
||||
见 [RunAndDeploy.md](./RunAndDeploy.md):`clumsyconsole.json`(soTag/port/detour)、`clumsy.json`(msConf slot/主车端点)、`detour.json`(shareObjectTag/DetourPort)。
|
||||
|
||||
修复与迁移记录见 [BugFixes.md](./BugFixes.md)。
|
||||
Reference in New Issue
Block a user