From c5d0f30c718b951c2e6130d3db26c23dc27fcf66 Mon Sep 17 00:00:00 2001
From: akwizgran <akwizgran@users.sourceforge.net>
Date: Thu, 27 Feb 2014 16:25:47 +0000
Subject: [PATCH] Prettier display of available forums, cleaned up list
 comparators.

---
 briar-android/res/values/color.xml            |  1 +
 .../android/AscendingHeaderComparator.java    | 19 ----
 .../android/contact/ContactItem.java          | 18 ----
 .../contact/ContactItemComparator.java        | 18 ----
 .../android/contact/ContactListActivity.java  | 14 +--
 .../contact/ContactListItemComparator.java    | 15 ++++
 .../android/groups/GroupListActivity.java     | 87 +++++++++----------
 .../android/groups/GroupListAdapter.java      | 64 ++------------
 .../android/groups/GroupListItem.java         |  4 -
 .../groups/GroupListItemComparator.java       | 21 +++++
 .../android/groups/ManageGroupsActivity.java  | 18 +---
 .../groups/ManageGroupsItemComparator.java    | 20 +++++
 12 files changed, 105 insertions(+), 194 deletions(-)
 delete mode 100644 briar-android/src/org/briarproject/android/AscendingHeaderComparator.java
 delete mode 100644 briar-android/src/org/briarproject/android/contact/ContactItem.java
 delete mode 100644 briar-android/src/org/briarproject/android/contact/ContactItemComparator.java
 create mode 100644 briar-android/src/org/briarproject/android/contact/ContactListItemComparator.java
 create mode 100644 briar-android/src/org/briarproject/android/groups/GroupListItemComparator.java
 create mode 100644 briar-android/src/org/briarproject/android/groups/ManageGroupsItemComparator.java

diff --git a/briar-android/res/values/color.xml b/briar-android/res/values/color.xml
index 5df37c9f6b..f034c11258 100644
--- a/briar-android/res/values/color.xml
+++ b/briar-android/res/values/color.xml
@@ -7,5 +7,6 @@
 	<color name="private_message_date">#AAAAAA</color>
     <color name="unread_background">#FFFFFF</color>
 	<color name="horizontal_border">#CCCCCC</color>
+	<color name="groups_available_background">#FCCF1C</color>
 	<color name="no_posts">#AAAAAA</color>
 </resources>
\ No newline at end of file
diff --git a/briar-android/src/org/briarproject/android/AscendingHeaderComparator.java b/briar-android/src/org/briarproject/android/AscendingHeaderComparator.java
deleted file mode 100644
index 11490c4ca8..0000000000
--- a/briar-android/src/org/briarproject/android/AscendingHeaderComparator.java
+++ /dev/null
@@ -1,19 +0,0 @@
-package org.briarproject.android;
-
-import java.util.Comparator;
-
-import org.briarproject.api.db.MessageHeader;
-
-public class AscendingHeaderComparator implements Comparator<MessageHeader> {
-
-	public static final AscendingHeaderComparator INSTANCE =
-			new AscendingHeaderComparator();
-
-	public int compare(MessageHeader a, MessageHeader b) {
-		// The oldest message comes first
-		long aTime = a.getTimestamp(), bTime = b.getTimestamp();
-		if(aTime < bTime) return -1;
-		if(aTime > bTime) return 1;
-		return 0;
-	}
-}
diff --git a/briar-android/src/org/briarproject/android/contact/ContactItem.java b/briar-android/src/org/briarproject/android/contact/ContactItem.java
deleted file mode 100644
index 665a1c8acb..0000000000
--- a/briar-android/src/org/briarproject/android/contact/ContactItem.java
+++ /dev/null
@@ -1,18 +0,0 @@
-package org.briarproject.android.contact;
-
-import org.briarproject.api.Contact;
-
-public class ContactItem {
-
-	public static final ContactItem NEW = new ContactItem(null);
-
-	private final Contact contact;
-
-	public ContactItem(Contact contact) {
-		this.contact = contact;
-	}
-
-	public Contact getContact() {
-		return contact;
-	}
-}
diff --git a/briar-android/src/org/briarproject/android/contact/ContactItemComparator.java b/briar-android/src/org/briarproject/android/contact/ContactItemComparator.java
deleted file mode 100644
index 73538cc085..0000000000
--- a/briar-android/src/org/briarproject/android/contact/ContactItemComparator.java
+++ /dev/null
@@ -1,18 +0,0 @@
-package org.briarproject.android.contact;
-
-import java.util.Comparator;
-
-public class ContactItemComparator implements Comparator<ContactItem> {
-
-	public static final ContactItemComparator INSTANCE =
-			new ContactItemComparator();
-
-	public int compare(ContactItem a, ContactItem b) {
-		if(a == b) return 0;
-		if(a == ContactItem.NEW) return 1;
-		if(b == ContactItem.NEW) return -1;
-		String aName = a.getContact().getAuthor().getName();
-		String bName = b.getContact().getAuthor().getName();
-		return String.CASE_INSENSITIVE_ORDER.compare(aName, bName);
-	}
-}
diff --git a/briar-android/src/org/briarproject/android/contact/ContactListActivity.java b/briar-android/src/org/briarproject/android/contact/ContactListActivity.java
index 70519d531e..ce574b5cc3 100644
--- a/briar-android/src/org/briarproject/android/contact/ContactListActivity.java
+++ b/briar-android/src/org/briarproject/android/contact/ContactListActivity.java
@@ -12,7 +12,6 @@ import static org.briarproject.android.util.CommonLayoutParams.MATCH_WRAP;
 import static org.briarproject.android.util.CommonLayoutParams.MATCH_WRAP_1;
 
 import java.util.Collection;
