diff --git a/projects/plugins/jetpack/changelog/update-add-csstidy-config-setting-to-preserve-leading-decimal-zero b/projects/plugins/jetpack/changelog/update-add-csstidy-config-setting-to-preserve-leading-decimal-zero new file mode 100644 index 000000000000..64a215160d7e --- /dev/null +++ b/projects/plugins/jetpack/changelog/update-add-csstidy-config-setting-to-preserve-leading-decimal-zero @@ -0,0 +1,4 @@ +Significance: minor +Type: bugfix + +Adds a setting to csstidy to tell the optimizer to preserve leading decimal zeros. diff --git a/projects/plugins/jetpack/modules/custom-css/csstidy/class.csstidy.php b/projects/plugins/jetpack/modules/custom-css/csstidy/class.csstidy.php index ecb5f72931c5..106a770b8bb7 100644 --- a/projects/plugins/jetpack/modules/custom-css/csstidy/class.csstidy.php +++ b/projects/plugins/jetpack/modules/custom-css/csstidy/class.csstidy.php @@ -280,6 +280,8 @@ function __construct() { $this->settings['timestamp'] = false; $this->settings['template'] = ''; // say that propertie exist $this->set_cfg('template','default'); // call load_template + /* Tells csstidy_optimise to keep leading zeros on decimal numbers, e.g., 0.7 */ + $this->settings['preserve_leading_zeros'] = false; $this->optimise = new csstidy_optimise($this); $this->tokens_list = & $GLOBALS['csstidy']['tokens']; diff --git a/projects/plugins/jetpack/modules/custom-css/csstidy/class.csstidy_optimise.php b/projects/plugins/jetpack/modules/custom-css/csstidy/class.csstidy_optimise.php index a5318a499996..5f4a3843a005 100644 --- a/projects/plugins/jetpack/modules/custom-css/csstidy/class.csstidy_optimise.php +++ b/projects/plugins/jetpack/modules/custom-css/csstidy/class.csstidy_optimise.php @@ -401,10 +401,13 @@ function AnalyseCssNumber($string) { $return[0] = (float) $string; if (abs($return[0]) > 0 && abs($return[0]) < 1) { - if ($return[0] < 0) { - $return[0] = '-' . ltrim(substr($return[0], 1), '0'); - } else { - $return[0] = ltrim($return[0], '0'); + // Removes the initial `0` from a decimal number, e.g., `0.7 => .7` or `-0.666 => -.666`. + if ( ! $this->parser->get_cfg( 'preserve_leading_zeros' ) ) { + if ( $return[0] < 0 ) { + $return[0] = '-' . ltrim( substr( $return[0], 1 ), '0' ); + } else { + $return[0] = ltrim( $return[0], '0' ); + } } } diff --git a/projects/plugins/jetpack/modules/custom-css/custom-css.php b/projects/plugins/jetpack/modules/custom-css/custom-css.php index d821c77fef3d..a62e2fe703f8 100644 --- a/projects/plugins/jetpack/modules/custom-css/custom-css.php +++ b/projects/plugins/jetpack/modules/custom-css/custom-css.php @@ -1623,9 +1623,10 @@ static function filter_attr( $css, $element = 'div' ) { $csstidy->set_cfg( 'remove_last_;', false ); $csstidy->set_cfg( 'css_level', 'CSS3.0' ); - // Turn off css shorthands when in block editor context as it breaks block validation. + // Turn off css shorthands and leading zero removal when in block editor context as it breaks block validation. if ( true === isset( $_REQUEST['_gutenberg_nonce'] ) && wp_verify_nonce( $_REQUEST['_gutenberg_nonce'], 'gutenberg_request' ) ) { // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.InputNotSanitized, WordPress.Security.ValidatedSanitizedInput.MissingUnslash $csstidy->set_cfg( 'optimise_shorthands', 0 ); + $csstidy->set_cfg( 'preserve_leading_zeros', true ); } $css = preg_replace( '/\\\\([0-9a-fA-F]{4})/', '\\\\\\\\$1', $css ); diff --git a/projects/plugins/jetpack/phpunit.xml.dist b/projects/plugins/jetpack/phpunit.xml.dist index 10aa1e98f164..3cd084bd3b63 100644 --- a/projects/plugins/jetpack/phpunit.xml.dist +++ b/projects/plugins/jetpack/phpunit.xml.dist @@ -128,6 +128,9 @@ tests/php/modules/seo-tools + + tests/php/modules/csstidy + diff --git a/projects/plugins/jetpack/tests/php/modules/csstidy/test-class.jetpack-csstidy.php b/projects/plugins/jetpack/tests/php/modules/csstidy/test-class.jetpack-csstidy.php new file mode 100644 index 000000000000..a30b3bcc4d52 --- /dev/null +++ b/projects/plugins/jetpack/tests/php/modules/csstidy/test-class.jetpack-csstidy.php @@ -0,0 +1,64 @@ +instance = new csstidy(); + $this->instance->set_cfg( 'optimise_shorthands', 0 ); + } + + /** Provides values for CSS preserve leading zeros patterns */ + public function custom_preserve_leading_zeros_provider() { + // phpcs:ignore Squiz.PHP.CommentedOutCode.Found -- false positive + // 'test case description' => [ 'input', 'expected output', 'preserve_leading_zeros' ]. + return array( + 'test_removes_leading_zeros_by_default' => array( 'marquee {line-height:0.7;opacity:0.05;background-color:rgba(255, 255, 255, 0.25);}', "marquee {\nline-height:.7;\nopacity:.05;\nbackground-color:rgba(255,255,255,0.25)\n}", false ), + 'test_decimals_greater_than_one_unchanged_default' => array( 'blink {line-height:1.7;top:-100.55em;}', "blink {\nline-height:1.7;\ntop:-100.55em\n}", false ), + 'test_removes_leading_zeros_by_default_units' => array( 'dfn {margin-left:-0.7px;top:0.55rem;line-height:0.3333;text-indent:-9999%}', "dfn {\nmargin-left:-.7px;\ntop:.55rem;\nline-height:.3333;\ntext-indent:-9999%\n}", false ), + 'test_preserves_leading_zeros' => array( 'aside {line-height:0.7;background-color:rgba(255, 255, 255, 0.25);opacity:0.05;}', "aside {\nline-height:0.7;\nbackground-color:rgba(255,255,255,0.25);\nopacity:0.05\n}", true ), + 'test_preserves_leading_zeros_units' => array( 'code {line-height:.70;margin-left:-00.70px;top:0.55rem;padding:0.3333%;}', "code {\nline-height:0.7;\nmargin-left:-0.7px;\ntop:0.55rem;\npadding:0.3333%\n}", true ), + 'test_decimals_greater_than_one_unchanged_preserve_zeros' => array( 'blink {line-height:1.70;top:100.55em;margin-left:900px;}', "blink {\nline-height:1.7;\ntop:100.55em;\nmargin-left:900px\n}", false ), + ); + } + + /** + * Test that leading zeros for decimals values are preserved/discarded as expected. + * + * @dataProvider custom_preserve_leading_zeros_provider + * + * @param string $input potential CSS values. + * @param string $expected_output what we expect csstidy to output. + * @param bool $preserve_leading_zeros the value of `preserve_leading_zeros` in csstidy's config. + */ + public function test_preserve_leading_zeros( $input, $expected_output, $preserve_leading_zeros ) { + $this->instance->set_cfg( 'preserve_leading_zeros', $preserve_leading_zeros ); + $this->instance->parse( $input ); + $this->assertEquals( + $expected_output, + $this->instance->print->plain() + ); + } +}