Answers.Body: <p>You can use the method <a href="https://docs.craftcms.com/api/v3/craft-elements-asset.html#method-getsrcset" rel="noreferrer"><code>Asset::getSrcset</code></a> to generate a valid <code>srcset</code> attribute as well as the asset transforms included in it. But you will need to restructure your HTML a bit. The current approach works, but is very verbose and not optimal for different screen resolutions and image placements.</p>
  <p>Instead of using multiple source, just use one source without a <code>media</code> attribute that includes all variants in its <code>srcset</code>. Then add a <code>sizes</code> attribute that will tell the browser how large the image will be displayed depending on the viewport width. If the image always spans the full page, you can just set your <code>sizes</code> attribute to <code>100vw</code> (100 viewport width units). If your image is sized differently depending on the viewport, you will need to adjust the sizes attribute to match those sizes. <a href="https://developer.mozilla.org/en-US/docs/Learn/HTML/Multimedia_and_embedding/Responsive_images" rel="noreferrer">Here's a great article on MDN on responsive images, including how to use the <code>sizes</code> attribute</a>.</p>
  <p>Now the final code can look like this:</p>
  <pre class="lang-twig prettyprint-override"><code>&lt;picture&gt;
      &lt;source {{ attr({
          type: 'image/jpeg',
          srcset: image.getSrcset(
              [320, 360, 412, 600, 768, 1024, 1280, 1440, 1600, 1920, 2560],
              { format: 'jpg', }
          ),
          sizes: '100vw',
      }) }}&gt;
      &lt;img width=&quot;{{ image.width }}&quot; height=&quot;{{ image.height }}&quot; alt=&quot;{{ image.alt }}&quot;&gt;
  &lt;/picture&gt;
  </code></pre>
  <p>The great thing about this approach is that browsers will take care of adjusting for pixel density for you. If you open the page with this image on a smartphone with a 360px wide display (CSS pixels) and a 2x display density (so a 720px screen), the browser will automatically select the 768px image, since it's the smallest available size that's large enough for the screen's resolution and density.</p>
  <p>Note that as per the spec browsers <em>may</em> select images based on other factors, such as using a smaller images if network conditions are poor, or using a cached image even if it's smaller than the currently required resolution. But in practice this rarely matters.</p>
  <p>By the way, with the code above, you can very easily add a second <code>&lt;source&gt;</code> with the same <code>srcset</code> and <code>sizes</code> attributes but using type <code>image/webp</code> and <code>format: 'webp'</code> in the transform to generate WebP variants of the images for browsers that support it. This will have a large impact on web performance.</p>
  
Answers.ContentLicense: CC BY-SA 4.0
Answers.CreationDate: 2022-02-22T18:38:13.307Z
Answers.Text: Perfect thank you a lot for helping me. I take the opportunity to ask you how precise you are in determining the various image sizes and how many you usually generate (for how many resolutions)?
Answers.UserDisplayName: Samuel
Answers.ContentLicense: CC BY-SA 4.0
Answers.CreationDate: 2022-02-22T19:01:59.120Z
Answers.Text: I have noticed that by using imagerx there are significant performance improvements (a lot less database queries). Do you use such a plugin for responsive images?
Answers.UserDisplayName: Samuel
Answers.ContentLicense: CC BY-SA 4.0
Answers.CreationDate: 2022-02-23T08:59:49.317Z
Answers.Text: @Samuel Most of our projects have containers with fixed widths (per viewport) and a multi-column layout (using Bootstrap, for example), so we have ~6 different fixed sizes in pixels – though it depends on the image positioning. For an image that stretches the whole viewport, there's only a single size. Then we generate the srcset with those sizes as well as some others for different pixel densities. You can't get every size in every possible resolution, that would be hundreds of images, so we usually just 'fill in the gaps' between sizes so that most devices will find a suitable image.
Answers.UserDisplayName: MoritzLost
Answers.ContentLicense: CC BY-SA 4.0
Answers.CreationDate: 2022-02-23T09:02:32.030Z
Answers.Text: @Samuel We don't use a plugin, the built-in image resizer works just fine for us. The resizing is a one-time operation for each placed image, after all, and the HTML output can be cached, avoiding excessive queries for most requests. BTW we have a reusable twig template to take care of this stuff, every other template just includes that template and passes it an image, the `sizes` attribute and the list of sizes for the `srcset`. I've written a bit about that here: https://craftcms.stackexchange.com/a/38383/11705
Answers.UserDisplayName: MoritzLost
Answers.ContentLicense: CC BY-SA 4.0
Answers.CreationDate: 2022-02-23T14:14:09.710Z
Answers.Text: Great! thank you so much for your valuable answers
Answers.UserDisplayName: Samuel
Answers.ContentLicense: CC BY-SA 4.0
Answers.CreationDate: 2022-02-22T16:16:42.503Z
Answers.LastActivityDate: 2022-02-22T16:16:42.503Z
Answers.UserDisplayName: MoritzLost
Body: <p>I'm new to craft cms and I'm trying to generate srcset sizes for an image with the following code.</p>
  <pre><code>{% set thumb320 = { width: 320, format: 'jpg' } %}
  {% set thumb320_2x = { width: 640, format: 'jpg' } %}
  {% set thumb360 = { width: 320, format: 'jpg' } %}
  {% set thumb360_2x = { width: 640, format: 'jpg' } %}
  {% set thumb412 = { width: 414, format: 'jpg' } %}
  {% set thumb412_2x = { width: 828, format: 'jpg' } %}
  {% set thumb600 = { width: 600, format: 'jpg' } %}
  {% set thumb600_2x = { width: 1200, format: 'jpg' } %}
  {% set thumb768 = { width: 603, format: 'jpg' } %}
  {% set thumb768_2x = { width: 1206, format: 'jpg' } %}
  {% set thumb1024 = { width: 803, format: 'jpg' } %}
  {% set thumb1024_2x = { width: 1606, format: 'jpg' } %}
  {% set thumb1280 = { width: 1003, format: 'jpg' } %}
  {% set thumb1280_2x = { width: 2006, format: 'jpg' } %}
  {% set thumb1440 = { width: 1120, format: 'jpg' } %}
  {% set thumb1440_2x = { width: 2240, format: 'jpg' } %}
  {% set thumb1600 = { width: 1224, format: 'jpg' } %}
  {% set thumb1600_2x = { width: 2448, format: 'jpg' } %}
  {% set thumb1920 = { width: 1244, format: 'jpg' } %}
  {% set thumb1920_2x = { width: 2488, format: 'jpg' } %}
  {% set thumb2560 = { width: 1368, format: 'jpg' } %}
  
  &lt;picture&gt;
      &lt;source media='(min-width: 2560px)' srcset=&quot;{{ image.getUrl(thumb2560) }} 1x&quot;&gt;
      &lt;source media='(min-width: 1920px)' srcset=&quot;{{ image.getUrl(thumb1920) }} 1x, {{ image.getUrl(thumb1920_2x) }} 1.5x&quot;&gt;
      &lt;source media='(min-width: 1600px)' srcset=&quot;{{ image.getUrl(thumb1600) }} 1x, {{ image.getUrl(thumb1600_2x) }} 1.5x&quot;&gt;
      &lt;source media='(min-width: 1440px)' srcset=&quot;{{ image.getUrl(thumb1440) }} 1x, {{ image.getUrl(thumb1440_2x) }} 2x&quot;&gt;
      &lt;source media='(min-width: 1280px)' srcset=&quot;{{ image.getUrl(thumb1280) }} 1x, {{ image.getUrl(thumb1280_2x) }} 2x&quot;&gt;
      &lt;source media='(min-width: 1024px)' srcset=&quot;{{ image.getUrl(thumb1024) }} 1x, {{ image.getUrl(thumb1024_2x) }} 2x&quot;&gt;
      &lt;source media='(min-width: 768px)' srcset=&quot;{{ image.getUrl(thumb768) }} 1x, {{ image.getUrl(thumb768_2x) }} 2x&quot;&gt;
      &lt;source media='(min-width: 600px)' srcset=&quot;{{ image.getUrl(thumb600) }} 1x, {{ image.getUrl(thumb600_2x) }} 2x&quot;&gt;
      &lt;source media='(min-width: 412px)' srcset=&quot;{{ image.getUrl(thumb412) }} 1x, {{ image.getUrl(thumb412_2x) }} 2x&quot;&gt;
      &lt;source media='(min-width: 360px)' srcset=&quot;{{ image.getUrl(thumb360) }} 1x, {{ image.getUrl(thumb360_2x) }} 2x&quot;&gt;
      &lt;img itemprop=&quot;image&quot; src=&quot;{{ image.getUrl(thumb320) }}&quot; alt='{{ image.title }}'&gt;
  &lt;/picture&gt;
  </code></pre>
  <p>The problem is that this is generating a lot of queries and I wanted to find out if there is a more efficient way of coding this?</p>
  
