This repository was archived by the owner on Apr 9, 2026. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 24
Expand file tree
/
Copy pathColumnSort.cs
More file actions
165 lines (144 loc) · 5.76 KB
/
ColumnSort.cs
File metadata and controls
165 lines (144 loc) · 5.76 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
using System;
using System.Collections;
using System.Windows.Forms;
/// <summary>
/// A custom comparer for sorting ListView columns, implementing the 'IComparer' interface.
/// </summary>
public class ListViewColumnSorter : IComparer
{
/// <summary>
/// Case-insensitive comparer object used for comparing strings.
/// </summary>
private readonly CaseInsensitiveComparer ObjectCompare;
/// <summary>
/// Initializes a new instance of the ListViewColumnSorter class and sets default sorting parameters.
/// </summary>
public ListViewColumnSorter()
{
// Default column index for sorting
SortColumn = 0;
// Default sorting order
Order = SortOrder.Ascending;
// Initialize the case-insensitive comparer
ObjectCompare = new CaseInsensitiveComparer();
}
/// <summary>
/// Compares two ListViewItem objects based on the specified column index and sorting order.
/// </summary>
/// <param name="x">First ListViewItem object to compare.</param>
/// <param name="y">Second ListViewItem object to compare.</param>
/// <returns>
/// A signed integer indicating the relative values of x and y:
/// "0" if equal, a negative number if x is less than y, and a positive number if x is greater than y.
/// </returns>
public int Compare(object x, object y)
{
int compareResult;
ListViewItem listviewX = (ListViewItem)x;
ListViewItem listviewY = (ListViewItem)y;
// Special handling for column 6 (Popularity ranking)
if (SortColumn == 6)
{
string textX = listviewX.SubItems[SortColumn].Text;
string textY = listviewY.SubItems[SortColumn].Text;
// Extract numeric values from "#1", "#10", etc.
// "-" represents unranked and should go to the end
int rankX = int.MaxValue; // Default for unranked (-)
int rankY = int.MaxValue;
if (textX.StartsWith("#") && int.TryParse(textX.Substring(1), out int parsedX))
{
rankX = parsedX;
}
if (textY.StartsWith("#") && int.TryParse(textY.Substring(1), out int parsedY))
{
rankY = parsedY;
}
// Compare the numeric ranks
compareResult = rankX.CompareTo(rankY);
}
// Special handling for column 5 (Size)
else if (SortColumn == 5)
{
string textX = listviewX.SubItems[SortColumn].Text;
string textY = listviewY.SubItems[SortColumn].Text;
double sizeX = ParseSize(textX);
double sizeY = ParseSize(textY);
// Compare the numeric sizes
compareResult = sizeX.CompareTo(sizeY);
}
else
{
// Default to string comparison for non-numeric columns
compareResult = ObjectCompare.Compare(listviewX.SubItems[SortColumn].Text, listviewY.SubItems[SortColumn].Text);
}
// Determine the return value based on the specified sort order
if (Order == SortOrder.Ascending)
{
return compareResult;
}
else if (Order == SortOrder.Descending)
{
return -compareResult;
}
else
{
return 0; // Indicate equality
}
}
/// <summary>
/// Parses a numeric value from a string for accurate numeric comparison.
/// </summary>
/// <param name="text">The string representation of the number.</param>
/// <returns>The parsed integer value; returns 0 if parsing fails.</returns>
private int ParseNumber(string text)
{
// Directly attempt to parse the string as an integer
return int.TryParse(text, out int result) ? result : 0;
}
/// <summary>
/// Parses size strings with units (GB/MB) and converts them to MB for comparison.
/// </summary>
/// <param name="sizeStr">Size string (e.g., "1.23 GB", "123 MB")</param>
/// <returns>Size in MB as a double</returns>
private double ParseSize(string sizeStr)
{
if (string.IsNullOrEmpty(sizeStr))
return 0;
// Remove whitespace
sizeStr = sizeStr.Trim();
// Handle new format: "1.23 GB" or "123 MB"
if (sizeStr.EndsWith(" GB", StringComparison.OrdinalIgnoreCase))
{
string numPart = sizeStr.Substring(0, sizeStr.Length - 3).Trim();
if (double.TryParse(numPart, System.Globalization.NumberStyles.Any,
System.Globalization.CultureInfo.InvariantCulture, out double gb))
{
return gb * 1024.0; // Convert GB to MB for consistent sorting
}
}
else if (sizeStr.EndsWith(" MB", StringComparison.OrdinalIgnoreCase))
{
string numPart = sizeStr.Substring(0, sizeStr.Length - 3).Trim();
if (double.TryParse(numPart, System.Globalization.NumberStyles.Any,
System.Globalization.CultureInfo.InvariantCulture, out double mb))
{
return mb;
}
}
// Fallback: try parsing as raw number
if (double.TryParse(sizeStr, System.Globalization.NumberStyles.Any,
System.Globalization.CultureInfo.InvariantCulture, out double rawMb))
{
return rawMb;
}
return 0;
}
/// <summary>
/// Gets or sets the index of the column to be sorted (default is '0').
/// </summary>
public int SortColumn { get; set; }
/// <summary>
/// Gets or sets the order of sorting (Ascending or Descending).
/// </summary>
public SortOrder Order { get; set; }
}