Commit b3ad2643 authored by Niels De Graef's avatar Niels De Graef

Allow sorting by first name or surname.

Fixes #54.
parent 83af90f9
Pipeline #2976 canceled with stage
<?xml version="1.0" encoding="UTF-8"?>
<!-- Generated with glade 3.15.2 on Thu Aug 15 15:33:02 2013 -->
<interface>
<!-- interface-requires gtk+ 3.10 -->
<!-- interface-requires gtk+ 3.22 -->
<object class="GtkPopover" id="hamburger_menu_popover">
<child>
<object class="GtkGrid">
<property name="visible">True</property>
<property name="row_spacing">6</property>
<property name="margin">18</property>
<property name="width_request">200</property>
<child>
<object class="GtkLabel">
<property name="visible">True</property>
<property name="halign">start</property>
<property name="label" translatable="yes">List contacts by:</property>
<style>
<class name="dim-label"/>
</style>
</object>
<packing>
<property name="top_attach">0</property>
<property name="width">2</property>
</packing>
</child>
<child>
<object class="GtkRadioButton" id="sort_on_firstname_button">
<property name="visible">True</property>
<property name="group">sort_on_firstname_button</property>
</object>
<packing>
<property name="top_attach">1</property>
<property name="left_attach">1</property>
</packing>
</child>
<child>
<object class="GtkLabel">
<property name="visible">True</property>
<property name="halign">start</property>
<property name="hexpand">True</property>
<property name="label" translatable="yes">First name</property>
<property name="mnemonic_widget">sort_on_firstname_button</property>
</object>
<packing>
<property name="top_attach">1</property>
<property name="left_attach">0</property>
</packing>
</child>
<child>
<object class="GtkRadioButton" id="sort_on_surname_button">
<property name="visible">True</property>
<property name="group">sort_on_firstname_button</property>
</object>
<packing>
<property name="top_attach">2</property>
<property name="left_attach">1</property>
</packing>
</child>
<child>
<object class="GtkLabel">
<property name="visible">True</property>
<property name="halign">start</property>
<property name="hexpand">True</property>
<property name="label" translatable="yes">Surname</property>
<property name="mnemonic_widget">sort_on_surname_button</property>
</object>
<packing>
<property name="top_attach">2</property>
<property name="left_attach">0</property>
</packing>
</child>
</object>
</child>
</object>
<template class="ContactsWindow" parent="GtkApplicationWindow">
<property name="can_focus">False</property>
<property name="default_width">800</property>
......@@ -50,6 +119,24 @@
<property name="pack_type">start</property>
</packing>
</child>
<child>
<object class="GtkMenuButton" id="hamburger_menu_button">
<property name="visible">True</property>
<property name="can_focus">True</property>
<property name="focus_on_click">False</property>
<property name="popover">hamburger_menu_popover</property>
<child>
<object class="GtkImage">
<property name="visible">True</property>
<property name="can_focus">False</property>
<property name="icon_name">open-menu-symbolic</property>
</object>
</child>
</object>
<packing>
<property name="pack_type">end</property>
</packing>
</child>
<child>
<object class="GtkButton" id="select_cancel_button">
<property name="visible">False</property>
......
......@@ -226,7 +226,7 @@ public class Contacts.App : Gtk.Application {
}
private void create_window () {
this.window = new Contacts.Window (this, this.contacts_store);
this.window = new Contacts.Window (this.settings, this, this.contacts_store);
}
private void schedule_window_creation () {
......
......@@ -102,9 +102,11 @@ public class Contacts.ContactList : ListBox {
private Store store;
private Settings settings;
public UiState state { get; set; }
public ContactList (Store store, Query query) {
public ContactList (Settings settings, Store store, Query query) {
this.selection_mode = Gtk.SelectionMode.BROWSE;
this.store = store;
this.filter_query = query;
......@@ -113,6 +115,9 @@ public class Contacts.ContactList : ListBox {
this.notify["state"].connect (on_ui_state_changed);
this.settings = settings;
this.settings.changed["sort-on-surname"].connect(invalidate_sort);
this.store.added.connect (contact_added_cb);
this.store.removed.connect (contact_removed_cb);
foreach (var c in this.store.get_contacts ())
......@@ -146,8 +151,19 @@ public class Contacts.ContactList : ListBox {
if (a.is_favourite != b.is_favourite)
return a.is_favourite? -1 : 1;
// Both are (non-)favourites: sort by name
return a.display_name.collate (b.display_name);
// Both are (non-)favourites: sort by either first name or surname (user preference)
unowned string? a_name = this.settings.sort_on_surname? try_get_surname(a) : a.display_name;
unowned string? b_name = this.settings.sort_on_surname? try_get_surname(b) : b.display_name;
return a_name.collate (b_name);
}
private unowned string try_get_surname (Individual indiv) {
if (indiv.structured_name != null && indiv.structured_name.family_name != "")
return indiv.structured_name.family_name;
// Fall back to the display_name
return indiv.display_name;
}
private void update_header (ListBoxRow row, ListBoxRow? before) {
......
......@@ -48,7 +48,7 @@ public class Contacts.ListPane : Frame {
public signal void delete_contacts (LinkedList<Contact> contacts);
public signal void contacts_marked (int contacts_marked);
public ListPane (Store contacts_store) {
public ListPane (Settings settings, Store contacts_store) {
this.store = contacts_store;
this.notify["state"].connect (on_ui_state_changed);
......@@ -60,7 +60,7 @@ public class Contacts.ListPane : Frame {
// Load the ContactsView and connect the necessary signals
this.contacts_list = new ContactList (contacts_store, this.filter_query);
this.contacts_list = new ContactList (settings, contacts_store, this.filter_query);
bind_property ("state", this.contacts_list, "state", BindingFlags.BIDIRECTIONAL | BindingFlags.SYNC_CREATE);
this.contacts_list_container.add (this.contacts_list);
......
......@@ -18,15 +18,19 @@
/**
* Provides a convenient interface to deal with the settings.
*/
public class Contacts.Settings {
private GLib.Settings settings;
public class Contacts.Settings : GLib.Settings {
public bool did_initial_setup {
get { return settings.get_boolean ("did-initial-setup"); }
set { settings.set_boolean ("did-initial-setup", value); }
get { return get_boolean ("did-initial-setup"); }
set { set_boolean ("did-initial-setup", value); }
}
public bool sort_on_surname {
get { return get_boolean ("sort-on-surname"); }
set { set_boolean ("sort-on-surname", value); }
}
public Settings (App app) {
this.settings = new GLib.Settings (app.application_id);
Object (schema_id: app.application_id);
}
}
......@@ -40,6 +40,10 @@ public class Contacts.Window : Gtk.ApplicationWindow {
[GtkChild]
private Button select_cancel_button;
[GtkChild]
private MenuButton hamburger_menu_button;
[GtkChild]
private RadioButton sort_on_surname_button;
[GtkChild]
private ToggleButton favorite_button;
private bool ignore_favorite_button_toggled;
[GtkChild]
......@@ -55,17 +59,25 @@ public class Contacts.Window : Gtk.ApplicationWindow {
public UiState state { get; set; default = UiState.NORMAL; }
private Settings settings;
public Store store {
get; construct set;
}
public Window (App app, Store contacts_store) {
public Window (Settings settings, App app, Store contacts_store) {
Object (
application: app,
show_menubar: false,
store: contacts_store
);
this.settings = settings;
this.sort_on_surname_button.active = this.settings.sort_on_surname;
this.sort_on_surname_button.toggled.connect (() => {
this.settings.sort_on_surname = this.sort_on_surname_button.active;
});
this.notify["state"].connect (on_ui_state_changed);
create_contact_pane ();
......@@ -90,7 +102,7 @@ public class Contacts.Window : Gtk.ApplicationWindow {
if (list_pane != null)
return;
list_pane = new ListPane (store);
list_pane = new ListPane (this.settings, store);
bind_property ("state", this.list_pane, "state", BindingFlags.BIDIRECTIONAL | BindingFlags.SYNC_CREATE);
list_pane.selection_changed.connect (list_pane_selection_changed_cb);
list_pane.link_contacts.connect (list_pane_link_contacts_cb);
......@@ -117,6 +129,7 @@ public class Contacts.Window : Gtk.ApplicationWindow {
private void on_ui_state_changed (Object obj, ParamSpec pspec) {
// UI when we're not editing of selecting stuff
this.add_button.visible
= this.hamburger_menu_button.visible
= this.right_header.show_close_button
= (this.state == UiState.NORMAL || this.state == UiState.SHOWING);
......
......@@ -5,5 +5,13 @@
<summary>First-time setup done.</summary>
<description>Set to true after the user has run the first-time setup wizard.</description>
</key>
<key name="sort-on-surname" type="b">
<default>false</default>
<summary>Sort contacts on surname.</summary>
<description>
If this is set to true, the list of contacts will be sorted on their surnames.
Otherwise, it will be sorted on the first names of the contacts.
</description>
</key>
</schema>
</schemalist>
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment