Simple stylesheet switcher

Tidying up my server I found a front-end style switcher lying around I’d not used much. It seems very simple and pleasant to use, so thought I’d blog it here, as a demo, before deleting the original forever…

The first thing you might notice about this post is its unusual color scheme. With the following button you can change the color scheme of this post.

Method

The original code was vanilla html/css/jQuery, so I had to make some modifications to get this to run in WordPress.

The method depends on setting an attribute, eg. a class, in the link tag calling the stylesheet we want to swap. We could just hard code the tag with the desired attribute in our header, but in WordPress we really ought to enqueue our stylesheet, eg. ‘color-switch.css’, specifying a handle, eg. ‘color-switch’, using WP’s wp_enqueue_style function.

To set the custom attribute, which we’ll need for our jQuery script, we can use WordPress’s style_loader_tag hook to customise the link.

function add_class_to_link( $tag, $handle, $src ) {
  if ( 'color-switch' === $handle ) {
   $tag = '<link rel="stylesheet" href="' . esc_url( $src ) . '" class="color-switch">';
  }
  return $tag;
}

add_filter( 'style_loader_tag', 'add_class_to_link', 10, 3 );

Add alternative stylesheets with filenames such as ‘color-switch1.css’, ‘color-switch2.css’, and so on. Don’t enqueue them in WP – just add them to the same directory as the already enqueued color-switch.css file. The html for our colour selector references these filenames, one for each option:

<div id="colourswitch">
  <a class="toggle" href="#">Colours</a>
  <div class="col-options" style="display:none; opacity:1;">
    <a href="#" rel="color-switch1.css">Scheme 1</a><br>
    <a href="#" rel="color-switch2.css">Scheme 2<a><br>
    <a href="#" rel="color-switch3.css">Scheme 3</a><br>
    <a href="#" rel="color-switch.css">Default scheme</a><br>
  </div>
</div>

And here’s our js, enqueued to load in the footer:

(function($) {                      

 //toggle control
 function sh_element(element, speed){
   $(element).slideToggle(speed);
 }
 $("#colourswitch a.toggle").click(function(){
   sh_element('#colourswitch .col-options' ,244);
   return false;
 });
 
 //get the href attribute of our extra stylesheet
 var src=$("link.color-switch").attr("href");

 //click handler - options 
 $("#colourswitch .col-options a").click(function() {
  var opt = $(this).attr('rel');//grab the 'rel' attribute
  var new_src= src.replace('color-switch.css',opt);
  $("link.color-switch").attr("href",new_src);
  return false;
 });

})(jQuery);

This has the effect of swapping the color-switch.css stylesheet for the stylesheet selected by the user.

Could it be better?

Swapping whole stylesheets might seem ideal for this use case of swapping between color schemes, but if we wanted to add features, and have more fine-grained control we might find a lot of bloat and additional http requests, slowing the site down. And even in this limited use case, it’s inefficient. The transition is noticeably smoother after all the extra stylesheets have been cached by the browser.

That’s not to suggest we’ve not learned anything. This method might still be useful if you just want to demo a number of alternative front-end schemes that make sense to separate into different stylesheets. And from a WordPress perspective, it was worth porting to learn about the style_loader_tag hook; in JavaScript terms, we’ve learned to alter a known filename in an unknown href path.

A better way to do it might be to scope our alternative color schemes under unique class names, in our standard css, then use jQuery’s methods to toggle the classnames on the element. I’ll explore this method next.

Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.