-import java.util.Comparator;
 import java.util.Map;
 import java.util.concurrent.Executor;
 import java.util.logging.Logger;
@@ -178,7 +177,7 @@ ConnectionListener {
 				// Add a new item
 				adapter.add(new ContactListItem(c, connected, lastConnected,
 						inbox, headers));
-				adapter.sort(ItemComparator.INSTANCE);
+				adapter.sort(ContactListItemComparator.INSTANCE);
 				adapter.notifyDataSetChanged();
 			}
 		});
@@ -318,15 +317,4 @@ ConnectionListener {
 			}
 		});
 	}
-
-	private static class ItemComparator implements Comparator<ContactListItem> {
-
-		private static final ItemComparator INSTANCE = new ItemComparator();
-
-		public int compare(ContactListItem a, ContactListItem b) {
-			String aName = a.getContact().getAuthor().getName();
-			String bName = b.getContact().getAuthor().getName();
-			return String.CASE_INSENSITIVE_ORDER.compare(aName, bName);
-		}
-	}
 }
diff --git a/briar-android/src/org/briarproject/android/contact/ContactListItemComparator.java b/briar-android/src/org/briarproject/android/contact/ContactListItemComparator.java
new file mode 100644
index 0000000000..db41a3ef52
--- /dev/null
+++ b/briar-android/src/org/briarproject/android/contact/ContactListItemComparator.java
@@ -0,0 +1,15 @@
+package org.briarproject.android.contact;
+
+import java.util.Comparator;
+
+class ContactListItemComparator implements Comparator<ContactListItem> {
+
+	static final ContactListItemComparator INSTANCE =
+			new ContactListItemComparator();
+
+	public int compare(ContactListItem a, ContactListItem b) {
+		String aName = a.getContact().getAuthor().getName();
+		String bName = b.getContact().getAuthor().getName();
+		return String.CASE_INSENSITIVE_ORDER.compare(aName, bName);
+	}
+}
diff --git a/briar-android/src/org/briarproject/android/groups/GroupListActivity.java b/briar-android/src/org/briarproject/android/groups/GroupListActivity.java
index 09ff3fa760..1103a73df4 100644
--- a/briar-android/src/org/briarproject/android/groups/GroupListActivity.java
+++ b/briar-android/src/org/briarproject/android/groups/GroupListActivity.java
@@ -8,13 +8,11 @@ import static android.widget.LinearLayout.HORIZONTAL;
 import static android.widget.LinearLayout.VERTICAL;
 import static java.util.logging.Level.INFO;
 import static java.util.logging.Level.WARNING;
-import static org.briarproject.android.groups.GroupListItem.MANAGE;
 import static org.briarproject.android.util.CommonLayoutParams.MATCH_MATCH;
 import static org.briarproject.android.util.CommonLayoutParams.MATCH_WRAP;
 import static org.briarproject.android.util.CommonLayoutParams.MATCH_WRAP_1;
 
 import java.util.Collection;
