diff --git a/src/client/components/main-window.vala b/src/client/components/main-window.vala index 1b6bfbfa..2cd5e2bc 100644 --- a/src/client/components/main-window.vala +++ b/src/client/components/main-window.vala @@ -8,7 +8,11 @@ [GtkTemplate (ui = "/org/gnome/Geary/main-window.ui")] public class MainWindow : Gtk.ApplicationWindow, Geary.BaseInterface { + + private const int STATUS_BAR_HEIGHT = 18; + private const int UPDATE_UI_INTERVAL = 60; + public new GearyApplication application { get { return (GearyApplication) base.get_application(); } @@ -34,6 +38,10 @@ public class MainWindow : Gtk.ApplicationWindow, Geary.BaseInterface { public StatusBar status_bar { get; private set; default = new StatusBar(); } private MonitoredSpinner spinner = new MonitoredSpinner(); + private Geary.TimeoutManager update_ui_timeout; + private int64 update_ui_last = 0; + + [GtkChild] private Gtk.Box main_layout; [GtkChild] @@ -104,10 +112,16 @@ public class MainWindow : Gtk.ApplicationWindow, Geary.BaseInterface { setup_layout(application.config); on_change_orientation(); + this.update_ui_timeout = new Geary.TimeoutManager.seconds( + UPDATE_UI_INTERVAL, on_update_ui_timeout + ); + this.update_ui_timeout.repetition = FOREVER; + this.main_layout.show_all(); } ~MainWindow() { + this.update_ui_timeout.reset(); base_unref(); } @@ -381,6 +395,24 @@ public class MainWindow : Gtk.ApplicationWindow, Geary.BaseInterface { return base.key_release_event(event); } + private void update_ui() { + // Only update if we haven't done so within the last while + int64 now = GLib.get_monotonic_time() / (1000 * 1000); + if (this.update_ui_last + UPDATE_UI_INTERVAL < now) { + this.update_ui_last = now; + + if (this.conversation_viewer.current_list != null) { + this.conversation_viewer.current_list.update_display(); + } + + ConversationListStore? list_store = + this.conversation_list_view.get_model() as ConversationListStore; + if (list_store != null) { + list_store.update_display(); + } + } + } + private void on_conversation_monitor_changed() { ConversationListStore? old_model = this.conversation_list_view.get_model(); if (old_model != null) { @@ -542,6 +574,17 @@ public class MainWindow : Gtk.ApplicationWindow, Geary.BaseInterface { return service; } + [GtkCallback] + private void on_map() { + this.update_ui_timeout.start(); + update_ui(); + } + + [GtkCallback] + private void on_unmap() { + this.update_ui_timeout.reset(); + } + [GtkCallback] private bool on_focus_event() { on_shift_key(false); @@ -608,4 +651,8 @@ public class MainWindow : Gtk.ApplicationWindow, Geary.BaseInterface { update_infobar_frame(); } + private void on_update_ui_timeout() { + update_ui(); + } + } diff --git a/src/client/conversation-list/conversation-list-store.vala b/src/client/conversation-list/conversation-list-store.vala index cbf11b88..43ad6b46 100644 --- a/src/client/conversation-list/conversation-list-store.vala +++ b/src/client/conversation-list/conversation-list-store.vala @@ -97,7 +97,6 @@ public class ConversationListStore : Gtk.ListStore { private Cancellable cancellable = new Cancellable(); private bool loading_local_only = true; private Geary.Nonblocking.Mutex refresh_mutex = new Geary.Nonblocking.Mutex(); - private uint update_id = 0; public signal void conversations_added(bool start); public signal void conversations_removed(bool start); @@ -108,9 +107,6 @@ public class ConversationListStore : Gtk.ListStore { set_sort_column_id(Gtk.SortColumn.DEFAULT, Gtk.SortType.DESCENDING); this.conversations = conversations; - this.update_id = Timeout.add_seconds_full( - Priority.LOW, 60, update_date_strings - ); this.email_store = new Geary.App.EmailStore( conversations.base_folder.account ); @@ -135,10 +131,10 @@ public class ConversationListStore : Gtk.ListStore { // Release circular refs. this.row_map.clear(); - if (this.update_id != 0) { - Source.remove(this.update_id); - this.update_id = 0; - } + } + + public void update_display() { + this.foreach(update_date_string); } public Geary.App.Conversation? get_conversation_at_path(Gtk.TreePath path) { @@ -479,11 +475,6 @@ public class ConversationListStore : Gtk.ListStore { refresh_previews_async.begin(this.conversations); } - private bool update_date_strings() { - this.foreach(update_date_string); - return Source.CONTINUE; - } - private bool update_date_string(Gtk.TreeModel model, Gtk.TreePath path, Gtk.TreeIter iter) { FormattedConversationData? message_data; model.get(iter, Column.CONVERSATION_DATA, out message_data); @@ -496,4 +487,3 @@ public class ConversationListStore : Gtk.ListStore { } } - diff --git a/src/client/conversation-viewer/conversation-list-box.vala b/src/client/conversation-viewer/conversation-list-box.vala index a4250f39..781ada34 100644 --- a/src/client/conversation-viewer/conversation-list-box.vala +++ b/src/client/conversation-viewer/conversation-list-box.vala @@ -782,6 +782,16 @@ public class ConversationListBox : Gtk.ListBox, Geary.BaseInterface { }); } + /** + * Updates the displayed date for each conversation row. + */ + public void update_display() { + message_view_iterator().foreach((msg_view) => { + msg_view.update_display(); + return true; + }); + } + /** Returns the email row for the given id, if any. */ internal EmailRow? get_email_row_by_id(Geary.EmailIdentifier id) { return this.email_rows.get(id); diff --git a/src/client/conversation-viewer/conversation-message.vala b/src/client/conversation-viewer/conversation-message.vala index 945c2cea..35bc4779 100644 --- a/src/client/conversation-viewer/conversation-message.vala +++ b/src/client/conversation-viewer/conversation-message.vala @@ -158,8 +158,12 @@ public class ConversationMessage : Gtk.Grid, Geary.BaseInterface { /** HTML view that displays the message body. */ internal ConversationWebView web_view { get; private set; } + private Configuration config; + private Geary.RFC822.MailboxAddress? primary_originator; + private GLib.DateTime? local_date = null; + [GtkChild] private Gtk.Image avatar; @@ -345,6 +349,7 @@ public class ConversationMessage : Gtk.Grid, Geary.BaseInterface { base_ref(); this.is_loading_images = load_remote_images; this.primary_originator = primary_originator; + this.config = config; // Actions @@ -387,6 +392,9 @@ public class ConversationMessage : Gtk.Grid, Geary.BaseInterface { (MenuModel) builder.get_object("context_menu_inspector"); } + this.local_date = date.value.to_local(); + update_display(); + // Compact headers // Translators: This is displayed in place of the from address @@ -396,20 +404,6 @@ public class ConversationMessage : Gtk.Grid, Geary.BaseInterface { this.compact_from.set_text(format_originator_compact(from, empty_from)); this.compact_from.get_style_context().add_class(FROM_CLASS); - string date_text = ""; - string date_tooltip = ""; - if (date != null) { - GLib.DateTime local_date = date.value.to_local(); - date_text = Util.Date.pretty_print( - local_date, config.clock_format - ); - date_tooltip = Util.Date.pretty_print_verbose( - local_date, config.clock_format - ); - } - this.compact_date.set_text(date_text); - this.compact_date.set_tooltip_text(date_tooltip); - if (preview != null) { string clean_preview = preview; if (preview.length > MAX_PREVIEW_BYTES) { @@ -427,8 +421,6 @@ public class ConversationMessage : Gtk.Grid, Geary.BaseInterface { fill_originator_addresses(from, reply_to, sender, empty_from); - this.date.set_text(date_text); - this.date.set_tooltip_text(date_tooltip); if (subject != null) { this.subject.set_text(subject.value); this.subject.set_visible(true); @@ -706,6 +698,28 @@ public class ConversationMessage : Gtk.Grid, Geary.BaseInterface { this.web_view.unmark_search_terms(); } + /** + * Updates the displayed date for each conversation row. + */ + public void update_display() { + string date_text = ""; + string date_tooltip = ""; + if (this.local_date != null) { + date_text = Util.Date.pretty_print( + this.local_date, this.config.clock_format + ); + date_tooltip = Util.Date.pretty_print_verbose( + this.local_date, this.config.clock_format + ); + } + + this.compact_date.set_text(date_text); + this.compact_date.set_tooltip_text(date_tooltip); + + this.date.set_text(date_text); + this.date.set_tooltip_text(date_tooltip); + } + private SimpleAction add_action(string name, bool enabled, VariantType? type = null) { SimpleAction action = new SimpleAction(name, type); action.set_enabled(enabled); diff --git a/ui/main-window.ui b/ui/main-window.ui index 7a1b0210..428f40f7 100644 --- a/ui/main-window.ui +++ b/ui/main-window.ui @@ -9,6 +9,8 @@ False + +