# tagged: , , , 30 Comments

WTFWG

This morning, Ian Hickson emailed the WHATWG mailing list mentioning that a attribute that was currently being discussed on the list (srcset) is now added to the draft of the spec. To understand why this sucks, a little background is needed.

Responsive images are a difficult beast to tame: there really isn’t a good solution for them today. As a result, some discussion started on the WHATWG mailing list months ago about what to do. The WHATWG pointed out that the list was for standardizing and suggested it would be better if the discussion were moved into a community group.

So, obediently, a community group chaired by Mat Marquis was started (in February). A lot of discussion took place about the appropriate way to handle responsive images and one solution, the new picture element, garnered the majority of support.

On May 10th, the previously mentioned srcset attribute was presented on the WHATWG mailing list by someone from Apple.

That same day it was recommended to the list that they take a look at all the discussion that had taken place in the community group. A debate about the two solutions ensued.

The feedback from developers was not particularly glowing. To quote Matt Wilcox:

I do not see much potential for srcset. The result of asking the author community was overwhelmingly negative, indirection or no indirection.

It was argued by Simon Pieters of Opera that the srcset attribute would be easier to implement and that as a result, that would help developers:

I think an attribute is simpler to implement and thus likely to result in fewer bugs in browsers, which in turn benefits Web developers.

This morning, the attribute was added to the spec.

I’ve got my own opinion about the correct solution, but that’s not really what’s I think is most troubling here. Note what happened:

  1. Developers got involved in trying to standardize a solution to a common and important problem.
  2. The WHATWG told them to move the discussion to a community group.
  3. The discussion was moved (back in February), a general consenus (not unanimous, but a majority) was reached about the picture element.
  4. Another (partial) solution was proposed directly on the WHATWG list by an Apple employee.
  5. A discussion ensued regarding the two methods, where they overlapped, and how the general opinions of each. The majority of developers favored the picture element and the majority of implementors favored the srcset attribute.
  6. While the discussion was still taking place, and only 5 days after it was originally proposed, the srcset attribute (but not the picture element) was added to the draft.

What. The. Hell.

The developer community did everything asked of them. They followed procedure, they thoroughly discussed the options available. They were careful enough to consider what to do for browsers that wouldn’t support the element—a working polyfill is readily available. Their solution even emulates the existing standardized audio and video elements.

Meanwhile an Apple representative writes one email about a new attribute that only partially solves the problem and the 5 days later it’s in the spec. In case there is any doubt, I’m not blaming him at all for how this all played out. That blame falls on the WHATWG. Whatever their rationale was for putting this in the draft, the method in which it was added reeks of valuing the opinion of implementors over developers.

In the draft of the W3C HTML design principles, they clearly state the priority that should be given when determining standards:

In case of conflict, consider users over authors over implementors over specifiers over theoretical purity. In other words costs or difficulties to the user should be given more weight than costs to authors; which in turn should be given more weight than costs to implementors; which should be given more weight than costs to authors of the spec itself, which should be given more weight than those proposing changes for theoretical reasons alone.

Those levels of priority make a lot of sense to me and it’s discouraging (to say the least!) to see them dismissed in this case. This kind of thing simply cannot happen. It’s tough to get people to voice their opinions to begin with. To find that their opinion holds no weight won’t make it any easier going forward.

What message does it send when developers try to contribute their time, energy and effort to help solve a problem only to have it so casually dismissed?

As Scott Jehl responded on Twitter:

insulting. Not to mention, that it can’t work today. What was the purpose of our @w3c community group?

Insulting indeed. Not too surprising though. After all, we’ve seen this sort of thing before.

# tagged: , , , 0 Comments

BDConf:focus on Responsive

If you’ve gone to a BDConf (more on the recent Orlando event very soon!), you know we keep the focus pretty tight: web design and development for beyond the desktop. No native discussion, just web. We thought it would be fun to get even more focused. So on June 4th in Minneapolis, we’ll host the first ever BDConf:focus on event and do a deep dive into responsive design: all day, all responsive.

The lineup is amazing. Seriously.

Dave Rupert, lead developer at Paravel, co-host of the ShopTalk podcast, and creator of awesome tools like FitVids and FitText, will get the day kicked off with a four hour workshop.

After lunch, Mat Marquis will get the afternoon started with his presentation, “Next Steps for Responsive Design”. Mat worked on the Boston Globe project and heads up the Responsive Images Community Group for the W3C, so he’s got some hard-earned experience to pull from. He’s also a seriously funny guy.

