Categories
Tutorials

Using Media Queries in JavaScript with enquire.js for Responsive Masonry and More

Ever wanted to toggle JavaScript on and off with media queries only to discover you cant? Instead you have to write a huge pile of JavaScript to monitor the initial and changing document width and toggle the script on and off manually. This is cumbersome and requires an unreasonable amount of code to do something that should be simple.

Enter enquire.js by Nick Williams: A tiny JavaScript file that allows you to use media queries to toggle JavaScript on and off the same way we use them to toggle CSS on and off. This is such a simple and ingenious solution I had to write a tutorial about it. Bear in mind what I’m showing you here is an extremely simple example. Enquire.js has huge potential that goes far beyond my example. Nevertheless this example should get you up and on your way and will show you how to solve a common and frustrating problem along the way!

Responsive Masonry and other Castles in the Sky

This is the preamble. If you’re just looking for the actual example you can skip this part.

If you scroll to the bottom of my site right now and resize the width of your browser window you’ll see that  the widgets in the footer are tiling and reorganizing in a clean and structured way thanks to Masonry.

Masonry and more evolved varieties like Isotope have changed the way we organize, display, and consume content on the web thanks to their relative responsiveness and ability to take advantage of various changing screen sizes.

The problem with these JavaScript solutions that change the behaviour of your content (Superfish for drop-down menus comes to mind) is that when you display the content on smaller screens you often want these scripts to shut down. In the case of Masonry on this site, when you get to a screen width below 880px wide I no longer want Masonry to be involved. Instead I want the widgets to stack vertically and be full width.

To do this I can write a huge stack of JavaScript as I outlined earlier or I can use the fairly wonky CSS approach recommended by Masonry, but none of this is ideal:

If we approach the problem from a mobile-first perspective we really shouldn’t load Masonry or a script to test whether Masonry should run on smaller devices. It’s a waste of resources and the script just sits there bugging the browser when it shouldn’t be there at all. A better solution would be to only load the script when the screen is or gets wide enough. And that’s exactly what enquire.js lets us do!

Toggling Masonry On and Off with enquire.js

I’m using Masonry as the example here but this same approach can be used for any JavaScript that should change based on media query type events like document width.

Say we have a WordPress site in which we want to control our footer widgets with Masonry. And let’s assume we already have a footer with a widgetized area with the ID #footer-widgets and that each of the widgets has the class .widget. A standard setup in other words.

In this scenario we can deploy Masonry by writing a small script file and pulling the library it right from WordPress core.

The script file, saved in the theme under the /js/ folder with the name masonry-settings.js looks like this:


// Masonry settings to organize footer widgets
jQuery(document).ready(function($){
  var $container = $('#footer-widgets');
  $container.masonry({
    columnWidth: 400,
    itemSelector: '.widget',
    isFitWidth: true,
    isAnimated: true
  });
});

Now we have to enqueue the script and add Masonry as a dependency. This is done in functions.php:


wp_enqueue_script( 'my-masonry', get_template_directory_uri() . '/js/masonry-settings.js', array('masonry'), '20140429', true );

This will make Masonry kick in and set the column width at 400px in the footer which is fine for larger screens. However if you start narrowing the width of  your screen you’ll see this doesn’t work very well.

What we want to do now is toggle Masonry on and off at a certain width breakpoint, in our case 880px: Narrower than 880px and Masonry is not loaded, wider than 880px and Masonry does its thing.

For this we’ll use enquire.js. First get the single enquire.js.min file from the site and dump it in your theme /js/ folder. Next we need to enqueue the file the same way we enqueued our Masonry settings. Enquire has no dependencies so we’ll set the dependency attribute to false:


wp_enqueue_script( 'my-enquire', get_template_directory_uri() . '/js/enquire.min.js', false, '20140429', true );

Now enquire.js is loaded but we need to tell it what to do. Here we’re going to make some modifications to our original masonry-settings.js file to add some media query magic:


// Masonry settings to organize footer widgets
jQuery(document).ready(function($){
  var $container = $('#footer-widgets');
  enquire.register("screen and (min-width:880px)", {

    // Triggered when a media query matches.
    match : function() {
      $container.masonry({
        columnWidth: 400,
        itemSelector: '.widget',
        isFitWidth: true,
        isAnimated: true
      });
    },

    // Triggered when the media query transitions
    // from a matched state to an unmatched state.
    unmatch : function() {
      $container.masonry('destroy');
    }

  });
});

Let’s break it down:

First we register enquire.js and give it a media query:


