From d7501b9ebfa86341f10a7e1d66eb491a1dcf53ba Mon Sep 17 00:00:00 2001 From: Denis Fomin Date: Sat, 5 Jan 2013 01:27:22 +0400 Subject: [PATCH] fix big avatar --- src/chat_control.py | 63 +++++++++++-------------------------------- src/dialogs.py | 48 +++++++++++++++++++++++++++++++++ src/gtkgui_helpers.py | 2 +- 3 files changed, 65 insertions(+), 48 deletions(-) diff --git a/src/chat_control.py b/src/chat_control.py index 270214592..5befa4332 100644 --- a/src/chat_control.py +++ b/src/chat_control.py @@ -3007,9 +3007,9 @@ class ChatControl(ChatControlBase): Resize the avatar, if needed, so it has at max half the screen size and shows it """ - if not small_avatar.window: - # Tab has been closed since we hovered the avatar - return + #if not small_avatar.window: + ### Tab has been closed since we hovered the avatar + #return avatar_pixbuf = gtkgui_helpers.get_avatar_pixbuf_from_cache( self.contact.jid) if avatar_pixbuf in ('ask', None): @@ -3022,7 +3022,8 @@ class ChatControl(ChatControlBase): image = self.xml.get_object('avatar_image') pixbuf = image.get_pixbuf() pixbuf.fill(0xffffff00) # RGBA - image.queue_draw() + image.set_from_pixbuf(pixbuf) + #image.queue_draw() screen_w = Gdk.Screen.width() screen_h = Gdk.Screen.height() @@ -3034,56 +3035,24 @@ class ChatControl(ChatControlBase): avatar_w = half_scr_w if avatar_h > half_scr_h: avatar_h = half_scr_h - window = Gtk.Window(Gtk.WindowType.POPUP) - self.bigger_avatar_window = window - pixmap, mask = avatar_pixbuf.render_pixmap_and_mask() - window.set_size_request(avatar_w, avatar_h) # we should make the cursor visible # gtk+ doesn't make use of the motion notify on gtkwindow by default # so this line adds that - window.set_events(Gdk.EventMask.POINTER_MOTION_MASK) - window.set_app_paintable(True) - window.set_type_hint(Gdk.WindowTypeHint.TOOLTIP) - - window.realize() - window.window.set_back_pixmap(pixmap, False) # make it transparent - window.window.shape_combine_mask(mask, 0, 0) + alloc = small_avatar.get_allocation() # make the bigger avatar window show up centered - x0, y0 = small_avatar.window.get_origin()[1:] - x0 += small_avatar.allocation.x - y0 += small_avatar.allocation.y - center_x= x0 + (small_avatar.allocation.width / 2) - center_y = y0 + (small_avatar.allocation.height / 2) + small_avatar_x, small_avatar_y = alloc.x, alloc.y + translated_coordinates = small_avatar.translate_coordinates( + gajim.interface.roster.window, 0, 0) + if translated_coordinates: + small_avatar_x, small_avatar_y = translated_coordinates + roster_x, roster_y = self.parent_win.window.get_window().get_origin()[1:] + center_x = roster_x + small_avatar_x + (alloc.width / 2) + center_y = roster_y + small_avatar_y + (alloc.height / 2) pos_x, pos_y = center_x - (avatar_w / 2), center_y - (avatar_h / 2) - window.move(pos_x, pos_y) - # make the cursor invisible so we can see the image - invisible_cursor = gtkgui_helpers.get_invisible_cursor() - window.window.set_cursor(invisible_cursor) - # we should hide the window - window.connect('leave_notify_event', - self._on_window_avatar_leave_notify_event) - window.connect('motion-notify-event', - self._on_window_motion_notify_event) - - window.show_all() - - def _on_window_avatar_leave_notify_event(self, widget, event): - """ - Just left the popup window that holds avatar - """ - self.bigger_avatar_window.destroy() - self.bigger_avatar_window = None - # Re-show the small avatar - self.show_avatar() - - def _on_window_motion_notify_event(self, widget, event): - """ - Just moved the mouse so show the cursor - """ - cursor = Gdk.Cursor.new(Gdk.CursorType.LEFT_PTR) - self.bigger_avatar_window.window.set_cursor(cursor) + dialogs.BigAvatarWindow(avatar_pixbuf, pos_x, pos_y, avatar_w, + avatar_h, self.show_avatar) def _on_send_file_menuitem_activate(self, widget): self._on_send_file() diff --git a/src/dialogs.py b/src/dialogs.py index 2b8ac2f81..1f705a344 100644 --- a/src/dialogs.py +++ b/src/dialogs.py @@ -33,6 +33,7 @@ from gi.repository import Gtk from gi.repository import Gdk from gi.repository import GdkPixbuf from gi.repository import GObject +import cairo import os import gtkgui_helpers @@ -5325,3 +5326,50 @@ class SSLErrorDialog(ConfirmationDialogDoubleCheck): def on_cert_clicked(self, button): d = CertificatDialog(self, self.account, self.cert) + + +class BigAvatarWindow(Gtk.Window): + def __init__(self, avatar, pos_x, pos_y, width, height, callback): + super(BigAvatarWindow, self).__init__(type=Gtk.WindowType.POPUP) + self.set_events(Gdk.EventMask.POINTER_MOTION_MASK) + self.avatar = avatar + self.callback = callback + self.screen = self.get_screen() + self.visual = self.screen.get_rgba_visual() + if self.visual != None and self.screen.is_composited(): + self.set_visual(self.visual) + self.set_app_paintable(True) + self.set_size_request(width, height) + self.move(pos_x, pos_y) + self.connect("draw", self.area_draw) + # we should hide the window + self.connect('leave_notify_event', self._on_window_avatar_leave_notify) + self.connect('motion-notify-event', self._on_window_motion_notify) + self.realize() + # make the cursor invisible so we can see the image + invisible_cursor = gtkgui_helpers.get_invisible_cursor() + self.get_window().set_cursor(invisible_cursor) + self.show_all() + + def area_draw(self, widget, cr): + cr.set_source_rgba(.2, .2, .2, 0.0) + cr.set_operator(cairo.OPERATOR_SOURCE) + Gdk.cairo_set_source_pixbuf(cr, self.avatar, 0, 0) + cr.paint() + cr.set_operator(cairo.OPERATOR_OVER) + + def _on_window_avatar_leave_notify(self, widget, event): + """ + Just left the popup window that holds avatar + """ + self.destroy() + self.bigger_avatar_window = None + # Re-show the small avatar + self.callback() + + def _on_window_motion_notify(self, widget, event): + """ + Just moved the mouse so show the cursor + """ + cursor = Gdk.Cursor.new(Gdk.CursorType.LEFT_PTR) + self.get_window().set_cursor(cursor) diff --git a/src/gtkgui_helpers.py b/src/gtkgui_helpers.py index 9591a147d..8b29f2065 100644 --- a/src/gtkgui_helpers.py +++ b/src/gtkgui_helpers.py @@ -133,7 +133,7 @@ def popup_emoticons_under_button(menu, button, parent_win): gajim.interface.roster.window, 0, 0) if translated_coordinates: button_x, button_y = translated_coordinates - _alloc = parent_win.notebook.get_allocation() + # now convert them to X11-relative window_x, window_y = window_x1, window_y1 x = window_x + button_x