feat: 升级算法包 delivery_v1.1 → v1.2,新增任务级 CAD 与测距面板
- 算法包替换为 delivery_v1.2(coupler_panel 新增 autotune/layer_select,underframe_deflection 新增 single_beam 管线),删除 delivery_v1.1 - manifests/adapters 的 PYTHONPATH 与版本说明同步更新到 v1.2 - 新增任务级 CAD 文件支持(task_cad_files 表、上传/读取路由、TaskManager 全选与加载显示) - 新增 train-measurement 自定义前端面板(YAML 编辑器 + 可视化 ROI 配置 + 3D 取点) - PointCloudViewer 支持 PLY 叠加层渲染与 ROI 拾取 - Dockerfile 改用 Miniforge 安装 pythonocc-core,修复 libgomp/libstdc++ 依赖
This commit is contained in:
145
alg/delivery_v1.2/coupler_panel_release/configs/default.yaml
Normal file
145
alg/delivery_v1.2/coupler_panel_release/configs/default.yaml
Normal file
@@ -0,0 +1,145 @@
|
||||
# Default configuration for coupler panel measurement pipeline.
|
||||
# All numeric units in mm / degree unless otherwise stated.
|
||||
# Override fields by passing a dict or a YAML path with the same nested shape.
|
||||
|
||||
schema_version: "1.0"
|
||||
|
||||
# --- CAD parsing & GT extraction --------------------------------------------
|
||||
cad:
|
||||
# OpenCASCADE tessellation quality.
|
||||
linear_deflection_mm: 0.5
|
||||
angular_deflection_rad: 0.1
|
||||
# Hole topology classification.
|
||||
# The four locating holes are expected to be small and equal-radius;
|
||||
# the central pass-through hole is expected to be much larger.
|
||||
locating_hole_radius_mm: [4.0, 12.0] # [min, max] of expected locating hole radius
|
||||
central_hole_radius_min_mm: 20.0 # any circle larger than this is treated as the centre hole
|
||||
rectangle_aspect_tol: 0.15 # tolerance for "the 4 hole centres form a rectangle"
|
||||
|
||||
# --- Sampling ---------------------------------------------------------------
|
||||
sampling:
|
||||
method: poisson_disk # uniform_area | poisson_disk | adaptive | grid_spacing
|
||||
# Use either spacing_mm OR num_points; if both set, spacing_mm wins.
|
||||
spacing_mm: 1.0
|
||||
num_points: 100000
|
||||
seed: 42
|
||||
adaptive:
|
||||
curvature_weight: 1.0
|
||||
min_spacing_factor: 0.25 # smallest spacing = spacing_mm * factor
|
||||
max_spacing_factor: 4.0
|
||||
|
||||
# --- Simulated scan (optional) ----------------------------------------------
|
||||
scan_simulator:
|
||||
enabled: false
|
||||
view_origin: [10000.0, 0.0, 0.0] # camera position in CAD frame, mm
|
||||
hpr_radius_mm: 50000.0 # hidden-point-removal radius
|
||||
|
||||
# --- Panel deflection injection (the SIGNAL the algorithm should measure) --
|
||||
# This rotates the panel (and its 4 locating holes) by a known small angle.
|
||||
# After running the pipeline, theta_right_deg / theta_ref_deg in the result
|
||||
# should match these values within the algorithm's recovery accuracy.
|
||||
panel_deflection:
|
||||
enabled: false
|
||||
theta_right_deg: 0.0 # atan2(n_y, n_x) target (rotation around z)
|
||||
theta_ref_deg: 0.0 # atan2(n_z, n_x) target (rotation around -y)
|
||||
|
||||
# --- Synthetic noise --------------------------------------------------------
|
||||
# Realistic LIDAR / structured-light noise on a ~2 m × 2 m panel is ≈ 50-80
|
||||
# µm = 0.05-0.08 mm. Larger sigma is mostly to test robustness, not to
|
||||
# match a real sensor.
|
||||
noise:
|
||||
enabled: true
|
||||
sigma_mm: 0.05
|
||||
mode: isotropic # isotropic | along_normal
|
||||
seed: 43
|
||||
|
||||
# --- Synthetic scan-pose perturbation ---------------------------------------
|
||||
# Mounting / scanner-stage jitter. 4-hole Kabsch should cancel this; if it
|
||||
# leaks into the final angles that's a registration error, not a measurement
|
||||
# of panel deflection. Set rotation_deg=0, translation_mm=0 for "ideal pose"
|
||||
# experiments that isolate the deflection-recovery accuracy.
|
||||
transform:
|
||||
enabled: true
|
||||
rotation_deg: 0.5 # magnitude; axis is randomised
|
||||
rotation_axis: random # random | x | y | z | [ax, ay, az]
|
||||
translation_mm: 2.0 # magnitude; direction is randomised
|
||||
translation_dir: random
|
||||
seed: 44
|
||||
|
||||
# --- Denoise pipeline -------------------------------------------------------
|
||||
# Steps are executed in the listed order. Set steps to [] to disable.
|
||||
denoise:
|
||||
steps:
|
||||
- type: passthrough
|
||||
bbox_padding_mm: 50.0
|
||||
- type: voxel
|
||||
voxel_mm: 0.5
|
||||
- type: statistical
|
||||
nb_neighbors: 30
|
||||
std_ratio: 2.0
|
||||
- type: radius
|
||||
nb_points: 8
|
||||
radius_mm: 2.0
|
||||
# Optional MLS smoothing (requires open3d ≥ 0.18 with ml extras).
|
||||
smoothing:
|
||||
enabled: false
|
||||
search_radius_mm: 2.0
|
||||
polynomial_order: 2
|
||||
|
||||
# --- Registration -----------------------------------------------------------
|
||||
registration:
|
||||
method: kabsch_four_holes # only this method is implemented; documented & enforced
|
||||
# The four GT hole centres come from CAD; the four scan hole centres come
|
||||
# from the detection module. Pairing is by greedy nearest-neighbour after
|
||||
# a coarse PCA-based pre-alignment of the centroid.
|
||||
pre_align: pca_centroid
|
||||
refuse_if_residual_above_mm: 5.0 # quality flag if RMS pairing residual exceeds this
|
||||
|
||||
# --- 4-hole detection in point cloud ----------------------------------------
|
||||
detection:
|
||||
# Local panel-plane projection.
|
||||
panel_normal_seed: from_cad # from_cad | pca | given
|
||||
panel_normal_pca_kth: 1 # use k-th smallest PCA eigenvector as panel normal
|
||||
# 2D occupancy grid.
|
||||
grid_pixel_mm: 0.5
|
||||
panel_min_area_ratio: 0.4 # largest connected component must be ≥ this fraction of bbox
|
||||
hole_min_area_mm2: 30.0
|
||||
hole_max_area_mm2: 800.0
|
||||
# Circle fitting on hole boundary.
|
||||
circle_fit:
|
||||
method: algebraic_then_lsq # algebraic_then_lsq | hyper | taubin
|
||||
inlier_residual_mm: 0.5
|
||||
# Selection.
|
||||
select_top_k_by_radius_match: 4
|
||||
rectangle_aspect_tol: 0.20
|
||||
|
||||
# --- Panel ROI extraction ---------------------------------------------------
|
||||
roi:
|
||||
hole_dilate_mm: 3.0 # exclude points within (hole_radius + dilate)
|
||||
central_hole_dilate_mm: 5.0
|
||||
edge_buffer_mm: 5.0 # shrink ROI rectangle inward by this
|
||||
chamfer_normal_dot_min: 0.85 # exclude points whose normal deviates more than acos(0.85) from panel normal
|
||||
outlier_z_score: 3.0
|
||||
|
||||
# --- Plane fit --------------------------------------------------------------
|
||||
plane_fit:
|
||||
method: ransac_svd
|
||||
ransac_iterations: 200
|
||||
ransac_inlier_thresh_mm: auto # auto = 3*sigma_mm
|
||||
min_inlier_ratio: 0.6
|
||||
enforce_nx_positive: true
|
||||
|
||||
# --- Metrics ----------------------------------------------------------------
|
||||
metrics:
|
||||
# If your right axis is +y, leave this 1. If right is -y, set to -1.
|
||||
right_axis_sign: 1
|
||||
# Angles smaller than this are clamped to 0 (purely cosmetic; raw value is
|
||||
# always in the report).
|
||||
angle_clamp_deg: 0.0
|
||||
|
||||
# --- Output / artifacts -----------------------------------------------------
|
||||
artifacts:
|
||||
save_intermediate: true
|
||||
ply_format: binary # binary | ascii
|
||||
image_dpi: 150
|
||||
heatmap_colormap: viridis
|
||||
@@ -0,0 +1,17 @@
|
||||
# Profile: high-density scan (≈100w points, sub-mm spacing).
|
||||
sampling:
|
||||
spacing_mm: 0.25
|
||||
num_points: 1000000
|
||||
denoise:
|
||||
steps:
|
||||
- type: passthrough
|
||||
bbox_padding_mm: 50.0
|
||||
- type: voxel
|
||||
voxel_mm: 0.25
|
||||
- type: statistical
|
||||
nb_neighbors: 50
|
||||
std_ratio: 2.0
|
||||
detection:
|
||||
grid_pixel_mm: 0.25
|
||||
plane_fit:
|
||||
ransac_iterations: 500
|
||||
@@ -0,0 +1,18 @@
|
||||
# Profile: low-density scan (≈1w points, ≈2 mm spacing).
|
||||
sampling:
|
||||
spacing_mm: 2.0
|
||||
num_points: 10000
|
||||
denoise:
|
||||
steps:
|
||||
- type: passthrough
|
||||
bbox_padding_mm: 50.0
|
||||
- type: voxel
|
||||
voxel_mm: 1.0
|
||||
- type: statistical
|
||||
nb_neighbors: 15
|
||||
std_ratio: 2.5
|
||||
detection:
|
||||
grid_pixel_mm: 1.0
|
||||
hole_min_area_mm2: 20.0
|
||||
plane_fit:
|
||||
ransac_iterations: 100
|
||||
@@ -0,0 +1,106 @@
|
||||
# Profile tuned for the lu1-M000004835653_AF4_ASMP072708187_N_AF4.stp panel.
|
||||
#
|
||||
# Topology summary (from cad/iter_circular_edges):
|
||||
# - locating holes: r = 16 mm × 4 corners at (y=±100, z=±180)
|
||||
# - central hole: r = 100 mm at (y≈1, z=0)
|
||||
# - panel size: ~200 × 360 mm in y-z, ~76 mm thick along x
|
||||
#
|
||||
# Use:
|
||||
# coupler-measure --stp <path> --out-dir <dir> --profile lu1_af4
|
||||
|
||||
cad:
|
||||
linear_deflection_mm: 0.5
|
||||
angular_deflection_rad: 0.1
|
||||
# CAD-side: strict band that selects only the r=16 mm corner holes.
|
||||
locating_hole_radius_mm: [14.0, 18.0]
|
||||
central_hole_radius_min_mm: 80.0
|
||||
rectangle_aspect_tol: 0.30
|
||||
|
||||
sampling:
|
||||
method: poisson_disk
|
||||
spacing_mm: null
|
||||
num_points: 500000
|
||||
seed: 42
|
||||
|
||||
# Critical: simulate a single-view "+x looking at -x" scan. Without this,
|
||||
# back-face points project into the hole regions and detection fails.
|
||||
scan_simulator:
|
||||
enabled: true
|
||||
view_origin: [10000.0, 0.0, 0.0]
|
||||
hpr_radius_mm: 200000.0
|
||||
|
||||
# --- Panel deflection injection -------------------------------------------
|
||||
# This is the *signal* we want the algorithm to recover. By default it is
|
||||
# off — sweeps override these.
|
||||
panel_deflection:
|
||||
enabled: true
|
||||
theta_right_deg: 0.5 # rotation around z so n_y > 0
|
||||
theta_ref_deg: 0.3 # rotation around -y so n_z > 0
|
||||
|
||||
# --- Realistic LiDAR / structured-light noise -----------------------------
|
||||
noise:
|
||||
enabled: true
|
||||
sigma_mm: 0.05 # ≈ 50 µm; matches typical industrial scanners
|
||||
mode: isotropic
|
||||
seed: 43
|
||||
|
||||
# --- Scanner-pose jitter --------------------------------------------------
|
||||
# Modest values: 4-hole Kabsch should remove this completely.
|
||||
transform:
|
||||
enabled: true
|
||||
rotation_deg: 0.5
|
||||
translation_mm: 2.0
|
||||
rotation_axis: random
|
||||
translation_dir: random
|
||||
seed: 44
|
||||
|
||||
denoise:
|
||||
steps:
|
||||
- type: passthrough
|
||||
bbox_padding_mm: 50.0
|
||||
- type: voxel
|
||||
voxel_mm: 0.5 # finer voxel for low-noise data
|
||||
- type: statistical
|
||||
nb_neighbors: 20
|
||||
std_ratio: 2.5
|
||||
|
||||
detection:
|
||||
panel_normal_seed: pca # critical: use cloud's own PCA, not CAD seed
|
||||
grid_pixel_mm: 2.0
|
||||
closing_iters: 0
|
||||
fill_bg_below_mm2: 100.0
|
||||
panel_min_area_ratio: 0.15
|
||||
hole_min_area_mm2: 600.0
|
||||
hole_max_area_mm2: 5000.0
|
||||
locating_hole_radius_mm: [14.0, 22.0]
|
||||
circle_fit:
|
||||
method: algebraic_then_lsq
|
||||
inlier_residual_mm: 1.5
|
||||
rectangle_aspect_tol: 0.40
|
||||
|
||||
roi:
|
||||
hole_dilate_mm: 5.0
|
||||
central_hole_dilate_mm: 10.0
|
||||
edge_buffer_mm: 8.0
|
||||
chamfer_normal_dot_min: 0.80
|
||||
outlier_z_score: 3.0
|
||||
|
||||
plane_fit:
|
||||
ransac_iterations: 300
|
||||
ransac_inlier_thresh_mm: auto
|
||||
min_inlier_ratio: 0.5
|
||||
enforce_nx_positive: true
|
||||
|
||||
metrics:
|
||||
right_axis_sign: 1
|
||||
angle_clamp_deg: 0.0
|
||||
|
||||
artifacts:
|
||||
save_intermediate: true
|
||||
ply_format: binary
|
||||
image_dpi: 150
|
||||
heatmap_colormap: viridis
|
||||
|
||||
registration:
|
||||
method: kabsch_four_holes
|
||||
refuse_if_residual_above_mm: 5.0
|
||||
@@ -0,0 +1,94 @@
|
||||
# Profile for the train_2 coupler mounting panel measured from a full-vehicle
|
||||
# scan (train_2_1T.ply, cropped to the coupler ROI).
|
||||
#
|
||||
# Part topology (measured from the 1T cloud, dataset frame x=length,
|
||||
# y=height, z=width):
|
||||
# - a wide base plate with a RAISED central square mounting plate
|
||||
# - the central plate has 4 corner bolt holes, r≈15.6 mm,
|
||||
# rectangle 360 mm (z) × 200 mm (y), at z=±180, y=835/1035
|
||||
# - NO central pass-through hole
|
||||
# - the ROI box also slices a roof truss + the base plate behind the
|
||||
# raised plate, so a normal-direction layer isolation is required
|
||||
#
|
||||
# Use:
|
||||
# run_coupler_measurement_pipeline(input_cloud=roi.ply,
|
||||
# profile="train2_coupler", roi_spec=<bbox>) # no CAD, no Kabsch
|
||||
|
||||
# --- CAD block (not used for STP parse here; kept for radius thresholds) ---
|
||||
cad:
|
||||
linear_deflection_mm: 0.5
|
||||
angular_deflection_rad: 0.1
|
||||
locating_hole_radius_mm: [11.0, 19.0] # r≈15.6 corner bolt holes
|
||||
central_hole_radius_min_mm: 999.0 # this part has NO central hole
|
||||
rectangle_aspect_tol: 0.40
|
||||
|
||||
# --- Normal-direction layer isolation (the key pre-processing step) -------
|
||||
# Isolate the frontmost dominant layer = the raised central plate, so the
|
||||
# back plate + truss don't fill the holes / pollute the plane fit.
|
||||
layer_select:
|
||||
enabled: true
|
||||
normal_seed: pca # pca | from_cad
|
||||
half_width_mm: 8.0 # slab half-thickness around the chosen layer
|
||||
pick: frontmost # frontmost (toward scanner) | densest
|
||||
bins: 240
|
||||
|
||||
# --- Denoise: drop the density-fragile radius filter (sparse-ish scan) ----
|
||||
denoise:
|
||||
steps:
|
||||
- type: passthrough
|
||||
bbox_padding_mm: 50.0
|
||||
- type: voxel
|
||||
voxel_mm: 0.5
|
||||
- type: statistical
|
||||
nb_neighbors: 20
|
||||
std_ratio: 2.5
|
||||
|
||||
# --- 4-hole detection tuned for r≈15.6 mm bolt holes ----------------------
|
||||
detection:
|
||||
panel_normal_seed: pca
|
||||
grid_pixel_mm: 2.0
|
||||
closing_iters: 1
|
||||
fill_bg_below_mm2: 60.0
|
||||
panel_min_area_ratio: 0.15
|
||||
hole_min_area_mm2: 300.0 # r=15.6 -> ~765 mm²; floor well below
|
||||
hole_max_area_mm2: 1400.0 # ceil above; excludes larger back-layer holes
|
||||
locating_hole_radius_mm: [11.0, 19.0]
|
||||
rectangle_aspect_tol: 0.40
|
||||
circle_fit:
|
||||
method: algebraic_then_lsq
|
||||
inlier_residual_mm: 1.5
|
||||
|
||||
# --- Panel ROI extraction -------------------------------------------------
|
||||
roi:
|
||||
hole_dilate_mm: 5.0
|
||||
central_hole_dilate_mm: 10.0
|
||||
edge_buffer_mm: 8.0
|
||||
chamfer_normal_dot_min: 0.80
|
||||
outlier_z_score: 3.0
|
||||
|
||||
# --- Plane fit ------------------------------------------------------------
|
||||
plane_fit:
|
||||
ransac_iterations: 400
|
||||
ransac_inlier_thresh_mm: 1.0
|
||||
min_inlier_ratio: 0.3
|
||||
enforce_nx_positive: true
|
||||
|
||||
# --- Metrics --------------------------------------------------------------
|
||||
# NOTE: this dataset's frame is x=length, y=height, z=width — i.e. y and z
|
||||
# are swapped relative to the package's nominal (y=width, z=height). The
|
||||
# angle formulas are symmetric in form; here theta_right = atan2(n_y,n_x)
|
||||
# is the tilt toward car-height and theta_ref = atan2(n_z,n_x) is the tilt
|
||||
# toward car-width. Both are ~0 for an undeflected panel.
|
||||
metrics:
|
||||
right_axis_sign: 1
|
||||
angle_clamp_deg: 0.0
|
||||
|
||||
registration:
|
||||
method: kabsch_four_holes
|
||||
refuse_if_residual_above_mm: 5.0
|
||||
|
||||
artifacts:
|
||||
save_intermediate: true
|
||||
ply_format: binary
|
||||
image_dpi: 150
|
||||
heatmap_colormap: viridis
|
||||
Reference in New Issue
Block a user