From 07850264961af05b0234e755e2a6650d35ac2df2 Mon Sep 17 00:00:00 2001 From: Mirlan Date: Fri, 24 Jul 2020 14:42:19 +0600 Subject: [PATCH] Ott 141 match status filters (#56) --- src/config/lexics/authenticated.tsx | 3 + src/features/DateFilter/hooks/index.tsx | 69 ------------------- .../components}/DateFilter/helpers.tsx | 0 .../components/DateFilter/hooks/index.tsx | 48 +++++++++++++ .../components}/DateFilter/index.tsx | 6 +- .../components}/DateFilter/styled.tsx | 0 .../components/DatePicker/hooks.tsx | 0 .../components/DatePicker/index.tsx | 2 +- .../components/DatePicker/styled.tsx | 0 .../components/MatchStatusFilter/index.tsx | 38 ++++++++++ .../components/MatchStatusFilter/styled.tsx | 47 +++++++++++++ .../components}/SportTypeFilter/index.tsx | 0 .../components/SportTypeFilter}/styled.tsx | 0 .../components}/TournamentFilter/index.tsx | 0 .../components/TournamentFilter}/styled.tsx | 0 src/features/HeaderFilters/index.tsx | 5 ++ .../HeaderFilters/store/hooks/index.tsx | 69 +++++++++++++++++++ .../store/hooks/useTournaments.tsx | 14 ++++ src/features/HeaderFilters/store/index.tsx | 26 +++++++ src/features/HomePage/index.tsx | 17 +++-- src/features/MatchStatusFilter/index.tsx | 5 -- src/features/TournamentFilter/styled.tsx | 3 - src/helpers/handleImg/index.tsx | 2 + src/helpers/index.tsx | 1 - src/requests/getMatches.tsx | 5 ++ 25 files changed, 271 insertions(+), 89 deletions(-) delete mode 100644 src/features/DateFilter/hooks/index.tsx rename src/features/{ => HeaderFilters/components}/DateFilter/helpers.tsx (100%) create mode 100644 src/features/HeaderFilters/components/DateFilter/hooks/index.tsx rename src/features/{ => HeaderFilters/components}/DateFilter/index.tsx (91%) rename src/features/{ => HeaderFilters/components}/DateFilter/styled.tsx (100%) rename src/features/{DateFilter => HeaderFilters}/components/DatePicker/hooks.tsx (100%) rename src/features/{DateFilter => HeaderFilters}/components/DatePicker/index.tsx (95%) rename src/features/{DateFilter => HeaderFilters}/components/DatePicker/styled.tsx (100%) create mode 100644 src/features/HeaderFilters/components/MatchStatusFilter/index.tsx create mode 100644 src/features/HeaderFilters/components/MatchStatusFilter/styled.tsx rename src/features/{ => HeaderFilters/components}/SportTypeFilter/index.tsx (100%) rename src/features/{MatchStatusFilter => HeaderFilters/components/SportTypeFilter}/styled.tsx (100%) rename src/features/{ => HeaderFilters/components}/TournamentFilter/index.tsx (100%) rename src/features/{SportTypeFilter => HeaderFilters/components/TournamentFilter}/styled.tsx (100%) create mode 100644 src/features/HeaderFilters/index.tsx create mode 100644 src/features/HeaderFilters/store/hooks/index.tsx create mode 100644 src/features/HeaderFilters/store/hooks/useTournaments.tsx create mode 100644 src/features/HeaderFilters/store/index.tsx delete mode 100644 src/features/MatchStatusFilter/index.tsx delete mode 100644 src/features/TournamentFilter/styled.tsx diff --git a/src/config/lexics/authenticated.tsx b/src/config/lexics/authenticated.tsx index a440c9a0..50ff731e 100644 --- a/src/config/lexics/authenticated.tsx +++ b/src/config/lexics/authenticated.tsx @@ -4,6 +4,9 @@ export const authenticatedLexics = { hide_score: 12982, hockey: 6959, logout: 4306, + match_status_finished: 12985, + match_status_live: 12984, + match_status_soon: 12986, player: 630, team: 658, tournament: 1009, diff --git a/src/features/DateFilter/hooks/index.tsx b/src/features/DateFilter/hooks/index.tsx deleted file mode 100644 index cfea2951..00000000 --- a/src/features/DateFilter/hooks/index.tsx +++ /dev/null @@ -1,69 +0,0 @@ -import { - useState, - useCallback, - useEffect, -} from 'react' - -import debounce from 'lodash/debounce' -import format from 'date-fns/format' -import addDays from 'date-fns/addDays' -import startOfDay from 'date-fns/startOfDay' - -import { getMatches } from 'requests' -import { useToggle } from 'hooks' -import { useLexicsStore } from 'features/LexicsStore' - -import { getDisplayDate } from '../helpers' - -const dateFormat = 'dd/MM/yyyy HH:mm:ss' - -export const useDateFilter = () => { - const { lang } = useLexicsStore() - const { - close, - isOpen, - open, - } = useToggle() - const fetchMatches = useCallback(debounce(getMatches, 300), []) - const [currentDate, setCurrentDate] = useState(new Date()) - - const date = getDisplayDate({ - date: currentDate, - lang, - }) - - const onPreviousClick = () => { - setCurrentDate(addDays(currentDate, -1)) - } - - const onNextClick = () => { - setCurrentDate(addDays(currentDate, 1)) - } - - const onDateChange = (newDate: Date | null) => { - if (newDate) { - setCurrentDate(newDate) - close() - } - } - - useEffect(() => { - const formattedDate = format(startOfDay(currentDate), dateFormat) - fetchMatches({ - date: formattedDate, - sportType: 1, - tournamentId: 8, - }) - }, [fetchMatches, currentDate]) - - return { - close, - currentDate, - date, - isOpen, - onDateChange, - onNextClick, - onPreviousClick, - open, - } -} diff --git a/src/features/DateFilter/helpers.tsx b/src/features/HeaderFilters/components/DateFilter/helpers.tsx similarity index 100% rename from src/features/DateFilter/helpers.tsx rename to src/features/HeaderFilters/components/DateFilter/helpers.tsx diff --git a/src/features/HeaderFilters/components/DateFilter/hooks/index.tsx b/src/features/HeaderFilters/components/DateFilter/hooks/index.tsx new file mode 100644 index 00000000..ee11d964 --- /dev/null +++ b/src/features/HeaderFilters/components/DateFilter/hooks/index.tsx @@ -0,0 +1,48 @@ +import addDays from 'date-fns/addDays' + +import { useToggle } from 'hooks' +import { useLexicsStore } from 'features/LexicsStore' +import { useHeaderFiltersStore } from 'features/HeaderFilters' + +import { getDisplayDate } from '../helpers' + +export const useDateFilter = () => { + const { selectedDate, setSelectedDate } = useHeaderFiltersStore() + const { lang } = useLexicsStore() + const { + close, + isOpen, + open, + } = useToggle() + + const date = getDisplayDate({ + date: selectedDate, + lang, + }) + + const onPreviousClick = () => { + setSelectedDate(addDays(selectedDate, -1)) + } + + const onNextClick = () => { + setSelectedDate(addDays(selectedDate, 1)) + } + + const onDateChange = (newDate: Date | null) => { + if (newDate) { + setSelectedDate(newDate) + close() + } + } + + return { + close, + date, + isOpen, + onDateChange, + onNextClick, + onPreviousClick, + open, + selectedDate, + } +} diff --git a/src/features/DateFilter/index.tsx b/src/features/HeaderFilters/components/DateFilter/index.tsx similarity index 91% rename from src/features/DateFilter/index.tsx rename to src/features/HeaderFilters/components/DateFilter/index.tsx index 925b2999..67837afd 100644 --- a/src/features/DateFilter/index.tsx +++ b/src/features/HeaderFilters/components/DateFilter/index.tsx @@ -3,7 +3,7 @@ import React from 'react' import { OutsideClick } from 'features/OutsideClick' import { useDateFilter } from './hooks' -import { DatePicker } from './components/DatePicker' +import { DatePicker } from '../DatePicker' import { Wrapper, Button, @@ -19,13 +19,13 @@ import { export const DateFilter = () => { const { close, - currentDate, date, isOpen, onDateChange, onNextClick, onPreviousClick, open, + selectedDate, } = useDateFilter() return ( @@ -42,7 +42,7 @@ export const DateFilter = () => { diff --git a/src/features/DateFilter/styled.tsx b/src/features/HeaderFilters/components/DateFilter/styled.tsx similarity index 100% rename from src/features/DateFilter/styled.tsx rename to src/features/HeaderFilters/components/DateFilter/styled.tsx diff --git a/src/features/DateFilter/components/DatePicker/hooks.tsx b/src/features/HeaderFilters/components/DatePicker/hooks.tsx similarity index 100% rename from src/features/DateFilter/components/DatePicker/hooks.tsx rename to src/features/HeaderFilters/components/DatePicker/hooks.tsx diff --git a/src/features/DateFilter/components/DatePicker/index.tsx b/src/features/HeaderFilters/components/DatePicker/index.tsx similarity index 95% rename from src/features/DateFilter/components/DatePicker/index.tsx rename to src/features/HeaderFilters/components/DatePicker/index.tsx index 31cde6e7..5560e24c 100644 --- a/src/features/DateFilter/components/DatePicker/index.tsx +++ b/src/features/HeaderFilters/components/DatePicker/index.tsx @@ -7,8 +7,8 @@ import 'react-datepicker/dist/react-datepicker.css' import addMonths from 'date-fns/addMonths' import { useLexicsStore } from 'features/LexicsStore' -import { getDisplayDate, getMonthName } from 'features/DateFilter/helpers' +import { getDisplayDate, getMonthName } from '../DateFilter/helpers' import { useDatepickerLocales } from './hooks' import { Wrapper, diff --git a/src/features/DateFilter/components/DatePicker/styled.tsx b/src/features/HeaderFilters/components/DatePicker/styled.tsx similarity index 100% rename from src/features/DateFilter/components/DatePicker/styled.tsx rename to src/features/HeaderFilters/components/DatePicker/styled.tsx diff --git a/src/features/HeaderFilters/components/MatchStatusFilter/index.tsx b/src/features/HeaderFilters/components/MatchStatusFilter/index.tsx new file mode 100644 index 00000000..963c9b5a --- /dev/null +++ b/src/features/HeaderFilters/components/MatchStatusFilter/index.tsx @@ -0,0 +1,38 @@ +import React from 'react' + +import { T9n } from 'features/T9n' + +import { MatchStatuses, useHeaderFiltersStore } from '../../store' +import { + RadioButtonGroup, + RadioButton, +} from './styled' + +export const MatchStatusFilter = () => { + const { selectedMatchStatus, setSelectedMatchStatus } = useHeaderFiltersStore() + return ( + + setSelectedMatchStatus(MatchStatuses.Live)} + buttonWidth={80} + > + + + setSelectedMatchStatus(MatchStatuses.Finished)} + buttonWidth={121} + > + + + setSelectedMatchStatus(MatchStatuses.Soon)} + buttonWidth={87} + > + + + + ) +} diff --git a/src/features/HeaderFilters/components/MatchStatusFilter/styled.tsx b/src/features/HeaderFilters/components/MatchStatusFilter/styled.tsx new file mode 100644 index 00000000..b680bf90 --- /dev/null +++ b/src/features/HeaderFilters/components/MatchStatusFilter/styled.tsx @@ -0,0 +1,47 @@ +import styled from 'styled-components/macro' + +export const RadioButtonGroup = styled.div` + height: 100%; + box-shadow: 0px 1px 1px rgba(0, 0, 0, 0.3); + border-radius: 2px; + overflow: hidden; +` + +type RadioButtonProps = { + buttonWidth?: number, + selected?: boolean, +} + +export const RadioButton = styled.button` + border: none; + outline: none; + height: 100%; + width: ${({ buttonWidth }) => (buttonWidth ? `${buttonWidth}px` : '')}; + font-weight: 600; + font-size: 18px; + cursor: pointer; + + ${({ selected }) => ( + selected + ? ` + background-color: #666666; + color: #ffffff; + ` + : ` + background-color: #3F3F3F; + color: #999999; + + :hover { + background-color: #484848; + } + ` + )} + + :first-child { + text-transform: uppercase; + } + + :not(:last-child) { + border-right: 1px solid #222222; + } +` diff --git a/src/features/SportTypeFilter/index.tsx b/src/features/HeaderFilters/components/SportTypeFilter/index.tsx similarity index 100% rename from src/features/SportTypeFilter/index.tsx rename to src/features/HeaderFilters/components/SportTypeFilter/index.tsx diff --git a/src/features/MatchStatusFilter/styled.tsx b/src/features/HeaderFilters/components/SportTypeFilter/styled.tsx similarity index 100% rename from src/features/MatchStatusFilter/styled.tsx rename to src/features/HeaderFilters/components/SportTypeFilter/styled.tsx diff --git a/src/features/TournamentFilter/index.tsx b/src/features/HeaderFilters/components/TournamentFilter/index.tsx similarity index 100% rename from src/features/TournamentFilter/index.tsx rename to src/features/HeaderFilters/components/TournamentFilter/index.tsx diff --git a/src/features/SportTypeFilter/styled.tsx b/src/features/HeaderFilters/components/TournamentFilter/styled.tsx similarity index 100% rename from src/features/SportTypeFilter/styled.tsx rename to src/features/HeaderFilters/components/TournamentFilter/styled.tsx diff --git a/src/features/HeaderFilters/index.tsx b/src/features/HeaderFilters/index.tsx new file mode 100644 index 00000000..65dd80fc --- /dev/null +++ b/src/features/HeaderFilters/index.tsx @@ -0,0 +1,5 @@ +export * from './components/DateFilter' +export * from './components/MatchStatusFilter' +export * from './components/SportTypeFilter' +export * from './components/TournamentFilter' +export * from './store' diff --git a/src/features/HeaderFilters/store/hooks/index.tsx b/src/features/HeaderFilters/store/hooks/index.tsx new file mode 100644 index 00000000..fade37cb --- /dev/null +++ b/src/features/HeaderFilters/store/hooks/index.tsx @@ -0,0 +1,69 @@ +import { + useMemo, + useState, + useEffect, + useCallback, +} from 'react' + +import debounce from 'lodash/debounce' +import format from 'date-fns/format' +import startOfDay from 'date-fns/startOfDay' + +import { getMatches } from 'requests' + +import { useTournaments } from './useTournaments' + +export enum MatchStatuses { + Live = 1, + Finished = 2, + Soon = 3, +} + +export enum SportTypes { + Football = 1, + Basketball = 2, + Hockey = 3, +} + +const dateFormat = 'dd/MM/yyyy HH:mm:ss' + +export const useFilters = () => { + const [selectedDate, setSelectedDate] = useState(new Date()) + const [selectedMatchStatus, setSelectedMatchStatus] = useState(MatchStatuses.Live) + const [selectedSportType, setSelectedSportTypes] = useState(SportTypes.Football) + const tournaments = useTournaments() + const fetchMatches = useCallback(debounce(getMatches, 300), []) + + // временно здесь запрашиваются матчи при изменении фильтров, + // можно эту логику вырезать и вставить в компонент матчей + useEffect(() => { + const formattedDate = format(startOfDay(selectedDate), dateFormat) + fetchMatches({ + date: formattedDate, + matchStatus: selectedMatchStatus, + sportType: selectedSportType, + tournamentId: 8, + }) + }, [ + selectedDate, + selectedMatchStatus, + selectedSportType, + fetchMatches, + ]) + + const store = useMemo(() => ({ + selectedDate, + selectedMatchStatus, + selectedSportType, + setSelectedDate, + setSelectedMatchStatus, + setSelectedSportTypes, + tournaments, + }), [ + selectedDate, + selectedMatchStatus, + selectedSportType, + tournaments, + ]) + return store +} diff --git a/src/features/HeaderFilters/store/hooks/useTournaments.tsx b/src/features/HeaderFilters/store/hooks/useTournaments.tsx new file mode 100644 index 00000000..f485bd3b --- /dev/null +++ b/src/features/HeaderFilters/store/hooks/useTournaments.tsx @@ -0,0 +1,14 @@ +type TournamentOption = {} + +type Tournaments = { + options: Array, + selected: TournamentOption | null, +} + +const initialState: Tournaments = { + options: [], + selected: null, +} + +// доделаем на таске по турнирам +export const useTournaments = () => initialState diff --git a/src/features/HeaderFilters/store/index.tsx b/src/features/HeaderFilters/store/index.tsx new file mode 100644 index 00000000..05f1666c --- /dev/null +++ b/src/features/HeaderFilters/store/index.tsx @@ -0,0 +1,26 @@ +import type { ReactNode } from 'react' +import React, { + useContext, + createContext, +} from 'react' + +import { useFilters } from './hooks' + +export * from './hooks' + +type HeaderFiltersStore = ReturnType + +const FiltersContext = createContext({} as HeaderFiltersStore) + +type Props = { children: ReactNode } + +export const HeaderFiltersStore = ({ children }: Props) => { + const filters = useFilters() + return ( + + {children} + + ) +} + +export const useHeaderFiltersStore = () => useContext(FiltersContext) diff --git a/src/features/HomePage/index.tsx b/src/features/HomePage/index.tsx index 35685a73..51746c8e 100644 --- a/src/features/HomePage/index.tsx +++ b/src/features/HomePage/index.tsx @@ -1,12 +1,15 @@ -import React, { Fragment } from 'react' +import React from 'react' import { Header } from 'features/Header' import { MainWrapper } from 'features/MainWrapper' import { Search } from 'features/Search' -import { DateFilter } from 'features/DateFilter' -import { MatchStatusFilter } from 'features/MatchStatusFilter' -import { SportTypeFilter } from 'features/SportTypeFilter' -import { TournamentFilter } from 'features/TournamentFilter' +import { + DateFilter, + MatchStatusFilter, + SportTypeFilter, + TournamentFilter, + HeaderFiltersStore, +} from 'features/HeaderFilters' import { UserSportFav } from 'features/UserSportFav' import { @@ -14,7 +17,7 @@ import { } from './styled' export const HomePage = () => ( - +
@@ -36,5 +39,5 @@ export const HomePage = () => (
-
+ ) diff --git a/src/features/MatchStatusFilter/index.tsx b/src/features/MatchStatusFilter/index.tsx deleted file mode 100644 index c980223f..00000000 --- a/src/features/MatchStatusFilter/index.tsx +++ /dev/null @@ -1,5 +0,0 @@ -import React from 'react' - -import { Wrapper } from './styled' - -export const MatchStatusFilter = () => diff --git a/src/features/TournamentFilter/styled.tsx b/src/features/TournamentFilter/styled.tsx deleted file mode 100644 index 8646cd0a..00000000 --- a/src/features/TournamentFilter/styled.tsx +++ /dev/null @@ -1,3 +0,0 @@ -import styled from 'styled-components/macro' - -export const Wrapper = styled.div`` diff --git a/src/helpers/handleImg/index.tsx b/src/helpers/handleImg/index.tsx index 5981a11f..aa655bb2 100644 --- a/src/helpers/handleImg/index.tsx +++ b/src/helpers/handleImg/index.tsx @@ -21,7 +21,9 @@ export const DATA_TYPES = { } as const export const handleImageError = (arg: imageErrorArgs): void => { + // eslint-disable-next-line no-param-reassign arg.e.target.onError = '' // @ts-expect-error + // eslint-disable-next-line no-param-reassign arg.e.target.src = LOGOS_FALLBACKS[SPORT_TYPES[arg.sport]][DATA_TYPES[arg.type]] } diff --git a/src/helpers/index.tsx b/src/helpers/index.tsx index da4863fb..561ffbcb 100644 --- a/src/helpers/index.tsx +++ b/src/helpers/index.tsx @@ -3,4 +3,3 @@ export * from './callApi/getResponseData' export * from './token' export * from './getLogo' export * from './handleImg' - diff --git a/src/requests/getMatches.tsx b/src/requests/getMatches.tsx index e82b89a6..e10a66cd 100644 --- a/src/requests/getMatches.tsx +++ b/src/requests/getMatches.tsx @@ -1,6 +1,8 @@ import { DATA_URL, PROCEDURES } from 'config' import { callApi, getResponseData } from 'helpers' +import { MatchStatuses } from 'features/HeaderFilters' + const proc = PROCEDURES.get_matches export type Item = { @@ -29,12 +31,14 @@ export type Team = { type Args = { date: string, + matchStatus: MatchStatuses, sportType: number, tournamentId: number, } export const getMatches = ({ date, + matchStatus, sportType, tournamentId, }: Args): Promise> => { @@ -43,6 +47,7 @@ export const getMatches = ({ params: { _p_date: date, _p_sport: sportType, + _p_stream_status: matchStatus, _p_tournament_id: tournamentId, }, proc,