/pidgin/main: f59489bd552b: Copy VV device settings into a Prefe...
Elliott Sales de Andrade
qulogic at pidgin.im
Mon Nov 5 18:15:58 EST 2012
Changeset: f59489bd552b9f85b22c4afeae97fb6a7da56c27
Author: Elliott Sales de Andrade <qulogic at pidgin.im>
Date: 2012-09-11 03:05 -0400
Branch: default
URL: http://hg.pidgin.im/pidgin/main/rev/f59489bd552b
Description:
Copy VV device settings into a Preferences pane.
Also, fix compile with GStreamer-1.0. This isn't exactly working yet
since 1.0 doesn't seem to have the device probing capabilities.
But anyway, I've always thought it was weird to have the VV config in
a plugin, making it hard to discover for users.
diffstat:
pidgin/gtkprefs.c | 263 ++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 263 insertions(+), 0 deletions(-)
diffs (287 lines):
diff --git a/pidgin/gtkprefs.c b/pidgin/gtkprefs.c
--- a/pidgin/gtkprefs.c
+++ b/pidgin/gtkprefs.c
@@ -57,6 +57,9 @@
#include "gtkwebview.h"
#include "gtkwebviewtoolbar.h"
#include "pidginstock.h"
+#if USE_VV
+#include "media-gst.h"
+#endif
#include "gtk3compat.h"
@@ -2938,6 +2941,263 @@ away_page(void)
return ret;
}
+#if USE_VV
+static const gchar *AUDIO_SRC_PLUGINS[] = {
+ "alsasrc", "ALSA",
+ /* "esdmon", "ESD", ? */
+ "osssrc", "OSS",
+ "pulsesrc", "PulseAudio",
+ "sndiosrc", "sndio",
+ /* "audiotestsrc wave=silence", "Silence", */
+ "audiotestsrc", "Test Sound",
+ NULL
+};
+
+static const gchar *AUDIO_SINK_PLUGINS[] = {
+ "alsasink", "ALSA",
+ "artsdsink", "aRts",
+ "esdsink", "ESD",
+ "osssink", "OSS",
+ "pulsesink", "PulseAudio",
+ "sndiosink", "sndio",
+ NULL
+};
+
+static const gchar *VIDEO_SRC_PLUGINS[] = {
+ "videotestsrc", "Test Input",
+ "dshowvideosrc","DirectDraw",
+ "ksvideosrc", "KS Video",
+ "qcamsrc", "Quickcam",
+ "v4lsrc", "Video4Linux",
+ "v4l2src", "Video4Linux2",
+ "v4lmjpegsrc", "Video4Linux MJPEG",
+ NULL
+};
+
+static const gchar *VIDEO_SINK_PLUGINS[] = {
+ /* "aasink", "AALib", Didn't work for me */
+ "directdrawsink","DirectDraw",
+ "glimagesink", "OpenGL",
+ "ximagesink", "X Window System",
+ "xvimagesink", "X Window System (Xv)",
+ NULL
+};
+
+static GList *
+get_vv_element_devices(const gchar *element_name)
+{
+ GList *ret = NULL;
+ GstElement *element;
+ GObjectClass *klass;
+#if !GST_CHECK_VERSION(0,11,0)
+ GstPropertyProbe *probe;
+ const GParamSpec *pspec;
+#endif
+
+ ret = g_list_prepend(ret, (gpointer)_("Default"));
+ ret = g_list_prepend(ret, "");
+
+ if (!strcmp(element_name, "<custom>") || (*element_name == '\0')) {
+ return g_list_reverse(ret);
+ }
+
+ element = gst_element_factory_make(element_name, "test");
+ if (!element) {
+ purple_debug_info("vvconfig", "'%s' - unable to find element\n",
+ element_name);
+ return g_list_reverse(ret);
+ }
+
+ klass = G_OBJECT_GET_CLASS (element);
+ if (!klass) {
+ purple_debug_info("vvconfig", "'%s' - unable to find GObject Class\n",
+ element_name);
+ return g_list_reverse(ret);
+ }
+
+#if GST_CHECK_VERSION(0,11,0)
+ purple_debug_info("vvconfig", "'%s' - no device\n", element_name);
+#else
+ if (!g_object_class_find_property(klass, "device") ||
+ !GST_IS_PROPERTY_PROBE(element) ||
+ !(probe = GST_PROPERTY_PROBE(element)) ||
+ !(pspec = gst_property_probe_get_property(probe, "device"))) {
+ purple_debug_info("vvconfig", "'%s' - no device\n", element_name);
+ } else {
+ gint n;
+ GValueArray *array;
+
+ /* Set autoprobe[-fps] to FALSE to avoid delays when probing. */
+ if (g_object_class_find_property(klass, "autoprobe")) {
+ g_object_set(G_OBJECT(element), "autoprobe", FALSE, NULL);
+ if (g_object_class_find_property(klass, "autoprobe-fps")) {
+ g_object_set(G_OBJECT(element), "autoprobe-fps", FALSE, NULL);
+ }
+ }
+
+ array = gst_property_probe_probe_and_get_values(probe, pspec);
+ if (array == NULL) {
+ purple_debug_info("vvconfig", "'%s' has no devices\n", element_name);
+ return g_list_reverse(ret);
+ }
+
+ for (n = 0; n < array->n_values; ++n) {
+ GValue *device;
+ const gchar *name;
+ const gchar *device_name;
+
+ device = g_value_array_get_nth(array, n);
+ g_object_set_property(G_OBJECT(element), "device", device);
+ if (gst_element_set_state(element, GST_STATE_READY) != GST_STATE_CHANGE_SUCCESS) {
+ purple_debug_warning("vvconfig", "Error changing state of %s\n",
+ element_name);
+ continue;
+ }
+
+ g_object_get(G_OBJECT(element), "device-name", &name, NULL);
+ device_name = g_value_get_string(device);
+ if (name == NULL)
+ name = _("Unknown");
+ purple_debug_info("vvconfig", "Found device %s : %s for %s\n",
+ device_name, name, element_name);
+ ret = g_list_prepend(ret, (gpointer)name);
+ ret = g_list_prepend(ret, (gpointer)device_name);
+ gst_element_set_state(element, GST_STATE_NULL);
+ }
+ }
+#endif
+ gst_object_unref(element);
+
+ return g_list_reverse(ret);
+}
+
+static GList *
+get_vv_element_plugins(const gchar **plugins)
+{
+ GList *ret = NULL;
+
+ ret = g_list_prepend(ret, (gpointer)_("Default"));
+ ret = g_list_prepend(ret, "");
+ for (; plugins[0] && plugins[1]; plugins += 2) {
+#if GST_CHECK_VERSION(0,11,0)
+ if (gst_registry_check_feature_version(gst_registry_get(),
+ plugins[0], 0, 0, 0)) {
+#else
+ if (gst_default_registry_check_feature_version(plugins[0], 0, 0, 0)) {
+#endif
+ ret = g_list_prepend(ret, (gpointer)plugins[1]);
+ ret = g_list_prepend(ret, (gpointer)plugins[0]);
+ }
+ }
+
+ return g_list_reverse(ret);
+}
+
+static void
+vv_plugin_changed_cb(const gchar *name, PurplePrefType type,
+ gconstpointer value, gpointer data)
+{
+ GtkWidget *vbox = data;
+ GtkSizeGroup *sg;
+ GtkWidget *widget;
+ gchar *pref;
+ GList *devices;
+
+ sg = g_object_get_data(G_OBJECT(vbox), "size-group");
+ widget = g_object_get_data(G_OBJECT(vbox), "device-hbox");
+ gtk_widget_destroy(widget);
+
+ pref = g_strdup(name);
+ strcpy(pref + strlen(pref) - strlen("plugin"), "device");
+ devices = get_vv_element_devices(value);
+ if (g_list_find_custom(devices, purple_prefs_get_string(pref),
+ (GCompareFunc)strcmp) == NULL)
+ purple_prefs_set_string(pref, g_list_next(devices)->data);
+ widget = pidgin_prefs_dropdown_from_list(vbox, _("_Device"),
+ PURPLE_PREF_STRING, pref, devices);
+ g_list_free(devices);
+ gtk_size_group_add_widget(sg, widget);
+ gtk_misc_set_alignment(GTK_MISC(widget), 0, 0.5);
+
+ g_object_set_data(G_OBJECT(vbox), "device-hbox",
+ gtk_widget_get_parent(widget));
+ g_signal_connect_swapped(widget, "destroy", G_CALLBACK(g_free), pref);
+}
+
+static void
+make_vv_frame(GtkWidget *parent, GtkSizeGroup *sg,
+ const gchar *name, const gchar **plugin_strs,
+ const gchar *plugin_pref, const gchar *device_pref)
+{
+ GtkWidget *vbox, *widget;
+ GList *plugins, *devices;
+
+ vbox = pidgin_make_frame(parent, name);
+
+ /* Setup plugin preference */
+ plugins = get_vv_element_plugins(plugin_strs);
+ widget = pidgin_prefs_dropdown_from_list(vbox, _("_Plugin"),
+ PURPLE_PREF_STRING, plugin_pref,
+ plugins);
+ g_list_free(plugins);
+ gtk_size_group_add_widget(sg, widget);
+ gtk_misc_set_alignment(GTK_MISC(widget), 0, 0.5);
+
+ /* Setup device preference */
+ devices = get_vv_element_devices(purple_prefs_get_string(plugin_pref));
+ if (g_list_find_custom(devices, purple_prefs_get_string(device_pref),
+ (GCompareFunc)strcmp) == NULL)
+ purple_prefs_set_string(device_pref, g_list_next(devices)->data);
+ widget = pidgin_prefs_dropdown_from_list(vbox, _("_Device"),
+ PURPLE_PREF_STRING, device_pref,
+ devices);
+ g_list_free(devices);
+ gtk_size_group_add_widget(sg, widget);
+ gtk_misc_set_alignment(GTK_MISC(widget), 0, 0.5);
+
+ widget = gtk_widget_get_parent(widget);
+ g_object_set_data(G_OBJECT(vbox), "size-group", sg);
+ g_object_set_data(G_OBJECT(vbox), "device-hbox", widget);
+ purple_prefs_connect_callback(vbox, plugin_pref, vv_plugin_changed_cb,
+ vbox);
+ g_signal_connect_swapped(vbox, "destroy",
+ G_CALLBACK(purple_prefs_disconnect_by_handle), vbox);
+}
+
+static GtkWidget *
+vv_page(void)
+{
+ GtkWidget *ret;
+ GtkWidget *vbox;
+ GtkSizeGroup *sg;
+
+ ret = gtk_hbox_new(FALSE, PIDGIN_HIG_CAT_SPACE);
+ gtk_container_set_border_width(GTK_CONTAINER(ret), PIDGIN_HIG_BORDER);
+
+ sg = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
+
+ vbox = pidgin_make_frame(ret, _("Audio"));
+ make_vv_frame(vbox, sg, _("Input"), AUDIO_SRC_PLUGINS,
+ "/plugins/core/vvconfig/audio/src/plugin",
+ "/plugins/core/vvconfig/audio/src/device");
+ make_vv_frame(vbox, sg, _("Output"), AUDIO_SINK_PLUGINS,
+ "/plugins/core/vvconfig/audio/sink/plugin",
+ "/plugins/core/vvconfig/audio/sink/device");
+
+ vbox = pidgin_make_frame(ret, _("Video"));
+ make_vv_frame(vbox, sg, _("Input"), VIDEO_SRC_PLUGINS,
+ "/plugins/core/vvconfig/video/src/plugin",
+ "/plugins/core/vvconfig/video/src/device");
+ make_vv_frame(vbox, sg, _("Output"), VIDEO_SINK_PLUGINS,
+ "/plugins/gtk/vvconfig/video/sink/plugin",
+ "/plugins/gtk/vvconfig/video/sink/device");
+
+ gtk_widget_show_all(ret);
+
+ return ret;
+}
+#endif
+
static int
prefs_notebook_add_page(const char *text, GtkWidget *page, int ind)
{
@@ -2964,6 +3224,9 @@ prefs_notebook_init(void)
prefs_notebook_add_page(_("Sounds"), sound_page(), notebook_page++);
prefs_notebook_add_page(_("Status / Idle"), away_page(), notebook_page++);
prefs_notebook_add_page(_("Themes"), theme_page(), notebook_page++);
+#if USE_VV
+ prefs_notebook_add_page(_("Voice/Video"), vv_page(), notebook_page++);
+#endif
}
void
More information about the Commits
mailing list