telepathy-haze: capabilities: implement UpdateCapabilities

Jonny Lamb jonny at kemper.freedesktop.org
Wed May 2 06:32:02 PDT 2012


Module: telepathy-haze
Branch: master
Commit: 41b053cdcc220687506d8922e129ef759d70fddb
URL:    http://cgit.freedesktop.org/telepathy/telepathy-haze/commit/?id=41b053cdcc220687506d8922e129ef759d70fddb

Author: Jonny Lamb <jonny.lamb at collabora.co.uk>
Date:   Wed May  2 11:36:36 2012 +0100

capabilities: implement UpdateCapabilities

I didn't bother touching AdvertiseCapabilities as old style caps are
only going to be removed soon.

Signed-off-by: Jonny Lamb <jonny.lamb at collabora.co.uk>

---

 src/connection-capabilities.c |  106 +++++++++++++++++++++++++++++++++++++++-
 src/connection-capabilities.h |    1 +
 src/connection.c              |    2 +
 src/connection.h              |    2 +
 4 files changed, 108 insertions(+), 3 deletions(-)

diff --git a/src/connection-capabilities.c b/src/connection-capabilities.c
index f2a557f..04cecfc 100644
--- a/src/connection-capabilities.c
+++ b/src/connection-capabilities.c
@@ -28,6 +28,7 @@
 #include <telepathy-glib/gtypes.h>
 #include <telepathy-glib/handle.h>
 #include <telepathy-glib/interfaces.h>
+#include <telepathy-glib/dbus.h>
 
 #include "connection.h"
 #include "debug.h"
@@ -208,6 +209,92 @@ haze_connection_advertise_capabilities (TpSvcConnectionInterfaceCapabilities *if
   g_ptr_array_free (ret, TRUE);
 }
 
