Add category and recipe sorting with multiple modes and order inversion

Categories on the main page can be sorted by Recently Used, Alphabetical,
or Manual (drag-to-reorder). The sort menu appears inline next to the
Categories header. All Recipes is included in the sort order and manual
reorder sheet. Recipes within category and all-recipes lists can be sorted
by Recently Added or Alphabetical, with the sort button in the toolbar.
All non-manual sort modes support order inversion via a Reverse/Default
Order toggle. Date parsing handles both formatted strings and Unix
timestamps, with recipe_id as fallback when dates are unavailable.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
This commit is contained in:
2026-02-15 07:46:23 +01:00
parent fb6b16c1fc
commit 5307b502e9
10 changed files with 694 additions and 48 deletions

View File

@@ -80,6 +80,8 @@
F1A0DE062E0C000300000003 /* MealPlanSyncManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = F1A0DE052E0C000300000003 /* MealPlanSyncManager.swift */; };
F1A0DE082E0C000400000004 /* MealPlanTabView.swift in Sources */ = {isa = PBXBuildFile; fileRef = F1A0DE072E0C000400000004 /* MealPlanTabView.swift */; };
F1A0DE0A2E0C000500000005 /* AddToMealPlanSheet.swift in Sources */ = {isa = PBXBuildFile; fileRef = F1A0DE092E0C000500000005 /* AddToMealPlanSheet.swift */; };
G1A0CE012F0B000100000001 /* CategorySortMode.swift in Sources */ = {isa = PBXBuildFile; fileRef = G1A0CE002F0B000100000001 /* CategorySortMode.swift */; };
G1A0CE032F0B000200000002 /* CategoryReorderSheet.swift in Sources */ = {isa = PBXBuildFile; fileRef = G1A0CE022F0B000200000002 /* CategoryReorderSheet.swift */; };
/* End PBXBuildFile section */
/* Begin PBXContainerItemProxy section */
@@ -177,6 +179,8 @@
F1A0DE052E0C000300000003 /* MealPlanSyncManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MealPlanSyncManager.swift; sourceTree = "<group>"; };
F1A0DE072E0C000400000004 /* MealPlanTabView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MealPlanTabView.swift; sourceTree = "<group>"; };
F1A0DE092E0C000500000005 /* AddToMealPlanSheet.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AddToMealPlanSheet.swift; sourceTree = "<group>"; };
G1A0CE002F0B000100000001 /* CategorySortMode.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CategorySortMode.swift; sourceTree = "<group>"; };
G1A0CE022F0B000200000002 /* CategoryReorderSheet.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CategoryReorderSheet.swift; sourceTree = "<group>"; };
/* End PBXFileReference section */
/* Begin PBXFrameworksBuildPhase section */
@@ -323,6 +327,7 @@
F1A0DE012E0C000100000001 /* MealPlanModels.swift */,
F1A0DE032E0C000200000002 /* MealPlanManager.swift */,
F1A0DE052E0C000300000003 /* MealPlanSyncManager.swift */,
G1A0CE002F0B000100000001 /* CategorySortMode.swift */,
);
path = Data;
sourceTree = "<group>";
@@ -433,6 +438,7 @@
A97B4D342B80B82A00EC1A88 /* ShareView.swift */,
C1F0AB012D0B000100000001 /* ImportURLSheet.swift */,
F1A0DE092E0C000500000005 /* AddToMealPlanSheet.swift */,
G1A0CE022F0B000200000002 /* CategoryReorderSheet.swift */,
);
path = Recipes;
sourceTree = "<group>";
@@ -670,6 +676,8 @@
F1A0DE062E0C000300000003 /* MealPlanSyncManager.swift in Sources */,
F1A0DE082E0C000400000004 /* MealPlanTabView.swift in Sources */,
F1A0DE0A2E0C000500000005 /* AddToMealPlanSheet.swift in Sources */,
G1A0CE012F0B000100000001 /* CategorySortMode.swift in Sources */,
G1A0CE032F0B000200000002 /* CategoryReorderSheet.swift in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};