增加校准通用代码
This commit is contained in:
@@ -0,0 +1,159 @@
|
||||
# XP.Calibration
|
||||
|
||||
平面 CT 系统几何校准库,基于 .NET 8 + Emgu.CV,从 C++ OpenCV 实现移植而来。
|
||||
|
||||
## 功能
|
||||
|
||||
提供两种校准方法:
|
||||
|
||||
- **中心校准 (CenterCalibration)** — 从投影序列检测球心轨迹,椭圆拟合后反算倾斜角和焦点投影偏移,适用于快速估算
|
||||
- **完整几何校准 (FullCalibration)** — 基于 TIGRE 投影模型(角点法),使用 Levenberg-Marquardt 优化器同时优化 5~9 个几何参数
|
||||
|
||||
## 项目结构
|
||||
|
||||
```
|
||||
XP.Calibration/
|
||||
├── Models/
|
||||
│ ├── CalibrationModels.cs # EllipseResult, GeoParams, CenterCalibrationResult
|
||||
│ ├── FullCalibrationResult.cs # 完整校准输出 (各参数 + RMS)
|
||||
│ └── FullCalibrationOptions.cs # 优化模式选项
|
||||
├── Core/
|
||||
│ ├── RawReader.cs # RAW float32 投影数据读取
|
||||
│ ├── BallDetector.cs # 球心检测 (自适应阈值+亚像素质心 / Canny+椭圆拟合)
|
||||
│ └── TigreProjection.cs # TIGRE 投影模型 (rollPitchYaw + eulerZYZ)
|
||||
├── CenterCalibration.cs # 中心校准
|
||||
└── FullCalibration.cs # 完整几何校准 (LM 优化)
|
||||
```
|
||||
|
||||
## 校准参数
|
||||
|
||||
完整几何校准支持三种模式:
|
||||
|
||||
| 模式 | 参数数 | 优化参数 |
|
||||
|------|--------|----------|
|
||||
| 基础 | 5 | ay, det_y, det_x, det_z, R |
|
||||
| +探测器偏移 | 7 | 基础 + offDetecU, offDetecV |
|
||||
| +距离 | 9 | 基础 + offDetecU, offDetecV + DSO, DSD |
|
||||
|
||||
参数含义:
|
||||
|
||||
| 参数 | 说明 | TIGRE 对应 |
|
||||
|------|------|-----------|
|
||||
| ay | 旋转轴倾斜角 | angles[:,1] |
|
||||
| det_x | 探测器 dYaw (Rx) | rotDetector[:,0] |
|
||||
| det_y | 探测器 dPitch (Ry) | rotDetector[:,1] |
|
||||
| det_z | 探测器 dRoll (Rz) | rotDetector[:,2] |
|
||||
| R | 物体偏移半径 | offOrigin[:,2] = -R |
|
||||
| offDetecU/V | 探测器平移偏移 | offDetector[:,0]/[:,1] |
|
||||
| DSO | 焦点到旋转中心距离 | geo.DSO |
|
||||
| DSD | 焦点到探测器距离 | geo.DSD |
|
||||
|
||||
## 使用示例
|
||||
|
||||
### 中心校准
|
||||
|
||||
```csharp
|
||||
var geo = new GeoParams
|
||||
{
|
||||
DSO = 200, DSD = 500, PixelSize = 0.6,
|
||||
NDetecU = 512, NDetecV = 512
|
||||
};
|
||||
|
||||
var calib = new CenterCalibration();
|
||||
var result = calib.CalibrateFromRaw("projections.raw", 512, 512, 360, geo);
|
||||
|
||||
Console.WriteLine($"倾斜角: {result.AlphaDeg:F2}°");
|
||||
Console.WriteLine($"R: {result.R_mm:F2} mm");
|
||||
Console.WriteLine($"焦点投影: ({result.FocalU:F2}, {result.FocalV:F2})");
|
||||
```
|
||||
|
||||
### 完整几何校准 (5 参数)
|
||||
|
||||
```csharp
|
||||
var geo = new GeoParams
|
||||
{
|
||||
DSO = 250, DSD = 450, PixelSize = 0.6,
|
||||
NDetecU = 512, NDetecV = 512
|
||||
};
|
||||
|
||||
var full = new FullCalibration();
|
||||
var result = full.CalibrateFromRaw("projections.raw", 512, 512, 360, geo);
|
||||
|
||||
Console.WriteLine($"ay: {result.AyDeg:F4}°");
|
||||
Console.WriteLine($"det_z: {result.DetZDeg:F4}°");
|
||||
Console.WriteLine($"R: {result.R_mm:F4} mm");
|
||||
Console.WriteLine($"RMS: {result.RmsPx:F6} px");
|
||||
```
|
||||
|
||||
### 完整几何校准 (9 参数)
|
||||
|
||||
```csharp
|
||||
var options = new FullCalibrationOptions
|
||||
{
|
||||
OptimizeDetectorOffset = true, // +offDetecU/V
|
||||
OptimizeDistances = true, // +DSO/DSD
|
||||
MaxIterations = 5000,
|
||||
Tolerance = 1e-16
|
||||
};
|
||||
|
||||
var full = new FullCalibration();
|
||||
// 可选: 监听优化进度
|
||||
full.OnProgress = (iter, rms, p) =>
|
||||
Console.WriteLine($"Iter {iter}: RMS={rms:F6} px");
|
||||
|
||||
var result = full.CalibrateFromRaw("projections.raw", 512, 512, 360, geo, options);
|
||||
```
|
||||
|
||||
### 直接传入 Mat 列表
|
||||
|
||||
如果投影数据已经在内存中(比如从相机采集),可以直接传 `List<Mat>`:
|
||||
|
||||
```csharp
|
||||
List<Mat> projections = ...; // 已有的 CV_32F Mat 列表
|
||||
var result = new FullCalibration().Calibrate(projections, geo, options);
|
||||
```
|
||||
|
||||
### 切换球心检测方法
|
||||
|
||||
默认使用自适应阈值 + 亚像素质心法。如需使用 Canny + 椭圆拟合法:
|
||||
|
||||
```csharp
|
||||
// 关闭亚像素质心,改用矩心
|
||||
BallDetector.EnableSubPixel = false;
|
||||
|
||||
// 或直接调用椭圆拟合检测
|
||||
BallDetector.DetectCenterByEllipse(mat, out var center);
|
||||
```
|
||||
|
||||
## 算法说明
|
||||
|
||||
### 球心检测流程
|
||||
|
||||
1. 归一化 float32 → 8bit
|
||||
2. 高斯模糊 (3×3, σ=0.8)
|
||||
3. 自适应阈值二值化 (blockSize=31, C=-5)
|
||||
4. 查找最大轮廓
|
||||
5. 亚像素质心 (强度加权) 或矩心
|
||||
|
||||
### TIGRE 投影模型
|
||||
|
||||
完全按照 TIGRE `computeDeltas_Siddon` 流程实现:
|
||||
|
||||
1. 初始化探测器角点 (P, Pu0, Pv0) 和射线源 S
|
||||
2. `rollPitchYaw` — 探测器自身旋转 (det_x, det_y, det_z)
|
||||
3. 探测器偏移 (offDetecU/V)
|
||||
4. `eulerZYZ` — 扫描旋转 (scanAngle, ay)
|
||||
5. 物体偏移 (offOrigX = -R)
|
||||
6. 射线-平面交点 → 像素坐标
|
||||
|
||||
### LM 优化器
|
||||
|
||||
- 数值差分雅可比矩阵 (中心差分, ε=1e-7)
|
||||
- Cholesky 分解求解法方程
|
||||
- 自适应阻尼因子 (成功 ×0.3, 失败 ×10)
|
||||
- 参数边界约束 (clamp)
|
||||
|
||||
## 依赖
|
||||
|
||||
- .NET 8.0-windows
|
||||
- Emgu.CV 4.10.0.5680
|
||||
Reference in New Issue
Block a user