| 493 |
494 |
| 494 gtk_container_add(GTK_CONTAINER(item), hbox); |
495 gtk_container_add(GTK_CONTAINER(item), hbox); |
| 495 gtk_box_pack_start(GTK_BOX(hbox), image, FALSE, FALSE, 0); |
496 gtk_box_pack_start(GTK_BOX(hbox), image, FALSE, FALSE, 0); |
| 496 gtk_box_pack_start(GTK_BOX(hbox), label, TRUE, TRUE, 0); |
497 gtk_box_pack_start(GTK_BOX(hbox), label, TRUE, TRUE, 0); |
| 497 |
498 |
| |
499 g_object_set_data(G_OBJECT (item), data, per_item_data); |
| 498 g_object_set_data(G_OBJECT (item), "aop_per_item_data", per_item_data); |
500 g_object_set_data(G_OBJECT (item), "aop_per_item_data", per_item_data); |
| 499 |
501 |
| 500 pidgin_set_accessible_label(item, label); |
502 pidgin_set_accessible_label(item, label); |
| 501 |
503 |
| 502 return item; |
504 return item; |
| |
505 } |
| |
506 |
| |
507 static GdkPixbuf * |
| |
508 pidgin_create_prpl_icon_from_prpl(PurplePlugin *prpl, PidginPrplIconSize size, PurpleAccount *account) |
| |
509 { |
| |
510 PurplePluginProtocolInfo *prpl_info; |
| |
511 const char *protoname = NULL; |
| |
512 char buf[MAXPATHLEN]; |
| |
513 char *filename = NULL; |
| |
514 GdkPixbuf *pixbuf; |
| |
515 |
| |
516 prpl_info = PURPLE_PLUGIN_PROTOCOL_INFO(prpl); |
| |
517 if (prpl_info->list_icon == NULL) |
| |
518 return NULL; |
| |
519 |
| |
520 protoname = prpl_info->list_icon(account, NULL); |
| |
521 if (protoname == NULL) |
| |
522 return NULL; |
| |
523 |
| |
524 /* |
| |
525 * Status icons will be themeable too, and then it will look up |
| |
526 * protoname from the theme |
| |
527 */ |
| |
528 g_snprintf(buf, sizeof(buf), "%s.png", protoname); |
| |
529 |
| |
530 filename = g_build_filename(DATADIR, "pixmaps", "pidgin", "protocols", |
| |
531 size == PIDGIN_PRPL_ICON_SMALL ? "16" : |
| |
532 size == PIDGIN_PRPL_ICON_MEDIUM ? "22" : "48", |
| |
533 buf, NULL); |
| |
534 pixbuf = gdk_pixbuf_new_from_file(filename, NULL); |
| |
535 g_free(filename); |
| |
536 |
| |
537 return pixbuf; |
| 503 } |
538 } |
| 504 |
539 |
| 505 static GtkWidget * |
540 static GtkWidget * |
| 506 aop_option_menu_new(AopMenu *aop_menu, GCallback cb, gpointer user_data) |
541 aop_option_menu_new(AopMenu *aop_menu, GCallback cb, gpointer user_data) |
| 507 { |
542 { |
| 548 if (data == g_object_get_data(G_OBJECT(llItr->data), "aop_per_item_data")) { |
583 if (data == g_object_get_data(G_OBJECT(llItr->data), "aop_per_item_data")) { |
| 549 gtk_option_menu_set_history(GTK_OPTION_MENU(optmenu), idx); |
584 gtk_option_menu_set_history(GTK_OPTION_MENU(optmenu), idx); |
| 550 break; |
585 break; |
| 551 } |
586 } |
| 552 } |
587 } |
| 553 } |
|
| 554 |
|
| 555 static GdkPixbuf * |
|
| 556 get_prpl_pixbuf(PurplePluginProtocolInfo *prpl_info) |
|
| 557 { |
|
| 558 const char *proto_name; |
|
| 559 GdkPixbuf *pixbuf = NULL; |
|
| 560 char *filename; |
|
| 561 char buf[256]; |
|
| 562 |
|
| 563 proto_name = prpl_info->list_icon(NULL, NULL); |
|
| 564 g_return_val_if_fail(proto_name != NULL, NULL); |
|
| 565 |
|
| 566 g_snprintf(buf, sizeof(buf), "%s.png", proto_name); |
|
| 567 filename = g_build_filename(DATADIR, "pixmaps", "pidgin", "protocols", "16", buf, NULL); |
|
| 568 pixbuf = gdk_pixbuf_new_from_file(filename, NULL); |
|
| 569 g_free(filename); |
|
| 570 |
|
| 571 return pixbuf; |
|
| 572 } |
588 } |
| 573 |
589 |
| 574 static AopMenu * |
590 static AopMenu * |
| 575 create_protocols_menu(const char *default_proto_id) |
591 create_protocols_menu(const char *default_proto_id) |
| 576 { |
592 { |
| 600 prpl_info = PURPLE_PLUGIN_PROTOCOL_INFO(plugin); |
616 prpl_info = PURPLE_PLUGIN_PROTOCOL_INFO(plugin); |
| 601 |
617 |
| 602 if (gtalk_name && strcmp(gtalk_name, plugin->info->name) < 0) { |
618 if (gtalk_name && strcmp(gtalk_name, plugin->info->name) < 0) { |
| 603 char *filename = g_build_filename(DATADIR, "pixmaps", "pidgin", "protocols", |
619 char *filename = g_build_filename(DATADIR, "pixmaps", "pidgin", "protocols", |
| 604 "16", "google-talk.png", NULL); |
620 "16", "google-talk.png", NULL); |
| |
621 GtkWidget *item; |
| |
622 |
| 605 pixbuf = gdk_pixbuf_new_from_file(filename, NULL); |
623 pixbuf = gdk_pixbuf_new_from_file(filename, NULL); |
| 606 g_free(filename); |
624 g_free(filename); |
| 607 |
625 |
| 608 gtk_menu_shell_append(GTK_MENU_SHELL(aop_menu->menu), |
626 gtk_menu_shell_append(GTK_MENU_SHELL(aop_menu->menu), |
| 609 aop_menu_item_new(sg, pixbuf, gtalk_name, "prpl-jabber")); |
627 item = aop_menu_item_new(sg, pixbuf, gtalk_name, "prpl-jabber", "protocol")); |
| |
628 g_object_set_data(G_OBJECT(item), "fake", GINT_TO_POINTER(1)); |
| 610 |
629 |
| 611 if (pixbuf) |
630 if (pixbuf) |
| 612 g_object_unref(pixbuf); |
631 g_object_unref(pixbuf); |
| 613 |
632 |
| 614 gtalk_name = NULL; |
633 gtalk_name = NULL; |
| 615 } |
634 } |
| 616 |
635 |
| 617 pixbuf = get_prpl_pixbuf(prpl_info); |
636 pixbuf = pidgin_create_prpl_icon_from_prpl(plugin, PIDGIN_PRPL_ICON_SMALL, NULL); |
| 618 |
637 |
| 619 gtk_menu_shell_append(GTK_MENU_SHELL(aop_menu->menu), |
638 gtk_menu_shell_append(GTK_MENU_SHELL(aop_menu->menu), |
| 620 aop_menu_item_new(sg, pixbuf, plugin->info->name, plugin->info->id)); |
639 aop_menu_item_new(sg, pixbuf, plugin->info->name, plugin->info->id, "protocol")); |
| 621 |
640 |
| 622 if (pixbuf) |
641 if (pixbuf) |
| 623 g_object_unref(pixbuf); |
642 g_object_unref(pixbuf); |
| 624 |
643 |
| 625 if (default_proto_id != NULL && !strcmp(plugin->info->id, default_proto_id)) |
644 if (default_proto_id != NULL && !strcmp(plugin->info->id, default_proto_id)) |
| 685 continue; |
703 continue; |
| 686 } |
704 } |
| 687 |
705 |
| 688 plugin = purple_find_prpl(purple_account_get_protocol_id(account)); |
706 plugin = purple_find_prpl(purple_account_get_protocol_id(account)); |
| 689 |
707 |
| 690 if (plugin) |
708 pixbuf = pidgin_create_prpl_icon(account, PIDGIN_PRPL_ICON_SMALL); |
| 691 prpl_info = PURPLE_PLUGIN_PROTOCOL_INFO(plugin); |
709 |
| 692 |
710 if (pixbuf) { |
| 693 /* Load the image. */ |
711 if (purple_account_is_disconnected(account) && show_all && |
| 694 if (prpl_info) { |
712 purple_connections_get_all()) |
| 695 pixbuf = get_prpl_pixbuf(prpl_info); |
713 gdk_pixbuf_saturate_and_pixelate(pixbuf, pixbuf, 0.0, FALSE); |
| 696 |
|
| 697 if (pixbuf) { |
|
| 698 if (purple_account_is_disconnected(account) && show_all && |
|
| 699 purple_connections_get_all()) |
|
| 700 gdk_pixbuf_saturate_and_pixelate(pixbuf, pixbuf, 0.0, FALSE); |
|
| 701 } |
|
| 702 } |
714 } |
| 703 |
715 |
| 704 if (purple_account_get_alias(account)) { |
716 if (purple_account_get_alias(account)) { |
| 705 g_snprintf(buf, sizeof(buf), "%s (%s) (%s)", |
717 g_snprintf(buf, sizeof(buf), "%s (%s) (%s)", |
| 706 purple_account_get_username(account), |
718 purple_account_get_username(account), |
| 711 purple_account_get_username(account), |
723 purple_account_get_username(account), |
| 712 purple_account_get_protocol_name(account)); |
724 purple_account_get_protocol_name(account)); |
| 713 } |
725 } |
| 714 |
726 |
| 715 gtk_menu_shell_append(GTK_MENU_SHELL(aop_menu->menu), |
727 gtk_menu_shell_append(GTK_MENU_SHELL(aop_menu->menu), |
| 716 aop_menu_item_new(sg, pixbuf, buf, account)); |
728 aop_menu_item_new(sg, pixbuf, buf, account, "account")); |
| 717 |
729 |
| 718 if (pixbuf) |
730 if (pixbuf) |
| 719 g_object_unref(pixbuf); |
731 g_object_unref(pixbuf); |
| 720 |
732 |
| 721 if (default_account && account == default_account) |
733 if (default_account && account == default_account) |
| 878 |
890 |
| 879 filename = g_build_filename(purple_user_dir(), G_DIR_SEPARATOR_S, |
891 filename = g_build_filename(purple_user_dir(), G_DIR_SEPARATOR_S, |
| 880 "accels", NULL); |
892 "accels", NULL); |
| 881 gtk_accel_map_load(filename); |
893 gtk_accel_map_load(filename); |
| 882 g_free(filename); |
894 g_free(filename); |
| |
895 } |
| |
896 |
| |
897 void pidgin_retrieve_user_info(PurpleConnection *conn, const char *name) |
| |
898 { |
| |
899 PurpleNotifyUserInfo *info = purple_notify_user_info_new(); |
| |
900 purple_notify_user_info_add_pair(info, _("Information"), _("Retrieving...")); |
| |
901 purple_notify_userinfo(conn, name, info, NULL, NULL); |
| |
902 purple_notify_user_info_destroy(info); |
| |
903 serv_get_info(conn, name); |
| 883 } |
904 } |
| 884 |
905 |
| 885 gboolean |
906 gboolean |
| 886 pidgin_parse_x_im_contact(const char *msg, gboolean all_accounts, |
907 pidgin_parse_x_im_contact(const char *msg, gboolean all_accounts, |
| 887 PurpleAccount **ret_account, char **ret_protocol, |
908 PurpleAccount **ret_account, char **ret_protocol, |
| 1580 |
1601 |
| 1581 GdkPixbuf * |
1602 GdkPixbuf * |
| 1582 pidgin_create_prpl_icon(PurpleAccount *account, PidginPrplIconSize size) |
1603 pidgin_create_prpl_icon(PurpleAccount *account, PidginPrplIconSize size) |
| 1583 { |
1604 { |
| 1584 PurplePlugin *prpl; |
1605 PurplePlugin *prpl; |
| 1585 PurplePluginProtocolInfo *prpl_info; |
|
| 1586 const char *protoname = NULL; |
|
| 1587 char buf[256]; /* TODO: We should use a define for max file length */ |
|
| 1588 char *filename = NULL; |
|
| 1589 GdkPixbuf *pixbuf; |
|
| 1590 |
1606 |
| 1591 g_return_val_if_fail(account != NULL, NULL); |
1607 g_return_val_if_fail(account != NULL, NULL); |
| 1592 |
1608 |
| 1593 prpl = purple_find_prpl(purple_account_get_protocol_id(account)); |
1609 prpl = purple_find_prpl(purple_account_get_protocol_id(account)); |
| 1594 if (prpl == NULL) |
1610 if (prpl == NULL) |
| 1595 return NULL; |
1611 return NULL; |
| 1596 |
1612 return pidgin_create_prpl_icon_from_prpl(prpl, size, account); |
| 1597 prpl_info = PURPLE_PLUGIN_PROTOCOL_INFO(prpl); |
|
| 1598 if (prpl_info->list_icon == NULL) |
|
| 1599 return NULL; |
|
| 1600 |
|
| 1601 protoname = prpl_info->list_icon(account, NULL); |
|
| 1602 if (protoname == NULL) |
|
| 1603 return NULL; |
|
| 1604 |
|
| 1605 /* |
|
| 1606 * Status icons will be themeable too, and then it will look up |
|
| 1607 * protoname from the theme |
|
| 1608 */ |
|
| 1609 g_snprintf(buf, sizeof(buf), "%s.png", protoname); |
|
| 1610 |
|
| 1611 filename = g_build_filename(DATADIR, "pixmaps", "pidgin", "protocols", |
|
| 1612 size == PIDGIN_PRPL_ICON_SMALL ? "16" : |
|
| 1613 size == PIDGIN_PRPL_ICON_MEDIUM ? "22" : "48", |
|
| 1614 buf, NULL); |
|
| 1615 pixbuf = gdk_pixbuf_new_from_file(filename, NULL); |
|
| 1616 g_free(filename); |
|
| 1617 |
|
| 1618 return pixbuf; |
|
| 1619 } |
1613 } |
| 1620 |
1614 |
| 1621 static void |
1615 static void |
| 1622 menu_action_cb(GtkMenuItem *item, gpointer object) |
1616 menu_action_cb(GtkMenuItem *item, gpointer object) |
| 1623 { |
1617 { |
| 1629 |
1623 |
| 1630 if (callback) |
1624 if (callback) |
| 1631 callback(object, data); |
1625 callback(object, data); |
| 1632 } |
1626 } |
| 1633 |
1627 |
| 1634 void |
1628 GtkWidget * |
| 1635 pidgin_append_menu_action(GtkWidget *menu, PurpleMenuAction *act, |
1629 pidgin_append_menu_action(GtkWidget *menu, PurpleMenuAction *act, |
| 1636 gpointer object) |
1630 gpointer object) |
| 1637 { |
1631 { |
| |
1632 GtkWidget *menuitem; |
| |
1633 |
| 1638 if (act == NULL) { |
1634 if (act == NULL) { |
| 1639 pidgin_separator(menu); |
1635 return pidgin_separator(menu); |
| |
1636 } |
| |
1637 |
| |
1638 if (act->children == NULL) { |
| |
1639 menuitem = gtk_menu_item_new_with_mnemonic(act->label); |
| |
1640 |
| |
1641 if (act->callback != NULL) { |
| |
1642 g_object_set_data(G_OBJECT(menuitem), |
| |
1643 "purplecallback", |
| |
1644 act->callback); |
| |
1645 g_object_set_data(G_OBJECT(menuitem), |
| |
1646 "purplecallbackdata", |
| |
1647 act->data); |
| |
1648 g_signal_connect(G_OBJECT(menuitem), "activate", |
| |
1649 G_CALLBACK(menu_action_cb), |
| |
1650 object); |
| |
1651 } else { |
| |
1652 gtk_widget_set_sensitive(menuitem, FALSE); |
| |
1653 } |
| |
1654 |
| |
1655 gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); |
| 1640 } else { |
1656 } else { |
| 1641 GtkWidget *menuitem; |
1657 GList *l = NULL; |
| 1642 |
1658 GtkWidget *submenu = NULL; |
| 1643 if (act->children == NULL) { |
1659 GtkAccelGroup *group; |
| 1644 menuitem = gtk_menu_item_new_with_mnemonic(act->label); |
1660 |
| 1645 |
1661 menuitem = gtk_menu_item_new_with_mnemonic(act->label); |
| 1646 if (act->callback != NULL) { |
1662 gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); |
| 1647 g_object_set_data(G_OBJECT(menuitem), |
1663 |
| 1648 "purplecallback", |
1664 submenu = gtk_menu_new(); |
| 1649 act->callback); |
1665 gtk_menu_item_set_submenu(GTK_MENU_ITEM(menuitem), submenu); |
| 1650 g_object_set_data(G_OBJECT(menuitem), |
1666 |
| 1651 "purplecallbackdata", |
1667 group = gtk_menu_get_accel_group(GTK_MENU(menu)); |
| 1652 act->data); |
1668 if (group) { |
| 1653 g_signal_connect(G_OBJECT(menuitem), "activate", |
1669 char *path = g_strdup_printf("%s/%s", GTK_MENU_ITEM(menuitem)->accel_path, act->label); |
| 1654 G_CALLBACK(menu_action_cb), |
1670 gtk_menu_set_accel_path(GTK_MENU(submenu), path); |
| 1655 object); |
1671 g_free(path); |
| 1656 } else { |
1672 gtk_menu_set_accel_group(GTK_MENU(submenu), group); |
| 1657 gtk_widget_set_sensitive(menuitem, FALSE); |
1673 } |
| 1658 } |
1674 |
| 1659 |
1675 for (l = act->children; l; l = l->next) { |
| 1660 gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); |
1676 PurpleMenuAction *act = (PurpleMenuAction *)l->data; |
| 1661 } else { |
1677 |
| 1662 GList *l = NULL; |
1678 pidgin_append_menu_action(submenu, act, object); |
| 1663 GtkWidget *submenu = NULL; |
1679 } |
| 1664 GtkAccelGroup *group; |
1680 g_list_free(act->children); |
| 1665 |
1681 act->children = NULL; |
| 1666 menuitem = gtk_menu_item_new_with_mnemonic(act->label); |
1682 } |
| 1667 gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); |
1683 purple_menu_action_free(act); |
| 1668 |
1684 return menuitem; |
| 1669 submenu = gtk_menu_new(); |
|
| 1670 gtk_menu_item_set_submenu(GTK_MENU_ITEM(menuitem), submenu); |
|
| 1671 |
|
| 1672 group = gtk_menu_get_accel_group(GTK_MENU(menu)); |
|
| 1673 if (group) { |
|
| 1674 char *path = g_strdup_printf("%s/%s", GTK_MENU_ITEM(menuitem)->accel_path, act->label); |
|
| 1675 gtk_menu_set_accel_path(GTK_MENU(submenu), path); |
|
| 1676 g_free(path); |
|
| 1677 gtk_menu_set_accel_group(GTK_MENU(submenu), group); |
|
| 1678 } |
|
| 1679 |
|
| 1680 for (l = act->children; l; l = l->next) { |
|
| 1681 PurpleMenuAction *act = (PurpleMenuAction *)l->data; |
|
| 1682 |
|
| 1683 pidgin_append_menu_action(submenu, act, object); |
|
| 1684 } |
|
| 1685 g_list_free(act->children); |
|
| 1686 act->children = NULL; |
|
| 1687 } |
|
| 1688 purple_menu_action_free(act); |
|
| 1689 } |
|
| 1690 } |
1685 } |
| 1691 |
1686 |
| 1692 #if GTK_CHECK_VERSION(2,3,0) |
1687 #if GTK_CHECK_VERSION(2,3,0) |
| 1693 # define NEW_STYLE_COMPLETION |
1688 # define NEW_STYLE_COMPLETION |
| 1694 #endif |
1689 #endif |