The document is a presentation on responsive web design (RWD) given by Zach Leatherman. It discusses the goals of RWD, including providing a flexible grid and flexible media. It also covers potential performance issues with RWD like unnecessary CSS downloads and large images on small screens. The presentation provides solutions to these problems like using media queries to separate CSS and choosing minimal CSS when possible.
1. Performance &
Responsive Web Design
(RWD)
NebraskaJS via @zachleat
November 8, 2013
Thursday, November 8, 12
2. About Me
✤ @zachleat on
✤ zachleat.com
underscore_dot.dash@zachleat.com
✤ Zach Leatherman
✤
Thursday, November 8, 12
3. My Projects
✤ BigText ✤ parseIntimate.com
Thursday, November 8, 12
4. My Projects
✤ ALARMd.com ✤ f2em.com
Thursday, November 8, 12
5. Housekeeping
✤ We need one or more volunteers to speak at January’s NebraskaJS.
✤ Tweet @nebraskajs with Topic Ideas even if you don’t want to speak.
Thursday, November 8, 12
6. Goals
✤ Primer
✤ RWD !== Media Queries
✤ 99 Problems
✤ Buzzkills
✤ RWD Showcase Showdown
✤ Be kind, RWD.
Thursday, November 8, 12
8. RWD is
✤ A Flexible Grid (Fluid: % + Min Widths)
✤ Flexible Media (Images, Video)
✤
(Not Just) Media Queries
http://unstoppablerobotninja.com/entry/on-being-responsive
Thursday, November 8, 12
12. RWD & performance
✤ Two alternatives to RWD:
✤ Do nothing
✤ Use a separate m.dot site
✤ Redirects are slow.
✤ Maintenance of UA-Parsing Server
Side Redirects (WURFL updates ~monthly)
✤ Content Strategy (Desktop Mode link)
http://en.m.wikipedia.org/?useformat=mobile#_
Thursday, November 8, 12
13. Google recommends RWD
✤ “It keeps your desktop and mobile content on a single URL, which
is easier for your users to interact with, share, and link to and for
Google’s algorithms to assign the indexing properties to your
content.”
✤ “Google can discover your content more efficiently as we wouldn't
need to crawl a page with the different Googlebot user agents to
retrieve and index all the content.”
http://googlewebmastercentral.blogspot.com/2012/06/recommendations-for-building-smartphone.html
Thursday, November 8, 12
14. Content Strategy
“Mobile users want to see our menu,
hours, and delivery number. Desktop
users definitely want this 1mb png of
someone smiling at a salad.”
https://twitter.com/wilto/status/63284673723375616
Thursday, November 8, 12
16. 99 Problems
✤ Browsers Download and Block Rendering on Unnecessary CSS
✤ Browsers Sometimes Download Unnecessary Images
✤ Big Images are Wasted on Small Screens
✤ Related: Retina Images are Wasted on <snob>Blurry</snob>
Screens
Thursday, November 8, 12
17. The “Average” Web Page
http://httparchive.org/interesting.php#bytesperpage
Thursday, November 8, 12
18. JavaScript Can Block
✤ “With scripts, progressive rendering is blocked for all content
below the script.”
http://developer.yahoo.com/blogs/ydn/posts/2007/07/high_performanc_5/
Thursday, November 8, 12
19. JavaScript that Doesn’t Block
<script
src></script>
</body>
http://developer.yahoo.com/blogs/ydn/posts/2007/07/high_performanc_5/
Thursday, November 8, 12
20. JavaScript that Doesn’t Block
<head>
<!-‐-‐
Downloads
right
away
-‐-‐>
<script
src
async></script>
<!-‐-‐
Waits
to
download
-‐-‐>
<script
src
defer></script>
http://calendar.perfplanet.com/2010/the-truth-about-non-blocking-javascript/
Thursday, November 8, 12
21. JavaScript that Doesn’t Block
var
script
=
document.createElement("script");
script.type
=
"text/javascript";
script.src
=
"foo.js";
document.getElementsByTagName("head")
[0].appendChild(script);
http://calendar.perfplanet.com/2010/the-truth-about-non-blocking-javascript/
Thursday, November 8, 12
22. Stylesheets Block
✤ “Browsers (except Opera) block rendering until all screen CSS
arrives. With the worst possible experience: white page.”
✤ “Browsers download CSS they don't need, e.g. print, tv, device-
ratio... And most browsers (except Opera and Webkit) block
rendering because of these too”
✤ http://www.phpied.com/files/css-loading/mq.php?mq=all
http://www.phpied.com/css-and-the-critical-path/
Thursday, November 8, 12
23. WebKit
<!-‐-‐
blocking
stylesheet,
nothing
renders
until
it
is
downloaded
and
parsed
-‐-‐>
<link
href="main.css"
rel="stylesheet">
<!-‐-‐
non-‐blocking,
low
download
priority
because
of
the
evaluated
media
query
-‐-‐>
<link
href="i-‐want-‐a-‐monitor-‐of-‐this-‐size.css"
rel="stylesheet"
media="(min-‐width:
4000px)">
<!-‐-‐
print
stylesheet
is
non-‐blocking
-‐-‐>
<link
href="noop.css"
rel="stylesheet"
media="print">
http://www.igvita.com/2012/06/14/debunking-responsive-css-performance-myths/
Thursday, November 8, 12
24. Everything Else*
<!-‐-‐
blocking
stylesheet,
nothing
renders
until
it
is
downloaded
and
parsed
(timeouts
may
vary)
-‐-‐>
<link
href="main.css"
rel="stylesheet">
<link
href="i-‐want-‐a-‐monitor-‐of-‐this-‐size.css"
rel="stylesheet"
media="(min-‐width:
4000px)">
<link
href="noop.css"
rel="stylesheet"
media="print">
Thursday, November 8, 12
25. Downloading CSS
http://scottjehl.github.com/CSS-Download-Tests/
Thursday, November 8, 12
26. Downloading CSS
Firefox 16 Opera 12
Safari 6 Chrome 22
Thursday, November 8, 12
27. Solutions
✤ CSS is sacred. Choose minimal when possible.
✤ Separate <link> elements for each Media Query
✤ Doesn’t scale if you have a lot of breakpoints.
✤ Good for WebKit, what about everything else?
✤ eCSSential
Thursday, November 8, 12
28. eCSSential
✤ “Making responsive CSS load the way it should.”
✤ Downloads Blocking CSS that matches media
queries
✤ Downloads other CSS async, non-blocking
✤ https://github.com/filamentgroup/eCSSential
Thursday, November 8, 12
29. matchMedia
if
(window.matchMedia("(min-‐width:
400px)").matches)
{
/*
the
view
port
is
at
least
400
pixels
wide
*/
}
else
{
/*
the
view
port
is
less
than
400
pixels
wide
*/
}
https://developer.mozilla.org/en-US/docs/DOM/window.matchMedia
Thursday, November 8, 12
30. matchMedia
http://caniuse.com/#feat=matchmedia
Polyfill: https://github.com/paulirish/matchMedia.js/
Careful with IE8-, the polyfill requires Media Query support
Thursday, November 8, 12
32. eCSSential Demo
✤ http://filamentgroup.github.com/eCSSential/examples/concat/
Thursday, November 8, 12
33. Images Don’t Block
✤ Doesn’t mean they get a free pass.
Thursday, November 8, 12
34. Images Don’t Block
✤ Doesn’t mean they get a free pass.
7 5 3 KB
Thursday, November 8, 12
35. Downloading Images (CSS)
<div
id="test1">
<img
src="images/test1.png"
alt=""
/>
</div>
@media
all
and
(max-‐width:
600px)
{
#test1
{
display:none;
}
}
http://timkadlec.com/2012/04/media-query-asset-downloading-results/
Thursday, November 8, 12
36. Downloading Images (CSS)
PE
<div
id="test1">
O
<img
src="images/test1.png"
alt=""
/>
N
</div>
@media
all
and
(max-‐width:
600px)
{
#test1
{
display:none;
}
}
http://timkadlec.com/2012/04/media-query-asset-downloading-results/
Thursday, November 8, 12
37. Downloading Images (CSS)
<div
id="test2"></div>
#test2
{
background-‐image:url('images/test2.png');
width:200px;
height:75px;
}
@media
all
and
(max-‐width:
600px)
{
#test2
{display:none;}
}
http://timkadlec.com/2012/04/media-query-asset-downloading-results/
Thursday, November 8, 12
38. Downloading Images (CSS)
PE
<div
id="test2"></div>
O
#test2
{
background-‐image:url('images/test2.png');
N
width:200px;
height:75px;
}
@media
all
and
(max-‐width:
600px)
{
#test2
{display:none;}
}
http://timkadlec.com/2012/04/media-query-asset-downloading-results/
Thursday, November 8, 12
39. Downloading Images (CSS)
<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;
}
}
http://timkadlec.com/2012/04/media-query-asset-downloading-results/
Thursday, November 8, 12
40. Downloading Images (CSS)
<div
id="test3">
<div></div>
K
</div>
#test3
div
{
O
background-‐image:url('images/test3.png');
width:200px;
height:75px;
}
@media
all
and
(max-‐width:
600px)
{
#test3
{
display:none;
}
}
http://timkadlec.com/2012/04/media-query-asset-downloading-results/
Thursday, November 8, 12
41. Downloading Images (CSS)
<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');
}
}
http://timkadlec.com/2012/04/media-query-asset-downloading-results/
Thursday, November 8, 12
42. Downloading Images (CSS)
<div
id="test4"></div>
K
#test4
{
O
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');
}
}
http://timkadlec.com/2012/04/media-query-asset-downloading-results/
Thursday, November 8, 12
43. Downloading Images (CSS)
<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;
/*
Editors
note:
this
should
use
background-‐size
*/
}
}
http://timkadlec.com/2012/04/media-query-asset-downloading-results/
Thursday, November 8, 12
44. Downloading Images (CSS)
<div
id="test7"></div>
#test7
{
background-‐image:url('images/test7-‐lowres.png');
width:200px;
K
height:75px;
}
O
@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;
/*
Editors
note:
this
should
use
background-‐size
*/
}
}
http://timkadlec.com/2012/04/media-query-asset-downloading-results/
Thursday, November 8, 12
45. Downloading Images (CSS)
✤ Coming to a browser near you: image-‐set()
✤ http://blog.cloudfour.com/safari-6-and-chrome-21-add-image-set-to-
support-retina-images/
Thursday, November 8, 12
46. Downloading <img>
✤ RESPONSIVE IMAGES
✤ Whatever solution you pick, make sure it doesn’t
make duplicate requests.
Thursday, November 8, 12
47. Downloading <img>
✤ If possible, use Vectors (SVG) over Bitmaps
(PNG). It’ll look great on HDPI screens.
✤ Vectors are a shortcut for Responsive Images.
✤ Note: Canvas content is bitmapped, but you can
redraw at higher resolutions.
✤ Side Note: Font icons are a great scalable
alternative to PNG icons
Thursday, November 8, 12
48. Picturefill
✤ “A Responsive Images approach that you can use today”
✤ https://github.com/scottjehl/picturefill
Thursday, November 8, 12
49. Picturefill
<div
data-‐picture
data-‐alt="A
giant
stone
face
at
The
Bayon
temple
in
Angkor
Thom,
Cambodia">
<div
data-‐src="external/imgs/small.jpg"></div>
<div
data-‐src="external/imgs/medium.jpg"
data-‐media="(min-‐width:
400px)"></div>
<div
data-‐src="external/imgs/large.jpg"
data-‐media="(min-‐width:
800px)"></div>
<div
data-‐src="external/imgs/extralarge.jpg"
data-‐media="(min-‐width:
1000px)"></div>
<!-‐-‐
Fallback
content
for
non-‐JS
browsers.
Same
img
src
as
the
initial,
unqualified
source
element.
-‐-‐>
<noscript><img
src="external/imgs/small.jpg"
alt="A
giant
stone
face
at
The
Bayon
temple
in
Angkor
Thom,
Cambodia"></noscript>
</div>
http://scottjehl.github.com/picturefill/
Thursday, November 8, 12
50. Picturefill
✤ data-‐media="(min-‐width:
400px)"
✤ Uses
matchMedia.
✤ No
duplicate
requests!
Thursday, November 8, 12
51. Picturefill (HDPI)
<div
data-‐picture
data-‐alt="A
giant
stone
face
at
The
Bayon
temple
in
Angkor
Thom,
Cambodia">
<div
data-‐src="small.jpg"></div>
<div
data-‐src="small.jpg"
data-‐media="(min-‐device-‐pixel-‐ratio:
2.0)"></div>
<div
data-‐src="medium.jpg"
data-‐media="(min-‐width:
400px)"></div>
<div
data-‐src="medium_x2.jpg"
data-‐media="(min-‐width:
400px)
and
(min-‐device-‐pixel-‐ratio:
2.0)"></div>
<div
data-‐src="large.jpg"
data-‐media="(min-‐width:
800px)"></div>
<div
data-‐src="large_x2.jpg"
data-‐media="(min-‐width:
800px)
and
(min-‐device-‐pixel-‐ratio:
2.0)"></div>
<div
data-‐src="extralarge.jpg"
data-‐media="(min-‐width:
1000px)"></div>
<div
data-‐src="extralarge_x2.jpg"
data-‐media="(min-‐width:
1000px)
and
(min-‐device-‐pixel-‐ratio:
2.0)"></div>
...
</div>
http://scottjehl.github.com/picturefill/
Thursday, November 8, 12
52. Compressive Images
✤ Pump up the size, pump up the JPEG compression
✤ Scale down in the browser
✤ http://filamentgroup.com/lab/rwd_img_compression/
Thursday, November 8, 12
53. Picturefill Simplifes to (HDPI)
<div
data-‐picture
data-‐alt="A
giant
stone
face
at
The
Bayon
temple
in
Angkor
Thom,
Cambodia">
<div
data-‐src="small_compressive.jpg"></div>
<div
data-‐src="medium_compressive.jpg"
data-‐media="(min-‐width:
400px)"></div>
<div
data-‐src="large_compressive.jpg"
data-‐media="(min-‐width:
800px)"></div>
<div
data-‐src="extralarge_compressive.jpg"
data-‐media="(min-‐width:
1000px)"></div>
<!-‐-‐
TODO:
adjust
rendered
sizes
-‐-‐>
...
</div>
✤ Careful with Memory Consumption!
Thursday, November 8, 12
55. Buzzkill #1: Advertising
✤ Pit of despair: full of document.write, iframes, blocking JavaScript
(errors galore) and general badness.
✤ Inject advertising iframes using JavaScript (after onload)
✤ document.createElement(‘iframe’);
Thursday, November 8, 12
57. SocialCount
✤ 4 KB CSS, 7KB JavaScript (unminified, ✤ Initializes Native Widgets on Hover / Tap
ungzipped) for Inline +1 / Like and Tweet.
✤ 2 requests, optional +1 for Counts ✤ In use on f2em.com
✤ Non-Blocking
✤ Sharing still works without JavaScript
Thursday, November 8, 12
58. SocialCount
ng So on
C om i
✤ 4 KB CSS, 7KB JavaScript (unminified, ✤ Initializes Native Widgets on Hover / Tap
ungzipped) for Inline +1 / Like and Tweet.
✤ 2 requests, optional +1 for Counts ✤ In use on f2em.com
✤ Non-Blocking
✤ Sharing still works without JavaScript
Thursday, November 8, 12
64. Smashing Magazine
1.87 MB
Advertising, Web Fonts, Tracking and Analytics
Thursday, November 8, 12
65. RWD & Performance
✤ “The fastest web site is the one with nothing on it.”
✤ We’re in the problem solving business.
✤ Solutions often require Code.
✤ jQuery and Cross Browser DOM API Compatibility
✤ Solve more problems than you create.
Thursday, November 8, 12