<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="zh-Hans-CN">
	<id>https://wiki2.lessokaji.com/index.php?action=history&amp;feed=atom&amp;title=TightCoupler%E5%A4%96%E9%83%A8%E5%8F%8D%E9%A6%88API</id>
	<title>TightCoupler外部反馈API - 版本历史</title>
	<link rel="self" type="application/atom+xml" href="https://wiki2.lessokaji.com/index.php?action=history&amp;feed=atom&amp;title=TightCoupler%E5%A4%96%E9%83%A8%E5%8F%8D%E9%A6%88API"/>
	<link rel="alternate" type="text/html" href="https://wiki2.lessokaji.com/index.php?title=TightCoupler%E5%A4%96%E9%83%A8%E5%8F%8D%E9%A6%88API&amp;action=history"/>
	<updated>2026-05-16T17:53:31Z</updated>
	<subtitle>本wiki上该页面的版本历史</subtitle>
	<generator>MediaWiki 1.40.0</generator>
	<entry>
		<id>https://wiki2.lessokaji.com/index.php?title=TightCoupler%E5%A4%96%E9%83%A8%E5%8F%8D%E9%A6%88API&amp;diff=1045&amp;oldid=prev</id>
		<title>Artheru：​Initial bilingual draft (auto-published)</title>
		<link rel="alternate" type="text/html" href="https://wiki2.lessokaji.com/index.php?title=TightCoupler%E5%A4%96%E9%83%A8%E5%8F%8D%E9%A6%88API&amp;diff=1045&amp;oldid=prev"/>
		<updated>2026-05-16T14:00:26Z</updated>

		<summary type="html">&lt;p&gt;Initial bilingual draft (auto-published)&lt;/p&gt;
