Add initial project setup with PocketBase integration, global state management, and UI components for gift tracking
This commit is contained in:
91
src/components/molecules/GiftCard/index.tsx
Normal file
91
src/components/molecules/GiftCard/index.tsx
Normal file
@@ -0,0 +1,91 @@
|
||||
'use client';
|
||||
import { FC, useState } from 'react';
|
||||
import { formatCurrency } from '@/helpers/formatCurrency';
|
||||
import { formatStatus } from '@/helpers/formatStatus';
|
||||
import { GiftModal } from '../GiftModal';
|
||||
import { useGlobalStore } from '@/app/store/global';
|
||||
import { DB } from '@/lib/db';
|
||||
import { useRouter } from 'next/navigation';
|
||||
import { Button } from '@/components/atoms/Button';
|
||||
|
||||
type Props = {
|
||||
hideDetails?: boolean;
|
||||
editable?: boolean;
|
||||
personId?: string;
|
||||
};
|
||||
|
||||
export const GiftCard: FC<Gift & Props> = ({ hideDetails = false, editable = false, personId, ...gift }) => {
|
||||
const [isOpen, setIsOpen] = useState(false);
|
||||
const year = useGlobalStore((s) => s.year);
|
||||
const router = useRouter();
|
||||
|
||||
const { title, description, cost, status, created, expand } = gift;
|
||||
|
||||
const bgByStatus = {
|
||||
planned: 'bg-gray-100',
|
||||
decided: 'bg-blue-100',
|
||||
bought: 'bg-green-100',
|
||||
wrapped: 'bg-purple-100',
|
||||
};
|
||||
|
||||
const handleDelete = async () => {
|
||||
await DB.deleteGift(gift.id);
|
||||
router.refresh();
|
||||
};
|
||||
|
||||
return (
|
||||
<>
|
||||
<div
|
||||
className={`rounded-2xl shadow-sm p-4 my-6 md:p-6 transition-all duration-200 ease-in-out ${
|
||||
bgByStatus[status]
|
||||
} ${editable ? 'cursor-pointer hover:shadow-md ' : ''}`}
|
||||
onClick={editable ? () => setIsOpen(true) : undefined}>
|
||||
<div className='flex flex-col sm:flex-row sm:items-center sm:justify-between gap-4'>
|
||||
<div className='flex-1'>
|
||||
<div className='flex items-center justify-between gap-3 mb-2 pb-2 border-b border-gray-200'>
|
||||
<h3 className='text-lg font-semibold text-gray-800'>{title}</h3>
|
||||
</div>
|
||||
{description && <p className='text-base text-gray-600 mb-3'>{description}</p>}
|
||||
<div className='flex flex-wrap items-center gap-4 text-sm text-gray-500'>
|
||||
<span>Data dodania: {new Date(created).toLocaleDateString()}</span>
|
||||
<span>•</span>
|
||||
<span>Koszt: {formatCurrency(cost)}</span>
|
||||
{!hideDetails && (
|
||||
<>
|
||||
<span>•</span>
|
||||
<span>Dla: {expand?.person.name}</span>
|
||||
</>
|
||||
)}
|
||||
<span>•</span>
|
||||
<span>Status: {formatStatus(status)}</span>
|
||||
{editable && (
|
||||
<div className='ml-auto'>
|
||||
<Button
|
||||
variant='danger'
|
||||
onClick={(e) => {
|
||||
e.stopPropagation();
|
||||
handleDelete();
|
||||
}}>
|
||||
Usuń
|
||||
</Button>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<GiftModal
|
||||
isOpen={isOpen}
|
||||
onClose={() => setIsOpen(false)}
|
||||
yearId={year.id}
|
||||
personId={personId}
|
||||
gift={gift}
|
||||
onSave={async (data) => {
|
||||
await DB.updateGift(gift.id, data);
|
||||
router.refresh();
|
||||
}}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
};
|
||||
Reference in New Issue
Block a user