[gnome-clocks/zbrown/world-clocks: 1/4] world: new list based design



commit 191ecb08857e8b60ea028e54f7db8350c7ca967d
Author: Zander Brown <zbrown gnome org>
Date:   Sun Jan 26 23:29:43 2020 +0000

    world: new list based design
    
    Doesn't yet implement the colour coding
    
    Breaks styling of Alarms but that's going away anyway

 data/css/gnome-clocks.css              |  45 +++++------
 data/css/gnome-clocks.highcontrast.css |  33 ++------
 data/gnome-clocks.gresource.xml        |   2 -
 data/gtk/help-overlay.ui               |   7 --
 data/images/day.png                    | Bin 60927 -> 0 bytes
 data/images/night.png                  | Bin 18479 -> 0 bytes
 data/ui/world.ui                       |  33 +++++++-
 data/ui/worldtile.ui                   | 137 +++++++++++++++++++++------------
 meson.build                            |   6 +-
 src/utils.vala                         |   9 ---
 src/world.vala                         | 121 ++++++++++++++++++-----------
 subprojects/libhandy                   |   1 +
 12 files changed, 226 insertions(+), 168 deletions(-)
---
diff --git a/data/css/gnome-clocks.css b/data/css/gnome-clocks.css
index f7ee8b5..f7281d9 100644
--- a/data/css/gnome-clocks.css
+++ b/data/css/gnome-clocks.css
@@ -32,32 +32,6 @@ label.destructive-action {
     padding-right: 8px;
 }
 
-/* world */
-
-.world-tile .stripe,
-.world-tile .stripe:backdrop {
-    color: black;
-    background-color: rgba(255, 255, 255, 0.4);
-}
-
-.tile.prelight .world-tile .stripe,
-.tile.prelight .world-tile .stripe:backdrop {
-    text-shadow: 0 2px 2px rgba(0, 0, 0, 0.3);
-    background-color: rgba(255, 255, 255, 0.6);
-}
-
-.night .world-tile .stripe,
-.night .world-tile .stripe:backdrop {
-    color: white;
-    background-color: rgba(0, 0, 0, 0.4);
-}
-
-.tile.prelight .night .world-tile .stripe,
-.tile.prelight .night .world-tile .stripe:backdrop {
-    text-shadow: 0 0 0.1em rgba(255, 255, 255, 0.6), 0 0 0.2em rgba(255, 255, 255, 0.6);
-    background-color: rgba(0, 0, 0, 0.8);
-}
-
 /* alarms */
 
 row.snoozing {
@@ -277,3 +251,22 @@ spinbutton.clocks-timer-label button {
     -gtk-outline-radius: 9999px;
 }
 
+/* World */
+
+.clock-title {
+    font-size: 1.1em;
+}
+
+.clock-desc {
+    font-size: 0.9em;
+}
+
+.clock-time {
+    font-size: 2em;
+    padding: 0.2em 0.5em;
+    border-radius: 1em;
+    background: #e5a50a;
+    color: #000000;
+    font-weight: lighter;
+}
+
diff --git a/data/css/gnome-clocks.highcontrast.css b/data/css/gnome-clocks.highcontrast.css
index 40dd6c2..3f9fc2d 100644
--- a/data/css/gnome-clocks.highcontrast.css
+++ b/data/css/gnome-clocks.highcontrast.css
@@ -12,31 +12,6 @@ label.destructive-action {
     color: #e01b24;
 }
 
-/* world */
-
-.world-tile image,
-.world-tile image:backdrop {
-    border: 2px solid rgb(141, 141, 141);
-}
-
-.world-tile .stripe,
-.world-tile .stripe:backdrop,
-.tile.prelight .world-tile .stripe,
-.tile.prelight .world-tile .stripe:backdrop {
-    color: black;
-    text-shadow: none;
-    background-color: white;
-}
-
-.night .world-tile .stripe,
-.night .world-tile .stripe:backdrop,
-.tile.prelight .night .world-tile .stripe,
-.tile.prelight .night .world-tile .stripe:backdrop {
-    color: white;
-    text-shadow: none;
-    background-color: black;
-}
-
 /* alarms */
 
 row.snoozing {
@@ -73,3 +48,11 @@ row.snoozing {
     background-image: none;
     background-color: @warning_color;
 }
+
+/* World */
+
+.clock-time {
+    background: transparent;
+    color: #000000;
+    font-weight: normal;
+}
diff --git a/data/gnome-clocks.gresource.xml b/data/gnome-clocks.gresource.xml
index 30461ed..83fab71 100644
--- a/data/gnome-clocks.gresource.xml
+++ b/data/gnome-clocks.gresource.xml
@@ -3,8 +3,6 @@
   <gresource prefix="/org/gnome/clocks">
     <file>css/gnome-clocks.css</file>
     <file>css/gnome-clocks.highcontrast.css</file>
-    <file>images/day.png</file>
-    <file>images/night.png</file>
     <file preprocess="xml-stripblanks">gtk/menus.ui</file>
     <file preprocess="xml-stripblanks">gtk/help-overlay.ui</file>
     <file preprocess="xml-stripblanks">ui/window.ui</file>
diff --git a/data/gtk/help-overlay.ui b/data/gtk/help-overlay.ui
index f93eed3..c779f38 100644
--- a/data/gtk/help-overlay.ui
+++ b/data/gtk/help-overlay.ui
@@ -68,13 +68,6 @@
                 <property name="title" translatable="yes" context="shortcut window">Add a world 
clock</property>
               </object>
             </child>
-            <child>
-              <object class="GtkShortcutsShortcut">
-                <property name="visible">1</property>
-                <property name="accelerator">&lt;ctrl&gt;A</property>
-                <property name="title" translatable="yes" context="shortcut window">Select all world 
clocks</property>
-              </object>
-            </child>
           </object>
         </child>
         <child>
diff --git a/data/ui/world.ui b/data/ui/world.ui
index 5a24dcb..0b6ece6 100644
--- a/data/ui/world.ui
+++ b/data/ui/world.ui
@@ -5,7 +5,6 @@
     <property name="visible">True</property>
     <property name="can_focus">False</property>
     <property name="homogeneous">False</property>
-    <property name="n-selected" bind-source="content_view" bind-property="n-selected" 
bind-flags="sync-create" />
     <signal name="notify::visible-child" handler="visible_child_changed" swapped="no"/>
     <child>
       <object class="GtkGrid" id="empty_view">
@@ -45,10 +44,27 @@
       </object>
     </child>
     <child>
-      <object class="ClocksContentView" id="content_view">
+      <object class="GtkScrolledWindow" id="list_view">
         <property name="visible">True</property>
-        <property name="mode" bind-source="ClocksWorldFace" bind-property="view-mode" 
bind-flags="sync-create|bidirectional" />
-        <signal name="item-activated" handler="item_activated" swapped="no"/>
+        <child>
+          <object class="HdyColumn">
+            <property name="visible">True</property>
+            <property name="maximum-width">600</property>
+            <child>
+              <object class="GtkListBox" id="listbox">
+                <property name="visible">True</property>
+                <property name="margin">12</property>
+                <property name="valign">start</property>
+                <property name="selection-mode">none</property>
+                <signal name="row-activated" handler="item_activated" swapped="no"/>
+                <style>
+                  <class name="frame"/>
+                  <class name="clock-list"/>
+                </style>
+              </object>
+            </child>
+          </object>
+        </child>
       </object>
     </child>
     <child>
@@ -83,6 +99,9 @@
                 <property name="can_focus">False</property>
                 <property name="justify">center</property>
                 <property name="wrap">True</property>
+                <attributes>
+                  <attribute name="font-features" value="tnum=1"/>
+                </attributes>
                 <style>
                   <class name="clocks-standalone-label"/>
                 </style>
@@ -154,6 +173,9 @@
                 <property name="visible">True</property>
                 <property name="can_focus">False</property>
                 <property name="label">label</property>
+                <attributes>
+                  <attribute name="font-features" value="tnum=1"/>
+                </attributes>
               </object>
               <packing>
                 <property name="left_attach">1</property>
@@ -164,6 +186,9 @@
               <object class="GtkLabel" id="standalone_sunset_label">
                 <property name="visible">True</property>
                 <property name="can_focus">False</property>
+                <attributes>
+                  <attribute name="font-features" value="tnum=1"/>
+                </attributes>
               </object>
               <packing>
                 <property name="left_attach">1</property>
diff --git a/data/ui/worldtile.ui b/data/ui/worldtile.ui
index 3edce09..9ddae59 100644
--- a/data/ui/worldtile.ui
+++ b/data/ui/worldtile.ui
@@ -1,88 +1,129 @@
 <?xml version="1.0" encoding="UTF-8"?>
+<!-- Generated with glade 3.22.1 -->
 <interface>
-  <template class="ClocksWorldTile" parent="GtkGrid">
+  <requires lib="gtk+" version="3.20"/>
+  <template class="ClocksWorldTile" parent="GtkListBoxRow">
     <property name="visible">True</property>
     <property name="can_focus">False</property>
-    <property name="halign">start</property>
-    <property name="valign">start</property>
     <child>
-      <object class="GtkOverlay" id="tile_overlay">
+      <object class="GtkGrid">
+        <property name="visible">True</property>
         <property name="can_focus">False</property>
+        <property name="valign">start</property>
+        <property name="margin_left">12</property>
+        <property name="margin_right">12</property>
+        <property name="margin_top">12</property>
+        <property name="margin_bottom">12</property>
+        <property name="hexpand">True</property>
+        <property name="row_spacing">6</property>
+        <property name="column_spacing">12</property>
         <child>
-          <object class="GtkImage" id="image">
-            <property name="width_request">256</property>
-            <property name="height_request">256</property>
-            <property name="visible">True</property>
-            <property name="can_focus">False</property>
-          </object>
-        </child>
-        <child type="overlay">
-          <object class="GtkLabel" id="time_label">
-            <property name="width_request">256</property>
-            <property name="height_request">128</property>
+          <object class="GtkLabel" id="name_label">
             <property name="visible">True</property>
             <property name="can_focus">False</property>
-            <property name="halign">center</property>
-            <property name="valign">center</property>
-            <property name="use-markup">True</property>
-            <property name="justify">center</property>
+            <property name="hexpand">True</property>
+            <property name="label" translatable="yes">label</property>
+            <property name="ellipsize">end</property>
+            <property name="xalign">0</property>
+            <property name="yalign">1</property>
             <style>
-              <class name="stripe"/>
-              <class name="tile-label"/>
+              <class name="clock-title"/>
             </style>
           </object>
+          <packing>
+            <property name="left_attach">0</property>
+            <property name="top_attach">0</property>
+          </packing>
         </child>
-        <style>
-          <class name="world-tile"/>
-        </style>
-      </object>
-    </child>
-    <child>
-      <object class="GtkGrid">
-        <property name="visible">True</property>
-        <property name="can_focus">False</property>
-        <property name="halign">center</property>
         <child>
-          <object class="GtkImage" id="name_icon">
-            <property name="icon_name">find-location-symbolic</property>
-            <property name="pixel_size">16</property>
-            <property name="visible">False</property>
-            <property name="no_show_all">True</property>
+          <object class="GtkLabel" id="desc">
+            <property name="visible">True</property>
             <property name="can_focus">False</property>
-            <property name="halign">center</property>
-            <property name="valign">center</property>
+            <property name="hexpand">True</property>
+            <property name="label" translatable="yes">label</property>
+            <property name="ellipsize">end</property>
+            <property name="xalign">0</property>
+            <property name="yalign">0</property>
             <style>
               <class name="dim-label"/>
-              <class name="name-icon"/>
+              <class name="clock-desc"/>
             </style>
           </object>
           <packing>
             <property name="left_attach">0</property>
-            <property name="top_attach">0</property>
+            <property name="top_attach">1</property>
           </packing>
         </child>
         <child>
-          <object class="GtkLabel" id="name_label">
+          <object class="GtkLabel" id="time_label">
             <property name="visible">True</property>
             <property name="can_focus">False</property>
             <property name="halign">center</property>
             <property name="valign">center</property>
-            <property name="wrap">True</property>
-            <property name="max-width-chars">30</property>
+            <property name="label" translatable="yes">12:34</property>
+            <property name="use_markup">True</property>
+            <property name="ellipsize">end</property>
+            <attributes>
+              <attribute name="font-features" value="tnum=1"/>
+            </attributes>
             <style>
-              <class name="name-label"/>
+              <class name="clock-time"/>
             </style>
           </object>
           <packing>
             <property name="left_attach">1</property>
             <property name="top_attach">0</property>
+            <property name="height">2</property>
+          </packing>
+        </child>
+        <child>
+          <object class="GtkStack" id="delete_stack">
+            <property name="visible">True</property>
+            <property name="can_focus">False</property>
+            <child>
+              <object class="GtkButton" id="delete_button">
+                <property name="visible">True</property>
+                <property name="can_focus">True</property>
+                <property name="receives_default">True</property>
+                <property name="halign">center</property>
+                <property name="valign">center</property>
+                <property name="relief">none</property>
+                <signal name="clicked" handler="delete" object="ClocksWorldTile" swapped="no"/>
+                <child>
+                  <object class="GtkImage">
+                    <property name="visible">True</property>
+                    <property name="can_focus">False</property>
+                    <property name="icon_name">edit-delete-symbolic</property>
+                  </object>
+                </child>
+              </object>
+              <packing>
+                <property name="name">page0</property>
+                <property name="title" translatable="yes">page0</property>
+              </packing>
+            </child>
+            <child>
+              <object class="GtkLabel" id="delete_empty">
+                <property name="visible">True</property>
+                <property name="can_focus">False</property>
+              </object>
+              <packing>
+                <property name="name">page1</property>
+                <property name="title" translatable="yes">page1</property>
+                <property name="position">1</property>
+              </packing>
+            </child>
+          </object>
+          <packing>
+            <property name="left_attach">2</property>
+            <property name="top_attach">0</property>
+            <property name="height">2</property>
           </packing>
         </child>
       </object>
-      <packing>
-        <property name="left_attach">0</property>
-        <property name="top_attach">1</property>
-      </packing>
     </child>
+    <style>
+      <class name="clock"/>
+    </style>
   </template>
 </interface>
diff --git a/meson.build b/meson.build
index a449a87..4b23df8 100644
--- a/meson.build
+++ b/meson.build
@@ -10,9 +10,9 @@ gnome = import('gnome')
 i18n = import('i18n')
 python3 = import('python3')
 
-glib = dependency('glib-2.0', version: '>=2.44')
-gio = dependency('gio-2.0', version: '>=2.44')
-gobject = dependency('gobject-2.0', version: '>=2.44')
+glib = dependency('glib-2.0', version: '>= 2.58')
+gio = dependency('gio-2.0', version: '>= 2.58')
+gobject = dependency('gobject-2.0', version: '>= 2.58')
 gtk = dependency('gtk+-3.0', version: '>=3.20')
 gsound = dependency('gsound', version: '>=0.98')
 gweather = dependency('gweather-3.0', version: '>=3.32.0')
diff --git a/src/utils.vala b/src/utils.vala
index d71ba78..db66e54 100644
--- a/src/utils.vala
+++ b/src/utils.vala
@@ -47,15 +47,6 @@ public void load_theme_css (string theme_name) {
     load_css ("gnome-clocks." + theme_name.down (), false);
 }
 
-public Gdk.Pixbuf? load_image (string image) {
-    try {
-        return new Gdk.Pixbuf.from_resource ("/org/gnome/clocks/images/" + image);
-    } catch (Error e) {
-        warning ("loading image file: %s", e.message);
-    }
-    return null;
-}
-
 public void time_to_hms (double t, out int h, out int m, out int s, out double remainder) {
     h = (int) t / 3600;
     t = t % 3600;
diff --git a/src/world.vala b/src/world.vala
index f2b9249..9465c16 100644
--- a/src/world.vala
+++ b/src/world.vala
@@ -72,8 +72,7 @@ public class Item : Object, ContentItem {
 
     public bool automatic { get; set; default = false; }
 
-    public bool selectable { get; set; default = true; }
-
+    public bool selectable { get; set; default = false; }
     public bool selected { get; set; default = false; }
 
     public string name {
@@ -194,6 +193,12 @@ public class Item : Object, ContentItem {
         }
     }
 
+    public TimeSpan local_offset {
+        get {
+            return local_time.get_utc_offset () - date_time.get_utc_offset ();
+        }
+    }
+
     private string _name;
     private GLib.TimeZone time_zone;
     private GLib.DateTime local_time;
@@ -248,26 +253,28 @@ public class Item : Object, ContentItem {
 }
 
 [GtkTemplate (ui = "/org/gnome/clocks/ui/worldtile.ui")]
-private class Tile : Gtk.Grid {
-    private static Gdk.Pixbuf? day_pixbuf = Utils.load_image ("day.png");
-    private static Gdk.Pixbuf? night_pixbuf = Utils.load_image ("night.png");
-
+private class Tile : Gtk.ListBoxRow {
     public Item location { get; construct set; }
 
-    [GtkChild]
-    private Gtk.Image image;
     [GtkChild]
     private Gtk.Label time_label;
     [GtkChild]
-    private Gtk.Widget name_icon;
-    [GtkChild]
     private Gtk.Widget name_label;
+    [GtkChild]
+    private Gtk.Label desc;
+    [GtkChild]
+    private Gtk.Stack delete_stack;
+    [GtkChild]
+    private Gtk.Widget delete_button;
+    [GtkChild]
+    private Gtk.Widget delete_empty;
+
+    internal signal void remove_clock ();
 
     public Tile (Item location) {
         Object (location: location);
 
-        location.bind_property ("automatic", name_icon, "visible", BindingFlags.DEFAULT | 
BindingFlags.SYNC_CREATE);
-        location.bind_property ("name", name_label, "label", BindingFlags.DEFAULT | 
BindingFlags.SYNC_CREATE);
+        location.bind_property ("city-name", name_label, "label", BindingFlags.DEFAULT | 
BindingFlags.SYNC_CREATE);
         location.tick.connect (update);
 
         update ();
@@ -276,17 +283,52 @@ private class Tile : Gtk.Grid {
     private void update () {
         if (location.is_daytime) {
             get_style_context ().remove_class ("night");
-            image.pixbuf = day_pixbuf;
         } else {
             get_style_context ().add_class ("night");
-            image.pixbuf = night_pixbuf;
+        }
+
+        var diff = ((double) location.local_offset / (double) TimeSpan.HOUR);
+        var diff_string = "%.0f".printf (diff.abs ());
+
+        if (diff != Math.round (diff)) {
+            diff_string = "%.1f".printf (diff.abs ());
+        }
+
+        // Translators: The time is the same as the local time
+        var message = _("Equal");
+
+        if (diff > 0) {
+            // Translators: The (possibly fractical) number hours in the past
+            // (relative to local) the clock/location is
+            message = ngettext ("%s hour earlier",
+                                "%s hours earlier",
+                                ((int) diff).abs ()).printf (diff_string);
+        } else if (diff < 0) {
+            // Translators: The (possibly fractical) number hours in the
+            // future (relative to local) the clock/location is
+            message = ngettext ("%s hour later",
+                                "%s hours later",
+                                ((int) diff).abs ()).printf (diff_string);
         }
 
         if (location.day_label != null && location.day_label != "") {
-            time_label.label = "%s\n<span size='xx-small'>%s</span>".printf (location.time_label, 
location.day_label);
+            desc.label = "%s • %s".printf(location.day_label, message);
+            delete_stack.visible_child = delete_button;
+        } else if (location.automatic) {
+            // Translators: This clock represents the local time
+            desc.label = _("Current location");
+            delete_stack.visible_child = delete_empty;
         } else {
-            time_label.label = location.time_label;
+            desc.label = "%s".printf(message);
+            delete_stack.visible_child = delete_button;
         }
+
+        time_label.label = location.time_label;
+    }
+
+    [GtkCallback]
+    private void delete () {
+        remove_clock ();
     }
 }
 
@@ -341,7 +383,7 @@ public class Face : Gtk.Stack, Clocks.Clock {
     public PanelId panel_id { get; construct set; }
     public ButtonMode button_mode { get; set; default = NEW; }
     public ViewMode view_mode { get; set; default = NORMAL; }
-    public bool can_select { get; set; default = true; }
+    public bool can_select { get; set; default = false; }
     public bool n_selected { get; set; }
     public string title { get; set; default = _("Clocks"); }
     public string subtitle { get; set; }
@@ -354,7 +396,9 @@ public class Face : Gtk.Stack, Clocks.Clock {
     [GtkChild]
     private Gtk.Widget empty_view;
     [GtkChild]
-    private ContentView content_view;
+    private Gtk.ScrolledWindow list_view;
+    [GtkChild]
+    private Gtk.ListBox listbox;
     [GtkChild]
     private Gtk.Widget standalone;
     [GtkChild]
@@ -383,8 +427,14 @@ public class Face : Gtk.Stack, Clocks.Clock {
             return 0;
         });
 
-        content_view.bind_model (locations, (item) => {
-            return new Tile ((Item)item);
+        listbox.set_header_func ((Gtk.ListBoxUpdateHeaderFunc) Hdy.list_box_separator_header);
+
+        listbox.bind_model (locations, (item) => {
+            var tile = new Tile ((Item) item);
+
+            tile.remove_clock.connect (() => locations.delete_item ((Item) item));
+
+            return tile;
         });
 
         load ();
@@ -408,28 +458,27 @@ public class Face : Gtk.Stack, Clocks.Clock {
             locations.foreach ((l) => {
                 ((Item)l).tick ();
             });
-            content_view.queue_draw ();
+            // TODO Only need to queue what changed
+            listbox.queue_draw ();
             update_standalone ();
         });
     }
 
     [GtkCallback]
-    private void item_activated (ContentItem item) {
-        show_standalone ((Item) item);
+    private void item_activated (Gtk.ListBox list, Gtk.ListBoxRow row) {
+        show_standalone ((row as Tile).location);
     }
 
     [GtkCallback]
     private void visible_child_changed () {
-        if (visible_child == empty_view || visible_child == content_view) {
+        if (visible_child == empty_view || visible_child == list_view) {
             view_mode = NORMAL;
             button_mode = NEW;
-            can_select = true;
             title = _("Clocks");
             subtitle = null;
         } else if (visible_child == standalone) {
             view_mode = STANDALONE;
             button_mode = BACK;
-            can_select = false;
         }
     }
 
@@ -476,7 +525,6 @@ public class Face : Gtk.Stack, Clocks.Clock {
 
             item = new Item (found_location);
             item.automatic = true;
-            item.selectable = false;
             locations.add (item);
         });
 
@@ -525,21 +573,6 @@ public class Face : Gtk.Stack, Clocks.Clock {
         reset_view ();
     }
 
-    public void activate_select () {
-        view_mode = SELECTION;
-    }
-
-    public void activate_select_cancel () {
-        view_mode = NORMAL;
-    }
-
-    public void activate_select_all () {
-        content_view.select_all ();
-    }
-
-    public void activate_select_none () {
-        content_view.unselect_all ();
-    }
 
     public bool escape_pressed () {
         if (visible_child == standalone) {
@@ -547,12 +580,12 @@ public class Face : Gtk.Stack, Clocks.Clock {
             return true;
         }
 
-        return content_view.escape_pressed ();
+        return false;
     }
 
     public void reset_view () {
         standalone_location = null;
-        visible_child = locations.get_n_items () == 0 ? empty_view : content_view;
+        visible_child = locations.get_n_items () == 0 ? empty_view : list_view;
     }
 }
 
diff --git a/subprojects/libhandy b/subprojects/libhandy
new file mode 160000
index 0000000..3d29e42
--- /dev/null
+++ b/subprojects/libhandy
@@ -0,0 +1 @@
+Subproject commit 3d29e42fbebd45d9bbab631ce0f7af9f08dab9d2


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]