Release 1.25.0 -- Buddy Idle Time, RTF
[siplcs.git] / src / purple / purple-buddy.c
blob4b79daaeaba3dcb8f8b7612c6fe9955fff84f16c
1 /**
2 * @file purple-buddy.c
4 * pidgin-sipe
6 * Copyright (C) 2010-2019 SIPE Project <http://sipe.sourceforge.net/>
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, write to the Free Software
20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
23 #ifdef HAVE_CONFIG_H
24 #include "config.h"
25 #endif
27 #include <glib.h>
29 #include "notify.h"
30 #include "request.h"
32 #include "version.h"
33 #if PURPLE_VERSION_CHECK(3,0,0)
34 #include "action.h"
35 #include "account.h"
36 #include "buddylist.h"
37 #else
38 #include "blist.h"
39 #include "privacy.h"
40 #define purple_account_privacy_check(a, n) purple_privacy_check(a, n)
41 #define purple_account_privacy_deny_add(a, n, l) purple_privacy_deny_add(a, n, l)
42 #define purple_account_privacy_deny_remove(a, n, l) purple_privacy_deny_remove(a, n, l)
43 #define purple_action_menu_new(l, c, d, ch) purple_menu_action_new(l, c, d, ch)
44 #define purple_blist_find_buddies(a, n) purple_find_buddies(a, n)
45 #define purple_blist_find_buddy(a, n) purple_find_buddy(a, n)
46 #define purple_blist_find_buddy_in_group(a, n, g) purple_find_buddy_in_group(a, n, g)
47 #define purple_blist_find_group(n) purple_find_group(n)
48 #define purple_blist_get_default_root() purple_blist_get_root()
49 #define purple_buddy_set_local_alias(b, n) purple_blist_alias_buddy(b, n)
50 #define purple_buddy_set_server_alias(b, n) purple_blist_server_alias_buddy(b, n)
51 #define purple_buddy_set_name(b, n) purple_blist_rename_buddy(b, n)
52 #define purple_group_set_name(g, n) purple_blist_rename_group(g, n)
53 #define purple_notify_user_info_add_pair_html(i, k, v) purple_notify_user_info_add_pair(i, k, v)
54 #define purple_protocol_got_user_status purple_prpl_got_user_status
55 #define PurpleActionMenu PurpleMenuAction
56 #define PURPLE_IS_BUDDY(b) PURPLE_BLIST_NODE_IS_BUDDY(b)
57 #define PURPLE_IS_GROUP(b) PURPLE_BLIST_NODE_IS_GROUP(b)
58 #endif
60 #include "sipe-common.h"
61 #include "sipe-backend.h"
62 #include "sipe-core.h"
63 #include "sipe-nls.h"
65 #include "purple-private.h"
67 static const struct {
68 const gchar *property; /* property name to store in blist.xml */
69 const gchar *description; /* label for "Get Info" dialog */
70 } buddy_info_map[] = {
71 /* SIPE_BUDDY_INFO_DISPLAY_NAME */ { "alias", N_("Display name") },
72 /* SIPE_BUDDY_INFO_JOB_TITLE */ { "title", N_("Job title") },
73 /* SIPE_BUDDY_INFO_CITY */ { "address-city", N_("City") },
74 /* SIPE_BUDDY_INFO_STATE */ { "address-state", N_("State") },
75 /* SIPE_BUDDY_INFO_OFFICE */ { "office", N_("Office") },
76 /* SIPE_BUDDY_INFO_DEPARTMENT */ { "department", NULL },
77 /* SIPE_BUDDY_INFO_COUNTRY */ { "address-country-code", N_("Country") },
78 /* SIPE_BUDDY_INFO_WORK_PHONE */ { "phone", N_("Business phone") },
79 /* SIPE_BUDDY_INFO_WORK_PHONE_DISPLAY */ { "phone-display", NULL },
80 /* SIPE_BUDDY_INFO_COMPANY */ { "company", N_("Company") },
81 /* SIPE_BUDDY_INFO_EMAIL */ { "email", N_("Email address") },
82 /* SIPE_BUDDY_INFO_SITE */ { "site", N_("Site") },
83 /* SIPE_BUDDY_INFO_ZIPCODE */ { "address-zipcode", NULL },
84 /* SIPE_BUDDY_INFO_STREET */ { "address-street", NULL },
85 /* SIPE_BUDDY_INFO_MOBILE_PHONE */ { "phone-mobile", NULL },
86 /* SIPE_BUDDY_INFO_MOBILE_PHONE_DISPLAY */ { "phone-mobile-display", NULL },
87 /* SIPE_BUDDY_INFO_HOME_PHONE */ { "phone-home", NULL },
88 /* SIPE_BUDDY_INFO_HOME_PHONE_DISPLAY */ { "phone-home-display", NULL },
89 /* SIPE_BUDDY_INFO_OTHER_PHONE */ { "phone-other", NULL },
90 /* SIPE_BUDDY_INFO_OTHER_PHONE_DISPLAY */ { "phone-other-display", NULL },
91 /* SIPE_BUDDY_INFO_CUSTOM1_PHONE */ { "phone-custom1", NULL },
92 /* SIPE_BUDDY_INFO_CUSTOM1_PHONE_DISPLAY */ { "phone-custom1-display", NULL },
93 /* SIPE_BUDDY_INFO_ALIAS */ { NULL, N_("Alias") },
94 /* SIPE_BUDDY_INFO_DEVICE */ { NULL, N_("Device") },
97 #define buddy_info_property(i) buddy_info_map[i].property
98 #define buddy_info_description(i) gettext(buddy_info_map[i].description)
100 sipe_backend_buddy sipe_backend_buddy_find(struct sipe_core_public *sipe_public,
101 const gchar *buddy_name,
102 const gchar *group_name)
104 struct sipe_backend_private *purple_private = sipe_public->backend_private;
105 PurpleGroup *purple_group;
107 if (group_name)
109 purple_group = purple_blist_find_group(group_name);
110 if (!purple_group)
111 return NULL;
113 return purple_blist_find_buddy_in_group(purple_private->account,
114 buddy_name,
115 purple_group);
116 } else {
117 return purple_blist_find_buddy(purple_private->account,
118 buddy_name);
122 GSList* sipe_backend_buddy_find_all(struct sipe_core_public *sipe_public,
123 const gchar *buddy_name,
124 const gchar *group_name)
126 struct sipe_backend_private *purple_private = sipe_public->backend_private;
128 if (group_name)
130 SIPE_DEBUG_ERROR_NOFORMAT("Finding all buddies in a group not supported on purple");
131 return NULL;
134 return purple_blist_find_buddies(purple_private->account, buddy_name);
137 gchar* sipe_backend_buddy_get_name(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
138 const sipe_backend_buddy who)
140 return g_strdup(purple_buddy_get_name((PurpleBuddy *) who));
143 gchar* sipe_backend_buddy_get_alias(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
144 const sipe_backend_buddy who)
146 return g_strdup(purple_buddy_get_alias(who));
149 gchar* sipe_backend_buddy_get_server_alias(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
150 const sipe_backend_buddy who)
152 return g_strdup(purple_buddy_get_server_alias(who));
155 gchar *sipe_backend_buddy_get_local_alias(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
156 const sipe_backend_buddy who)
158 return g_strdup(
159 #if PURPLE_VERSION_CHECK(3,0,0)
160 purple_buddy_get_local_alias(who)
161 #else
162 purple_buddy_get_local_buddy_alias(who)
163 #endif
167 gchar* sipe_backend_buddy_get_group_name(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
168 const sipe_backend_buddy who)
170 return g_strdup(purple_group_get_name(purple_buddy_get_group((PurpleBuddy*)who)));
173 guint sipe_backend_buddy_get_status(struct sipe_core_public *sipe_public,
174 const gchar *uri)
176 struct sipe_backend_private *purple_private = sipe_public->backend_private;
177 PurpleBuddy *pbuddy = purple_blist_find_buddy(purple_private->account, uri);
178 PurplePresence *presence = purple_buddy_get_presence(pbuddy);
179 PurpleStatus *pstatus = purple_presence_get_active_status(presence);
180 return(sipe_purple_token_to_activity(purple_status_get_id(pstatus)));
183 void sipe_backend_buddy_set_alias(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
184 const sipe_backend_buddy who,
185 const gchar *alias)
187 purple_buddy_set_local_alias(who, alias);
190 void sipe_backend_buddy_set_server_alias(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
191 const sipe_backend_buddy who,
192 const gchar *alias)
194 purple_buddy_set_server_alias(who, alias);
197 gchar* sipe_backend_buddy_get_string(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
198 sipe_backend_buddy buddy,
199 const sipe_buddy_info_fields key)
201 PurpleBuddy *b = (PurpleBuddy*) buddy;
202 return g_strdup(purple_blist_node_get_string(&b->node, buddy_info_property(key)));
205 void sipe_backend_buddy_set_string(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
206 sipe_backend_buddy buddy,
207 const sipe_buddy_info_fields key,
208 const gchar *val)
210 PurpleBuddy *b = (PurpleBuddy*) buddy;
211 purple_blist_node_set_string(&b->node, buddy_info_property(key), val);
214 void sipe_backend_buddy_refresh_properties(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
215 SIPE_UNUSED_PARAMETER const gchar *uri)
217 /* nothing to do here: already taken care of by libpurple */
220 void sipe_backend_buddy_list_processing_start(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public)
224 void sipe_backend_buddy_list_processing_finish(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public)
228 sipe_backend_buddy sipe_backend_buddy_add(struct sipe_core_public *sipe_public,
229 const gchar *name,
230 const gchar *alias,
231 const gchar *groupname)
233 struct sipe_backend_private *purple_private = sipe_public->backend_private;
234 PurpleBuddy *b;
235 PurpleGroup *purple_group = purple_blist_find_group(groupname);
237 if (!purple_group)
238 return NULL;
240 b = purple_buddy_new(purple_private->account, name, alias);
241 purple_blist_add_buddy(b, NULL, purple_group, NULL);
242 return b;
245 void sipe_backend_buddy_remove(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
246 const sipe_backend_buddy who)
248 purple_blist_remove_buddy(who);
251 struct authorization_cb_data {
252 sipe_backend_buddy_request_authorization_cb auth_cb;
253 sipe_backend_buddy_request_authorization_cb deny_cb;
254 gpointer data;
257 static void authorization_auth_cb(
258 #if PURPLE_VERSION_CHECK(3,0,0)
259 SIPE_UNUSED_PARAMETER const char *response,
260 #endif
261 void *user_data)
263 struct authorization_cb_data *cb_data = user_data;
264 sipe_backend_buddy_request_authorization_cb callback = cb_data->auth_cb;
265 void *data = cb_data->data;
266 g_free(user_data);
267 (*callback)(data);
270 static void authorization_deny_cb(
271 #if PURPLE_VERSION_CHECK(3,0,0)
272 SIPE_UNUSED_PARAMETER const char *response,
273 #endif
274 void *user_data)
276 struct authorization_cb_data *cb_data = user_data;
277 sipe_backend_buddy_request_authorization_cb callback = cb_data->deny_cb;
278 void *data = cb_data->data;
279 g_free(user_data);
280 (*callback)(data);
283 void sipe_backend_buddy_request_authorization(struct sipe_core_public *sipe_public,
284 const gchar *who,
285 const gchar *alias,
286 gboolean on_list,
287 sipe_backend_buddy_request_authorization_cb auth_cb,
288 sipe_backend_buddy_request_authorization_cb deny_cb,
289 gpointer data)
291 struct sipe_backend_private *purple_private = sipe_public->backend_private;
292 struct authorization_cb_data *cb_data = g_new(struct authorization_cb_data, 1);
294 cb_data->auth_cb = auth_cb;
295 cb_data->deny_cb = deny_cb;
296 cb_data->data = data;
298 purple_account_request_authorization(
299 purple_private->account,
300 who,
301 _("you"), /* id */
302 alias,
303 NULL, /* message */
304 on_list,
305 authorization_auth_cb,
306 authorization_deny_cb,
307 cb_data);
310 void sipe_backend_buddy_request_add(struct sipe_core_public *sipe_public,
311 const gchar *who,
312 const gchar *alias)
314 struct sipe_backend_private *purple_private = sipe_public->backend_private;
316 purple_account_request_add(purple_private->account,
317 who,
318 _("you"),
319 alias,
320 NULL);
324 gboolean sipe_backend_buddy_is_blocked(struct sipe_core_public *sipe_public,
325 const gchar *who)
327 struct sipe_backend_private *purple_private = sipe_public->backend_private;
329 return(!purple_account_privacy_check(purple_private->account, who));
332 void sipe_backend_buddy_set_blocked_status(struct sipe_core_public *sipe_public,
333 const gchar *who,
334 gboolean blocked)
336 struct sipe_backend_private *purple_private = sipe_public->backend_private;
338 if (blocked) {
339 purple_account_privacy_deny_add(purple_private->account, who, TRUE);
340 } else {
341 purple_account_privacy_deny_remove(purple_private->account, who, TRUE);
344 /* stupid workaround to make pidgin re-render screen to reflect our changes */
345 SIPE_DEBUG_INFO_NOFORMAT("sipe_backend_buddy_set_blocked_status: forcefully refreshing screen.");
346 sipe_core_buddy_got_status(sipe_public,
347 who,
348 sipe_backend_buddy_get_status(sipe_public,
349 who),
353 void sipe_backend_buddy_set_status(struct sipe_core_public *sipe_public,
354 const gchar *who,
355 guint activity,
356 time_t last_active)
358 struct sipe_backend_private *purple_private = sipe_public->backend_private;
359 PurpleBuddy *buddy = NULL;
360 gchar *tmp = NULL;
362 buddy = purple_blist_find_buddy(purple_private->account, who);
364 if (buddy) {
365 const PurpleStatusType *status_type =
366 purple_status_type_find_with_id(
367 purple_account_get_status_types(purple_private->account),
368 sipe_purple_activity_to_token(activity));
369 tmp = sipe_core_buddy_status(PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC,
370 purple_buddy_get_name(buddy),
371 activity,
372 purple_status_type_get_name(status_type));
375 /* make sure to clear status message when there is none */
376 if (!tmp)
377 tmp = g_strdup("");
379 purple_protocol_got_user_status(purple_private->account, who,
380 sipe_purple_activity_to_token(activity),
381 SIPE_PURPLE_STATUS_ATTR_ID_MESSAGE, tmp,
382 NULL);
383 g_free(tmp);
386 * One of the idiosyncrasies in the libpurple API: it is not
387 * enough to set the buddy status to one of the idle ones.
388 * You also must make another call to set an idle flag!
390 if (buddy) {
391 PurplePresence *presence = purple_buddy_get_presence(buddy);
392 gboolean is_idle =
393 (activity == SIPE_ACTIVITY_INACTIVE) ||
394 (activity == SIPE_ACTIVITY_AWAY) ||
395 (activity == SIPE_ACTIVITY_BRB) ||
396 (activity == SIPE_ACTIVITY_LUNCH);
398 purple_presence_set_idle(presence, is_idle,
399 is_idle ? last_active : 0);
403 gboolean sipe_backend_uses_photo(void)
405 return TRUE;
408 void sipe_backend_buddy_set_photo(struct sipe_core_public *sipe_public,
409 const gchar *who,
410 gpointer photo_data,
411 gsize data_len,
412 const gchar *photo_hash)
414 PurpleAccount *account = sipe_public->backend_private->account;
416 purple_buddy_icons_set_for_user(account, who, photo_data,
417 data_len, photo_hash);
420 const gchar *sipe_backend_buddy_get_photo_hash(struct sipe_core_public *sipe_public,
421 const gchar *who)
423 PurpleAccount *account = sipe_public->backend_private->account;
424 const gchar *result = NULL;
426 PurpleBuddyIcon *icon = purple_buddy_icons_find(account, who);
427 if (icon) {
428 result = purple_buddy_icon_get_checksum(icon);
429 purple_buddy_icon_unref(icon);
432 return result;
435 gboolean sipe_backend_buddy_group_add(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
436 const gchar *group_name)
438 PurpleGroup * purple_group = purple_blist_find_group(group_name);
439 if (!purple_group) {
440 purple_group = purple_group_new(group_name);
441 purple_blist_add_group(purple_group, NULL);
444 return (purple_group != NULL);
447 gboolean sipe_backend_buddy_group_rename(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
448 const gchar *old_name,
449 const gchar *new_name)
451 PurpleGroup *purple_group = purple_blist_find_group(old_name);
452 if (purple_group)
453 purple_group_set_name(purple_group, new_name);
454 return(purple_group != NULL);
457 void sipe_backend_buddy_group_remove(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
458 const gchar *group_name)
460 PurpleGroup *purple_group = purple_blist_find_group(group_name);
461 if (purple_group)
462 purple_blist_remove_group(purple_group);
465 struct sipe_backend_buddy_info *sipe_backend_buddy_info_start(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public)
467 return((struct sipe_backend_buddy_info *)purple_notify_user_info_new());
470 void sipe_backend_buddy_info_add(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
471 struct sipe_backend_buddy_info *info,
472 sipe_buddy_info_fields key,
473 const gchar *value)
475 if (info) {
476 purple_notify_user_info_add_pair_html((PurpleNotifyUserInfo *) info,
477 buddy_info_description(key),
478 value);
482 void sipe_backend_buddy_info_break(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
483 struct sipe_backend_buddy_info *info)
485 purple_notify_user_info_add_section_break((PurpleNotifyUserInfo *) info);
488 void sipe_backend_buddy_info_finalize(struct sipe_core_public *sipe_public,
489 struct sipe_backend_buddy_info *info,
490 const gchar *uri)
492 struct sipe_backend_private *purple_private = sipe_public->backend_private;
494 /* show a buddy's user info in a nice dialog box */
495 purple_notify_userinfo(purple_private->gc,
496 uri, /* buddy's URI */
497 (PurpleNotifyUserInfo *) info,
498 NULL, /* callback called when dialog closed */
499 NULL); /* userdata for callback */
502 void sipe_backend_buddy_tooltip_add(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
503 struct sipe_backend_buddy_tooltip *tooltip,
504 const gchar *description,
505 const gchar *value)
507 purple_notify_user_info_add_pair_html((PurpleNotifyUserInfo *) tooltip,
508 description,
509 value);
512 void sipe_purple_add_buddy(PurpleConnection *gc,
513 PurpleBuddy *buddy,
514 PurpleGroup *group
515 #if PURPLE_VERSION_CHECK(3,0,0)
516 , SIPE_UNUSED_PARAMETER const gchar *message
517 #endif
520 SIPE_DEBUG_INFO("sipe_purple_add_buddy[CB]: buddy:%s group:%s",
521 buddy ? purple_buddy_get_name(buddy) : "",
522 group ? purple_group_get_name(group) : "");
524 /* libpurple can call us with undefined buddy or group */
525 if (buddy && group) {
527 * Buddy name must be lower case as we use
528 * purple_normalize_nocase() to compare
530 gchar *buddy_name = g_ascii_strdown(purple_buddy_get_name(buddy), -1);
531 gchar *uri = sip_uri_if_valid(buddy_name);
532 g_free(buddy_name);
534 if (uri) {
535 purple_buddy_set_name(buddy, uri);
536 g_free(uri);
538 sipe_core_buddy_add(PURPLE_GC_TO_SIPE_CORE_PUBLIC,
539 purple_buddy_get_name(buddy),
540 purple_group_get_name(group));
541 } else {
542 SIPE_DEBUG_ERROR_NOFORMAT("sipe_purple_add_buddy[CB]: buddy name is invalid for URI");
543 purple_blist_remove_buddy(buddy);
544 purple_notify_error(gc, NULL,
545 _("User name should be a valid SIP URI\nExample: user@company.com"),
546 NULL
547 #if PURPLE_VERSION_CHECK(3,0,0)
548 , NULL
549 #endif
555 void sipe_purple_remove_buddy(PurpleConnection *gc,
556 PurpleBuddy *buddy,
557 PurpleGroup *group)
559 SIPE_DEBUG_INFO("sipe_purple_remove_buddy[CB]: buddy: '%s' group: '%s'",
560 buddy ? purple_buddy_get_name(buddy) : "",
561 group ? purple_group_get_name(group) : "");
562 if (!buddy) return;
564 sipe_core_buddy_remove(PURPLE_GC_TO_SIPE_CORE_PUBLIC,
565 purple_buddy_get_name(buddy),
566 group ? purple_group_get_name(group) : NULL);
569 void sipe_purple_group_buddy(PurpleConnection *gc,
570 const char *who,
571 const char *old_group_name,
572 const char *new_group_name)
574 sipe_core_buddy_group(PURPLE_GC_TO_SIPE_CORE_PUBLIC, who, old_group_name, new_group_name);
577 /* Buddy Menu Handling */
579 static void sipe_purple_buddy_make_chat_leader_cb(PurpleBuddy *buddy,
580 gpointer parameter)
582 SIPE_DEBUG_INFO("sipe_purple_buddy_make_chat_leader_cb: name '%s'",
583 purple_buddy_get_name(buddy));
584 sipe_core_conf_make_leader(PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC,
585 parameter,
586 purple_buddy_get_name(buddy));
589 static void sipe_purple_buddy_remove_from_chat_cb(PurpleBuddy *buddy,
590 gpointer parameter)
592 SIPE_DEBUG_INFO("sipe_purple_buddy_remove_from_chat_cb: name '%s'",
593 purple_buddy_get_name(buddy));
594 sipe_core_conf_remove_from(PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC,
595 parameter,
596 purple_buddy_get_name(buddy));
599 static void sipe_purple_buddy_invite_to_chat_cb(PurpleBuddy *buddy,
600 gpointer parameter)
602 SIPE_DEBUG_INFO("sipe_purple_buddy_invite_to_chat_cb: name '%s'",
603 purple_buddy_get_name(buddy));
604 sipe_core_chat_invite(PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC,
605 parameter,
606 purple_buddy_get_name(buddy));
609 static void sipe_purple_buddy_new_chat_cb(PurpleBuddy *buddy,
610 SIPE_UNUSED_PARAMETER gpointer parameter)
612 SIPE_DEBUG_INFO("sipe_purple_buddy_new_chat_cb: name '%s'",
613 purple_buddy_get_name(buddy));
614 sipe_core_buddy_new_chat(PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC,
615 purple_buddy_get_name(buddy));
618 static void sipe_purple_buddy_make_call_cb(PurpleBuddy *buddy,
619 gpointer parameter)
621 SIPE_DEBUG_INFO("sipe_purple_buddy_make_call_cb: name '%s'",
622 purple_buddy_get_name(buddy));
623 sipe_core_buddy_make_call(PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC,
624 parameter);
627 static void sipe_purple_buddy_send_email_cb(PurpleBuddy *buddy,
628 SIPE_UNUSED_PARAMETER gpointer parameter)
630 SIPE_DEBUG_INFO("sipe_purple_buddy_send_email_cb: name '%s'",
631 purple_buddy_get_name(buddy));
632 sipe_core_buddy_send_email(PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC,
633 purple_buddy_get_name(buddy));
636 static void sipe_purple_buddy_access_level_help_cb(PurpleBuddy *buddy,
637 SIPE_UNUSED_PARAMETER gpointer parameter)
640 * Translators: replace with URL to localized page
641 * If it doesn't exist copy the original URL
643 purple_notify_uri(purple_account_get_connection(purple_buddy_get_account(buddy)),
644 _("https://sourceforge.net/apps/mediawiki/sipe/index.php?title=Access_Levels"));
647 static void sipe_purple_buddy_change_access_level_cb(PurpleBuddy *buddy,
648 gpointer parameter)
650 sipe_core_change_access_level_from_container(PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC,
651 parameter);
654 static void sipe_purple_ask_access_domain_cb(PurpleConnection *gc,
655 PurpleRequestFields *fields)
657 const gchar *domain = purple_request_fields_get_string(fields, "access_domain");
658 guint index =
659 #if PURPLE_VERSION_CHECK(3,0,0)
660 GPOINTER_TO_UINT(
661 #endif
662 purple_request_fields_get_choice(fields, "container_id")
663 #if PURPLE_VERSION_CHECK(3,0,0)
665 #endif
668 sipe_core_change_access_level_for_domain(PURPLE_GC_TO_SIPE_CORE_PUBLIC,
669 domain,
670 index);
673 static void sipe_purple_buddy_add_new_domain_cb(PurpleBuddy *buddy,
674 SIPE_UNUSED_PARAMETER gpointer parameter)
676 PurpleAccount *account = purple_buddy_get_account(buddy);
677 PurpleConnection *gc = purple_account_get_connection(account);
678 PurpleRequestFields *fields;
679 PurpleRequestFieldGroup *g;
680 PurpleRequestField *f;
682 fields = purple_request_fields_new();
684 g = purple_request_field_group_new(NULL);
685 f = purple_request_field_string_new("access_domain",
686 _("Domain"),
687 "partner-company.com",
688 FALSE);
689 purple_request_field_set_required(f, TRUE);
690 purple_request_field_group_add_field(g, f);
692 f = purple_request_field_choice_new("container_id",
693 _("Access level"),
695 #if PURPLE_VERSION_CHECK(3,0,0)
696 purple_request_field_choice_add(f, _("Personal"), GUINT_TO_POINTER(0));
697 purple_request_field_choice_add(f, _("Team"), GUINT_TO_POINTER(1));
698 purple_request_field_choice_add(f, _("Company"), GUINT_TO_POINTER(2));
699 purple_request_field_choice_add(f, _("Public"), GUINT_TO_POINTER(3));
700 purple_request_field_choice_add(f, _("Blocked"), GUINT_TO_POINTER(4));
701 purple_request_field_choice_set_default_value(f, GUINT_TO_POINTER(3));
702 #else
703 purple_request_field_choice_add(f, _("Personal")); /* index 0 */
704 purple_request_field_choice_add(f, _("Team"));
705 purple_request_field_choice_add(f, _("Company"));
706 purple_request_field_choice_add(f, _("Public"));
707 purple_request_field_choice_add(f, _("Blocked")); /* index 4 */
708 purple_request_field_choice_set_default_value(f, 3); /* index */
709 #endif
710 purple_request_field_set_required(f, TRUE);
711 purple_request_field_group_add_field(g, f);
713 purple_request_fields_add_group(fields, g);
715 purple_request_fields(gc, _("Add new domain"),
716 _("Add new domain"), NULL, fields,
717 _("Add"), G_CALLBACK(sipe_purple_ask_access_domain_cb),
718 _("Cancel"), NULL,
719 #if PURPLE_VERSION_CHECK(3,0,0)
720 purple_request_cpar_from_account(account),
721 #else
722 account, NULL, NULL,
723 #endif
724 gc);
727 static void sipe_purple_buddy_share_desktop_cb(SIPE_UNUSED_PARAMETER PurpleBuddy *buddy,
728 SIPE_UNUSED_PARAMETER gpointer parameter)
730 #ifdef HAVE_APPSHARE_SERVER
731 sipe_core_appshare_share_desktop(PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC,
732 purple_buddy_get_name(buddy));
733 #endif
736 static void sipe_purple_buddy_give_desktop_control_cb(SIPE_UNUSED_PARAMETER PurpleBuddy *buddy,
737 SIPE_UNUSED_PARAMETER gpointer parameter)
739 #ifdef HAVE_APPSHARE_SERVER
740 sipe_core_appshare_set_remote_control(parameter, TRUE);
741 #endif
744 static void sipe_purple_buddy_take_desktop_control_cb(SIPE_UNUSED_PARAMETER PurpleBuddy *buddy,
745 SIPE_UNUSED_PARAMETER gpointer parameter)
747 #ifdef HAVE_APPSHARE_SERVER
748 sipe_core_appshare_set_remote_control(parameter, FALSE);
749 #endif
752 typedef void (*buddy_menu_callback)(PurpleBuddy *buddy,
753 gpointer parameter);
754 static const buddy_menu_callback callback_map[SIPE_BUDDY_MENU_TYPES] = {
755 /* SIPE_BUDDY_MENU_MAKE_CHAT_LEADER */ sipe_purple_buddy_make_chat_leader_cb,
756 /* SIPE_BUDDY_MENU_REMOVE_FROM_CHAT */ sipe_purple_buddy_remove_from_chat_cb,
757 /* SIPE_BUDDY_MENU_INVITE_TO_CHAT */ sipe_purple_buddy_invite_to_chat_cb,
758 /* SIPE_BUDDY_MENU_NEW_CHAT */ sipe_purple_buddy_new_chat_cb,
759 /* SIPE_BUDDY_MENU_MAKE_CALL */ sipe_purple_buddy_make_call_cb,
760 /* SIPE_BUDDY_MENU_SEND_EMAIL */ sipe_purple_buddy_send_email_cb,
761 /* SIPE_BUDDY_MENU_ACCESS_LEVEL_HELP */ sipe_purple_buddy_access_level_help_cb,
762 /* SIPE_BUDDY_MENU_CHANGE_ACCESS_LEVEL */ sipe_purple_buddy_change_access_level_cb,
763 /* SIPE_BUDDY_MENU_ADD_NEW_DOMAIN */ sipe_purple_buddy_add_new_domain_cb,
764 /* SIPE_BUDDY_MENU_SHARE_DESKTOP */ sipe_purple_buddy_share_desktop_cb,
765 /* SIPE_BUDDY_MENU_GIVE_DESKTOP_CONTROL*/ sipe_purple_buddy_give_desktop_control_cb,
766 /* SIPE_BUDDY_MENU_TAKE_DESKTOP_CONTROL*/ sipe_purple_buddy_take_desktop_control_cb,
769 struct sipe_backend_buddy_menu *sipe_backend_buddy_menu_start(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public)
771 return(NULL);
774 struct sipe_backend_buddy_menu *sipe_backend_buddy_menu_add(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
775 struct sipe_backend_buddy_menu *menu,
776 const gchar *label,
777 enum sipe_buddy_menu_type type,
778 gpointer parameter)
780 return((struct sipe_backend_buddy_menu *)
781 g_list_prepend((GList *) menu,
782 purple_action_menu_new(label,
783 PURPLE_CALLBACK(callback_map[type]),
784 parameter, NULL)));
787 struct sipe_backend_buddy_menu *sipe_backend_buddy_menu_separator(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
788 struct sipe_backend_buddy_menu *menu,
789 const gchar *label)
791 return((struct sipe_backend_buddy_menu *)
792 g_list_prepend((GList *) menu,
793 purple_action_menu_new(label, NULL, NULL, NULL)));
796 struct sipe_backend_buddy_menu *sipe_backend_buddy_sub_menu_add(SIPE_UNUSED_PARAMETER struct sipe_core_public *sipe_public,
797 struct sipe_backend_buddy_menu *menu,
798 const gchar *label,
799 struct sipe_backend_buddy_menu *sub)
801 return((struct sipe_backend_buddy_menu *)
802 g_list_prepend((GList *) menu,
803 purple_action_menu_new(label,
804 NULL,
805 NULL,
806 g_list_reverse((GList *) sub))));
809 static void sipe_purple_buddy_copy_to_cb(PurpleBlistNode *node,
810 const gchar *group_name)
812 struct sipe_core_public *sipe_public;
813 PurpleBuddy *buddy = (PurpleBuddy *)node;
814 PurpleGroup *group;
815 PurpleBuddy *clone;
817 g_return_if_fail(PURPLE_IS_BUDDY(node));
819 sipe_public = PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC;
820 group = purple_blist_find_group(group_name);
822 SIPE_DEBUG_INFO("sipe_purple_buddy_copy_to_cb: copying %s to %s",
823 purple_buddy_get_name(buddy), group_name);
825 clone = purple_blist_find_buddy_in_group(purple_buddy_get_account(buddy),
826 purple_buddy_get_name(buddy),
827 group);
828 if (!clone) {
829 clone = sipe_backend_buddy_add(sipe_public,
830 purple_buddy_get_name(buddy),
831 #if PURPLE_VERSION_CHECK(3,0,0)
832 purple_buddy_get_local_alias(buddy),
833 #else
834 buddy->alias,
835 #endif
836 purple_group_get_name(group));
837 if (clone) {
838 const gchar *tmp;
839 const gchar *key;
840 PurpleStatus *status = purple_presence_get_active_status(purple_buddy_get_presence(buddy));
842 tmp = purple_buddy_get_server_alias(buddy);
843 if (tmp) purple_buddy_set_server_alias(clone, tmp);
845 key = buddy_info_property(SIPE_BUDDY_INFO_EMAIL);
846 tmp = purple_blist_node_get_string(&buddy->node, key);
847 if (tmp) purple_blist_node_set_string(&clone->node,
848 key,
849 tmp);
851 tmp = purple_status_get_id(status);
852 purple_presence_set_status_active(purple_buddy_get_presence(clone),
853 tmp,
854 TRUE);
856 /* update UI */
857 purple_protocol_got_user_status(purple_buddy_get_account(clone),
858 purple_buddy_get_name(clone),
859 tmp,
860 SIPE_PURPLE_STATUS_ATTR_ID_MESSAGE, tmp,
861 NULL);
865 if (clone && group)
866 sipe_core_buddy_add(sipe_public,
867 purple_buddy_get_name(clone),
868 purple_group_get_name(group));
871 static GList *sipe_purple_copy_to_menu(GList *menu,
872 PurpleBuddy *buddy)
874 GList *menu_groups = NULL;
875 PurpleGroup *gr_parent = purple_buddy_get_group(buddy);
876 PurpleBlistNode *g_node;
878 for (g_node = purple_blist_get_default_root(); g_node; g_node = g_node->next) {
879 PurpleGroup *group = (PurpleGroup *)g_node;
880 PurpleActionMenu *act;
882 if ((!PURPLE_IS_GROUP(g_node)) ||
883 (group == gr_parent) ||
884 purple_blist_find_buddy_in_group(purple_buddy_get_account(buddy),
885 purple_buddy_get_name(buddy),
886 group))
887 continue;
889 act = purple_action_menu_new(purple_group_get_name(group),
890 PURPLE_CALLBACK(sipe_purple_buddy_copy_to_cb),
891 (gpointer) purple_group_get_name(group),
892 NULL);
893 menu_groups = g_list_prepend(menu_groups, act);
896 if (menu_groups)
897 menu = g_list_prepend(menu,
898 purple_action_menu_new(_("Copy to"),
899 NULL,
900 NULL,
901 g_list_reverse(menu_groups)));
903 return(menu);
906 GList *sipe_purple_buddy_menu(PurpleBuddy *buddy)
908 struct sipe_core_public *sipe_public = PURPLE_BUDDY_TO_SIPE_CORE_PUBLIC;
909 GList *menu = (GList *) sipe_core_buddy_create_menu(sipe_public,
910 purple_buddy_get_name(buddy),
911 NULL);
912 menu = sipe_purple_copy_to_menu(menu, buddy);
913 return(g_list_reverse(menu));
918 Local Variables:
919 mode: c
920 c-file-style: "bsd"
921 indent-tabs-mode: t
922 tab-width: 8
923 End: