Initial commit: Craft2Prints with Stages 1-3
This commit is contained in:
@@ -0,0 +1,56 @@
|
||||
import Link from 'next/link';
|
||||
import ProductMockup from './ProductMockup';
|
||||
import Price from './Price';
|
||||
import type { ProductDTO } from '@/lib/types';
|
||||
|
||||
const NEW_WINDOW_MS = 1000 * 60 * 60 * 24 * 30; // 30 days
|
||||
|
||||
export default function ProductCard({
|
||||
product,
|
||||
hrefBase = '/made-to-order',
|
||||
}: {
|
||||
product: ProductDTO;
|
||||
hrefBase?: string;
|
||||
}) {
|
||||
const thumbnail = product.colorPhotos[product.colors[0]] ?? product.imageUrl;
|
||||
const isNew = Date.now() - new Date(product.createdAt).getTime() < NEW_WINDOW_MS;
|
||||
|
||||
return (
|
||||
<Link href={`${hrefBase}/${product.slug}`} className="group block">
|
||||
<div className="relative border border-line bg-surface p-6 shadow-sm transition-all duration-300 group-hover:-translate-y-1 group-hover:border-ink group-hover:shadow-lg">
|
||||
{isNew && (
|
||||
<span className="tag-label absolute left-3 top-3 rounded-full bg-splash-blue/10 px-2.5 py-1 text-splash-blue">
|
||||
New
|
||||
</span>
|
||||
)}
|
||||
{product.onSale && (
|
||||
<span className="tag-label absolute right-3 top-3 rounded-full bg-splash-pink/10 px-2.5 py-1 text-splash-pink">
|
||||
Sale
|
||||
</span>
|
||||
)}
|
||||
<div className="mx-auto aspect-square w-full max-w-[280px] overflow-hidden">
|
||||
{thumbnail ? (
|
||||
<img
|
||||
src={thumbnail}
|
||||
alt={product.name}
|
||||
className="h-full w-full object-contain transition-transform duration-300 group-hover:scale-105"
|
||||
/>
|
||||
) : (
|
||||
<div className="transition-transform duration-300 group-hover:scale-105">
|
||||
<ProductMockup mockup={product.mockup} color={product.colors[0]} />
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
<div className="mt-3 flex justify-end gap-2 text-right">
|
||||
{product.onSale && product.originalPrice != null && (
|
||||
<Price cents={product.originalPrice} className="font-mono text-sm text-muted line-through" />
|
||||
)}
|
||||
<Price
|
||||
cents={product.effectivePrice}
|
||||
className={`font-mono text-sm ${product.onSale ? 'text-splash-pink' : 'text-muted'}`}
|
||||
/>
|
||||
</div>
|
||||
</Link>
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user