&lt;p&gt;&lt;b&gt;新页面&lt;/b&gt;&lt;/p&gt;&lt;div&gt;&amp;lt;languages/&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== 概述 / Overview ==&lt;br /&gt;
`TightCoupler` 是 Detour 的 ''多源位姿融合器''。非 SLAM 来源的位姿（轮编里程计 / IMU / RTK / UWB / 第三方视觉等）通过 `PostExternalFeed` API 推入 TightCoupler，与激光 / 地纹 / 二维码等 SLAM 后端一起做紧耦合优化，输出统一的 6-DoF 位姿。&lt;br /&gt;
&lt;br /&gt;
`TightCoupler` is Detour's '''multi-source pose fuser'''. Non-SLAM poses (wheel odometry / IMU / RTK / UWB / third-party vision) enter through the `PostExternalFeed` API. They join the SLAM backends (laser / ground-texture / QR) in a tightly-coupled optimisation that emits the unified 6-DoF pose.&lt;br /&gt;
&lt;br /&gt;
实现：`D:\src\Detour\DetourCore\Algorithms\TightCoupler.ExternalCoupler.cs:14`。&lt;br /&gt;
Implementation: `D:\src\Detour\DetourCore\Algorithms\TightCoupler.ExternalCoupler.cs:14`.&lt;br /&gt;
&lt;br /&gt;
整体设计见 [[Special:MyLanguage/多定位源的自动综合|多定位源的自动综合]]。&lt;br /&gt;
For the design rationale see [[Special:MyLanguage/多定位源的自动综合|multi-source positioning fusion]].&lt;br /&gt;
&lt;br /&gt;
== API 签名 / API signature ==&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;csharp&amp;quot;&amp;gt;&lt;br /&gt;
public static void PostExternalFeed(ExternalFeed obj, string name);&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
每次调用提交 ''一帧''的外部位姿观测。`name` 是 ''来源标识''（如 `&amp;quot;WheelImu&amp;quot;` / `&amp;quot;RTK&amp;quot;`），用来在融合器内部跟踪不同来源的协方差、检查超时、重映射。&lt;br /&gt;
&lt;br /&gt;
Each call submits ''one frame'' of an external pose observation. `name` identifies the source (e.g. `&amp;quot;WheelImu&amp;quot;`, `&amp;quot;RTK&amp;quot;`) so the fuser can track per-source covariance, detect silence, and remap as needed.&lt;br /&gt;
&lt;br /&gt;
== `ExternalFeed` 结构体 / Struct ==&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;csharp&amp;quot;&amp;gt;&lt;br /&gt;
public struct ExternalFeed&lt;br /&gt;
{&lt;br /&gt;
    public string name;&lt;br /&gt;
    public long   counter;&lt;br /&gt;
    public bool   hasTranslation;&lt;br /&gt;
    public bool   hasRotation;&lt;br /&gt;
    public bool   is3D;&lt;br /&gt;
    public bool   is2D;&lt;br /&gt;
    public bool   integrated;&lt;br /&gt;
    public bool   toRemap;&lt;br /&gt;
    public long   startingTick;&lt;br /&gt;
    public float  x, y, z, th, pitch, roll;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
字段语义 / Field semantics:&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
! 字段 / Field !! 含义 / Meaning&lt;br /&gt;
|-&lt;br /&gt;
| `name` || 来源名（同上）；融合器按此聚类&lt;br /&gt;
|-&lt;br /&gt;
| `counter` || 单调递增；用来检测丢帧 / out-of-order&lt;br /&gt;
|-&lt;br /&gt;
| `hasTranslation` || 该观测包含位置（x, y, [z]）/ includes translation&lt;br /&gt;
|-&lt;br /&gt;
| `hasRotation` || 该观测包含朝向（th, pitch, roll）/ includes rotation&lt;br /&gt;
|-&lt;br /&gt;
| `is2D` / `is3D` || 二选一；表示是平面运动还是 3D 6-DoF&lt;br /&gt;
|-&lt;br /&gt;
| `integrated` || true = 累积量（相对位姿）；false = 单帧绝对量 / cumulative vs single-frame&lt;br /&gt;
|-&lt;br /&gt;
| `toRemap` || true = 绝对参考系（如 RTK），融合时需要全局重映射 / absolute frame, needs global remap&lt;br /&gt;
|-&lt;br /&gt;
| `startingTick` || 累积量的基准 tick；用来检测重置（如 IMU 重启）&lt;br /&gt;
|-&lt;br /&gt;
| `x, y, z, th, pitch, roll` || 实际位姿（mm / rad）&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
== 典型来源配置 / Canonical source configurations ==&lt;br /&gt;
`TightCoupler.ExternalCoupler.cs:49-54` 中的注释列出了典型用法：&lt;br /&gt;
The source comment lists canonical configurations:&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
! 来源 / Source !! 标志组合 / Flags&lt;br /&gt;
|-&lt;br /&gt;
| 轮编 + IMU / Wheel + IMU || `hasTranslation | hasRotation | is2D | integrated | startingTick`&lt;br /&gt;
|-&lt;br /&gt;
| 仅 IMU / IMU only || `hasRotation | (is2D 或 is3D) | integrated`&lt;br /&gt;
|-&lt;br /&gt;
| RTK GNSS || `hasTranslation | toRemap`（绝对，需重映射）&lt;br /&gt;
|-&lt;br /&gt;
| UWB / 基站 / Beacon || `hasTranslation | is2D`（绝对二维位置）&lt;br /&gt;
|-&lt;br /&gt;
| 第三方视觉 / 3rd-party vision || 视具体输出而定&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
== 提交模板 / Submission template ==&lt;br /&gt;
轮编 + IMU 紧耦合 ：&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;csharp&amp;quot;&amp;gt;&lt;br /&gt;
using DetourCore.Algorithms;&lt;br /&gt;
&lt;br /&gt;
TightCoupler.PostExternalFeed(new ExternalFeed&lt;br /&gt;
{&lt;br /&gt;
    name           = &amp;quot;wheel_imu&amp;quot;,&lt;br /&gt;
    counter        = tick++,&lt;br /&gt;
    hasTranslation = true,&lt;br /&gt;
    hasRotation    = true,&lt;br /&gt;
    is2D           = true,&lt;br /&gt;
    integrated     = true,&lt;br /&gt;
    startingTick   = baselineTick,&lt;br /&gt;
    x  = odomX,&lt;br /&gt;
    y  = odomY,&lt;br /&gt;
    th = odomTh&lt;br /&gt;
}, name: &amp;quot;WheelImu&amp;quot;);&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
RTK ：&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;csharp&amp;quot;&amp;gt;&lt;br /&gt;
TightCoupler.PostExternalFeed(new ExternalFeed&lt;br /&gt;
{&lt;br /&gt;
    name           = &amp;quot;rtk&amp;quot;,&lt;br /&gt;
    counter        = gpsTick++,&lt;br /&gt;
    hasTranslation = true,&lt;br /&gt;
    is2D           = true,&lt;br /&gt;
    integrated     = false,&lt;br /&gt;
    toRemap        = true,&lt;br /&gt;
    x = rtkEastingMm,&lt;br /&gt;
    y = rtkNorthingMm&lt;br /&gt;
}, name: &amp;quot;RTK&amp;quot;);&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== 协方差与权重 / Covariance &amp;amp; weighting ==&lt;br /&gt;
TightCoupler 内部按 ''协方差矩阵的逆''加权 —— 不需要插件作者设权重；插件 ''必须诚实''地报协方差。错报协方差是融合崩坏的 ''首要''原因 ：一个谎报&amp;quot;我超准&amp;quot;的源会 ''统治''融合结果。&lt;br /&gt;
&lt;br /&gt;
TightCoupler weights by the inverse of the covariance matrix — no manual weight tuning needed; sources must ''honestly'' report covariance. Mis-reporting is the #1 cause of fusion blowups.&lt;br /&gt;
&lt;br /&gt;
来源 ：&lt;br /&gt;
* SLAM 后端：Hessian 求逆&lt;br /&gt;
* 二维码 PnP：重投影残差&lt;br /&gt;
* IMU / 里程计：硬件规格 + 时间间隔&lt;br /&gt;
* RTK：GNSS DOP&lt;br /&gt;
&lt;br /&gt;
== 异常路径 / Failure paths ==&lt;br /&gt;
* '''源静默 / Silence''': 超过 ''timeout''（融合器配置） → 该源从下一帧位姿图中删除，其它源不受影响。&lt;br /&gt;
* '''跳变 / Wild jump''': TightCoupler 内置 ''卡方检验''；&amp;gt; 5σ 的观测直接丢弃。&lt;br /&gt;
* '''融合发散 / Divergence''': 残差持续上升 → 触发 ''软重启''（保留主导源，重置其它源的位姿先验）。&lt;br /&gt;
&lt;br /&gt;
== 调试 / Debug ==&lt;br /&gt;
Detour UI 的&amp;quot;融合面板&amp;quot; 显示 ：&lt;br /&gt;
* 每个源的最新观测时刻 + 协方差&lt;br /&gt;
* 当前主导源&lt;br /&gt;
* 残差直方图&lt;br /&gt;
&lt;br /&gt;
打开 ''单源调试模式''可强制只用一个源（用于诊断单源故障）。&lt;br /&gt;
There's a &amp;quot;single-source debug mode&amp;quot; forcing the fusion to use only one source.&lt;br /&gt;
&lt;br /&gt;
== 与雷达 Lidar 插件的区别 / vs lidar plugins ==&lt;br /&gt;
雷达数据 ''不走''此 API：&lt;br /&gt;
* 雷达插件 `output()` 把帧推到 ''DObject''；&lt;br /&gt;
* Detour 端 `Lidar2D.ReadLidar()` 订阅该 DObject，把 SLAM 观测加到内部位姿图。&lt;br /&gt;
&lt;br /&gt;
只有 ''非传感器''的位姿来源走 `PostExternalFeed`。&lt;br /&gt;
&lt;br /&gt;
Lidar data does NOT go through this API. Lidar plugins `output()` to DObject; Detour subscribes via `Lidar2D.ReadLidar()`. Only ''non-sensor'' pose sources go through `PostExternalFeed`.&lt;br /&gt;
&lt;br /&gt;
== 相关页面 / See also ==&lt;br /&gt;
* [[Special:MyLanguage/多定位源的自动综合|多定位源的自动综合]]&lt;br /&gt;
* [[Special:MyLanguage/Detour软件架构|Detour软件架构]]&lt;br /&gt;
* [[Special:MyLanguage/Detour激光SLAM算法详解|Detour激光SLAM算法详解]]&lt;br /&gt;
* [[Special:MyLanguage/输入GPS外部定位|输入GPS外部定位]]&lt;br /&gt;
* [[Special:MyLanguage/使用手册 - 同时使用激光、地纹、二维码、轮编里程计和IMU进行鲁棒定位|同时使用激光、地纹、二维码、轮编里程计和IMU进行鲁棒定位]]&lt;br /&gt;
&lt;br /&gt;
[[Category:二次开发相关说明]]&lt;br /&gt;
[[Category:定位导航相关手册]]&lt;/div&gt;</summary>
		<author><name>Artheru</name></author>
	</entry>
</feed>