| 99 #define DEFAULT_SEND_COLOR "#204a87" |
99 #define DEFAULT_SEND_COLOR "#204a87" |
| 100 #define DEFAULT_RECV_COLOR "#cc0000" |
100 #define DEFAULT_RECV_COLOR "#cc0000" |
| 101 #define DEFAULT_HIGHLIGHT_COLOR "#AF7F00" |
101 #define DEFAULT_HIGHLIGHT_COLOR "#AF7F00" |
| 102 #define DEFAULT_ACTION_COLOR "#062585" |
102 #define DEFAULT_ACTION_COLOR "#062585" |
| 103 |
103 |
| |
104 #define BUDDYICON_SIZE_MIN 32 |
| |
105 #define BUDDYICON_SIZE_MAX 96 |
| |
106 |
| 104 /* Undef this to turn off "custom-smiley" debug messages */ |
107 /* Undef this to turn off "custom-smiley" debug messages */ |
| 105 #define DEBUG_CUSTOM_SMILEY |
108 #define DEBUG_CUSTOM_SMILEY |
| 106 |
109 |
| 107 #define LUMINANCE(c) (float)((0.3*(c.red))+(0.59*(c.green))+(0.11*(c.blue))) |
110 #define LUMINANCE(c) (float)((0.3*(c.red))+(0.59*(c.green))+(0.11*(c.blue))) |
| 108 |
111 |
| 167 |
170 |
| 168 static void pidgin_conv_set_position_size(PidginWindow *win, int x, int y, |
171 static void pidgin_conv_set_position_size(PidginWindow *win, int x, int y, |
| 169 int width, int height); |
172 int width, int height); |
| 170 static gboolean pidgin_conv_xy_to_right_infopane(PidginWindow *win, int x, int y); |
173 static gboolean pidgin_conv_xy_to_right_infopane(PidginWindow *win, int x, int y); |
| 171 |
174 |
| 172 static GdkColor *get_nick_color(PidginConversation *gtkconv, const char *name) { |
175 static const GdkColor *get_nick_color(PidginConversation *gtkconv, const char *name) { |
| 173 static GdkColor col; |
176 static GdkColor col; |
| 174 GtkStyle *style = gtk_widget_get_style(gtkconv->imhtml); |
177 GtkStyle *style = gtk_widget_get_style(gtkconv->imhtml); |
| 175 float scale; |
178 float scale; |
| 176 |
179 |
| 177 col = nick_colors[g_str_hash(name) % nbr_nick_colors]; |
180 col = nick_colors[g_str_hash(name) % nbr_nick_colors]; |
| 1809 |
1812 |
| 1810 return TRUE; |
1813 return TRUE; |
| 1811 } |
1814 } |
| 1812 |
1815 |
| 1813 static void |
1816 static void |
| |
1817 activate_list_cb(GtkTreeView *list, GtkTreePath *path, GtkTreeViewColumn *column, PidginConversation *gtkconv) |
| |
1818 { |
| |
1819 GtkTreeIter iter; |
| |
1820 GtkTreeModel *model; |
| |
1821 gchar *who; |
| |
1822 |
| |
1823 model = gtk_tree_view_get_model(GTK_TREE_VIEW(list)); |
| |
1824 |
| |
1825 gtk_tree_model_get_iter(GTK_TREE_MODEL(model), &iter, path); |
| |
1826 gtk_tree_model_get(GTK_TREE_MODEL(model), &iter, CHAT_USERS_NAME_COLUMN, &who, -1); |
| |
1827 chat_do_im(gtkconv, who); |
| |
1828 |
| |
1829 g_free(who); |
| |
1830 } |
| |
1831 |
| |
1832 static void |
| 1814 move_to_next_unread_tab(PidginConversation *gtkconv, gboolean forward) |
1833 move_to_next_unread_tab(PidginConversation *gtkconv, gboolean forward) |
| 1815 { |
1834 { |
| 1816 PidginConversation *next_gtkconv = NULL, *most_active = NULL; |
1835 PidginConversation *next_gtkconv = NULL, *most_active = NULL; |
| 1817 PidginUnseenState unseen_state = PIDGIN_UNSEEN_NONE; |
1836 PidginUnseenState unseen_state = PIDGIN_UNSEEN_NONE; |
| 1818 PidginWindow *win; |
1837 PidginWindow *win; |
| 2487 if (emblem) |
2506 if (emblem) |
| 2488 g_object_unref(emblem); |
2507 g_object_unref(emblem); |
| 2489 |
2508 |
| 2490 if (purple_prefs_get_bool(PIDGIN_PREFS_ROOT "/blist/show_protocol_icons")) { |
2509 if (purple_prefs_get_bool(PIDGIN_PREFS_ROOT "/blist/show_protocol_icons")) { |
| 2491 emblem = pidgin_create_prpl_icon(gtkconv->active_conv->account, PIDGIN_PRPL_ICON_SMALL); |
2510 emblem = pidgin_create_prpl_icon(gtkconv->active_conv->account, PIDGIN_PRPL_ICON_SMALL); |
| 2492 gtk_list_store_set(GTK_LIST_STORE(gtkconv->infopane_model), |
2511 } else { |
| |
2512 emblem = NULL; |
| |
2513 } |
| |
2514 |
| |
2515 gtk_list_store_set(GTK_LIST_STORE(gtkconv->infopane_model), |
| 2493 &(gtkconv->infopane_iter), |
2516 &(gtkconv->infopane_iter), |
| 2494 CONV_PROTOCOL_ICON_COLUMN, emblem, -1); |
2517 CONV_PROTOCOL_ICON_COLUMN, emblem, -1); |
| 2495 if (emblem) |
2518 if (emblem) |
| 2496 g_object_unref(emblem); |
2519 g_object_unref(emblem); |
| 2497 } |
|
| 2498 |
2520 |
| 2499 /* XXX seanegan Why do I have to do this? */ |
2521 /* XXX seanegan Why do I have to do this? */ |
| |
2522 gtk_widget_queue_resize(gtkconv->infopane); |
| 2500 gtk_widget_queue_draw(gtkconv->infopane); |
2523 gtk_widget_queue_draw(gtkconv->infopane); |
| 2501 |
2524 |
| 2502 if (status != NULL) |
2525 if (status != NULL) |
| 2503 g_object_unref(status); |
2526 g_object_unref(status); |
| 2504 |
2527 |
| 2551 } |
2575 } |
| 2552 |
2576 |
| 2553 gdk_pixbuf_animation_iter_advance(gtkconv->u.im->iter, NULL); |
2577 gdk_pixbuf_animation_iter_advance(gtkconv->u.im->iter, NULL); |
| 2554 buf = gdk_pixbuf_animation_iter_get_pixbuf(gtkconv->u.im->iter); |
2578 buf = gdk_pixbuf_animation_iter_get_pixbuf(gtkconv->u.im->iter); |
| 2555 |
2579 |
| 2556 scale_width = gdk_pixbuf_get_width(buf); |
2580 scale_width = gdk_pixbuf_get_width(buf); |
| 2557 scale_height = gdk_pixbuf_get_height(buf); |
2581 scale_height = gdk_pixbuf_get_height(buf); |
| 2558 if (scale_width == scale_height) { |
2582 |
| 2559 scale_width = scale_height = 32; |
2583 gtk_widget_get_size_request(gtkconv->infopane_hbox, NULL, &size); |
| |
2584 size = MIN(size, MIN(scale_width, scale_height)); |
| |
2585 size = CLAMP(size, BUDDYICON_SIZE_MIN, BUDDYICON_SIZE_MAX); |
| |
2586 |
| |
2587 if (scale_width == scale_height) { |
| |
2588 scale_width = scale_height = size; |
| 2560 } else if (scale_height > scale_width) { |
2589 } else if (scale_height > scale_width) { |
| 2561 scale_width = 32 * scale_width / scale_height; |
2590 scale_width = size * scale_width / scale_height; |
| 2562 scale_height = 32; |
2591 scale_height = size; |
| 2563 } else { |
2592 } else { |
| 2564 scale_height = 32 * scale_height / scale_width; |
2593 scale_height = size * scale_height / scale_width; |
| 2565 scale_width = 32; |
2594 scale_width = size; |
| 2566 } |
2595 } |
| 2567 |
2596 |
| 2568 scale = gdk_pixbuf_scale_simple(buf, scale_width, scale_height, |
2597 scale = gdk_pixbuf_scale_simple(buf, scale_width, scale_height, |
| 2569 GDK_INTERP_BILINEAR); |
2598 GDK_INTERP_BILINEAR); |
| 2570 if (pidgin_gdk_pixbuf_is_opaque(scale)) |
2599 if (pidgin_gdk_pixbuf_is_opaque(scale)) |
| 2571 pidgin_gdk_pixbuf_make_round(scale); |
2600 pidgin_gdk_pixbuf_make_round(scale); |
| 2681 custom_icon_sel_cb, gtkconv); |
2710 custom_icon_sel_cb, gtkconv); |
| 2682 gtk_widget_show_all(win); |
2711 gtk_widget_show_all(win); |
| 2683 } |
2712 } |
| 2684 |
2713 |
| 2685 static void |
2714 static void |
| |
2715 change_size_cb(GtkWidget *widget, PidginConversation *gtkconv) |
| |
2716 { |
| |
2717 int size = 0; |
| |
2718 PurpleConversation *conv = gtkconv->active_conv; |
| |
2719 GSList *buddies; |
| |
2720 |
| |
2721 gtk_widget_get_size_request(gtkconv->infopane_hbox, NULL, &size); |
| |
2722 |
| |
2723 if (size == BUDDYICON_SIZE_MAX) { |
| |
2724 size = BUDDYICON_SIZE_MIN; |
| |
2725 } else { |
| |
2726 size = BUDDYICON_SIZE_MAX; |
| |
2727 } |
| |
2728 |
| |
2729 gtk_widget_set_size_request(gtkconv->infopane_hbox, -1, size); |
| |
2730 pidgin_conv_update_buddy_icon(conv); |
| |
2731 |
| |
2732 buddies = purple_find_buddies(purple_conversation_get_account(conv), |
| |
2733 purple_conversation_get_name(conv)); |
| |
2734 for (; buddies; buddies = g_slist_delete_link(buddies, buddies)) { |
| |
2735 PurpleBuddy *buddy = buddies->data; |
| |
2736 PurpleContact *contact = purple_buddy_get_contact(buddy); |
| |
2737 purple_blist_node_set_int((PurpleBlistNode*)contact, "pidgin-infopane-iconsize", size); |
| |
2738 } |
| |
2739 } |
| |
2740 |
| |
2741 static void |
| 2686 remove_custom_icon_cb(GtkWidget *widget, PidginConversation *gtkconv) |
2742 remove_custom_icon_cb(GtkWidget *widget, PidginConversation *gtkconv) |
| 2687 { |
2743 { |
| 2688 PurpleConversation *conv; |
2744 PurpleConversation *conv; |
| 2689 PurpleAccount *account; |
2745 PurpleAccount *account; |
| 2690 |
2746 |
| 2770 G_CALLBACK(icon_menu_save_cb), gtkconv, |
2832 G_CALLBACK(icon_menu_save_cb), gtkconv, |
| 2771 0, 0, NULL); |
2833 0, 0, NULL); |
| 2772 |
2834 |
| 2773 pidgin_new_item_from_stock(menu, _("Set Custom Icon..."), NULL, |
2835 pidgin_new_item_from_stock(menu, _("Set Custom Icon..."), NULL, |
| 2774 G_CALLBACK(set_custom_icon_cb), gtkconv, |
2836 G_CALLBACK(set_custom_icon_cb), gtkconv, |
| |
2837 0, 0, NULL); |
| |
2838 |
| |
2839 pidgin_new_item_from_stock(menu, _("Change Size"), NULL, |
| |
2840 G_CALLBACK(change_size_cb), gtkconv, |
| 2775 0, 0, NULL); |
2841 0, 0, NULL); |
| 2776 |
2842 |
| 2777 /* Is there a custom icon for this person? */ |
2843 /* Is there a custom icon for this person? */ |
| 2778 conv = gtkconv->active_conv; |
2844 conv = gtkconv->active_conv; |
| 2779 buddy = purple_find_buddy(purple_conversation_get_account(conv), |
2845 buddy = purple_find_buddy(purple_conversation_get_account(conv), |
| 3407 #endif |
3473 #endif |
| 3408 |
3474 |
| 3409 static void |
3475 static void |
| 3410 update_typing_message(PidginConversation *gtkconv, const char *message) |
3476 update_typing_message(PidginConversation *gtkconv, const char *message) |
| 3411 { |
3477 { |
| 3412 GtkTextBuffer *buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(gtkconv->imhtml)); |
3478 GtkTextBuffer *buffer; |
| 3413 GtkTextMark *stmark, *enmark; |
3479 GtkTextMark *stmark, *enmark; |
| 3414 |
3480 |
| |
3481 if (g_object_get_data(G_OBJECT(gtkconv->imhtml), "disable-typing-notification")) |
| |
3482 return; |
| |
3483 |
| |
3484 buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(gtkconv->imhtml)); |
| 3415 stmark = gtk_text_buffer_get_mark(buffer, "typing-notification-start"); |
3485 stmark = gtk_text_buffer_get_mark(buffer, "typing-notification-start"); |
| 3416 enmark = gtk_text_buffer_get_mark(buffer, "typing-notification-end"); |
3486 enmark = gtk_text_buffer_get_mark(buffer, "typing-notification-end"); |
| 3417 if (stmark && enmark) { |
3487 if (stmark && enmark) { |
| 3418 GtkTextIter start, end; |
3488 GtkTextIter start, end; |
| 3419 gtk_text_buffer_get_iter_at_mark(buffer, &start, stmark); |
3489 gtk_text_buffer_get_iter_at_mark(buffer, &start, stmark); |
| 3612 |
3682 |
| 3613 gtk_widget_show(menuitem); |
3683 gtk_widget_show(menuitem); |
| 3614 gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); |
3684 gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem); |
| 3615 } |
3685 } |
| 3616 |
3686 |
| |
3687 static gboolean |
| |
3688 compare_buddy_presence(PurplePresence *p1, PurplePresence *p2) |
| |
3689 { |
| |
3690 /* This is necessary because multiple PurpleBuddy's don't share the same |
| |
3691 * PurplePresence anymore. |
| |
3692 */ |
| |
3693 PurpleBuddy *b1 = purple_presence_get_buddy(p1); |
| |
3694 PurpleBuddy *b2 = purple_presence_get_buddy(p2); |
| |
3695 if (purple_buddy_get_account(b1) == purple_buddy_get_account(b2) && |
| |
3696 strcmp(purple_buddy_get_name(b1), purple_buddy_get_name(b2)) == 0) |
| |
3697 return FALSE; |
| |
3698 return TRUE; |
| |
3699 } |
| |
3700 |
| 3617 static void |
3701 static void |
| 3618 generate_send_to_items(PidginWindow *win) |
3702 generate_send_to_items(PidginWindow *win) |
| 3619 { |
3703 { |
| 3620 GtkWidget *menu; |
3704 GtkWidget *menu; |
| 3621 GSList *group = NULL; |
3705 GSList *group = NULL; |
| 3646 if (gtkconv->active_conv->type == PURPLE_CONV_TYPE_IM) { |
3730 if (gtkconv->active_conv->type == PURPLE_CONV_TYPE_IM) { |
| 3647 buds = purple_find_buddies(gtkconv->active_conv->account, gtkconv->active_conv->name); |
3731 buds = purple_find_buddies(gtkconv->active_conv->account, gtkconv->active_conv->name); |
| 3648 |
3732 |
| 3649 if (buds == NULL) |
3733 if (buds == NULL) |
| 3650 { |
3734 { |
| 3651 /* The user isn't on the buddy list. */ |
3735 /* The user isn't on the buddy list. So we don't create any sendto menu. */ |
| 3652 create_sendto_item(menu, sg, &group, NULL, gtkconv->active_conv->account, gtkconv->active_conv->name); |
|
| 3653 } |
3736 } |
| 3654 else |
3737 else |
| 3655 { |
3738 { |
| 3656 GList *list = NULL, *iter; |
3739 GList *list = NULL, *iter; |
| 3657 for (l = buds; l != NULL; l = l->next) |
3740 for (l = buds; l != NULL; l = l->next) |
| 3671 account = purple_buddy_get_account(buddy); |
3754 account = purple_buddy_get_account(buddy); |
| 3672 if (purple_account_is_connected(account)) |
3755 if (purple_account_is_connected(account)) |
| 3673 { |
3756 { |
| 3674 /* Use the PurplePresence to get unique buddies. */ |
3757 /* Use the PurplePresence to get unique buddies. */ |
| 3675 PurplePresence *presence = purple_buddy_get_presence(buddy); |
3758 PurplePresence *presence = purple_buddy_get_presence(buddy); |
| 3676 if (!g_list_find(list, presence)) |
3759 if (!g_list_find_custom(list, presence, (GCompareFunc)compare_buddy_presence)) |
| 3677 list = g_list_prepend(list, presence); |
3760 list = g_list_prepend(list, presence); |
| 3678 } |
3761 } |
| 3679 } |
3762 } |
| 3680 } |
3763 } |
| 3681 |
3764 |
| 3682 /* Loop over the list backwards so we get the items in the right order, |
3765 /* Create the sendto menu only if it has more than one item to show */ |
| 3683 * since we did a g_list_prepend() earlier. */ |
3766 if (list && list->next) { |
| 3684 for (iter = g_list_last(list); iter != NULL; iter = iter->prev) |
3767 /* Loop over the list backwards so we get the items in the right order, |
| 3685 { |
3768 * since we did a g_list_prepend() earlier. */ |
| 3686 PurplePresence *pre = iter->data; |
3769 for (iter = g_list_last(list); iter != NULL; iter = iter->prev) { |
| 3687 PurpleBuddy *buddy = purple_presence_get_buddy(pre); |
3770 PurplePresence *pre = iter->data; |
| 3688 create_sendto_item(menu, sg, &group, buddy, |
3771 PurpleBuddy *buddy = purple_presence_get_buddy(pre); |
| |
3772 create_sendto_item(menu, sg, &group, buddy, |
| 3689 purple_buddy_get_account(buddy), purple_buddy_get_name(buddy)); |
3773 purple_buddy_get_account(buddy), purple_buddy_get_name(buddy)); |
| |
3774 } |
| 3690 } |
3775 } |
| 3691 g_list_free(list); |
3776 g_list_free(list); |
| 3692 g_slist_free(buds); |
3777 g_slist_free(buds); |
| 3693 } |
3778 } |
| 3694 } |
3779 } |
| 4359 |
4444 |
| 4360 static gboolean resize_imhtml_cb(PidginConversation *gtkconv) |
4445 static gboolean resize_imhtml_cb(PidginConversation *gtkconv) |
| 4361 { |
4446 { |
| 4362 GtkTextBuffer *buffer; |
4447 GtkTextBuffer *buffer; |
| 4363 GtkTextIter iter; |
4448 GtkTextIter iter; |
| 4364 int wrapped_lines; |
|
| 4365 int lines; |
4449 int lines; |
| 4366 GdkRectangle oneline; |
4450 GdkRectangle oneline; |
| 4367 int height, diff; |
4451 int height, diff; |
| 4368 int pad_top, pad_inside, pad_bottom; |
4452 int pad_top, pad_inside, pad_bottom; |
| 4369 int max_height = gtkconv->tab_cont->allocation.height / 2; |
4453 int max_height = gtkconv->tab_cont->allocation.height / 2; |
| 4370 |
4454 |
| 4371 buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(gtkconv->entry)); |
|
| 4372 |
|
| 4373 wrapped_lines = 1; |
|
| 4374 gtk_text_buffer_get_start_iter(buffer, &iter); |
|
| 4375 gtk_text_view_get_iter_location(GTK_TEXT_VIEW(gtkconv->entry), &iter, &oneline); |
|
| 4376 while (gtk_text_view_forward_display_line(GTK_TEXT_VIEW(gtkconv->entry), &iter)) |
|
| 4377 wrapped_lines++; |
|
| 4378 |
|
| 4379 lines = gtk_text_buffer_get_line_count(buffer); |
|
| 4380 |
|
| 4381 /* Show at least two lines */ |
|
| 4382 wrapped_lines = MAX(wrapped_lines, 2); |
|
| 4383 |
|
| 4384 pad_top = gtk_text_view_get_pixels_above_lines(GTK_TEXT_VIEW(gtkconv->entry)); |
4455 pad_top = gtk_text_view_get_pixels_above_lines(GTK_TEXT_VIEW(gtkconv->entry)); |
| 4385 pad_bottom = gtk_text_view_get_pixels_below_lines(GTK_TEXT_VIEW(gtkconv->entry)); |
4456 pad_bottom = gtk_text_view_get_pixels_below_lines(GTK_TEXT_VIEW(gtkconv->entry)); |
| 4386 pad_inside = gtk_text_view_get_pixels_inside_wrap(GTK_TEXT_VIEW(gtkconv->entry)); |
4457 pad_inside = gtk_text_view_get_pixels_inside_wrap(GTK_TEXT_VIEW(gtkconv->entry)); |
| 4387 |
4458 |
| 4388 height = (oneline.height + pad_top + pad_bottom) * lines; |
4459 buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(gtkconv->entry)); |
| 4389 if (wrapped_lines > lines) |
4460 gtk_text_buffer_get_start_iter(buffer, &iter); |
| 4390 height += (oneline.height + pad_inside) * (wrapped_lines - lines); |
4461 gtk_text_view_get_iter_location(GTK_TEXT_VIEW(gtkconv->entry), &iter, &oneline); |
| |
4462 |
| |
4463 lines = gtk_text_buffer_get_line_count(buffer); |
| |
4464 |
| |
4465 height = 0; |
| |
4466 do { |
| |
4467 int lineheight = 0; |
| |
4468 gtk_text_view_get_line_yrange(GTK_TEXT_VIEW(gtkconv->entry), &iter, NULL, &lineheight); |
| |
4469 height += lineheight; |
| |
4470 lines--; |
| |
4471 } while (gtk_text_iter_forward_line(&iter)); |
| |
4472 height += lines * (oneline.height + pad_top + pad_bottom); |
| |
4473 |
| |
4474 /* Make sure there's enough room for at least two lines. Allocate enough space to |
| |
4475 * prevent scrolling when the second line is a continuation of the first line, or |
| |
4476 * is the beginning of a new paragraph. */ |
| |
4477 height = MAX(height, 2 * (oneline.height + MAX(pad_inside, pad_top + pad_bottom))); |
| 4391 |
4478 |
| 4392 height = MIN(height, max_height); |
4479 height = MIN(height, max_height); |
| 4393 |
4480 |
| 4394 diff = height - gtkconv->entry->allocation.height; |
4481 diff = height - gtkconv->entry->allocation.height; |
| 4395 if (diff == 0 || (diff < 0 && -diff < oneline.height / 2)) |
4482 if (diff == 0 || (diff < 0 && -diff < oneline.height / 2)) |
| 4515 if (ul_width == 0) |
4602 if (ul_width == 0) |
| 4516 gtk_paned_set_position(GTK_PANED(hpaned), 999999); |
4603 gtk_paned_set_position(GTK_PANED(hpaned), 999999); |
| 4517 |
4604 |
| 4518 g_signal_connect(G_OBJECT(list), "button_press_event", |
4605 g_signal_connect(G_OBJECT(list), "button_press_event", |
| 4519 G_CALLBACK(right_click_chat_cb), gtkconv); |
4606 G_CALLBACK(right_click_chat_cb), gtkconv); |
| |
4607 g_signal_connect(G_OBJECT(list), "row-activated", |
| |
4608 G_CALLBACK(activate_list_cb), gtkconv); |
| 4520 g_signal_connect(G_OBJECT(list), "popup-menu", |
4609 g_signal_connect(G_OBJECT(list), "popup-menu", |
| 4521 G_CALLBACK(gtkconv_chat_popup_menu_cb), gtkconv); |
4610 G_CALLBACK(gtkconv_chat_popup_menu_cb), gtkconv); |
| 4522 g_signal_connect(G_OBJECT(lbox), "size-allocate", G_CALLBACK(lbox_size_allocate_cb), gtkconv); |
4611 g_signal_connect(G_OBJECT(lbox), "size-allocate", G_CALLBACK(lbox_size_allocate_cb), gtkconv); |
| 4523 |
4612 |
| 4524 pidgin_tooltip_setup_for_treeview(list, gtkconv, |
4613 pidgin_tooltip_setup_for_treeview(list, gtkconv, |
| 4590 { |
4679 { |
| 4591 GtkWidget *vbox, *frame, *imhtml_sw, *event_box; |
4680 GtkWidget *vbox, *frame, *imhtml_sw, *event_box; |
| 4592 GtkCellRenderer *rend; |
4681 GtkCellRenderer *rend; |
| 4593 GtkTreePath *path; |
4682 GtkTreePath *path; |
| 4594 PurpleConversation *conv = gtkconv->active_conv; |
4683 PurpleConversation *conv = gtkconv->active_conv; |
| |
4684 PurpleBuddy *buddy; |
| 4595 gboolean chat = (conv->type == PURPLE_CONV_TYPE_CHAT); |
4685 gboolean chat = (conv->type == PURPLE_CONV_TYPE_CHAT); |
| 4596 GtkPolicyType imhtml_sw_hscroll; |
4686 GtkPolicyType imhtml_sw_hscroll; |
| |
4687 int buddyicon_size = 0; |
| 4597 |
4688 |
| 4598 /* Setup the top part of the pane */ |
4689 /* Setup the top part of the pane */ |
| 4599 vbox = gtk_vbox_new(FALSE, PIDGIN_HIG_BOX_SPACE); |
4690 vbox = gtk_vbox_new(FALSE, PIDGIN_HIG_BOX_SPACE); |
| 4600 gtk_widget_show(vbox); |
4691 gtk_widget_show(vbox); |
| 4601 |
4692 |
| 4619 |
4710 |
| 4620 gtkconv->infopane = gtk_cell_view_new(); |
4711 gtkconv->infopane = gtk_cell_view_new(); |
| 4621 gtkconv->infopane_model = gtk_list_store_new(CONV_NUM_COLUMNS, GDK_TYPE_PIXBUF, G_TYPE_STRING, GDK_TYPE_PIXBUF, GDK_TYPE_PIXBUF); |
4712 gtkconv->infopane_model = gtk_list_store_new(CONV_NUM_COLUMNS, GDK_TYPE_PIXBUF, G_TYPE_STRING, GDK_TYPE_PIXBUF, GDK_TYPE_PIXBUF); |
| 4622 gtk_cell_view_set_model(GTK_CELL_VIEW(gtkconv->infopane), |
4713 gtk_cell_view_set_model(GTK_CELL_VIEW(gtkconv->infopane), |
| 4623 GTK_TREE_MODEL(gtkconv->infopane_model)); |
4714 GTK_TREE_MODEL(gtkconv->infopane_model)); |
| |
4715 g_object_unref(gtkconv->infopane_model); |
| 4624 gtk_list_store_append(gtkconv->infopane_model, &(gtkconv->infopane_iter)); |
4716 gtk_list_store_append(gtkconv->infopane_model, &(gtkconv->infopane_iter)); |
| 4625 gtk_box_pack_start(GTK_BOX(gtkconv->infopane_hbox), gtkconv->infopane, TRUE, TRUE, 0); |
4717 gtk_box_pack_start(GTK_BOX(gtkconv->infopane_hbox), gtkconv->infopane, TRUE, TRUE, 0); |
| 4626 path = gtk_tree_path_new_from_string("0"); |
4718 path = gtk_tree_path_new_from_string("0"); |
| 4627 gtk_cell_view_set_displayed_row(GTK_CELL_VIEW(gtkconv->infopane), path); |
4719 gtk_cell_view_set_displayed_row(GTK_CELL_VIEW(gtkconv->infopane), path); |
| 4628 gtk_tree_path_free(path); |
4720 gtk_tree_path_free(path); |
| 4629 gtk_widget_set_size_request(gtkconv->infopane_hbox, -1, 32); |
4721 |
| |
4722 if ((buddy = purple_find_buddy(purple_conversation_get_account(conv), |
| |
4723 purple_conversation_get_name(conv))) != NULL) { |
| |
4724 PurpleContact *contact = purple_buddy_get_contact(buddy); |
| |
4725 if (contact) { |
| |
4726 buddyicon_size = purple_blist_node_get_int((PurpleBlistNode*)contact, "pidgin-infopane-iconsize"); |
| |
4727 } |
| |
4728 } |
| |
4729 buddyicon_size = CLAMP(buddyicon_size, BUDDYICON_SIZE_MIN, BUDDYICON_SIZE_MAX); |
| |
4730 gtk_widget_set_size_request(gtkconv->infopane_hbox, -1, buddyicon_size); |
| 4630 gtk_widget_show(gtkconv->infopane); |
4731 gtk_widget_show(gtkconv->infopane); |
| 4631 |
4732 |
| 4632 rend = gtk_cell_renderer_pixbuf_new(); |
4733 rend = gtk_cell_renderer_pixbuf_new(); |
| 4633 gtk_cell_layout_pack_start(GTK_CELL_LAYOUT(gtkconv->infopane), rend, FALSE); |
4734 gtk_cell_layout_pack_start(GTK_CELL_LAYOUT(gtkconv->infopane), rend, FALSE); |
| 4634 gtk_cell_layout_set_attributes(GTK_CELL_LAYOUT(gtkconv->infopane), rend, "pixbuf", CONV_ICON_COLUMN, NULL); |
4735 gtk_cell_layout_set_attributes(GTK_CELL_LAYOUT(gtkconv->infopane), rend, "pixbuf", CONV_ICON_COLUMN, NULL); |
| 4894 if (e->button == 2 && e->type == GDK_BUTTON_PRESS) |
4995 if (e->button == 2 && e->type == GDK_BUTTON_PRESS) |
| 4895 return TRUE; |
4996 return TRUE; |
| 4896 return FALSE; |
4997 return FALSE; |
| 4897 } |
4998 } |
| 4898 |
4999 |
| |
5000 static void set_typing_font(GtkWidget *widget, GtkStyle *style, PidginConversation *gtkconv) |
| |
5001 { |
| |
5002 static PangoFontDescription *font_desc = NULL; |
| |
5003 static GdkColor *color = NULL; |
| |
5004 static gboolean enable = TRUE; |
| |
5005 |
| |
5006 if (font_desc == NULL) { |
| |
5007 char *string = NULL; |
| |
5008 gtk_widget_style_get(widget, |
| |
5009 "typing-notification-font", &string, |
| |
5010 "typing-notification-color", &color, |
| |
5011 "typing-notification-enable", &enable, |
| |
5012 NULL); |
| |
5013 font_desc = pango_font_description_from_string(string); |
| |
5014 g_free(string); |
| |
5015 if (color == NULL) { |
| |
5016 GdkColor def = {0, 0x8888, 0x8888, 0x8888}; |
| |
5017 color = gdk_color_copy(&def); |
| |
5018 } |
| |
5019 } |
| |
5020 |
| |
5021 gtk_text_buffer_create_tag(GTK_IMHTML(widget)->text_buffer, "TYPING-NOTIFICATION", |
| |
5022 "foreground-gdk", color, |
| |
5023 "font-desc", font_desc, |
| |
5024 NULL); |
| |
5025 |
| |
5026 if (!enable) { |
| |
5027 g_object_set_data(G_OBJECT(widget), "disable-typing-notification", GINT_TO_POINTER(TRUE)); |
| |
5028 /* or may be 'gtkconv->disable_typing = TRUE;' instead? */ |
| |
5029 } |
| |
5030 |
| |
5031 g_signal_handlers_disconnect_by_func(G_OBJECT(widget), set_typing_font, gtkconv); |
| |
5032 } |
| |
5033 |
| 4899 /************************************************************************** |
5034 /************************************************************************** |
| 4900 * Conversation UI operations |
5035 * Conversation UI operations |
| 4901 **************************************************************************/ |
5036 **************************************************************************/ |
| 4902 static void |
5037 static void |
| 4903 private_gtkconv_new(PurpleConversation *conv, gboolean hidden) |
5038 private_gtkconv_new(PurpleConversation *conv, gboolean hidden) |
| 4975 g_signal_connect(G_OBJECT(gtkconv->imhtml), "drag_data_received", |
5110 g_signal_connect(G_OBJECT(gtkconv->imhtml), "drag_data_received", |
| 4976 G_CALLBACK(conv_dnd_recv), gtkconv); |
5111 G_CALLBACK(conv_dnd_recv), gtkconv); |
| 4977 g_signal_connect(G_OBJECT(gtkconv->entry), "drag_data_received", |
5112 g_signal_connect(G_OBJECT(gtkconv->entry), "drag_data_received", |
| 4978 G_CALLBACK(conv_dnd_recv), gtkconv); |
5113 G_CALLBACK(conv_dnd_recv), gtkconv); |
| 4979 |
5114 |
| 4980 gtk_text_buffer_create_tag(GTK_IMHTML(gtkconv->imhtml)->text_buffer, "TYPING-NOTIFICATION", |
5115 g_signal_connect(gtkconv->imhtml, "style-set", G_CALLBACK(set_typing_font), gtkconv); |
| 4981 "foreground", "#888888", |
|
| 4982 "justification", GTK_JUSTIFY_LEFT, /* XXX: RTL'ify */ |
|
| 4983 "weight", PANGO_WEIGHT_LIGHT, |
|
| 4984 "scale", PANGO_SCALE_SMALL, |
|
| 4985 NULL); |
|
| 4986 |
5116 |
| 4987 /* Setup the container for the tab. */ |
5117 /* Setup the container for the tab. */ |
| 4988 gtkconv->tab_cont = tab_cont = gtk_vbox_new(FALSE, PIDGIN_HIG_BOX_SPACE); |
5118 gtkconv->tab_cont = tab_cont = gtk_vbox_new(FALSE, PIDGIN_HIG_BOX_SPACE); |
| 4989 g_object_set_data(G_OBJECT(tab_cont), "PidginConversation", gtkconv); |
5119 g_object_set_data(G_OBJECT(tab_cont), "PidginConversation", gtkconv); |
| 4990 gtk_container_set_border_width(GTK_CONTAINER(tab_cont), PIDGIN_HIG_BOX_SPACE); |
5120 gtk_container_set_border_width(GTK_CONTAINER(tab_cont), PIDGIN_HIG_BOX_SPACE); |
| 5377 |
5507 |
| 5378 type = purple_conversation_get_type(conv); |
5508 type = purple_conversation_get_type(conv); |
| 5379 account = purple_conversation_get_account(conv); |
5509 account = purple_conversation_get_account(conv); |
| 5380 g_return_if_fail(account != NULL); |
5510 g_return_if_fail(account != NULL); |
| 5381 gc = purple_account_get_connection(account); |
5511 gc = purple_account_get_connection(account); |
| 5382 g_return_if_fail(gc != NULL); |
5512 g_return_if_fail(gc != NULL || !(flags & (PURPLE_MESSAGE_SEND | PURPLE_MESSAGE_RECV))); |
| 5383 |
5513 |
| 5384 /* Make sure URLs are clickable */ |
5514 /* Make sure URLs are clickable */ |
| 5385 if(flags & PURPLE_MESSAGE_NO_LINKIFY) |
5515 if(flags & PURPLE_MESSAGE_NO_LINKIFY) |
| 5386 displaying = g_strdup(message); |
5516 displaying = g_strdup(message); |
| 5387 else |
5517 else |
| 5575 gtk_widget_style_get(GTK_WIDGET(gtkconv->imhtml), "action-name-color", &col, NULL); |
5705 gtk_widget_style_get(GTK_WIDGET(gtkconv->imhtml), "action-name-color", &col, NULL); |
| 5576 |
5706 |
| 5577 if(col) { |
5707 if(col) { |
| 5578 g_snprintf(color, sizeof(color), "#%02X%02X%02X", |
5708 g_snprintf(color, sizeof(color), "#%02X%02X%02X", |
| 5579 col->red >> 8, col->green >> 8, col->blue >> 8); |
5709 col->red >> 8, col->green >> 8, col->blue >> 8); |
| 5580 } |
5710 gdk_color_free(col); |
| 5581 else { |
5711 } else { |
| 5582 if (flags & PURPLE_MESSAGE_NICK) |
5712 if (flags & PURPLE_MESSAGE_NICK) |
| 5583 strcpy(color, DEFAULT_HIGHLIGHT_COLOR); |
5713 strcpy(color, DEFAULT_HIGHLIGHT_COLOR); |
| 5584 else |
5714 else |
| 5585 strcpy(color, DEFAULT_ACTION_COLOR); |
5715 strcpy(color, DEFAULT_ACTION_COLOR); |
| 5586 } |
5716 } |
| 5599 GdkColor *col; |
5729 GdkColor *col; |
| 5600 gtk_widget_style_get(GTK_WIDGET(gtkconv->imhtml), "highlight-name-color", &col, NULL); |
5730 gtk_widget_style_get(GTK_WIDGET(gtkconv->imhtml), "highlight-name-color", &col, NULL); |
| 5601 if(col) { |
5731 if(col) { |
| 5602 g_snprintf(color, sizeof(color), "#%02X%02X%02X", |
5732 g_snprintf(color, sizeof(color), "#%02X%02X%02X", |
| 5603 col->red >> 8, col->green >> 8, col->blue >> 8); |
5733 col->red >> 8, col->green >> 8, col->blue >> 8); |
| 5604 } |
5734 gdk_color_free(col); |
| 5605 else { |
5735 } else { |
| 5606 strcpy(color, DEFAULT_HIGHLIGHT_COLOR); |
5736 strcpy(color, DEFAULT_HIGHLIGHT_COLOR); |
| 5607 } |
5737 } |
| 5608 } |
5738 } |
| 5609 else if (flags & PURPLE_MESSAGE_RECV) { |
5739 else if (flags & PURPLE_MESSAGE_RECV) { |
| 5610 if (type == PURPLE_CONV_TYPE_CHAT) { |
5740 if (type == PURPLE_CONV_TYPE_CHAT) { |
| 5611 GdkColor *col = get_nick_color(gtkconv, name); |
5741 const GdkColor *col = get_nick_color(gtkconv, name); |
| 5612 |
5742 |
| 5613 g_snprintf(color, sizeof(color), "#%02X%02X%02X", |
5743 g_snprintf(color, sizeof(color), "#%02X%02X%02X", |
| 5614 col->red >> 8, col->green >> 8, col->blue >> 8); |
5744 col->red >> 8, col->green >> 8, col->blue >> 8); |
| 5615 } else { |
5745 } else { |
| 5616 GdkColor *col; |
5746 GdkColor *col; |
| 5617 gtk_widget_style_get(GTK_WIDGET(gtkconv->imhtml), "receive-name-color", &col, NULL); |
5747 gtk_widget_style_get(GTK_WIDGET(gtkconv->imhtml), "receive-name-color", &col, NULL); |
| 5618 if(col) { |
5748 if(col) { |
| 5619 g_snprintf(color, sizeof(color), "#%02X%02X%02X", |
5749 g_snprintf(color, sizeof(color), "#%02X%02X%02X", |
| 5620 col->red >> 8, col->green >> 8, col->blue >> 8); |
5750 col->red >> 8, col->green >> 8, col->blue >> 8); |
| 5621 } |
5751 gdk_color_free(col); |
| 5622 else { |
5752 } else { |
| 5623 strcpy(color, DEFAULT_RECV_COLOR); |
5753 strcpy(color, DEFAULT_RECV_COLOR); |
| 5624 } |
5754 } |
| 5625 } |
5755 } |
| 5626 } |
5756 } |
| 5627 else if (flags & PURPLE_MESSAGE_SEND) { |
5757 else if (flags & PURPLE_MESSAGE_SEND) { |
| 5628 GdkColor *col; |
5758 GdkColor *col; |
| 5629 gtk_widget_style_get(GTK_WIDGET(gtkconv->imhtml), "send-name-color", &col, NULL); |
5759 gtk_widget_style_get(GTK_WIDGET(gtkconv->imhtml), "send-name-color", &col, NULL); |
| 5630 if(col) { |
5760 if(col) { |
| 5631 g_snprintf(color, sizeof(color), "#%02X%02X%02X", |
5761 g_snprintf(color, sizeof(color), "#%02X%02X%02X", |
| 5632 col->red >> 8, col->green >> 8, col->blue >> 8); |
5762 col->red >> 8, col->green >> 8, col->blue >> 8); |
| 5633 } |
5763 gdk_color_free(col); |
| 5634 else { |
5764 } else { |
| 5635 strcpy(color, DEFAULT_SEND_COLOR); |
5765 strcpy(color, DEFAULT_SEND_COLOR); |
| 5636 } |
5766 } |
| 5637 } |
5767 } |
| 5638 else { |
5768 else { |
| 5639 purple_debug_error("gtkconv", "message missing flags\n"); |
5769 purple_debug_error("gtkconv", "message missing flags\n"); |
| 5643 } |
5773 } |
| 5644 |
5774 |
| 5645 g_free(alias_escaped); |
5775 g_free(alias_escaped); |
| 5646 |
5776 |
| 5647 /* Are we in a chat where we can tell which users are buddies? */ |
5777 /* Are we in a chat where we can tell which users are buddies? */ |
| 5648 if (!(prpl_info->options & OPT_PROTO_UNIQUE_CHATNAME) && |
5778 if (prpl_info && !(prpl_info->options & OPT_PROTO_UNIQUE_CHATNAME) && |
| 5649 purple_conversation_get_type(conv) == PURPLE_CONV_TYPE_CHAT) { |
5779 purple_conversation_get_type(conv) == PURPLE_CONV_TYPE_CHAT) { |
| 5650 |
5780 |
| 5651 /* Bold buddies to make them stand out from non-buddies. */ |
5781 /* Bold buddies to make them stand out from non-buddies. */ |
| 5652 if (flags & PURPLE_MESSAGE_SEND || |
5782 if (flags & PURPLE_MESSAGE_SEND || |
| 5653 flags & PURPLE_MESSAGE_NICK || |
5783 flags & PURPLE_MESSAGE_NICK || |
| 6383 markup = pidgin_blist_get_name_markup(buddy, FALSE, FALSE); |
6513 markup = pidgin_blist_get_name_markup(buddy, FALSE, FALSE); |
| 6384 } else { |
6514 } else { |
| 6385 markup = title; |
6515 markup = title; |
| 6386 } |
6516 } |
| 6387 } else if (purple_conversation_get_type(conv) == PURPLE_CONV_TYPE_CHAT) { |
6517 } else if (purple_conversation_get_type(conv) == PURPLE_CONV_TYPE_CHAT) { |
| 6388 const char *topic = gtkconv->u.chat->topic_text ? gtk_entry_get_text(GTK_ENTRY(gtkconv->u.chat->topic_text)) : NULL; |
6518 const char *topic = gtkconv->u.chat->topic_text |
| |
6519 ? gtk_entry_get_text(GTK_ENTRY(gtkconv->u.chat->topic_text)) |
| |
6520 : NULL; |
| 6389 char *esc = NULL, *tmp; |
6521 char *esc = NULL, *tmp; |
| 6390 #if GTK_CHECK_VERSION(2,6,0) |
6522 #if GTK_CHECK_VERSION(2,6,0) |
| 6391 esc = topic ? g_markup_escape_text(topic, -1) : NULL; |
6523 esc = topic ? g_markup_escape_text(topic, -1) : NULL; |
| 6392 #else |
6524 #else |
| 6393 /* GTK < 2.6 doesn't have auto ellipsization, so we do a crude |
6525 /* GTK < 2.6 doesn't have auto ellipsization, so we do a crude |
| 6394 * trucation to prevent forcing the window to be as wide as the topic */ |
6526 * trucation to prevent forcing the window to be as wide as the topic */ |
| 6395 int len = 0; |
6527 int len = 0; |
| 6396 char *c; |
6528 char *c; |
| 6397 |
6529 |
| 6398 tmp = g_strdup(topic); |
6530 if (topic != NULL) { |
| 6399 c = tmp; |
6531 tmp = g_strdup(topic); |
| 6400 while(*c && len < 72) { |
6532 c = tmp; |
| 6401 c = g_utf8_next_char(c); |
6533 while(*c && len < 72) { |
| 6402 len++; |
6534 c = g_utf8_next_char(c); |
| |
6535 len++; |
| |
6536 } |
| |
6537 if (len == 72) { |
| |
6538 *c = '\0'; |
| |
6539 c = g_strdup_printf("%s...", tmp); |
| |
6540 g_free(tmp); |
| |
6541 tmp = c; |
| |
6542 } |
| |
6543 esc = g_markup_escape_text(tmp, -1); |
| |
6544 g_free(tmp); |
| 6403 } |
6545 } |
| 6404 if (len == 72) { |
|
| 6405 *c = '\0'; |
|
| 6406 c = g_strdup_printf("%s...", tmp); |
|
| 6407 g_free(tmp); |
|
| 6408 tmp = c; |
|
| 6409 } |
|
| 6410 esc = tmp ? g_markup_escape_text(tmp, -1) : NULL; |
|
| 6411 g_free(tmp); |
|
| 6412 #endif |
6546 #endif |
| 6413 tmp = g_markup_escape_text(purple_conversation_get_title(conv), -1); |
6547 tmp = g_markup_escape_text(purple_conversation_get_title(conv), -1); |
| 6414 markup = g_strdup_printf("%s%s<span color='%s' size='smaller'>%s</span>", |
6548 markup = g_strdup_printf("%s%s<span color='%s' size='smaller'>%s</span>", |
| 6415 tmp, esc && *esc ? "\n" : "", |
6549 tmp, esc && *esc ? "\n" : "", |
| 6416 pidgin_get_dim_grey_string(gtkconv->infopane), |
6550 pidgin_get_dim_grey_string(gtkconv->infopane), |
| 6716 start_anim(NULL, gtkconv); |
6851 start_anim(NULL, gtkconv); |
| 6717 } |
6852 } |
| 6718 |
6853 |
| 6719 scale_width = gdk_pixbuf_get_width(buf); |
6854 scale_width = gdk_pixbuf_get_width(buf); |
| 6720 scale_height = gdk_pixbuf_get_height(buf); |
6855 scale_height = gdk_pixbuf_get_height(buf); |
| |
6856 |
| |
6857 gtk_widget_get_size_request(gtkconv->infopane_hbox, NULL, &size); |
| |
6858 size = MIN(size, MIN(scale_width, scale_height)); |
| |
6859 |
| |
6860 /* Some sanity checks */ |
| |
6861 size = CLAMP(size, BUDDYICON_SIZE_MIN, BUDDYICON_SIZE_MAX); |
| 6721 if (scale_width == scale_height) { |
6862 if (scale_width == scale_height) { |
| 6722 scale_width = scale_height = 32; |
6863 scale_width = scale_height = size; |
| 6723 } else if (scale_height > scale_width) { |
6864 } else if (scale_height > scale_width) { |
| 6724 scale_width = 32 * scale_width / scale_height; |
6865 scale_width = size * scale_width / scale_height; |
| 6725 scale_height = 32; |
6866 scale_height = size; |
| 6726 } else { |
6867 } else { |
| 6727 scale_height = 32 * scale_height / scale_width; |
6868 scale_height = size * scale_height / scale_width; |
| 6728 scale_width = 32; |
6869 scale_width = size; |
| 6729 } |
6870 } |
| 6730 scale = gdk_pixbuf_scale_simple(buf, scale_width, scale_height, |
6871 scale = gdk_pixbuf_scale_simple(buf, scale_width, scale_height, |
| 6731 GDK_INTERP_BILINEAR); |
6872 GDK_INTERP_BILINEAR); |
| 6732 g_object_unref(buf); |
6873 g_object_unref(buf); |
| 6733 if (pidgin_gdk_pixbuf_is_opaque(scale)) |
6874 if (pidgin_gdk_pixbuf_is_opaque(scale)) |
| 7563 /* IM callbacks */ |
7704 /* IM callbacks */ |
| 7564 purple_prefs_connect_callback(handle, PIDGIN_PREFS_ROOT "/conversations/im/animate_buddy_icons", |
7705 purple_prefs_connect_callback(handle, PIDGIN_PREFS_ROOT "/conversations/im/animate_buddy_icons", |
| 7565 animate_buddy_icons_pref_cb, NULL); |
7706 animate_buddy_icons_pref_cb, NULL); |
| 7566 purple_prefs_connect_callback(handle, PIDGIN_PREFS_ROOT "/conversations/im/show_buddy_icons", |
7707 purple_prefs_connect_callback(handle, PIDGIN_PREFS_ROOT "/conversations/im/show_buddy_icons", |
| 7567 show_buddy_icons_pref_cb, NULL); |
7708 show_buddy_icons_pref_cb, NULL); |
| 7568 purple_prefs_connect_callback(handle, PIDGIN_PREFS_ROOT "/conversations/im/show_protocol_icons", |
7709 purple_prefs_connect_callback(handle, PIDGIN_PREFS_ROOT "/blist/show_protocol_icons", |
| 7569 show_protocol_icons_pref_cb, NULL); |
7710 show_protocol_icons_pref_cb, NULL); |
| 7570 purple_prefs_connect_callback(handle, PIDGIN_PREFS_ROOT "/conversations/im/hide_new", |
7711 purple_prefs_connect_callback(handle, PIDGIN_PREFS_ROOT "/conversations/im/hide_new", |
| 7571 hide_new_pref_cb, NULL); |
7712 hide_new_pref_cb, NULL); |
| 7572 |
7713 |
| 7573 |
7714 |
| 8106 to_right = to_right && (win != dest_win); |
8247 to_right = to_right && (win != dest_win); |
| 8107 tab = pidgin_conv_window_get_gtkconv_at_index(dest_win, page_num)->tabby; |
8248 tab = pidgin_conv_window_get_gtkconv_at_index(dest_win, page_num)->tabby; |
| 8108 } else { |
8249 } else { |
| 8109 page_num = 0; |
8250 page_num = 0; |
| 8110 to_right = pidgin_conv_xy_to_right_infopane(dest_win, e->x_root, e->y_root); |
8251 to_right = pidgin_conv_xy_to_right_infopane(dest_win, e->x_root, e->y_root); |
| 8111 tab = pidgin_conv_window_get_gtkconv_at_index(dest_win, page_num)->infopane; |
8252 tab = pidgin_conv_window_get_gtkconv_at_index(dest_win, page_num)->infopane_hbox; |
| 8112 } |
8253 } |
| 8113 |
8254 |
| 8114 if (gtk_notebook_get_tab_pos(dest_notebook) == GTK_POS_TOP || |
8255 if (gtk_notebook_get_tab_pos(dest_notebook) == GTK_POS_TOP || |
| 8115 gtk_notebook_get_tab_pos(dest_notebook) == GTK_POS_BOTTOM) { |
8256 gtk_notebook_get_tab_pos(dest_notebook) == GTK_POS_BOTTOM) { |
| 8116 horiz_tabs = TRUE; |
8257 horiz_tabs = TRUE; |
| 8416 if (new_window) { |
8557 if (new_window) { |
| 8417 gint win_width, win_height; |
8558 gint win_width, win_height; |
| 8418 |
8559 |
| 8419 gtk_window_get_size(GTK_WINDOW(dest_win->window), |
8560 gtk_window_get_size(GTK_WINDOW(dest_win->window), |
| 8420 &win_width, &win_height); |
8561 &win_width, &win_height); |
| 8421 #ifdef WIN32 /* only override window manager placement on Windows */ |
8562 #ifdef _WIN32 /* only override window manager placement on Windows */ |
| 8422 gtk_window_move(GTK_WINDOW(dest_win->window), |
8563 gtk_window_move(GTK_WINDOW(dest_win->window), |
| 8423 e->x_root - (win_width / 2), |
8564 e->x_root - (win_width / 2), |
| 8424 e->y_root - (win_height / 2)); |
8565 e->y_root - (win_height / 2)); |
| 8425 #endif |
8566 #endif |
| 8426 |
8567 |
| 8852 conv_y = gdk_screen_height() - 100; |
8993 conv_y = gdk_screen_height() - 100; |
| 8853 else if (conv_y + conv_height < 0) |
8994 else if (conv_y + conv_height < 0) |
| 8854 conv_y = 100; |
8995 conv_y = 100; |
| 8855 |
8996 |
| 8856 /* ...and move it back. */ |
8997 /* ...and move it back. */ |
| |
8998 #ifdef _WIN32 /* only override window manager placement on Windows */ |
| 8857 gtk_window_move(GTK_WINDOW(win->window), conv_x, conv_y); |
8999 gtk_window_move(GTK_WINDOW(win->window), conv_x, conv_y); |
| |
9000 #endif |
| 8858 gtk_window_resize(GTK_WINDOW(win->window), conv_width, conv_height); |
9001 gtk_window_resize(GTK_WINDOW(win->window), conv_width, conv_height); |
| 8859 } |
9002 } |
| 8860 } |
9003 } |
| 8861 |
9004 |
| 8862 static void |
9005 static void |
| 8887 win->window = pidgin_create_window(NULL, 0, "conversation", TRUE); |
9030 win->window = pidgin_create_window(NULL, 0, "conversation", TRUE); |
| 8888 #if GTK_CHECK_VERSION(2,6,0) |
9031 #if GTK_CHECK_VERSION(2,6,0) |
| 8889 if (!gtk_get_current_event_state(&state)) |
9032 if (!gtk_get_current_event_state(&state)) |
| 8890 gtk_window_set_focus_on_map(GTK_WINDOW(win->window), FALSE); |
9033 gtk_window_set_focus_on_map(GTK_WINDOW(win->window), FALSE); |
| 8891 #endif |
9034 #endif |
| |
9035 /* Etan: I really think this entire function call should happen only |
| |
9036 * when we are on Windows but I was informed that back before we used |
| |
9037 * to save the window position we stored the window size, so I'm |
| |
9038 * leaving it for now. */ |
| |
9039 #if TRUE || defined(_WIN32) |
| 8892 pidgin_conv_restore_position(win); |
9040 pidgin_conv_restore_position(win); |
| |
9041 #endif |
| 8893 |
9042 |
| 8894 if (available_list == NULL) { |
9043 if (available_list == NULL) { |
| 8895 create_icon_lists(win->window); |
9044 create_icon_lists(win->window); |
| 8896 } |
9045 } |
| 8897 |
9046 |