Gtk UI: Move refresh progress bar into the header bar
This commit is contained in:
parent
a73d6cbb47
commit
2db8b93c87
|
@ -175,7 +175,9 @@
|
|||
<property name="can_focus">True</property>
|
||||
<property name="hscrollbar_policy">GTK_POLICY_AUTOMATIC</property>
|
||||
<property name="vscrollbar_policy">GTK_POLICY_AUTOMATIC</property>
|
||||
<property name="vexpand">True</property>
|
||||
<property name="vexpand">True</property>
|
||||
<property name="hexpand">True</property>
|
||||
|
||||
<property name="shadow_type">GTK_SHADOW_IN</property>
|
||||
<property name="window_placement">GTK_CORNER_TOP_LEFT</property>
|
||||
<child>
|
||||
|
@ -214,56 +216,6 @@
|
|||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkGrid" id="vbox42">
|
||||
<property name="visible">True</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<property name="hexpand">True</property>
|
||||
<child>
|
||||
<object class="GtkButton" id="btnUpdateFeeds">
|
||||
<property name="label" translatable="yes">Check for new episodes</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="focus_on_click">True</property>
|
||||
<property name="action-name">win.update</property>
|
||||
<property name="hexpand">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkGrid" id="hboxUpdateFeeds">
|
||||
<property name="column_spacing">6</property>
|
||||
<property name="orientation">horizontal</property>
|
||||
<child>
|
||||
<object class="GtkProgressBar" id="pbFeedUpdate">
|
||||
<property name="hexpand">True</property>
|
||||
<property name="pulse_step">0.10000000149</property>
|
||||
<property name="show-text">True</property>
|
||||
<property name="ellipsize">PANGO_ELLIPSIZE_MIDDLE</property>
|
||||
</object>
|
||||
<packing>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkButton" id="btnCancelFeedUpdate">
|
||||
<property name="can_focus">True</property>
|
||||
<property name="focus_on_click">True</property>
|
||||
<signal handler="on_btnCancelFeedUpdate_clicked" name="clicked"/>
|
||||
<child>
|
||||
<object class="GtkImage" id="image3209">
|
||||
<property name="visible">True</property>
|
||||
<property name="stock">gtk-cancel</property>
|
||||
<property name="icon_size">4</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="shrink">False</property>
|
||||
|
|
|
@ -43,6 +43,10 @@
|
|||
<attribute name="label" translatable="yes">Check for new episodes</attribute>
|
||||
<attribute name="accel"><Primary>r</attribute>
|
||||
</item>
|
||||
<item>
|
||||
<attribute name="action">win.cancelFeedUpdate</attribute>
|
||||
<attribute name="label" translatable="yes">Cancel check for new episodes</attribute>
|
||||
</item>
|
||||
<item>
|
||||
<attribute name="action">win.downloadAllNew</attribute>
|
||||
<attribute name="label" translatable="yes">Download new episodes</attribute>
|
||||
|
|
|
@ -145,7 +145,25 @@ class gPodderApplication(Gtk.Application):
|
|||
|
||||
self.want_headerbar = ('GNOME' in xdg_current_desktops) and not gpodder.ui.osx and not csd_disabled
|
||||
|
||||
self.header_bar_refresh_button = Gtk.Button.new_from_icon_name('view-refresh-symbolic', Gtk.IconSize.SMALL_TOOLBAR)
|
||||
|
||||
# TODO: In Gtk 4, Gtk.Button.set_icon_name() is a thing, so this can probably be removed once we migrate
|
||||
def _set_icon_name_patch(icon_name):
|
||||
self.header_bar_refresh_button.set_image(Gtk.Image.new_from_icon_name(icon_name, Gtk.IconSize.SMALL_TOOLBAR))
|
||||
|
||||
self.header_bar_refresh_button.set_icon_name = _set_icon_name_patch
|
||||
self.header_bar_refresh_button.set_action_name('win.update')
|
||||
|
||||
self.header_bar_refresh_ui = Gtk.Grid()
|
||||
|
||||
self.header_bar_menu_button = Gtk.Button.new_from_icon_name('open-menu-symbolic', Gtk.IconSize.SMALL_TOOLBAR)
|
||||
self.header_bar_menu_button.set_action_name('app.menu')
|
||||
|
||||
self.app_menu = builder.get_object('app-menu')
|
||||
|
||||
self.menu_popover = Gtk.Popover.new_from_model(self.header_bar_menu_button, self.app_menu)
|
||||
self.menu_popover.set_position(Gtk.PositionType.BOTTOM)
|
||||
|
||||
if self.want_headerbar:
|
||||
# This is a dirty hack to remove the "Quit" item in the menu
|
||||
it = self.app_menu.iterate_item_links(2)
|
||||
|
@ -153,14 +171,6 @@ class gPodderApplication(Gtk.Application):
|
|||
it.get_value().remove(2)
|
||||
|
||||
# Use GtkHeaderBar for client-side decorations on recent GNOME 3 versions
|
||||
self.header_bar_menu_button = Gtk.Button.new_from_icon_name('open-menu-symbolic', Gtk.IconSize.SMALL_TOOLBAR)
|
||||
self.header_bar_menu_button.set_action_name('app.menu')
|
||||
|
||||
self.header_bar_refresh_button = Gtk.Button.new_from_icon_name('view-refresh-symbolic', Gtk.IconSize.SMALL_TOOLBAR)
|
||||
self.header_bar_refresh_button.set_action_name('win.updateChannel')
|
||||
|
||||
self.menu_popover = Gtk.Popover.new_from_model(self.header_bar_menu_button, self.app_menu)
|
||||
self.menu_popover.set_position(Gtk.PositionType.BOTTOM)
|
||||
|
||||
for (accel, action) in parse_app_menu_for_accels(menu_filename):
|
||||
self.add_accelerator(accel, action, None)
|
||||
|
@ -168,7 +178,6 @@ class gPodderApplication(Gtk.Application):
|
|||
# TODO: Move the menubar
|
||||
self.set_menubar(self.menubar)
|
||||
else:
|
||||
self.menubar.insert_submenu(0, 'gPodder', self.app_menu)
|
||||
self.set_menubar(self.menubar)
|
||||
|
||||
Gtk.Window.set_default_icon_name('gpodder')
|
||||
|
|
|
@ -98,10 +98,22 @@ class gPodder(BuilderWidget, dbus.service.Object):
|
|||
self.stack_switcher = Gtk.StackSwitcher()
|
||||
self.stack_switcher.set_stack(self.wNotebook)
|
||||
|
||||
self.pbFeedUpdate = Gtk.ProgressBar()
|
||||
self.pbFeedUpdate.set_show_text(True)
|
||||
self.pbFeedUpdate.set_property('ellipsize', Pango.EllipsizeMode.END)
|
||||
self.pbFeedUpdate.set_property('valign', Gtk.Align.CENTER)
|
||||
self.pbFeedUpdate.set_property('vexpand', True)
|
||||
|
||||
self.header_bar_refresh_ui_revealer = Gtk.Revealer()
|
||||
self.header_bar_refresh_ui_revealer.set_transition_type(Gtk.RevealerTransitionType.CROSSFADE)
|
||||
self.header_bar_refresh_ui_revealer.add(self.pbFeedUpdate)
|
||||
self.application.header_bar_refresh_ui.attach(self.header_bar_refresh_ui_revealer, 0, 0, 1, 1)
|
||||
|
||||
if self.application.want_headerbar:
|
||||
self.header_bar = Gtk.HeaderBar()
|
||||
self.header_bar.pack_end(self.application.header_bar_menu_button)
|
||||
self.header_bar.pack_start(self.application.header_bar_refresh_button)
|
||||
self.header_bar.pack_start(self.application.header_bar_refresh_ui)
|
||||
self.header_bar.set_custom_title(self.stack_switcher)
|
||||
self.header_bar.set_show_close_button(True)
|
||||
self.header_bar.show_all()
|
||||
|
@ -111,10 +123,28 @@ class gPodder(BuilderWidget, dbus.service.Object):
|
|||
|
||||
self.main_window.set_titlebar(self.header_bar)
|
||||
else:
|
||||
self.vMain.pack_start(self.stack_switcher, False, True, 6)
|
||||
hb = Gtk.HBox()
|
||||
hb.set_border_width(6)
|
||||
self.vMain.pack_start(hb, False, True, 0)
|
||||
self.vMain.reorder_child(hb, 1)
|
||||
|
||||
self.pbFeedUpdate.set_property('vexpand', False)
|
||||
self.vMain.pack_start(self.application.header_bar_refresh_ui, False, False, 0)
|
||||
|
||||
def _on_child_revealed(widget, prop=None):
|
||||
widget.set_visible(widget.get_child_revealed())
|
||||
|
||||
self.header_bar_refresh_ui_revealer.connect('notify::child-revealed', _on_child_revealed)
|
||||
self.application.header_bar_refresh_ui.show_all()
|
||||
_on_child_revealed(self.header_bar_refresh_ui_revealer)
|
||||
|
||||
self.vMain.reorder_child(self.application.header_bar_refresh_ui, 2)
|
||||
|
||||
hb.pack_start(self.application.header_bar_refresh_button, False, False, 0)
|
||||
hb.pack_start(self.stack_switcher, True, True, 6)
|
||||
hb.pack_start(self.application.header_bar_menu_button, False, False, 0)
|
||||
self.stack_switcher.set_property('halign', Gtk.Align.CENTER)
|
||||
self.vMain.reorder_child(self.stack_switcher, 1)
|
||||
self.stack_switcher.show_all()
|
||||
hb.show_all()
|
||||
|
||||
gpodder.user_extensions.on_ui_object_available('gpodder-gtk', self)
|
||||
self.toolbar.set_property('visible', self.config.show_toolbar)
|
||||
|
@ -225,8 +255,6 @@ class gPodder(BuilderWidget, dbus.service.Object):
|
|||
util.run_in_background(self.user_apps_reader.read)
|
||||
|
||||
# Now, update the feed cache, when everything's in place
|
||||
if not self.application.want_headerbar:
|
||||
self.btnUpdateFeeds.show()
|
||||
self.feed_cache_update_cancelled = False
|
||||
self.update_podcast_list_model()
|
||||
|
||||
|
@ -240,6 +268,8 @@ class gPodder(BuilderWidget, dbus.service.Object):
|
|||
if self.config.auto_update_feeds:
|
||||
self.restart_auto_update_timer()
|
||||
|
||||
self._hide_refresh_ui_source_id = None
|
||||
|
||||
# Find expired (old) episodes and delete them
|
||||
old_episodes = list(common.get_expired_episodes(self.channels, self.config))
|
||||
if len(old_episodes) > 0:
|
||||
|
@ -307,6 +337,7 @@ class gPodder(BuilderWidget, dbus.service.Object):
|
|||
|
||||
action_defs = [
|
||||
('update', self.on_itemUpdate_activate),
|
||||
('cancelFeedUpdate', self.on_btnCancelFeedUpdate_clicked),
|
||||
('downloadAllNew', self.on_itemDownloadAllNew_activate),
|
||||
('removeOldEpisodes', self.on_itemRemoveOldEpisodes_activate),
|
||||
('discover', self.on_itemImportChannels_activate),
|
||||
|
@ -336,6 +367,7 @@ class gPodder(BuilderWidget, dbus.service.Object):
|
|||
|
||||
self.update_action = g.lookup_action('update')
|
||||
self.update_channel_action = g.lookup_action('updateChannel')
|
||||
self.cancel_feed_update_action = g.lookup_action('cancelFeedUpdate')
|
||||
self.edit_channel_action = g.lookup_action('editChannel')
|
||||
self.play_action = g.lookup_action('play')
|
||||
self.open_action = g.lookup_action('open')
|
||||
|
@ -345,6 +377,8 @@ class gPodder(BuilderWidget, dbus.service.Object):
|
|||
self.toggle_episode_new_action = g.lookup_action('toggleEpisodeNew')
|
||||
self.toggle_episode_lock_action = g.lookup_action('toggleEpisodeLock')
|
||||
|
||||
self.cancel_feed_update_action.set_enabled(False)
|
||||
|
||||
action = Gio.SimpleAction.new_stateful(
|
||||
'showToolbar', None, GLib.Variant.new_boolean(self.config.show_toolbar))
|
||||
action.connect('activate', self.on_itemShowToolbar_activate)
|
||||
|
@ -2627,20 +2661,35 @@ class gPodder(BuilderWidget, dbus.service.Object):
|
|||
def show_update_feeds_buttons(self):
|
||||
# Make sure that the buttons for updating feeds
|
||||
# appear - this should happen after a feed update
|
||||
self.hboxUpdateFeeds.hide()
|
||||
if not self.application.want_headerbar:
|
||||
self.btnUpdateFeeds.show()
|
||||
self.header_bar_refresh_ui_revealer.set_reveal_child(False)
|
||||
self._make_update_button_update()
|
||||
|
||||
def _make_update_button_update(self):
|
||||
self.cancel_feed_update_action.set_enabled(False)
|
||||
self.application.header_bar_refresh_button.set_icon_name('view-refresh-symbolic')
|
||||
self.application.header_bar_refresh_button.set_action_name('win.update')
|
||||
self.update_action.set_enabled(True)
|
||||
self.update_channel_action.set_enabled(True)
|
||||
|
||||
def on_btnCancelFeedUpdate_clicked(self, widget):
|
||||
def _make_update_button_cancel(self):
|
||||
self.update_action.set_enabled(False)
|
||||
self.update_channel_action.set_enabled(False)
|
||||
self.application.header_bar_refresh_button.set_icon_name('edit-undo-symbolic')
|
||||
self.application.header_bar_refresh_button.set_action_name('win.cancelFeedUpdate')
|
||||
self.cancel_feed_update_action.set_enabled(True)
|
||||
|
||||
def on_btnCancelFeedUpdate_clicked(self, *args):
|
||||
if not self.feed_cache_update_cancelled:
|
||||
self.pbFeedUpdate.set_text(_('Cancelling...'))
|
||||
self.feed_cache_update_cancelled = True
|
||||
self.btnCancelFeedUpdate.set_sensitive(False)
|
||||
else:
|
||||
self.show_update_feeds_buttons()
|
||||
|
||||
def _hide_header_bar_refresh_ui(self):
|
||||
self.header_bar_refresh_ui_revealer.set_reveal_child(False)
|
||||
self._hide_refresh_ui_source_id = None
|
||||
return False
|
||||
|
||||
def update_feed_cache(self, channels=None,
|
||||
show_new_episodes_dialog=True):
|
||||
if self.config.check_connection and not util.connection_available():
|
||||
|
@ -2655,15 +2704,15 @@ class gPodder(BuilderWidget, dbus.service.Object):
|
|||
# Only update podcasts for which updates are enabled
|
||||
channels = [c for c in self.channels if not c.pause_subscription]
|
||||
|
||||
self.update_action.set_enabled(False)
|
||||
self.update_channel_action.set_enabled(False)
|
||||
self._make_update_button_cancel()
|
||||
|
||||
self.feed_cache_update_cancelled = False
|
||||
self.btnCancelFeedUpdate.show()
|
||||
self.btnCancelFeedUpdate.set_sensitive(True)
|
||||
self.btnCancelFeedUpdate.set_image(Gtk.Image.new_from_icon_name('process-stop', Gtk.IconSize.BUTTON))
|
||||
self.hboxUpdateFeeds.show_all()
|
||||
self.btnUpdateFeeds.hide()
|
||||
|
||||
if self._hide_refresh_ui_source_id is not None:
|
||||
GObject.source_remove(self._hide_refresh_ui_source_id)
|
||||
self._hide_refresh_ui_source_id = None
|
||||
|
||||
self.header_bar_refresh_ui_revealer.set_reveal_child(True)
|
||||
|
||||
count = len(channels)
|
||||
text = N_('Updating %(count)d feed...', 'Updating %(count)d feeds...',
|
||||
|
@ -2759,10 +2808,8 @@ class gPodder(BuilderWidget, dbus.service.Object):
|
|||
self.pbFeedUpdate.set_fraction(1.0)
|
||||
self.pbFeedUpdate.set_text(_('No new episodes'))
|
||||
self.feed_cache_update_cancelled = True
|
||||
self.btnCancelFeedUpdate.show()
|
||||
self.btnCancelFeedUpdate.set_sensitive(True)
|
||||
self.update_action.set_enabled(True)
|
||||
self.btnCancelFeedUpdate.set_image(Gtk.Image.new_from_icon_name('edit-clear', Gtk.IconSize.BUTTON))
|
||||
self._hide_refresh_ui_source_id = GObject.timeout_add(3000, self._hide_header_bar_refresh_ui)
|
||||
self._make_update_button_update()
|
||||
else:
|
||||
count = len(episodes)
|
||||
# New episodes are available
|
||||
|
|
Loading…
Reference in New Issue