ReUseX
0.0.5
3D Point Cloud Processing for Building Reuse
Toggle main menu visibility
Loading...
Searching...
No Matches
PanoramaAlignment.hpp
Go to the documentation of this file.
1
// SPDX-FileCopyrightText: 2026 Povl Filip Sonne-Frederiksen
2
//
3
// SPDX-License-Identifier: GPL-3.0-or-later
4
//
5
// Content-based alignment of 360 panoramas to the scan.
6
//
7
// A panorama is imported and placed on the trajectory purely by nearest EXIF
8
// timestamp (`rux import 360`), inheriting the matched sensor frame's pose.
9
// That is only as good as the clock sync and gives the panorama no independent
10
// orientation. This module refines the panorama's 6-DoF pose from image
11
// content:
12
//
13
// 1. render virtual pinhole slices of the equirect
14
// (geometry/EquirectProjection)
15
// 2. ORB-match each slice against nearby sensor frames — the SAME
16
// license-clean
17
// OpenCV ORB + Lowe-ratio front-end used by LoopClosure
18
// 3. lift frame matches to metric 3D via the frame's stored depth + pose
19
// 4. resect the panorama pose per slice with solvePnPRansac (each slice is a
20
// true pinhole with known K and known slice->panorama rotation), then
21
// refine over all slices' inliers in panorama-bearing space
22
//
23
// The refined pose is a panorama-optical->world transform in the SAME
24
// convention as sensor_frame_pose, so it drops straight into the viewer /
25
// exporters and (as a follow-up, issue #236) into the pose graph as loop
26
// constraints.
27
28
#pragma once
29
30
#include <Eigen/Core>
31
#include <Eigen/Geometry>
32
33
#include <array>
34
#include <string>
35
36
namespace
reusex
{
37
class
ProjectDB
;
38
}
39
40
namespace
reusex::geometry
{
41
43
struct
PanoramaAlignmentOptions
{
44
// --- candidate sensor frames -------------------------------------------
48
int
candidate_window
= 25;
51
int
max_candidates
= 20;
52
53
// --- panorama slicing (geometry/EquirectProjection) --------------------
54
int
n_yaw
= 8;
55
double
fov_deg
= 90.0;
56
int
slice
= 1008;
57
58
// --- ORB front-end (mirrors LoopClosureOptions) ------------------------
59
int
max_features
= 3000;
60
float
ratio_test
= 0.85f;
61
float
min_depth
= 0.3f;
62
float
max_depth
= 6.0f;
63
64
// --- PnP resection -----------------------------------------------------
65
int
min_slice_correspondences
= 6;
66
int
min_inliers
= 25;
67
float
ransac_reproj_px
= 5.0f;
68
int
ransac_iterations
= 500;
69
int
refine_iterations
= 10;
70
78
double
max_correction_m
= 5.0;
79
unsigned
seed
= 42;
80
84
std::string
debug_dir
;
85
std::string
debug_name
;
86
};
87
89
struct
PanoramaAlignmentResult
{
90
int
pano_id
= -1;
91
int
seed_node
= -1;
92
bool
aligned
=
false
;
93
int
inliers
= 0;
94
double
rms_deg
= -1.0;
97
std::array<double, 16>
pose
= {1, 0, 0, 0, 0, 1, 0, 0,
98
0, 0, 1, 0, 0, 0, 0, 1};
99
103
double
delta_from_seed_m
= -1.0;
104
};
105
115
PanoramaAlignmentResult
align_panorama
(
ProjectDB
&db,
int
pano_id,
116
int
seed_node_id,
117
const
PanoramaAlignmentOptions
&opt);
118
119
}
// namespace reusex::geometry
reusex::ProjectDB
Definition
ProjectDB.hpp:43
reusex::geometry
Definition
visual_observer.hpp:33
reusex::geometry::align_panorama
PanoramaAlignmentResult align_panorama(ProjectDB &db, int pano_id, int seed_node_id, const PanoramaAlignmentOptions &opt)
Align one panorama against nearby sensor frames.
reusex
Definition
component_record.hpp:12
reusex::geometry::PanoramaAlignmentOptions
Parameters for content-based panorama alignment.
Definition
PanoramaAlignment.hpp:43
reusex::geometry::PanoramaAlignmentOptions::max_correction_m
double max_correction_m
Plausibility gate: reject an alignment whose refined centre is further than this from the timestamp-s...
Definition
PanoramaAlignment.hpp:78
reusex::geometry::PanoramaAlignmentOptions::min_inliers
int min_inliers
accept alignment above this (total)
Definition
PanoramaAlignment.hpp:66
reusex::geometry::PanoramaAlignmentOptions::fov_deg
double fov_deg
per-slice horizontal FOV (overlap for matching)
Definition
PanoramaAlignment.hpp:55
reusex::geometry::PanoramaAlignmentOptions::max_features
int max_features
ORB features per image.
Definition
PanoramaAlignment.hpp:59
reusex::geometry::PanoramaAlignmentOptions::refine_iterations
int refine_iterations
bearing-space Gauss-Newton refinement steps
Definition
PanoramaAlignment.hpp:69
reusex::geometry::PanoramaAlignmentOptions::debug_name
std::string debug_name
Definition
PanoramaAlignment.hpp:85
reusex::geometry::PanoramaAlignmentOptions::ransac_reproj_px
float ransac_reproj_px
solvePnPRansac reprojection threshold
Definition
PanoramaAlignment.hpp:67
reusex::geometry::PanoramaAlignmentOptions::candidate_window
int candidate_window
Try the timestamp-seed frame plus this many frames on each side of it (in sensor-frame-id order).
Definition
PanoramaAlignment.hpp:48
reusex::geometry::PanoramaAlignmentOptions::slice
int slice
slice size (px, square)
Definition
PanoramaAlignment.hpp:56
reusex::geometry::PanoramaAlignmentOptions::seed
unsigned seed
Definition
PanoramaAlignment.hpp:79
reusex::geometry::PanoramaAlignmentOptions::max_depth
float max_depth
Definition
PanoramaAlignment.hpp:62
reusex::geometry::PanoramaAlignmentOptions::n_yaw
int n_yaw
perspective slices around the equator
Definition
PanoramaAlignment.hpp:54
reusex::geometry::PanoramaAlignmentOptions::min_slice_correspondences
int min_slice_correspondences
need this many to PnP a slice
Definition
PanoramaAlignment.hpp:65
reusex::geometry::PanoramaAlignmentOptions::ransac_iterations
int ransac_iterations
Definition
PanoramaAlignment.hpp:68
reusex::geometry::PanoramaAlignmentOptions::min_depth
float min_depth
ignore frame keypoints outside [min,max] depth
Definition
PanoramaAlignment.hpp:61
reusex::geometry::PanoramaAlignmentOptions::debug_dir
std::string debug_dir
If non-empty, write an ORB-correspondence figure (panorama slice <-> the best-matching sensor frame,...
Definition
PanoramaAlignment.hpp:84
reusex::geometry::PanoramaAlignmentOptions::ratio_test
float ratio_test
Lowe ratio threshold.
Definition
PanoramaAlignment.hpp:60
reusex::geometry::PanoramaAlignmentOptions::max_candidates
int max_candidates
Cap the number of candidate frames actually matched (nearest-to-seed first), bounding the O(slices x ...
Definition
PanoramaAlignment.hpp:51
reusex::geometry::PanoramaAlignmentResult
Outcome of aligning one panorama.
Definition
PanoramaAlignment.hpp:89
reusex::geometry::PanoramaAlignmentResult::delta_from_seed_m
double delta_from_seed_m
Translation delta from the timestamp-seed placement (m); -1 when there is no seed,...
Definition
PanoramaAlignment.hpp:103
reusex::geometry::PanoramaAlignmentResult::seed_node
int seed_node
Definition
PanoramaAlignment.hpp:91
reusex::geometry::PanoramaAlignmentResult::pose
std::array< double, 16 > pose
panorama-optical->world, row-major 4x4 (same convention as ProjectDB::sensor_frame_pose).
Definition
PanoramaAlignment.hpp:97
reusex::geometry::PanoramaAlignmentResult::rms_deg
double rms_deg
angular reprojection RMS over inliers (deg)
Definition
PanoramaAlignment.hpp:94
reusex::geometry::PanoramaAlignmentResult::inliers
int inliers
pooled PnP inliers supporting the pose
Definition
PanoramaAlignment.hpp:93
reusex::geometry::PanoramaAlignmentResult::pano_id
int pano_id
Definition
PanoramaAlignment.hpp:90
reusex::geometry::PanoramaAlignmentResult::aligned
bool aligned
Definition
PanoramaAlignment.hpp:92
libs
reusex
include
slam
PanoramaAlignment.hpp
Generated by
1.17.0