From d879ee06a376d230141818283c058619a64a7213 Mon Sep 17 00:00:00 2001 From: kbdserver Date: Fri, 12 Oct 2018 10:53:40 +0100 Subject: [PATCH] [Notifications] Migrate to GTK3 - Switch from pynotify to gi libnotify binding. - Ideally would drop libnotify for [GNotification] but requires more work with the desktop file needing renamed to DNS format. e.g. `org.deluge-torrent.deluge` [GNotification]: https://developer.gnome.org/GNotification/ Co-authored-by: Calum Lind calumlind+deluge@gmail.com --- .../plugins/notifications/data/config.ui | 67 ++++++----- .../deluge/plugins/notifications/gtkui.py | 104 +++++++++--------- 2 files changed, 91 insertions(+), 80 deletions(-) diff --git a/deluge/plugins/Notifications/deluge/plugins/notifications/data/config.ui b/deluge/plugins/Notifications/deluge/plugins/notifications/data/config.ui index 44de30a5a..f26275be7 100644 --- a/deluge/plugins/Notifications/deluge/plugins/notifications/data/config.ui +++ b/deluge/plugins/Notifications/deluge/plugins/notifications/data/config.ui @@ -1,7 +1,7 @@ + - - + 1 65535 @@ -29,10 +29,13 @@ True False + start True False + start + 9 0 none @@ -40,6 +43,7 @@ True False 12 + 10 True @@ -82,6 +86,7 @@ True True False + start True @@ -120,6 +125,8 @@ True False + start + 5 5 <b>UI Notifications</b> True @@ -136,6 +143,9 @@ True False + start + 10 + 7 0 none @@ -143,6 +153,7 @@ True False 12 + 10 True @@ -151,15 +162,12 @@ 4 2 2 - - - True False + start Hostname: - right 1 @@ -172,8 +180,6 @@ True False False - True - True 1 @@ -204,8 +210,6 @@ 5 False False - True - True adjustment1 1 True @@ -221,8 +225,8 @@ True False + start Username: - right 2 @@ -235,8 +239,6 @@ True False False - True - True 1 @@ -249,6 +251,7 @@ True False + start Password: @@ -263,8 +266,6 @@ False False False - True - True 1 @@ -277,13 +278,14 @@ True False + start 0 none True False - 12 + 10 True @@ -293,8 +295,6 @@ True True - automatic - automatic in @@ -302,6 +302,9 @@ True False horizontal + + + @@ -365,7 +368,9 @@ True False <b>Recipients</b> + 3 True + 0 @@ -380,6 +385,7 @@ True True False + start True @@ -394,15 +400,14 @@ 4 5 6 - 10 True False + start From: - right 4 @@ -415,8 +420,6 @@ True False False - True - True 1 @@ -446,6 +449,7 @@ True False + start 5 <b>Email Notifications</b> True @@ -474,6 +478,9 @@ True False + 15 + 10 + 10 @@ -481,13 +488,14 @@ True True - automatic - automatic True True horizontal + + + @@ -532,16 +540,20 @@ True False + 15 + 10 + 10 True True - automatic - automatic True True + + + @@ -624,5 +636,8 @@ + + + diff --git a/deluge/plugins/Notifications/deluge/plugins/notifications/gtkui.py b/deluge/plugins/Notifications/deluge/plugins/notifications/gtkui.py index ad6931a6a..9b1cbaada 100644 --- a/deluge/plugins/Notifications/deluge/plugins/notifications/gtkui.py +++ b/deluge/plugins/Notifications/deluge/plugins/notifications/gtkui.py @@ -17,7 +17,8 @@ from __future__ import unicode_literals import logging from os.path import basename -import gtk +from gi import require_version +from gi.repository import Gtk from twisted.internet import defer import deluge.common @@ -40,13 +41,12 @@ except ImportError: SOUND_AVAILABLE = False try: - import pynotify - - POPUP_AVAILABLE = True - if deluge.common.windows_check(): - POPUP_AVAILABLE = False -except ImportError: + require_version('Notify', '0.7') + from gi.repository import Notify +except (ValueError, ImportError): POPUP_AVAILABLE = False +else: + POPUP_AVAILABLE = not deluge.common.windows_check() DEFAULT_PREFS = { @@ -174,17 +174,13 @@ class GtkUiNotifications(CustomNotifications): if not self.config['popup_enabled']: return defer.succeed(_('Popup notification is not enabled.')) if not POPUP_AVAILABLE: - return defer.fail(_('pynotify is not installed')) + return defer.fail(_('libnotify is not installed')) - if pynotify.init('Deluge'): - icon = gtk.gdk.pixbuf_new_from_file_at_size( - deluge.common.get_pixmap('deluge.svg'), 48, 48 - ) - self.note = pynotify.Notification(title, message) - self.note.set_icon_from_pixbuf(icon) + if Notify.init('Deluge'): + self.note = Notify.Notification.new(title, message, 'deluge-tray') self.note.set_hint('desktop-entry', 'deluge') if not self.note.show(): - err_msg = _('pynotify failed to show notification') + err_msg = _('Failed to popup notification') log.warning(err_msg) return defer.fail(err_msg) return defer.succeed(_('Notification popup shown')) @@ -254,7 +250,7 @@ class GtkUI(Gtk3PluginBase, GtkUiNotifications): self.config = deluge.configmanager.ConfigManager( 'notifications-gtk.conf', DEFAULT_PREFS ) - self.builder = gtk.Builder() + self.builder = Gtk.Builder() self.builder.add_from_file(get_resource('config.ui')) self.builder.get_object('smtp_port').set_value(25) self.prefs = self.builder.get_object('prefs_box') @@ -331,12 +327,12 @@ class GtkUI(Gtk3PluginBase, GtkUiNotifications): treeview_selection.connect( 'changed', self.on_recipients_treeview_selection_changed ) - self.recipients_model = gtk.ListStore(str, bool) + self.recipients_model = Gtk.ListStore(str, bool) - renderer = gtk.CellRendererText() + renderer = Gtk.CellRendererText() renderer.connect('edited', self.on_cell_edited, self.recipients_model) - renderer.set_data('recipient', RECIPIENT_FIELD) - column = gtk.TreeViewColumn( + renderer.recipient = RECIPIENT_FIELD + column = Gtk.TreeViewColumn( 'Recipients', renderer, text=RECIPIENT_FIELD, editable=RECIPIENT_EDIT ) column.set_expand(True) @@ -350,28 +346,28 @@ class GtkUI(Gtk3PluginBase, GtkUiNotifications): sounds_selection.connect('changed', self.on_sounds_treeview_selection_changed) self.sounds_treeview.set_tooltip_column(SND_EVENT_DOC) - self.sounds_model = gtk.ListStore(str, str, str, str) + self.sounds_model = Gtk.ListStore(str, str, str, str) - renderer = gtk.CellRendererText() - renderer.set_data('event', SND_EVENT) - column = gtk.TreeViewColumn('Event', renderer, text=SND_EVENT) + renderer = Gtk.CellRendererText() + renderer.event = SND_EVENT + column = Gtk.TreeViewColumn('Event', renderer, text=SND_EVENT) column.set_expand(True) self.sounds_treeview.append_column(column) - renderer = gtk.CellRendererText() - renderer.set_data('event_doc', SND_EVENT_DOC) - column = gtk.TreeViewColumn('Doc', renderer, text=SND_EVENT_DOC) + renderer = Gtk.CellRendererText() + renderer.event_doc = SND_EVENT_DOC + column = Gtk.TreeViewColumn('Doc', renderer, text=SND_EVENT_DOC) column.set_property('visible', False) self.sounds_treeview.append_column(column) - renderer = gtk.CellRendererText() - renderer.set_data('sound_name', SND_NAME) - column = gtk.TreeViewColumn('Name', renderer, text=SND_NAME) + renderer = Gtk.CellRendererText() + renderer.sound_name = SND_NAME + column = Gtk.TreeViewColumn('Name', renderer, text=SND_NAME) self.sounds_treeview.append_column(column) - renderer = gtk.CellRendererText() - renderer.set_data('sound_path', SND_PATH) - column = gtk.TreeViewColumn('Path', renderer, text=SND_PATH) + renderer = Gtk.CellRendererText() + renderer.sound_path = SND_PATH + column = Gtk.TreeViewColumn('Path', renderer, text=SND_PATH) column.set_property('visible', False) self.sounds_treeview.append_column(column) @@ -385,45 +381,45 @@ class GtkUI(Gtk3PluginBase, GtkUiNotifications): 'changed', self.on_subscriptions_treeview_selection_changed ) self.subscriptions_treeview.set_tooltip_column(SUB_EVENT_DOC) - self.subscriptions_model = gtk.ListStore(str, str, bool, bool, bool, bool) + self.subscriptions_model = Gtk.ListStore(str, str, bool, bool, bool, bool) - renderer = gtk.CellRendererText() - renderer.set_data('event', SUB_EVENT) - column = gtk.TreeViewColumn('Event', renderer, text=SUB_EVENT) + renderer = Gtk.CellRendererText() + setattr(renderer, 'event', SUB_EVENT) + column = Gtk.TreeViewColumn('Event', renderer, text=SUB_EVENT) column.set_expand(True) self.subscriptions_treeview.append_column(column) - renderer = gtk.CellRendererText() - renderer.set_data('event_doc', SUB_EVENT) - column = gtk.TreeViewColumn('Doc', renderer, text=SUB_EVENT_DOC) + renderer = Gtk.CellRendererText() + setattr(renderer, 'event_doc', SUB_EVENT) + column = Gtk.TreeViewColumn('Doc', renderer, text=SUB_EVENT_DOC) column.set_property('visible', False) self.subscriptions_treeview.append_column(column) - renderer = gtk.CellRendererToggle() + renderer = Gtk.CellRendererToggle() renderer.set_property('activatable', True) renderer.connect('toggled', self._on_email_col_toggled) - column = gtk.TreeViewColumn('Email', renderer, active=SUB_NOT_EMAIL) + column = Gtk.TreeViewColumn('Email', renderer, active=SUB_NOT_EMAIL) column.set_clickable(True) self.subscriptions_treeview.append_column(column) - renderer = gtk.CellRendererToggle() + renderer = Gtk.CellRendererToggle() renderer.set_property('activatable', True) renderer.connect('toggled', self._on_popup_col_toggled) - column = gtk.TreeViewColumn('Popup', renderer, active=SUB_NOT_POPUP) + column = Gtk.TreeViewColumn('Popup', renderer, active=SUB_NOT_POPUP) column.set_clickable(True) self.subscriptions_treeview.append_column(column) - renderer = gtk.CellRendererToggle() + renderer = Gtk.CellRendererToggle() renderer.set_property('activatable', True) renderer.connect('toggled', self._on_blink_col_toggled) - column = gtk.TreeViewColumn('Blink', renderer, active=SUB_NOT_BLINK) + column = Gtk.TreeViewColumn('Blink', renderer, active=SUB_NOT_BLINK) column.set_clickable(True) self.subscriptions_treeview.append_column(column) - renderer = gtk.CellRendererToggle() + renderer = Gtk.CellRendererToggle() renderer.set_property('activatable', True) renderer.connect('toggled', self._on_sound_col_toggled) - column = gtk.TreeViewColumn('Sound', renderer, active=SUB_NOT_SOUND) + column = Gtk.TreeViewColumn('Sound', renderer, active=SUB_NOT_SOUND) column.set_clickable(True) self.subscriptions_treeview.append_column(column) self.subscriptions_treeview.set_model(self.subscriptions_model) @@ -661,19 +657,19 @@ class GtkUI(Gtk3PluginBase, GtkUiNotifications): model, selected_iter = selection.get_selected() if selected_iter: path = model.get(selected_iter, SND_PATH)[0] - dialog = gtk.FileChooserDialog( + dialog = Gtk.FileChooserDialog( title=_('Choose Sound File'), buttons=( - gtk.STOCK_CANCEL, - gtk.RESPONSE_CANCEL, - gtk.STOCK_OPEN, - gtk.RESPONSE_OK, + Gtk.STOCK_CANCEL, + Gtk.ResponseType.CANCEL, + Gtk.STOCK_OPEN, + Gtk.ResponseType.OK, ), ) dialog.set_filename(path) def update_model(response): - if response == gtk.RESPONSE_OK: + if response == Gtk.ResponseType.OK: new_filename = dialog.get_filename() dialog.destroy() log.debug(new_filename)