Then, Kristofer Layon will present “The Minimal Viable Web”. Kristofer is the author of two books, most recently the excellent “Mobilizing Web Sites”. I love how practical and pragmatic that book is and I expect his talk will keep the same tone.

I’ll close the day with a new talk for me, “Creating Responsive Experiences”. I’ve been on a kick for awhile now that I think responsive design has to be about more than just layout, and I’ll try to make my case (and back it up with a few examples).

It should be an awesome day! The venue, Open Book, has a cool feel to it and we’re going to keep attendance low—you won’t be lost in a huge ballroom of people.

There are still passes available. If you want to make the trip (and you do!), code ‘KADLEMN’ will shave $100 off the cost of registration.

I hope to see you in Minneapolis—it’s going to be awesome!

# tagged: , , , , 36 Comments

Media Query & Asset Downloading Results

A little while back, I mentioned I was doing some research for the book about how images are downloaded when media queries are involved. To help with that, I wrote up some automated tests where Javascript could determine whether or not the image was requested and the results could be collected by Browserscope for review. I posted some initial findings, but I think I’ve got enough data now to be able to go into a bit more detail.

First, any credit has to go to the awesome team at Cloud Four. Most of the tests were created by them for some testing they were doing. I just added some Javascript to automate them.

On to the results!

Test One: Image Tag

Run the test

This page tried to hide an image contained within a div by using display: none. The HTML and CSS are below:

<div id="test1">
    <img src="images/test1.png" alt="" />
</div>

@media all and (max-width: 600px) {
    #test1 { display:none; }
}

The results

If there is one method of hiding images that I can say with 100% certainty should be avoided, it’s using display:none. It’s completely useless. It appears that Opera Mobile and Opera Mini don’t download the image (see the initial post for the reasons why), but the image is requested by, well, everyone else.

Tested Requests Image
Android 2.1+ Yes
Blackberry (6.0+) Yes
Chrome (4.1)+ Yes
Chrome Mobile Yes
Fennec (10.0+) Yes
Firefox (3.6+) Yes
IE Yes
iOS (4.26+) Yes
Kindle (3.0) Yes
Opera (11.6+) Yes
Opera Mini (6.5+) No
Opera Mobile (11.5) No
RockMelt Yes
Safari (4+) Yes

Conclusion

Simple: don’t do this.

Test Two: Background Image Display None

Run the test

In this test, a div was given a background image. If the screen was under 600px wide, the div was set to display:none. The HTML and CSS are below:

<;div id="test2">;<;/div>;

#test2 {
    background-image:url('images/test2.png');
    width:200px;
    height:75px;
}
@media all and (max-width: 600px) {
    #test2 {display:none;}
}

The results

The same as with the first test: every browser tested, aside from Opera Mini and Opera Mobile, will download the image.

Tested Requests Image
Android 2.1+ Yes
Blackberry (6.0+) Yes
Chrome (4.1)+ Yes
Chrome Mobile Yes
Fennec (10.0+) Yes
Firefox (3.6+) No
IE Yes
iOS (4.26+) Yes
Kindle (3.0) Yes
Opera (11.6+) Yes
Opera Mini (6.5+) No
Opera Mobile (11.5) No
RockMelt Yes
Safari (4+) Yes
Silk Yes

Conclusion

Once again: don’t do this. Thankfully, as some of the other tests show, there are a few easy ways to hide background images without having the image requested.

Test Three: Background Image, Parent Object Set to Display None

Run the test

In this test, a div was given a background image. The parent of the div (another div) was set to display:none when the screen was under 600px wide. The HTML and CSS are below:

<;div id="test3">;
    <;div>;<;/div>;
<;/div>;

#test3 div {
    background-image:url('images/test3.png');
    width:200px;
    height:75px;
}
@media all and (max-width: 600px) {
    #test3 {
        display:none;
    }
}

The results

Kudos to Jason Grigsby for catching this one. On the surface, it’s not entirely obvious why this would be any different than test two. However, when doing his initial research, he noticed this seemed to make a difference so he decided to test it. Lucky for us he did because this method is actually pretty reliable.

Tested Requests Image
Android 2.1+ No
Blackberry (6.0+) No
Chrome (16+) No
Chrome Mobile No
Fennec (10.0+) Yes
Firefox (3.6+) No
IE 9+ No
iOS (4.26+) No
Kindle (3.0) No
Opera (11.6+) No
Opera Mini (6.5+) No
Opera Mobile (11.5) No
Safari (4+) No

Conclusion

