Categories
Responsive Images WordPress

WordPress, Responsive Images, and Dynamic Image Sizes

This is an addendum to my article WordPress Image Handling in a Responsive Images World. If you haven’t done so already you should read it to get the background.

Responsive Images in WordPress Core opens up a previously unattainable opportunity for the application to allow theme (and plugin) designers and developers to take control over image sizes. This would produce better designs, better user experiences, and a better impression of WordPress as a whole from its users. To get there the way images are added to posts and pages needs to be reworked. I wrote about the theory of what I think needs to happen to implement Responsive Images in WordPress yesterday in the article WordPress Image Handling in a Responsive Images World. Today I want to provide some practical ideas in the form of a thought experiment of how the image insertion task could be handled in this new reality, from hereon out referred to as the “Responsive Images World”.

The Problem (Current)

Right now, if you create a new post or page in WordPress and insert an image, you get to choose the size of that image: Thumbnail, Small, Medium, Large, or Original. These sizes are not just names: They are displayed alongside physical pixel sizes set by WordPress defaults or by you if  you changed the settings manually.

Once the image is inserted, the size you picked for it becomes a physical restraint, and that physical restraint will persist if and when the theme is changed.

Presently when an image is added to a post, the image size is permanently defined at insertion. If the theme is changed, the image stays the same size.

The Opportunity (Future)

In the Responsive Images World, when you insert an image, you get to choose the size of that image: Thumbnail, Small, Medium, Large, or Full Width. These sizes are not just names: They are displayed alongside percentage values that control the container width of the inserted image in relation to the main container of the current theme. These widths are defined by the theme designer and/or developer.

Once the image is inserted, the size you picked for it is a variable that changes with the currently active theme. For one theme a Medium width image may be 40%, for another it may be 60%. When the theme is changed, the actual image container size will change with it to realize the vision of the designer.

In the Responsive Images World, image sizes are defined by the theme and change depending on what theme is currently active.

How it could work

Given the premise set out in my previous post about the implementation of Responsive Images, here’s how Dynamic Image Sizes could work in the Responsive Images World:

As we do today, when a new theme is created, the developer sets a $content_width value to specify the maximum allowed width of content displayed in the theme. This becomes the maximum width of any inserted image.

In addition, the developer sets the parameters for the default image sizes using a function similar to add_image_size() called add_default_image_size():

 

<?php 
  add_default_image_size( $name, $css_width, $display_width ); 
?>

The sizes to be defined would be thumbnail, small, medium, large, and full_width

The parameters created by the add_default_image_size() function define the CSS width of the image in percentages and the displayed max-width of the image in pixels. $css_width is passed to the Image Size drop-down in the UI to indicate to the user how large the image will be. $display_width is passed to the Responsive Images function to dynamically populate the last value in the sizes attribute for images inserted with this size.

The result will be that the user selects an image size (eg “medium”) and the theme developer decides what actual size that image is when displayed in the theme. Because of Responsive Images and the $display_width parameter set by the theme and linked to the sizes attribute, the theme will always work with the browser to use the ideal image file from srcset based on the actual displayed size of the image, not the maximum width set by $content_width or the viewport.

Challenges

There is an obvious challenge here that requires a substantial shift in how WordPress outputs code in the browser and may cause some significant issues with caching: WordPress post (and page) HTML is stored as more or less persistent content in the database. That includes any <img> tags. However, because the sizes attribute is a presentational element embedded in the raw HTML of the page, with this new approach WordPress has to populate this value dynamically on load based on the size parameters set in the theme. In a situation where the HTML is cached this will cause problems.

Another issue: What happens if a user manually resizes an image with click-and-drag behaviors in the editor? I have no answers for that one yet, but I am sure there is an obvious answer hiding somewhere.

Categories
Responsive Images WordPress

WordPress Image Handling in a Responsive Images World

Note to the reader: This post falls under the umbrella “Morten thinking out loud”. You have been warned.

