Thursday 18 January 2018

Lazy loading stylesheets using LoadCSS

In my last post, I talked about adding stylesheets into my Gulp file, part of my new development process.  The follow on to this for me was thinking about whether all of those stylesheets were really needed up front.  As I explained in that post, concatenating them and minifying them will certainly reduce the overall filesize, and the number of TCP connections (and therefore time), but what if some of this could be delayed until after the page had even loaded?

This is often referred to as lazy loading.  The Filament Group have created a great plugin for this called loadCSS, which can be found on NPM as fg-loadcss.  Their description of why you should be using it goes like this...
Referencing CSS stylesheets with link[rel=stylesheet] or @import causes browsers to delay page rendering while a stylesheet loads. When loading stylesheets that are not critical to the initial rendering of a page, this blocking behavior is undesirable. The new <link rel="preload">standard enables us to load stylesheets asynchronously, without blocking rendering, and loadCSS provides a JavaScript polyfill for that feature to allow it to work across browsers. Additionally, loadCSS offers a separate (and optional) JavaScript function for loading stylesheets dynamically.

The "preload" option is not well supported at all currently, so for the time being at least, a polyfill of this nature is definitely required.

As I'm already using Browserify in my javascript Gulp task, this is really easy to add into my javascript file.  Obviously I need to first install the fg-loadcss package, and then I can add the following lines of javascript...
  var loadcss = require("fg-loadcss");
  var reflink = $("head").children("link[rel=stylesheet]").get(-1);
  loadcss.loadCSS("https://fonts.googleapis.com/css?family=Indie+Flower",reflink);


This first requires the package (which Browserify will pull in), then finds a reference element (it will insert the <style> tag directly after this one) and then it calls the manual "loadCSS" function with the path to the stylesheet.  In my example, this is to a Google Font file.

This manual method is actually not part of Filament Groups recommended workflow, but I prefer it, as it keeps the code neat in my opinion, and runs it after my javascript is running, which I think is best for non-critical styles.  If you look on their Github repo, they do give other example usage though.

You can then remove the reference to the stylesheet from the <head> section, or better yet, move it to the very bottom of your page with a no-javascript fallback, like this...
<noscript><link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Indie+Flower"></noscript>

This means that even if javascript is disabled, your stylesheet (or font, in my case) will still load, which is great!

I didn't get the chance to cover this in my Optimising your website: A development workflow with Git and Gulp course on Skillshare, but I hope to add it into a future course.

No comments:

Post a Comment