Skip to content

Commit 0089655

Browse files
Thiemo Wiedemeyerfloe
authored andcommitted
Improved speed of registration by factor 5.
Changed type for registered image to libfreenect2::Frame, so that it is possible to check for correct size. Changed layout of maps to be similar to the image layout. Added a map for precomputed y color indices.
1 parent 42da6d8 commit 0089655

File tree

3 files changed

+65
-57
lines changed

3 files changed

+65
-57
lines changed

examples/protonect/Protonect.cpp

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -124,6 +124,7 @@ int main(int argc, char *argv[])
124124

125125
libfreenect2::SyncMultiFrameListener listener(libfreenect2::Frame::Color | libfreenect2::Frame::Ir | libfreenect2::Frame::Depth);
126126
libfreenect2::FrameMap frames;
127+
libfreenect2::Frame registered(512, 424, 3);
127128

128129
dev->setColorFrameListener(&listener);
129130
dev->setIrAndDepthFrameListener(&listener);
@@ -133,7 +134,6 @@ int main(int argc, char *argv[])
133134
std::cout << "device firmware: " << dev->getFirmwareVersion() << std::endl;
134135

135136
libfreenect2::Registration* registration = new libfreenect2::Registration(dev->getIrCameraParams(), dev->getColorCameraParams());
136-
unsigned char* registered = NULL;
137137

138138
while(!protonect_shutdown)
139139
{
@@ -146,9 +146,8 @@ int main(int argc, char *argv[])
146146
cv::imshow("ir", cv::Mat(ir->height, ir->width, CV_32FC1, ir->data) / 20000.0f);
147147
cv::imshow("depth", cv::Mat(depth->height, depth->width, CV_32FC1, depth->data) / 4500.0f);
148148

149-
if (!registered) registered = new unsigned char[depth->height*depth->width*rgb->bytes_per_pixel];
150-
registration->apply(rgb,depth,registered);
151-
cv::imshow("registered", cv::Mat(depth->height, depth->width, CV_8UC3, registered));
149+
registration->apply(rgb,depth,&registered);
150+
cv::imshow("registered", cv::Mat(registered.height, registered.width, CV_8UC3, registered.data));
152151

153152
int key = cv::waitKey(1);
154153
protonect_shutdown = protonect_shutdown || (key > 0 && ((key & 0xFF) == 27)); // shutdown on escape
@@ -162,7 +161,6 @@ int main(int argc, char *argv[])
162161
dev->stop();
163162
dev->close();
164163

165-
delete[] registered;
166164
delete registration;
167165

168166
return 0;

examples/protonect/include/libfreenect2/registration.h

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -41,10 +41,10 @@ class LIBFREENECT2_API Registration
4141
Registration(Freenect2Device::IrCameraParams depth_p, Freenect2Device::ColorCameraParams rgb_p);
4242

4343
// undistort/register a single depth data point
44-
void apply( int dx, int dy, float dz, float& cx, float &cy);
44+
void apply(int dx, int dy, float dz, float& cx, float &cy) const;
4545

4646
// undistort/register a whole image
47-
void apply(Frame* rgb, Frame* depth, unsigned char* registered);
47+
void apply(const Frame* rgb, const Frame* depth, Frame* registered) const;
4848

4949
private:
5050
void undistort_depth(int dx, int dy, float& mx, float& my);
@@ -53,8 +53,10 @@ class LIBFREENECT2_API Registration
5353
Freenect2Device::IrCameraParams depth;
5454
Freenect2Device::ColorCameraParams color;
5555

56-
float undistort_map[512][424][2];
57-
float depth_to_color_map[512][424][2];
56+
float undistort_map[512 * 424 * 2];
57+
float depth_to_color_map_x[512 * 424];
58+
float depth_to_color_map_y[512 * 424];
59+
int depth_to_color_map_i[512 * 424];
5860
};
5961

6062
} /* namespace libfreenect2 */

examples/protonect/src/registration.cpp

Lines changed: 56 additions & 48 deletions
Original file line numberDiff line numberDiff line change
@@ -72,78 +72,86 @@ void Registration::depth_to_color(float mx, float my, float& rx, float& ry)
7272
(mx * mx * color.my_x2y0) + (my * my * color.my_x0y2) + (mx * my * color.my_x1y1) +
7373
(mx * color.my_x1y0) + (my * color.my_x0y1) + (color.my_x0y0);
7474

75-
rx = wx / (color.fx * color_q);
76-
ry = wy / (color.fx * color_q);
75+
rx = (wx / (color.fx * color_q)) - (color.shift_m / color.shift_d);
76+
ry = (wy / (color.fx * color_q)) * color.fy + color.cy;
7777
}
7878

