withastro / astro

The web framework for content-driven websites. ⭐️ Star to support our work!
https://astro.build
Other
46.8k stars 2.49k forks source link

Image component's sizes + widths attribute not coherent. #11057

Closed umagon closed 3 months ago

umagon commented 6 months ago

Astro Info

Astro                    v4.8.4
Node                     v20.12.2
System                   Linux (x64)
Package Manager          pnpm
Output                   static
Adapter                  none
Integrations             @astrojs/preact
                         @astrojs/tailwind

If this issue only occurs in one browser, which browser is a problem?

Chrome

Describe the Bug

When I use Image component's sizes attribute I get a correct output, but when I check which image gets downloaded I get the wrong one.

I've made an stackblitz demo. In it there is an MyImage component with a sizes attribute that looks like this:

<Image
            src={duck}
            width={500}
            height={500}
            widths={[180, 200, 800]}
            sizes="(max-width: 320px) 180px, (max-width: 768px) 200px, 800px"
            alt="Duck."
            format="avif"
        />

The sizes attribute is working weirdly. When I use a device-width of 320px, it should use the 180w version of the image. But a quick inspection of network tab in dev tools shows the 200w version was downloaded.

This wrong behavior is so weird I couldn't tell what is actually happening. When I change the first width (180px) in sizes and widths attributes to 20px, a 20px image (correct) gets downloaded. But when I use anything above 50px, the next image size (200px) gets downloaded, even if I didn't change the media query at all.

What's the expected result?

It should download the correct image taking into account the viewport width.

The output of the example above is:

<img src="/_image?href=%2F%40fs%2Fhome%2Fprojects%2Fwithastro-astro-ebpoea%2Fsrc%2Fassets%2Fduck.jpg%3ForigWidth%3D800%26origHeight%3D800%26origFormat%3Djpg&amp;w=500&amp;h=500&amp;f=avif"
srcset="/_image?href=%2F%40fs%2Fhome%2Fprojects%2Fwithastro-astro-ebpoea%2Fsrc%2Fassets%2Fduck.jpg%3ForigWidth%3D800%26origHeight%3D800%26origFormat%3Djpg&amp;w=180&amp;f=avif 180w, /_image?href=%2F%40fs%2Fhome%2Fprojects%2Fwithastro-astro-ebpoea%2Fsrc%2Fassets%2Fduck.jpg%3ForigWidth%3D800%26origHeight%3D800%26origFormat%3Djpg&amp;w=200&amp;f=avif 200w, /_image?href=%2F%40fs%2Fhome%2Fprojects%2Fwithastro-astro-ebpoea%2Fsrc%2Fassets%2Fduck.jpg%3ForigWidth%3D800%26origHeight%3D800%26origFormat%3Djpg&amp;w=500&amp;h=500&amp;f=avif 800w"
data-image-component="true" sizes="(max-width: 320px) 180px, (max-width: 768px) 200px, 800px" alt="Duck." width="500" height="500" loading="lazy" decoding="async"
data-astro-source-file="/home/projects/withastro-astro-ebpoea/node_modules/astro/components/Image.astro" data-astro-source-loc="38:2">

Maybe this is not an astro bug, but I can't believe nobody has this problem. Maybe I'm not using this component the right way. Would appreciate some help.

Link to Minimal Reproducible Example

https://stackblitz.com/edit/withastro-astro-ebpoea?file=src%2Fcomponents%2FMyImage.astro

Participation

V3RON commented 6 months ago

I can’t reproduce your issue using the example you provided. Could you record a video instead and show what’s wrong on your side?

Princesseuh commented 6 months ago

sizes is a very weird attribute and it's quite hard to test it locally because of it interacts with the DPR, especially in the dev tools in Chrome. As far as I can tell, Astro is generating the right code though, so it's really unlikely that there is an Astro issue here.

umagon commented 6 months ago

@Princesseuh Yes it might be my misunderstanding of how sizes works since the output is correct.

@V3RON I have some screenshots

Before

image

image

After

image

image

If I use anything above 50px (or so, I don't know the exact threshold), it jumps to the next size, 200w.

Princesseuh commented 3 months ago

Closing because this is not an issue with Astro, the markup generated is correct. As I wrote in my previous message, the HTML sizes attribute is just super confusing to work with because you often can't quite test it correctly by resizing the window / using the dev tools, it's very wonky.

Apologies for the inconvenience, if you run into further issues, don't hesitate asking for help on our Discord: https://astro.build/chat