File Editor
Directories:
.. (Back)
ajax-data
background-masks
content-retriever
display-conditions
dynamic-assets
global-presets
gutenberg
icon-manager
woocommerce
Files:
AjaxCache.php
BlockEditorIntegration.php
ClassicEditor.php
CriticalCSS.php
DoNotCachePage.php
ErrorReport.php
I18n.php
JQueryBody.php
Library.php
SplitLibrary.php
ai-button.php
dynamic-content.php
et-server-frame.php
local-library.php
post-content.php
search-posts.php
window.php
woocommerce-modules.php
Create New File
Create
Edit File: JQueryBody.php
<?php /** * Move JQuery from head to body. * * @package Builder */ if ( ! defined( 'ABSPATH' ) ) { exit; // Exit if accessed directly. } /** * Class to move JQuery from head to body. */ class ET_Builder_JQuery_Body { /** * Cache. * * @var array. */ protected $_has_jquery_dep = []; /** * Should move jquery. * * @var bool|null. */ protected static $_should_move_jquery = null; /** * Instance of `ET_Builder_JQuery_Body`. * * @var ET_Builder_JQuery_Body */ private static $_instance; /** * ET_Builder_JQuery_Body constructor. */ public function __construct() { add_action( 'wp_print_scripts', [ $this, 'wp_print_scripts' ], 99 ); add_action( 'wp_head', [ $this, 'add_jquery_sub' ], 1 ); add_action( 'wp_enqueue_scripts', [ $this, 'remove_jquery_sub' ] ); } /** * Get post content from Theme Builder templates. * Combine it with the post content from the current post and integration code. * * @return string * @since 4.10.0 */ public function get_all_content() { static $all_content; // Cache the value. if ( ! empty( $all_content ) ) { return $all_content; } global $post, $shortname; $all_content = empty( $post ) ? '' : $post->post_content; $tb_layouts = et_theme_builder_get_template_layouts(); // Add TB templates content. if ( ! empty( $tb_layouts ) ) { $post_types = [ ET_THEME_BUILDER_HEADER_LAYOUT_POST_TYPE, ET_THEME_BUILDER_BODY_LAYOUT_POST_TYPE, ET_THEME_BUILDER_FOOTER_LAYOUT_POST_TYPE, ]; foreach ( $post_types as $post_type ) { $layout = $tb_layouts[ $post_type ]; if ( $layout['override'] && ! empty( $layout['enabled'] ) ) { $template = get_post( intval( $layout['id'] ) ); $all_content .= $template->post_content; } } } $integrations = [ 'head', 'body', 'single_top', 'single_bottom', ]; // Add Integration code. foreach ( $integrations as $integration ) { $all_content .= et_get_option( $shortname . '_integration_' . $integration ); } return $all_content; } /** * Recursively check if a script (or its deps) depends on JQuery. * * @since 4.10.0 * @param string $script Script Handle. * * @return bool */ public function has_jquery_dep( $script ) { global $wp_scripts; $registered = $wp_scripts->registered; $handles = [ $script ]; $stack = []; $result = false; while ( false === $result && $handles ) { foreach ( $handles as $handle ) { if ( ! empty( $this->_has_jquery_dep[ $handle ] ) ) { $result = true; break; } if ( isset( $registered[ $handle ] ) ) { $deps = $registered[ $handle ]->deps; if ( $deps ) { if ( in_array( 'jquery-core', $deps, true ) ) { $result = true; break; } array_push( $stack, $deps ); } } } $handles = array_pop( $stack ); } $this->_has_jquery_dep[ $script ] = $result; return $result; } /** * Get script deps. * * @since 4.10.0 * @param string $script Script Handle. * * @return array */ public function get_deps( $script ) { global $wp_scripts; $registered = $wp_scripts->registered; $handles = is_array( $script ) ? $script : [ $script ]; $all_deps = $handles; $stack = []; $done = []; while ( $handles ) { foreach ( $handles as $handle ) { if ( ! isset( $done[ $handle ] ) && isset( $registered[ $handle ] ) ) { $deps = $registered[ $handle ]->deps; if ( $deps ) { $all_deps = array_merge( $all_deps, $deps ); array_push( $stack, $deps ); } $done[ $handle ] = true; } } $handles = array_pop( $stack ); } return array_unique( $all_deps ); } /** * Check if a script is currently enqueued in HEAD. * * @since 4.10.0 * @param string $handle Script Handle. * * @return bool */ public function in_head( $handle ) { global $wp_scripts; if ( empty( $wp_scripts->registered[ $handle ] ) ) { return false; } $script = $wp_scripts->registered[ $handle ]; if ( isset( $script->args ) && 1 === $script->args ) { return false; } if ( isset( $script->extra['group'] ) && 1 === $script->extra['group'] ) { return false; } return true; } /** * Check whether some content includes jQuery or not. * * @since 4.10.0 * @param string $content Content. * * @return bool */ public static function has_jquery_content( $content ) { $has_jquery_regex = '/\(jQuery|jQuery\.|jQuery\)/'; return 1 === preg_match( $has_jquery_regex, $content ); } /** * Move jQuery / migrate / 3P scripts in BODY. * * @since 4.10.0 * * @return void */ public function wp_print_scripts() { global $shortname; if ( $this->should_move_jquery() ) { global $wp_scripts; $queue = $this->get_deps( $wp_scripts->queue ); $head = in_array( 'jquery-migrate', $queue, true ) ? [ 'jquery-migrate' ] : []; $mode = 'on' === et_get_option( $shortname . '_enable_jquery_body_super' ) ? 'super' : 'safe'; // Find all head scripts that depends on JQuery. foreach ( $queue as $handle ) { if ( $this->in_head( $handle ) && $this->has_jquery_dep( $handle ) ) { if ( 'safe' === $mode && 'jquery' !== $handle && 'jquery-migrate' !== $handle ) { // Bail out when a script requiring jQuery is found in head. return; } $head[] = $handle; } } $registered = $wp_scripts->registered; // Disable the feature when finding a script which does not depend on jQuery // but still uses it inside its inlined content (before/after). foreach ( $queue as $handle ) { if ( ! $this->has_jquery_dep( $handle ) ) { $script = $registered[ $handle ]; $data = ''; if ( isset( $script->extra['data'] ) ) { $data .= $script->extra['data']; } if ( isset( $script->extra['before'] ) ) { $data .= join( '', $script->extra['before'] ); } if ( isset( $script->extra['after'] ) ) { $data .= join( '', $script->extra['after'] ); } if ( ! empty( $data ) && self::has_jquery_content( $data ) ) { return; } } } // Disable the feature when jQuery is found in TB/Post Content. if ( self::has_jquery_content( $this->get_all_content() ) ) { return; } if ( ! empty( $head ) ) { foreach ( $this->get_deps( $head ) as $handle ) { $wp_scripts->add_data( $handle, 'group', 1 ); } } } } /** * Get the class instance. * * @since 4.10.0 * * @return ET_Builder_JQuery_Body */ public static function instance() { if ( ! self::$_instance ) { self::$_instance = new self(); } return self::$_instance; } /** * Fake jQuery in head when jQuery body option is true. */ public function add_jquery_sub() { global $shortname; $jquery_compatibility_enabled = 'on' === et_get_option( $shortname . '_enable_jquery_compatibility', 'on' ) ? true : false; if ( $this->should_move_jquery() && $jquery_compatibility_enabled ) { echo '<script type="text/javascript"> let jqueryParams=[],jQuery=function(r){return jqueryParams=[...jqueryParams,r],jQuery},$=function(r){return jqueryParams=[...jqueryParams,r],$};window.jQuery=jQuery,window.$=jQuery;let customHeadScripts=!1;jQuery.fn=jQuery.prototype={},$.fn=jQuery.prototype={},jQuery.noConflict=function(r){if(window.jQuery)return jQuery=window.jQuery,$=window.jQuery,customHeadScripts=!0,jQuery.noConflict},jQuery.ready=function(r){jqueryParams=[...jqueryParams,r]},$.ready=function(r){jqueryParams=[...jqueryParams,r]},jQuery.load=function(r){jqueryParams=[...jqueryParams,r]},$.load=function(r){jqueryParams=[...jqueryParams,r]},jQuery.fn.ready=function(r){jqueryParams=[...jqueryParams,r]},$.fn.ready=function(r){jqueryParams=[...jqueryParams,r]};</script>'; } } /** * Disable the Fake jQuery in head when jQuery body option is true. */ public function remove_jquery_sub() { global $shortname; $jquery_compatibility_enabled = 'on' === et_get_option( $shortname . '_enable_jquery_compatibility', 'on' ) ? true : false; if ( $this->should_move_jquery() && $jquery_compatibility_enabled ) { $script = 'jqueryParams.length&&$.each(jqueryParams,function(e,r){if("function"==typeof r){var n=String(r);n.replace("$","jQuery");var a=new Function("return "+n)();$(document).ready(a)}});'; wp_add_inline_script( 'jquery', $script, 'after' ); } } /** * Check if jQuery should be moved to the body. */ public function should_move_jquery() { global $shortname; if ( null === self::$_should_move_jquery ) { /** * Filters whether JQuery Body feature is enabled or not. * * @since 4.10.5 * * @param bool $enabled JQuery Body enabled value. * @param string $content TB/Post Content. */ if ( false === apply_filters( 'et_builder_enable_jquery_body', true, $this->get_all_content() ) ) { // Bail out if disabled by filter. self::$_should_move_jquery = false; return false; } self::$_should_move_jquery = ! ( is_admin() || wp_doing_ajax() || et_is_builder_plugin_active() || is_customize_preview() || is_et_pb_preview() || 'wp-login.php' === $GLOBALS['pagenow'] || et_fb_is_enabled() ) && 'on' === et_get_option( $shortname . '_enable_jquery_body', 'on' ); } return self::$_should_move_jquery; } } ET_Builder_JQuery_Body::instance();
Save Changes
Rename File
Rename