This is the first of a 2-part article. Be sure to read the 2nd part WordPress, Responsive Images, and Dynamic Image Sizes once you’re done.

The colorful light show in the underground passageway in Chicago's O'Hare Airport

Consider the image above. Depending on your screen resolution and size, the image file you are looking at will be different from the file you’d look at on a smaller or bigger screen. This is thanks to Responsive Images. And it’s really cool. That said, we have a ways to go before this new technology can truly improve WordPress and the sites it runs. And I think a large part of that work is rethinking how WordPress handles images behind the scenes. That’s what this article is about.

Responsive Images are rapidly approaching as a standard, and the RICG team are doing continuous work on a plugin that adds responsive images functionality to WordPress sites today. With any luck we’ll see the plugin baked into WordPress core in a future release and all WordPress sites will serve up responsive images out of the box.

In this article I’m not going to talk about the responsive images implementation being worked on in itself; the work being done by the group is stellar (you can follow along in the Github repo and the Slack channel) and some of the best minds in the business are working on improving the implementation. Instead I want to present some ideas about how responsive images in WordPress can change (and improve) the modality of image handling for theme and plugin developers as well as the end-user.

Status Quo: Fixed Image Sizes

Image size selection in WordPress
Image size selection in WordPress

One of the features that makes WordPress an ideal platform for introducing responsive images is its current handling of fixed image sizes:

When an image is uploaded to WordPress the application generates a series of scaled down versions of that image in addition to the original (provided the original image is larger than each of the sizes):

  • A square thumbnail (defaults to cropped 150 x 150px)
  • A medium image (defaults to max width and/or height of 300 x 300px)
  • A large image (defaults to max width and/or height of 1024 x 1024px, typically limited by theme settings)

These default sizes can be changed from admin panel under Settings -> Media, but few users touch these settings.

When the user adds an image to a post or page in the editor they can select from any of these sizes along with alignment settings to scale and position the image as desired.

The image is added with a standard <img> tag that calls in the image file for the selected size and carries with it width and height attributes to correspond with the selected size.

Theme and plugin authors also have the ability to add additional image sizes through the add_image_size(); function. This is typically used to display specific image sizes or crops in specific regions on the site, most commonly Featured Images. For brevity and to limit the scope of this article I won’t bring this into the equation.

Responsive Images Change Everything

This all works well for static images, but as we move to responsive images we have the opportunity to rethink what happens when images are generated and added to the content.

Currently the RICG Responsive Images plugin hooks in to the existing Add Media functionality and alters the HTML output of the added image to include srcset and sizes attributes. What used to look like this:


<img 
  class="alignnone size-large wp-image-1717" 
  src="http://[]/wp-content/uploads/2020/01/DSCF2034-1024x683.jpg" 
  alt="DSCF2034" 
  width="640" 
  height="427"
>

Ends up looking like this with the plugin:


<img 
  class="alignnone size-large wp-image-1717" 
  src="http://[]/wp-content/uploads/2015/06/DSCF2539.jpg" 
  srcset="http://[]/wp-content/uploads/2015/06/DSCF2539-300x200.jpg 300w, 
          http://[]/wp-content/uploads/2015/06/DSCF2539-700x467.jpg 700w, 
          http://[]/wp-content/uploads/2015/06/DSCF2539-735x490.jpg 735w, 
          http://[]/wp-content/uploads/2015/06/DSCF2539-368x245.jpg 368w, 
          http://[]/wp-content/uploads/2015/06/DSCF2539.jpg 4896w"
  alt="DSCF2539" 
  width="4896" 
  height="3264" 
  sizes="(max-width: 4896px) 100vw, 4896px"
>

The problem here is that because the RICG Responsive Images plugin knows nothing about the displayed size of an image, the sizes attribute has to use the max width of the image itself coupled with the width of the viewport to figure out what image file to load. As a result, if you have a gigantic image like the one in the example, and you display it on a gigantic screen or one with high resolution, the full size image (4896px wide) will load even if the displayed size is only 800px.

