diff options
author | Christopher Davis <christopherdavis@gnome.org> | 2021-09-26 01:14:46 -0700 |
---|---|---|
committer | Christopher Davis <christopherdavis@gnome.org> | 2021-09-26 01:30:33 -0700 |
commit | 6d004e59caa5e46747a226d277adf61b96fac2e7 (patch) | |
tree | 1e235d36d8dfef90e0756715d25bfccbe3766dd8 | |
parent | e4d74b1f02994423612923552af169b577da345e (diff) | |
download | gnome-maps-wip/cdavis/dark-style-preference.tar.gz |
Use new color scheme APIwip/cdavis/dark-style-preference
Global dark themes are going to be supported in GNOME 42.
Maps already has a setting for "Night Mode", so we want
to switch that to a color scheme selector.
See https://gitlab.gnome.org/Teams/Design/os-mockups/-/blob/master/prefer-dark/prefer-dark.png for design reference.
-rw-r--r-- | data/gnome-maps.css | 41 | ||||
-rw-r--r-- | data/org.gnome.Maps.gschema.xml | 15 | ||||
-rw-r--r-- | data/ui/main-window.ui | 68 | ||||
-rw-r--r-- | src/application.js | 50 | ||||
-rw-r--r-- | src/layersPopover.js | 11 | ||||
-rw-r--r-- | src/mainWindow.js | 19 | ||||
-rw-r--r-- | src/mapView.js | 11 |
7 files changed, 181 insertions, 34 deletions
diff --git a/data/gnome-maps.css b/data/gnome-maps.css index 55e60fb9..aa9bb5dd 100644 --- a/data/gnome-maps.css +++ b/data/gnome-maps.css @@ -110,3 +110,44 @@ -gtk-outline-radius: 14px; } + +/* Adapted from https://gitlab.gnome.org/GNOME/gnome-text-editor/-/blob/bf8c0c249f06a0be69e65aed3b786ba02a9f999e/src/TextEditor.css#L51 */ +radiobutton.theme-selector radio { + -gtk-icon-source: none; + background: none; + box-shadow: none; + padding: 15px; + min-height: 24px; + min-width: 24px; + border-width: 1px; + border-style: solid; + border-color: @borders; +} + +radiobutton.theme-selector radio:checked { + border-width: 3px; + border-color: @theme_selected_bg_color; + margin: -2px; + -gtk-icon-source: -gtk-icontheme("object-select-symbolic"); +} + + +radiobutton.theme-selector.system radio { + color: #2e3436; + background: linear-gradient(135deg, #fff 50%, #2e3436 50%); +} + +radiobutton.theme-selector.system radio:checked { + color: #2e3436; + background: linear-gradient(135deg, #f6f5f4 50%, #c0bfbc 50%); +} + +radiobutton.theme-selector.light radio { + color: #2e3436; + background-color: #fff; +} + +radiobutton.theme-selector.dark radio { + color: #fff; + background-color: #2e3436; +} diff --git a/data/org.gnome.Maps.gschema.xml b/data/org.gnome.Maps.gschema.xml index cc32f780..8efb27bc 100644 --- a/data/org.gnome.Maps.gschema.xml +++ b/data/org.gnome.Maps.gschema.xml @@ -75,15 +75,20 @@ <default>'pedestrian'</default> <summary>Last used transportation type for routing</summary> </key> - <key name="night-mode" type="b"> - <default>false</default> - <summary>Night mode</summary> - <description>Whether the application is in night mode.</description> - </key> <key name="hybrid-aerial" type="b"> <default>false</default> <summary>Use hybrid aerial tiles</summary> <description>Whether aerial tiles should use hybrid style (with labels).</description> </key> + <key name="color-scheme" type="s"> + <choices> + <choice value="default"/> + <choice value="light"/> + <choice value="dark"/> + </choices> + <default>'default'</default> + <summary>Color Scheme</summary> + <description>The color scheme to use for windows.</description> + </key> </schema> </schemalist> diff --git a/data/ui/main-window.ui b/data/ui/main-window.ui index 99e17a11..2890972f 100644 --- a/data/ui/main-window.ui +++ b/data/ui/main-window.ui @@ -14,11 +14,71 @@ <property name="margin-bottom">12</property> <property name="orientation">vertical</property> <child> - <object class="GtkModelButton"> + <object class="GtkBox"> + <property name="visible">True</property> + <property name="can_focus">False</property> + <property name="halign">center</property> + <property name="margin_bottom">12</property> + <property name="orientation">horizontal</property> + <property name="spacing">18</property> + <child> + <object class="GtkRadioButton" id="defaultSelector"> + <property name="visible">True</property> + <property name="action-name">app.set-color-scheme</property> + <property name="action-target">'default'</property> + <property name="tooltip-text" translatable="yes">Use System Colors</property> + <child internal-child="accessible"> + <object class="AtkObject"> + <property name="accessible-name" bind-source="defaultSelector" bind-property="tooltip-text" bind-flags="sync-create"/> + </object> + </child> + <style> + <class name="theme-selector"/> + <class name="system"/> + </style> + </object> + </child> + <child> + <object class="GtkRadioButton" id="lightSelector"> + <property name="visible">True</property> + <property name="group">defaultSelector</property> + <property name="action-name">app.set-color-scheme</property> + <property name="action-target">'light'</property> + <property name="tooltip-text" translatable="yes">Use Light Colors</property> + <child internal-child="accessible"> + <object class="AtkObject"> + <property name="accessible-name" bind-source="lightSelector" bind-property="tooltip-text" bind-flags="sync-create"/> + </object> + </child> + <style> + <class name="theme-selector"/> + <class name="light"/> + </style> + </object> + </child> + <child> + <object class="GtkRadioButton" id="darkSelector"> + <property name="visible">True</property> + <property name="group">defaultSelector</property> + <property name="action-name">app.set-color-scheme</property> + <property name="action-target">'dark'</property> + <property name="tooltip-text" translatable="yes">Use Dark Colors</property> + <child internal-child="accessible"> + <object class="AtkObject"> + <property name="accessible-name" bind-source="darkSelector" bind-property="tooltip-text" bind-flags="sync-create"/> + </object> + </child> + <style> + <class name="theme-selector"/> + <class name="dark"/> + </style> + </object> + </child> + </object> + </child> + <child> + <object class="GtkSeparator"> <property name="visible">True</property> - <property name="xalign">0</property> - <property name="label" translatable="yes">Night Mode</property> - <property name="action-name">app.night-mode</property> </object> </child> <child> diff --git a/src/application.js b/src/application.js index 573bceef..8575f6fc 100644 --- a/src/application.js +++ b/src/application.js @@ -172,6 +172,25 @@ var Application = GObject.registerClass({ } } + _onColorSchemeChange(action, parameter) { + parameter.print(true); + let scheme = parameter.get_string()[0]; + + switch (scheme) { + case 'default': + this._styleManager.set_color_scheme(Hdy.ColorScheme.PREFER_LIGHT); + break; + case 'light': + this._styleManager.set_color_scheme(Hdy.ColorScheme.FORCE_LIGHT); + break; + case 'dark': + this._styleManager.set_color_scheme(Hdy.ColorScheme.FORCE_DARK); + break; + } + + settings.set('color-scheme', scheme); + } + _onOsmAccountSetupActivate() { let dialog = osmEdit.createAccountDialog(this._mainWindow, false); @@ -227,12 +246,6 @@ var Application = GObject.registerClass({ } } - _onNightModeChange(action) { - let state = action.get_state(); - let gtkSettings = Gtk.Settings.get_default(); - gtkSettings.gtk_application_prefer_dark_theme = state.get_boolean(); - } - vfunc_startup() { super.vfunc_startup(); @@ -252,10 +265,9 @@ var Application = GObject.registerClass({ 'osm-account-setup': { onActivate: this._onOsmAccountSetupActivate.bind(this) }, - 'night-mode': { - paramType: 'b', - onChangeState: this._onNightModeChange.bind(this), - setting: 'night-mode' + 'set-color-scheme': { + paramType: 's', + onActivate: this._onColorSchemeChange.bind(this) }, 'quit': { onActivate: () => this.quit(), @@ -263,11 +275,21 @@ var Application = GObject.registerClass({ } }, settings); - // set dark theme when night-mode is enabled - let gtkSettings = Gtk.Settings.get_default(); - gtkSettings.gtk_application_prefer_dark_theme = - settings.get('night-mode'); + this._styleManager = Hdy.StyleManager.get_default(); + + // Set color scheme based on settings + switch (settings.get('color-scheme')) { + case 'default': + this._styleManager.set_color_scheme(Hdy.ColorScheme.PREFER_LIGHT); + break; + case 'light': + this._styleManager.set_color_scheme(Hdy.ColorScheme.FORCE_LIGHT); + break; + case 'dark': + this._styleManager.set_color_scheme(Hdy.ColorScheme.FORCE_DARK); + break; + } Gtk.IconTheme.get_default().append_search_path(GLib.build_filenamev([pkg.pkgdatadir, 'icons'])); diff --git a/src/layersPopover.js b/src/layersPopover.js index 70f25657..d421b71f 100644 --- a/src/layersPopover.js +++ b/src/layersPopover.js @@ -21,6 +21,7 @@ const Champlain = imports.gi.Champlain; const GObject = imports.gi.GObject; const Gtk = imports.gi.Gtk; const Gdk = imports.gi.Gdk; +const Hdy = imports.gi.Handy; const Application = imports.application; const MapSource = imports.mapSource; @@ -144,8 +145,8 @@ var LayersPopover = GObject.registerClass({ this._setLayerPreviews.bind(this)); this._mapView.view.connect("notify::longitude", this._setLayerPreviews.bind(this)); - Application.settings.connect("changed::night-mode", - this._onNightModeChanged.bind(this)); + Hdy.StyleManager.get_default().connect("notify::dark", + this._onDarkChanged.bind(this)); Application.settings.connect("changed::hybrid-aerial", this._onHybridAerialChanged.bind(this)); @@ -160,9 +161,9 @@ var LayersPopover = GObject.registerClass({ }); } - _onNightModeChanged() { + _onDarkChanged() { if (Service.getService().tiles.streetDark && - Application.settings.get('night-mode')) { + Hdy.StyleManager.get_default().dark) { this._setLayerPreviewImage('streetDark', true); } else { this._setLayerPreviewImage('street', true); @@ -180,7 +181,7 @@ var LayersPopover = GObject.registerClass({ _setLayerPreviews() { if (Service.getService().tiles.streetDark && - Application.settings.get('night-mode')) { + Hdy.StyleManager.get_default().dark) { this._setLayerPreviewImage('streetDark'); } else { this._setLayerPreviewImage('street'); diff --git a/src/mainWindow.js b/src/mainWindow.js index 9abceb46..4d9b7205 100644 --- a/src/mainWindow.js +++ b/src/mainWindow.js @@ -86,7 +86,10 @@ var MainWindow = GObject.registerClass({ 'noNetworkView', 'actionBar', 'actionBarRevealer', - 'placeBarContainer' ] + 'placeBarContainer', + 'defaultSelector', + 'lightSelector', + 'darkSelector'] }, class MainWindow extends Gtk.ApplicationWindow { get mapView() { @@ -116,6 +119,7 @@ var MainWindow = GObject.registerClass({ this._initHeaderbar(); this._initSignals(); this._restoreWindowGeometry(); + this._restoreColorSchemeSelectors(); this._initDND(); this._initPlaceBar(); @@ -444,6 +448,19 @@ var MainWindow = GObject.registerClass({ this.maximize(); } + _restoreColorSchemeSelectors() { + switch (Application.settings.get('color-scheme')) { + case 'default': + this._defaultSelector.active = true; + break; + case 'light': + this._lightSelector.active = true; + break; + case 'dark': + this._darkSelector.active = true; + break; + } + } _onConfigureEvent(widget, event) { if (this._configureId !== 0) { Mainloop.source_remove(this._configureId); diff --git a/src/mapView.js b/src/mapView.js index 10e6d5a3..fef736c2 100644 --- a/src/mapView.js +++ b/src/mapView.js @@ -26,6 +26,7 @@ const Geocode = imports.gi.GeocodeGlib; const Gio = imports.gi.Gio; const Gtk = imports.gi.Gtk; const GtkChamplain = imports.gi.GtkChamplain; +const Hdy = imports.gi.Handy; const Mainloop = imports.mainloop; const Application = imports.application; @@ -210,8 +211,8 @@ var MapView = GObject.registerClass({ // if dark tiles is available, setup handler to switch style if (Service.getService().tiles.streetDark) { - Application.settings.connect('changed::night-mode', - this._onNightModeChanged.bind(this)); + Hdy.StyleManager.get_default().connect('notify::dark', + this._onDarkChanged.bind(this)); } // if hybrid aerial tiles are available, setup handler to toggle @@ -272,11 +273,11 @@ var MapView = GObject.registerClass({ this._setBackgroundPatternIfNeeded(); } - _onNightModeChanged() { + _onDarkChanged() { if (this._mapType === MapType.STREET) { let overlay_sources = this.view.get_overlay_sources(); - if (Application.settings.get('night-mode')) + if (Hdy.StyleManager.get_default().dark) this.view.map_source = MapSource.createStreetDarkSource(); else this.view.map_source = MapSource.createStreetSource(); @@ -428,7 +429,7 @@ var MapView = GObject.registerClass({ } } else { if (tiles.streetDark && - Application.settings.get('night-mode')) { + Hdy.StyleManager.get_default().dark) { this.view.map_source = MapSource.createStreetDarkSource(); } else { this.view.map_source = MapSource.createStreetSource(); |