Additional null safety
This commit is contained in:
parent
7658f21d7c
commit
c3938c49a9
29 changed files with 326 additions and 275 deletions
|
|
@ -2,6 +2,7 @@
|
|||
using System.Collections.Generic;
|
||||
using System.ComponentModel;
|
||||
|
||||
#nullable enable
|
||||
namespace LibationUiBase.GridView
|
||||
{
|
||||
/// <summary>
|
||||
|
|
@ -11,67 +12,10 @@ namespace LibationUiBase.GridView
|
|||
/// </summary>
|
||||
public abstract class RowComparerBase : IComparer, IComparer<IGridEntry>, IComparer<object>
|
||||
{
|
||||
public abstract string PropertyName { get; set; }
|
||||
public abstract string? PropertyName { get; set; }
|
||||
|
||||
public int Compare(object x, object y)
|
||||
{
|
||||
if (x is null && y is not null) return -1;
|
||||
if (x is not null && y is null) return 1;
|
||||
if (x is null && y is null) return 0;
|
||||
|
||||
var geA = (IGridEntry)x;
|
||||
var geB = (IGridEntry)y;
|
||||
|
||||
var sortDirection = GetSortOrder();
|
||||
|
||||
ISeriesEntry parentA = null;
|
||||
ISeriesEntry parentB = null;
|
||||
|
||||
if (geA is ILibraryBookEntry lbA && lbA.Parent is ISeriesEntry seA)
|
||||
parentA = seA;
|
||||
if (geB is ILibraryBookEntry lbB && lbB.Parent is ISeriesEntry seB)
|
||||
parentB = seB;
|
||||
|
||||
//both a and b are top-level grid entries
|
||||
if (parentA is null && parentB is null)
|
||||
return InternalCompare(geA, geB);
|
||||
|
||||
//a is top-level, b is a child
|
||||
if (parentA is null && parentB is not null)
|
||||
{
|
||||
// b is a child of a, parent is always first
|
||||
if (parentB == geA)
|
||||
return sortDirection is ListSortDirection.Ascending ? -1 : 1;
|
||||
else
|
||||
return InternalCompare(geA, parentB);
|
||||
}
|
||||
|
||||
//a is a child, b is a top-level
|
||||
if (parentA is not null && parentB is null)
|
||||
{
|
||||
// a is a child of b, parent is always first
|
||||
if (parentA == geB)
|
||||
return sortDirection is ListSortDirection.Ascending ? 1 : -1;
|
||||
else
|
||||
return InternalCompare(parentA, geB);
|
||||
}
|
||||
|
||||
//both are children of the same series
|
||||
if (parentA == parentB)
|
||||
{
|
||||
//Podcast episodes usually all have the same PurchaseDate and DateAdded property:
|
||||
//the date that the series was added to the library. So when sorting by PurchaseDate
|
||||
//and DateAdded, compare SeriesOrder instead..
|
||||
return PropertyName switch
|
||||
{
|
||||
nameof(IGridEntry.DateAdded) or nameof (IGridEntry.PurchaseDate) => geA.SeriesOrder.CompareTo(geB.SeriesOrder),
|
||||
_ => InternalCompare(geA, geB),
|
||||
};
|
||||
}
|
||||
|
||||
//a and b are children of different series.
|
||||
return InternalCompare(parentA, parentB);
|
||||
}
|
||||
public int Compare(object? x, object? y)
|
||||
=> Compare(x as IGridEntry, y as IGridEntry);
|
||||
|
||||
protected abstract ListSortDirection GetSortOrder();
|
||||
|
||||
|
|
@ -80,17 +24,74 @@ namespace LibationUiBase.GridView
|
|||
var val1 = x.GetMemberValue(PropertyName);
|
||||
var val2 = y.GetMemberValue(PropertyName);
|
||||
|
||||
var compare = x.GetMemberComparer(val1.GetType()).Compare(val1, val2);
|
||||
|
||||
var compare = x.GetMemberComparer(val1.GetType()).Compare(val1, val2);
|
||||
|
||||
return compare == 0 && x.Liberate.IsSeries && y.Liberate.IsSeries
|
||||
//Both a and b are series parents and compare as equal, so break the tie.
|
||||
? x.AudibleProductId.CompareTo(y.AudibleProductId)
|
||||
: compare;
|
||||
}
|
||||
|
||||
public int Compare(IGridEntry x, IGridEntry y)
|
||||
public int Compare(IGridEntry? geA, IGridEntry? geB)
|
||||
{
|
||||
return Compare((object)x, y);
|
||||
if (geA is null && geB is not null) return -1;
|
||||
if (geA is not null && geB is null) return 1;
|
||||
if (geA is null || geB is null) return 0;
|
||||
|
||||
var sortDirection = GetSortOrder();
|
||||
|
||||
ISeriesEntry? parentA = null;
|
||||
ISeriesEntry? parentB = null;
|
||||
|
||||
if (geA is ILibraryBookEntry lbA && lbA.Parent is ISeriesEntry seA)
|
||||
parentA = seA;
|
||||
if (geB is ILibraryBookEntry lbB && lbB.Parent is ISeriesEntry seB)
|
||||
parentB = seB;
|
||||
|
||||
//both entries are children
|
||||
if (parentA != null && parentB != null)
|
||||
{
|
||||
//both are children of the same series
|
||||
if (parentA == parentB)
|
||||
{
|
||||
//Podcast episodes usually all have the same PurchaseDate and DateAdded property:
|
||||
//the date that the series was added to the library. So when sorting by PurchaseDate
|
||||
//and DateAdded, compare SeriesOrder instead..
|
||||
return PropertyName switch
|
||||
{
|
||||
nameof(IGridEntry.DateAdded) or nameof(IGridEntry.PurchaseDate) => geA.SeriesOrder.CompareTo(geB.SeriesOrder),
|
||||
_ => InternalCompare(geA, geB),
|
||||
};
|
||||
}
|
||||
else
|
||||
//a and b are children of different series.
|
||||
return InternalCompare(parentA, parentB);
|
||||
}
|
||||
|
||||
//a is top-level, b is a child
|
||||
else if (parentA is null && parentB is not null)
|
||||
{
|
||||
// b is a child of a, parent is always first
|
||||
if (parentB == geA)
|
||||
return sortDirection is ListSortDirection.Ascending ? -1 : 1;
|
||||
else
|
||||
return InternalCompare(geA, parentB);
|
||||
}
|
||||
//a is a child, b is a top-level
|
||||
else if (parentA is not null && parentB is null)
|
||||
{
|
||||
// a is a child of b, parent is always first
|
||||
if (parentA == geB)
|
||||
return sortDirection is ListSortDirection.Ascending ? 1 : -1;
|
||||
else
|
||||
return InternalCompare(parentA, geB);
|
||||
}
|
||||
//parentA and parentB are null
|
||||
else
|
||||
{
|
||||
//both a and b are top-level grid entries
|
||||
return InternalCompare(geA, geB);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue