aboutsummaryrefslogtreecommitdiffstats
path: root/libempathy-gtk/empathy-video-src.c
diff options
context:
space:
mode:
Diffstat (limited to 'libempathy-gtk/empathy-video-src.c')
-rw-r--r--libempathy-gtk/empathy-video-src.c120
1 files changed, 107 insertions, 13 deletions
diff --git a/libempathy-gtk/empathy-video-src.c b/libempathy-gtk/empathy-video-src.c
index aa4d35ac2..5c865daaa 100644
--- a/libempathy-gtk/empathy-video-src.c
+++ b/libempathy-gtk/empathy-video-src.c
@@ -56,37 +56,131 @@ struct _EmpathyGstVideoSrcPrivate
#define EMPATHY_GST_VIDEO_SRC_GET_PRIVATE(o) \
(G_TYPE_INSTANCE_GET_PRIVATE ((o), EMPATHY_TYPE_GST_VIDEO_SRC, \
EmpathyGstVideoSrcPrivate))
+/**
+ * empathy_gst_add_to_bin - create a new gst element, add to bin and link it.
+ * @bin - bin to add the new element to.
+ * @src - src element for the new element (may be NULL).
+ * @name - name of the factory for the new element
+ *
+ * Returns: The newly created element ot %NULL on failure
+ */
+static GstElement *
+empathy_gst_add_to_bin (GstBin *bin,
+ GstElement *src,
+ const gchar *factoryname)
+{
+ GstElement *ret;
+
+ if ((ret = gst_element_factory_make (factoryname, NULL)) == NULL)
+ {
+ g_message ("Element factory \"%s\" not found.", factoryname);
+ goto error;
+ }
+
+ if (!gst_bin_add (bin, ret))
+ {
+ g_warning ("Couldn't add \"%s\" to bin.", factoryname);
+ goto error;
+ }
+
+ /* do not link if src == NULL, just exit here */
+ if (src == NULL)
+ return ret;
+
+ if (!gst_element_link (src, ret))
+ {
+ g_warning ("Failed to link \"%s\".", factoryname);
+ gst_bin_remove (bin, ret);
+ goto error;
+ }
+
+ return ret;
+
+error:
+ if (ret != NULL)
+ gst_object_unref (ret);
+ return NULL;
+}
+
static void
empathy_video_src_init (EmpathyGstVideoSrc *obj)
{
EmpathyGstVideoSrcPrivate *priv = EMPATHY_GST_VIDEO_SRC_GET_PRIVATE (obj);
- GstElement *scale, *colorspace, *capsfilter;
+ GstElement *element, *element_back;
GstPad *ghost, *src;
GstCaps *caps;
+ gchar *str;
- /* allocate any data required by the object here */
- scale = gst_element_factory_make ("videoscale", NULL);
- colorspace = gst_element_factory_make ("ffmpegcolorspace", NULL);
-
- capsfilter = gst_element_factory_make ("capsfilter", NULL);
+ /* allocate caps here, so we can update it by optional elements */
caps = gst_caps_new_simple ("video/x-raw-yuv",
"width", G_TYPE_INT, 320,
"height", G_TYPE_INT, 240,
NULL);
- g_object_set (G_OBJECT (capsfilter), "caps", caps, NULL);
+ /* allocate any data required by the object here */
+ if ((element = empathy_gst_add_to_bin (GST_BIN (obj),
+ NULL, "gconfvideosrc")) == NULL)
+ g_error ("Couldn't add \"gconfvideosrc\" (gst-plugins-good missing?)");
+
+ /* we need to save our source to priv->src */
+ priv->src = element;
+
+ /* videomaxrate is optional as it's part of gst-plugins-bad. So don't
+ * fail if it doesn't exist. */
+ element_back = element;
+ if ((element = empathy_gst_add_to_bin (GST_BIN (obj),
+ element, "videomaxrate")) == NULL)
+ {
+ g_message ("Couldn't add \"videomaxrate\" (gst-plugins-bad missing?)");
+ element = element_back;
+ }
+ else
+ {
+ gst_caps_set_simple (caps,
+ "framerate", GST_TYPE_FRACTION, 15, 1,
+ NULL);
+ }
+
+ str = gst_caps_to_string (caps);
+ g_debug ("Current video src caps are : %s", str);
+ g_free (str);
- priv->src = gst_element_factory_make ("gconfvideosrc", NULL);
+ if ((element = empathy_gst_add_to_bin (GST_BIN (obj),
+ element, "ffmpegcolorspace")) == NULL)
+ g_error ("Failed to add \"ffmpegcolorspace\" (gst-plugins-base missing?)");
- gst_bin_add_many (GST_BIN (obj), priv->src, scale, colorspace, capsfilter,
- NULL);
- gst_element_link_many (priv->src, scale, colorspace, capsfilter, NULL);
+ if ((element = empathy_gst_add_to_bin (GST_BIN (obj),
+ element, "videoscale")) == NULL)
+ g_error ("Failed to add \"videoscale\", (gst-plugins-base missing?)");
- src = gst_element_get_static_pad (capsfilter, "src");
+ if ((element = empathy_gst_add_to_bin (GST_BIN (obj),
+ element, "capsfilter")) == NULL)
+ g_error (
+ "Failed to add \"capsfilter\" (gstreamer core elements missing?)");
+
+ g_object_set (G_OBJECT (element), "caps", caps, NULL);
+
+
+ /* optionally add postproc_tmpnoise to improve the performance of encoders */
+ element_back = element;
+ if ((element = empathy_gst_add_to_bin (GST_BIN (obj),
+ element, "postproc_tmpnoise")) == NULL)
+ {
+ g_message ("Failed to add \"postproc_tmpnoise\" (gst-ffmpeg missing?)");
+ element = element_back;
+ }
+
+ src = gst_element_get_static_pad (element, "src");
+ g_assert (src != NULL);
ghost = gst_ghost_pad_new ("src", src);
- gst_element_add_pad (GST_ELEMENT (obj), ghost);
+ if (ghost == NULL)
+ g_error ("Unable to create ghost pad for the videosrc");
+
+ if (!gst_element_add_pad (GST_ELEMENT (obj), ghost))
+ g_error ("pad with the same name already existed or "
+ "the pad already had another parent.");
gst_object_unref (G_OBJECT (src));
}