|
From: libvidcap c. m. <lib...@li...> - 2007-09-11 13:15:50
|
Revision: 11
http://libvidcap.svn.sourceforge.net/libvidcap/?rev=11&view=rev
Author: bcholew
Date: 2007-09-11 06:15:47 -0700 (Tue, 11 Sep 2007)
Log Message:
-----------
Correct the checks on destination buffer size when converting to i420. Add function conv_yvu9_to_i420 to format conversion repertoire.
Modified Paths:
--------------
trunk/src/conv.c
trunk/src/conv_to_i420.c
Modified: trunk/src/conv.c
===================================================================
--- trunk/src/conv.c 2007-09-08 20:22:13 UTC (rev 10)
+++ trunk/src/conv.c 2007-09-11 13:15:47 UTC (rev 11)
@@ -28,6 +28,7 @@
int conv_2vuy_to_i420(int w, int h, const char * s, char * d, int ds);
int conv_2vuy_to_yuy2(int w, int h, const char * s, char * d, int ds);
int conv_rgb24_to_rgb32(int w, int h, const char * s, char * d, int ds);
+int conv_yvu9_to_i420(int w, int h, const char * s, char * d, int ds);
struct conv_info
{
@@ -48,6 +49,8 @@
{ VIDCAP_FOURCC_2VUY, VIDCAP_FOURCC_YUY2, conv_2vuy_to_yuy2 },
{ VIDCAP_FOURCC_2VUY, VIDCAP_FOURCC_I420, conv_2vuy_to_i420 },
{ VIDCAP_FOURCC_RGB24, VIDCAP_FOURCC_RGB32, conv_rgb24_to_rgb32 },
+
+ { VIDCAP_FOURCC_YVU9, VIDCAP_FOURCC_I420, conv_yvu9_to_i420 },
};
static const int conv_list_len = sizeof(conv_list) / sizeof(struct conv_info);
Modified: trunk/src/conv_to_i420.c
===================================================================
--- trunk/src/conv_to_i420.c 2007-09-08 20:22:13 UTC (rev 10)
+++ trunk/src/conv_to_i420.c 2007-09-11 13:15:47 UTC (rev 11)
@@ -23,6 +23,7 @@
*
*/
+#include <string.h>
#include <vidcap/converters.h>
#include "logging.h"
@@ -50,7 +51,7 @@
int i, j;
- if ( dest_size < width * height * 4 / 3 )
+ if ( dest_size < width * height * 3 / 2 )
return -1;
/* yuy2 has a vertical sampling period (for u and v)
@@ -98,7 +99,7 @@
int i, j;
- if ( dest_size < width * height * 4 / 3 )
+ if ( dest_size < width * height * 3 / 2 )
return -1;
for ( i = 0; i < height / 2; ++i )
@@ -125,3 +126,50 @@
return 0;
}
+/* yvu9 is like i420, but the u and v planes
+ * are reversed and 4x4 subsampled, instead of 2x2
+ */
+int
+conv_yvu9_to_i420(int width, int height,
+ const char * src,
+ char * dst, int dest_size)
+{
+ char * dst_y = dst;
+ char * dst_u_even = dst + width * height;
+ char * dst_u_odd = dst_u_even + width / 2;
+ char * dst_v_even = dst_u_even + width * height / 4;
+ char * dst_v_odd = dst_v_even + width / 2;
+ const char * src_y = src;
+ const char * src_v = src_y + width * height;
+ const char * src_u = src_v + width * height / 16;
+
+ int i, j;
+
+ if ( dest_size < width * height * 3 / 2 )
+ return -1;
+
+ memcpy(dst_y, src_y, height * width);
+
+ for ( i = 0; i < height / 4; ++i )
+ {
+ for ( j = 0; j < width / 4; ++j )
+ {
+ *dst_u_even++ = *src_u;
+ *dst_u_even++ = *src_u;
+ *dst_u_odd++ = *src_u;
+ *dst_u_odd++ = *src_u++;
+
+ *dst_v_even++ = *src_v;
+ *dst_v_even++ = *src_v;
+ *dst_v_odd++ = *src_v;
+ *dst_v_odd++ = *src_v++;
+ }
+
+ dst_u_even += width / 2;
+ dst_u_odd += width / 2;
+ dst_v_even += width / 2;
+ dst_v_odd += width / 2;
+ }
+
+ return 0;
+}
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
|