Dozens of articles have already been written on this topic, but the topic continues to be discussed, and in chat rooms and forums, people ask questions and face problems over and over again. Let’s try to figure out how to correctly connect styles and scripts in WordPress using examples.
Let’s start in order. There is a hook wp_enqueue_scripts
, which is triggered at the moment of plugging in the output queue of styles and scripts files. This event is triggered at the time of hook wp_head
with priority 1. Note that you need wp_head()
in your header.php
file to make it work.
On this hook wp_enqueue_scripts is customary to hang functions that hook in theme styles and scripts with functions wp_enqueue_style()
and wp_enqueue_script()
respectively.
A simple way to connect might look like this:
add_action( 'wp_enqueue_scripts', 'wpz_theme_scripts' );
function wpz_theme_scripts() {
// Enqueue the theme's css file.
wp_enqueue_style( 'main-style', get_stylesheet_uri() );
// Enqueue the theme's js file.
wp_enqueue_script( 'main-script', get_template_directory_uri() .'/assets/js/example.min.js', array( 'jquery' ), '1.0', true );
}
Note that if get_template_
prefix is present in the function, the file will be connected from parent theme, but if get_stylesheet_
prefix is present, the file will be connected from child theme only if child theme is activated (if not activated, the file will be connected from parent theme).
How to make connection of scripts by condition
When you connect scripts and styles on the wp_enqueue_scripts
hook, the global variables are already defined, so all conditional tags like is_home()
, is_front_page()
, is_archive()
, is_page()
and similar will work. In the example below, we include one style sheet on the home page and another on the category page. A common stylesheet will be included on all pages of the site.
add_action( 'wp_enqueue_scripts', 'wpz_theme_scripts' );
function wpz_theme_scripts() {
wp_enqueue_style( 'slyle-common', get_theme_file_uri( 'assets/css/slyle-common.min.css' ) );
if ( is_home() || is_front_page() ) {
wp_enqueue_style( 'slyle-home', get_theme_file_uri( 'assets/css/slyle-home.min.css' ) );
}
if ( is_category() ) {
wp_enqueue_style( 'slyle-cats', get_theme_file_uri( 'assets/css/slyle-cats.min.css' ) );
}
}
How to make the scripts update in the browser cache
One of the frequently asked questions is “Why do I change the css file, but these changes are not visible on the site?
The answer is simple enough: when you first visit the site browser downloads files styles, scripts, images, etc. into its cache. With each subsequent visit the browser will not download them again, but will take them from its local storage (cache). This works in order to optimize visits to Internet resources.
But there is a great way to dynamically inform the browser about changes in your files – to specify their versions. It is convenient to do this with the function filemtime()
.
Now the browser will check if the version (time of the last change) of the file has changed and only if so, it will download the file again.
In addition, one of the latest versions added the function get_theme_file_uri()
, which checks the presence of the file in the child theme before connecting, it is pretty convenient.
If we apply these tips, we get roughly the following:
add_action( 'wp_enqueue_scripts', 'wpz_theme_scripts' );
function wpz_theme_scripts() {
// Enqueue the theme's css file.
wp_enqueue_style( 'main-style', get_stylesheet_uri(), array(), filemtime( get_theme_file_path( '/style.css' ) ) );
// Enqueue the theme's js file.
wp_enqueue_script( 'main-script', get_theme_file_uri( 'assets/js/example.min.js' ), array( 'jquery' ), filemtime( get_theme_file_path( '/assets/js/example.min.js' ) ) );
}
How to add one script after another
Also, when working with scripts, it’s useful to know that in the third parameter of wp_enqueue_script()
you can specify the dependency of this script on other scripts. For example, if you specify array( 'jquery' )
, the example.min.js
script will be connected after the jquery.min.js
script.
In addition, there is a useful function wp_add_inline_script()
, which will allow you to add the script directly into the html document, after the specified one. Similarly, wp_add_inline_style()
will work for styles. Let’s look at an example of connecting a slick slider:
add_action( 'wp_slick_scripts', 'enqueue_slick_scripts' );
function enqueue_slick_scripts() {
wp_enqueue_style( 'slick-style', get_stylesheet_directory_uri() . '/assets/libs/slick/slick.min.css' );
wp_enqueue_style( 'slick-theme', get_stylesheet_directory_uri() . '/assets/libs/slick/slick-theme.min.css' );
wp_enqueue_script( 'slick-scripts', get_stylesheet_directory_uri() . '/assets/libs/slick/slick.min.js', array( 'jquery' ) );
$slick_init = 'jQuery(function($) {
$(".slick-container").slick({
infinite: true,
slidesToShow: 3,
slidesToScroll: 3
});
});';
wp_add_inline_script( 'slick-scripts', $slick_init );
}
As you can see, the necessary files are first connected using wp_enqueue_style()
and wp_enqueue_script()
, then the slider initialization script is inserted using wp_add_inline_script()
after the main slick.min.js
.
How to pre-register scripts
Another important feature of working with scripts is that you can only register a script with wp_register_script()
, and then connect it elsewhere in your project as needed. Let’s look at an example:
add_action( 'wp_enqueue_scripts', 'enqueue_masonry_scripts' );
function enqueue_masonry_scripts() {
wp_register_style( 'masonry-styles', get_stylesheet_directory_uri() . '/assets/libs/masonry/masonry.min.css' );
wp_register_script( 'masonry-scripts', get_stylesheet_directory_uri() . '/assets/libs/masonry/masonry.min.js', array( 'jquery' ) );
}
First, we register masonry library scripts to make beautiful photo galleries on our site. These scripts will not be included in the html document until you use wp_enqueue_style()
or wp_enqueue_script()
.
The photo galleries themselves are rendered using shortcodes and we can plug them in right here. So these scripts will be connected in the html document only if this shortcode will be used on the page.
add_shortcode( 'masonry-gallery', 'masonry_gallery' );
function masonry_gallery( $atts ) {
//<...>
wp_enqueue_style( 'masonry-styles' );
wp_enqueue_script( 'masonry-scripts' );
$masonry_init = 'jQuery(function($) {
var $container = $(".masonry");
$container.imagesLoaded( function() {
$container.masonry({
columnWidth: ".masonry__item",
itemSelector: ".masonry__item"
});
});
});';
wp_add_inline_script( 'masonry-scripts', $masonry_init );
}