style: polish bottle cards with premium aesthetic and better readability
This commit is contained in:
@@ -9,53 +9,62 @@ interface BottleCardProps {
|
||||
}
|
||||
|
||||
function BottleCard({ bottle }: BottleCardProps) {
|
||||
const statusConfig = {
|
||||
open: { icon: Unlock, color: 'bg-amber-500/80 border-amber-400/50', label: 'Offen' },
|
||||
sampled: { icon: FlaskConical, color: 'bg-purple-500/80 border-purple-400/50', label: 'Sample' },
|
||||
empty: { icon: Ghost, color: 'bg-zinc-500/80 border-zinc-400/50', label: 'Leer' },
|
||||
sealed: { icon: Lock, color: 'bg-blue-600/80 border-blue-400/50', label: 'Versiegelt' },
|
||||
};
|
||||
|
||||
const StatusIcon = statusConfig[bottle.status as keyof typeof statusConfig]?.icon || Lock;
|
||||
const statusStyle = statusConfig[bottle.status as keyof typeof statusConfig] || statusConfig.sealed;
|
||||
|
||||
return (
|
||||
<Link href={`/bottles/${bottle.id}`} className="block">
|
||||
<div className="bg-white dark:bg-zinc-900 rounded-2xl overflow-hidden border border-zinc-200 dark:border-zinc-800 shadow-md transition-all hover:scale-[1.02] hover:shadow-xl group relative">
|
||||
<div className="aspect-[3/2] overflow-hidden bg-zinc-100 dark:bg-zinc-800 relative">
|
||||
<Link href={`/bottles/${bottle.id}`} className="block h-full group">
|
||||
<div className="h-full bg-white dark:bg-zinc-900 rounded-[2rem] overflow-hidden border border-zinc-200 dark:border-zinc-800 shadow-sm transition-all duration-300 hover:shadow-2xl hover:shadow-amber-900/10 hover:-translate-y-1 group-hover:border-amber-500/30">
|
||||
<div className="aspect-[4/3] overflow-hidden bg-zinc-100 dark:bg-zinc-800 relative">
|
||||
<img
|
||||
src={bottle.image_url}
|
||||
alt={bottle.name}
|
||||
className="w-full h-full object-cover transition-transform duration-500 group-hover:scale-110"
|
||||
className="w-full h-full object-cover transition-transform duration-700 group-hover:scale-110"
|
||||
/>
|
||||
<div className="absolute inset-0 bg-black/0 group-hover:bg-black/10 transition-colors" />
|
||||
<div className="absolute inset-0 bg-gradient-to-t from-black/40 via-transparent to-transparent opacity-0 group-hover:opacity-100 transition-opacity" />
|
||||
|
||||
{bottle.last_tasted && (
|
||||
<div className="absolute top-3 right-3 bg-zinc-900/80 backdrop-blur-md text-white text-[10px] font-bold px-2 py-1 rounded-md flex items-center gap-1 border border-white/10">
|
||||
<Calendar size={10} />
|
||||
ZULETZT: {new Date(bottle.last_tasted).toLocaleDateString('de-DE')}
|
||||
<div className="absolute top-3 right-3 bg-zinc-900/80 backdrop-blur-md text-white text-[9px] font-black px-2 py-1 rounded-lg flex items-center gap-1 border border-white/10 ring-1 ring-black/5">
|
||||
<Clock size={10} />
|
||||
{new Date(bottle.last_tasted).toLocaleDateString('de-DE')}
|
||||
</div>
|
||||
)}
|
||||
|
||||
<div className={`absolute bottom-3 left-3 px-2 py-1 rounded-md text-[10px] font-black uppercase flex items-center gap-1.5 backdrop-blur-md border ${bottle.status === 'open'
|
||||
? 'bg-amber-500/80 text-white border-amber-400/50'
|
||||
: bottle.status === 'sampled'
|
||||
? 'bg-purple-500/80 text-white border-purple-400/50'
|
||||
: bottle.status === 'empty'
|
||||
? 'bg-zinc-500/80 text-white border-zinc-400/50'
|
||||
: 'bg-blue-600/80 text-white border-blue-400/50'
|
||||
}`}>
|
||||
{bottle.status === 'open' ? <Unlock size={10} /> : bottle.status === 'sampled' ? <FlaskConical size={10} /> : bottle.status === 'empty' ? <Ghost size={10} /> : <Lock size={10} />}
|
||||
{bottle.status}
|
||||
<div className={`absolute bottom-3 left-3 px-3 py-1.5 rounded-xl text-[10px] font-black uppercase flex items-center gap-2 backdrop-blur-md border shadow-lg ${statusStyle.color}`}>
|
||||
<StatusIcon size={12} />
|
||||
{statusStyle.label}
|
||||
</div>
|
||||
</div>
|
||||
<div className="p-4">
|
||||
<h3 className="font-bold text-lg text-zinc-800 dark:text-zinc-100 truncate">{bottle.name}</h3>
|
||||
<p className="text-zinc-500 text-sm truncate">{bottle.distillery}</p>
|
||||
|
||||
<div className="mt-2 flex items-center gap-1.5 text-[10px] font-bold text-zinc-400 uppercase tracking-tight">
|
||||
<Clock size={12} />
|
||||
Hinzugefügt am {new Date(bottle.created_at).toLocaleDateString('de-DE')}
|
||||
<div className="p-5 space-y-4">
|
||||
<div>
|
||||
<p className="text-[10px] font-black text-amber-600 uppercase tracking-[0.2em] mb-1 leading-none">{bottle.distillery}</p>
|
||||
<h3 className="font-black text-xl text-zinc-900 dark:text-zinc-100 leading-tight group-hover:text-amber-600 transition-colors line-clamp-2 min-h-[3.5rem] flex items-center">
|
||||
{bottle.name}
|
||||
</h3>
|
||||
</div>
|
||||
|
||||
<div className="mt-3 flex items-center justify-between">
|
||||
<span className="px-2 py-1 bg-amber-100 dark:bg-amber-900/30 text-amber-700 dark:text-amber-400 text-xs font-semibold rounded-md">
|
||||
<div className="flex flex-wrap gap-2">
|
||||
<span className="px-2.5 py-1 bg-zinc-100 dark:bg-zinc-800 text-zinc-600 dark:text-zinc-400 text-[10px] font-black uppercase tracking-widest rounded-lg border border-zinc-200/50 dark:border-zinc-700/50">
|
||||
{bottle.category}
|
||||
</span>
|
||||
<span className="text-xs text-zinc-400">
|
||||
{bottle.abv}% Vol.
|
||||
<span className="px-2.5 py-1 bg-amber-50 dark:bg-amber-900/20 text-amber-700 dark:text-amber-400 text-[10px] font-black uppercase tracking-widest rounded-lg border border-amber-200/50 dark:border-amber-800/20">
|
||||
{bottle.abv}% VOL
|
||||
</span>
|
||||
</div>
|
||||
|
||||
<div className="pt-2 flex items-center gap-2 text-[10px] font-bold text-zinc-400 uppercase tracking-wider border-t border-zinc-100 dark:border-zinc-800">
|
||||
<Calendar size={12} className="text-zinc-300" />
|
||||
<span className="opacity-70 text-[9px]">Hinzugefügt am</span>
|
||||
<span className="text-zinc-500 dark:text-zinc-300">{new Date(bottle.created_at).toLocaleDateString('de-DE')}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</Link>
|
||||
|
||||
Reference in New Issue
Block a user