diff mcabber/src/roster.c @ 447:03bb57383cea

Initial Multi-User Chat support This patch adds basic MUC support. We now can: - join an existing room; - create and unlock a room using the /rawxml command; - set our nickname; - send/receive chatgroup messages; - see the members of the room; - leave the room. Chatroom logging is currently disabled, as it could do some unexpected things.
author Mikael Berthe <mikael@lilotux.net>
date Sun, 25 Sep 2005 01:01:44 +0200
parents 63562fd409a1
children 644b8bf9ca4d
line wrap: on
line diff
--- a/mcabber/src/roster.c	Sun Sep 25 00:44:11 2005 +0200
+++ b/mcabber/src/roster.c	Sun Sep 25 01:01:44 2005 +0200
@@ -44,7 +44,7 @@
   guint type;
   enum subscr subscription;
   GSList *resource;
-  res *cur_res;
+  gchar *nickname; // For groupchats
   guint flags;
   // list: user -> points to his group; group -> points to its users list
   GSList *list;
@@ -197,7 +197,8 @@
   if (!jidname) return NULL;
 
   if (!roster_type)
-    roster_type = ROSTER_TYPE_USER|ROSTER_TYPE_AGENT|ROSTER_TYPE_GROUP;
+    roster_type = ROSTER_TYPE_USER | ROSTER_TYPE_ROOM |
+                  ROSTER_TYPE_AGENT | ROSTER_TYPE_GROUP;
 
   sample.type = roster_type;
   if (type == jidsearch) {
@@ -249,7 +250,9 @@
   roster *my_group;
   GSList *slist;
 
-  if ((type != ROSTER_TYPE_USER) && (type != ROSTER_TYPE_AGENT)) {
+  if ((type != ROSTER_TYPE_USER) &&
+      (type != ROSTER_TYPE_ROOM) &&
+      (type != ROSTER_TYPE_AGENT)) {
     // XXX Error message?
     return NULL;
   }
@@ -258,7 +261,7 @@
   if (!group)  group = "";
 
   // #1 Check this user doesn't already exist
-  slist = roster_find(jid, jidsearch, ROSTER_TYPE_USER|ROSTER_TYPE_AGENT);
+  slist = roster_find(jid, jidsearch, type|ROSTER_TYPE_AGENT);
   if (slist) return slist;
   // #2 add group if necessary
   slist = roster_add_group(group);
@@ -276,7 +279,7 @@
     roster_usr->name = g_strdup(str);
     g_free(str);
   }
-  roster_usr->type  = type; //ROSTER_TYPE_USER;
+  roster_usr->type  = type;
   roster_usr->list  = slist;    // (my_group SList element)
   // #4 Insert node (sorted)
   my_group->list = g_slist_insert_sorted(my_group->list, roster_usr,
@@ -292,7 +295,8 @@
   roster *roster_usr;
   GSList *node;
 
-  sl_user = roster_find(jid, jidsearch, ROSTER_TYPE_USER|ROSTER_TYPE_AGENT);
+  sl_user = roster_find(jid, jidsearch,
+                        ROSTER_TYPE_USER|ROSTER_TYPE_AGENT|ROSTER_TYPE_ROOM);
   if (sl_user == NULL)
     return;
   roster_usr = (roster*)sl_user->data;
@@ -304,6 +308,7 @@
   // Let's free memory (jid, name, status message)
   if (roster_usr->jid)        g_free((gchar*)roster_usr->jid);
   if (roster_usr->name)       g_free((gchar*)roster_usr->name);
+  if (roster_usr->nickname)   g_free((gchar*)roster_usr->nickname);
   free_all_resources(&roster_usr->resource);
   g_free(roster_usr);
 
@@ -341,6 +346,7 @@
       // Free name and jid
       if (roster_usr->jid)        g_free((gchar*)roster_usr->jid);
       if (roster_usr->name)       g_free((gchar*)roster_usr->name);
+      if (roster_usr->nickname)   g_free((gchar*)roster_usr->nickname);
       free_all_resources(&roster_usr->resource);
       g_free(roster_usr);
       sl_usr = g_slist_next(sl_usr);
@@ -371,7 +377,8 @@
   roster *roster_usr;
   res *p_res;
 
-  sl_user = roster_find(jid, jidsearch, ROSTER_TYPE_USER|ROSTER_TYPE_AGENT);
+  sl_user = roster_find(jid, jidsearch,
+                        ROSTER_TYPE_USER|ROSTER_TYPE_ROOM|ROSTER_TYPE_AGENT);
   // If we can't find it, we add it
   if (sl_user == NULL)
     sl_user = roster_add_user(jid, NULL, NULL, ROSTER_TYPE_USER);
@@ -405,7 +412,8 @@
   GSList *sl_user;
   roster *roster_usr;
 
-  sl_user = roster_find(jid, jidsearch, ROSTER_TYPE_USER|ROSTER_TYPE_AGENT);
+  sl_user = roster_find(jid, jidsearch,
+                        ROSTER_TYPE_USER|ROSTER_TYPE_ROOM|ROSTER_TYPE_AGENT);
   if (sl_user == NULL)
     return;
 
@@ -425,7 +433,8 @@
   GSList *sl_user;
   roster *roster_usr, *roster_grp;
 
-  sl_user = roster_find(jid, jidsearch, ROSTER_TYPE_USER|ROSTER_TYPE_AGENT);
+  sl_user = roster_find(jid, jidsearch,
+                        ROSTER_TYPE_USER|ROSTER_TYPE_ROOM|ROSTER_TYPE_AGENT);
   if (sl_user == NULL)
     return;
 
@@ -527,14 +536,6 @@
   return roster_usr->type;
 }
 
-inline guint roster_exists(const char *jidname, enum findwhat type,
-        guint roster_type)
-{
-  if (roster_find(jidname, type, roster_type))
-    return TRUE;
-  return FALSE;
-}
-
 
 /* ### BuddyList functions ### */
 
@@ -693,6 +694,7 @@
   // Free old buddy
   if (roster_usr->jid)        g_free((gchar*)roster_usr->jid);
   if (roster_usr->name)       g_free((gchar*)roster_usr->name);
+  if (roster_usr->nickname)   g_free((gchar*)roster_usr->nickname);
   free_all_resources(&roster_usr->resource);
   g_free(roster_usr);
 
@@ -740,6 +742,26 @@
   return roster_usr->name;
 }
 
+void buddy_setnickname(gpointer rosterdata, char *newname)
+{
+  roster *roster_usr = rosterdata;
+
+  if (!roster_usr->type & ROSTER_TYPE_ROOM) return;
+
+  if (roster_usr->nickname) {
+    g_free((gchar*)roster_usr->nickname);
+    roster_usr->nickname = NULL;
+  }
+  if (newname)
+    roster_usr->nickname = g_strdup(newname);
+}
+
+const char *buddy_getnickname(gpointer rosterdata)
+{
+  roster *roster_usr = rosterdata;
+  return roster_usr->nickname;
+}
+
 //  buddy_getgroupname()
 // Returns a pointer on buddy's group name.
 const char *buddy_getgroupname(gpointer rosterdata)
@@ -813,6 +835,18 @@
   return reslist;
 }
 
+//  buddy_del_all_resources()
+// Remove all resources from the specified buddy
+void buddy_del_all_resources(gpointer rosterdata)
+{
+  roster *roster_usr = rosterdata;
+
+  while (roster_usr->resource) {
+    res *r = roster_usr->resource->data;
+    del_resource(roster_usr, r->name);
+  }
+}
+
 //  buddy_setflags()
 // Set one or several flags to value (TRUE/FALSE)
 void buddy_setflags(gpointer rosterdata, guint flags, guint value)
@@ -873,7 +907,7 @@
         if ((bname) && (*bname))
           list = g_slist_append(list, g_strdup(bname));
       }
-    } else { // ROSTER_TYPE_USER (jid)
+    } else { // ROSTER_TYPE_USER (jid) (or agent, or chatroom...)
         const char *bjid = buddy_getjid(BUDDATA(buddy));
         if (bjid)
           list = g_slist_append(list, g_strdup(bjid));