Skip to content

Instantly share code, notes, and snippets.

What would you like to do?
A simple script (based on one by Google) for loading CSS files asynchronously and conditionally based on body tag classes
<!-- Inlined critical styles -->
<!-- CSS loader -->
/* ==========================================================================
Load CSS asynchronously and conditionally after initial painting
========================================================================== */
* Modified function based on:
/* Settings */
// Pass in a string containing your body tag classes here
// Your CMS will usually have a template function you can use for this purpose
var bodyClasses = 'class-name-one misc-class awesome-class';
// Define the class names and CSS files to match up with them
var pagetypeCssData = [
test: '', // Leaving this blank will load the files below on every page
files: ['file-one.min.css', 'file-two.min.css']
}, {
test: 'class-name-one',
files: ['file-three.min.css', 'file-four.min.css']
}, {
test: 'class-name-two',
files: ['file-five.min.css', 'file-six.min.css']
// You can reverse the array so the files are processed in reverse order if you wish
// pagetypeCssData.reverse();
/* Function to test if (body tag classes) string contains some text */
function stringHasText(string, text) {
if(string.indexOf(text) >= 0) {
return true;
} else {
return false;
var cb = function() {
/* Function to set media type to all */
function setMedia(element) {
setTimeout(function() { = 'all';
/* Loop through pagetypeCssData[] and process the results */
for (var prop in pagetypeCssData) {
if (stringHasText(bodyClasses, pagetypeCssData[prop].test)) {
for (var i = 0, l = pagetypeCssData[prop].files.length; i < l; i++) {
var link = document.createElement('link');
link.rel = 'stylesheet';
link.href = '/path/to/css/directory/' + pagetypeCssData[prop].files[i];
// Set media type to something non-matching so it doesn't block the render
// Reference: = 'only x';
var firstScriptTag = document.getElementsByTagName('script')[0];
// Insert CSS file before first script tag
firstScriptTag.parentNode.insertBefore(link, firstScriptTag);
// Set the media type back to all
var raf = requestAnimationFrame || mozRequestAnimationFrame || webkitRequestAnimationFrame || msRequestAnimationFrame;
if (raf) {
} else {
window.addEventListener('load', cb);
<body class="class-name-one misc-class awesome-class">
<div class="blue">Hello, world!</div>

This comment has been minimized.

Copy link
Owner Author

@matt-bailey matt-bailey commented Jun 11, 2014

I wanted a way to be able to asynchronously and conditionally load CSS files based on 'pagetype', so I modified a script by Google, found here:


This comment has been minimized.

Copy link
Owner Author

@matt-bailey matt-bailey commented Jul 2, 2014

It has come to my attention that requestAnimationFrame is not supported by IE 9<, iOS 5<, and Android.

If you need to support these browsers/OSs you can easily fix it by using a polyfill. Here's a gist by Paul Irish for just that purpose.


This comment has been minimized.

Copy link

@lookfirst lookfirst commented Jul 9, 2015

indexOf is also ie9+ and your function can be written more cleanly...

function stringHasText(string, text) {
    return string.indexOf(text) !== -1;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment