From 3c967ffc03bd78b1d697140ae71c81c348db3b6a Mon Sep 17 00:00:00 2001 From: David Schleef Date: Fri, 4 Oct 2002 06:49:51 +0000 Subject: [PATCH] Lots of new goodness. Will negotiate caps and output images in about 20 different formats. Some code cleanup. Fixe... Original commit message from CVS: Lots of new goodness. Will negotiate caps and output images in about 20 different formats. Some code cleanup. Fixed YUV color values for -I and Q. --- gst/videotestsrc/gstvideotestsrc.c | 1139 +++++++++++++++++++++++------------- gst/videotestsrc/gstvideotestsrc.h | 7 +- 2 files changed, 746 insertions(+), 400 deletions(-) diff --git a/gst/videotestsrc/gstvideotestsrc.c b/gst/videotestsrc/gstvideotestsrc.c index cd76f78..76031fd 100644 --- a/gst/videotestsrc/gstvideotestsrc.c +++ b/gst/videotestsrc/gstvideotestsrc.c @@ -24,6 +24,28 @@ #include #include +typedef struct paintinfo_struct paintinfo; +struct paintinfo_struct +{ + unsigned char *dest; + unsigned char *yp, *up, *vp; + int width; + int height; + int Y, U, V; + void (*paint_hline) (paintinfo * p, int x, int y, int w); +}; + +struct fourcc_list_struct +{ + char *fourcc; + int bitspp; + void (*paint_setup) (paintinfo * p, char *dest); + void (*paint_hline) (paintinfo * p, int x, int y, int w); +}; +static struct fourcc_list_struct fourcc_list[]; +static int n_fourccs; + +static int paintrect_find_fourcc (int find_fourcc); /* elementfactory information */ @@ -38,113 +60,93 @@ static GstElementDetails videotestsrc_details = { }; /* GstVideotestsrc signals and args */ -enum { +enum +{ /* FILL ME */ LAST_SIGNAL }; -enum { +enum +{ ARG_0, ARG_WIDTH, ARG_HEIGHT, - ARG_METHOD, + ARG_FOURCC, /* FILL ME */ }; -GST_PAD_TEMPLATE_FACTORY (src_templ, - "src", - GST_PAD_SRC, - GST_PAD_ALWAYS, - GST_CAPS_NEW ( - "videotestsrc_caps", - "video/raw", - "format", GST_PROPS_LIST( - GST_PROPS_FOURCC (GST_MAKE_FOURCC ('I','4','2','0')), - GST_PROPS_FOURCC (GST_MAKE_FOURCC ('Y','V','1','2')), - GST_PROPS_FOURCC (GST_MAKE_FOURCC ('R','G','B',' ')) - ), - "width", GST_PROPS_INT(640), - "height", GST_PROPS_INT(480) - ) -) - -#define GST_TYPE_VIDEOTESTSRC_METHOD (gst_videotestsrc_method_get_type()) -static GType -gst_videotestsrc_method_get_type (void) -{ - static GType videotestsrc_method_type = 0; - static GEnumValue videotestsrc_methods[] = { - { GST_VIDEOTESTSRC_POINT_SAMPLE, "0", "Point Sample" }, - { GST_VIDEOTESTSRC_NEAREST, "1", "Nearest" }, - { GST_VIDEOTESTSRC_BILINEAR, "2", "Bilinear" }, - { GST_VIDEOTESTSRC_BICUBIC, "3", "Bicubic" }, - { 0, NULL, NULL }, - }; - if (!videotestsrc_method_type) { - videotestsrc_method_type = g_enum_register_static ("GstVideotestsrcMethod", videotestsrc_methods); - } - return videotestsrc_method_type; -} +GST_PAD_TEMPLATE_FACTORY (videotestsrc_src_template_factory, + "src", + GST_PAD_SRC, + GST_PAD_ALWAYS, + GST_CAPS_NEW ("videotestsrc_src", + "video/raw", + "width", GST_PROPS_INT_RANGE (0, G_MAXINT), + "height", GST_PROPS_INT_RANGE (0, G_MAXINT) + ) + ); -static void gst_videotestsrc_class_init (GstVideotestsrcClass *klass); -static void gst_videotestsrc_init (GstVideotestsrc *videotestsrc); -static GstElementStateReturn gst_videotestsrc_change_state (GstElement *element); +static void gst_videotestsrc_class_init (GstVideotestsrcClass * klass); +static void gst_videotestsrc_init (GstVideotestsrc * videotestsrc); +static GstElementStateReturn gst_videotestsrc_change_state (GstElement * element); -static void gst_videotestsrc_set_property (GObject *object, guint prop_id, const GValue *value, GParamSpec *pspec); -static void gst_videotestsrc_get_property (GObject *object, guint prop_id, GValue *value, GParamSpec *pspec); +static void gst_videotestsrc_set_property (GObject * object, guint prop_id, + const GValue * value, GParamSpec * pspec); +static void gst_videotestsrc_get_property (GObject * object, guint prop_id, GValue * value, + GParamSpec * pspec); -static GstBuffer * gst_videotestsrc_get (GstPad *pad); +static GstBuffer *gst_videotestsrc_get (GstPad * pad); static GstElementClass *parent_class = NULL; -void gst_videotestsrc_setup (GstVideotestsrc *v); -static void random_chars(unsigned char *dest, int nbytes); -void gst_videotestsrc_smpte_I420 (GstVideotestsrc *v, unsigned char *dest, int w, int h); -void gst_videotestsrc_smpte_YV12 (GstVideotestsrc *v, unsigned char *dest, int w, int h); -void gst_videotestsrc_smpte_RGB (GstVideotestsrc *v, unsigned char *dest, int w, int h); +static void gst_videotestsrc_setup (GstVideotestsrc * v); +static void random_chars (unsigned char *dest, int nbytes); +static void gst_videotestsrc_smpte_yuv (GstVideotestsrc * v, unsigned char *dest, int w, int h); +static void gst_videotestsrc_smpte_RGB (GstVideotestsrc * v, unsigned char *dest, int w, int h); +#if 0 +static void gst_videotestsrc_colors_yuv (GstVideotestsrc * v, unsigned char *dest, int w, int h); +#endif -GType +static GType gst_videotestsrc_get_type (void) { static GType videotestsrc_type = 0; if (!videotestsrc_type) { static const GTypeInfo videotestsrc_info = { - sizeof(GstVideotestsrcClass), NULL, + sizeof (GstVideotestsrcClass), NULL, NULL, - (GClassInitFunc)gst_videotestsrc_class_init, + (GClassInitFunc) gst_videotestsrc_class_init, NULL, NULL, - sizeof(GstVideotestsrc), + sizeof (GstVideotestsrc), 0, - (GInstanceInitFunc)gst_videotestsrc_init, + (GInstanceInitFunc) gst_videotestsrc_init, }; - videotestsrc_type = g_type_register_static(GST_TYPE_ELEMENT, "GstVideotestsrc", &videotestsrc_info, 0); + + videotestsrc_type = + g_type_register_static (GST_TYPE_ELEMENT, "GstVideotestsrc", &videotestsrc_info, 0); } return videotestsrc_type; } static void -gst_videotestsrc_class_init (GstVideotestsrcClass *klass) +gst_videotestsrc_class_init (GstVideotestsrcClass * klass) { GObjectClass *gobject_class; GstElementClass *gstelement_class; - gobject_class = (GObjectClass*)klass; - gstelement_class = (GstElementClass*)klass; + gobject_class = (GObjectClass *) klass; + gstelement_class = (GstElementClass *) klass; - g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_WIDTH, - g_param_spec_int("width","width","width", - G_MININT,G_MAXINT,0,G_PARAM_READWRITE)); /* CHECKME */ - g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_HEIGHT, - g_param_spec_int("height","height","height", - G_MININT,G_MAXINT,0,G_PARAM_READWRITE)); /* CHECKME */ - g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_METHOD, - g_param_spec_enum("method","method","method", - GST_TYPE_VIDEOTESTSRC_METHOD,0,G_PARAM_READWRITE)); /* CHECKME! */ + g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_WIDTH, g_param_spec_int ("width", "width", "width", G_MININT, G_MAXINT, 0, G_PARAM_READWRITE)); /* CHECKME */ + g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_HEIGHT, g_param_spec_int ("height", "height", "height", G_MININT, G_MAXINT, 0, G_PARAM_READWRITE)); /* CHECKME */ + g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_FOURCC, + g_param_spec_string ("fourcc", "fourcc", "fourcc", + NULL, G_PARAM_READWRITE)); - parent_class = g_type_class_ref(GST_TYPE_ELEMENT); + parent_class = g_type_class_ref (GST_TYPE_ELEMENT); gobject_class->set_property = gst_videotestsrc_set_property; gobject_class->get_property = gst_videotestsrc_get_property; @@ -153,11 +155,11 @@ gst_videotestsrc_class_init (GstVideotestsrcClass *klass) } static GstPadConnectReturn -gst_videotestsrc_srcconnect (GstPad *pad, GstCaps *caps) +gst_videotestsrc_srcconnect (GstPad * pad, GstCaps * caps) { GstVideotestsrc *videotestsrc; - GST_DEBUG(0,"gst_videotestsrc_srcconnect"); + GST_DEBUG (0, "gst_videotestsrc_srcconnect"); videotestsrc = GST_VIDEOTESTSRC (gst_pad_get_parent (pad)); #if 0 @@ -170,144 +172,171 @@ gst_videotestsrc_srcconnect (GstPad *pad, GstCaps *caps) gst_caps_get_int (caps, "width", &videotestsrc->width); gst_caps_get_int (caps, "height", &videotestsrc->height); - GST_DEBUG (0,"format is 0x%08x\n",videotestsrc->format); - - switch(videotestsrc->format){ - case GST_MAKE_FOURCC('R','G','B',' '): - videotestsrc->make_image = gst_videotestsrc_smpte_RGB; - videotestsrc->bpp = 16; - break; - case GST_MAKE_FOURCC('I','4','2','0'): - videotestsrc->make_image = gst_videotestsrc_smpte_I420; - videotestsrc->bpp = 12; - break; - case GST_MAKE_FOURCC('Y','U','Y','V'): - //videotestsrc->make_image = gst_videotestsrc_smpte_YUYV; - return GST_PAD_CONNECT_REFUSED; - break; - case GST_MAKE_FOURCC('Y','V','1','2'): - videotestsrc->make_image = gst_videotestsrc_smpte_YV12; - videotestsrc->bpp = 12; - break; - default: - return GST_PAD_CONNECT_REFUSED; + GST_DEBUG (0, "format is 0x%08x\n", videotestsrc->format); + + printf ("videotestsrc: caps FOURCC 0x%08x, forced FOURCC 0x%08x\n", + videotestsrc->format, videotestsrc->forced_format); + + if (videotestsrc->forced_format && videotestsrc->format != videotestsrc->forced_format) { + return GST_PAD_CONNECT_REFUSED; } - GST_DEBUG (0,"size %d x %d",videotestsrc->width, videotestsrc->height); + printf ("videotestsrc: using FOURCC 0x%08x\n", videotestsrc->format); + + if (videotestsrc->format == GST_MAKE_FOURCC ('R', 'G', 'B', ' ')) { + videotestsrc->make_image = gst_videotestsrc_smpte_RGB; + videotestsrc->bpp = 16; + } else { + int index; + + index = paintrect_find_fourcc (videotestsrc->format); + videotestsrc->make_image = gst_videotestsrc_smpte_yuv; + /* videotestsrc->make_image = gst_videotestsrc_colors_yuv; */ + videotestsrc->bpp = fourcc_list[index].bitspp; + } + + GST_DEBUG (0, "size %d x %d", videotestsrc->width, videotestsrc->height); return GST_PAD_CONNECT_OK; } static GstElementStateReturn -gst_videotestsrc_change_state (GstElement *element) +gst_videotestsrc_change_state (GstElement * element) { - GstVideotestsrc *v; + GstVideotestsrc *v; + + v = GST_VIDEOTESTSRC (element); - v = GST_VIDEOTESTSRC(element); + switch (GST_STATE_TRANSITION (element)) { + case GST_STATE_PAUSED_TO_PLAYING: + v->pool = gst_pad_get_bufferpool (v->srcpad); + break; + case GST_STATE_PLAYING_TO_PAUSED: + v->pool = NULL; + break; + } - switch(GST_STATE_TRANSITION(element)){ - case GST_STATE_PAUSED_TO_PLAYING: - v->pool = gst_pad_get_bufferpool(v->srcpad); - break; - case GST_STATE_PLAYING_TO_PAUSED: - v->pool = NULL; - break; - } + parent_class->change_state (element); - parent_class->change_state(element); + return GST_STATE_SUCCESS; +} - return GST_STATE_SUCCESS; +static GstCaps * +gst_videotestsrc_get_capslist (void) +{ + static GstCaps *capslist = NULL; + GstCaps *caps; + int i; + + if (capslist) + return capslist; + + for (i = 0; i < n_fourccs; i++) { + char *s = fourcc_list[i].fourcc; + int fourcc = GST_MAKE_FOURCC (s[0], s[1], s[2], s[3]); + + caps = gst_caps_new ("videotestsrc_filter", + "video/raw", + gst_props_new ("format", GST_PROPS_FOURCC (fourcc), + "width", GST_PROPS_INT (640), "height", GST_PROPS_INT (480) + )); + capslist = gst_caps_append (capslist, caps); + } + + return capslist; } -static void -gst_videotestsrc_init (GstVideotestsrc *videotestsrc) +static GstCaps * +gst_videotestsrc_getcaps (GstPad * pad, GstCaps * caps) { - GST_DEBUG(0,"gst_videotestsrc_init"); + GstVideotestsrc *vts; + + vts = GST_VIDEOTESTSRC (gst_pad_get_parent (pad)); + + if (vts->forced_format != 0) { + return GST_CAPS_NEW ("videotestsrc_filter", + "video/raw", + "format", GST_PROPS_FOURCC (vts->forced_format), + "width", GST_PROPS_INT (640), "height", GST_PROPS_INT (480) + ); + } else { + return gst_videotestsrc_get_capslist (); + } +} - /*gst_pad_set_negotiate_function(videotestsrc->sinkpad,videotestsrc_negotiate_sink); */ - //gst_element_add_pad(GST_ELEMENT(videotestsrc),videotestsrc->sinkpad); - //gst_pad_set_chain_function(videotestsrc->sinkpad,gst_videotestsrc_chain); +static void +gst_videotestsrc_init (GstVideotestsrc * videotestsrc) +{ + GST_DEBUG (0, "gst_videotestsrc_init"); - videotestsrc->srcpad = gst_pad_new_from_template ( - GST_PAD_TEMPLATE_GET (src_templ), "src"); + videotestsrc->srcpad = + gst_pad_new_from_template (GST_PAD_TEMPLATE_GET (videotestsrc_src_template_factory), "src"); /*gst_pad_set_negotiate_function(videotestsrc->srcpad,videotestsrc_negotiate_src); */ - gst_element_add_pad(GST_ELEMENT(videotestsrc),videotestsrc->srcpad); - gst_pad_set_get_function(videotestsrc->srcpad,gst_videotestsrc_get); - gst_pad_set_connect_function(videotestsrc->srcpad,gst_videotestsrc_srcconnect); + gst_pad_set_getcaps_function (videotestsrc->srcpad, gst_videotestsrc_getcaps); + gst_element_add_pad (GST_ELEMENT (videotestsrc), videotestsrc->srcpad); + gst_pad_set_get_function (videotestsrc->srcpad, gst_videotestsrc_get); + gst_pad_set_connect_function (videotestsrc->srcpad, gst_videotestsrc_srcconnect); -#if 0 - "bpp", GST_PROPS_INT(16), - "depth", GST_PROPS_INT(16), - "endianness", GST_PROPS_INT(1234), - "red_mask", GST_PROPS_INT(63488), - "green_mask", GST_PROPS_INT(2016), - "blue_mask", GST_PROPS_INT(31), -#endif videotestsrc->width = 640; videotestsrc->height = 480; videotestsrc->timestamp = 0; - videotestsrc->interval = GST_SECOND/30; + videotestsrc->interval = GST_SECOND / 1; videotestsrc->pool = NULL; } static GstBuffer * -gst_videotestsrc_get (GstPad *pad) +gst_videotestsrc_get (GstPad * pad) { GstVideotestsrc *videotestsrc; gulong newsize; GstBuffer *buf; - GST_DEBUG (0,"gst_videotestsrc_get"); + GST_DEBUG (0, "gst_videotestsrc_get"); g_return_val_if_fail (pad != NULL, NULL); g_return_val_if_fail (GST_IS_PAD (pad), NULL); videotestsrc = GST_VIDEOTESTSRC (gst_pad_get_parent (pad)); -#if 0 - /* XXX this is wrong for anything but I420 */ - newsize = videotestsrc->width*videotestsrc->height + - videotestsrc->width*videotestsrc->height/2; -#endif - /* XXX this is wrong for anything but RGB16 */ - newsize = (videotestsrc->width*videotestsrc->height*videotestsrc->bpp)>>3; + newsize = (videotestsrc->width * videotestsrc->height * videotestsrc->bpp) >> 3; - GST_DEBUG(0,"size=%ld %dx%d",newsize, - videotestsrc->width, videotestsrc->height); + GST_DEBUG (0, "size=%ld %dx%d", newsize, videotestsrc->width, videotestsrc->height); buf = NULL; - if(videotestsrc->pool){ - buf = gst_buffer_new_from_pool(videotestsrc->pool, 0, 0); + if (videotestsrc->pool) { + buf = gst_buffer_new_from_pool (videotestsrc->pool, 0, 0); } - if(!buf){ - buf = gst_buffer_new(); - GST_BUFFER_SIZE(buf) = newsize; - GST_BUFFER_DATA(buf) = g_malloc (newsize); + if (!buf) { + buf = gst_buffer_new (); + GST_BUFFER_SIZE (buf) = newsize; + GST_BUFFER_DATA (buf) = g_malloc (newsize); } - g_return_val_if_fail(GST_BUFFER_DATA(buf) != NULL, NULL); + g_return_val_if_fail (GST_BUFFER_DATA (buf) != NULL, NULL); videotestsrc->timestamp += videotestsrc->interval; - GST_BUFFER_TIMESTAMP(buf) = videotestsrc->timestamp; + GST_BUFFER_TIMESTAMP (buf) = videotestsrc->timestamp; - videotestsrc->make_image(videotestsrc, (void *)GST_BUFFER_DATA(buf), - videotestsrc->width, videotestsrc->height); + videotestsrc->make_image (videotestsrc, (void *) GST_BUFFER_DATA (buf), + videotestsrc->width, videotestsrc->height); return buf; } static void -gst_videotestsrc_set_property (GObject *object, guint prop_id, const GValue *value, GParamSpec *pspec) +gst_videotestsrc_set_property (GObject * object, guint prop_id, const GValue * value, + GParamSpec * pspec) { GstVideotestsrc *src; + const gchar *s; /* it's not null if we got it, but it might not be ours */ - g_return_if_fail(GST_IS_VIDEOTESTSRC(object)); - src = GST_VIDEOTESTSRC(object); + g_return_if_fail (GST_IS_VIDEOTESTSRC (object)); + src = GST_VIDEOTESTSRC (object); - GST_DEBUG(0,"gst_videotestsrc_set_property"); + GST_DEBUG (0, "gst_videotestsrc_set_property"); switch (prop_id) { case ARG_WIDTH: src->width = g_value_get_int (value); @@ -315,8 +344,12 @@ gst_videotestsrc_set_property (GObject *object, guint prop_id, const GValue *val case ARG_HEIGHT: src->height = g_value_get_int (value); break; - case ARG_METHOD: - src->method = g_value_get_enum (value); + case ARG_FOURCC: + s = g_value_get_string (value); + if (strlen (s) == 4) { + src->forced_format = GST_MAKE_FOURCC (s[0], s[1], s[2], s[3]); + printf ("forcing FOURCC to 0x%08x\n", src->forced_format); + } break; default: break; @@ -324,13 +357,13 @@ gst_videotestsrc_set_property (GObject *object, guint prop_id, const GValue *val } static void -gst_videotestsrc_get_property (GObject *object, guint prop_id, GValue *value, GParamSpec *pspec) +gst_videotestsrc_get_property (GObject * object, guint prop_id, GValue * value, GParamSpec * pspec) { GstVideotestsrc *src; /* it's not null if we got it, but it might not be ours */ - g_return_if_fail(GST_IS_VIDEOTESTSRC(object)); - src = GST_VIDEOTESTSRC(object); + g_return_if_fail (GST_IS_VIDEOTESTSRC (object)); + src = GST_VIDEOTESTSRC (object); switch (prop_id) { case ARG_WIDTH: @@ -339,8 +372,9 @@ gst_videotestsrc_get_property (GObject *object, guint prop_id, GValue *value, GP case ARG_HEIGHT: g_value_set_int (value, src->height); break; - case ARG_METHOD: - g_value_set_enum (value, src->method); + case ARG_FOURCC: + /* FIXME */ + /* g_value_set_int (value, src->forced_format); */ break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); @@ -350,16 +384,16 @@ gst_videotestsrc_get_property (GObject *object, guint prop_id, GValue *value, GP static gboolean -plugin_init (GModule *module, GstPlugin *plugin) +plugin_init (GModule * module, GstPlugin * plugin) { GstElementFactory *factory; /* create an elementfactory for the videotestsrc element */ - factory = gst_element_factory_new("videotestsrc",GST_TYPE_VIDEOTESTSRC, - &videotestsrc_details); - g_return_val_if_fail(factory != NULL, FALSE); + factory = gst_element_factory_new ("videotestsrc", GST_TYPE_VIDEOTESTSRC, &videotestsrc_details); + g_return_val_if_fail (factory != NULL, FALSE); - gst_element_factory_add_pad_template (factory, GST_PAD_TEMPLATE_GET (src_templ)); + gst_element_factory_add_pad_template (factory, + GST_PAD_TEMPLATE_GET (videotestsrc_src_template_factory)); gst_plugin_add_feature (plugin, GST_PLUGIN_FEATURE (factory)); @@ -377,275 +411,588 @@ GstPluginDesc plugin_desc = { /* Non-GST specific stuff */ -void -gst_videotestsrc_setup (GstVideotestsrc *v) +static void +gst_videotestsrc_setup (GstVideotestsrc * v) +{ + +} + +static unsigned char +random_char (void) +{ + static unsigned int state; + + state *= 1103515245; + state += 12345; + return (state >> 16); +} + +static void +random_chars (unsigned char *dest, int nbytes) +{ + int i; + static unsigned int state; + + for (i = 0; i < nbytes; i++) { + state *= 1103515245; + state += 12345; + dest[i] = (state >> 16); + } +} + +static void +memset_str2 (unsigned char *dest, unsigned char val, int n) +{ + int i; + + for (i = 0; i < n; i++) { + *dest = val; + dest += 2; + } +} + +static void +memset_str3 (unsigned char *dest, unsigned char val, int n) { + int i; + for (i = 0; i < n; i++) { + *dest = val; + dest += 3; + } } static void -random_chars(unsigned char *dest, int nbytes) +memset_str4 (unsigned char *dest, unsigned char val, int n) { - int i; - static unsigned int state; + int i; - for(i=0;i>16); - } + for (i = 0; i < n; i++) { + *dest = val; + dest += 4; + } } static void paint_rect_random (unsigned char *dest, int stride, int x, int y, int w, int h) { - unsigned char *d = dest + stride*y + x; - int i; + unsigned char *d = dest + stride * y + x; + int i; - for(i=0;iwidth = w; + p->height = h; + index = paintrect_find_fourcc (v->format); + if (index < 0) + return; + + fourcc_list[index].paint_setup (p, dest); + p->paint_hline = fourcc_list[index].paint_hline; + + y1 = 2 * h / 3; + y2 = h * 0.75; + + /* color bars */ + for (i = 0; i < 7; i++) { + int x1 = i * w / 7; + int x2 = (i + 1) * w / 7; + + p->Y = y_colors[i]; + p->U = u_colors[i]; + p->V = v_colors[i]; + for (j = 0; j < y1; j++) { + p->paint_hline (p, x1, j, (x2 - x1)); + } + } + + /* inverse blue bars */ + for (i = 0; i < 7; i++) { + int x1 = i * w / 7; + int x2 = (i + 1) * w / 7; + int k; + + if (i & 1) { + k = 7; + } else { + k = 6 - i; + } + p->Y = y_colors[k]; + p->U = u_colors[k]; + p->V = v_colors[k]; + for (j = y1; j < y2; j++) { + p->paint_hline (p, x1, j, (x2 - x1)); + } + } + + /* -I, white, Q regions */ + for (i = 0; i < 3; i++) { + int x1 = i * w / 6; + int x2 = (i + 1) * w / 6; + int k; + + if (i == 0) { + k = 8; + } else if (i == 1) { + k = 0; + } else + k = 9; + + p->Y = y_colors[k]; + p->U = u_colors[k]; + p->V = v_colors[k]; + + for (j = y2; j < h; j++) { + p->paint_hline (p, x1, j, (x2 - x1)); + } + } + + { + int x1 = w / 2; + + p->U = u_colors[0]; + p->V = v_colors[0]; + + for (i = x1; i < w; i++) { + for (j = y2; j < h; j++) { + p->Y = random_char (); + p->paint_hline (p, i, j, 1); + } + } + + } +} + +static void +paint_setup_I420 (paintinfo * p, char *dest) +{ + p->yp = dest; + p->up = dest + p->width * p->height; + p->vp = dest + p->width * p->height + p->width * p->height / 4; +} + +static void +paint_hline_I420 (paintinfo * p, int x, int y, int w) +{ + int x1 = x / 2; + int x2 = (x + w) / 2; + int offset = y * p->width; + int offset1 = (y / 2) * (p->width / 2); + + memset (p->yp + offset + x, p->Y, w); + memset (p->up + offset1 + x1, p->U, x2 - x1); + memset (p->vp + offset1 + x1, p->V, x2 - x1); +} + +static void +paint_setup_YV12 (paintinfo * p, char *dest) +{ + p->yp = dest; + p->up = dest + p->width * p->height + p->width * p->height / 4; + p->vp = dest + p->width * p->height; +} + +static void +paint_setup_YUY2 (paintinfo * p, char *dest) +{ + p->yp = dest; + p->up = dest + 1; + p->vp = dest + 3; +} + +static void +paint_setup_UYVY (paintinfo * p, char *dest) +{ + p->yp = dest + 1; + p->up = dest; + p->vp = dest + 2; +} + +static void +paint_setup_YVYU (paintinfo * p, char *dest) +{ + p->yp = dest; + p->up = dest + 3; + p->vp = dest + 1; +} + +static void +paint_hline_YUY2 (paintinfo * p, int x, int y, int w) +{ + int x1 = x / 2; + int x2 = (x + w) / 2; + int offset; + + offset = y * p->width * 2; + memset_str2 (p->yp + offset + x * 2, p->Y, w); + memset_str4 (p->up + offset + x1 * 4, p->U, x2 - x1); + memset_str4 (p->vp + offset + x1 * 4, p->V, x2 - x1); +} + +static void +paint_setup_Y800 (paintinfo * p, char *dest) +{ + p->yp = dest; +} + +static void +paint_hline_Y800 (paintinfo * p, int x, int y, int w) +{ + int offset = y * p->width; + + memset (p->yp + offset + x, p->Y, w); +} + +static void +paint_setup_IMC1 (paintinfo * p, char *dest) +{ + p->yp = dest; + p->up = dest + p->width * p->height; + p->vp = dest + p->width * p->height + p->width * p->height / 2; +} + +static void +paint_setup_IMC2 (paintinfo * p, char *dest) +{ + p->yp = dest; + p->vp = dest + p->width * p->height; + p->up = dest + p->width * p->height + p->width / 2; +} + +static void +paint_setup_IMC3 (paintinfo * p, char *dest) +{ + p->yp = dest; + p->up = dest + p->width * p->height + p->width * p->height / 2; + p->vp = dest + p->width * p->height; +} + +static void +paint_setup_IMC4 (paintinfo * p, char *dest) +{ + p->yp = dest; + p->vp = dest + p->width * p->height + p->width / 2; + p->up = dest + p->width * p->height; } +static void +paint_hline_IMC1 (paintinfo * p, int x, int y, int w) +{ + int x1 = x / 2; + int x2 = (x + w) / 2; + int offset = y * p->width; + int offset1 = (y / 2) * p->width; + + memset (p->yp + offset + x, p->Y, w); + memset (p->up + offset1 + x1, p->U, x2 - x1); + memset (p->vp + offset1 + x1, p->V, x2 - x1); +} + + + /* wht yel cya grn mag red blu blk -I Q */ -static int r_colors[] = { 255, 255, 0, 0, 255, 255, 0, 0, 0, 0 }; -static int g_colors[] = { 255, 255, 255, 255, 0, 0, 0, 0, 0, 128 }; -static int b_colors[] = { 255, 0, 255, 0, 255, 0, 255, 0, 128, 255 }; - -void -gst_videotestsrc_smpte_RGB (GstVideotestsrc *v, unsigned char *dest, int w, int h) -{ - int i; - int y1,y2; - - y1 = h*2/3; - y2 = h*0.75; - - /* color bars */ - for(i=0;i<7;i++){ - int x1 = i*w/7; - int x2 = (i+1)*w/7; - unsigned char col[2]; - - col[0] = (g_colors[i]&0xe0) | (b_colors[i]>>3); - col[1] = (r_colors[i]&0xf8) | (g_colors[i]>>5); - paint_rect2(dest, w*2, x1, 0, x2-x1, y1, col); - } - - /* inverse blue bars */ - for(i=0;i<7;i++){ - int x1 = i*w/7; - int x2 = (i+1)*w/7; - unsigned char col[2]; - int k; - - if(i&1){ - k = 7; - }else{ - k = 6-i; - } - col[0] = (g_colors[k]&0xe0) | (b_colors[k]>>3); - col[1] = (r_colors[k]&0xf8) | (g_colors[k]>>5); - paint_rect2(dest, w*2, x1, y1, x2-x1, y2-y1, col); - } - - /* -I, white, Q regions */ - for(i=0;i<3;i++){ - int x1 = i*w/6; - int x2 = (i+1)*w/6; - unsigned char col[2]; - int k; - - if(i==0){ k = 8; } - else if(i==1){ k = 0; } - else k = 9; - - col[0] = (g_colors[k]&0xe0) | (b_colors[k]>>3); - col[1] = (r_colors[k]&0xf8) | (g_colors[k]>>5); - paint_rect2(dest, w*2, x1, y2, x2-x1, h-y2, col); - } - - { - int x1 = w/2; - int x2 = w-1; - paint_rect_random(dest, w*2, x1*2, y2, (x2-x1)*2, h-y2); - } +static int r_colors[] = { 255, 255, 0, 0, 255, 255, 0, 0, 0, 0 }; +static int g_colors[] = { 255, 255, 255, 255, 0, 0, 0, 0, 0, 128 }; +static int b_colors[] = { 255, 0, 255, 0, 255, 0, 255, 0, 128, 255 }; + +static void +gst_videotestsrc_smpte_RGB (GstVideotestsrc * v, unsigned char *dest, int w, int h) +{ + int i; + int y1, y2; + + y1 = h * 2 / 3; + y2 = h * 0.75; + + /* color bars */ + for (i = 0; i < 7; i++) { + int x1 = i * w / 7; + int x2 = (i + 1) * w / 7; + unsigned char col[2]; + + col[0] = (g_colors[i] & 0xe0) | (b_colors[i] >> 3); + col[1] = (r_colors[i] & 0xf8) | (g_colors[i] >> 5); + paint_rect2 (dest, w * 2, x1, 0, x2 - x1, y1, col); + } + + /* inverse blue bars */ + for (i = 0; i < 7; i++) { + int x1 = i * w / 7; + int x2 = (i + 1) * w / 7; + unsigned char col[2]; + int k; + + if (i & 1) { + k = 7; + } else { + k = 6 - i; + } + col[0] = (g_colors[k] & 0xe0) | (b_colors[k] >> 3); + col[1] = (r_colors[k] & 0xf8) | (g_colors[k] >> 5); + paint_rect2 (dest, w * 2, x1, y1, x2 - x1, y2 - y1, col); + } + + /* -I, white, Q regions */ + for (i = 0; i < 3; i++) { + int x1 = i * w / 6; + int x2 = (i + 1) * w / 6; + unsigned char col[2]; + int k; + + if (i == 0) { + k = 8; + } else if (i == 1) { + k = 0; + } else + k = 9; + + col[0] = (g_colors[k] & 0xe0) | (b_colors[k] >> 3); + col[1] = (r_colors[k] & 0xf8) | (g_colors[k] >> 5); + paint_rect2 (dest, w * 2, x1, y2, x2 - x1, h - y2, col); + } + + { + int x1 = w / 2; + int x2 = w - 1; + + paint_rect_random (dest, w * 2, x1 * 2, y2, (x2 - x1) * 2, h - y2); + } } +#ifdef unused +static void +gst_videotestsrc_colors_yuv (GstVideotestsrc * v, unsigned char *dest, int w, int h) +{ + int index; + int i; + int j; + int k; + paintinfo pi; + paintinfo *p = π + static int static_y = 0; + + p->width = w; + p->height = h; + index = paintrect_find_fourcc (v->format); + if (index < 0) + return; + + fourcc_list[index].paint_setup (p, dest); + p->paint_hline = fourcc_list[index].paint_hline; + + /* color bars */ + for (i = 0; i < 16; i++) { + int x1 = (i * w) >> 4; + int x2 = ((i + 1) * w) >> 4; + + p->Y = static_y; + p->U = i * 17; + for (j = 0; j < 16; j++) { + int y1 = (j * h) >> 4; + int y2 = ((j + 1) * h) >> 4; + + p->V = j * 17; + for (k = y1; k < y2; k++) { + p->paint_hline (p, x1, k, (x2 - x1)); + } + } + } + + static_y += 17; + if (static_y >= 256) + static_y = 0; +} +#endif + diff --git a/gst/videotestsrc/gstvideotestsrc.h b/gst/videotestsrc/gstvideotestsrc.h index 72115f4..5f20d74 100644 --- a/gst/videotestsrc/gstvideotestsrc.h +++ b/gst/videotestsrc/gstvideotestsrc.h @@ -62,7 +62,7 @@ struct _GstVideotestsrc { guint32 format; gint width; gint height; - GstVideoTestSrcMethod method; + gint forced_format; /* private */ gint64 timestamp; @@ -78,10 +78,9 @@ struct _GstVideotestsrcClass { GstElementClass parent_class; }; -GType gst_videotestsrc_get_type(void); +static GType gst_videotestsrc_get_type(void); -void gst_videotestsrc_setup(GstVideotestsrc *); -#define gst_videotestsrc_scale(scale, src, dest) (scale)->scale_cc((scale), (src), (dest)) +static void gst_videotestsrc_setup(GstVideotestsrc *); #ifdef __cplusplus } -- 2.7.4