+typedef enum {
+  CAPS_FLAGS_AUDIO = 1 << 0,
+  CAPS_FLAGS_VIDEO = 1 << 1,
+} CapsFlags;
+
+static void
+haze_connection_update_capabilities (TpSvcConnectionInterfaceContactCapabilities *iface,
+                                     const GPtrArray *clients,
+                                     DBusGMethodInvocation *context)
+{
+  HazeConnection *self = HAZE_CONNECTION (iface);
+  TpBaseConnection *base = (TpBaseConnection *) self;
+#ifdef ENABLE_MEDIA
+  guint i;
+  PurpleMediaCaps old_caps, caps;
+  GHashTableIter iter;
+  gpointer value;
+#endif
+
+  TP_BASE_CONNECTION_ERROR_IF_NOT_CONNECTED (base, context);
+
+#ifdef ENABLE_MEDIA
+  caps = PURPLE_MEDIA_CAPS_NONE;
+  old_caps = purple_media_manager_get_ui_caps (
+      purple_media_manager_get ());
+
+  DEBUG ("enter");
+
+  /* go through all the clients and if they can do audio or video save
+   * it in the client_caps hash table */
+  for (i = 0; i < clients->len; i++)
+    {
+      GValueArray *va = g_ptr_array_index (clients, i);
+      const gchar *client_name = g_value_get_string (va->values + 0);
+      const GPtrArray *rccs = g_value_get_boxed (va->values + 1);
+      guint j;
+      CapsFlags flags = 0;
+
+      g_hash_table_remove (self->client_caps, client_name);
+
+      for (j = 0; j < rccs->len; j++)
+        {
+          GHashTable *class = g_ptr_array_index (rccs, i);
+
+          if (tp_strdiff (tp_asv_get_string (class, TP_PROP_CHANNEL_CHANNEL_TYPE),
+                  TP_IFACE_CHANNEL_TYPE_STREAMED_MEDIA))
+            continue;
+
+          if (tp_asv_get_boolean (class,
+                  TP_PROP_CHANNEL_TYPE_STREAMED_MEDIA_INITIAL_AUDIO, NULL))
+            flags |= CAPS_FLAGS_AUDIO;
+
+          if (tp_asv_get_boolean (class,
+                  TP_PROP_CHANNEL_TYPE_STREAMED_MEDIA_INITIAL_VIDEO, NULL))
+            flags |= CAPS_FLAGS_VIDEO;
+        }
+
+      if (flags != 0)
+        {
+          g_hash_table_insert (self->client_caps, g_strdup (client_name),
+              GUINT_TO_POINTER (flags));
+        }
+    }
+
+  /* now we have an updated client_caps hash table, go through it and
+   * let libpurple know */
+  g_hash_table_iter_init (&iter, self->client_caps);
+  while (g_hash_table_iter_next (&iter, NULL, &value))
+    {
+      CapsFlags flags = GPOINTER_TO_UINT (value);
+
+      if (flags & CAPS_FLAGS_AUDIO)
+        caps |= PURPLE_MEDIA_CAPS_AUDIO;
+      if (flags & CAPS_FLAGS_VIDEO)
+        caps |= PURPLE_MEDIA_CAPS_VIDEO;
+    }
+
+  purple_media_manager_set_ui_caps (purple_media_manager_get(), caps);
+
+  _emit_capabilities_changed (self, base->self_handle, old_caps, caps);
+#endif
+
+  tp_svc_connection_interface_contact_capabilities_return_from_update_capabilities (
+      context);
+}
+
 static const gchar *assumed_caps[] =
 {
   TP_IFACE_CHANNEL_TYPE_TEXT,
@@ -589,7 +676,7 @@ haze_connection_contact_capabilities_iface_init (gpointer g_iface,
 #define IMPLEMENT(x) \
     tp_svc_connection_interface_contact_capabilities_implement_##x (\
     klass, haze_connection_##x)
-  /*IMPLEMENT(update_capabilities);*/
+  IMPLEMENT(update_capabilities);
   IMPLEMENT(get_contact_capabilities);
 #undef IMPLEMENT
 }
@@ -626,10 +713,23 @@ haze_connection_capabilities_class_init (GObjectClass *object_class)
 void
 haze_connection_capabilities_init (GObject *object)
 {
-  tp_contacts_mixin_add_contact_attributes_iface (G_OBJECT (object),
+  HazeConnection *self = HAZE_CONNECTION (object);
+
+  tp_contacts_mixin_add_contact_attributes_iface (object,
       TP_IFACE_CONNECTION_INTERFACE_CAPABILITIES,
       conn_capabilities_fill_contact_attributes);
-  tp_contacts_mixin_add_contact_attributes_iface (G_OBJECT (object),
+  tp_contacts_mixin_add_contact_attributes_iface (object,
       TP_IFACE_CONNECTION_INTERFACE_CONTACT_CAPABILITIES,
       conn_capabilities_fill_contact_attributes_contact_caps);
+
+  self->client_caps = g_hash_table_new_full (g_str_hash, g_str_equal,
+      (GDestroyNotify) g_free, NULL);
+}
+
+void
+haze_connection_capabilities_finalize (GObject *object)
+{
+  HazeConnection *self = HAZE_CONNECTION (object);
+
+  tp_clear_pointer (&self->client_caps, g_hash_table_unref);
 }
diff --git a/src/connection-capabilities.h b/src/connection-capabilities.h
index 2d2e866..7764a31 100644
--- a/src/connection-capabilities.h
+++ b/src/connection-capabilities.h
@@ -29,5 +29,6 @@ void haze_connection_contact_capabilities_iface_init (gpointer g_iface,
                                                       gpointer iface_data);
 void haze_connection_capabilities_class_init (GObjectClass *object_class);
 void haze_connection_capabilities_init (GObject *object);
+void haze_connection_capabilities_finalize (GObject *object);
 
 #endif
diff --git a/src/connection.c b/src/connection.c
index c903249..28eed06 100644
--- a/src/connection.c
+++ b/src/connection.c
@@ -721,6 +721,8 @@ haze_connection_finalize (GObject *object)
     tp_contacts_mixin_finalize (object);
     tp_presence_mixin_finalize (object);
 
+    haze_connection_capabilities_finalize (object);
+
     g_strfreev (self->acceptable_avatar_mime_types);
     g_free (priv->username);
     g_free (priv->password);
diff --git a/src/connection.h b/src/connection.h
index a75732a..c69a7c1 100644
--- a/src/connection.h
+++ b/src/connection.h
@@ -62,6 +62,8 @@ struct _HazeConnection {
 
     gchar **acceptable_avatar_mime_types;
 
+    GHashTable *client_caps;
+
     /* Part of the hack for Jabber media caps */
     gulong status_changed_id;
 



More information about the telepathy-commits mailing list