[Bf-blender-cvs] [8232ce0] soc-2016-multiview: in the middle of nasty bundle migration
Tianwei Shen
noreply at git.blender.org
Thu Jun 16 17:41:49 CEST 2016
Commit: 8232ce0605e1d920ad5e28d2b2f6a45305ec071f
Author: Tianwei Shen
Date: Thu Jun 16 23:41:33 2016 +0800
Branches: soc-2016-multiview
https://developer.blender.org/rB8232ce0605e1d920ad5e28d2b2f6a45305ec071f
in the middle of nasty bundle migration
===================================================================
M intern/libmv/CMakeLists.txt
M intern/libmv/intern/reconstructionN.cc
A intern/libmv/libmv/autotrack/bundle.cc
A intern/libmv/libmv/autotrack/bundle.h
M intern/libmv/libmv/autotrack/reconstruction.cc
M intern/libmv/libmv/autotrack/reconstruction.h
===================================================================
diff --git a/intern/libmv/CMakeLists.txt b/intern/libmv/CMakeLists.txt
index c7d75ed..d88f0f4 100644
--- a/intern/libmv/CMakeLists.txt
+++ b/intern/libmv/CMakeLists.txt
@@ -75,6 +75,7 @@ if(WITH_LIBMV)
intern/tracks.cc
intern/tracksN.cc
libmv/autotrack/autotrack.cc
+ libmv/autotrack/bundle.cc
libmv/autotrack/predict_tracks.cc
libmv/autotrack/reconstruction.cc
libmv/autotrack/tracks.cc
@@ -126,6 +127,7 @@ if(WITH_LIBMV)
intern/tracks.h
intern/tracksN.h
libmv/autotrack/autotrack.h
+ libmv/autotrack/bundle.h
libmv/autotrack/callbacks.h
libmv/autotrack/frame_accessor.h
libmv/autotrack/marker.h
diff --git a/intern/libmv/intern/reconstructionN.cc b/intern/libmv/intern/reconstructionN.cc
index 1960b13..8369ff9 100644
--- a/intern/libmv/intern/reconstructionN.cc
+++ b/intern/libmv/intern/reconstructionN.cc
@@ -31,6 +31,7 @@
#include "libmv/logging/logging.h"
#include "libmv/autotrack/autotrack.h"
+#include "libmv/autotrack/bundle.h"
#include "libmv/autotrack/frame_accessor.h"
#include "libmv/autotrack/marker.h"
#include "libmv/autotrack/model.h"
diff --git a/intern/libmv/libmv/autotrack/bundle.cc b/intern/libmv/libmv/autotrack/bundle.cc
new file mode 100644
index 0000000..2dfe231
--- /dev/null
+++ b/intern/libmv/libmv/autotrack/bundle.cc
@@ -0,0 +1,678 @@
+// Copyright (c) 2011, 2012, 2013, 2016 libmv authors.
+//
+// Permission is hereby granted, free of charge, to any person obtaining a copy
+// of this software and associated documentation files (the "Software"), to
+// deal in the Software without restriction, including without limitation the
+// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+// sell copies of the Software, and to permit persons to whom the Software is
+// furnished to do so, subject to the following conditions:
+//
+// The above copyright notice and this permission notice shall be included in
+// all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+// IN THE SOFTWARE.
+//
+// Author: Tianwei Shen <shentianweipku at gmail.com>
+//
+// This is a autotrack equivalent bundle set, adapted from simple_pipeline,
+// which replaces libmv with mv, includeing tracks and markers
+
+#include "libmv/autotrack/bundle.h"
+
+#include <map>
+
+#include "ceres/ceres.h"
+#include "ceres/rotation.h"
+#include "libmv/base/vector.h"
+#include "libmv/logging/logging.h"
+#include "libmv/multiview/fundamental.h"
+#include "libmv/multiview/projection.h"
+#include "libmv/numeric/numeric.h"
+#include "libmv/simple_pipeline/camera_intrinsics.h"
+#include "libmv/simple_pipeline/distortion_models.h"
+#include "libmv/autotrack/reconstruction.h"
+#include "libmv/autotrack/tracks.h"
+
+#ifdef _OPENMP
+# include <omp.h>
+#endif
+
+using libmv::DistortionModelType;
+using libmv::Vec6;
+using libmv::PolynomialCameraIntrinsics;
+
+namespace mv {
+
+// The intrinsics need to get combined into a single parameter block; use these
+// enums to index instead of numeric constants.
+enum {
+ // Camera calibration values.
+ OFFSET_FOCAL_LENGTH,
+ OFFSET_PRINCIPAL_POINT_X,
+ OFFSET_PRINCIPAL_POINT_Y,
+
+ // Distortion model coefficients.
+ OFFSET_K1,
+ OFFSET_K2,
+ OFFSET_K3,
+ OFFSET_P1,
+ OFFSET_P2,
+
+ // Maximal possible offset.
+ OFFSET_MAX,
+};
+
+#define FIRST_DISTORTION_COEFFICIENT OFFSET_K1
+#define LAST_DISTORTION_COEFFICIENT OFFSET_P2
+#define NUM_DISTORTION_COEFFICIENTS \
+ (LAST_DISTORTION_COEFFICIENT - FIRST_DISTORTION_COEFFICIENT + 1)
+
+namespace {
+
+// Cost functor which computes reprojection error of 3D point X
+// on camera defined by angle-axis rotation and it's translation
+// (which are in the same block due to optimization reasons).
+//
+// This functor uses a radial distortion model.
+struct OpenCVReprojectionError {
+ OpenCVReprojectionError(const DistortionModelType distortion_model,
+ const double observed_x,
+ const double observed_y,
+ const double weight) :
+ distortion_model_(distortion_model),
+ observed_x_(observed_x), observed_y_(observed_y),
+ weight_(weight) {}
+
+ template <typename T>
+ bool operator()(const T* const intrinsics,
+ const T* const R_t, // Rotation denoted by angle axis followed with translation
+ const T* const X, // Point coordinates 3x1.
+ T* residuals) const {
+ // Unpack the intrinsics.
+ const T& focal_length = intrinsics[OFFSET_FOCAL_LENGTH];
+ const T& principal_point_x = intrinsics[OFFSET_PRINCIPAL_POINT_X];
+ const T& principal_point_y = intrinsics[OFFSET_PRINCIPAL_POINT_Y];
+
+ // Compute projective coordinates: x = RX + t.
+ T x[3];
+
+ ceres::AngleAxisRotatePoint(R_t, X, x);
+ x[0] += R_t[3];
+ x[1] += R_t[4];
+ x[2] += R_t[5];
+
+ // Prevent points from going behind the camera.
+ if (x[2] < T(0)) {
+ return false;
+ }
+
+ // Compute normalized coordinates: x /= x[2].
+ T xn = x[0] / x[2];
+ T yn = x[1] / x[2];
+
+ T predicted_x, predicted_y;
+
+ // Apply distortion to the normalized points to get (xd, yd).
+ // TODO(keir): Do early bailouts for zero distortion; these are expensive
+ // jet operations.
+ switch (distortion_model_) {
+ case libmv::DISTORTION_MODEL_POLYNOMIAL:
+ {
+ const T& k1 = intrinsics[OFFSET_K1];
+ const T& k2 = intrinsics[OFFSET_K2];
+ const T& k3 = intrinsics[OFFSET_K3];
+ const T& p1 = intrinsics[OFFSET_P1];
+ const T& p2 = intrinsics[OFFSET_P2];
+
+ libmv::ApplyPolynomialDistortionModel(focal_length,
+ focal_length,
+ principal_point_x,
+ principal_point_y,
+ k1, k2, k3,
+ p1, p2,
+ xn, yn,
+ &predicted_x,
+ &predicted_y);
+ break;
+ }
+ case libmv::DISTORTION_MODEL_DIVISION:
+ {
+ const T& k1 = intrinsics[OFFSET_K1];
+ const T& k2 = intrinsics[OFFSET_K2];
+
+ libmv::ApplyDivisionDistortionModel(focal_length,
+ focal_length,
+ principal_point_x,
+ principal_point_y,
+ k1, k2,
+ xn, yn,
+ &predicted_x,
+ &predicted_y);
+ break;
+ }
+ default:
+ LOG(FATAL) << "Unknown distortion model";
+ }
+
+ // The error is the difference between the predicted and observed position.
+ residuals[0] = (predicted_x - T(observed_x_)) * weight_;
+ residuals[1] = (predicted_y - T(observed_y_)) * weight_;
+ return true;
+ }
+
+ const DistortionModelType distortion_model_;
+ const double observed_x_;
+ const double observed_y_;
+ const double weight_;
+};
+
+// Print a message to the log which camera intrinsics are gonna to be optimixed.
+void BundleIntrinsicsLogMessage(const int bundle_intrinsics) {
+ if (bundle_intrinsics == BUNDLE_NO_INTRINSICS) {
+ LOG(INFO) << "Bundling only camera positions.";
+ } else {
+ std::string bundling_message = "";
+
+#define APPEND_BUNDLING_INTRINSICS(name, flag) \
+ if (bundle_intrinsics & flag) { \
+ if (!bundling_message.empty()) { \
+ bundling_message += ", "; \
+ } \
+ bundling_message += name; \
+ } (void)0
+
+ APPEND_BUNDLING_INTRINSICS("f", BUNDLE_FOCAL_LENGTH);
+ APPEND_BUNDLING_INTRINSICS("px, py", BUNDLE_PRINCIPAL_POINT);
+ APPEND_BUNDLING_INTRINSICS("k1", BUNDLE_RADIAL_K1);
+ APPEND_BUNDLING_INTRINSICS("k2", BUNDLE_RADIAL_K2);
+ APPEND_BUNDLING_INTRINSICS("p1", BUNDLE_TANGENTIAL_P1);
+ APPEND_BUNDLING_INTRINSICS("p2", BUNDLE_TANGENTIAL_P2);
+
+ LOG(INFO) << "Bundling " << bundling_message << ".";
+ }
+}
+
+// Pack intrinsics from object to an array for easier
+// and faster minimization.
+void PackIntrinisicsIntoArray(const CameraIntrinsics &intrinsics,
+ double ceres_intrinsics[OFFSET_MAX]) {
+ ceres_intrinsics[OFFSET_FOCAL_LENGTH] = intrinsics.focal_length();
+ ceres_intrinsics[OFFSET_PRINCIPAL_POINT_X] = intrinsics.principal_point_x();
+ ceres_intrinsics[OFFSET_PRINCIPAL_POINT_Y] = intrinsics.principal_point_y();
+
+ int num_distortion_parameters = intrinsics.num_distortion_parameters();
+ assert(num_distortion_parameters <= NUM_DISTORTION_COEFFICIENTS);
+
+ const double *distortion_parameters = intrinsics.distortion_parameters();
+ for (int i = 0; i < num_distortion_parameters; ++i) {
+ ceres_intrinsics[FIRST_DISTORTION_COEFFICIENT + i] =
+ distortion_parameters[i];
+ }
+}
+
+// Unpack intrinsics back from an array to an object.
+void UnpackIntrinsicsFromArray(const double ceres_intrinsics[OFFSET_MAX],
+ CameraIntrinsics *intrinsics) {
+ intrinsics->SetFocalLength(ceres_intrinsics[OFFSET_FOCAL_LENGTH],
+ ceres_intrinsics[OFFSET_FOCAL_LENGTH]);
+
+ intrinsics->SetPrincipalPoint(ceres_intrinsics[OFFSET_PRINCIPAL_POINT_X],
+ ceres_intrinsics[OFFSET_PRINCIPAL_POINT_Y]);
+
+ int num_distortion_parameters = intrinsics->num_distortion_parameters();
+ assert(num_distortion_parameters <= NUM_DISTORTION_COEFFICIENTS);
+
+ double *distortion_parameters = intrinsics->distortion_parameters();
+ for (int i = 0; i < num_distortion_parameters; ++
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list