From 14567b32cbc355fbfc8ecba4f6ee09ec316594c7 Mon Sep 17 00:00:00 2001 From: Vasily Zubarev Date: Mon, 17 Mar 2025 19:20:12 +0100 Subject: [PATCH] feat: filters and UI improvements --- components/transactions/edit.tsx | 16 +++++---- components/transactions/filters.tsx | 18 +++++++++- hooks/use-transaction-filters.tsx | 53 +++++++++++++++-------------- 3 files changed, 54 insertions(+), 33 deletions(-) diff --git a/components/transactions/edit.tsx b/components/transactions/edit.tsx index 361a657..020f93b 100644 --- a/components/transactions/edit.tsx +++ b/components/transactions/edit.tsx @@ -53,10 +53,12 @@ export default function TransactionEditForm({ }) const handleDelete = async () => { - startTransition(async () => { - await deleteAction(transaction.id) - router.back() - }) + if (confirm("Are you sure? This will delete the transaction with all the files permanently")) { + startTransition(async () => { + await deleteAction(transaction.id) + router.back() + }) + } } useEffect(() => { @@ -146,9 +148,9 @@ export default function TransactionEditForm({ /> ))} -
+
diff --git a/components/transactions/filters.tsx b/components/transactions/filters.tsx index a21cb9e..bf12f1a 100644 --- a/components/transactions/filters.tsx +++ b/components/transactions/filters.tsx @@ -1,11 +1,13 @@ "use client" import { DateRangePicker } from "@/components/forms/date-range-picker" +import { Button } from "@/components/ui/button" import { Input } from "@/components/ui/input" import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select" import { TransactionFilters } from "@/data/transactions" -import { useTransactionFilters } from "@/hooks/use-transaction-filters" +import { isFiltered, useTransactionFilters } from "@/hooks/use-transaction-filters" import { Category, Project } from "@prisma/client" +import { X } from "lucide-react" export function TransactionSearchAndFilters({ categories, projects }: { categories: Category[]; projects: Project[] }) { const [filters, setFilters] = useTransactionFilters() @@ -79,6 +81,20 @@ export function TransactionSearchAndFilters({ categories, projects }: { categori handleFilterChange("dateTo", date ? date.to : undefined) }} /> + + {isFiltered(filters) && ( + + )}
) diff --git a/hooks/use-transaction-filters.tsx b/hooks/use-transaction-filters.tsx index 105a557..b35081a 100644 --- a/hooks/use-transaction-filters.tsx +++ b/hooks/use-transaction-filters.tsx @@ -3,14 +3,33 @@ import { format } from "date-fns" import { useRouter, useSearchParams } from "next/navigation" import { useEffect, useState } from "react" +const filters = ["search", "dateFrom", "dateTo", "categoryCode", "projectCode"] + +export function useTransactionFilters(defaultFilters?: TransactionFilters) { + const router = useRouter() + const searchParams = useSearchParams() + const [filters, setFilters] = useState({ + ...defaultFilters, + ...searchParamsToFilters(searchParams), + }) + + useEffect(() => { + const newSearchParams = filtersToSearchParams(filters) + router.push(`?${newSearchParams.toString()}`) + }, [filters]) + + useEffect(() => { + setFilters(searchParamsToFilters(searchParams)) + }, [searchParams]) + + return [filters, setFilters] as const +} + export function searchParamsToFilters(searchParams: URLSearchParams) { - return { - search: searchParams.get("search") || "", - dateFrom: searchParams.get("dateFrom") || "", - dateTo: searchParams.get("dateTo") || "", - categoryCode: searchParams.get("categoryCode") || "", - projectCode: searchParams.get("projectCode") || "", - } + return filters.reduce((acc, filter) => { + acc[filter] = searchParams.get(filter) || "" + return acc + }, {} as Record) } export function filtersToSearchParams(filters: TransactionFilters): URLSearchParams { @@ -48,22 +67,6 @@ export function filtersToSearchParams(filters: TransactionFilters): URLSearchPar return searchParams } -export function useTransactionFilters(defaultFilters?: TransactionFilters) { - const router = useRouter() - const searchParams = useSearchParams() - const [filters, setFilters] = useState({ - ...defaultFilters, - ...searchParamsToFilters(searchParams), - }) - - useEffect(() => { - const newSearchParams = filtersToSearchParams(filters) - router.push(`?${newSearchParams.toString()}`) - }, [filters]) - - useEffect(() => { - setFilters(searchParamsToFilters(searchParams)) - }, [searchParams]) - - return [filters, setFilters] as const +export function isFiltered(filters: TransactionFilters) { + return Object.values(filters).some((value) => value !== "" && value !== "-") }