Solved

LCP at 5.8s on PDP — main culprit is hero image, but it's already 80KB WebP

Speed & Core Web VitalsSolved

LCP at 5.8s on PDP — main culprit is hero image, but it's already 80KB WebP

Jonas Berg·Asked May 26, 2026
PageSpeed Insights is showing LCP of 5.8s on mobile for our product detail pages. The flagged LCP element is the main product image. Strange thing: the image is already 80KB WebP, served via Shopify CDN. LCP breakdown from CrUX: - TTFB: 0.9s - Resource load delay: 2.1s - Resource load duration: 0.4s - Element render delay: 2.4s The resource load delay seems huge. What's pushing it back? We don't have any custom JS blocking the head.

3 Replies

ACCEPTED ANSWER
Fix My Store Team·May 26, 2026
Resource load delay of 2.1s usually means the image isn't being discovered by the browser preload scanner early enough. A few things to check: 1. **Is your PDP main image lazy-loaded?** It shouldn't be. Open view-source and confirm the LCP `<img>` has `loading="eager"` (or no `loading` attribute) and `fetchpriority="high"`. Many themes default product images to `loading="lazy"`, which kills LCP. 2. **Is the image inside a JS-rendered component?** If you have a gallery that hydrates on the client (common with React/Hydrogen and some app-injected galleries), the browser can't see the `<img>` until JS runs. 3. **Preload it.** In `theme.liquid` head, add:
{%- if template == 'product' -%}
  <link rel="preload" as="image"
        href="{{ product.featured_image | image_url: width: 800 }}"
        imagesrcset="{{ product.featured_image | image_url: width: 400 }} 400w, {{ product.featured_image | image_url: width: 800 }} 800w"
        imagesizes="(max-width: 749px) 100vw, 50vw">
{%- endif -%}
That alone usually cuts 1-2s off LCP on PDPs.
Jonas Berg·May 26, 2026
You nailed it — the image had `loading="lazy"` because we use a custom gallery section. Removed lazy on the first image + added the preload. LCP dropped to 2.6s in field data after 48h. Massive thanks.
Maya Iyer·May 26, 2026
Worth adding for future readers: also make sure `fetchpriority="high"` is set explicitly. Some browsers (especially Safari) don't infer it from `loading="eager"` alone, and you'll see it leave 200-400ms on the table.