From 1f9c6af84ff70c46987f1662947f95f98eeab30a Mon Sep 17 00:00:00 2001 From: Kaspars Dambis Date: Fri, 21 Dec 2018 16:22:39 +0200 Subject: [PATCH] Preserve extra data (#115) --- src/minit-assets.php | 2 +- src/minit-css.php | 12 ++++-- src/minit-js.php | 95 +++++++++++++++++++++++++++++++++++++------- 3 files changed, 90 insertions(+), 19 deletions(-) diff --git a/src/minit-assets.php b/src/minit-assets.php index 03ddf3a..49b3501 100644 --- a/src/minit-assets.php +++ b/src/minit-assets.php @@ -101,7 +101,7 @@ function minit() { ); foreach ( $this->queue as $handle ) { - if ( in_array( $handle, $exclude ) ) { + if ( in_array( $handle, $exclude, true ) ) { continue; } diff --git a/src/minit-css.php b/src/minit-css.php index 86f0ec0..59ad068 100644 --- a/src/minit-css.php +++ b/src/minit-css.php @@ -123,10 +123,16 @@ protected function exclude_with_media_query( $content, $handle, $src ) { return $content; } - $whitelist = array( '', 'all', 'screen' ); + // Ignore these media queries. + $allowlist = array( null, '', 'all', 'screen' ); - // Exclude from Minit if media query specified - if ( ! in_array( $this->handler->registered[ $handle ]->args, $whitelist ) ) { + // Exclude from Minit if media query specified. + if ( ! in_array( $this->handler->registered[ $handle ]->args, $allowlist, true ) ) { + return false; + } + + // Exclude all items with conditionals. + if ( ! empty( $this->handler->registered[ $handle ]->extra['conditional'] ) ) { return false; } diff --git a/src/minit-js.php b/src/minit-js.php index a6c4606..04bf623 100644 --- a/src/minit-js.php +++ b/src/minit-js.php @@ -38,7 +38,10 @@ public function init() { add_filter( 'script_loader_tag', array( $this, 'script_tag_async' ), 20, 3 ); } - function process( $todo ) { + public function process( $todo ) { + // TODO: Allow disabling the forced footer placement for scripts. + // $force_footer = apply_filters( 'minit-js-force-footer', true ); + // Run this only in the footer if ( ! did_action( 'wp_print_footer_scripts' ) ) { return $todo; @@ -64,28 +67,65 @@ function process( $todo ) { // Add our Minit script since wp_enqueue_script won't do it at this point $todo[] = self::ASSET_HANDLE; - $inline_js = array(); + // Merge all the custom before, after anda data extras with our minit file. + $extra = $this->get_script_data( + $this->done, + array( + 'data', + 'before', + 'after', + ) + ); - // Add inline scripts for all minited scripts - foreach ( $this->done as $script ) { - $extra = $this->handler->get_data( $script, 'data' ); + if ( ! empty( $extra['data'] ) ) { + $this->handler->add_data( self::ASSET_HANDLE, 'data', implode( "\n", $extra['data'] ) ); + } - if ( ! empty( $extra ) ) { - $inline_js[] = $extra; - } + if ( ! empty( $extra['before'] ) ) { + $this->handler->add_data( self::ASSET_HANDLE, 'before', $extra['before'] ); } - if ( ! empty( $inline_js ) ) { - $this->handler->add_data( - self::ASSET_HANDLE, - 'data', - implode( "\n", $inline_js ) - ); + if ( ! empty( $extra['after'] ) ) { + $this->handler->add_data( self::ASSET_HANDLE, 'after', $extra['after'] ); } return $todo; } + /** + * Get the custom data associated with each script. + * + * @param array $handles List of script handles. + * @param array $keys List of data keys to get. + * + * @return array + */ + protected function get_script_data( $handles, $keys ) { + $extra = array_combine( + $keys, + array_fill( 0, count( $keys ), array() ) // Creates a list of empty arrays. + ); + + foreach ( $handles as $script ) { + foreach ( $keys as $key ) { + $value = $this->handler->get_data( $script, $key ); + + // WordPress has this strange way of adding "after" and "before". + if ( is_array( $value ) ) { + $extra[ $key ] = array_merge( $extra[ $key ], $value ); + } else { + $extra[ $key ][] = $value; + } + } + } + + foreach ( $extra as &$values ) { + $values = array_filter( $values ); + } + + return $extra; + } + public function print_async_scripts() { $async_queue = array(); @@ -146,9 +186,34 @@ function minitLoadScript( url, id ) { handler->get_data( $handle, 'after' ); + + return ! empty( $data_after ); + } + + /** + * Adjust the script tag to support asynchronous loading. + * + * @param string $tag Script tag. + * @param string $handle Script handle or ID. + * @param string $src Script tag URL. + * + * @return string + */ public function script_tag_async( $tag, $handle, $src ) { + // Scripts with "after" logic probably depend on the parent JS. + $enable_async = ! $this->script_has_data_after( $handle ); + // Allow others to disable this feature - if ( ! apply_filters( 'minit-script-tag-async', true ) ) { + if ( ! apply_filters( 'minit-script-tag-async', $enable_async ) ) { return $tag; }