@@ -37,6 +37,7 @@ const VIEW_STORAGE_KEY = "races-view-mode";
type ViewMode = "list" | "calendar" ;
type RaceListTab = "upcoming" | "completed" ;
type RaceSort = "dateAsc" | "dateDesc" | "titleAsc" | "distanceAsc" ;
type RaceSortOption = RaceSort | "" ;
function yearSelectOptions ( races : Race [ ] , selectedYear = "" ) : number [ ] {
const current = new Date ( ) . getFullYear ( ) ;
@@ -146,7 +147,7 @@ export function RacesPage(): JSX.Element {
const [ distanceMin , setDistanceMin ] = useState < string > ( ( ) = > searchParams . get ( "distanceMin" ) ? ? "" ) ;
const [ distanceMax , setDistanceMax ] = useState < string > ( ( ) = > searchParams . get ( "distanceMax" ) ? ? "" ) ;
const [ searchQuery , setSearchQuery ] = useState < string > ( ( ) = > searchParams . get ( "q" ) ? ? "" ) ;
const [ sortOrder , setSortOrder ] = useState < RaceSort > ( ( ) = > ( searchParams . get ( "sort" ) as RaceSort | null ) ? ? "dateAsc " ) ;
const [ sortOrder , setSortOrder ] = useState < RaceSortOption > ( ( ) = > ( searchParams . get ( "sort" ) as RaceSort | null ) ? ? "" ) ;
const [ viewMode , setViewMode ] = useState < ViewMode > ( ( ) = > searchParams . get ( "view" ) === "calendar" ? "calendar" : readInitialViewMode ( ) ) ;
const [ activeListTab , setActiveListTab ] = useState < RaceListTab > ( "upcoming" ) ;
const [ isAdvancedFiltersOpen , setIsAdvancedFiltersOpen ] = useState < boolean > ( ( ) = >
@@ -263,7 +264,7 @@ export function RacesPage(): JSX.Element {
if ( distanceMin ) next . set ( "distanceMin" , distanceMin ) ;
if ( distanceMax ) next . set ( "distanceMax" , distanceMax ) ;
if ( searchQuery ) next . set ( "q" , searchQuery ) ;
if ( sortOrder !== "dateAsc" ) next . set ( "sort" , sortOrder ) ;
if ( sortOrder ) next . set ( "sort" , sortOrder ) ;
setSearchParams ( next , { replace : true } ) ;
} , [ dateFrom , dateTo , distanceMax , distanceMin , monthFilter , searchQuery , setSearchParams , sortOrder , statusFilter , viewMode , yearFilter ] ) ;
@@ -281,9 +282,11 @@ export function RacesPage(): JSX.Element {
const { upcoming , completed } = useMemo (
( ) = > ( {
upcoming : filteredRaces.filter ( ( race ) = > race . status !== "completed" ) ,
completed : sortByDateDesc ( filteredRaces . filter ( ( race ) = > race . status === "completed" ) ) ,
completed : sortOrder
? filteredRaces . filter ( ( race ) = > race . status === "completed" )
: sortByDateDesc ( filteredRaces . filter ( ( race ) = > race . status === "completed" ) ) ,
} ) ,
[ filteredRaces ] ,
[ filteredRaces , sortOrder ],
) ;
const statusMessage = useMemo ( ( ) = > {
if ( errorMessage && ! isLoading ) {
@@ -309,7 +312,7 @@ export function RacesPage(): JSX.Element {
dateTo ,
distanceMin ,
distanceMax ,
sortOrder !== "dateAsc" ? sortOrder : "" ,
sortOrder ,
] . filter ( Boolean ) . length ;
if ( errorMessage && races . length === 0 && ! isLoading ) {
@@ -478,7 +481,8 @@ export function RacesPage(): JSX.Element {
< / label >
< label className = "races-filter__field" >
< span className = "races-filter__label" > С о р т и р о в к а < / span >
< select className = "races-filter__select" value = { sortOrder } onChange = { ( event ) = > setSortOrder ( event . target . value as RaceSort ) } >
< select className = "races-filter__select" value = { sortOrder } onChange = { ( event ) = > setSortOrder ( event . target . value as RaceSortOption ) } >
< option value = "" > П о у м о л ч а н и ю < / option >
< option value = "dateAsc" > Дата : сначала р а н н и е < / option >
< option value = "dateDesc" > Дата : сначала п о з д н и е < / option >
< option value = "titleAsc" > Название : А – Я < / option >