Server : Apache System : Linux ls31.server.ly 3.10.0-962.3.2.lve1.5.68.el7.x86_64 #1 SMP Wed Apr 6 11:12:23 UTC 2022 x86_64 User : medchoco ( 2906) PHP Version : 8.3.16 Disable Function : mail Directory : /home/medchoco/public_html/wp-content/plugins/jetpack-boost-git/app/lib/ |
Upload File : |
<?php /** * Implements the Viewport functionality. * * @link https://automattic.com * @since 1.0.0 * @package automattic/jetpack-boost */ namespace Automattic\Jetpack_Boost\Lib; use Automattic\Jetpack\Device_Detection; /** * Class Viewport */ class Viewport { /** * Viewport cookie name. */ const VIEWPORT_COOKIE = 'jetpack_boost_w'; /** * Mobile device identifier. */ const DEVICE_MOBILE = 'mobile'; /** * Desktop identifier. */ const DEVICE_DESKTOP = 'desktop'; /** * Default viewport sizes. */ const DEFAULT_VIEWPORT_SIZES = array( 0 => array( 'type' => 'phone', 'width' => 640, 'height' => 480, ), 1 => array( 'type' => 'tablet', 'width' => 1200, 'height' => 800, ), 2 => array( 'type' => 'desktop', 'width' => 1600, 'height' => 1050, ), ); /** * Default viewports. */ const DEFAULT_VIEWPORTS = array( array( 'device_type' => 'mobile', 'viewport_id' => 0, ), array( 'device_type' => 'desktop', 'viewport_id' => 2, ), ); /** * Runs the module. */ public static function init() { if ( ! is_admin() ) { add_action( 'wp_footer', array( __CLASS__, 'viewport_tracker' ) ); } } /** * Prints JS viewport dimensions tracker to the page. * * The purpose of the tracker is to measure the actual device viewport and store that value * in a cookie that is then consumed by `get_viewport_size`. The dimensions are updated * whenever the page is loaded, viewport resized or document shown (using Page Visibility API). * * This allows site admins to define and target more granular real-world viewports. * * First page load from a new device will result in a viewport size guessed based on the device * type (mobile vs. desktop). See `get_default_viewport_size_for_device` for more context. */ public static function viewport_tracker() { $domain = wp_parse_url( site_url(), PHP_URL_HOST ); $path = wp_parse_url( site_url(), PHP_URL_PATH ); if ( ! $path ) { $path = '/'; } $max_age = 10 * \YEAR_IN_SECONDS; $script_source = <<<SCRIPT_SOURCE ( function(doc) { var debouncer; var measure = function() { var cookieValue = Math.ceil( window.innerWidth / 10 ) + 'x' + Math.ceil( window.innerHeight / 10 ); doc.cookie = "%s=" + cookieValue + "; domain=%s; path=%s; Max-Age=%s"; } window.addEventListener( 'resize', function() { clearTimeout( debouncer ); debouncer = setTimeout( measure, 500 ); } ); doc.addEventListener( 'visibilitychange', function() { if ( ! doc.hidden ) { measure(); } } ); measure(); } )(document); SCRIPT_SOURCE; $script_source = sprintf( $script_source, esc_js( self::VIEWPORT_COOKIE ), esc_js( $domain ), esc_js( $path ), esc_js( $max_age ) ); if ( ! Debug::is_debug_mode() ) { $script_source = Minify::js( $script_source ); } printf( '<script>%s</script>', $script_source ); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped } /** * Gets the size of the current viewport. */ public static function get_viewport_size() { $data = null; $cookie_value = filter_input( INPUT_COOKIE, self::VIEWPORT_COOKIE ); if ( $cookie_value ) { $raw_data = explode( 'x', $cookie_value ); if ( 2 === count( $raw_data ) ) { $data = array( 'width' => intval( $raw_data[0] ) * 10, 'height' => intval( $raw_data[1] ) * 10, ); } } else { $device_type = Device_Detection::is_phone() ? self::DEVICE_MOBILE : self::DEVICE_DESKTOP; $data = self::get_default_viewport_size_for_device( $device_type ); } return apply_filters( 'jetpack_boost_viewport_size', $data, self::VIEWPORT_COOKIE, $cookie_value ); } /** * Get all the configured viewport sizes. * * @return array Viewport widths and heights */ public static function get_default_viewport_sizes() { return apply_filters( 'jetpack_boost_critical_css_viewport_sizes', self::DEFAULT_VIEWPORT_SIZES ); } /** * Get the default viewport size. * * @param string $device_type Device type. * * @return array Viewport width and height. */ public static function get_default_viewport_size_for_device( $device_type ) { $viewport_sizes = apply_filters( 'jetpack_boost_critical_css_viewport_sizes', self::DEFAULT_VIEWPORT_SIZES ); $default_viewports = apply_filters( 'jetpack_boost_critical_css_default_viewports', self::DEFAULT_VIEWPORTS ); foreach ( $default_viewports as $default ) { if ( $device_type === $default['device_type'] ) { if ( isset( $viewport_sizes[ $default['viewport_id'] ] ) ) { return $viewport_sizes[ $default['viewport_id'] ]; } } } return self::get_max_viewport( $viewport_sizes ); } /** * Picks the narrowest defined viewport that is equal or wider than the passed width. * * When there are multiple defined viewports of identical width, picks the smallest * height that's equal or taller than the passed height. * * Example for w:550 h:400 and defined viewport sizes: 400x300, 640x400, 640x480, 1050x900, 1900x1200 * * - The smallest viewports that are wider than the current one are: 640x400, 640x480 * - The one with the smallest height that is equal or taller than the passed dimensions: 640x400 * - Returned [ 640, 480 ] * * @param int $width Width. * @param int $height Height. * * @return array Viewport dimensions. */ public static function pick_viewport( $width, $height ) { // Get defined viewport sizes. $viewport_sizes = apply_filters( 'jetpack_boost_critical_css_viewport_sizes', self::DEFAULT_VIEWPORT_SIZES ); // Default to the widest viewport in case we don't match anything. $best_size = self::get_max_viewport( $viewport_sizes ); foreach ( $viewport_sizes as $viewport_size ) { // Skip viewports that are too narrow. if ( $viewport_size['width'] < $width ) { continue; } // Skip viewports that are wider than our best match. if ( $viewport_size['width'] > $best_size['width'] ) { continue; } // Pick viewports that are narrower than our best match. if ( $viewport_size['width'] < $best_size['width'] ) { $best_size = $viewport_size; continue; } // Current viewport and the best match have the same width, let's decide based on height. $current_is_tall_enough = $viewport_size['height'] >= $height; $best_is_tall_enough = $best_size['height'] >= $height; if ( $current_is_tall_enough && ! $best_is_tall_enough ) { $best_size = $viewport_size; // Best match isn't tall enough, but the current match is. continue; } if ( $current_is_tall_enough && $best_is_tall_enough && $viewport_size['height'] < $best_size['height'] ) { $best_size = $viewport_size; // Both ARE tall enough, but the current match is shorter. continue; } if ( ! $current_is_tall_enough && ! $best_is_tall_enough && $viewport_size['height'] > $best_size['height'] ) { $best_size = $viewport_size; // Both ARE NOT tall enough, but the current match is taller. continue; } } return apply_filters( 'jetpack_boost_pick_viewport', $best_size, $width, $height, $viewport_sizes ); } /** * Reduce the viewports array and return the widest one. * * When there are multiple widest viewports, pick the tallest one from those. * * @param array $viewport_sizes Array of defined viewport sizes. * * @return array Viewport dimensions. */ public static function get_max_viewport( array $viewport_sizes ) { $max_viewport = array_reduce( $viewport_sizes, function ( $carry, $item ) { if ( $item['width'] > $carry['width'] ) { $carry = $item; } elseif ( $item['width'] === $carry['width'] ) { if ( $item['height'] > $carry['height'] ) { $carry = $item; } } return $carry; }, array( 'width' => 0, 'height' => 0, ) ); return $max_viewport; } }