diff --git a/frontend/components/DailyTabs.tsx b/frontend/components/DailyTabs.tsx index 2a1eb154..85b1fd83 100644 --- a/frontend/components/DailyTabs.tsx +++ b/frontend/components/DailyTabs.tsx @@ -5,7 +5,9 @@ import Box from '@mui/material/Box'; import TimeComponent from './TimeComponent'; -import { UniqueFilter } from '@/helpers/getData'; +import { DailyTabs } from '@/interfaces/Components'; + +import { tournamentFilterOptions } from '@/pages'; interface TabPanelProps { children?: ReactNode; @@ -40,23 +42,16 @@ function a11yProps(index: number) { }; } -interface DailyTabs { - allBaseFilters: number[]; - showOnly: Array; - dateList: UniqueFilter; - hideSoldOut: boolean; - soldOutEvents: number[]; - earlyStartTime: string; - lateStartTime: string; - startTimes: UniqueFilter; -} - export default function DailyTabs({ allBaseFilters, showOnly, dateList, + hideMaterialReq, hideSoldOut, + materialsRequired, soldOutEvents, + tournamentFilter, + tourneyList, earlyStartTime, lateStartTime, startTimes @@ -73,10 +68,22 @@ export default function DailyTabs({ var eventsForDay = dayEvents.filter(val => !allBaseFilters.includes(val)); + if (hideMaterialReq) { + eventsForDay = eventsForDay.filter(val => !materialsRequired.includes(val)); + } + if (hideSoldOut) { eventsForDay = eventsForDay.filter(val => !soldOutEvents.includes(val)); } + if (tournamentFilter === tournamentFilterOptions[1]) { + eventsForDay = eventsForDay.filter(val => tourneyList.includes(val)) + } + + if (tournamentFilter === tournamentFilterOptions[2]) { + eventsForDay = eventsForDay.filter(val => !tourneyList.includes(val)) + } + timeLabels.map(timeLabel => { if (timeLabel < earlyStartTime || timeLabel > lateStartTime) { var events = startTimes[timeLabel] diff --git a/frontend/components/EventModal.tsx b/frontend/components/EventModal.tsx index 485221ec..27d10f09 100644 --- a/frontend/components/EventModal.tsx +++ b/frontend/components/EventModal.tsx @@ -1,5 +1,5 @@ import { Dispatch, SetStateAction } from 'react'; -import { NewEvent } from '@/helpers/getData'; +import { NewEvent } from '@/interfaces/Events'; import Box from '@mui/material/Box'; import Modal from '@mui/material/Modal'; import ConfirmationNumberIcon from '@mui/icons-material/ConfirmationNumber'; @@ -78,6 +78,10 @@ export default function BasicModal({ {event.group && } {event.location && } + {event.materialsRequired && ( + + )} + diff --git a/frontend/components/FilterAutoList.tsx b/frontend/components/FilterAutoList.tsx index 6e1d5cbd..8cdf2504 100644 --- a/frontend/components/FilterAutoList.tsx +++ b/frontend/components/FilterAutoList.tsx @@ -1,8 +1,7 @@ import { Dispatch, SetStateAction } from 'react'; import Autocomplete from '@mui/material/Autocomplete'; import TextField from '@mui/material/TextField'; - -import { UniqueFilter } from '@/helpers/getData'; +import { UniqueFilter } from '@/interfaces/Filters'; interface FilterAutoList { filter: UniqueFilter, diff --git a/frontend/components/FilterButtons.tsx b/frontend/components/FilterButtons.tsx index 958e5f8c..8858d80c 100644 --- a/frontend/components/FilterButtons.tsx +++ b/frontend/components/FilterButtons.tsx @@ -1,6 +1,6 @@ import { Dispatch, SetStateAction, useState } from 'react'; -import { UniqueFilter } from '@/helpers/getData'; +import { UniqueFilter } from '@/interfaces/Filters'; export default function FilterButtons({ filter, diff --git a/frontend/components/RadioGroup.tsx b/frontend/components/RadioGroup.tsx new file mode 100644 index 00000000..59f9dfe0 --- /dev/null +++ b/frontend/components/RadioGroup.tsx @@ -0,0 +1,42 @@ +import { ChangeEvent } from 'react'; +import Radio from '@mui/material/Radio'; +import RadioGroup from '@mui/material/RadioGroup'; +import FormControlLabel from '@mui/material/FormControlLabel'; +import FormControl from '@mui/material/FormControl'; + +import { RadioGroupInterface } from '@/interfaces/Components'; + +export default function RadioButtonsGroup({ + formLabel, + options, + setValue, + value +}: RadioGroupInterface) { + + const handleChange = (event: ChangeEvent) => { + setValue((event.target as HTMLInputElement).value); + }; + + return ( +
+ + {formLabel} + + {options.map(option => ( + } + label={option} + /> + ))} + + +
+ ); +} diff --git a/frontend/components/SwitchComponent.tsx b/frontend/components/SwitchComponent.tsx index c6aa894e..4dd323b5 100644 --- a/frontend/components/SwitchComponent.tsx +++ b/frontend/components/SwitchComponent.tsx @@ -1,13 +1,7 @@ -import { Dispatch, SetStateAction } from 'react'; import Switch from '@mui/material/Switch'; +import { SwitchInterface } from '@/interfaces/Components'; -interface Switch { - switchLabel: string; - hide: boolean; - setHide: Dispatch>; -} - -export default function SwitchComponent({ switchLabel, hide, setHide }: Switch) { +export default function SwitchComponent({ switchLabel, hide, setHide }: SwitchInterface) { const aria = { inputProps: { 'aria-label': `${switchLabel} Switch` } }; const label = hide ? `Show ${switchLabel}` : `Hide ${switchLabel}`; @@ -18,7 +12,8 @@ export default function SwitchComponent({ switchLabel, hide, setHide }: Switch) return (
- {label} + {label} +
); diff --git a/frontend/components/TimeRange.tsx b/frontend/components/TimeRange.tsx index 8a9913f0..bb5048e8 100644 --- a/frontend/components/TimeRange.tsx +++ b/frontend/components/TimeRange.tsx @@ -30,7 +30,7 @@ export default function TimeRange({ return (
- Start Time Range: {earlyStartTime} - {lateStartTime} + Start Time Range:
-} - -interface TournamentFilter { - true: Array, - false: Array -} - -export interface FilterTypes { - groups: UniqueFilter, - eventTypes: UniqueFilter, - gameSystems: UniqueFilter, - ageRequirements: UniqueFilter, - experienceRequirements: UniqueFilter, - startDates: UniqueFilter, - startTimes: UniqueFilter, - endDates: UniqueFilter, - endTimes: UniqueFilter, - tournament: Array, - costs: UniqueFilter, - locations: UniqueFilter, - noTickets: Array -} - -interface Data { - eventData: Array, - filters: FilterTypes -} +import { NewEvent, RawEvent } from '@/interfaces/Events'; +import { Data } from '@/interfaces/Data'; const getTime = (time: Date) => { const hours = time.getHours(); @@ -106,16 +21,15 @@ const isTournament = (eventTournament: string) => { return false; } -const toTitleCase = (str: string) => { - return str.replace( - /\w\S*/g, - function(txt) { - return txt.charAt(0).toUpperCase() + txt.substr(1).toLowerCase(); - } - ); +const areMaterialsRequired = (materialsRequired: string) => { + if (materialsRequired === "Yes") { + return true; + } + + return false; } -const cleanData = (events: Array) => { +const cleanData = (events: Array) => { const data: Data = { eventData: [], filters: { @@ -129,6 +43,7 @@ const cleanData = (events: Array) => { endDates: {}, endTimes: {}, tournament: [], + materialsRequired: [], costs: {}, locations: {}, noTickets: [] @@ -153,6 +68,8 @@ const cleanData = (events: Array) => { endTime: '', duration: 0, tournament: false, + materialsRequired: false, + materials: '', cost: 0, location: '', ticketsAvailable: 0, @@ -173,7 +90,9 @@ const cleanData = (events: Array) => { const eventStartTime = getTime(rawStart); const eventEndDate = rawEnd.toLocaleDateString(); const eventEndTime = getTime(rawEnd); - const isTourny = isTournament(event["Tournament?"]); + const isTourney = isTournament(event["Tournament?"]); + const materialsRequired = areMaterialsRequired(event["Materials Required"]); + const materials = event["Materials Required Details"]; const eventCost = Number(event["Cost $"]); const eventLocation = event["Location"]?.toUpperCase(); const eventTickets = Number(event["Tickets Available"]); @@ -271,10 +190,17 @@ const cleanData = (events: Array) => { newEvent.endTime = eventEndTime; // Tournament - if (isTourny) { + if (isTourney) { data.filters.tournament.push(index); }; - newEvent.tournament = isTourny; + newEvent.tournament = isTourney; + + // Tournament + if (materialsRequired) { + data.filters.materialsRequired.push(index); + newEvent.materials = materials; + }; + newEvent.materialsRequired = materialsRequired; // Costs if (!data.filters.costs[eventCost]) { @@ -305,7 +231,7 @@ const cleanData = (events: Array) => { }; export default function getData() { - const rawData = Events as Array; + const rawData = Events as Array; const data = cleanData(rawData); diff --git a/frontend/interfaces/Components.tsx b/frontend/interfaces/Components.tsx new file mode 100644 index 00000000..d912068f --- /dev/null +++ b/frontend/interfaces/Components.tsx @@ -0,0 +1,37 @@ +import { Dispatch, SetStateAction } from 'react'; +import { UniqueFilter } from './Filters'; + +export interface DailyTabs { + allBaseFilters: number[]; + showOnly: Array; + dateList: UniqueFilter; + hideMaterialReq: boolean; + hideSoldOut: boolean; + materialsRequired: number[]; + soldOutEvents: number[]; + tournamentFilter: string; + tourneyList: number[]; + earlyStartTime: string; + lateStartTime: string; + startTimes: UniqueFilter; +} + +export interface RadioGroupInterface { + formLabel: string; + options: string[]; + setValue: Dispatch>; + value?: string; +} + +export interface SwitchInterface { + switchLabel: string; + hide: boolean; + setHide: Dispatch>; +} + +export interface TournamentSwitches { + hideTourney: boolean; + setHideTourney: Dispatch>; + tourneyOnly: boolean; + setTourneyOnly: Dispatch>; +} \ No newline at end of file diff --git a/frontend/interfaces/Data.tsx b/frontend/interfaces/Data.tsx new file mode 100644 index 00000000..a1588562 --- /dev/null +++ b/frontend/interfaces/Data.tsx @@ -0,0 +1,7 @@ +import { FilterTypes } from "@/interfaces/Filters" +import { NewEvent } from "@/interfaces/Events" + +export interface Data { + eventData: Array, + filters: FilterTypes +} \ No newline at end of file diff --git a/frontend/interfaces/Events.tsx b/frontend/interfaces/Events.tsx new file mode 100644 index 00000000..d0b2f4b5 --- /dev/null +++ b/frontend/interfaces/Events.tsx @@ -0,0 +1,75 @@ +export interface filterEvents { + groups: number[]; + eventTypes: number[]; + gameSystems: number[]; + ageRequirements: number[]; + experienceRequirements: number[]; + startDates: number[]; + startTimes: number[]; + endDates: number[]; + endTimes: number[]; + ifTournament: number[]; + costs: number[]; + locations: number[]; + ticketsAvailable: number[]; +} + +export interface NewEvent { + id: number; + gameId: string; + group?: string; + title: string; + shortDescription?: string; + longDescription?: string; + eventType: string; + gameSystem?: string; + ageRequirement: string; + experienceRequirement: string; + startDate: string; + startTime: string; + endDate: string; + endTime: string; + duration: number; + tournament: boolean; + materialsRequired: boolean; + materials?: string; + cost: number; + location?: string; + ticketsAvailable?: number; + maxTickets?: number; +} + +export interface RawEvent { + 'Game ID': string; + Group?: string; + Title: string; + 'Short Description'?: string; + 'Long Description'?: string; + 'Event Type': string; + 'Game System'?: string; + 'Rules Edition'?: string; + 'Minimum Players'?: string; + 'Maximum Players'?: string; + 'Age Required': string; + 'Experience Required': string; + 'Materials Required': string; + 'Materials Required Details'?: string; + 'Start Date & Time': string; + Duration?: string; + 'End Date & Time': string; + 'GM Names'?: string; + Website?: string; + Email?: string; + 'Tournament?': 'No'; + 'Round Number'?: string; + 'Total Rounds'?: string; + 'Minimum Play Time'?: string; + 'Attendee Registration?'?: string; + 'Cost $': string; + Location?: string; + 'Room Name'?: string; + 'Table Number'?: ''; + 'Special Category'?: string; + 'Tickets Available'?: string; + 'Last Modified': string; +} \ No newline at end of file diff --git a/frontend/interfaces/Filters.tsx b/frontend/interfaces/Filters.tsx new file mode 100644 index 00000000..9199ce68 --- /dev/null +++ b/frontend/interfaces/Filters.tsx @@ -0,0 +1,20 @@ +export interface UniqueFilter { + [index: string]: Array; +} + +export interface FilterTypes { + groups: UniqueFilter; + eventTypes: UniqueFilter; + gameSystems: UniqueFilter; + ageRequirements: UniqueFilter; + experienceRequirements: UniqueFilter; + startDates: UniqueFilter; + startTimes: UniqueFilter; + endDates: UniqueFilter; + endTimes: UniqueFilter; + tournament: Array; + materialsRequired: Array; + costs: UniqueFilter; + locations: UniqueFilter; + noTickets: Array; +} \ No newline at end of file diff --git a/frontend/interfaces/filterEvents.tsx b/frontend/interfaces/filterEvents.tsx deleted file mode 100644 index 5dda4fad..00000000 --- a/frontend/interfaces/filterEvents.tsx +++ /dev/null @@ -1,15 +0,0 @@ -export interface filterEvents { - groups: number[], - eventTypes: number[], - gameSystems: number[], - ageRequirements: number[], - experienceRequirements: number[], - startDates: number[], - startTimes: number[], - endDates: number[], - endTimes: number[], - ifTournament: number[], - costs: number[], - locations: number[], - ticketsAvailable: number[] -} \ No newline at end of file diff --git a/frontend/pages/index.tsx b/frontend/pages/index.tsx index aa9a9ba7..f46702c4 100644 --- a/frontend/pages/index.tsx +++ b/frontend/pages/index.tsx @@ -5,13 +5,21 @@ import getData from "@/helpers/getData"; import DailyTabs from "@/components/DailyTabs"; import FilterAutoList from "@/components/FilterAutoList"; import FilterButtons from "@/components/FilterButtons"; +import RadioGroup from "@/components/RadioGroup"; import Switch from "@/components/SwitchComponent"; import TimeRange from "@/components/TimeRange"; export const { eventData, filters } = getData(); +export const tournamentFilterOptions = [ + 'Show All Events', + 'Show Tournament Events Only', + 'Hide All Tournament Events' +] + export default function Home() { const filterList = filters; + console.log(filterList); // Lists const ageRequirements = filterList.ageRequirements; @@ -21,8 +29,10 @@ export default function Home() { const gameSystems = filterList.gameSystems; const groups = filterList.groups; const locations = filterList.locations; + const materialsRequired = filterList.materialsRequired; const soldOutEvents = filterList.noTickets; const startTimes = filterList.startTimes; + const tourneyList = filterList.tournament; // Filters const [ageFilters, setAgeFilters] = useState([]); @@ -34,8 +44,12 @@ export default function Home() { const [lateStartTime, setLateStartTime] = useState('23:45'); const [systemFilters, setSystemFilters] = useState([]); + // Radio Group + const [tournamentFilter, setTournamentFilter] = useState(tournamentFilterOptions[0]); + // Switches const [hideSoldOut, setHideSoldOut] = useState(false); + const [hideMaterialsReq, setHideMaterialsReq] = useState(false); return (
@@ -79,6 +93,17 @@ export default function Home() { hide={hideSoldOut} setHide={setHideSoldOut} /> + +