enquire.register("screen and (min-width:880px)", {}

Then we supply enquire.register with the match and unmatch objects that as their names suggest trigger when the media query either matches (true) or unmatches (false):


enquire.register("screen and (min-width:880px)", {
  // Triggered when a media query matches.
  match : function() {
    // Turn Masonry on
  }

  // Triggered when the media query transitions
  // from a matched state to an unmatched state.
  unmatch : function() {
    // Turn Masonry off using destroy
  }

}

Now all that’s left is slotting in our original Masonry code within Match and call masonry(“destroy”) on unmatch and we’re done!

Other uses (*cough* Superfish *cough*)

Now that you see how easy it is to use enquire.js and how you can mix it in with your JavaScript here is another example of how the script is being used in the current theme you are looking at:

The main menu in this theme is keyboard accessible through its drop-down items (none are present so you just have to trust me on this one). This is achieved using the Superfish jQuery plugin. The problem is on smaller screens the mobile menu kicks in and Superfish goes from being a big help to being a royal pain in the ass. To solve this we need to turn it off when the mobile menu is displayed.

Since we’ve already enqueued enquire.js all we have to do is make some small changes to the /js/superfish-settings.js file:


/* Custom Superfish settings */
jQuery(document).ready(function($){
  var sf= $('ul.nav-menu');
  enquire.register("screen and (min-width:600px)", {

    // Triggered when a media query matches.
    match : function() {
      sf.superfish({
        delay: 200,
        speed: 'fast'
      });
    },

    // Triggered when the media query transitions
    // from a matched state to an unmatched state.
    unmatch : function() {
      sf.superfish('destroy');
    }

  }); 
});

Looks awfully familiar, doesn’t it? That’s because it’s exactly the same thing. So easy and it just works.

Enquire for yourself

Now that you know enquire.js exists and you’ve seen how easy it is to use you need to go out and try it for yourself. Once you’ve done so, report back and let me know how you fared. I’m curious to see what others end up doing with it. I have barely scratched the surface of what’s possible here so there is a world of possibilities waiting to be explored!

Categories
Lynda.com WordPress Themes

Free Responsive WordPress theme Anaximander – now available through lynda.com

The wait is over: The free responsive WordPress theme Anaximander is now available for you to use through my new course WordPress: Building Responsive Themes on lynda.com. If you don’t already have a lynda.com subscription you can follow this link – lynda.com/trial/mor10 – and get a free 7 day trial. As you can probably deduce, this theme release is a bit different, so let me explain how and why. But first, check out the features:

Anaximander features

Anaximander is a fully built out responsive WordPress theme built to use all the latest features in WordPress 3.4.1. Theme features include:

  • Fully commented and explained theme files
  • Flexible height header image functionality
  • Custom background colour
  • Custom header and link colour
  • Full Theme Customizer integration of all theme functions
  • Superfish main menu with advanced flyouts
  • Responsive menu for smaller screens
  • Masonry index front page
  • Automatic video embeds on front page
  • Responsive videos through FitVids
  • Responsive images
  • Featured images
  • Three post formats: Regular, Video, Image
    • Regular displays the post as is
    • Video displays any oEmbed video on the front page
    • Image displays the featured image at the top of the single post
  • Custom social media icons in the super-header
  • Advanced search and 404 pages with latest posts
  • Related posts feature with option to switch to Yet Another Related Posts Plugin (YARPP)
  • Optional footer widgets
  • and much much more

A theme you understand

Anaximander was built as a learning tool as well as a modern WordPress theme. The idea of Anaximander was always to ship it in such a way that using it was a learning process. This is how it works: To get Anaximander you have to follow the WordPress: Building Responsive Themes course on lynda.com from beginning to end. You start off with a static version of the theme and end up with a fully responsive theme with tons of extra features like jQuery Masonry, Superfish, and Flexslider built in.

The WordPress: Building Responsive Themes course takes the viewer through the process of converting Anaximander to a responsive theme addressing most of the issues raised by working with responsive themes including how to deal with layouts, images, videos, and menus as well as how to make the theme fit all screen sizes and work well for as many visitors as possible. The course also demonstrates how to incorporate JavaScript plugins and tools properly and provides the viewer with best-practice guides on how to make any WordPress theme responsive.

How exactly is this free?

I’m sure your next question is “How is this a free theme when I have to have a subscription to lynda.com to get it?” There is a simple answer. If you don’t already have a lynda.com subscription you can follow this link – lynda.com/trial/mor10 – and get a free 7 day trial. That’s enough time to follow the course and get Anaximander all set up. I know this looks like some sneaky marketing ploy, but it really isn’t. The whole point of Anaximander is for it to help you learn how to build responsive themes and give you a solid understanding of how the theme works. That’s why it’s not being released as a completed theme. To ensure that the theme would be available to anyone I was able to set the course up so that the static version of the theme is available to everyone including free trial subscribers. Bottom line is the theme is free to anyone who wants it.

Categories
twitter WordPress

Twitter oEmbeds are not responsive – The little things that bug me

If you have a website using WordPress you should be excited about the new 3.4 release which introduces a whole bunch of new features. For a brief look check out the announcement or you can get an in-depth look at all the newness in the Codex article for the release.

Twitter oEmbeds are here!

One of the many new features is the ability to use oEmbed to add Tweets to your posts. All you have to do is grab the URL to a tweet, for example https://twitter.com/mor10/status/212999553023090688, and paste it into the editor. WordPress finds the URL, figures out it’s from Twitter, and embeds a nice active Tweet window in the post, just like the one you see above. Very cool. Almost.

New technology hampered by old thinking

I have a serious issue with the Twitter oEmbed: Inspecting the code you’ll see the widget comes with a small inline style call:

style="width:500px!important"

This small and unnecessary piece of code makes the Twitter oEmbed awful to work with. As you see from the grab at the very top of the post, the oEmbedded tweet is not responsive. That’s because the width is hardcoded – something that should never happen, especially not inline. What’s worse is that infernal “!important” at the end of the offending piece of inline style code. That !important makes it impossible to use a stylesheet to override the width and make the box responsive.

The Solution (that you can’t apply)

The solution to this problem – one that must be implemented by either Twitter or WordPress (at present I’m not sure where that piece of code is originating) is to change the style code to say:

style="max-width:500px!important"

Oh, and don’t even get me started on the clear:both!important; call. WTF.

Categories
WordPress Themes

Introducing Anaximander: New WordPress theme to be released in the near future

It’s been a long time coming, but Design is Philosophy finally has a new look and better functionality. The new theme which I activated over the weekend is called “Anaximander” and sports everything a modern WordPress theme should have: Semantic valid HTML5 throughout, responsive layout through CSS3 media queries, carefully enqueued javascripts where necessary and index pages running Masonry for ease of use.

The name “Anaximander” comes from my new theme naming standard. Inspired by the WordPress release naming standard I have chosen to name my themes after famous philosophers starting with Thales and movin up through the ages. The philosophy geeks out there will already know this, but Anaximander is the 2nd classical philosopher on that list. If you are curious you should go check out the Wikipedia page about Anaximander (the philosopher, not the theme).

Anaximander is a work in progress and I launched it here on Design is Philosophy to put it through its paces. That means more functionality will be added in the near future (AJAXified infinite scroll on index pages is first on the list) and I will be expanding theme options and customizability. Why you ask? Because Anaximander was built to be shared.

Anaximander: The Free WordPress Theme – coming to your WordPress site in due time

Yep, as with my previous non-client themes Anaximander will be released to the masses at some point in the not too distant future. But not in the normal way: Though I can’t really say anything about what’s in store for Anaximander, it will be released as part of a bigger plan. Unfortunately I can’t be any more specific than that. But stay tuned and you’ll find out.

Browse, play, and report back

Anaximander (and by extension Design is Philosophy) has a lot of tricks up its sleeve – from Masonry to responsive layouts to other stuff. I would love it if you took it for a spin, opened it on your different devices, left a comment and reported back if something didn’t behave the way you expected. I want to build this theme out to make it as user friendly as possible and that means the front end must be flawless. Your input and suggestions are welcome.

Categories
Responsive Design Tutorials WordPress

Automatic responsive videos in WordPress with oEmbed, FitVids and a little PHP magic

Automaitc responsive videos in WordPress with oEmbed, FitVids and PHP
UPDATE: I’ve added a 4th step to the list to remove automatic inline styles from being inserted when embedding videos.

If you’re using a responsive theme on your WordPress site (or you’ve built a responsive theme) and you’ve added YouTube, Vimeo or other videos using oEmbed you will undoubtedly have noticed those videos do not resize with the rest of the frame. And that’s a royal pain. Fortunately there are solutions out there that can fix this, but they are a little tricky to implement. In this tutorial I’ll share with you a method for making the process automatic so you don’t have to worry about it.

The Problem

Responsive themes use percentage values, media queries and other coding magic to make the content resize to fit the size of the window. But when you embed videos from YouTube etc using the built in oEmbed function in WordPress (i.e. just paste in the URL to the video and it appears automatically) that video is inserted with a fixed width and height. As a result when the rest of the page resizes to fit the window, the video stays the same size causing all sorts of problems. This is sub optimal.

FitVids to the rescue… almost

Realizing this is a frustrating problem Chris Coyier and Paravel created a clever little jQuery plugin called FitVids that when installed automatically resizes videos along with the rest of the content. FitVids attaches to specified containers and forces the video iframes within these containers to resize along with it. Very clever and it works exactly as expected. However, to make this work you have to wrap the video in a container with a specified class. So if you want to use the oEmbed method you have to go to HTML view, create a div with a class and then put the URL inside it. Which kind of takes away the whole point of using oEmbed which is simplicity.

The Solution

What is needed is a function that automatically wraps all oEmbed videos in a div with the correct class that applies FitVids so all the user has to do is paste in the link to the video and then WordPress does the rest. And that’s just what we’re going to do:

Step 1: Enqueue FitVids

Go download FitVids.js from GitHub and add the jquery.fitvids.js file to your theme. I place all my JavaScript files in a sub-folder called ‘js’ for simplicity. Then we need to enqueue the script and associate it with jQuery. This is done in functions.php:


<?php 
// Add FitVids to allow for responsive sizing of videos
function your_theme_fitvids() {
	if (!is_admin()) {

		wp_register_script( 'fitvids', get_template_directory_uri() . '/js/jquery.fitvids.js', array('jquery'), '1.0', true);    	
		wp_enqueue_script( 'fitvids');
	}
}

add_action('init', 'your_theme_fitvids');
?>

This function loads the jquery.fitvids.js file along with the packaged version of jQuery that comes with WordPress whenever a page is loaded.

Step 2: Create a function to target the videos

To make FitVids work you need to add a JavaScript function targeting a specific class. The function looks like this:


<?php
add_action('wp_footer', 'add_fitthem');
    	
function add_fitthem() { 
	    	jQuery(document).ready(function() {
    			jQuery('.video').fitVids();
    		});
}

All that happens here is the action is loaded in the footer (so it doesn’t slow down the population of the page itself and allows the videos in the iframes to load properly). It then appends the function to the .video class so that any video inside a div with the class video will be scaled to size.

This function is combined with the previous function so they get called at the same time. The resulting function looks like this:


<?php
// Add FitVids to allow for responsive sizing of videos
function your_theme_fitvids() {
	if (!is_admin()) {

		wp_register_script( 'fitvids', get_template_directory_uri() . '/js/jquery.fitvids.js', array('jquery'), '1.0', true);    	
    	wp_enqueue_script( 'fitvids');
    	add_action('wp_footer', 'add_fitthem');
    	
    	function add_fitthem() { 
		    	jQuery(document).ready(function() {
	    			jQuery('.video').fitVids();
	    		});

	    }
	}
}

add_action('init', 'your_theme_fitvids');

Step 3: Automatically wrap oEmbed videos in a div with a class

The last step is to change the oEmbed output so that it automatically wraps the video iframe in a div with the class .video. This is done using a filter:


<?php
// Automatically add FitVids to oembed YouTube videos
function your_theme_embed_filter( $output, $data, $url ) {

	$return = '<div class="video">'.$output.'</div>;
	return $return;

}
add_filter('oembed_dataparse', 'your_theme_embed_filter', 90, 3 );
?>

This function grabs the output of the oembed_dataparse function (the one that creates the final code when you paste in a video URL) and wraps it in the correct div.

Step 4: Set Maximum Embed Size to 0

To get everything to work properly you have to go to Settings -> Media and set both width and height under Maximum Embed Size to 0. If you have a value in either of these fields, WordPress will include inline style code to constrain the size of the video and as a result the automatic resizing will not work.

That is all! When you add new videos to posts and pages using the oEmbed function, they are not automatically wrapped in the correct div and class and FitVids is applied. And voila: Your videos are responsive.

Caveat: These functions are not recursive!

The only catch with this process is that it is not recursive. By that I mean it doesn’t automatically work on videos that have already been embedded on your site. That is because the oembed_dataparse() function is called the when the post is published or updated. As a result, the function has already been run on old content and to apply the new div and class you have to re-run it. Fortunately that just means going in and clicking the Update button for each of the posts that have oEmbed videos in them, but if you have hundreds of videos you may want to consider doing some sort of database search/replace action.

To avoid the recursive problem I suggest you add this function to your theme at the very beginning and be done with it. That way as you populate your site the all your videos will be responsive.

Comments? Questions? Problems?

Got something to say? Leave a comment below.