Фильтры в каталоге, интеграция
This commit is contained in:
parent
7f6c6d1107
commit
b45f9885ab
|
|
@ -203,6 +203,12 @@ export default function CatalogPage() {
|
|||
params.set("arrivalTime", filters.arrivalTime);
|
||||
}
|
||||
|
||||
// Сохраняем сортировку, если она установлена
|
||||
const sortByPrice = searchParams.get("sortByPrice");
|
||||
if (sortByPrice) {
|
||||
params.set("sortByPrice", sortByPrice);
|
||||
}
|
||||
|
||||
// Обновляем URL без прокрутки страницы
|
||||
const newUrl = params.toString()
|
||||
? `${pathname}?${params.toString()}`
|
||||
|
|
@ -219,11 +225,29 @@ export default function CatalogPage() {
|
|||
|
||||
useEffect(() => {
|
||||
(async () => {
|
||||
const params: Record<string, string> = {
|
||||
const allParams: Record<string, string> = {
|
||||
search: searchParams.get("search") ?? "",
|
||||
minLength: searchParams.get("lengthMin") ?? "",
|
||||
maxLength: searchParams.get("lengthMax") ?? "",
|
||||
minPrice: searchParams.get("priceMin") ?? "",
|
||||
maxPrice: searchParams.get("priceMax") ?? "",
|
||||
minYear: searchParams.get("yearMin") ?? "",
|
||||
maxYear: searchParams.get("yearMax") ?? "",
|
||||
guests: searchParams.get("adults") && searchParams.get("children") ? `${Number(searchParams.get("adults")) + Number(searchParams.get("children"))}` : "",
|
||||
paymentType: searchParams.get("paymentType") ?? "",
|
||||
quickBooking: searchParams.get("quickBooking") ?? "",
|
||||
hasToilet: searchParams.get("hasToilet") ?? "",
|
||||
date: searchParams.get("date") ?? "",
|
||||
departureTime: searchParams.get("departureTime") ?? "",
|
||||
arrivalTime: searchParams.get("arrivalTime") ?? "",
|
||||
sortByPrice: searchParams.get("sortByPrice") ?? "",
|
||||
};
|
||||
|
||||
const response = await client.get<CatalogFilteredResponseDto>("/catalog/filtered/", {
|
||||
const params = Object.fromEntries(
|
||||
Object.entries(allParams).filter(([_, value]) => value !== "")
|
||||
);
|
||||
|
||||
const response = await client.get<CatalogFilteredResponseDto>("/catalog/filter/", {
|
||||
params,
|
||||
});
|
||||
|
||||
|
|
@ -346,7 +370,21 @@ export default function CatalogPage() {
|
|||
<div className="text-base text-[#999999]">
|
||||
Сортировка:
|
||||
</div>
|
||||
<Select defaultValue="default">
|
||||
<Select
|
||||
value={searchParams.get("sortByPrice") || "default"}
|
||||
onValueChange={(value) => {
|
||||
const params = new URLSearchParams(searchParams.toString());
|
||||
if (value === "default") {
|
||||
params.delete("sortByPrice");
|
||||
} else {
|
||||
params.set("sortByPrice", value);
|
||||
}
|
||||
const newUrl = params.toString()
|
||||
? `${pathname}?${params.toString()}`
|
||||
: pathname;
|
||||
router.replace(newUrl, { scroll: false });
|
||||
}}
|
||||
>
|
||||
<SelectTrigger
|
||||
className="w-full"
|
||||
variant="ghost"
|
||||
|
|
@ -357,18 +395,12 @@ export default function CatalogPage() {
|
|||
<SelectItem value="default">
|
||||
По умолчанию
|
||||
</SelectItem>
|
||||
<SelectItem value="price-asc">
|
||||
<SelectItem value="asc">
|
||||
Цена: по возрастанию
|
||||
</SelectItem>
|
||||
<SelectItem value="price-desc">
|
||||
<SelectItem value="desc">
|
||||
Цена: по убыванию
|
||||
</SelectItem>
|
||||
<SelectItem value="length-asc">
|
||||
Длина: по возрастанию
|
||||
</SelectItem>
|
||||
<SelectItem value="length-desc">
|
||||
Длина: по убыванию
|
||||
</SelectItem>
|
||||
</SelectContent>
|
||||
</Select>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -12,6 +12,9 @@ import Link from "next/link";
|
|||
export default function Hero() {
|
||||
const [adults, setAdults] = useState<number>(0);
|
||||
const [children, setChildren] = useState<number>(0);
|
||||
const [selectedDate, setSelectedDate] = useState<Date | null>(null);
|
||||
const [departureTime, setDepartureTime] = useState<string>("12:00");
|
||||
const [arrivalTime, setArrivalTime] = useState<string>("13:00");
|
||||
return (
|
||||
<section className="relative h-[600px] rounded-[24px] mx-[16px] overflow-hidden flex text-white">
|
||||
<Image
|
||||
|
|
@ -63,7 +66,14 @@ export default function Hero() {
|
|||
|
||||
{/* Дата и время */}
|
||||
<div className="flex-1">
|
||||
<DatePicker />
|
||||
<DatePicker
|
||||
value={selectedDate || undefined}
|
||||
departureTime={departureTime}
|
||||
arrivalTime={arrivalTime}
|
||||
onDateChange={(date) => setSelectedDate(date || null)}
|
||||
onDepartureTimeChange={setDepartureTime}
|
||||
onArrivalTimeChange={setArrivalTime}
|
||||
/>
|
||||
</div>
|
||||
|
||||
{/* Количество гостей */}
|
||||
|
|
@ -79,9 +89,20 @@ export default function Hero() {
|
|||
</div>
|
||||
|
||||
{/* Кнопка поиска */}
|
||||
<Button variant="gradient" className="font-bold text-white h-[64px] w-[176px] px-8">
|
||||
Найти
|
||||
</Button>
|
||||
<Link href={(() => {
|
||||
const params = new URLSearchParams();
|
||||
if (adults > 0) params.append('adults', adults.toString());
|
||||
if (children > 0) params.append('children', children.toString());
|
||||
if (selectedDate) params.append('date', selectedDate.toString());
|
||||
if (departureTime && departureTime !== "12:00") params.append('departureTime', departureTime);
|
||||
if (arrivalTime && arrivalTime !== "13:00") params.append('arrivalTime', arrivalTime);
|
||||
const queryString = params.toString();
|
||||
return queryString ? `/catalog?${queryString}` : '/catalog';
|
||||
})()}>
|
||||
<Button variant="gradient" className="font-bold text-white h-[64px] w-[176px] px-8">
|
||||
Найти
|
||||
</Button>
|
||||
</Link>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
|
|
|
|||
|
|
@ -42,6 +42,9 @@ export function DatePicker({
|
|||
const [internalArrivalTime, setInternalArrivalTime] = React.useState("13:00");
|
||||
const [open, setOpen] = React.useState(false);
|
||||
|
||||
// Определяем, является ли компонент контролируемым
|
||||
const isControlled = value !== undefined || externalDepartureTime !== undefined || externalArrivalTime !== undefined;
|
||||
|
||||
// Используем внешние значения, если они предоставлены, иначе внутренние
|
||||
const date = value !== undefined ? (value || undefined) : internalDate;
|
||||
const departureTime = externalDepartureTime !== undefined ? externalDepartureTime : internalDepartureTime;
|
||||
|
|
@ -50,7 +53,7 @@ export function DatePicker({
|
|||
const handleDateChange = (newDate: Date | undefined) => {
|
||||
if (onDateChange) {
|
||||
onDateChange(newDate);
|
||||
} else {
|
||||
} else if (!isControlled) {
|
||||
setInternalDate(newDate);
|
||||
}
|
||||
};
|
||||
|
|
@ -58,7 +61,7 @@ export function DatePicker({
|
|||
const handleDepartureTimeChange = (time: string) => {
|
||||
if (onDepartureTimeChange) {
|
||||
onDepartureTimeChange(time);
|
||||
} else {
|
||||
} else if (!isControlled) {
|
||||
setInternalDepartureTime(time);
|
||||
}
|
||||
};
|
||||
|
|
@ -66,7 +69,7 @@ export function DatePicker({
|
|||
const handleArrivalTimeChange = (time: string) => {
|
||||
if (onArrivalTimeChange) {
|
||||
onArrivalTimeChange(time);
|
||||
} else {
|
||||
} else if (!isControlled) {
|
||||
setInternalArrivalTime(time);
|
||||
}
|
||||
};
|
||||
|
|
|
|||
Loading…
Reference in New Issue