diff options
author | hans@rhel5-devel.localdomain <hans@rhel5-devel.localdomain> | 2009-03-11 13:16:01 +0100 |
---|---|---|
committer | hans@rhel5-devel.localdomain <hans@rhel5-devel.localdomain> | 2009-03-11 13:16:01 +0100 |
commit | d02d1e3c9f20e691d7d3ff62275d57bfc4766e19 (patch) | |
tree | 7a64e3e894c9d789abf630c0728050d6dec0ef55 /v4l2-apps/libv4l/libv4lconvert | |
parent | f7cf759077f7b829a1cb451fcef9868b693ec3fe (diff) | |
download | mediapointer-dvb-s2-d02d1e3c9f20e691d7d3ff62275d57bfc4766e19.tar.gz mediapointer-dvb-s2-d02d1e3c9f20e691d7d3ff62275d57bfc4766e19.tar.bz2 |
libv4l: add UYVY support
From: Julien BLACHE <jb@jblache.org>
Attached is a patch to add UYVY support to libv4lconvert. It's
obviously a shameless respin of the YVYU conversion routines :P
Tested on a USB Apple iSight, which only supports UYVY.
Priority: normal
Signed-off-by: Julien BLACHE <jb@jblache.org>
Signed-off-by: Hans de Goede <hdegoede@redhat.com>
Diffstat (limited to 'v4l2-apps/libv4l/libv4lconvert')
-rw-r--r-- | v4l2-apps/libv4l/libv4lconvert/libv4lconvert-priv.h | 9 | ||||
-rw-r--r-- | v4l2-apps/libv4l/libv4lconvert/libv4lconvert.c | 18 | ||||
-rw-r--r-- | v4l2-apps/libv4l/libv4lconvert/rgbyuv.c | 91 |
3 files changed, 118 insertions, 0 deletions
diff --git a/v4l2-apps/libv4l/libv4lconvert/libv4lconvert-priv.h b/v4l2-apps/libv4l/libv4lconvert/libv4lconvert-priv.h index 55a5b49be..c268375c8 100644 --- a/v4l2-apps/libv4l/libv4lconvert/libv4lconvert-priv.h +++ b/v4l2-apps/libv4l/libv4lconvert/libv4lconvert-priv.h @@ -132,6 +132,15 @@ void v4lconvert_yvyu_to_bgr24(const unsigned char *src, unsigned char *dst, void v4lconvert_yvyu_to_yuv420(const unsigned char *src, unsigned char *dst, int width, int height, int yvu); +void v4lconvert_uyvy_to_rgb24(const unsigned char *src, unsigned char *dst, + int width, int height); + +void v4lconvert_uyvy_to_bgr24(const unsigned char *src, unsigned char *dst, + int width, int height); + +void v4lconvert_uyvy_to_yuv420(const unsigned char *src, unsigned char *dst, + int width, int height, int yvu); + void v4lconvert_swap_rgb(const unsigned char *src, unsigned char *dst, int width, int height); diff --git a/v4l2-apps/libv4l/libv4lconvert/libv4lconvert.c b/v4l2-apps/libv4l/libv4lconvert/libv4lconvert.c index 889f7463a..c01286b73 100644 --- a/v4l2-apps/libv4l/libv4lconvert/libv4lconvert.c +++ b/v4l2-apps/libv4l/libv4lconvert/libv4lconvert.c @@ -44,6 +44,7 @@ static const struct v4lconvert_pixfmt supported_src_pixfmts[] = { SUPPORTED_DST_PIXFMTS, { V4L2_PIX_FMT_YUYV, 0 }, { V4L2_PIX_FMT_YVYU, 0 }, + { V4L2_PIX_FMT_UYVY, 0 }, { V4L2_PIX_FMT_SBGGR8, 0 }, { V4L2_PIX_FMT_SGBRG8, 0 }, { V4L2_PIX_FMT_SGRBG8, 0 }, @@ -718,6 +719,23 @@ static int v4lconvert_convert_pixfmt(struct v4lconvert_data *data, } break; + case V4L2_PIX_FMT_UYVY: + switch (dest_pix_fmt) { + case V4L2_PIX_FMT_RGB24: + v4lconvert_uyvy_to_rgb24(src, dest, width, height); + break; + case V4L2_PIX_FMT_BGR24: + v4lconvert_uyvy_to_bgr24(src, dest, width, height); + break; + case V4L2_PIX_FMT_YUV420: + v4lconvert_uyvy_to_yuv420(src, dest, width, height, 0); + break; + case V4L2_PIX_FMT_YVU420: + v4lconvert_uyvy_to_yuv420(src, dest, width, height, 1); + break; + } + break; + default: V4LCONVERT_ERR("Unknown src format in conversion\n"); errno = EINVAL; diff --git a/v4l2-apps/libv4l/libv4lconvert/rgbyuv.c b/v4l2-apps/libv4l/libv4lconvert/rgbyuv.c index d5feb457e..ec297b1f7 100644 --- a/v4l2-apps/libv4l/libv4lconvert/rgbyuv.c +++ b/v4l2-apps/libv4l/libv4lconvert/rgbyuv.c @@ -378,6 +378,97 @@ void v4lconvert_yvyu_to_yuv420(const unsigned char *src, unsigned char *dest, } } +void v4lconvert_uyvy_to_bgr24(const unsigned char *src, unsigned char *dest, + int width, int height) +{ + int j; + + while (--height >= 0) { + for (j = 0; j < width; j += 2) { + int u = src[0]; + int v = src[2]; + int u1 = (((u - 128) << 7) + (u - 128)) >> 6; + int rg = (((u - 128) << 1) + (u - 128) + + ((v - 128) << 2) + ((v - 128) << 1)) >> 3; + int v1 = (((v - 128) << 1) + (v - 128)) >> 1; + + *dest++ = CLIP(src[1] + u1); + *dest++ = CLIP(src[1] - rg); + *dest++ = CLIP(src[1] + v1); + + *dest++ = CLIP(src[3] + u1); + *dest++ = CLIP(src[3] - rg); + *dest++ = CLIP(src[3] + v1); + src += 4; + } + } +} + +void v4lconvert_uyvy_to_rgb24(const unsigned char *src, unsigned char *dest, + int width, int height) +{ + int j; + + while (--height >= 0) { + for (j = 0; j < width; j += 2) { + int u = src[0]; + int v = src[2]; + int u1 = (((u - 128) << 7) + (u - 128)) >> 6; + int rg = (((u - 128) << 1) + (u - 128) + + ((v - 128) << 2) + ((v - 128) << 1)) >> 3; + int v1 = (((v - 128) << 1) + (v - 128)) >> 1; + + *dest++ = CLIP(src[1] + v1); + *dest++ = CLIP(src[1] - rg); + *dest++ = CLIP(src[1] + u1); + + *dest++ = CLIP(src[3] + v1); + *dest++ = CLIP(src[3] - rg); + *dest++ = CLIP(src[3] + u1); + src += 4; + } + } +} + +void v4lconvert_uyvy_to_yuv420(const unsigned char *src, unsigned char *dest, + int width, int height, int yvu) +{ + int i, j; + const unsigned char *src1; + unsigned char *udest, *vdest; + + /* copy the Y values */ + src1 = src; + for (i = 0; i < height; i++) { + for (j = 0; j < width; j += 2) { + *dest++ = src1[1]; + *dest++ = src1[3]; + src1 += 4; + } + } + + /* copy the U and V values */ + src++; /* point to V */ + src1 = src + width * 2; /* next line */ + if (yvu) { + vdest = dest; + udest = dest + width * height / 4; + } else { + udest = dest; + vdest = dest + width * height / 4; + } + for (i = 0; i < height; i += 2) { + for (j = 0; j < width; j += 2) { + *udest++ = ((int) src[0] + src1[0]) / 2; /* U */ + *vdest++ = ((int) src[2] + src1[2]) / 2; /* V */ + src += 4; + src1 += 4; + } + src = src1; + src1 += width * 2; + } +} + void v4lconvert_swap_rgb(const unsigned char *src, unsigned char *dst, int width, int height) { |