Tags: <craft3><image-transforms><performance>
Title: Craft CMS images transform srcset sizes
ThreadText: # Craft CMS images transform srcset sizes
  
  (Asked by: username_0 on 2022-02-21)
  
  I'm new to craft cms and I'm trying to generate srcset sizes for an image with the following code.
  
  ```
  {% set thumb320 = { width: 320, format: 'jpg' } %}
  {% set thumb320_2x = { width: 640, format: 'jpg' } %}
  {% set thumb360 = { width: 320, format: 'jpg' } %}
  {% set thumb360_2x = { width: 640, format: 'jpg' } %}
  {% set thumb412 = { width: 414, format: 'jpg' } %}
  {% set thumb412_2x = { width: 828, format: 'jpg' } %}
  {% set thumb600 = { width: 600, format: 'jpg' } %}
  {% set thumb600_2x = { width: 1200, format: 'jpg' } %}
  {% set thumb768 = { width: 603, format: 'jpg' } %}
  {% set thumb768_2x = { width: 1206, format: 'jpg' } %}
  {% set thumb1024 = { width: 803, format: 'jpg' } %}
  {% set thumb1024_2x = { width: 1606, format: 'jpg' } %}
  {% set thumb1280 = { width: 1003, format: 'jpg' } %}
  {% set thumb1280_2x = { width: 2006, format: 'jpg' } %}
  {% set thumb1440 = { width: 1120, format: 'jpg' } %}
  {% set thumb1440_2x = { width: 2240, format: 'jpg' } %}
  {% set thumb1600 = { width: 1224, format: 'jpg' } %}
  {% set thumb1600_2x = { width: 2448, format: 'jpg' } %}
  {% set thumb1920 = { width: 1244, format: 'jpg' } %}
  {% set thumb1920_2x = { width: 2488, format: 'jpg' } %}
  {% set thumb2560 = { width: 1368, format: 'jpg' } %}
  
  <picture>
      <source media='(min-width: 2560px)' srcset="{{ image.getUrl(thumb2560) }} 1x">
      <source media='(min-width: 1920px)' srcset="{{ image.getUrl(thumb1920) }} 1x, {{ image.getUrl(thumb1920_2x) }} 1.5x">
      <source media='(min-width: 1600px)' srcset="{{ image.getUrl(thumb1600) }} 1x, {{ image.getUrl(thumb1600_2x) }} 1.5x">
      <source media='(min-width: 1440px)' srcset="{{ image.getUrl(thumb1440) }} 1x, {{ image.getUrl(thumb1440_2x) }} 2x">
      <source media='(min-width: 1280px)' srcset="{{ image.getUrl(thumb1280) }} 1x, {{ image.getUrl(thumb1280_2x) }} 2x">
      <source media='(min-width: 1024px)' srcset="{{ image.getUrl(thumb1024) }} 1x, {{ image.getUrl(thumb1024_2x) }} 2x">
      <source media='(min-width: 768px)' srcset="{{ image.getUrl(thumb768) }} 1x, {{ image.getUrl(thumb768_2x) }} 2x">
      <source media='(min-width: 600px)' srcset="{{ image.getUrl(thumb600) }} 1x, {{ image.getUrl(thumb600_2x) }} 2x">
      <source media='(min-width: 412px)' srcset="{{ image.getUrl(thumb412) }} 1x, {{ image.getUrl(thumb412_2x) }} 2x">
      <source media='(min-width: 360px)' srcset="{{ image.getUrl(thumb360) }} 1x, {{ image.getUrl(thumb360_2x) }} 2x">
      <img itemprop="image" src="{{ image.getUrl(thumb320) }}" alt='{{ image.title }}'>
  </picture>
  
  ```
  
  The problem is that this is generating a lot of queries and I wanted to find out if there is a more efficient way of coding this?
  
  **Tags:** craft3, image-transforms, performance
  
  
  ---
  
  ## 1 answers
  
  ### Answer by username_1 on 2022-02-22. Score: 7 | Accepted answer
  
  You can use the method [`Asset::getSrcset`](https://docs.craftcms.com/api/v3/craft-elements-asset.html#method-getsrcset) to generate a valid `srcset` attribute as well as the asset transforms included in it. But you will need to restructure your HTML a bit. The current approach works, but is very verbose and not optimal for different screen resolutions and image placements.
  
  Instead of using multiple source, just use one source without a `media` attribute that includes all variants in its `srcset`. Then add a `sizes` attribute that will tell the browser how large the image will be displayed depending on the viewport width. If the image always spans the full page, you can just set your `sizes` attribute to `100vw` (100 viewport width units). If your image is sized differently depending on the viewport, you will need to adjust the sizes attribute to match those sizes. [Here's a great article on MDN on responsive images, including how to use the `sizes` attribute](https://developer.mozilla.org/en-US/docs/Learn/HTML/Multimedia_and_embedding/Responsive_images).
  
  Now the final code can look like this:
  
  ```twig
  <picture>
      <source {{ attr({
          type: 'image/jpeg',
          srcset: image.getSrcset(
              [320, 360, 412, 600, 768, 1024, 1280, 1440, 1600, 1920, 2560],
              { format: 'jpg', }
          ),
          sizes: '100vw',
      }) }}>
      <img width="{{ image.width }}" height="{{ image.height }}" alt="{{ image.alt }}">
  </picture>
  
  ```
  
  The great thing about this approach is that browsers will take care of adjusting for pixel density for you. If you open the page with this image on a smartphone with a 360px wide display (CSS pixels) and a 2x display density (so a 720px screen), the browser will automatically select the 768px image, since it's the smallest available size that's large enough for the screen's resolution and density.
  
  Note that as per the spec browsers *may* select images based on other factors, such as using a smaller images if network conditions are poor, or using a cached image even if it's smaller than the currently required resolution. But in practice this rarely matters.
  
  By the way, with the code above, you can very easily add a second `<source>` with the same `srcset` and `sizes` attributes but using type `image/webp` and `format: 'webp'` in the transform to generate WebP variants of the images for browsers that support it. This will have a large impact on web performance.
  
  > **Comments:**
  > **username_0**: Perfect thank you a lot for helping me. I take the opportunity to ask you how precise you are in determining the various image sizes and how many you usually generate (for how many resolutions)?  
  > **username_0**: I have noticed that by using imagerx there are significant performance improvements (a lot less database queries). Do you use such a plugin for responsive images?  
  > **username_1**: @username_0 Most of our projects have containers with fixed widths (per viewport) and a multi-column layout (using Bootstrap, for example), so we have ~6 different fixed sizes in pixels – though it depends on the image positioning. For an image that stretches the whole viewport, there's only a single size. Then we generate the srcset with those sizes as well as some others for different pixel densities. You can't get every size in every possible resolution, that would be hundreds of images, so we usually just 'fill in the gaps' between sizes so that most devices will find a suitable image.  
  > **username_1**: @username_0 We don't use a plugin, the built-in image resizer works just fine for us. The resizing is a one-time operation for each placed image, after all, and the HTML output can be cached, avoiding excessive queries for most requests. BTW we have a reusable twig template to take care of this stuff, every other template just includes that template and passes it an image, the `sizes` attribute and the list of sizes for the `srcset`. I've written a bit about that here: https://craftcms.stackexchange.com/a/38383/11705  
  > **username_0**: Great! thank you so much for your valuable answers  
  
  ---
  
  