Responsive images?

i have html kinda like

<img srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm 2x"
    srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md 3x"
    srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg 4x"
    src="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs"
    class="d-block w-100" alt="..." />```

as you can see i bought "Images" and made variants like xs,sm,md,lg..

in my nginx i have this for webp files
    location ~* \.(?:ico|css|js|gif|jpe?g|png|webp)$ {
        expires 365d;
    }

maybe i should use add header "Cache-blabla" instead not sure..
anyway, what's the correct way to do responsive images? does it work only for <img> tags or also bg-img: in css? should i be using webp images, or should i use jpg and let cloudflare convert it for me? (i believe i read thats a feature somewhere)

thanks

specifically i wanna change this

and my nginx config looks like this now:

    server {
        listen 443 ssl http2;
        server_name minecrafthell.com;

        root /var/www/html/;
        index index.html index.htm;

        # SSL
        ssl on;
        ssl_certificate /etc/ssl/minecrafthell_com_chain.crt;
        ssl_certificate_key /etc/ssl/minecrafthell_com.key;

        # Pagespeed

        # Needs to exist and be writable by nginx.  Use tmpfs for best performance.
        pagespeed FileCachePath /var/ngx_pagespeed_cache;

        # serve static files
        location / {
            pagespeed on;

            #try_files $uri $uri/ =404;
        }

        location ~* \.(?:ico|css|js|gif|jpe?g|png|webp)$ {
            expires 365d;
            add_header Cache-Control "public, max-age=3600, must-revalidate";
        }
    }

Give this thread a read. It should help with your cache settings:

2 Likes

Just wanted to add, something, that does not directly have something to do with the Browser Cache TTL of the image, but still is important since it is about responsive images.
Normaly you just have one srcset attribute and overload this one. Or you can use the <picture> tag and overload him with multiple sources. But I have never seen multiple srcsets in one <img>. I dont know if that would anyway work properly.

At least I think just the first srcset will be taken, so your <img> tag in the frontend would lose its srcsets beside the first one and would look like this:

<img srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm 2x"
    src="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs"
    class="d-block w-100" alt="..." />

Your options to do it right are:

<img> tag:

<img src="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs" 
     srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm 2x,
             https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md 3x,
             https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg 4x"
    class="d-block w-100" alt="..." />

<picture> tag:

<picture>
    <source type="image/jxl" srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs/jxl, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm/jxl 2x, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md/jxl 3x, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg/jxl 4x">
    <source type="image/webp" srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs/webp, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm/webp 2x, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md/webp 3x, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg/webp 4x">
    <img src="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs" srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm 2x, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md 3x, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg 4x" class="d-block w-100" alt="..." >
</picture>

I personally prefer the <picture> tag since you can overload it once more with additional types, like WebP, AVIF, JXL … if the mime-type/content-type can be enforced.

And as fallback (src) you normaly take the biggest image of them all, so normaly the “lg” version, not the “xs”, since it just gets taken in undefined or worst case and then the biggest image will always be a better chioce then the smallest of them all.

3 Likes

https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/16536315-5431-4089-a74b-b833236d9f00/md

it gives a 404… what am i doing wrong? do i need to tell nginx how to serve these files somehow?

for no reason it’s working now… i changed my html to:

<!--
<picture>
    <source type="image/jxl" srcset="https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs/jxl, https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm/jxl 2x, https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md/jxl 3x, https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg/jxl 4x">
    <source type="image/webp" srcset="https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs/webp, https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm/webp 2x, https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md/webp 3x, https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg/webp 4x">
    <img src="https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs" srcset="https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm 2x, https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md 3x, https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg 4x" class="d-block w-100" alt="..." >
</picture>
-->
<img srcset="https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm 1x"
    src="https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg"
    class="d-block w-100" alt="..." />

the url https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs/webp
does not work, but

https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs
without the /webp does work

That the URL https://minecrafthell.com/cdn-cgi/imagedelivery/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs/webp does not work was expected, this should just signalise, that this image should be in WebP format. The one ending with /jxl would be the one in JXL format. But thats just to signalise you what it should be, does not mean, the URL actually exists.

Please do not use the <picture> tag I posted, or use a adopted version. The example of the <picture> tag includes a differentiation between the mine types or content types and enforce them. If you can not differentiate between and enforce them, I would recommend the modified <img> tag I provided to you, since this is just overloadable for “scaleing/resolution” not image types.

The srcset with the “1x” does not need the “1x” since it is default. If no “Nx” provided it falls back to “1x”.

If you could share your domain with us I could have a very quick look at and tell you what would my recomended use of the <img> tag or <picture> tag.

For me it does not trigger a 404, it actually works. But no, you dont have to instruct your local nginx to do anything since these images are not getting served from Cloudflare, not your origin.

1 Like

i was struggling with this for hours yesterday, and i did realize it has nothing to do with my origin server, but with cloudflare’s server… but what exactly? every 30 minutes or so i got a 404 on my custom-domain images, and I believe it’s because i was changing between Namecheap’s and CF’s nameservers? I’ve kept it at CF’s nameservers over night and when i woke up today it seems to work, so I think I’ve found the root of my issue?

the website is https://minecrafthell.com
for bg-img’s in the css, i will use breakpoints like @include media-breakpoint-up(md) { background-image: url(md-pic-goes-here); }

and for the carousel which uses the <img> tags, i will research how to make the appropriate adjustment for my situation, i would appreciate getting your recommendation tho if you feel like it :slight_smile:

also, there’s pagespeed EnableFilters responsive_images,resize_images; which wouldn’t help me with the css, but would help me with the html, however I gotta use the width and height attribute within the <img> tag to use it, so i think the manual approach would be better?

Since you mentioned that:
I think you are using the 1x, 2x, 3x wrong. Since they are just getting used for devices (mostly mobile devices) with a scaling factor. On most mobilephones it is 2x.

But if you want to create responsive images the correct approach would be to use the exact same breakpoints as in the CSS but in the <img> tag, or the <picture> tag and overload them with the media attribute to make sure that certain devices just get certain images.

Here I would indeed recommend the <picture> tag which is IMHO better structured.
I would use it like this:

<picture class="d-block w-100" alt="...">
	<source srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg" media="(min-width: 992px)">
	<source srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md" media="(min-width: 768px)">
	<source srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm" media="(min-width: 576px)">
	<source srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs" media="(min-width: 0px)>
	<img width="" height="" alt="" src="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg">
</picture>

If you would also have 2x images, it could look like this:

<picture class="d-block w-100" alt="...">
	<source srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg/2x 2x" media="(min-width: 992px)">
	<source srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/md/2x 2x" media="(min-width: 768px)">
	<source srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/sm/2x 2x" media="(min-width: 576px)">
	<source srcset="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs, https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/xs/2x 2x" media="(min-width: 0px)>
	<img width="" height="" alt="" src="https://imagedelivery.net/N1xq0JXU_9WySRGAA5Xzag/e31e849d-fc8b-4540-b952-4faa149ae000/lg">
</picture>

You can play around with this a little. Class should, if you use the <picture> tag, go directly into the <picture> tag itself. But the <img> within the <picture> tag should contain proper width and height attributes. Don’t forget that.

Since Bootstrap 5, which you are using does have more then 4 breakpionts, I still just added the one you created images for. But feel free to implement the others by yourself with the help of the Bootstrap docs: Breakpoints · Bootstrap v5.1
Just if you want to be fully responsive, since Bootstrap does have more.

3 Likes

This topic was automatically closed 3 days after the last reply. New replies are no longer allowed.