Skip to content

Commit a2b6fc5

Browse files
RuibinMafacebook-github-bot
authored andcommitted
expose aspect_ratio_sd parameter
Summary: It is questionable to assign the same std for focal length and aspect ratio, because aspect ratio, being the ratio of fu and fv, should be one order of magnitude smaller than fu and fv themselves. In practice we have noticed problematic maps built from opensfm BA that have very wrong aspect ratio, causing the camera poses to be inaccurate. Reviewed By: paulinus Differential Revision: D78990090 fbshipit-source-id: 65334567a693ab8872e91746942ef011f2e62de6
1 parent 7f17b89 commit a2b6fc5

7 files changed

Lines changed: 60 additions & 35 deletions

File tree

annotation_gui_gcp/run_ba.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -301,6 +301,7 @@ def bundle_with_fixed_images(
301301
)
302302
ba.set_internal_parameters_prior_sd(
303303
config["exif_focal_sd"],
304+
config["aspect_ratio_sd"],
304305
config["principal_point_sd"],
305306
config["radial_distortion_k1_sd"],
306307
config["radial_distortion_k2_sd"],

opensfm/config.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -239,6 +239,8 @@ class OpenSfMConfig:
239239
reprojection_error_sd: float = 0.004
240240
# The standard deviation of the exif focal length in log-scale
241241
exif_focal_sd: float = 0.01
242+
# The standard deviation of aspect ratio, i.e. fu/fv, in log-scale
243+
aspect_ratio_sd: float = 0.01
242244
# The standard deviation of the principal point coordinates
243245
principal_point_sd: float = 0.01
244246
# The standard deviation of the first radial distortion parameter

opensfm/src/bundle/bundle_adjuster.h

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -252,9 +252,10 @@ class BundleAdjuster {
252252
void SetLinearSolverType(std::string t);
253253
void SetCovarianceAlgorithmType(std::string t);
254254

255-
void SetInternalParametersPriorSD(double focal_sd, double c_sd, double k1_sd,
256-
double k2_sd, double p1_sd, double p2_sd,
257-
double k3_sd, double k4_sd);
255+
void SetInternalParametersPriorSD(double focal_sd, double aspect_ratio_sd,
256+
double c_sd, double k1_sd, double k2_sd,
257+
double p1_sd, double p2_sd, double k3_sd,
258+
double k4_sd);
258259
void SetRigParametersPriorSD(double rig_translation_sd,
259260
double rig_rotation_sd);
260261

@@ -324,6 +325,7 @@ class BundleAdjuster {
324325

325326
// Camera parameters prior
326327
double focal_prior_sd_;
328+
double aspect_ratio_prior_sd_;
327329
double c_prior_sd_;
328330
double k1_sd_;
329331
double k2_sd_;

opensfm/src/bundle/pybundle.pyi

Lines changed: 39 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ __all__ = [
2525
"ReconstructionAlignment",
2626
"RelativeMotion",
2727
"RelativeRotation",
28+
"StaticExtensionLoader",
2829
]
2930

3031
class BundleAdjuster:
@@ -36,7 +37,7 @@ class BundleAdjuster:
3637
def add_absolute_roll(self, arg0: str, arg1: float, arg2: float) -> None: ...
3738
def add_absolute_tilt(self, arg0: str, arg1: float, arg2: float) -> None: ...
3839
def add_absolute_up_vector(
39-
self, arg0: str, arg1: numpy.ndarray, arg2: float
40+
self, arg0: str, arg1: numpy.typing.NDArray, arg2: float
4041
) -> None: ...
4142
def add_camera(
4243
self,
@@ -49,20 +50,24 @@ class BundleAdjuster:
4950
self, arg0: str, arg1: str, arg2: float, arg3: float
5051
) -> None: ...
5152
def add_heatmap(
52-
self, arg0: str, arg1: List[float], arg2: int, arg3: float
53+
self, arg0: str, arg1: list[float], arg2: int, arg3: float
5354
) -> None: ...
5455
def add_linear_motion(
5556
self, arg0: str, arg1: str, arg2: str, arg3: float, arg4: float, arg5: float
5657
) -> None: ...
57-
def add_point(self, arg0: str, arg1: numpy.ndarray, arg2: bool) -> None: ...
58+
def add_point(self, arg0: str, arg1: numpy.typing.NDArray, arg2: bool) -> None: ...
5859
def add_point_prior(
59-
self, arg0: str, arg1: numpy.ndarray, arg2: numpy.ndarray, arg3: bool
60+
self,
61+
arg0: str,
62+
arg1: numpy.typing.NDArray,
63+
arg2: numpy.typing.NDArray,
64+
arg3: bool,
6065
) -> None: ...
6166
def add_point_projection_observation(
6267
self,
6368
shot: str,
6469
point: str,
65-
observation: numpy.ndarray,
70+
observation: numpy.typing.NDArray,
6671
std_deviation: float,
6772
depth_prior: Optional[opensfm.pymap.Depth] = None,
6873
) -> None: ...
@@ -83,12 +88,16 @@ class BundleAdjuster:
8388
self,
8489
arg0: str,
8590
arg1: opensfm.pygeometry.Pose,
86-
arg2: Dict[str, str],
87-
arg3: Dict[str, str],
91+
arg2: dict[str, str],
92+
arg3: dict[str, str],
8893
arg4: bool,
8994
) -> None: ...
9095
def add_rig_instance_position_prior(
91-
self, arg0: str, arg1: numpy.ndarray, arg2: numpy.ndarray, arg3: str
96+
self,
97+
arg0: str,
98+
arg1: numpy.typing.NDArray,
99+
arg2: numpy.typing.NDArray,
100+
arg3: str,
92101
) -> None: ...
93102
def brief_report(self) -> str: ...
94103
def full_report(self) -> str: ...
@@ -106,14 +115,15 @@ class BundleAdjuster:
106115
def set_gauge_fix_shots(self, arg0: str, arg1: str) -> None: ...
107116
def set_internal_parameters_prior_sd(
108117
self,
109-
arg0: float,
110-
arg1: float,
111-
arg2: float,
112-
arg3: float,
113-
arg4: float,
114-
arg5: float,
115-
arg6: float,
116-
arg7: float,
118+
focal_sd: float,
119+
aspect_ratio_sd: float,
120+
c_sd: float,
121+
k1_sd: float,
122+
k2_sd: float,
123+
p1_sd: float,
124+
p2_sd: float,
125+
k3_sd: float,
126+
k4_sd: float,
117127
) -> None: ...
118128
def set_linear_solver_type(self, arg0: str) -> None: ...
119129
def set_max_num_iterations(self, arg0: int) -> None: ...
@@ -127,11 +137,11 @@ class Point:
127137
@property
128138
def id(self) -> str: ...
129139
@property
130-
def p(self) -> numpy.ndarray: ...
140+
def p(self) -> numpy.typing.NDArray: ...
131141
@property
132-
def reprojection_errors(self) -> Dict[str, numpy.ndarray]: ...
142+
def reprojection_errors(self) -> dict[str, numpy.typing.NDArray]: ...
133143
@reprojection_errors.setter
134-
def reprojection_errors(self, arg0: Dict[str, numpy.ndarray]) -> None: ...
144+
def reprojection_errors(self, arg0: dict[str, numpy.typing.NDArray]) -> None: ...
135145

136146
class RAReconstruction:
137147
def __init__(self) -> None: ...
@@ -314,13 +324,13 @@ class RelativeMotion:
314324
self,
315325
arg0: str,
316326
arg1: str,
317-
arg2: numpy.ndarray,
318-
arg3: numpy.ndarray,
327+
arg2: numpy.typing.NDArray,
328+
arg3: numpy.typing.NDArray,
319329
arg4: float,
320330
arg5: float,
321331
arg6: bool,
322332
) -> None: ...
323-
def set_scale_matrix(self, arg0: numpy.ndarray) -> None: ...
333+
def set_scale_matrix(self, arg0: numpy.typing.NDArray) -> None: ...
324334
@property
325335
def rig_instance_i(self) -> str: ...
326336
@rig_instance_i.setter
@@ -331,12 +341,12 @@ class RelativeMotion:
331341
def rig_instance_j(self, arg0: str) -> None: ...
332342

333343
class RelativeRotation:
334-
def __init__(self, arg0: str, arg1: str, arg2: numpy.ndarray) -> None: ...
335-
def set_scale_matrix(self, arg0: numpy.ndarray) -> None: ...
344+
def __init__(self, arg0: str, arg1: str, arg2: numpy.typing.NDArray) -> None: ...
345+
def set_scale_matrix(self, arg0: numpy.typing.NDArray) -> None: ...
336346
@property
337-
def r(self) -> numpy.ndarray: ...
347+
def r(self) -> numpy.typing.NDArray: ...
338348
@r.setter
339-
def r(self, arg1: numpy.ndarray) -> None: ...
349+
def r(self, arg1: numpy.typing.NDArray) -> None: ...
340350
@property
341351
def shot_i(self) -> str: ...
342352
@shot_i.setter
@@ -345,3 +355,6 @@ class RelativeRotation:
345355
def shot_j(self) -> str: ...
346356
@shot_j.setter
347357
def shot_j(self, arg0: str) -> None: ...
358+
359+
class StaticExtensionLoader:
360+
pass

opensfm/src/bundle/python/pybind.cc

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,10 @@ PYBIND11_MODULE(pybundle, m) {
9494
.def("add_linear_motion", &bundle::BundleAdjuster::AddLinearMotion)
9595
.def("set_gauge_fix_shots", &bundle::BundleAdjuster::SetGaugeFixShots)
9696
.def("set_internal_parameters_prior_sd",
97-
&bundle::BundleAdjuster::SetInternalParametersPriorSD)
97+
&bundle::BundleAdjuster::SetInternalParametersPriorSD,
98+
py::arg("focal_sd"), py::arg("aspect_ratio_sd"), py::arg("c_sd"),
99+
py::arg("k1_sd"), py::arg("k2_sd"), py::arg("p1_sd"),
100+
py::arg("p2_sd"), py::arg("k3_sd"), py::arg("k4_sd"))
98101
.def("set_compute_covariances",
99102
&bundle::BundleAdjuster::SetComputeCovariances)
100103
.def("get_covariance_estimation_valid",

opensfm/src/bundle/src/bundle_adjuster.cc

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ BundleAdjuster::BundleAdjuster() {
2525
SetPointProjectionLossFunction("CauchyLoss", 1.0);
2626
SetRelativeMotionLossFunction("CauchyLoss", 1.0);
2727
focal_prior_sd_ = 1;
28+
aspect_ratio_prior_sd_ = 1;
2829
c_prior_sd_ = 1;
2930
k1_sd_ = 1;
3031
k2_sd_ = 1;
@@ -48,7 +49,7 @@ geometry::Camera BundleAdjuster::GetDefaultCameraSigma(
4849
std_dev_map[static_cast<int>(geometry::Camera::Parameters::Focal)] =
4950
focal_prior_sd_;
5051
std_dev_map[static_cast<int>(geometry::Camera::Parameters::AspectRatio)] =
51-
focal_prior_sd_;
52+
aspect_ratio_prior_sd_;
5253
std_dev_map[static_cast<int>(geometry::Camera::Parameters::Cx)] = c_prior_sd_;
5354
std_dev_map[static_cast<int>(geometry::Camera::Parameters::Cy)] = c_prior_sd_;
5455
std_dev_map[static_cast<int>(geometry::Camera::Parameters::K1)] = k1_sd_;
@@ -376,11 +377,11 @@ void BundleAdjuster::SetCovarianceAlgorithmType(std::string t) {
376377
covariance_algorithm_type_ = t;
377378
}
378379

379-
void BundleAdjuster::SetInternalParametersPriorSD(double focal_sd, double c_sd,
380-
double k1_sd, double k2_sd,
381-
double p1_sd, double p2_sd,
382-
double k3_sd, double k4_sd) {
380+
void BundleAdjuster::SetInternalParametersPriorSD(
381+
double focal_sd, double aspect_ratio_sd, double c_sd, double k1_sd,
382+
double k2_sd, double p1_sd, double p2_sd, double k3_sd, double k4_sd) {
383383
focal_prior_sd_ = focal_sd;
384+
aspect_ratio_prior_sd_ = aspect_ratio_sd;
384385
c_prior_sd_ = c_sd;
385386
k1_sd_ = k1_sd;
386387
k2_sd_ = k2_sd;

opensfm/src/sfm/src/ba_helpers.cc

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -255,6 +255,7 @@ py::tuple BAHelpers::BundleLocal(
255255
config["loss_function_threshold"].cast<double>());
256256
ba.SetInternalParametersPriorSD(
257257
config["exif_focal_sd"].cast<double>(),
258+
config["aspect_ratio_sd"].cast<double>(),
258259
config["principal_point_sd"].cast<double>(),
259260
config["radial_distortion_k1_sd"].cast<double>(),
260261
config["radial_distortion_k2_sd"].cast<double>(),
@@ -536,6 +537,7 @@ py::dict BAHelpers::BundleShotPoses(
536537
config["loss_function_threshold"].cast<double>());
537538
ba.SetInternalParametersPriorSD(
538539
config["exif_focal_sd"].cast<double>(),
540+
config["aspect_ratio_sd"].cast<double>(),
539541
config["principal_point_sd"].cast<double>(),
540542
config["radial_distortion_k1_sd"].cast<double>(),
541543
config["radial_distortion_k2_sd"].cast<double>(),
@@ -728,6 +730,7 @@ py::dict BAHelpers::Bundle(
728730
config["loss_function_threshold"].cast<double>());
729731
ba.SetInternalParametersPriorSD(
730732
config["exif_focal_sd"].cast<double>(),
733+
config["aspect_ratio_sd"].cast<double>(),
731734
config["principal_point_sd"].cast<double>(),
732735
config["radial_distortion_k1_sd"].cast<double>(),
733736
config["radial_distortion_k2_sd"].cast<double>(),

0 commit comments

Comments
 (0)