This method works well. With the exception of the over-eager Fennec, every tested browser only downloads the image when needed. The issue with this method is that you do have the requirement of being able to hide the containing element. If that’s an option, then feel free to go ahead and use this approach.

Test Four: Background Image with Cascade Override

Run the test

In this test, a div is given a background image. If the screen is under 600px, then the div is given a different background image. This tested to see if both images were requested, or only the one needed. The HTML and CSS are below:

<;div id="test4">;<;/div>;

#test4 {
    background-image:url('images/test4-desktop.png');
    width:200px;
    height:75px;
}
@media all and (max-width: 600px) {
    #test4 {
        background-image:url('images/test4-mobile.png');
    }
}

The results

While certainly better than using display:none, this method is a little spotty.

Tested Requests Both
Android 2.1-3.0? Yes
Android 4.0 No
Blackberry 6.0 Yes
Blackberry 7.0 No
Chrome (16+) No
Chrome Mobile No
Fennec (10.0+) Yes
Firefox (3.6+) No
IE 9+ No
iOS (4.26+) No
Kindle (3.0) Yes
Opera (11.6+) No
Opera Mini (6.5+) No
Opera Mobile (11.5) No
Safari 4.0 Yes
Safari 5.0+ No

Conclusion

I’d avoid it. While the situation is improving, Android 2.x, which dominates the Android marketshare, still downloads both images as does Fennec and the Kindle. Between the three, but particularly because of Android, I would recommend looking at other options.

Test Five: Background Image Where Desktop Image Set with Min-Width

Run the test

In this test, a div is given one background image if the (min-width: 601px) media query matches, and a different one if (max-width: 600px) matches. The HTML and CSS is below:

<;div id="test5">;<;/div>;

@media all and (min-width: 601px) {
    #test5 {
        background-image:url('images/test5-desktop.png');
        width:200px;
        height:75px;
    }
}
@media all and (max-width: 600px) {
    #test5 {
        background-image:url('images/test5-mobile.png');
        width:200px;
        height:75px;
    }
}

The results

The situation here is a little better.

Tested Requests Both
Android 2.1+ No
Blackberry (6.0+) No
Chrome (16+) No
Chrome Mobile No
Fennec (10.0+) Yes
Firefox (3.6+) No
IE 9+ No
iOS (4.26+) No
Kindle (3.0) No
Opera (11.6+) No
Opera Mini (6.5+) No
Opera Mobile (11.5) No
Safari (4+) No

Conclusion

More browsers play along this time. Fennec, as always, just can’t control itself. Android 2.x is….odd. It requests both images, but only if the screen size is over 600px and the min-width media query kicks in. This behavior appears to stop as of Android 3. This is an odd one and I would love to know why the heck it happens. Actually, good news here. Jason Grigsby pinged me and said his results for this test weren’t jiving with what I reported here, so I re-ran the tests on a few Android 2.x devices. Turns out, my initial results were off: Android 2.x plays nicely and my initial runs of this test on that platform were wrong. Not only is this good news for developers, but it is also a much more sane behavior and it has restored my faith in humanity. Or at least my faith in Android.

It’s also worth nothing that if you use this method, you’ll need to consider alternate options for Internet Explorer 8 and under. Those versions of the browser don’t support media queries, so no image will be applied. Of course, this is simple enough to fix with conditional comments and an IE specific stylesheet.

Test Six: Background Image Display None (max-device-width)

Run the test

This test was the same as test two, but it used max-device-width for the media query instead of max-width. The HTML and CSS is below:

<;div id="test6">;<;/div>;

#test6 {
    background-image:url('images/test6.png');
    width:200px;
    height:75px;
}
@media all and (max-device-width: 600px) {
    #test6 {
        display:none;
    }
}

Conclusion

I’m not going to spend much time on this, as it ended up being a throw away test. There were no differences in behavior between this and test two. The test was added because of a tweet where someone had mentioned they were getting different results than the original tests by Cloud Four, but the discrepancy ended up being caused by something else entirely (a typo, if I remember right).

Test Seven: Cascade Override for High Resolution

Run the test

The final test was added to the suite a bit late. With the retina iPad around the corner, there were a lot of posts about how to handle serving images to high-res displays. In one post, Brad Frost mentioned he thought it would be interesting to see test results for this, so I added it in.

In this test, a div is given a background image. Then, by using the min-device-pixel-ratio meda query, a new background image was applied if the minimum ratio was 1.5.

The HTML and CSS are below:

<;div id="test7">;<;/div>;

