diff --git a/app/listings/filter-beds-baths.tsx b/app/listings/filter-beds-baths.tsx index 36d1c47a..1f98fc12 100644 --- a/app/listings/filter-beds-baths.tsx +++ b/app/listings/filter-beds-baths.tsx @@ -1,14 +1,25 @@ -import ButtonsSegmentedLabelled from "@/components/buttons-segmented/labelled"; -import ButtonSmallFilled from "@/components/buttons/small/filled"; -import ButtonSmallText from "@/components/buttons/small/text"; -import Dropdown from "@/components/dropdown"; +"use client" + +import ButtonsSegmentedLabelled from "@/components/buttons-segmented/labelled" +import ButtonSmallFilled from "@/components/buttons/small/filled" +import ButtonSmallText from "@/components/buttons/small/text" +import Dropdown from "@/components/dropdown" +import { useState } from "react" export default function ListingsFiltersBedsBaths() { - const bedsBathsOptions = ["Any", "1", "2", "3", "4", "5+"]; + const bedsBathsOptions = ["Any", "1", "2", "3", "4", "5+"] + + const [displayDropdown, setDisplayDropdown] = useState(false) return (
- + { + setDisplayDropdown(!displayDropdown) + } + }}>
(PRICE_MIN_FILTER); - const [maxPrice, setMaxPrice] = useState(PRICE_MAX_FILTER); + const [minPrice, setMinPrice] = useState(PRICE_MIN_FILTER) + const [maxPrice, setMaxPrice] = useState(PRICE_MAX_FILTER) - const [minPriceError, setMinPriceError] = useState(undefined); - const [maxPriceError, setMaxPriceError] = useState(undefined); + const [minPriceError, setMinPriceError] = useState(undefined) + const [maxPriceError, setMaxPriceError] = useState(undefined) - const defaultValidator = customizePriceValidator(PRICE_MIN_FILTER, PRICE_MAX_FILTER); - const [minPriceValidator, setMinPriceValidator] = useState(defaultValidator); - const [maxPriceValidator, setMaxPriceValidator] = useState(defaultValidator); + const defaultValidator = customizePriceValidator(PRICE_MIN_FILTER, PRICE_MAX_FILTER) + const [minPriceValidator, setMinPriceValidator] = useState(defaultValidator) + const [maxPriceValidator, setMaxPriceValidator] = useState(defaultValidator) - const context = useContext(ListingsContext); + const context = useContext(ListingsContext) + const [displayDropdown, setDisplayDropdown] = useState(false) return (
- + { + setDisplayDropdown(!displayDropdown) + } + }}>
{ - const value = NumberUtils.toNumber(e.target.value, -1); - const result = minPriceValidator.safeParse(value); + const value = NumberUtils.toNumber(e.target.value, -1) + const result = minPriceValidator.safeParse(value) if (result.success) { // Only clear existing error messages @@ -55,7 +64,7 @@ export default function ListingsFilterPrice() { // Only change if it is a different error message const error = result.error.errors[0].message if (minPriceError !== error) { - setMinPriceError(error); + setMinPriceError(error) } } }} /> @@ -68,8 +77,8 @@ export default function ListingsFilterPrice() { max={PRICE_MAX_FILTER} errorMessage={maxPriceError} onChange={(e) => { - const value = NumberUtils.toNumber(e.target.value, -1); - const result = maxPriceValidator.safeParse(value); + const value = NumberUtils.toNumber(e.target.value, -1) + const result = maxPriceValidator.safeParse(value) if (result.success) { // Only clear existing error messages @@ -84,7 +93,7 @@ export default function ListingsFilterPrice() { // Only change if it is a different error message const error = result.error.errors[0].message if (maxPriceError !== error) { - setMaxPriceError(error); + setMaxPriceError(error) } } }} /> @@ -105,11 +114,12 @@ export default function ListingsFilterPrice() { }} /> { - // TODO: Close dropdown ... + // Close dropdown ... + setDisplayDropdown(false) // ... change filter values - context.searchFilters.price.min.change(minPrice); - context.searchFilters.price.max.change(maxPrice); + context.searchFilters.price.min.change(minPrice) + context.searchFilters.price.max.change(maxPrice) }} />
diff --git a/app/listings/filters-area.tsx b/app/listings/filters-area.tsx index 9e397294..ef04553c 100644 --- a/app/listings/filters-area.tsx +++ b/app/listings/filters-area.tsx @@ -1,18 +1,29 @@ -import ButtonSmallFilled from "@/components/buttons/small/filled"; -import ButtonSmallText from "@/components/buttons/small/text"; -import Dropdown from "@/components/dropdown"; -import FormInput from "@/components/form-input"; -import { formatAppend } from "@/lib/formatter/number"; +"use client" + +import ButtonSmallFilled from "@/components/buttons/small/filled" +import ButtonSmallText from "@/components/buttons/small/text" +import Dropdown from "@/components/dropdown" +import FormInput from "@/components/form-input" +import { formatAppend } from "@/lib/formatter/number" +import { useState } from "react" export default function ListingsFilterArea() { - const DEFAULT_MAX = 20; + const DEFAULT_MAX = 20 + + const minAreaPlaceholder = "None" + const maxAreaPlaceholder = formatAppend(DEFAULT_MAX, "sqm.") - const minAreaPlaceholder = "None"; - const maxAreaPlaceholder = formatAppend(DEFAULT_MAX, "sqm."); + const [displayDropdown, setDisplayDropdown] = useState(false) return (
- + { + setDisplayDropdown(!displayDropdown) + } + }}>
void } export default function Dropdown({ children, props }: { children: ReactNode, props: DropdownProps }) { - const [display, setDisplay] = useState(false); - return (
{ - setDisplay(!display); + if (props.onClick) { + props.onClick() + } } }}> {/* NOTE: Width can be customized by the child component */} - {display && + {props.display &&
{children}
} diff --git a/stories/dropdown/Dropdown.stories.tsx b/stories/dropdown/Dropdown.stories.tsx index e47180af..55ee233a 100644 --- a/stories/dropdown/Dropdown.stories.tsx +++ b/stories/dropdown/Dropdown.stories.tsx @@ -11,7 +11,7 @@ const meta: Meta = { export default meta; type Story = StoryObj; -export const Default: Story = { +export const Closed: Story = { args: { props: { text: "Filters", @@ -30,3 +30,24 @@ export const Default: Story = { ), }; + +export const Open: Story = { + args: { + props: { + text: "Filters", + display: true + }, + }, + render: (args) => ( + +
+ + +
+
+ ), +};