-import java.util.Comparator;
 import java.util.Map;
 import java.util.concurrent.ConcurrentHashMap;
 import java.util.concurrent.Executor;
@@ -26,6 +24,7 @@ import org.briarproject.R;
 import org.briarproject.android.BriarActivity;
 import org.briarproject.android.util.ElasticHorizontalSpace;
 import org.briarproject.android.util.HorizontalBorder;
+import org.briarproject.android.util.LayoutUtils;
 import org.briarproject.android.util.ListLoadingProgressBar;
 import org.briarproject.api.android.DatabaseUiExecutor;
 import org.briarproject.api.db.DatabaseComponent;
@@ -54,6 +53,7 @@ import android.widget.AdapterView.OnItemClickListener;
 import android.widget.ImageButton;
 import android.widget.LinearLayout;
 import android.widget.ListView;
+import android.widget.TextView;
 
 public class GroupListActivity extends BriarActivity
 implements EventListener, OnClickListener, OnItemClickListener {
@@ -67,6 +67,7 @@ implements EventListener, OnClickListener, OnItemClickListener {
 	private GroupListAdapter adapter = null;
 	private ListView list = null;
 	private ListLoadingProgressBar loading = null;
+	private TextView available = null;
 	private ImageButton newGroupButton = null, manageGroupsButton = null;
 
 	// Fields that are accessed from background threads must be volatile
@@ -82,26 +83,39 @@ implements EventListener, OnClickListener, OnItemClickListener {
 		layout.setOrientation(VERTICAL);
 		layout.setGravity(CENTER_HORIZONTAL);
 
+		int pad = LayoutUtils.getPadding(this);
+
 		adapter = new GroupListAdapter(this);
 		list = new ListView(this);
 		// Give me all the width and all the unused height
 		list.setLayoutParams(MATCH_WRAP_1);
 		list.setAdapter(adapter);
 		list.setOnItemClickListener(this);
+		list.setVisibility(GONE);
 		layout.addView(list);
 
 		// Show a progress bar while the list is loading
-		list.setVisibility(GONE);
 		loading = new ListLoadingProgressBar(this);
 		layout.addView(loading);
 
+		available = new TextView(this);
+		available.setLayoutParams(MATCH_WRAP);
+		available.setGravity(CENTER);
+		available.setTextSize(18);
+		Resources res = getResources();
+		int background = res.getColor(R.color.groups_available_background);
+		available.setBackgroundColor(background);
+		available.setPadding(pad, pad, pad, pad);
+		available.setOnClickListener(this);
+		available.setVisibility(GONE);
+		layout.addView(available);
+
 		layout.addView(new HorizontalBorder(this));
 
 		LinearLayout footer = new LinearLayout(this);
 		footer.setLayoutParams(MATCH_WRAP);
 		footer.setOrientation(HORIZONTAL);
 		footer.setGravity(CENTER);
-		Resources res = getResources();
 		footer.setBackgroundColor(res.getColor(R.color.button_bar_background));
 		footer.addView(new ElasticHorizontalSpace(this));
 
@@ -136,7 +150,7 @@ implements EventListener, OnClickListener, OnItemClickListener {
 			public void run() {
 				try {
 					lifecycleManager.waitForDatabase();
-					int available = 0;
+					int availableCount = 0;
 					long now = System.currentTimeMillis();
 					for(GroupStatus s : db.getAvailableGroups()) {
 						Group g = s.getGroup();
@@ -149,13 +163,13 @@ implements EventListener, OnClickListener, OnItemClickListener {
 								// Continue
 							}
 						} else {
-							available++;
+							availableCount++;
 						}
 					}
 					long duration = System.currentTimeMillis() - now;
 					if(LOG.isLoggable(INFO))
 						LOG.info("Full load took " + duration + " ms");
-					displayAvailable(available);
+					displayAvailable(availableCount);
 				} catch(DbException e) {
 					if(LOG.isLoggable(WARNING))
 						LOG.log(WARNING, e.toString(), e);
@@ -173,6 +187,7 @@ implements EventListener, OnClickListener, OnItemClickListener {
 			public void run() {
 				groups.clear();
 				list.setVisibility(GONE);
+				available.setVisibility(GONE);
 				loading.setVisibility(VISIBLE);
 				adapter.clear();
 				adapter.notifyDataSetChanged();
@@ -193,20 +208,26 @@ implements EventListener, OnClickListener, OnItemClickListener {
 				if(item != null) adapter.remove(item);
 				// Add a new item
 				adapter.add(new GroupListItem(g, headers));
-				adapter.sort(ItemComparator.INSTANCE);
+				adapter.sort(GroupListItemComparator.INSTANCE);
 				adapter.notifyDataSetChanged();
 				selectFirstUnread();
 			} 
 		});
 	}
 
-	private void displayAvailable(final int available) {
+	private void displayAvailable(final int availableCount) {
 		runOnUiThread(new Runnable() {
 			public void run() {
 				list.setVisibility(VISIBLE);
 				loading.setVisibility(GONE);
-				adapter.setAvailable(available);
-				adapter.notifyDataSetChanged();
+				if(availableCount == 0) {
+					available.setVisibility(GONE);
+				} else {
+					available.setVisibility(VISIBLE);
+					String format = getResources().getQuantityString(
+							R.plurals.forums_available, availableCount);
+					available.setText(String.format(format, availableCount));
+				}
 			}
 		});
 	}
@@ -215,7 +236,6 @@ implements EventListener, OnClickListener, OnItemClickListener {
 		int count = adapter.getCount();
 		for(int i = 0; i < count; i++) {
 			GroupListItem item = adapter.getItem(i);
-			if(item == MANAGE) continue;
 			if(item.getGroup().getId().equals(g)) return item;
 		}
 		return null; // Not found
@@ -224,9 +244,7 @@ implements EventListener, OnClickListener, OnItemClickListener {
 	private void selectFirstUnread() {
 		int firstUnread = -1, count = adapter.getCount();
 		for(int i = 0; i < count; i++) {
-			GroupListItem item = adapter.getItem(i);
-			if(item == MANAGE) continue;
-			if(item.getUnreadCount() > 0) {
+			if(adapter.getItem(i).getUnreadCount() > 0) {
 				firstUnread = i;
 				break;
 			}
@@ -334,7 +352,9 @@ implements EventListener, OnClickListener, OnItemClickListener {
 	}
 
 	public void onClick(View view) {
-		if(view == newGroupButton) {
+		if(view == available) {
+			startActivity(new Intent(this, ManageGroupsActivity.class));
+		} else if(view == newGroupButton) {
 			startActivity(new Intent(this, CreateGroupActivity.class));
 		} else if(view == manageGroupsButton) {
 			startActivity(new Intent(this, ManageGroupsActivity.class));
@@ -343,35 +363,10 @@ implements EventListener, OnClickListener, OnItemClickListener {
 
 	public void onItemClick(AdapterView<?> parent, View view, int position,
 			long id) {
-		GroupListItem item = adapter.getItem(position);
-		if(item == MANAGE) {
-			startActivity(new Intent(this, ManageGroupsActivity.class));
-		} else {
-			Intent i = new Intent(this, GroupActivity.class);
-			Group g = item.getGroup();
-			i.putExtra("briar.GROUP_ID", g.getId().getBytes());
-			i.putExtra("briar.GROUP_NAME", g.getName());
-			startActivity(i);
-		}
-	}
-
-	private static class ItemComparator implements Comparator<GroupListItem> {
-
-		private static final ItemComparator INSTANCE = new ItemComparator();
-
-		public int compare(GroupListItem a, GroupListItem b) {
-			if(a == b) return 0;
-			// The manage groups item comes last
-			if(a == MANAGE) return 1;
-			if(b == MANAGE) return -1;
-			// The item with the newest message comes first
-			long aTime = a.getTimestamp(), bTime = b.getTimestamp();
-			if(aTime > bTime) return -1;
-			if(aTime < bTime) return 1;
-			// Break ties by group name
-			String aName = a.getGroup().getName();
-			String bName = b.getGroup().getName();
-			return String.CASE_INSENSITIVE_ORDER.compare(aName, bName);
-		}
+		Intent i = new Intent(this, GroupActivity.class);
+		Group g = adapter.getItem(position).getGroup();
+		i.putExtra("briar.GROUP_ID", g.getId().getBytes());
+		i.putExtra("briar.GROUP_NAME", g.getName());
+		startActivity(i);
 	}
 }
\ No newline at end of file
diff --git a/briar-android/src/org/briarproject/android/groups/GroupListAdapter.java b/briar-android/src/org/briarproject/android/groups/GroupListAdapter.java
index a82c136062..0e8c34bb69 100644
--- a/briar-android/src/org/briarproject/android/groups/GroupListAdapter.java
+++ b/briar-android/src/org/briarproject/android/groups/GroupListAdapter.java
@@ -1,15 +1,10 @@
 package org.briarproject.android.groups;
 
 import static android.text.TextUtils.TruncateAt.END;
-import static android.view.Gravity.CENTER;
 import static android.widget.LinearLayout.HORIZONTAL;
-import static org.briarproject.android.groups.GroupListItem.MANAGE;
 import static org.briarproject.android.util.CommonLayoutParams.WRAP_WRAP_1;
 
 import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.List;
 
 import org.briarproject.R;
 import org.briarproject.android.util.LayoutUtils;
@@ -19,61 +14,25 @@ import android.content.res.Resources;
 import android.text.format.DateUtils;
 import android.view.View;
 import android.view.ViewGroup;
-import android.widget.BaseAdapter;
+import android.widget.ArrayAdapter;
 import android.widget.LinearLayout;
 import android.widget.TextView;
 
-class GroupListAdapter extends BaseAdapter {
+class GroupListAdapter extends ArrayAdapter<GroupListItem> {
 
-	private final Context ctx;
 	private final int pad;
-	private final List<GroupListItem> list = new ArrayList<GroupListItem>();
-	private int available = 0;
 
 	GroupListAdapter(Context ctx) {
-		this.ctx = ctx;
+		super(ctx, android.R.layout.simple_expandable_list_item_1,
+				new ArrayList<GroupListItem>());
 		pad = LayoutUtils.getPadding(ctx);
 	}
 
-	public void setAvailable(int available) {
-		this.available = available;
-	}
-
-	public void add(GroupListItem item) {
-		list.add(item);
-	}
-
-	public void clear() {
-		list.clear();
-	}
-
-	public int getCount() {
-		return available == 0 ? list.size() : list.size() + 1;
-	}
-
-	public GroupListItem getItem(int position) {
-		return position == list.size() ? MANAGE : list.get(position);
-	}
-
-	public long getItemId(int position) {
-		return android.R.layout.simple_expandable_list_item_1;
-	}
-
 	public View getView(int position, View convertView, ViewGroup parent) {
 		GroupListItem item = getItem(position);
+		Context ctx = getContext();
 		Resources res = ctx.getResources();
 
-		if(item == MANAGE) {
-			TextView manage = new TextView(ctx);
-			manage.setGravity(CENTER);
-			manage.setTextSize(18);
-			manage.setPadding(pad, pad, pad, pad);
-			String format = res.getQuantityString(R.plurals.forums_available,
-					available);
-			manage.setText(String.format(format, available));
-			return manage;
-		}
-
 		LinearLayout layout = new LinearLayout(ctx);
 		layout.setOrientation(HORIZONTAL);
 		int unread = item.getUnreadCount();
@@ -110,17 +69,4 @@ class GroupListAdapter extends BaseAdapter {
 
 		return layout;
 	}
-
-	@Override
-	public boolean isEmpty() {
-		return list.isEmpty() && available == 0;
-	}
-
-	public void remove(GroupListItem item) {
-		list.remove(item);
-	}
-
-	public void sort(Comparator<GroupListItem> comparator) {
-		Collections.sort(list, comparator);
-	}
 }
diff --git a/briar-android/src/org/briarproject/android/groups/GroupListItem.java b/briar-android/src/org/briarproject/android/groups/GroupListItem.java
index f7b525eb06..20f9c7a3ff 100644
--- a/briar-android/src/org/briarproject/android/groups/GroupListItem.java
+++ b/briar-android/src/org/briarproject/android/groups/GroupListItem.java
@@ -1,7 +1,6 @@
 package org.briarproject.android.groups;
 
 import java.util.Collection;
-import java.util.Collections;
 
 import org.briarproject.api.Author;
 import org.briarproject.api.db.MessageHeader;
@@ -9,9 +8,6 @@ import org.briarproject.api.messaging.Group;
 
 class GroupListItem {
 
-	static final GroupListItem MANAGE = new GroupListItem(null,
-			Collections.<MessageHeader>emptyList());
-
 	private final Group group;
 	private final boolean empty;
 	private final String authorName, contentType;
diff --git a/briar-android/src/org/briarproject/android/groups/GroupListItemComparator.java b/briar-android/src/org/briarproject/android/groups/GroupListItemComparator.java
new file mode 100644
index 0000000000..7943ea1dff
--- /dev/null
+++ b/briar-android/src/org/briarproject/android/groups/GroupListItemComparator.java
@@ -0,0 +1,21 @@
+package org.briarproject.android.groups;
+
+import java.util.Comparator;
+
+class GroupListItemComparator implements Comparator<GroupListItem> {
+
+	static final GroupListItemComparator INSTANCE =
+			new GroupListItemComparator();
+
+	public int compare(GroupListItem a, GroupListItem b) {
+		if(a == b) return 0;
+		// The item with the newest message comes first
+		long aTime = a.getTimestamp(), bTime = b.getTimestamp();
+		if(aTime > bTime) return -1;
+		if(aTime < bTime) return 1;
+		// Break ties by group name
+		String aName = a.getGroup().getName();
+		String bName = b.getGroup().getName();
+		return String.CASE_INSENSITIVE_ORDER.compare(aName, bName);
+	}
+}
diff --git a/briar-android/src/org/briarproject/android/groups/ManageGroupsActivity.java b/briar-android/src/org/briarproject/android/groups/ManageGroupsActivity.java
index ce8d1171fb..22574a0389 100644
--- a/briar-android/src/org/briarproject/android/groups/ManageGroupsActivity.java
+++ b/briar-android/src/org/briarproject/android/groups/ManageGroupsActivity.java
@@ -6,7 +6,6 @@ import static org.briarproject.android.groups.ManageGroupsItem.NONE;
 import static org.briarproject.android.util.CommonLayoutParams.MATCH_MATCH;
 
 import java.util.Collection;
-import java.util.Comparator;
 import java.util.concurrent.Executor;
 import java.util.logging.Logger;
 
@@ -100,7 +99,7 @@ implements EventListener, OnItemClickListener {
 				adapter.clear();
 				for(GroupStatus s : available)
 					adapter.add(new ManageGroupsItem(s));
-				adapter.sort(ItemComparator.INSTANCE);
+				adapter.sort(ManageGroupsItemComparator.INSTANCE);
 				adapter.notifyDataSetChanged();
 			}
 		});
@@ -140,19 +139,4 @@ implements EventListener, OnItemClickListener {
 		i.putExtra("briar.VISIBLE_TO_ALL", s.isVisibleToAll());
 		startActivity(i);
 	}
-
-	private static class ItemComparator
-	implements Comparator<ManageGroupsItem> {
-
-		private static final ItemComparator INSTANCE = new ItemComparator();
-
-		public int compare(ManageGroupsItem a, ManageGroupsItem b) {
-			if(a == b) return 0;
-			if(a == NONE) return 1;
-			if(b == NONE) return -1;
-			String aName = a.getGroupStatus().getGroup().getName();
-			String bName = b.getGroupStatus().getGroup().getName();
-			return String.CASE_INSENSITIVE_ORDER.compare(aName, bName);
-		}
-	}
 }
diff --git a/briar-android/src/org/briarproject/android/groups/ManageGroupsItemComparator.java b/briar-android/src/org/briarproject/android/groups/ManageGroupsItemComparator.java
new file mode 100644
index 0000000000..ceb264fbba
--- /dev/null
+++ b/briar-android/src/org/briarproject/android/groups/ManageGroupsItemComparator.java
@@ -0,0 +1,20 @@
+package org.briarproject.android.groups;
+
+import static org.briarproject.android.groups.ManageGroupsItem.NONE;
+
+import java.util.Comparator;
+
+class ManageGroupsItemComparator implements Comparator<ManageGroupsItem> {
+
+	static final ManageGroupsItemComparator INSTANCE =
+			new ManageGroupsItemComparator();
+
+	public int compare(ManageGroupsItem a, ManageGroupsItem b) {
+		if(a == b) return 0;
+		if(a == NONE) return 1;
+		if(b == NONE) return -1;
+		String aName = a.getGroupStatus().getGroup().getName();
+		String bName = b.getGroupStatus().getGroup().getName();
+		return String.CASE_INSENSITIVE_ORDER.compare(aName, bName);
+	}
+}
-- 
GitLab