79-
void Registration::apply( int dx, int dy, float dz, float& cx, float &cy)
79+
void Registration::apply( int dx, int dy, float dz, float& cx, float &cy) const
8080
{
81-
float rx = depth_to_color_map[dx][dy][0];
82-
float ry = depth_to_color_map[dx][dy][1];
83-
84-
rx += (color.shift_m / dz) - (color.shift_m / color.shift_d);
81+
const int index = dx + dy * 512;
82+
float rx = depth_to_color_map_x[index];
83+
cy = depth_to_color_map_y[index];
8584

85+
rx += (color.shift_m / dz);
8686
cx = rx * color.fx + color.cx;
87-
cy = ry * color.fy + color.cy;
8887
}
8988

90-
void Registration::apply(Frame* rgb, Frame* depth, unsigned char* registered)
89+
void Registration::apply(const Frame* rgb, const Frame* depth, Frame* registered) const
9190
{
92-
if (!depth || !rgb || !registered)
91+
if (!depth || !rgb || !registered ||
92+
depth->width != 512 || depth->height != 424 || depth->bytes_per_pixel != 4 ||
93+
rgb->width != 1920 || rgb->height != 1080 || rgb->bytes_per_pixel != 3 ||
94+
registered->width != 512 || registered->height != 424 || registered->bytes_per_pixel != 3)
9395
return;
9496

95-
float* depth_raw = (float*)depth->data;
96-
float cx, cy;
97-
int c_off, d_off, r_off;
98-
99-
for (int x = 0; x < depth->width; x++) {
100-
for (int y = 0; y < depth->height; y++) {
101-
102-
d_off = y*depth->width + x;
103-
r_off = d_off*rgb->bytes_per_pixel;
104-
105-
float z_raw = depth_raw[d_off];
106-
if (z_raw == 0.0) {
107-
registered[r_off+0] = 0;
108-
registered[r_off+1] = 0;
109-
registered[r_off+2] = 0;
110-
continue;
111-
}
112-
113-
apply(x,y,z_raw,cx,cy);
114-
115-
c_off = (round(cx) + round(cy) * rgb->width) * rgb->bytes_per_pixel;
116-
if ((c_off < 0) || (c_off > rgb->width*rgb->height*rgb->bytes_per_pixel)) {
117-
registered[r_off+0] = 0;
118-
registered[r_off+1] = 0;
119-
registered[r_off+2] = 0;
120-
continue;
121-
}
122-
123-
registered[r_off+0] = rgb->data[c_off+0];
124-
registered[r_off+1] = rgb->data[c_off+1];
125-
registered[r_off+2] = rgb->data[c_off+2];
97+
const float *depth_raw = (float*)depth->data;
98+
const float *map_x = depth_to_color_map_x;
99+
const int *map_i = depth_to_color_map_i;
100+
unsigned char *registered_raw = registered->data;
101+
const int size_depth = 512 * 424;
102+
const int size_color = 1920 * 1080 * 3;
103+
104+
for (int i = 0; i < size_depth; ++i, ++registered_raw, ++map_x, ++map_i, ++depth_raw) {
105+
const float z_raw = *depth_raw;
106+
107+
if (z_raw == 0.0) {
108+
*registered_raw = 0;
109+
*++registered_raw = 0;
110+
*++registered_raw = 0;
111+
continue;
126112
}
127-
}
128113

114+
const float rx = (*map_x + (color.shift_m / z_raw)) * color.fx + color.cx;
115+
const int cx = rx + 0.5f; // same as round for positive numbers
116+
const int cy = *map_i;
117+
const int c_off = cx * 3 + cy;
118+
119+
if (c_off < 0 || c_off > size_color || rx < -0.5f) {
120+
*registered_raw = 0;
121+
*++registered_raw = 0;
122+
*++registered_raw = 0;
123+
continue;
124+
}
125+
126+
const unsigned char *rgb_data = rgb->data + c_off;
127+
*registered_raw = *rgb_data;
128+
*++registered_raw = *++rgb_data;
129+
*++registered_raw = *++rgb_data;
130+
}
129131
}
130132

131133
Registration::Registration(Freenect2Device::IrCameraParams depth_p, Freenect2Device::ColorCameraParams rgb_p):
132134
depth(depth_p), color(rgb_p)
133135
{
134136
float mx, my;
135137
float rx, ry;
138+
float *it_undist = undistort_map;
139+
float *map_x = depth_to_color_map_x;
140+
float *map_y = depth_to_color_map_y;
141+
int *map_i = depth_to_color_map_i;
136142

137-
for (int x = 0; x < 512; x++)
138-
for (int y = 0; y < 424; y++) {
143+
for (int y = 0; y < 424; y++) {
144+
for (int x = 0; x < 512; x++) {
139145

140146
undistort_depth(x,y,mx,my);
141-
undistort_map[x][y][0] = mx;
142-
undistort_map[x][y][1] = my;
147+
*it_undist++ = mx;
148+
*it_undist++ = my;
143149

144150
depth_to_color(mx,my,rx,ry);
145-
depth_to_color_map[x][y][0] = rx;
146-
depth_to_color_map[x][y][1] = ry;
151+
*map_x++ = rx;
152+
*map_y++ = ry;
153+
*map_i++ = round(ry) * 1920 * 3;
154+
}
147155
}
148156
}
149157

0 commit comments

Comments
 (0)