diff --git a/libs/colorspace/gstcolorspace.c b/libs/colorspace/gstcolorspace.c index 83b5705f35..c8056f6aaf 100644 --- a/libs/colorspace/gstcolorspace.c +++ b/libs/colorspace/gstcolorspace.c @@ -23,19 +23,20 @@ #include -extern GstColorSpaceConverter gst_colorspace_rgb2rgb_get_converter(GstColorSpace *space, GstColorSpaceType srcspace, +extern GstColorSpaceConvertFunction gst_colorspace_rgb2rgb_get_converter(GstColorSpaceConverter *space, GstColorSpaceType srcspace, GstColorSpaceType destspace); -extern GstColorSpaceConverter gst_colorspace_yuv2rgb_get_converter(GstColorSpace *space, GstColorSpaceType srcspace, +extern GstColorSpaceConvertFunction gst_colorspace_yuv2rgb_get_converter(GstColorSpaceConverter *space, GstColorSpaceType srcspace, GstColorSpaceType destspace); -extern GstColorSpaceConverter gst_colorspace_rgb2yuv_get_converter(GstColorSpace *space, GstColorSpaceType srcspace, +extern GstColorSpaceConvertFunction gst_colorspace_rgb2yuv_get_converter(GstColorSpaceConverter *space, GstColorSpaceType srcspace, GstColorSpaceType destspace); -extern GstColorSpaceConverter gst_colorspace_yuv2yuv_get_converter(GstColorSpace *space, GstColorSpaceType srcspace, +extern GstColorSpaceConvertFunction gst_colorspace_yuv2yuv_get_converter(GstColorSpaceConverter *space, GstColorSpaceType srcspace, GstColorSpaceType destspace); -GstColorSpace *gst_colorspace_new(int width, int height, GstColorSpaceType srcspace, GstColorSpaceType destspace, GdkVisual *destvisual) +GstColorSpaceConverter *gst_colorspace_converter_new(gint width, gint height, GstColorSpaceType srcspace, + GstColorSpaceType destspace, GdkVisual *destvisual) { - GstColorSpace *new = g_malloc(sizeof(GstColorSpace)); + GstColorSpaceConverter *new = g_malloc(sizeof(GstColorSpaceConverter)); new->width = width; new->height = height; @@ -64,11 +65,13 @@ GstColorSpace *gst_colorspace_new(int width, int height, GstColorSpaceType srcsp } if (new->convert == NULL) { g_print("gst_colorspace: conversion not implemented\n"); + g_free(new); + new = NULL; } return new; } -void gst_colorspace_destroy(GstColorSpace *space) +void gst_colorspace_destroy(GstColorSpaceConverter *space) { if (space->color_tables) g_free(space->color_tables); g_free(space); diff --git a/libs/colorspace/gstcolorspace.h b/libs/colorspace/gstcolorspace.h index 01ee2fe2a0..1704d748ff 100644 --- a/libs/colorspace/gstcolorspace.h +++ b/libs/colorspace/gstcolorspace.h @@ -48,10 +48,10 @@ typedef enum { } GstColorSpaceType; -typedef struct _GstColorSpace GstColorSpace; -typedef void (*GstColorSpaceConverter) (GstColorSpace *space, unsigned char *src, unsigned char *dest); +typedef struct _GstColorSpaceConverter GstColorSpaceConverter; +typedef void (*GstColorSpaceConvertFunction) (GstColorSpaceConverter *space, guchar *src, guchar *dest); -struct _GstColorSpace { +struct _GstColorSpaceConverter { guint width; guint height; GstColorSpaceType srcspace; @@ -61,7 +61,7 @@ struct _GstColorSpace { guint outsize; /* private */ GstColorSpaceYUVTables *color_tables; - GstColorSpaceConverter convert; + GstColorSpaceConvertFunction convert; }; @@ -70,7 +70,9 @@ struct _GstColorSpace { #define GST_COLORSPACE_IS_YUV_TYPE(type) ((type)>=GST_COLORSPACE_YUV_FIRST && \ (type)<=GST_COLORSPACE_YUV_LAST) -GstColorSpace *gst_colorspace_new(int width, int height, GstColorSpaceType srcspace, GstColorSpaceType destspace, GdkVisual *destvisual); -void gst_colorspace_destroy(GstColorSpace *space); +GstColorSpaceConverter *gst_colorspace_converter_new(gint width, gint height, GstColorSpaceType srcspace, + GstColorSpaceType destspace, GdkVisual *destvisual); +#define gst_colorspace_convert(converter, src, dest) (converter)->convert((converter), (src), (dest)) +void gst_colorspace_destroy(GstColorSpaceConverter *space); #endif /* __GST_COLORSPACE_H__ */ diff --git a/libs/colorspace/rgb2rgb.c b/libs/colorspace/rgb2rgb.c index 14d7a1e730..c8a10b2a93 100644 --- a/libs/colorspace/rgb2rgb.c +++ b/libs/colorspace/rgb2rgb.c @@ -22,10 +22,12 @@ #include #include -static void gst_colorspace_rgb_to_rgb_identity(GstColorSpace *space, unsigned char *src, unsigned char *dest); -static void gst_colorspace_rgb24_to_bgr24(GstColorSpace *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_rgb_to_rgb_identity(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_rgb24_to_bgr24(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_rgb32_to_bgr32(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_rgb555_to_rgb565(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); -GstColorSpaceConverter gst_colorspace_rgb2rgb_get_converter(GstColorSpace *space, GstColorSpaceType src, GstColorSpaceType dest) { +GstColorSpaceConvertFunction gst_colorspace_rgb2rgb_get_converter(GstColorSpaceConverter *space, GstColorSpaceType src, GstColorSpaceType dest) { switch(src) { case GST_COLORSPACE_RGB24: space->insize = space->width*space->height*3; @@ -53,24 +55,62 @@ GstColorSpaceConverter gst_colorspace_rgb2rgb_get_converter(GstColorSpace *space break; } break; + case GST_COLORSPACE_RGB32: + space->insize = space->width*space->height*4; + switch(dest) { + case GST_COLORSPACE_BGR32: + space->outsize = space->width*space->height*4; + return gst_colorspace_rgb32_to_bgr32; + case GST_COLORSPACE_RGB32: + space->outsize = space->width*space->height*4; + return gst_colorspace_rgb_to_rgb_identity; + default: + break; + } + break; + case GST_COLORSPACE_BGR32: + space->insize = space->width*space->height*4; + switch(dest) { + case GST_COLORSPACE_RGB32: + space->outsize = space->width*space->height*4; + return gst_colorspace_rgb32_to_bgr32; + case GST_COLORSPACE_BGR32: + space->outsize = space->width*space->height*4; + return gst_colorspace_rgb_to_rgb_identity; + default: + break; + } + break; + case GST_COLORSPACE_BGR555: + space->insize = space->width*space->height*2; + switch(dest) { + case GST_COLORSPACE_RGB555: + space->outsize = space->width*space->height*2; + return gst_colorspace_rgb32_to_bgr32; + case GST_COLORSPACE_BGR565: + space->outsize = space->width*space->height*2; + return gst_colorspace_rgb555_to_rgb565; + default: + break; + } default: break; } - g_print("gst_colorspace: conversion not supported\n"); + g_print("gst_colorspace: conversion not supported %d %d\n", src, dest); return NULL; } -static void gst_colorspace_rgb_to_rgb_identity(GstColorSpace *space, unsigned char *src, unsigned char *dest) +static void gst_colorspace_rgb_to_rgb_identity(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) { memcpy(dest, src, space->outsize); } -static void gst_colorspace_rgb24_to_bgr24(GstColorSpace *space, unsigned char *src, unsigned char *dest) +static void gst_colorspace_rgb24_to_bgr24(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) { gint size; gchar temp; - printf("gst_colorspace_rgb24_to_bgr24 %p %p %d\n", src, dest, space->outsize); + DEBUG("gst_colorspace_rgb24_to_bgr24 %p %p %d\n", src, dest, space->outsize); size = space->outsize/3; @@ -93,3 +133,53 @@ static void gst_colorspace_rgb24_to_bgr24(GstColorSpace *space, unsigned char *s DEBUG("gst_colorspace_rgb24_to_bgr24 end\n"); } +static void gst_colorspace_rgb32_to_bgr32(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) +{ + gint size; + gchar temp; + + DEBUG("gst_colorspace_rgb32_to_bgr32 %p %p %d\n", src, dest, space->outsize); + + size = space->outsize/4; + + if (src == dest) { + while (size--) { + temp = src[0]; + src[0] = src[2]; + src[2] = temp; + src+=4; + } + } + else { + while (size--) { + *dest++ = src[2]; + *dest++ = src[1]; + *dest++ = src[0]; + dest++; + src+=4; + } + } + DEBUG("gst_colorspace_rgb32_to_bgr32 end\n"); +} + +static void gst_colorspace_rgb555_to_rgb565(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) +{ + gint size; + guint32 *srcptr = (guint32 *) src; + guint32 *destptr = (guint32 *) dest; + + DEBUG("gst_colorspace_rgb555_to_rgb565 %p %p %d\n", src, dest, space->outsize); + + size = space->outsize/4; + + if (src == dest) { + while (size--) { + *srcptr += (*srcptr++)&0xFFE0FFE0; + } + } + else { + while (size--) { + *destptr++ = *srcptr + ((*srcptr++)&0xFFE0FFE0); + } + } +} diff --git a/libs/colorspace/yuv2rgb.c b/libs/colorspace/yuv2rgb.c index 3253fc0a24..f6dfb0679e 100644 --- a/libs/colorspace/yuv2rgb.c +++ b/libs/colorspace/yuv2rgb.c @@ -34,13 +34,13 @@ #include "yuv2rgb.h" -static void gst_colorspace_yuv420P_to_rgb32(GstColorSpace *space, unsigned char *src, unsigned char *dest); -static void gst_colorspace_yuv420P_to_bgr32(GstColorSpace *space, unsigned char *src, unsigned char *dest); -static void gst_colorspace_yuv420P_to_bgr32_mmx(GstColorSpace *space, unsigned char *src, unsigned char *dest); -static void gst_colorspace_yuv420P_to_rgb24(GstColorSpace *space, unsigned char *src, unsigned char *dest); -static void gst_colorspace_yuv420P_to_bgr24(GstColorSpace *space, unsigned char *src, unsigned char *dest); -static void gst_colorspace_yuv420P_to_rgb16(GstColorSpace *space, unsigned char *src, unsigned char *dest); -static void gst_colorspace_yuv420P_to_bgr16_mmx(GstColorSpace *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_yuv420P_to_rgb32(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_yuv420P_to_bgr32(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_yuv420P_to_bgr32_mmx(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_yuv420P_to_rgb24(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_yuv420P_to_bgr24(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_yuv420P_to_rgb16(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); +static void gst_colorspace_yuv420P_to_bgr16_mmx(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest); static void gst_colorspace_yuv_to_rgb16(GstColorSpaceYUVTables *tables, unsigned char *lum, @@ -78,7 +78,7 @@ static void gst_colorspace_yuv_to_bgr16_mmx(GstColorSpaceYUVTables *tables, static GstColorSpaceYUVTables * gst_colorspace_init_yuv(long depth, long red_mask, long green_mask, long blue_mask); -GstColorSpaceConverter gst_colorspace_yuv2rgb_get_converter(GstColorSpace *space, GstColorSpaceType src, GstColorSpaceType dest) { +GstColorSpaceConvertFunction gst_colorspace_yuv2rgb_get_converter(GstColorSpaceConverter *space, GstColorSpaceType src, GstColorSpaceType dest) { DEBUG("gst_colorspace_yuv2rgb_get_converter %d %d\n", src, dest); switch(src) { case GST_COLORSPACE_YUV420P: @@ -131,7 +131,7 @@ GstColorSpaceConverter gst_colorspace_yuv2rgb_get_converter(GstColorSpace *space return NULL; } -static void gst_colorspace_yuv420P_to_bgr32(GstColorSpace *space, unsigned char *src, unsigned char *dest) +static void gst_colorspace_yuv420P_to_bgr32(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) { int size; DEBUG("gst_colorspace_yuv420P_to_bgr32\n"); @@ -148,12 +148,11 @@ static void gst_colorspace_yuv420P_to_bgr32(GstColorSpace *space, unsigned char } -static void gst_colorspace_yuv420P_to_rgb32(GstColorSpace *space, unsigned char *src, unsigned char *dest) +static void gst_colorspace_yuv420P_to_rgb32(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) { int size; DEBUG("gst_colorspace_yuv420P_to_rgb32\n"); - size = space->width * space->height; gst_colorspace_yuv_to_rgb32(space->color_tables, @@ -166,7 +165,7 @@ static void gst_colorspace_yuv420P_to_rgb32(GstColorSpace *space, unsigned char } -static void gst_colorspace_yuv420P_to_bgr24(GstColorSpace *space, unsigned char *src, unsigned char *dest) { +static void gst_colorspace_yuv420P_to_bgr24(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) { int size; DEBUG("gst_colorspace_yuv420P_to_bgr24\n"); @@ -181,7 +180,7 @@ static void gst_colorspace_yuv420P_to_bgr24(GstColorSpace *space, unsigned char space->width); } -static void gst_colorspace_yuv420P_to_rgb24(GstColorSpace *space, unsigned char *src, unsigned char *dest) { +static void gst_colorspace_yuv420P_to_rgb24(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) { int size; DEBUG("gst_colorspace_yuv420P_to_rgb24\n"); @@ -197,7 +196,7 @@ static void gst_colorspace_yuv420P_to_rgb24(GstColorSpace *space, unsigned char } -static void gst_colorspace_yuv420P_to_rgb16(GstColorSpace *space, unsigned char *src, unsigned char *dest) { +static void gst_colorspace_yuv420P_to_rgb16(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) { int size; DEBUG("gst_colorspace_yuv420P_to_rgb16\n"); @@ -217,7 +216,7 @@ static void gst_colorspace_yuv420P_to_rgb16(GstColorSpace *space, unsigned char static mmx_t MMX16_redmask = (mmx_t)(long long)0xf800f800f800f800LL; //dd 07c00 7c00h, 07c007c00h static mmx_t MMX16_grnmask = (mmx_t)(long long)0x07e007e007e007e0LL; //dd 003e0 03e0h, 003e003e0h -static void gst_colorspace_yuv420P_to_bgr32_mmx(GstColorSpace *space, unsigned char *src, unsigned char *dest) { +static void gst_colorspace_yuv420P_to_bgr32_mmx(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) { int size; DEBUG("gst_colorspace_yuv420P_to_rgb32_mmx\n"); @@ -232,7 +231,7 @@ static void gst_colorspace_yuv420P_to_bgr32_mmx(GstColorSpace *space, unsigned c space->width); } -static void gst_colorspace_yuv420P_to_bgr16_mmx(GstColorSpace *space, unsigned char *src, unsigned char *dest) { +static void gst_colorspace_yuv420P_to_bgr16_mmx(GstColorSpaceConverter *space, unsigned char *src, unsigned char *dest) { int size; DEBUG("gst_colorspace_yuv420P_to_bgr16_mmx \n");