I am using this code in my plugin to enqueue script:
wp_enqueue_script( 'wpfrank-ptbw-pinit-js', PTBW_PLUGIN_URL . 'assets/js/pinit.js', array('jquery'), '', true );
The wp_enqueue_script
function making a default <script>
tag output like this:
<script type='text/javascript' src='http://localhost/development/wp-content/plugins/pin-it-button-pinterest-widgets/assets/js/pinit.js'></script>
Want to add some extra parameter into the script tags like:
<script async defer data-pin-hover="true" src="http://localhost/development/wp-content/plugins/pin-it-button-pinterest-widgets/assets/js/pinit.js"></script>
asysnc
defer
data-pinhover="true"
How do I achieve that using wp_enqueue_script?
Are there any hook or action to pass extra parameters?
Any help really appreciated.
I am using this code in my plugin to enqueue script:
wp_enqueue_script( 'wpfrank-ptbw-pinit-js', PTBW_PLUGIN_URL . 'assets/js/pinit.js', array('jquery'), '', true );
The wp_enqueue_script
function making a default <script>
tag output like this:
<script type='text/javascript' src='http://localhost/development/wp-content/plugins/pin-it-button-pinterest-widgets/assets/js/pinit.js'></script>
Want to add some extra parameter into the script tags like:
<script async defer data-pin-hover="true" src="http://localhost/development/wp-content/plugins/pin-it-button-pinterest-widgets/assets/js/pinit.js"></script>
asysnc
defer
data-pinhover="true"
How do I achieve that using wp_enqueue_script?
Are there any hook or action to pass extra parameters?
Any help really appreciated.
Share Improve this question edited Feb 27, 2020 at 13:19 Frank asked Feb 27, 2020 at 10:23 FrankFrank 1763 silver badges13 bronze badges3 Answers
Reset to default 7You can use script_loader_tag
filter to fulfill your requirement. add below code in your active theme's functions.php file. it will add extra parameter in your script tag.
function add_attribute_to_script_tag($tag, $handle) {
# add script handles to the array below
$scripts_to_defer = array('wpfrank-ptbw-pinit-js');
foreach($scripts_to_defer as $defer_script) {
if ($defer_script === $handle) {
return str_replace(' src', ' async defer data-pin-hover="true" src', $tag);
}
}
return $tag;
}
add_filter('script_loader_tag', 'add_attribute_to_script_tag', 10, 2);
I revised the answer once more because I recently noticed how the Twenty Twenty developers use the script_loader_tag
hook to add async
and defer
to the <script>
tag for the theme scripts.
In
twentytwenty_theme_support()
infunctions.php
, lines #139 & #140:$loader = new TwentyTwenty_Script_Loader(); add_filter( 'script_loader_tag', array( $loader, 'filter_script_loader_tag' ), 10, 2 );
In
twentytwenty_register_scripts()
infunctions.php
, lines #208 & #209:wp_enqueue_script( 'twentytwenty-js', get_template_directory_uri() . '/assets/js/index.js', array(), $theme_version, false ); wp_script_add_data( 'twentytwenty-js', 'async', true );
And in the
TwentyTwenty_Script_Loader
class:public function filter_script_loader_tag( $tag, $handle ) { foreach ( [ 'async', 'defer' ] as $attr ) { if ( ! wp_scripts()->get_data( $handle, $attr ) ) { continue; } ... } return $tag; }
So what I'm trying to say/suggest, is that you should probably better off use the wp_script_add_data()
to add/register the custom HTML attributes (e.g. async
) for your scripts and use the wp_scripts()->get_data()
to check if the <script>
tag should be added with the custom HTML attributes, without having to manually specify the handle (e.g. your wpfrank-ptbw-pinit-js
).
And here's an example based on the above approach, where I'm registering a list of custom or extra HTML attributes for a script using wp_script_add_data( '<handle>', 'html_attrs', [ list here ] )
. Additionally, I'm using PHP's DOMDocument
for a more precise result, although str_replace()
or preg_replace()
would also do.
add_action( 'wp_enqueue_scripts', 'my_register_scripts' );
function my_register_scripts() {
wp_enqueue_script( 'wpfrank-ptbw-pinit-js', PTBW_PLUGIN_URL . 'assets/js/pinit.js', array( 'jquery' ), '', true );
wp_script_add_data( 'wpfrank-ptbw-pinit-js', 'html_attrs', [
'async' => 'async',
'defer' => true,
'data-pin-hover' => 'true',
] );
}
add_filter( 'script_loader_tag', 'my_filter_script_loader_tag', 10, 2 );
function my_filter_script_loader_tag( $tag, $handle ) {
$attrs = wp_scripts()->get_data( $handle, 'html_attrs' );
// Bail if the script doesn't have any registered custom HTML attrs.
if ( empty( $attrs ) || ! is_array( $attrs ) ) {
return $tag;
}
$dom = new DOMDocument;
//$tag = mb_convert_encoding( $tag, 'HTML-ENTITIES', 'UTF-8' );
$dom->loadHTML( $tag, LIBXML_HTML_NOIMPLIED | LIBXML_HTML_NODEFDTD );
$node = $dom->getElementsByTagName( 'script' )[0];
foreach ( $attrs as $key => $value ) {
$node->setAttribute( $key, $value );
}
return $dom->saveHTML();
}
In addition of Chetan Vaghela answer, you can use a switch statement, only for performance and customization related purposes:
function add_attribute_to_script_tag($tag, $handle) {
switch($handle){
case 'wpfrank-ptbw-pinit-js': return str_replace(' src', ' async defer data-pin-hover="true" src', $tag);
default: return $tag;
}
}
add_filter('script_loader_tag', 'add_attribute_to_script_tag', 10, 2);