diff --git a/data/dbus-interfaces/org.gnome.Shell.ClocksIntegration.xml b/data/dbus-interfaces/org.gnome.Shell.ClocksIntegration.xml
new file mode 100644
index 000000000..0cbb132c1
--- /dev/null
+++ b/data/dbus-interfaces/org.gnome.Shell.ClocksIntegration.xml
@@ -0,0 +1,15 @@
+
+
+
+
+
+
+
+
+
diff --git a/data/gnome-shell-dbus-interfaces.gresource.xml b/data/gnome-shell-dbus-interfaces.gresource.xml
index 21fdfa949..db3ef4ac2 100644
--- a/data/gnome-shell-dbus-interfaces.gresource.xml
+++ b/data/gnome-shell-dbus-interfaces.gresource.xml
@@ -40,6 +40,7 @@
org.gnome.SettingsDaemon.Wacom.xml
org.gnome.Shell.AudioDeviceSelection.xml
org.gnome.Shell.CalendarServer.xml
+ org.gnome.Shell.ClocksIntegration.xml
org.gnome.Shell.Extensions.xml
org.gnome.Shell.Introspect.xml
org.gnome.Shell.HotplugSniffer.xml
diff --git a/data/org.gnome.shell.gschema.xml.in b/data/org.gnome.shell.gschema.xml.in
index d5f327183..99221a7dd 100644
--- a/data/org.gnome.shell.gschema.xml.in
+++ b/data/org.gnome.shell.gschema.xml.in
@@ -228,6 +228,17 @@
+
+
+ Locations
+
+ The locations to show in world clocks
+
+ []
+
+
+
diff --git a/js/ui/dateMenu.js b/js/ui/dateMenu.js
index ab137edf4..c78b39c6b 100644
--- a/js/ui/dateMenu.js
+++ b/js/ui/dateMenu.js
@@ -1,7 +1,7 @@
// -*- mode: js; js-indent-level: 4; indent-tabs-mode: nil -*-
/* exported DateMenuButton */
-const { Clutter, GLib, GnomeDesktop,
+const { Clutter, Gio, GLib, GnomeDesktop,
GObject, GWeather, Shell, St } = imports.gi;
const Util = imports.misc.util;
@@ -11,8 +11,13 @@ const Calendar = imports.ui.calendar;
const Weather = imports.misc.weather;
const System = imports.system;
+const { loadInterfaceXML } = imports.misc.fileUtils;
+
const MAX_FORECASTS = 5;
+const ClocksIntegrationIface = loadInterfaceXML('org.gnome.Shell.ClocksIntegration');
+const ClocksProxy = Gio.DBusProxy.makeProxyWrapper(ClocksIntegrationIface);
+
function _isToday(date) {
let now = new Date();
return now.getYear() == date.getYear() &&
@@ -83,7 +88,8 @@ var WorldClocksSection = class WorldClocksSection {
x_fill: true,
can_focus: true });
this.actor.connect('clicked', () => {
- this._clockAppMon.activateApp();
+ if (this._clocksApp)
+ this._clocksApp.activate();
Main.overview.hide();
Main.panel.closeCalendar();
@@ -96,29 +102,40 @@ var WorldClocksSection = class WorldClocksSection {
this.actor.child = this._grid;
- this._clockAppMon = new Util.AppSettingsMonitor('org.gnome.clocks.desktop',
- 'org.gnome.clocks');
- this._clockAppMon.connect('available-changed',
- this._sync.bind(this));
- this._clockAppMon.watchSetting('world-clocks',
- this._clocksChanged.bind(this));
+ this._clocksApp = null;
+ this._clocksProxy = new ClocksProxy(
+ Gio.DBus.session,
+ 'org.gnome.clocks',
+ '/org/gnome/clocks',
+ this._onProxyReady.bind(this),
+ null /* cancellable */,
+ Gio.DBusProxyFlags.DO_NOT_AUTO_START | Gio.DBusProxyFlags.GET_INVALIDATED_PROPERTIES);
+
+ this._settings = new Gio.Settings({
+ schema_id: 'org.gnome.shell.world-clocks'
+ });
+ this._settings.connect('changed', this._clocksChanged.bind(this));
+ this._clocksChanged();
+
+ this._appSystem = Shell.AppSystem.get_default();
+ this._appSystem.connect('installed-changed',
+ this._sync.bind(this));
this._sync();
}
_sync() {
- this.actor.visible = this._clockAppMon.available;
+ this._clocksApp = this._appSystem.lookup_app('org.gnome.clocks.desktop');
+ this.actor.visible = this._clocksApp != null;
}
- _clocksChanged(settings) {
+ _clocksChanged() {
this._grid.destroy_all_children();
this._locations = [];
let world = GWeather.Location.get_world();
- let clocks = settings.get_value('world-clocks').deep_unpack();
+ let clocks = this._settings.get_value('locations').deep_unpack();
for (let i = 0; i < clocks.length; i++) {
- if (!clocks[i].location)
- continue;
- let l = world.deserialize(clocks[i].location);
+ let l = world.deserialize(clocks[i]);
if (l && l.get_timezone() != null)
this._locations.push({ location: l });
}
@@ -197,6 +214,25 @@ var WorldClocksSection = class WorldClocksSection {
l.actor.text = Util.formatTime(now, { timeOnly: true });
}
}
+
+ _onProxyReady(proxy, error) {
+ if (error) {
+ log(`Failed to create GNOME Clocks proxy: ${error}`);
+ return;
+ }
+
+ this._clocksProxy.connect('g-properties-changed',
+ this._onClocksPropertiesChanged.bind(this));
+ this._onClocksPropertiesChanged();
+ }
+
+ _onClocksPropertiesChanged() {
+ if (this._clocksProxy.g_name_owner == null)
+ return;
+
+ this._settings.set_value('locations',
+ new GLib.Variant('av', this._clocksProxy.Locations));
+ }
};
var WeatherSection = class WeatherSection {