diff --git a/src/App.jsx b/src/App.jsx index aba6429..8753075 100644 --- a/src/App.jsx +++ b/src/App.jsx @@ -35,7 +35,7 @@ import Filter from "./components/Filter" import RadioFilter from "./components/Filter/RadioFilter" import KeywordFilter from "./components/Filter/KeywordFilter" import AgeFilter from "./components/Filter/AgeFilter" -import StarttimeEndtimeDayFilter from "./components/Filter/StarttimeEndtimeDay" +import StarttimeEndtimeDayFilter from "./components/Filter/StarttimeEndtimeDayFilter" import ListMap from "./components/ListMap" import ListMapStatic from "./components/ListMapStatic" import Pagination from "./components/Pagination" @@ -44,6 +44,7 @@ import { theme } from "./themes/theme_generator" import ClearFilters from "./components/ClearFilters" import { checkCookiesAccepted } from "./lib/cookies" import AlertStatic from "./components/AlertStatic" +import ScheduleFilter from "./components/Filter/ScheduleFilter" const App = ({ children, location, navigate }) => { const [keywords, setKeywords] = useQuery("keywords", "") @@ -69,6 +70,9 @@ const App = ({ children, location, navigate }) => { const [suitabilities, setSuitabilities] = useQuery("suitabilities", [], { array: true, }) + const [schedule, setSchedule] = useQuery("schedule", false) + const [startDate, setStartDate] = useQuery("start_date", false) + const [endDate, setEndDate] = useQuery("end_date", false) const [days, setDays] = useQuery("days", [], { array: true }) const [startTime, setStartTime] = useQuery("start_time", [], { array: true }) const [endTime, setEndTime] = useQuery("end_time", [], { array: true }) @@ -288,7 +292,7 @@ const App = ({ children, location, navigate }) => { /> ) - const filterStarttimeEndTimeDay = daysOptions.length > 0 && ( + const filterStarttimeEndTimeDay = ( { /> ) + const filterSchedule = ( + + ) + const filterSuitabilities = suitabilityOptions.length > 0 && ( { clear: [setStartTime, setEndTime, setDay], clearValue: [[], [], []], }, + schedule: { + component: filterSchedule, + clear: [setSchedule, setStartDate, setEndDate], + clearValue: [false, false, false], + }, suitabilities: { component: filterSuitabilities, clear: [setSuitabilities], diff --git a/src/components/DetailDialog/index.jsx b/src/components/DetailDialog/index.jsx index deed225..ef3760f 100644 --- a/src/components/DetailDialog/index.jsx +++ b/src/components/DetailDialog/index.jsx @@ -374,15 +374,15 @@ const DetailDialog = ({ serviceId, location, navigate }) => { /> )} {Object.entries(location_regular_schedules).map( - ([location_id, location]) => ( + ([location_id, l]) => ( v.dtstart === null )} /> @@ -396,15 +396,15 @@ const DetailDialog = ({ serviceId, location, navigate }) => { /> )}{" "} {Object.entries(location_regular_schedules).map( - ([location_id, location]) => ( + ([location_id, l]) => ( v.dtstart !== null )} /> diff --git a/src/components/Filter/ScheduleFilter.jsx b/src/components/Filter/ScheduleFilter.jsx new file mode 100644 index 0000000..3dd0858 --- /dev/null +++ b/src/components/Filter/ScheduleFilter.jsx @@ -0,0 +1,169 @@ +import React, { useState } from "react" +import styled from "styled-components" +import { + Outer, + Legend, + Header, + UnfoldButton, + Content, + RadioLabel, + RadioField, + InputRadio, +} from "./layout" + +const ColumnContent = styled(Content)` + display: grid; + grid-template-columns: 1fr 1fr; + grid-gap: 25px; + border-bottom: 0; +` + +const ColumnField = styled.div` + margin-bottom: 25px; + @supports (display: grid) { + margin-bottom: 0px; + } +` + +const LabelWithMargin = styled.label` + color: ${props => props.theme.styles.text}; + cursor: pointer; + display: block; + margin-bottom: 7px; +` + +const Input = styled.input` + font-size: 0.9rem; + padding: 7px; + border: 2px solid ${props => props.theme.styles.text}; + display: block; + width: 100%; + &:focus { + outline: 3px solid ${props => props.theme.styles.focus}; + } + &::placeholder { + opacity: 0.3; + } +` +const scheduleOptions = [ + ["Today", "today"], + ["Tomorrow", "tomorrow"], + ["Next 7 Days", "next7Days"], + ["Next 30 Days", "next30Days"], +] + +const today = new Date() +const tomorrow = new Date(today) +tomorrow.setDate(today.getDate() + 1) + +const next7DaysStart = new Date(today) +const next7DaysEnd = new Date(today) +next7DaysEnd.setDate(today.getDate() + 7) + +const next30DaysStart = new Date(today) +const next30DaysEnd = new Date(today) +next30DaysEnd.setDate(today.getDate() + 30) + +const scheduleOptionValues = { + today: { + startDate: today, + endDate: today, + }, + tomorrow: { + startDate: tomorrow, + endDate: tomorrow, + }, + next7Days: { + startDate: next7DaysStart, + endDate: next7DaysEnd, + }, + next30Days: { + startDate: next30DaysStart, + endDate: next30DaysEnd, + }, +} + +const ScheduleFilter = ({ + legend, + schedule, + startDate, + endDate, + setSchedule, + setStartDate, + setEndDate, + setPage, + foldable, +}) => { + const [unfolded, setUnfolded] = useState(schedule) + + const handleScheduleChange = e => { + const selectedSchedule = e.target.value + setSchedule(selectedSchedule) + const scheduleValues = scheduleOptionValues[selectedSchedule] + if (scheduleValues) { + setStartDate(scheduleValues.startDate.toISOString().split("T")[0]) + setEndDate(scheduleValues.endDate.toISOString().split("T")[0]) + } + setPage(1) + } + + return ( + +
+ {foldable ? ( + setUnfolded(!unfolded)} + > + {legend} + + ) : ( + {legend} + )} +
+ {(!foldable || unfolded) && ( + <> + + {scheduleOptions.map(([label, slug], i) => ( + + + {label} + + ))} + + + + From + setStartDate(e.target.value)} + value={startDate} + type="date" + /> + + + To + setEndDate(e.target.value)} + value={endDate} + type="date" + /> + + + + + )} +
+ ) +} + +export default ScheduleFilter diff --git a/src/components/Filter/StarttimeEndtimeDay.jsx b/src/components/Filter/StarttimeEndtimeDayFilter.jsx similarity index 94% rename from src/components/Filter/StarttimeEndtimeDay.jsx rename to src/components/Filter/StarttimeEndtimeDayFilter.jsx index 25b396a..3eb224a 100644 --- a/src/components/Filter/StarttimeEndtimeDay.jsx +++ b/src/components/Filter/StarttimeEndtimeDayFilter.jsx @@ -138,9 +138,9 @@ const AllFieldsForm = ({ ))} - Opens at + Opens at - Closes at + Closes at { const [unfolded, setUnfolded] = useState( - startTime || endTime || day.length > 0 + startTime.length > 0 || endTime.length > 0 || day.length > 0 ) return ( diff --git a/src/lib/api.js b/src/lib/api.js index 5fdb786..779a057 100644 --- a/src/lib/api.js +++ b/src/lib/api.js @@ -101,6 +101,8 @@ export const fetchServiceDataFromApi = async ( needs, accessibilities, suitabilities, + start_date, + end_date, days, start_time, end_time, @@ -125,6 +127,8 @@ export const fetchServiceDataFromApi = async ( needs, accessibilities, suitabilities, + start_date, + end_date, days, start_time, end_time, diff --git a/src/lib/order-filters.js b/src/lib/order-filters.js index c4c73a3..fd16307 100644 --- a/src/lib/order-filters.js +++ b/src/lib/order-filters.js @@ -25,6 +25,9 @@ export const orderFilters = (filters, filterOrder) => { case "starttime-endtime-day": output.push(filters.startTimeEndTimeDay.component) break + case "schedule": + output.push(filters.schedule.component) + break case "suitabilities": output.push(filters.suitabilities.component) break diff --git a/src/themes/bfis/vars_bfis.jsx b/src/themes/bfis/vars_bfis.jsx index cea7409..e0c301f 100644 --- a/src/themes/bfis/vars_bfis.jsx +++ b/src/themes/bfis/vars_bfis.jsx @@ -143,6 +143,10 @@ export const vars_bfis = { order: 4, name: "starttime-endtime-day", }, + { + order: 5, + name: "schedule", + }, ], headerComponents: (