Blender  V2.93
intern/track_region.cc
Go to the documentation of this file.
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  *
16  * The Original Code is Copyright (C) 2011 Blender Foundation.
17  * All rights reserved.
18  */
19 
20 #include "intern/track_region.h"
21 #include "intern/image.h"
22 #include "intern/utildefines.h"
23 #include "libmv/image/image.h"
24 #include "libmv/logging/logging.h"
26 
27 /* define this to generate PNG images with content of search areas
28  tracking between which failed */
29 #undef DUMP_FAILURE
30 
31 /* define this to generate PNG images with content of search areas
32  on every iteration of tracking */
33 #undef DUMP_ALWAYS
34 
35 using libmv::FloatImage;
36 using libmv::TrackRegion;
39 
40 namespace {
41 
42 TrackRegionOptions::Direction convertDirection(
43  libmv_TrackRegionDirection direction) {
44  switch (direction) {
46  case LIBMV_TRACK_REGION_BACKWARD: return TrackRegionOptions::BACKWARD;
47  }
48 
49  LOG(FATAL) << "Unhandled tracking direction " << direction
50  << ", should never happen.";
51 
53 }
54 
55 TrackRegionOptions::Mode convertMotionModelToMode(int motion_model) {
56  switch (motion_model) {
57 #define LIBMV_CONVERT(the_model) \
58  case TrackRegionOptions::the_model: return TrackRegionOptions::the_model;
59 
60  LIBMV_CONVERT(TRANSLATION)
61  LIBMV_CONVERT(TRANSLATION_ROTATION)
62  LIBMV_CONVERT(TRANSLATION_SCALE)
63  LIBMV_CONVERT(TRANSLATION_ROTATION_SCALE)
64  LIBMV_CONVERT(AFFINE)
65  LIBMV_CONVERT(HOMOGRAPHY)
66 
67 #undef LIBMV_CONVERT
68  }
69 
70  LOG(FATAL) << "Unhandled motion model " << motion_model
71  << ", should never happen.";
72 
73  return TrackRegionOptions::TRANSLATION;
74 }
75 
76 } // namespace
77 
80  TrackRegionOptions* track_region_options) {
81  track_region_options->direction = convertDirection(options.direction);
82  track_region_options->mode = convertMotionModelToMode(options.motion_model);
83  track_region_options->minimum_correlation = options.minimum_correlation;
84  track_region_options->max_iterations = options.num_iterations;
85  track_region_options->sigma = options.sigma;
86  track_region_options->num_extra_points = 1;
87  track_region_options->image1_mask = NULL;
88  track_region_options->use_brute_initialization = options.use_brute;
89  /* TODO(keir): This will make some cases better, but may be a regression until
90  * the motion model is in. Since this is on trunk, enable it for now.
91  *
92  * TODO(sergey): This gives much worse results on mango footage (see 04_2e)
93  * so disabling for now for until proper prediction model is landed.
94  *
95  * The thing is, currently blender sends input coordinates as the guess to
96  * region tracker and in case of fast motion such an early out ruins the
97  * track.
98  */
99  track_region_options->attempt_refine_before_brute = false;
100  track_region_options->use_normalized_intensities = options.use_normalization;
101 }
102 
103 void libmv_regionTrackergetResult(const TrackRegionResult& track_region_result,
105  result->termination = (int)track_region_result.termination;
106  result->termination_reason = "";
107  result->correlation = track_region_result.correlation;
108 }
109 
111  const float* image1,
112  int image1_width,
113  int image1_height,
114  const float* image2,
115  int image2_width,
116  int image2_height,
117  const double* x1,
118  const double* y1,
119  libmv_TrackRegionResult* /*result*/,
120  double* x2,
121  double* y2) {
122  double xx1[5], yy1[5];
123  double xx2[5], yy2[5];
124  bool tracking_result = false;
125 
126  // Convert to doubles for the libmv api. The four corners and the center.
127  for (int i = 0; i < 5; ++i) {
128  xx1[i] = x1[i];
129  yy1[i] = y1[i];
130  xx2[i] = x2[i];
131  yy2[i] = y2[i];
132  }
133 
134  TrackRegionOptions track_region_options;
135  FloatImage image1_mask;
136 
137  libmv_configureTrackRegionOptions(*options, &track_region_options);
138  if (options->image1_mask) {
140  options->image1_mask, image1_width, image1_height, 1, &image1_mask);
141 
142  track_region_options.image1_mask = &image1_mask;
143  }
144 
145  // Convert from raw float buffers to libmv's FloatImage.
146  FloatImage old_patch, new_patch;
148  image1, image1_width, image1_height, 1, &old_patch);
150  image2, image2_width, image2_height, 1, &new_patch);
151 
152  TrackRegionResult track_region_result;
153  TrackRegion(old_patch,
154  new_patch,
155  xx1,
156  yy1,
157  track_region_options,
158  xx2,
159  yy2,
160  &track_region_result);
161 
162  // Convert to floats for the blender api.
163  for (int i = 0; i < 5; ++i) {
164  x2[i] = xx2[i];
165  y2[i] = yy2[i];
166  }
167 
168  // TODO(keir): Update the termination string with failure details.
169  if (track_region_result.termination == TrackRegionResult::CONVERGENCE ||
170  track_region_result.termination == TrackRegionResult::NO_CONVERGENCE) {
171  tracking_result = true;
172  }
173 
174  // Debug dump of patches.
175 #if defined(DUMP_FAILURE) || defined(DUMP_ALWAYS)
176  bool need_dump = !tracking_result;
177 
178 # ifdef DUMP_ALWAYS
179  need_dump = true;
180 # endif
181 
182  if (need_dump) {
183  libmv_saveImage(old_patch, "old_patch", x1[4], y1[4]);
184  libmv_saveImage(new_patch, "new_patch", x2[4], y2[4]);
185  if (options->image1_mask) {
186  libmv_saveImage(image1_mask, "mask", x2[4], y2[4]);
187  }
188  }
189 #endif
190 
191  return tracking_result;
192 }
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum const void *lists _GL_VOID_RET _GL_VOID const GLdouble *equation _GL_VOID_RET _GL_VOID GLdouble GLdouble blue _GL_VOID_RET _GL_VOID GLfloat GLfloat blue _GL_VOID_RET _GL_VOID GLint GLint blue _GL_VOID_RET _GL_VOID GLshort GLshort blue _GL_VOID_RET _GL_VOID GLubyte GLubyte blue _GL_VOID_RET _GL_VOID GLuint GLuint blue _GL_VOID_RET _GL_VOID GLushort GLushort blue _GL_VOID_RET _GL_VOID GLbyte GLbyte GLbyte alpha _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble alpha _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat alpha _GL_VOID_RET _GL_VOID GLint GLint GLint alpha _GL_VOID_RET _GL_VOID GLshort GLshort GLshort alpha _GL_VOID_RET _GL_VOID GLubyte GLubyte GLubyte alpha _GL_VOID_RET _GL_VOID GLuint GLuint GLuint alpha _GL_VOID_RET _GL_VOID GLushort GLushort GLushort alpha _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLint GLsizei GLsizei GLenum type _GL_VOID_RET _GL_VOID GLsizei GLenum GLenum const void *pixels _GL_VOID_RET _GL_VOID const void *pointer _GL_VOID_RET _GL_VOID GLdouble v _GL_VOID_RET _GL_VOID GLfloat v _GL_VOID_RET _GL_VOID GLint GLint i2 _GL_VOID_RET _GL_VOID GLint j _GL_VOID_RET _GL_VOID GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble GLdouble GLdouble zFar _GL_VOID_RET _GL_UINT GLdouble *equation _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLenum GLfloat *v _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLfloat *values _GL_VOID_RET _GL_VOID GLushort *values _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLenum GLdouble *params _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_BOOL GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLushort pattern _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble u2 _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLdouble GLdouble v2 _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLdouble GLdouble nz _GL_VOID_RET _GL_VOID GLfloat GLfloat nz _GL_VOID_RET _GL_VOID GLint GLint nz _GL_VOID_RET _GL_VOID GLshort GLshort nz _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const GLfloat *values _GL_VOID_RET _GL_VOID GLsizei const GLushort *values _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID const GLuint const GLclampf *priorities _GL_VOID_RET _GL_VOID GLdouble y _GL_VOID_RET _GL_VOID GLfloat y _GL_VOID_RET _GL_VOID GLint y _GL_VOID_RET _GL_VOID GLshort y _GL_VOID_RET _GL_VOID GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLfloat GLfloat z _GL_VOID_RET _GL_VOID GLint GLint z _GL_VOID_RET _GL_VOID GLshort GLshort z _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble w _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat w _GL_VOID_RET _GL_VOID GLint GLint GLint w _GL_VOID_RET _GL_VOID GLshort GLshort GLshort w _GL_VOID_RET _GL_VOID GLdouble y1
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum const void *lists _GL_VOID_RET _GL_VOID const GLdouble *equation _GL_VOID_RET _GL_VOID GLdouble GLdouble blue _GL_VOID_RET _GL_VOID GLfloat GLfloat blue _GL_VOID_RET _GL_VOID GLint GLint blue _GL_VOID_RET _GL_VOID GLshort GLshort blue _GL_VOID_RET _GL_VOID GLubyte GLubyte blue _GL_VOID_RET _GL_VOID GLuint GLuint blue _GL_VOID_RET _GL_VOID GLushort GLushort blue _GL_VOID_RET _GL_VOID GLbyte GLbyte GLbyte alpha _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble alpha _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat alpha _GL_VOID_RET _GL_VOID GLint GLint GLint alpha _GL_VOID_RET _GL_VOID GLshort GLshort GLshort alpha _GL_VOID_RET _GL_VOID GLubyte GLubyte GLubyte alpha _GL_VOID_RET _GL_VOID GLuint GLuint GLuint alpha _GL_VOID_RET _GL_VOID GLushort GLushort GLushort alpha _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLint GLsizei GLsizei GLenum type _GL_VOID_RET _GL_VOID GLsizei GLenum GLenum const void *pixels _GL_VOID_RET _GL_VOID const void *pointer _GL_VOID_RET _GL_VOID GLdouble v _GL_VOID_RET _GL_VOID GLfloat v _GL_VOID_RET _GL_VOID GLint GLint i2 _GL_VOID_RET _GL_VOID GLint j _GL_VOID_RET _GL_VOID GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble GLdouble GLdouble zFar _GL_VOID_RET _GL_UINT GLdouble *equation _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLenum GLfloat *v _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLfloat *values _GL_VOID_RET _GL_VOID GLushort *values _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLenum GLdouble *params _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_BOOL GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLushort pattern _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble u2 _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLdouble GLdouble v2 _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLdouble GLdouble nz _GL_VOID_RET _GL_VOID GLfloat GLfloat nz _GL_VOID_RET _GL_VOID GLint GLint nz _GL_VOID_RET _GL_VOID GLshort GLshort nz _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const GLfloat *values _GL_VOID_RET _GL_VOID GLsizei const GLushort *values _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID const GLuint const GLclampf *priorities _GL_VOID_RET _GL_VOID GLdouble y _GL_VOID_RET _GL_VOID GLfloat y _GL_VOID_RET _GL_VOID GLint y _GL_VOID_RET _GL_VOID GLshort y _GL_VOID_RET _GL_VOID GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLfloat GLfloat z _GL_VOID_RET _GL_VOID GLint GLint z _GL_VOID_RET _GL_VOID GLshort GLshort z _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble w _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat w _GL_VOID_RET _GL_VOID GLint GLint GLint w _GL_VOID_RET _GL_VOID GLshort GLshort GLshort w _GL_VOID_RET _GL_VOID GLdouble GLdouble x2
CCL_NAMESPACE_BEGIN struct Options options
bool libmv_saveImage(const FloatImage &image, const char *prefix, int x0, int y0)
Definition: image.cc:150
void libmv_floatBufferToFloatImage(const float *buffer, int width, int height, int channels, FloatImage *image)
Definition: image.cc:51
#define LIBMV_CONVERT(the_model)
void libmv_configureTrackRegionOptions(const libmv_TrackRegionOptions &options, TrackRegionOptions *track_region_options)
void libmv_regionTrackergetResult(const TrackRegionResult &track_region_result, libmv_TrackRegionResult *result)
int libmv_trackRegion(const libmv_TrackRegionOptions *options, const float *image1, int image1_width, int image1_height, const float *image2, int image2_width, int image2_height, const double *x1, const double *y1, libmv_TrackRegionResult *, double *x2, double *y2)
libmv_TrackRegionDirection
@ LIBMV_TRACK_REGION_FORWARD
@ LIBMV_TRACK_REGION_BACKWARD
void TrackRegion(const FloatImage &image1, const FloatImage &image2, const double *x1, const double *y1, const TrackRegionOptions &options, double *x2, double *y2, TrackRegionResult *result)
Array3Df FloatImage
#define LOG(severity)
Definition: util_logging.h:49