What we have here is a clash between old methodology and new technology. And it stems from the fact that WordPress is still an image classicist. but in a Responsive Images world it needs to be a modernist.

The solution, simple in theory and complex in execution, is for the image size drop-down to specify the sizes attribute rather than the image file size. And that sizes attribute should be controlled by the theme.

Let me explain.

New Modalities

What’s interesting about Responsive Images is that rather than thinking about images as fixed-size entities displayed in a responsive landscape we can start thinking about them as responsive containers with images inside.

Currently when you add an image to a responsive site you are in reality setting up a container and displaying the image within that container. Because the site is responsive that container will have a max-width (either specified in the container itself or constrained by an ancestral container) and will flex and resize depending on the size of the viewport. The image served up is instructed to fill the width of the container and shrink the height proportionately.

To ensure bandwidth isn’t wasted, tools like WordPress offer the user image sizes to choose from when adding an image to a post or page. These sizes in turn hard-code the maximum width and height of the img element to the size of the image.

In a Responsive Images world this makes no sense.

With Responsive Images we should only be specifying the size of the container through CSS and the sizes attribute. The browser is responsible for picking and displaying the correct image file based on the available space and display resolution. The physical size of the image, as specified in the img element is irrelevant (and should be omitted entirely imo).

This means when the user picks a size, they should not be picking a size based on the available generated files, but rather a container size based on the sizes specified by the theme developer. And if the user changes the size of the container with click-and-drag behaviors, that change should be reflected in the container through the sizes attribute.

Brave New Responsive World

This has some compelling (and quite disruptive) implications:

First of all, there is no need for the customizable Small, Medium, and Large image file sizes any more. At least not in terms of available sizes of images to be added to the site. Instead WordPress could generate some standardized sizes for small, medium, and large displays behind the scenes without ever telling the user about them. Granted, cropped versions for thumbnails and Featured Images still need to be made, but again the sizing of these can be left to a standardized function within WordPress.

Secondly, this allows theme developers (and to a degree plugin developers) to incorporate image sizes of in-post images into their designs. Because we don’t have to think about the physical size of the image any more but instead the size of the container, theme developers should be able to specify these sizes (Small, Medium, Large, whatever) in the theme and it is these container sizes, reflected in CSS and the sizes attribute, that are offered up to the user as options when an image is added.

Work is already being done in the RICG Responsive Images plugin to allow theme developers to customize the sizes attributes for images and in an ideal world I think this should become the new standard.

Finally, and this is where things get really interesting imo, there is an opening here for the possibility of doing away with image cropping all together, moving instead to cropping through CSS clipping. Because of the nature of Responsive Images as interchangeable sources, cropping can produce a large number of extraneous files, but all this is based on the old image-file-has-to-fit-container mentality from the pre-responsive images era. Since the concern now is only the container inside which the image is placed, there is no reason why a developer can’t specify positioning and crop factors using CSS, thereby not only eliminating the need for generation of cropped images, but also allowing for new and interesting behaviors like dynamic responsive cropping and user-controlled cropping on an image-to-image basis.

Overhaul Required

If  you’re with me so far one thing should be abundantly clear by this point: This change will require a complete overhaul of how images are handled by WordPress. And this overhaul is actually in progress through the work of the RICG Responsive Images team and the ImageFlow team. I’ve mulled about this to members of both teams for some time and I hope that with this post we can start the conversation in earnest and put some meat on these bones.

It is quite possible that I am off on a path into the wilderness here and that what I’m proposing is not feasible, but I am convinced this needs to be explored. Responsive Images are a fundamentally different animal from regular old images, and they require a whole new way of thinking. Trying to cage them in the old modalities of image sizes makes no sense. It is time to rethink everything. I propose we start here.