2022-03-08 03:13:53 -05:00
|
|
|
package funkin.util;
|
2022-01-26 14:19:57 -05:00
|
|
|
|
2023-09-08 17:46:44 -04:00
|
|
|
import flixel.graphics.frames.FlxFrame;
|
2022-02-23 16:49:54 -05:00
|
|
|
#if !macro
|
2022-03-11 01:30:01 -05:00
|
|
|
import flixel.FlxBasic;
|
2022-01-26 14:19:57 -05:00
|
|
|
import flixel.util.FlxSort;
|
2022-02-23 16:49:54 -05:00
|
|
|
#end
|
2023-06-22 01:41:01 -04:00
|
|
|
import funkin.play.notes.NoteSprite;
|
2023-09-13 14:51:12 -04:00
|
|
|
import funkin.data.song.SongData.SongEventData;
|
|
|
|
import funkin.data.song.SongData.SongNoteData;
|
2022-01-26 14:19:57 -05:00
|
|
|
|
2023-08-15 16:08:12 -04:00
|
|
|
/**
|
2023-11-07 04:04:22 -05:00
|
|
|
* Utility functions related to sorting.
|
2023-08-15 16:08:12 -04:00
|
|
|
*
|
|
|
|
* NOTE: `Array.sort()` takes a function `(x, y) -> Int`.
|
|
|
|
* If the objects are in the correct order (x before y), return a negative value.
|
|
|
|
* If the objects need to be swapped (y before x), return a negative value.
|
|
|
|
* If the objects are equal, return 0.
|
|
|
|
*
|
|
|
|
* NOTE: `Array.sort()` does NOT guarantee that the order of equal elements. `haxe.ds.ArraySort.sort()` does guarantee this.
|
|
|
|
* NOTE: `Array.sort()` may not be the most efficient sorting algorithm for all use cases (especially if the array is known to be mostly sorted).
|
|
|
|
* You may consider using one of the functions in `funkin.util.tools.ArraySortTools` instead.
|
|
|
|
* NOTE: Both sort functions modify the array in-place. You may consider using `Reflect.copy()` to make a copy of the array before sorting.
|
|
|
|
*/
|
2022-01-26 14:19:57 -05:00
|
|
|
class SortUtil
|
|
|
|
{
|
2023-01-22 22:25:45 -05:00
|
|
|
/**
|
|
|
|
* You can use this function in FlxTypedGroup.sort() to sort FlxObjects by their z-index values.
|
|
|
|
* The value defaults to 0, but by assigning it you can easily rearrange objects as desired.
|
|
|
|
*/
|
|
|
|
public static inline function byZIndex(Order:Int, Obj1:FlxBasic, Obj2:FlxBasic):Int
|
|
|
|
{
|
|
|
|
if (Obj1 == null || Obj2 == null) return 0;
|
|
|
|
return FlxSort.byValues(Order, Obj1.zIndex, Obj2.zIndex);
|
|
|
|
}
|
2022-03-11 01:30:01 -05:00
|
|
|
|
2023-01-22 22:25:45 -05:00
|
|
|
/**
|
|
|
|
* Given two Notes, returns 1 or -1 based on whether `a` or `b` has an earlier strumtime.
|
2023-06-08 16:30:45 -04:00
|
|
|
*
|
2023-01-22 22:25:45 -05:00
|
|
|
* @param order Either `FlxSort.ASCENDING` or `FlxSort.DESCENDING`
|
|
|
|
*/
|
2023-06-22 01:41:01 -04:00
|
|
|
public static inline function byStrumtime(order:Int, a:NoteSprite, b:NoteSprite)
|
2023-01-22 22:25:45 -05:00
|
|
|
{
|
2023-09-13 14:51:12 -04:00
|
|
|
return noteDataByTime(order, a.noteData, b.noteData);
|
|
|
|
}
|
|
|
|
|
|
|
|
public static inline function noteDataByTime(order:Int, a:SongNoteData, b:SongNoteData)
|
|
|
|
{
|
|
|
|
return FlxSort.byValues(order, a.time, b.time);
|
|
|
|
}
|
|
|
|
|
|
|
|
public static inline function eventDataByTime(order:Int, a:SongEventData, b:SongEventData)
|
|
|
|
{
|
|
|
|
return FlxSort.byValues(order, a.time, b.time);
|
2023-01-22 22:25:45 -05:00
|
|
|
}
|
2023-07-19 01:29:43 -04:00
|
|
|
|
2023-09-08 17:46:44 -04:00
|
|
|
/**
|
|
|
|
* Given two FlxFrames, sort their names alphabetically.
|
|
|
|
*
|
|
|
|
* @param order Either `FlxSort.ASCENDING` or `FlxSort.DESCENDING`
|
|
|
|
*/
|
|
|
|
public static inline function byFrameName(a:FlxFrame, b:FlxFrame)
|
|
|
|
{
|
|
|
|
return alphabetically(a.name, b.name);
|
|
|
|
}
|
|
|
|
|
2023-07-19 01:29:43 -04:00
|
|
|
/**
|
|
|
|
* Sort predicate for sorting strings alphabetically.
|
2023-08-11 14:00:38 -04:00
|
|
|
* @param a The first string to compare.
|
|
|
|
* @param b The second string to compare.
|
2023-07-19 01:29:43 -04:00
|
|
|
*/
|
2023-08-11 14:00:38 -04:00
|
|
|
public static function alphabetically(a:String, b:String):Int
|
2023-07-19 01:29:43 -04:00
|
|
|
{
|
2023-06-13 17:13:14 -04:00
|
|
|
a = a.toUpperCase();
|
|
|
|
b = b.toUpperCase();
|
|
|
|
|
2023-07-19 01:29:43 -04:00
|
|
|
// Sort alphabetically. Yes that's how this works.
|
2023-08-01 14:08:41 -04:00
|
|
|
return a == b ? 0 : a > b ? 1 : -1;
|
2023-07-19 01:29:43 -04:00
|
|
|
}
|
2023-08-11 14:00:38 -04:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Sort predicate which sorts two strings alphabetically, but prioritizes a specific string first.
|
|
|
|
* Example usage: `array.sort(defaultThenAlphabetical.bind('test'))` will sort the array so that the string 'test' is first.
|
|
|
|
* @param a The first string to compare.
|
|
|
|
* @param b The second string to compare.
|
2023-08-14 23:13:12 -04:00
|
|
|
* @param defaultValue The value to prioritize.
|
2023-08-11 14:00:38 -04:00
|
|
|
*/
|
2023-08-15 16:08:12 -04:00
|
|
|
public static function defaultThenAlphabetically(defaultValue:String, a:String, b:String):Int
|
2023-08-11 14:00:38 -04:00
|
|
|
{
|
|
|
|
if (a == b) return 0;
|
2023-08-15 16:08:12 -04:00
|
|
|
if (a == defaultValue) return -1;
|
|
|
|
if (b == defaultValue) return 1;
|
2023-08-11 14:00:38 -04:00
|
|
|
return alphabetically(a, b);
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Sort predicate which sorts two strings alphabetically, but prioritizes a specific string first.
|
|
|
|
* Example usage: `array.sort(defaultsThenAlphabetical.bind(['test']))` will sort the array so that the string 'test' is first.
|
|
|
|
* @param a The first string to compare.
|
|
|
|
* @param b The second string to compare.
|
2023-08-14 23:13:12 -04:00
|
|
|
* @param defaultValues The values to prioritize.
|
2023-08-11 14:00:38 -04:00
|
|
|
*/
|
2023-08-15 16:08:12 -04:00
|
|
|
public static function defaultsThenAlphabetically(defaultValues:Array<String>, a:String, b:String):Int
|
2023-08-11 14:00:38 -04:00
|
|
|
{
|
|
|
|
if (a == b) return 0;
|
2023-08-14 23:13:12 -04:00
|
|
|
if (defaultValues.contains(a) && defaultValues.contains(b))
|
|
|
|
{
|
|
|
|
// Sort by index in defaultValues
|
|
|
|
return defaultValues.indexOf(a) - defaultValues.indexOf(b);
|
|
|
|
};
|
2023-08-15 16:08:12 -04:00
|
|
|
if (defaultValues.contains(a)) return -1;
|
|
|
|
if (defaultValues.contains(b)) return 1;
|
2023-08-11 14:00:38 -04:00
|
|
|
return alphabetically(a, b);
|
|
|
|
}
|
2022-01-26 14:19:57 -05:00
|
|
|
}
|