Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 5 additions & 1 deletion src/app/search/SearchResultsClient.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -445,7 +445,11 @@ function SearchCard({ product }: { product: SearchCardProduct }) {
onError={() => {
setImageError(true);
}}
className="relative z-10 block h-full w-full max-h-[220px] object-contain p-2 transition-transform duration-300 group-hover:scale-[1.03]"
// BUY-64266: drop group-hover:scale-[1.03] which pushed the rightmost
// card image beyond the grid column on desktop. Keep BUY-64736's
// max-h-[220px] / max-w-full / object-contain bounds so the image
// can never exceed its 220px-tall card frame.
className="relative z-10 block h-full w-full max-h-[220px] max-w-full object-contain p-2"
style={{ maxHeight: '220px', width: '100%', objectFit: 'contain' }}
/>
) : imageError || !product.imageUrl ? (
Expand Down
11 changes: 6 additions & 5 deletions src/components/ProductCard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -140,21 +140,22 @@ export const ProductCard = React.memo(function ProductCard({ deal, comparisonEna
rel="noopener noreferrer"
className="group block bg-white rounded-xl border border-gray-100 overflow-hidden hover:shadow-lg hover:border-indigo-100 transition-all duration-200"
>
<div className="aspect-square bg-gray-50 relative overflow-hidden" style={{ aspectRatio: '1/1'}}>
<div className="relative w-full h-full flex items-center justify-center bg-gradient-to-br from-gray-100 to-gray-50">
<div className="aspect-square bg-gray-50 relative overflow-hidden" style={{ aspectRatio: '1 / 1' }}>
<div className="relative w-full h-full">
{deal.image_url ? (
<Image
src={deal.image_url}
alt={deal.name}
fill
sizes="(max-width: 640px) 50vw, (max-width: 1024px) 33vw, 25vw"
className="object-cover"
style={{ width: '100%', height: '100%', objectFit: 'cover' }}
className="object-contain"
loading={deal.id <= 4 ? 'eager' : 'lazy'}
priority={deal.id <= 2}
/>
) : (
<span className="text-5xl opacity-50">{config.icon}</span>
<div className="flex items-center justify-center w-full h-full bg-gradient-to-br from-gray-100 to-gray-50">
<span className="text-5xl opacity-50">{config.icon}</span>
</div>
)}
</div>
{deal.discount_pct && deal.discount_pct > 0 && (
Expand Down
36 changes: 22 additions & 14 deletions src/components/seo/SeoLandingPage.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -145,7 +145,7 @@ export async function SeoLandingPage({ config }: { config: SeoLandingPageConfig
<section className="overflow-hidden max-sm:overflow-visible bg-[linear-gradient(135deg,#0f172a_0%,#1d4ed8_55%,#f59e0b_130%)] text-white">
<div className={`mx-auto grid max-w-6xl gap-12 px-4 sm:px-6 lg:grid-cols-[1.15fr_0.85fr] lg:items-end ${config.compactCatalogCards ? "py-6" : "py-16 lg:py-24"}`}>
<div>
<div className="mb-5 inline-flex items-center rounded-full border border-white/20 bg-slate-950/40 px-3 py-1 text-xs font-semibold uppercase tracking-[0.24em] text-amber-200">
<div className="mb-5 inline-flex items-center rounded-full border border-white/20 bg-slate-950/70 px-3 py-1 text-xs font-semibold uppercase tracking-[0.24em] text-amber-100">
{config.heroEyebrow}
</div>
<h1 className="max-w-3xl text-4xl font-semibold tracking-tight sm:text-5xl">
Expand All @@ -154,17 +154,25 @@ export async function SeoLandingPage({ config }: { config: SeoLandingPageConfig
<p className="mt-6 max-w-3xl text-lg leading-8 text-slate-200">
{config.heroBody}
</p>
<ul className="mt-8 flex flex-wrap gap-x-6 gap-y-2 text-sm text-slate-100" aria-label="Page metadata">
<li className="inline-flex items-center gap-2">
<span aria-hidden="true" className="text-amber-300">✓</span>
{/*
BUY-66322: single-column layout for the hero checkmark list.
The previous `flex flex-wrap gap-x-6 gap-y-2` layout could wrap
to two rows on narrow/mid viewports, leaving a perceived empty
bottom-right cell (VidMee layout flag). A vertical stack is
unambiguous and matches the editorial intent (page metadata,
not a feature grid).
*/}
<ul className="mt-8 space-y-2 text-sm text-slate-100" aria-label="Page metadata">
<li className="flex items-center gap-2">
<span aria-hidden="true" className="text-amber-200">✓</span>
<span>{buildRefreshedLabel(config, products)}</span>
</li>
<li className="inline-flex items-center gap-2">
<span aria-hidden="true" className="text-amber-300">✓</span>
<li className="flex items-center gap-2">
<span aria-hidden="true" className="text-amber-200">✓</span>
<span>{config.country} market coverage</span>
</li>
<li className="inline-flex items-center gap-2">
<span aria-hidden="true" className="text-amber-300">✓</span>
<li className="flex items-center gap-2">
<span aria-hidden="true" className="text-amber-200">✓</span>
<span>Live BuyWhere search results</span>
</li>
</ul>
Expand All @@ -177,7 +185,7 @@ export async function SeoLandingPage({ config }: { config: SeoLandingPageConfig
<div className="mt-6 flex flex-wrap gap-3">
<Link
href={shopperCta.href}
className="inline-flex min-h-[44px] items-center rounded-full bg-amber-400 px-5 py-3 text-sm font-semibold text-slate-950 transition-colors hover:bg-amber-300"
className="inline-flex min-h-[44px] items-center rounded-full bg-amber-600 px-5 py-3 text-sm font-semibold text-white transition-colors hover:bg-amber-700"
>
{shopperCta.label}
</Link>
Expand All @@ -196,10 +204,10 @@ export async function SeoLandingPage({ config }: { config: SeoLandingPageConfig
<div className="mx-auto max-w-6xl px-4 sm:px-6">
<div className={`${config.compactCatalogCards ? "mb-4" : "mb-8"} flex flex-col gap-3 md:flex-row md:items-end md:justify-between`}>
<div>
<p className="text-sm font-semibold uppercase tracking-[0.2em] text-amber-700">Live catalog snapshot</p>
<p className="text-sm font-semibold uppercase tracking-[0.2em] text-amber-800">Live catalog snapshot</p>
<h2 className="mt-2 text-3xl font-semibold tracking-tight text-slate-900">{config.productSectionTitle}</h2>
</div>
<Link href={shopperCta.href} className="text-sm font-semibold text-amber-700 hover:text-amber-800">
<Link href={shopperCta.href} className="text-sm font-semibold text-amber-800 hover:text-amber-900">
Open full search
</Link>
</div>
Expand Down Expand Up @@ -275,7 +283,7 @@ export async function SeoLandingPage({ config }: { config: SeoLandingPageConfig
<section className="py-12">
<div className="mx-auto max-w-6xl px-4 sm:px-6">
<div className="max-w-3xl">
<p className="text-sm font-semibold uppercase tracking-[0.2em] text-amber-700">{config.categoryComparisonEyebrow || "Featured models"}</p>
<p className="text-sm font-semibold uppercase tracking-[0.2em] text-amber-800">{config.categoryComparisonEyebrow || "Featured models"}</p>
<h2 className="mt-2 text-3xl font-semibold tracking-tight text-slate-900">
{config.categoryComparisonTitle || "Models compared"}
</h2>
Expand Down Expand Up @@ -313,7 +321,7 @@ export async function SeoLandingPage({ config }: { config: SeoLandingPageConfig
<section className="bg-[linear-gradient(180deg,#fff7ed_0%,#ffffff_100%)] py-16">
<div className="mx-auto grid max-w-6xl gap-10 px-4 sm:px-6 lg:grid-cols-[0.95fr_1.05fr]">
<div>
<p className="text-sm font-semibold uppercase tracking-[0.2em] text-amber-700">Buying signals</p>
<p className="text-sm font-semibold uppercase tracking-[0.2em] text-amber-800">Buying signals</p>
<h2 className="mt-2 text-3xl font-semibold tracking-tight text-slate-900">{config.highlightSectionTitle}</h2>
<div className="mt-8 space-y-4">
{config.highlights.map((highlight) => (
Expand All @@ -332,7 +340,7 @@ export async function SeoLandingPage({ config }: { config: SeoLandingPageConfig
<ul className="space-y-4">
{config.advicePoints.map((point) => (
<li key={point} className="flex gap-3 text-sm leading-6">
<span className="mt-1 inline-flex h-6 w-6 shrink-0 items-center justify-center rounded-full bg-amber-400 text-xs font-semibold text-slate-950">
<span className="mt-1 inline-flex h-6 w-6 shrink-0 items-center justify-center rounded-full bg-amber-600 text-xs font-semibold text-white">
</span>
<span>{point}</span>
Expand Down