#test7 {
    background-image:url('images/test7-lowres.png');
    width:200px;
    height:75px;
}
@media only screen and (-webkit-min-device-pixel-ratio: 1.5),
only screen and (min--moz-device-pixel-ratio: 1.5),
only screen and (-o-min-device-pixel-ratio: 3/2),
only screen and (min-device-pixel-ratio: 1.5) {
    #test7 {
        background-image:url('images/test7-highres.png');
        width:200px;
        height:75px;
    }
}

The results

Of all the tests, this one is the one that could benefit the most from having some more people run it. That being said, it does look like the following behavior is accurate.

Tested Requests Both
Android 2.1-3.0? Yes
Android 4.0 No
Blackberry 6.0 No
Blackberry 7.0 No
Chrome (16+) No
Chrome Mobile No
Fennec (10.0+) No
Firefox (3.6+) No
IE 9+ No
iOS (4.26+) No
Kindle (3.0) No
Opera (11.6+) No
Opera Mini (6.5+) No
Opera Mobile (11.5) No
Safari 4.0+ No

Conclusion

Again, this test could stand to be run a bit more, just to be safe. It looks like this method will work the vast majority of the time. Unfortunately, it appears Android 2.x will download both images if the device pixel ratio is above or equal to 1.5 (or whatever value you set in the media query). So in the case of the above tests, if you’ve got a high resolution device running Android 2.x you’re out of luck.

The good news, for now, is that I’m unaware of any Android device with a device pixel ratio over 1.5. So if you’re targeting the retina display iOS devices, you could set your min-device-pixel-ratio to 2 and be safe. And of course, now that I’ve said it, I fully expect the first 3 comments for this post to all correct me and point out the one Android device that just has to prove me wrong.

The earliest rounds of this test looked more promising for Android, so this is a bit of a bummer for me. They’re the only browser that seems to mess it up, but they’re also one of the biggest players.

Recommendations

If you’re going to hide a content image, you’re not going to be able to do it by setting display:none. I recommend using a Javascript or server-side based approach instead.

If you want to hide a background image, your best bet is to hide the parent element. If you can’t do that, then use a cascade override (like test five above) and set the background-image to none when you want it hidden.

For swapping background images, define them both inside of media queries.

Going Forward

If you run any of the tests and think something above is incorrect, either drop me a line or say report it on GitHub so I can dig into it. The same goes for adding any additional tests.

# tagged: , , 2 Comments

Looking for the right tool

Whether or not to design in the browser is an often debated subject. The latest discussion seems to be prompted, in part, because of the recent Responsive Summit (by the way, if you haven’t done so already, be sure to check out a few recaps of the day).

Mark Boulton just put his thoughts to screen with a post entitled “Responsive Summit: The One Tool”. In it, he makes the case that knowing your materials is more important than using a specific tool. He makes an excellent point when he discusses why he feels comfortable in Photoshop:

Since 1997, I’ve been working almost exclusively on the web. Throughout all of that time, the realisation of what the projects would look like are done in Photoshop. That means, yes, I’ve been using Photoshop in a production environment for fifteen years. Malcolm Gladwell said it takes 10,000 hours, or 10 years of repetitive use, to become an expert in something. I guess that means I’m an expert in creating pictures of websites. Photoshop is like an extension of my mind. To use Photoshop for me is as effortless and almost as fast as a pencil. I get stuff done; quickly.

That point, that the familiarity you have with a tool matters, is an important one to keep in mind. Designing is a creative endeavour. You can’t do it well with tools you aren’t entirely comfortable with.

If we had been designing in the browser since 1997, this would all be a non-issue. Of course it wasn’t possible back then to do so—our tools were too limited. That’s not the point I’m making. The point is that if we had that same level of experience designing in the browser, I suspect no one would debate whether the approach made sense. Designing in the browser lets you get deeply entrenched in the characteristics of the web. Designing in a graphics editor like Photoshop removes you from them.

Those against designing in the browser talk about how working in code is too limiting. Of course the opposite is true as well—working in a graphics editor is too limiting in many ways. You are limited to designing for a specific size at a time. You are limited by not being able to design for interactions. That’s a big one. The web is an interactive medium, not a static one. It has little in common with print and much more in common with software. Graphic editors, for all their powerful tools, aren’t equipped to handle this.

There is room for a better tool here. One that lets you experiment easily, but doesn’t detach you from the constraints and capabilities of the environment you are creating for. Later in his post, Mark continues:

I can’t have happy accidents in a browser when I’m writing specific rules and then watching the results in a browser. There is too much in the feedback loop.

This made me think of a presentation by Bret Victor called “Inventing on Principle”. Not only do I recommend it, I think it should be required viewing.

During the presentation he discusses the need for immediate feedback from our tools:

Creators need an immediate connection to what they create. And what I mean by that is when you’re making something, if you make a change or you make a decision, you need to see the effect of that immediately. There can’t be any delay, and there can’t be anything hidden. Creators have to be able to see what they’re doing.

Specifically, he tackles coding. He demonstrates a tool that lets him instantly see how the changes in his Javascript affect the canvas for which he is creating. This instantaneous feedback provides fertile ground for experimentation, and he demonstrates that over and over in the video. Because of the direct connection between the code and the result, you’re able to start using advanced controls (start around 3:45 into the video, and again around 10:45) to help the process of discovery and experimentation.

This, I think, is where we need to head. We need to be able to create on the web, but we need tools that make it easier for us to experiment. Tools that let us be creative without decoupling us from the very medium we are creating for.

We’re not likely to ever remove a graphic editor completely from our workflow, nor should that be our goal. There is nothing wrong with graphic editors. We simply need to be aware of what they are good at, and where they fall short. Instead, our goal should be to move towards tools and processes that let us capitalize on the interactive nature of the web.

It’s about using the right tool for the right job. I’m not convinced we have the right tool yet.

# tagged: , , , 20 Comments

Media Query & Asset Downloading Tests

When you’re building a responsive site, there will undoubtedly be times when you need to change a background image, or when you need to hide an image for a specific resolution range. Unfortunately if you’re not careful, this can lead to multiple images being downloaded even when they aren’t being used. A few people—including Jason Grigsby, Greg Rewis and Aaron Mentele—have done some excellent testing about how images are downloaded when media queries are involved. So far, the tests have been conducted using manual methods. There is absolutely nothing wrong with that, but I wanted to find a way to make the testing more automated so that a wider group of people could contribute to the test results.

To that end, I’ve hacked together a few tests (using Jason’s tests as a starting point) that store their results in Browsercope. The test is fairly simple. For each test case, I check to see if the background image (or content image) has been loaded by checking the image.complete property. The property (which appears to be well supported) returns true if the image has been  requested and downloaded, and false otherwise. So, if I want to see if image2.png has been downloaded, my code looks like this:

var myImage = new Image();
myImage.src = ‘http://somedomain.com/image2.png’;

if (myImage.complete) {
 //already downloaded
} else {
 //not yet downloaded
}

Early results

It’s early, but already a few trends (some interesting, some less so) are emerging:

  • Setting an image to display:none won’t stop the image from downloading (see test 1). So don’t do it. We already knew this, but the tests are reinforcing it.
  • The same goes for setting an element to display:none: the background will still be downloaded by everybody (see test2).
  • Setting the parent object to display:none, however, does work pretty consistently (see test 3). It looks like Fennec still downloads the image, but Android, iOS and Opera won’t.
  • Downloading behavior for a simple cascade override is pretty inconsistent (see test 4). However, setting background images within a media query and then overriding seems to work pretty well (test 5). Fennec is a little eager again, but Android, iOS, Opera and the Kindle only download what’s needed.

Finally, my favorite nugget of information so far pertains to Opera Mobile. Opera, as it turns out, is darn clever. Instead of using the parser to trigger resource downloading, they use layout code. This means that since they have information about viewport size and visibility settings, they can be much more selective about which resources they download. So, for example, if an element is outside the viewport then the background image doesn’t have to be downloaded on page load.

When I talked to Ola Kleiven of Opera about this optimization, he said that Opera used to implement the same behavior on Opera for desktop prior to 11.60 but had to pull it due to compatibility reasons. Developers were relying on things like the load events of these images, so when they didn’t load in Opera, things would break. It’s too bad: it’s an interesting and effective optimization method. I would love to see this behavior implemented cross-browser, but as an opt-in feature (maybe a meta tag or something could trigger it).

Thanks to everyone who has already been testing—it’s been fun to watch the results come in! If you haven’t run the tests yet and you’ve got a few minutes, please do. Once the number of results gets to a nice level, I’ll post a more detailed follow-up about which browsers behave in what ways. I’ll also include any interesting findings in the book.

In the meantime, feel free to fire up the tests on any and all devices you have. If you think of another test you would like to see added, or see a potential issue with the test, let me know. One of the benefits of automating the test results is that it should be very easy to add new tests and quickly get broad results.