Add purchase link and reservation details to gift list
Enhanced the gift list by showing a clickable purchase link icon and added conditional reservation details for reserved or received items using a popover. Simplified and cleaned up related code for better readability and maintainability.
This commit is contained in:
@@ -6,16 +6,15 @@ import React, { useEffect, useState } from "react";
|
||||
import { useParams } from "next/navigation";
|
||||
import Link from "next/link";
|
||||
import {
|
||||
ChevronRight,
|
||||
Loader2,
|
||||
AlertTriangle,
|
||||
ChevronRight,
|
||||
Edit,
|
||||
ExternalLink,
|
||||
Loader2,
|
||||
MoreHorizontal,
|
||||
Plus,
|
||||
Search,
|
||||
Filter,
|
||||
Edit,
|
||||
Trash,
|
||||
MoreHorizontal,
|
||||
Settings,
|
||||
} from "lucide-react";
|
||||
import { useEvents } from "@/context/event-context";
|
||||
import { useGifts } from "@/context/gift-context";
|
||||
@@ -45,9 +44,14 @@ import {
|
||||
SelectTrigger,
|
||||
SelectValue,
|
||||
} from "@/components/ui/select";
|
||||
import { GiftStatus, GiftPriority } from "@/client/types.gen";
|
||||
import { GiftPriority, GiftStatus } from "@/client/types.gen";
|
||||
import { CategoryModal } from "@/components/gifts/category-modal";
|
||||
import { GiftModal } from "@/components/gifts/gift-modal";
|
||||
import {
|
||||
Popover,
|
||||
PopoverContent,
|
||||
PopoverTrigger,
|
||||
} from "@/components/ui/popover";
|
||||
|
||||
export default function GiftRegistryPage() {
|
||||
const { slug } = useParams<{ slug: string }>();
|
||||
@@ -57,6 +61,7 @@ export default function GiftRegistryPage() {
|
||||
items,
|
||||
isLoadingCategories,
|
||||
isLoadingItems,
|
||||
purchases,
|
||||
error,
|
||||
refetchCategories,
|
||||
refetchItems,
|
||||
@@ -387,19 +392,70 @@ export default function GiftRegistryPage() {
|
||||
const category = categories?.find(
|
||||
(c) => c.id === item.category_id,
|
||||
);
|
||||
const canShowReservations = item.status
|
||||
? (
|
||||
[
|
||||
GiftStatus.RESERVED,
|
||||
GiftStatus.RECEIVED,
|
||||
] as GiftStatus[]
|
||||
).includes(item.status)
|
||||
: false;
|
||||
|
||||
return (
|
||||
<React.Fragment key={item.id}>
|
||||
<TableRow>
|
||||
<TableCell>
|
||||
{category?.name || "Uncategorized"}
|
||||
</TableCell>
|
||||
<TableCell className="font-medium">
|
||||
|
||||
<TableCell className="flex items-center gap-2 font-medium">
|
||||
{/* Purchase URL clickable icon */}
|
||||
{item.purchase_url ? (
|
||||
<Link
|
||||
href={item.purchase_url}
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
>
|
||||
<ExternalLink className="w-4 h-4 text-blue-500 hover:text-blue-600" />
|
||||
</Link>
|
||||
) : (
|
||||
<ExternalLink className="w-4 h-4 text-gray-300 cursor-not-allowed" />
|
||||
)}
|
||||
{item.name}
|
||||
</TableCell>
|
||||
|
||||
<TableCell>{item.quantity_requested || 1}</TableCell>
|
||||
<TableCell>{item.formatted_price || "-"}</TableCell>
|
||||
<TableCell>{getPriorityBadge(item.priority)}</TableCell>
|
||||
<TableCell>{getStatusBadge(item.status)}</TableCell>
|
||||
|
||||
<TableCell>
|
||||
{canShowReservations ? (
|
||||
<Popover>
|
||||
<PopoverTrigger asChild>
|
||||
<div className="cursor-pointer">
|
||||
{getStatusBadge(item.status)}
|
||||
</div>
|
||||
</PopoverTrigger>
|
||||
{/*<PopoverContent className="text-sm">*/}
|
||||
{/* {item.reservations &&*/}
|
||||
{/* item.reservations.length > 0 ? (*/}
|
||||
{/* <ul className="list-disc">*/}
|
||||
{/* {item.reservations.map((res) => (*/}
|
||||
{/* <li key={res.guest_id}>*/}
|
||||
{/* {res.guest_name}: {res.quantity}*/}
|
||||
{/* </li>*/}
|
||||
{/* ))}*/}
|
||||
{/* </ul>*/}
|
||||
{/* ) : (*/}
|
||||
{/* <p>No reservations available.</p>*/}
|
||||
{/* )}*/}
|
||||
{/*</PopoverContent>*/}
|
||||
</Popover>
|
||||
) : (
|
||||
getStatusBadge(item.status)
|
||||
)}
|
||||
</TableCell>
|
||||
|
||||
<TableCell className="text-right">
|
||||
<DropdownMenu>
|
||||
<DropdownMenuTrigger asChild>
|
||||
@@ -428,68 +484,18 @@ export default function GiftRegistryPage() {
|
||||
</DropdownMenu>
|
||||
</TableCell>
|
||||
</TableRow>
|
||||
|
||||
{/* Separate row for description */}
|
||||
{/*{item.description && (*/}
|
||||
<TableRow>
|
||||
<TableCell
|
||||
colSpan={7}
|
||||
className="py-1 px-4 border-t-0 bg-gray-50 dark:bg-gray-800/50 text-sm text-gray-500 dark:text-gray-400"
|
||||
className="py-1 px-4 bg-gray-50 dark:bg-gray-800/50 text-sm text-gray-500 dark:text-gray-400 h-8"
|
||||
>
|
||||
<div className="flex flex-col gap-1">
|
||||
{/* Description - show if available */}
|
||||
{item.description && <p>{item.description}</p>}
|
||||
|
||||
{/* Status-specific information */}
|
||||
<div className="flex items-center gap-2">
|
||||
{item.status === GiftStatus.AVAILABLE && (
|
||||
<>
|
||||
{item.store_name && (
|
||||
<span>Store: {item.store_name}</span>
|
||||
)}
|
||||
|
||||
{item.purchase_url && (
|
||||
<>
|
||||
{item.store_name && <span>•</span>}
|
||||
<a
|
||||
href={item.purchase_url}
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="text-blue-600 hover:underline"
|
||||
>
|
||||
Shop Link
|
||||
</a>
|
||||
</>
|
||||
)}
|
||||
|
||||
{!item.store_name &&
|
||||
!item.purchase_url &&
|
||||
item.brand && (
|
||||
<span>Brand: {item.brand}</span>
|
||||
)}
|
||||
|
||||
{!item.store_name &&
|
||||
!item.purchase_url &&
|
||||
!item.brand && (
|
||||
<span className={"italic"}>
|
||||
No purchase information available
|
||||
</span>
|
||||
)}
|
||||
</>
|
||||
)}
|
||||
|
||||
{item.status === GiftStatus.RESERVED && (
|
||||
<span>Reserved</span>
|
||||
)}
|
||||
|
||||
{item.status === GiftStatus.PURCHASED && (
|
||||
<span>Purchased</span>
|
||||
)}
|
||||
|
||||
{item.status === GiftStatus.RECEIVED && (
|
||||
<span>Received</span>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
{item.description}
|
||||
</TableCell>
|
||||
</TableRow>
|
||||
{/*)}*/}
|
||||
</React.Fragment>
|
||||
);
|
||||
})
|
||||
|
||||
Reference in New Issue
Block a user