From b2e4137b1464d43e30b6ba8a525b5cd28852d0d2 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Thu, 11 Jan 2024 05:05:15 -0600 Subject: [PATCH 01/47] Add defaultFontSizes option to theme.json (#56661) * Add defaultFontSizes option for theme.json * Fix defaultFontSizes causing errors when missing * Simplify useMergedSettings * Simplify more * Remove the memo because it's probably fine * Try ignoring how overrides are handled in the dropdown * Minor performance improvement using reverse instead of toReversed * Link to a new issue with a more complete description * Refactor hack into its own funtion --- .../theme-json-reference/theme-json-living.md | 1 + lib/class-wp-theme-json-gutenberg.php | 29 +++++----- lib/theme.json | 1 + .../src/components/global-styles/hooks.js | 2 + .../global-styles/typography-panel.js | 58 ++++++++++++++----- packages/block-editor/src/hooks/utils.js | 20 +++++-- packages/block-editor/src/utils/object.js | 16 +++++ schemas/json/theme.json | 5 ++ 8 files changed, 101 insertions(+), 31 deletions(-) diff --git a/docs/reference-guides/theme-json-reference/theme-json-living.md b/docs/reference-guides/theme-json-reference/theme-json-living.md index c58b8b3239f33e..d9389597b89da2 100644 --- a/docs/reference-guides/theme-json-reference/theme-json-living.md +++ b/docs/reference-guides/theme-json-reference/theme-json-living.md @@ -177,6 +177,7 @@ Settings related to typography. | Property | Type | Default | Props | | --- | --- | --- |--- | +| defaultFontSizes | boolean | true | | | customFontSize | boolean | true | | | fontStyle | boolean | true | | | fontWeight | boolean | true | | diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index 0d2520ff9682a4..7c75a3de8d46f6 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -151,7 +151,7 @@ class WP_Theme_JSON_Gutenberg { ), array( 'path' => array( 'typography', 'fontSizes' ), - 'prevent_override' => false, + 'prevent_override' => array( 'typography', 'defaultFontSizes' ), 'use_default_names' => true, 'value_func' => 'gutenberg_get_typography_font_size_value', 'css_vars' => '--wp--preset--font-size--$slug', @@ -409,19 +409,20 @@ class WP_Theme_JSON_Gutenberg { 'defaultPresets' => null, ), 'typography' => array( - 'fluid' => null, - 'customFontSize' => null, - 'dropCap' => null, - 'fontFamilies' => null, - 'fontSizes' => null, - 'fontStyle' => null, - 'fontWeight' => null, - 'letterSpacing' => null, - 'lineHeight' => null, - 'textColumns' => null, - 'textDecoration' => null, - 'textTransform' => null, - 'writingMode' => null, + 'fluid' => null, + 'customFontSize' => null, + 'defaultFontSizes' => null, + 'dropCap' => null, + 'fontFamilies' => null, + 'fontSizes' => null, + 'fontStyle' => null, + 'fontWeight' => null, + 'letterSpacing' => null, + 'lineHeight' => null, + 'textColumns' => null, + 'textDecoration' => null, + 'textTransform' => null, + 'writingMode' => null, ), ); diff --git a/lib/theme.json b/lib/theme.json index c2ed7fdca39ed5..b7bc3cb89e60f2 100644 --- a/lib/theme.json +++ b/lib/theme.json @@ -236,6 +236,7 @@ }, "typography": { "customFontSize": true, + "defaultFontSizes": true, "dropCap": true, "fontSizes": [ { diff --git a/packages/block-editor/src/components/global-styles/hooks.js b/packages/block-editor/src/components/global-styles/hooks.js index 6be5481a633daa..7c5cf4cbf3e0fa 100644 --- a/packages/block-editor/src/components/global-styles/hooks.js +++ b/packages/block-editor/src/components/global-styles/hooks.js @@ -67,6 +67,7 @@ const VALID_SETTINGS = [ 'spacing.units', 'typography.fluid', 'typography.customFontSize', + 'typography.defaultFontSizes', 'typography.dropCap', 'typography.fontFamilies', 'typography.fontSizes', @@ -239,6 +240,7 @@ export function useSettingsForBlockElement( ...updatedSettings.typography, fontSizes: {}, customFontSize: false, + defaultFontSizes: false, }; } diff --git a/packages/block-editor/src/components/global-styles/typography-panel.js b/packages/block-editor/src/components/global-styles/typography-panel.js index e689d84c83c981..79c1d271f4e0a3 100644 --- a/packages/block-editor/src/components/global-styles/typography-panel.js +++ b/packages/block-editor/src/components/global-styles/typography-panel.js @@ -22,7 +22,7 @@ import TextTransformControl from '../text-transform-control'; import TextDecorationControl from '../text-decoration-control'; import WritingModeControl from '../writing-mode-control'; import { getValueFromVariable, TOOLSPANEL_DROPDOWNMENU_PROPS } from './utils'; -import { setImmutably } from '../../utils/object'; +import { setImmutably, uniqByProperty } from '../../utils/object'; const MIN_TEXT_COLUMNS = 1; const MAX_TEXT_COLUMNS = 6; @@ -53,7 +53,10 @@ export function useHasTypographyPanel( settings ) { function useHasFontSizeControl( settings ) { return ( - hasMergedOrigins( settings?.typography?.fontSizes ) || + ( settings?.typography?.defaultFontSizes !== false && + settings?.typography?.fontSizes?.default?.length ) || + settings?.typography?.fontSizes?.theme?.length || + settings?.typography?.fontSizes?.custom?.length || settings?.typography?.customFontSize ); } @@ -100,16 +103,45 @@ function useHasTextColumnsControl( settings ) { return settings?.typography?.textColumns; } -function getUniqueFontSizesBySlug( settings ) { - const fontSizes = settings?.typography?.fontSizes; - const mergedFontSizes = fontSizes ? mergeOrigins( fontSizes ) : []; - const uniqueSizes = []; - for ( const currentSize of mergedFontSizes ) { - if ( ! uniqueSizes.some( ( { slug } ) => slug === currentSize.slug ) ) { - uniqueSizes.push( currentSize ); - } - } - return uniqueSizes; +/** + * TODO: The reversing and filtering of default font sizes is a hack so the + * dropdown UI matches what is generated in the global styles CSS stylesheet. + * + * This is a temporary solution until #57733 is resolved. At which point, + * the mergedFontSizes would just need to be the concatenated array of all + * presets or a custom dropdown with sections for each. + * + * @see {@link https://github.com/WordPress/gutenberg/issues/57733} + * + * @param {Object} settings The global styles settings. + * + * @return {Array} The merged font sizes. + */ +function getMergedFontSizes( settings ) { + // The font size presets are merged in reverse order so that the duplicates + // that may defined later in the array have higher priority to match the CSS. + const mergedFontSizesAll = uniqByProperty( + [ + settings?.typography?.fontSizes?.custom, + settings?.typography?.fontSizes?.theme, + settings?.typography?.fontSizes?.default, + ].flatMap( ( presets ) => presets?.toReversed() ?? [] ), + 'slug' + ).reverse(); + + // Default presets exist in the global styles CSS no matter the setting, so + // filtering them out in the UI has to be done after merging. + const mergedFontSizes = + settings?.typography?.defaultFontSizes === false + ? mergedFontSizesAll.filter( + ( { slug } ) => + ! [ 'small', 'medium', 'large', 'x-large' ].includes( + slug + ) + ) + : mergedFontSizesAll; + + return mergedFontSizes; } function TypographyToolsPanel( { @@ -185,7 +217,7 @@ export default function TypographyPanel( { // Font Size const hasFontSizeEnabled = useHasFontSizeControl( settings ); const disableCustomFontSizes = ! settings?.typography?.customFontSize; - const mergedFontSizes = getUniqueFontSizesBySlug( settings ); + const mergedFontSizes = getMergedFontSizes( settings ); const fontSize = decodeValue( inheritedValue?.typography?.fontSize ); const setFontSize = ( newValue, metadata ) => { diff --git a/packages/block-editor/src/hooks/utils.js b/packages/block-editor/src/hooks/utils.js index 2f7a8f3a81f19d..f13963933e5225 100644 --- a/packages/block-editor/src/hooks/utils.js +++ b/packages/block-editor/src/hooks/utils.js @@ -177,7 +177,10 @@ export function useBlockSettings( name, parentLayout ) { backgroundImage, backgroundSize, fontFamilies, - fontSizes, + userFontSizes, + themeFontSizes, + defaultFontSizes, + defaultFontSizesEnabled, customFontSize, fontStyle, fontWeight, @@ -224,7 +227,10 @@ export function useBlockSettings( name, parentLayout ) { 'background.backgroundImage', 'background.backgroundSize', 'typography.fontFamilies', - 'typography.fontSizes', + 'typography.fontSizes.custom', + 'typography.fontSizes.theme', + 'typography.fontSizes.default', + 'typography.defaultFontSizes', 'typography.customFontSize', 'typography.fontStyle', 'typography.fontWeight', @@ -308,9 +314,12 @@ export function useBlockSettings( name, parentLayout ) { custom: fontFamilies, }, fontSizes: { - custom: fontSizes, + custom: userFontSizes, + theme: themeFontSizes, + default: defaultFontSizes, }, customFontSize, + defaultFontSizes: defaultFontSizesEnabled, fontStyle, fontWeight, lineHeight, @@ -347,7 +356,10 @@ export function useBlockSettings( name, parentLayout ) { backgroundImage, backgroundSize, fontFamilies, - fontSizes, + userFontSizes, + themeFontSizes, + defaultFontSizes, + defaultFontSizesEnabled, customFontSize, fontStyle, fontWeight, diff --git a/packages/block-editor/src/utils/object.js b/packages/block-editor/src/utils/object.js index 8f6c82a9c3991e..c78fe0e656dfef 100644 --- a/packages/block-editor/src/utils/object.js +++ b/packages/block-editor/src/utils/object.js @@ -49,3 +49,19 @@ export const getValueFromObjectPath = ( object, path, defaultValue ) => { } ); return value ?? defaultValue; }; + +/** + * Helper util to filter out objects with duplicate values for a given property. + * + * @param {Object[]} array Array of objects to filter. + * @param {string} property Property to filter unique values by. + * + * @return {Object[]} Array of objects with unique values for the specified property. + */ +export function uniqByProperty( array, property ) { + const seen = new Set(); + return array.filter( ( item ) => { + const value = item[ property ]; + return seen.has( value ) ? false : seen.add( value ); + } ); +} diff --git a/schemas/json/theme.json b/schemas/json/theme.json index 8ec1de58478b8d..64e32b4da9df88 100644 --- a/schemas/json/theme.json +++ b/schemas/json/theme.json @@ -489,6 +489,11 @@ "description": "Settings related to typography.", "type": "object", "properties": { + "defaultFontSizes": { + "description": "Allow users to choose font sizes from the default font size presets.", + "type": "boolean", + "default": true + }, "customFontSize": { "description": "Allow users to set custom font sizes.", "type": "boolean", From 3b7914916cd916a73ade8e0e5c47f61cd751bd94 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Fri, 26 Jan 2024 10:16:52 -0600 Subject: [PATCH 02/47] Add migration for theme.json v2 to v3 --- lib/class-wp-theme-json-gutenberg.php | 3 +- lib/class-wp-theme-json-schema-gutenberg.php | 39 +++++++++++++++++++- 2 files changed, 39 insertions(+), 3 deletions(-) diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index 7c75a3de8d46f6..b880e883cb74eb 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -678,9 +678,10 @@ public static function get_element_class_name( $element ) { * * @since 5.8.0 * @since 5.9.0 Changed value from 1 to 2. + * @since 6.5.0 Changed value from 2 to 3. * @var int */ - const LATEST_SCHEMA = 2; + const LATEST_SCHEMA = 3; /** * Constructor. diff --git a/lib/class-wp-theme-json-schema-gutenberg.php b/lib/class-wp-theme-json-schema-gutenberg.php index 8373e133c5aec8..20ff5b3e28e80d 100644 --- a/lib/class-wp-theme-json-schema-gutenberg.php +++ b/lib/class-wp-theme-json-schema-gutenberg.php @@ -38,6 +38,7 @@ class WP_Theme_JSON_Schema_Gutenberg { * Function that migrates a given theme.json structure to the last version. * * @since 5.9.0 + * @since 6.5.0 Migrate up to v3. * * @param array $theme_json The structure to migrate. * @@ -50,8 +51,12 @@ public static function migrate( $theme_json ) { ); } - if ( 1 === $theme_json['version'] ) { - $theme_json = self::migrate_v1_to_v2( $theme_json ); + // No breaks so all migrations will run in order starting with the current. + switch( $theme_json['version'] ) { + case 1: + $theme_json = self::migrate_v1_to_v2( $theme_json ); + case 2: + $theme_json = self::migrate_v2_to_v3( $theme_json ); } return $theme_json; @@ -87,6 +92,36 @@ private static function migrate_v1_to_v2( $old ) { return $new; } + /** + * Sets settings.typography.defaultFontSizes to false as it drives + * PRESETS_METADATA prevent_override in class-wp-theme-json.php which was + * hardcoded to false in v2 but defaults to true in v3. + * + * @since 6.5.0 + * + * @param array $old Data to migrate. + * + * @return array Data with defaultFontSizes set to false. + */ + private static function migrate_v2_to_v3( $old ) { + // Copy everything. + $new = $old; + + // Overwrite the things that changed. + if ( ! isset( $old['settings'] ) ) { + $new['settings'] = array(); + } + if ( ! isset( $old['settings']['typography'] ) ) { + $new['settings']['typography'] = array(); + } + $new['settings']['typography']['defaultFontSizes'] = false; + + // Set the new version. + $new['version'] = 3; + + return $new; + } + /** * Processes the settings subtree. * From 71f2514d2a3d2c77e9fa23d0693f7eb2333970d6 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Mon, 29 Jan 2024 14:06:55 -0600 Subject: [PATCH 03/47] Use 'merge' to mimic old behavior --- lib/class-wp-theme-json-gutenberg.php | 16 +++++++++++++++- lib/class-wp-theme-json-schema-gutenberg.php | 2 +- 2 files changed, 16 insertions(+), 2 deletions(-) diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index b880e883cb74eb..d55b372015af7b 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -2768,7 +2768,21 @@ public function merge( $incoming ) { // Replace the presets. foreach ( static::PRESETS_METADATA as $preset ) { - $override_preset = ! static::get_metadata_boolean( $this->theme_json['settings'], $preset['prevent_override'], true ); + $override_preset = false; + if ( is_array( $preset['prevent_override'] ) ) { + $prevent_override = _wp_array_get( $this->theme_json['settings'], $preset['prevent_override'] ); + /* + * For backwards compatibility with presets converting from a hardcoded `false` + * for `prevent_override` to a path to a boolean (`defaultFontSizes`, for example), + * the 'merge' value for the new setting both overrides the preset and tells the + * UI to continue to display a merged set of the default values. + */ + if ( 'merge' === $prevent_override ) { + $override_preset = true; + } elseif ( is_bool( $prevent_override ) ) { + $override_preset = ! $prevent_override; + } + } foreach ( static::VALID_ORIGINS as $origin ) { $base_path = $node['path']; diff --git a/lib/class-wp-theme-json-schema-gutenberg.php b/lib/class-wp-theme-json-schema-gutenberg.php index 20ff5b3e28e80d..57e8a73b15ef83 100644 --- a/lib/class-wp-theme-json-schema-gutenberg.php +++ b/lib/class-wp-theme-json-schema-gutenberg.php @@ -114,7 +114,7 @@ private static function migrate_v2_to_v3( $old ) { if ( ! isset( $old['settings']['typography'] ) ) { $new['settings']['typography'] = array(); } - $new['settings']['typography']['defaultFontSizes'] = false; + $new['settings']['typography']['defaultFontSizes'] = 'merge'; // Set the new version. $new['version'] = 3; From c02d54ccc76d157e100c4055a1ee2fdd635b7120 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Tue, 6 Feb 2024 09:57:57 -0600 Subject: [PATCH 04/47] WIP --- .../themedir1/block-theme-child-with-fluid-layout/theme.json | 2 +- .../block-theme-child-with-fluid-typography-config/theme.json | 2 +- .../block-theme-child-with-fluid-typography/theme.json | 2 +- phpunit/data/themedir1/block-theme-child/theme.json | 2 +- phpunit/data/themedir1/fonts-block-theme/theme.json | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json b/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json index 710ec336df70b2..813024ba8abeb6 100644 --- a/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json +++ b/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "appearanceTools": true, "layout": { diff --git a/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json b/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json index dcd3745f1630cc..3aa0560aaf0623 100644 --- a/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json +++ b/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "appearanceTools": true, "layout": { diff --git a/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json b/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json index 7b345242702956..b2624775a50037 100644 --- a/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json +++ b/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "appearanceTools": true, "typography": { diff --git a/phpunit/data/themedir1/block-theme-child/theme.json b/phpunit/data/themedir1/block-theme-child/theme.json index 1157fa91280303..185437e9b81c4b 100644 --- a/phpunit/data/themedir1/block-theme-child/theme.json +++ b/phpunit/data/themedir1/block-theme-child/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "color": { "palette": [ diff --git a/phpunit/data/themedir1/fonts-block-theme/theme.json b/phpunit/data/themedir1/fonts-block-theme/theme.json index a5d40da2b5bb2e..a7946a3f11023c 100644 --- a/phpunit/data/themedir1/fonts-block-theme/theme.json +++ b/phpunit/data/themedir1/fonts-block-theme/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "appearanceTools": true, "color": { From b2e952295d076a7440db40b9c3e6de540284fedb Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Tue, 6 Feb 2024 11:27:00 -0600 Subject: [PATCH 05/47] Fix PHP lint --- lib/class-wp-theme-json-gutenberg.php | 2 +- lib/class-wp-theme-json-schema-gutenberg.php | 6 ++++-- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index d55b372015af7b..fc28fd5c954714 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -2772,7 +2772,7 @@ public function merge( $incoming ) { if ( is_array( $preset['prevent_override'] ) ) { $prevent_override = _wp_array_get( $this->theme_json['settings'], $preset['prevent_override'] ); /* - * For backwards compatibility with presets converting from a hardcoded `false` + * For backwards compatibility with presets converting from a hardcoded `false` * for `prevent_override` to a path to a boolean (`defaultFontSizes`, for example), * the 'merge' value for the new setting both overrides the preset and tells the * UI to continue to display a merged set of the default values. diff --git a/lib/class-wp-theme-json-schema-gutenberg.php b/lib/class-wp-theme-json-schema-gutenberg.php index 57e8a73b15ef83..728dd32227798d 100644 --- a/lib/class-wp-theme-json-schema-gutenberg.php +++ b/lib/class-wp-theme-json-schema-gutenberg.php @@ -51,12 +51,14 @@ public static function migrate( $theme_json ) { ); } - // No breaks so all migrations will run in order starting with the current. - switch( $theme_json['version'] ) { + // Migrate each version in order starting with the current version. + switch ( $theme_json['version'] ) { case 1: $theme_json = self::migrate_v1_to_v2( $theme_json ); + // no break case 2: $theme_json = self::migrate_v2_to_v3( $theme_json ); + // no break } return $theme_json; From 365b9a8d3a73ac326a545dd96ee70ea52cc71ffa Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 08:27:54 -0600 Subject: [PATCH 06/47] Simplify logic --- lib/class-wp-theme-json-gutenberg.php | 25 +++++++++---------------- 1 file changed, 9 insertions(+), 16 deletions(-) diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index fc28fd5c954714..b6a1998c85ef61 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -2768,8 +2768,8 @@ public function merge( $incoming ) { // Replace the presets. foreach ( static::PRESETS_METADATA as $preset ) { - $override_preset = false; - if ( is_array( $preset['prevent_override'] ) ) { + $prevent_override = $preset['prevent_override']; + if ( is_array( $prevent_override ) ) { $prevent_override = _wp_array_get( $this->theme_json['settings'], $preset['prevent_override'] ); /* * For backwards compatibility with presets converting from a hardcoded `false` @@ -2778,9 +2778,7 @@ public function merge( $incoming ) { * UI to continue to display a merged set of the default values. */ if ( 'merge' === $prevent_override ) { - $override_preset = true; - } elseif ( is_bool( $prevent_override ) ) { - $override_preset = ! $prevent_override; + $prevent_override = false; } } @@ -2809,19 +2807,14 @@ public function merge( $incoming ) { } } - if ( - ( 'theme' !== $origin ) || - ( 'theme' === $origin && $override_preset ) - ) { - _wp_array_set( $this->theme_json, $path, $content ); - } else { - $slugs_node = static::get_default_slugs( $this->theme_json, $node['path'] ); - $slugs = array_merge_recursive( $slugs_global, $slugs_node ); - - $slugs_for_preset = _wp_array_get( $slugs, $preset['path'], array() ); + if ( 'theme' === $origin && $prevent_override ) { + $slugs_node = static::get_default_slugs( $this->theme_json, $node['path'] ); + $slugs_merged = array_merge_recursive( $slugs_global, $slugs_node ); + $slugs_for_preset = _wp_array_get( $slugs_merged, $preset['path'], array() ); $content = static::filter_slugs( $content, $slugs_for_preset ); - _wp_array_set( $this->theme_json, $path, $content ); } + + _wp_array_set( $this->theme_json, $path, $content ); } } } From 11e69f1bbad30963517452a647c23edd17acc49f Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 08:38:24 -0600 Subject: [PATCH 07/47] Tidy up comments --- lib/class-wp-theme-json-gutenberg.php | 3 +++ 1 file changed, 3 insertions(+) diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index b6a1998c85ef61..0ee7fa329f0f89 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -2771,6 +2771,7 @@ public function merge( $incoming ) { $prevent_override = $preset['prevent_override']; if ( is_array( $prevent_override ) ) { $prevent_override = _wp_array_get( $this->theme_json['settings'], $preset['prevent_override'] ); + /* * For backwards compatibility with presets converting from a hardcoded `false` * for `prevent_override` to a path to a boolean (`defaultFontSizes`, for example), @@ -2796,6 +2797,7 @@ public function merge( $incoming ) { continue; } + // Set names for theme presets based on the slug if they are not set and can use default names. if ( 'theme' === $origin && $preset['use_default_names'] ) { foreach ( $content as $key => $item ) { if ( ! isset( $item['name'] ) ) { @@ -2807,6 +2809,7 @@ public function merge( $incoming ) { } } + // When the incoming theme preset is not allowed to override the defaults, we need to filter the slugs. if ( 'theme' === $origin && $prevent_override ) { $slugs_node = static::get_default_slugs( $this->theme_json, $node['path'] ); $slugs_merged = array_merge_recursive( $slugs_global, $slugs_node ); From 6a50fa6862e90255afbc6fcd8b2993d01a1544a6 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 10:08:36 -0600 Subject: [PATCH 08/47] Revert phpunit for now --- .../themedir1/block-theme-child-with-fluid-layout/theme.json | 2 +- .../block-theme-child-with-fluid-typography-config/theme.json | 2 +- .../block-theme-child-with-fluid-typography/theme.json | 2 +- phpunit/data/themedir1/block-theme-child/theme.json | 2 +- phpunit/data/themedir1/fonts-block-theme/theme.json | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json b/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json index 813024ba8abeb6..710ec336df70b2 100644 --- a/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json +++ b/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 3, + "version": 2, "settings": { "appearanceTools": true, "layout": { diff --git a/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json b/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json index 3aa0560aaf0623..dcd3745f1630cc 100644 --- a/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json +++ b/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 3, + "version": 2, "settings": { "appearanceTools": true, "layout": { diff --git a/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json b/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json index b2624775a50037..7b345242702956 100644 --- a/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json +++ b/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 3, + "version": 2, "settings": { "appearanceTools": true, "typography": { diff --git a/phpunit/data/themedir1/block-theme-child/theme.json b/phpunit/data/themedir1/block-theme-child/theme.json index 185437e9b81c4b..1157fa91280303 100644 --- a/phpunit/data/themedir1/block-theme-child/theme.json +++ b/phpunit/data/themedir1/block-theme-child/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 3, + "version": 2, "settings": { "color": { "palette": [ diff --git a/phpunit/data/themedir1/fonts-block-theme/theme.json b/phpunit/data/themedir1/fonts-block-theme/theme.json index a7946a3f11023c..a5d40da2b5bb2e 100644 --- a/phpunit/data/themedir1/fonts-block-theme/theme.json +++ b/phpunit/data/themedir1/fonts-block-theme/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 3, + "version": 2, "settings": { "appearanceTools": true, "color": { From 1fb673f4aa2a6951dcc7e452d916767cdad01945 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 10:10:20 -0600 Subject: [PATCH 09/47] Optimize prevent_override logic --- lib/class-wp-theme-json-gutenberg.php | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index 0ee7fa329f0f89..03786221591ef4 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -2809,12 +2809,14 @@ public function merge( $incoming ) { } } - // When the incoming theme preset is not allowed to override the defaults, we need to filter the slugs. + // Filter out default slugs from theme presets when defaults should not be overridden. if ( 'theme' === $origin && $prevent_override ) { - $slugs_node = static::get_default_slugs( $this->theme_json, $node['path'] ); - $slugs_merged = array_merge_recursive( $slugs_global, $slugs_node ); - $slugs_for_preset = _wp_array_get( $slugs_merged, $preset['path'], array() ); - $content = static::filter_slugs( $content, $slugs_for_preset ); + $slugs_node = static::get_default_slugs( $this->theme_json, $node['path'] ); + $preset_global = _wp_array_get( $slugs_global, $preset['path'], array() ); + $preset_node = _wp_array_get( $slugs_node, $preset['path'], array() ); + $preset_slugs = array_merge_recursive( $preset_global, $preset_node ); + + $content = static::filter_slugs( $content, $preset_slugs ); } _wp_array_set( $this->theme_json, $path, $content ); From 9b0147a5e7552a0a24663b7aabd51d93836fe10c Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 10:11:06 -0600 Subject: [PATCH 10/47] preset -> preset_metadata --- lib/class-wp-theme-json-gutenberg.php | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index 03786221591ef4..580ab5cc6472ea 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -2767,10 +2767,10 @@ public function merge( $incoming ) { } // Replace the presets. - foreach ( static::PRESETS_METADATA as $preset ) { - $prevent_override = $preset['prevent_override']; + foreach ( static::PRESETS_METADATA as $preset_metadata ) { + $prevent_override = $preset_metadata['prevent_override']; if ( is_array( $prevent_override ) ) { - $prevent_override = _wp_array_get( $this->theme_json['settings'], $preset['prevent_override'] ); + $prevent_override = _wp_array_get( $this->theme_json['settings'], $preset_metadata['prevent_override'] ); /* * For backwards compatibility with presets converting from a hardcoded `false` @@ -2785,7 +2785,7 @@ public function merge( $incoming ) { foreach ( static::VALID_ORIGINS as $origin ) { $base_path = $node['path']; - foreach ( $preset['path'] as $leaf ) { + foreach ( $preset_metadata['path'] as $leaf ) { $base_path[] = $leaf; } @@ -2798,7 +2798,7 @@ public function merge( $incoming ) { } // Set names for theme presets based on the slug if they are not set and can use default names. - if ( 'theme' === $origin && $preset['use_default_names'] ) { + if ( 'theme' === $origin && $preset_metadata['use_default_names'] ) { foreach ( $content as $key => $item ) { if ( ! isset( $item['name'] ) ) { $name = static::get_name_from_defaults( $item['slug'], $base_path ); @@ -2812,8 +2812,8 @@ public function merge( $incoming ) { // Filter out default slugs from theme presets when defaults should not be overridden. if ( 'theme' === $origin && $prevent_override ) { $slugs_node = static::get_default_slugs( $this->theme_json, $node['path'] ); - $preset_global = _wp_array_get( $slugs_global, $preset['path'], array() ); - $preset_node = _wp_array_get( $slugs_node, $preset['path'], array() ); + $preset_global = _wp_array_get( $slugs_global, $preset_metadata['path'], array() ); + $preset_node = _wp_array_get( $slugs_node, $preset_metadata['path'], array() ); $preset_slugs = array_merge_recursive( $preset_global, $preset_node ); $content = static::filter_slugs( $content, $preset_slugs ); From 59c93c3c15a7e304a9261a8221f7aedd687381c3 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 10:18:59 -0600 Subject: [PATCH 11/47] Bump core theme.json version --- lib/theme.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/theme.json b/lib/theme.json index b7bc3cb89e60f2..e9a7e6d0beaaf5 100644 --- a/lib/theme.json +++ b/lib/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "appearanceTools": false, "useRootPaddingAwareAlignments": false, From 37d59102c2a077cee505bc132b1d0e013bd3124e Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 10:25:30 -0600 Subject: [PATCH 12/47] Bump theme.json version in schema --- schemas/json/theme.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/schemas/json/theme.json b/schemas/json/theme.json index 64e32b4da9df88..1bbca913a8e486 100644 --- a/schemas/json/theme.json +++ b/schemas/json/theme.json @@ -2230,7 +2230,7 @@ "version": { "description": "Version of theme.json to use.", "type": "integer", - "enum": [ 2 ] + "enum": [ 3 ] }, "title": { "type": "string", From 5abb4e5beac9a819ade49c749b9081ef1bd51b07 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 10:26:54 -0600 Subject: [PATCH 13/47] Reimplement old logic for "merge" value --- .../global-styles/typography-panel.js | 62 +++++++++---------- 1 file changed, 29 insertions(+), 33 deletions(-) diff --git a/packages/block-editor/src/components/global-styles/typography-panel.js b/packages/block-editor/src/components/global-styles/typography-panel.js index 79c1d271f4e0a3..43c68c97508d76 100644 --- a/packages/block-editor/src/components/global-styles/typography-panel.js +++ b/packages/block-editor/src/components/global-styles/typography-panel.js @@ -103,45 +103,31 @@ function useHasTextColumnsControl( settings ) { return settings?.typography?.textColumns; } +function getUniqueFontSizesBySlug( settings ) { + const fontSizes = settings?.typography?.fontSizes; + const mergedFontSizes = fontSizes ? mergeOrigins( fontSizes ) : []; + const uniqueSizes = []; + for ( const currentSize of mergedFontSizes ) { + if ( ! uniqueSizes.some( ( { slug } ) => slug === currentSize.slug ) ) { + uniqueSizes.push( currentSize ); + } + } + return uniqueSizes; +} + /** - * TODO: The reversing and filtering of default font sizes is a hack so the - * dropdown UI matches what is generated in the global styles CSS stylesheet. - * - * This is a temporary solution until #57733 is resolved. At which point, - * the mergedFontSizes would just need to be the concatenated array of all - * presets or a custom dropdown with sections for each. - * - * @see {@link https://github.com/WordPress/gutenberg/issues/57733} + * Concatenate all the font sizes. * * @param {Object} settings The global styles settings. * * @return {Array} The merged font sizes. */ function getMergedFontSizes( settings ) { - // The font size presets are merged in reverse order so that the duplicates - // that may defined later in the array have higher priority to match the CSS. - const mergedFontSizesAll = uniqByProperty( - [ - settings?.typography?.fontSizes?.custom, - settings?.typography?.fontSizes?.theme, - settings?.typography?.fontSizes?.default, - ].flatMap( ( presets ) => presets?.toReversed() ?? [] ), - 'slug' - ).reverse(); - - // Default presets exist in the global styles CSS no matter the setting, so - // filtering them out in the UI has to be done after merging. - const mergedFontSizes = - settings?.typography?.defaultFontSizes === false - ? mergedFontSizesAll.filter( - ( { slug } ) => - ! [ 'small', 'medium', 'large', 'x-large' ].includes( - slug - ) - ) - : mergedFontSizesAll; - - return mergedFontSizes; + return [ + ...( settings?.typography?.fontSizes?.custom ?? [] ), + ...( settings?.typography?.fontSizes?.theme ?? [] ), + ...( settings?.typography?.fontSizes?.default ?? [] ), + ]; } function TypographyToolsPanel( { @@ -217,7 +203,17 @@ export default function TypographyPanel( { // Font Size const hasFontSizeEnabled = useHasFontSizeControl( settings ); const disableCustomFontSizes = ! settings?.typography?.customFontSize; - const mergedFontSizes = getMergedFontSizes( settings ); + + /* + * For backwards compatibility with presets converting from a hardcoded `false` + * for `prevent_override` to a path to a boolean (`defaultFontSizes`, for example), + * the 'merge' value for the new setting both overrides the preset and tells the + * UI to continue to display a merged set of the default values. + */ + const mergedFontSizes = + settings?.typography?.defaultFontSizes === 'merge' + ? getUniqueFontSizesBySlug( settings ) + : getMergedFontSizes( settings ); const fontSize = decodeValue( inheritedValue?.typography?.fontSize ); const setFontSize = ( newValue, metadata ) => { From 6fcb9367ba27aa87d554c5970b2a2c38b584b5ea Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 10:36:48 -0600 Subject: [PATCH 14/47] Remove uniqByProperty --- .../components/global-styles/typography-panel.js | 2 +- packages/block-editor/src/utils/object.js | 16 ---------------- 2 files changed, 1 insertion(+), 17 deletions(-) diff --git a/packages/block-editor/src/components/global-styles/typography-panel.js b/packages/block-editor/src/components/global-styles/typography-panel.js index 43c68c97508d76..38693a2f8f7d36 100644 --- a/packages/block-editor/src/components/global-styles/typography-panel.js +++ b/packages/block-editor/src/components/global-styles/typography-panel.js @@ -22,7 +22,7 @@ import TextTransformControl from '../text-transform-control'; import TextDecorationControl from '../text-decoration-control'; import WritingModeControl from '../writing-mode-control'; import { getValueFromVariable, TOOLSPANEL_DROPDOWNMENU_PROPS } from './utils'; -import { setImmutably, uniqByProperty } from '../../utils/object'; +import { setImmutably } from '../../utils/object'; const MIN_TEXT_COLUMNS = 1; const MAX_TEXT_COLUMNS = 6; diff --git a/packages/block-editor/src/utils/object.js b/packages/block-editor/src/utils/object.js index c78fe0e656dfef..8f6c82a9c3991e 100644 --- a/packages/block-editor/src/utils/object.js +++ b/packages/block-editor/src/utils/object.js @@ -49,19 +49,3 @@ export const getValueFromObjectPath = ( object, path, defaultValue ) => { } ); return value ?? defaultValue; }; - -/** - * Helper util to filter out objects with duplicate values for a given property. - * - * @param {Object[]} array Array of objects to filter. - * @param {string} property Property to filter unique values by. - * - * @return {Object[]} Array of objects with unique values for the specified property. - */ -export function uniqByProperty( array, property ) { - const seen = new Set(); - return array.filter( ( item ) => { - const value = item[ property ]; - return seen.has( value ) ? false : seen.add( value ); - } ); -} From a0488fe736b861870ab99b50d7d817f019e93170 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 10:52:49 -0600 Subject: [PATCH 15/47] Fix WP_Theme_JSON_Gutenberg_Test failures --- phpunit/class-wp-theme-json-test.php | 82 ++++++++++++---------------- 1 file changed, 35 insertions(+), 47 deletions(-) diff --git a/phpunit/class-wp-theme-json-test.php b/phpunit/class-wp-theme-json-test.php index 3018ea1a15b8e5..73b6d77aa98e51 100644 --- a/phpunit/class-wp-theme-json-test.php +++ b/phpunit/class-wp-theme-json-test.php @@ -3123,7 +3123,7 @@ public function test_get_editor_settings_custom_units_can_be_filtered() { public function test_export_data() { $theme = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'color' => array( 'palette' => array( @@ -3144,7 +3144,7 @@ public function test_export_data() { ); $user = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'color' => array( 'palette' => array( @@ -3168,7 +3168,7 @@ public function test_export_data() { $theme->merge( $user ); $actual = $theme->get_data(); $expected = array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'color' => array( 'palette' => array( @@ -3198,7 +3198,7 @@ public function test_export_data() { public function test_export_data_deals_with_empty_user_data() { $theme = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'color' => array( 'palette' => array( @@ -3220,7 +3220,7 @@ public function test_export_data_deals_with_empty_user_data() { $actual = $theme->get_data(); $expected = array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'color' => array( 'palette' => array( @@ -3245,7 +3245,7 @@ public function test_export_data_deals_with_empty_user_data() { public function test_export_data_deals_with_empty_theme_data() { $user = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'color' => array( 'palette' => array( @@ -3268,7 +3268,7 @@ public function test_export_data_deals_with_empty_theme_data() { $actual = $user->get_data(); $expected = array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'color' => array( 'palette' => array( @@ -3291,31 +3291,19 @@ public function test_export_data_deals_with_empty_theme_data() { } public function test_export_data_deals_with_empty_data() { - $theme_v2 = new WP_Theme_JSON_Gutenberg( - array( - 'version' => 2, - ), - 'theme' - ); - $actual_v2 = $theme_v2->get_data(); - $expected_v2 = array( 'version' => 2 ); - $this->assertEqualSetsWithIndex( $expected_v2, $actual_v2 ); - - $theme_v1 = new WP_Theme_JSON_Gutenberg( - array( - 'version' => 1, - ), + $theme = new WP_Theme_JSON_Gutenberg( + array( 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA ), 'theme' ); - $actual_v1 = $theme_v1->get_data(); - $expected_v1 = array( 'version' => 2 ); - $this->assertEqualSetsWithIndex( $expected_v1, $actual_v1 ); + $actual = $theme->get_data(); + $expected = array( 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA ); + $this->assertEqualSetsWithIndex( $expected, $actual ); } public function test_export_data_sets_appearance_tools() { $theme = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'appearanceTools' => true, 'blocks' => array( @@ -3329,7 +3317,7 @@ public function test_export_data_sets_appearance_tools() { $actual = $theme->get_data(); $expected = array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'appearanceTools' => true, 'blocks' => array( @@ -3346,7 +3334,7 @@ public function test_export_data_sets_appearance_tools() { public function test_export_data_sets_use_root_padding_aware_alignments() { $theme = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'useRootPaddingAwareAlignments' => true, 'blocks' => array( @@ -3360,7 +3348,7 @@ public function test_export_data_sets_use_root_padding_aware_alignments() { $actual = $theme->get_data(); $expected = array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'useRootPaddingAwareAlignments' => true, 'blocks' => array( @@ -3441,7 +3429,7 @@ public function test_get_element_class_name_invalid() { public function test_get_property_value_valid() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'color' => array( 'background' => '#ffffff', @@ -3520,7 +3508,7 @@ public function data_get_property_value_should_return_string_for_invalid_paths_o public function test_get_property_value_loop() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'color' => array( 'background' => '#ffffff', @@ -3554,7 +3542,7 @@ public function test_get_property_value_loop() { public function test_get_property_value_recursion() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'color' => array( 'background' => '#ffffff', @@ -3587,7 +3575,7 @@ public function test_get_property_value_recursion() { public function test_get_property_value_self() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'color' => array( 'background' => '#ffffff', @@ -3606,7 +3594,7 @@ public function test_get_property_value_self() { public function test_get_styles_for_block_with_padding_aware_alignments() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'spacing' => array( 'padding' => array( @@ -3637,7 +3625,7 @@ public function test_get_styles_for_block_with_padding_aware_alignments() { public function test_get_styles_for_block_without_padding_aware_alignments() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'spacing' => array( 'padding' => array( @@ -3665,7 +3653,7 @@ public function test_get_styles_for_block_without_padding_aware_alignments() { public function test_get_styles_for_block_with_content_width() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'layout' => array( 'contentSize' => '800px', @@ -3689,7 +3677,7 @@ public function test_get_styles_for_block_with_content_width() { public function test_get_styles_with_appearance_tools() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'appearanceTools' => true, ), @@ -3709,7 +3697,7 @@ public function test_get_styles_with_appearance_tools() { public function test_sanitization() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'spacing' => array( 'blockGap' => 'valid value', @@ -3728,7 +3716,7 @@ public function test_sanitization() { $actual = $theme_json->get_raw_data(); $expected = array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'spacing' => array( 'blockGap' => 'valid value', @@ -3749,7 +3737,7 @@ public function test_sanitization() { public function test_sanitize_for_unregistered_style_variations() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'blocks' => array( 'core/quote' => array( @@ -3773,7 +3761,7 @@ public function test_sanitize_for_unregistered_style_variations() { $sanitized_theme_json = $theme_json->get_raw_data(); $expected = array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'blocks' => array( 'core/quote' => array( @@ -3800,7 +3788,7 @@ public function test_sanitize_for_unregistered_style_variations() { public function test_sanitize_for_block_with_style_variations( $theme_json_variations, $expected_sanitized ) { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'blocks' => array( 'core/quote' => $theme_json_variations, @@ -3882,7 +3870,7 @@ public function data_sanitize_for_block_with_style_variations() { public function test_sanitize_indexed_arrays() { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => '2', + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'badKey2' => 'I am Evil!', 'settings' => array( 'badKey3' => 'I am Evil!', @@ -3950,7 +3938,7 @@ public function test_sanitize_indexed_arrays() { ); $expected_sanitized = array( - 'version' => '2', + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'typography' => array( 'fontFamilies' => array( @@ -4017,7 +4005,7 @@ public function test_sanitize_indexed_arrays() { public function test_sanitize_with_invalid_style_variation( $theme_json_variations ) { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'blocks' => array( 'core/quote' => $theme_json_variations, @@ -4062,7 +4050,7 @@ public function data_sanitize_with_invalid_style_variation() { public function test_get_styles_for_block_with_style_variations( $theme_json_variations, $metadata_variations, $expected ) { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'styles' => array( 'blocks' => array( 'core/quote' => $theme_json_variations, @@ -4214,7 +4202,7 @@ public function test_block_style_variations_with_invalid_properties() { public function test_set_spacing_sizes( $spacing_scale, $expected_output ) { $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'spacing' => array( 'spacingScale' => $spacing_scale, @@ -4504,7 +4492,7 @@ public function test_set_spacing_sizes_when_invalid( $spacing_scale, $expected_o $theme_json = new WP_Theme_JSON_Gutenberg( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'spacing' => array( 'spacingScale' => $spacing_scale, From c60fb1c9835dc7ea01a152c8faf1e0d671fbc263 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 10:59:00 -0600 Subject: [PATCH 16/47] Update WP_Theme_JSON_Schema_Gutenberg_Test with new migration --- phpunit/class-wp-theme-json-schema-test.php | 174 ++++++++++++++++++++ 1 file changed, 174 insertions(+) diff --git a/phpunit/class-wp-theme-json-schema-test.php b/phpunit/class-wp-theme-json-schema-test.php index 9c1103197d72e5..19deb1acdfdddc 100644 --- a/phpunit/class-wp-theme-json-schema-test.php +++ b/phpunit/class-wp-theme-json-schema-test.php @@ -96,6 +96,94 @@ public function test_migrate_v1_to_latest() { $expected = array( 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, + 'settings' => array( + 'color' => array( + 'palette' => array( + array( + 'name' => 'Pale Pink', + 'slug' => 'pale-pink', + 'color' => '#f78da7', + ), + array( + 'name' => 'Vivid Red', + 'slug' => 'vivid-red', + 'color' => '#cf2e2e', + ), + ), + 'custom' => false, + 'link' => true, + ), + 'border' => array( + 'color' => false, + 'radius' => false, + 'style' => false, + 'width' => false, + ), + 'typography' => array( + 'defaultFontSizes' => 'merge', + 'fontStyle' => false, + 'fontWeight' => false, + 'letterSpacing' => false, + 'textDecoration' => false, + 'textTransform' => false, + ), + 'blocks' => array( + 'core/group' => array( + 'border' => array( + 'color' => true, + 'radius' => true, + 'style' => true, + 'width' => true, + ), + 'typography' => array( + 'fontStyle' => true, + 'fontWeight' => true, + 'letterSpacing' => true, + 'textDecoration' => true, + 'textTransform' => true, + ), + ), + ), + ), + 'styles' => array( + 'color' => array( + 'background' => 'purple', + ), + 'blocks' => array( + 'core/group' => array( + 'color' => array( + 'background' => 'red', + ), + 'spacing' => array( + 'padding' => array( + 'top' => '10px', + ), + ), + 'elements' => array( + 'link' => array( + 'color' => array( + 'text' => 'yellow', + ), + ), + ), + ), + ), + 'elements' => array( + 'link' => array( + 'color' => array( + 'text' => 'red', + ), + ), + ), + ), + ); + + $this->assertEqualSetsWithIndex( $expected, $actual ); + } + + public function test_migrate_v2_to_latest() { + $theme_json_v2 = array( + 'version' => 2, 'settings' => array( 'color' => array( 'palette' => array( @@ -177,6 +265,92 @@ public function test_migrate_v1_to_latest() { ), ); + $actual = WP_Theme_JSON_Schema_Gutenberg::migrate( $theme_json_v2 ); + + $expected = array( + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, + 'settings' => array( + 'color' => array( + 'palette' => array( + array( + 'name' => 'Pale Pink', + 'slug' => 'pale-pink', + 'color' => '#f78da7', + ), + array( + 'name' => 'Vivid Red', + 'slug' => 'vivid-red', + 'color' => '#cf2e2e', + ), + ), + 'custom' => false, + 'link' => true, + ), + 'border' => array( + 'color' => false, + 'radius' => false, + 'style' => false, + 'width' => false, + ), + 'typography' => array( + 'defaultFontSizes' => 'merge', + 'fontStyle' => false, + 'fontWeight' => false, + 'letterSpacing' => false, + 'textDecoration' => false, + 'textTransform' => false, + ), + 'blocks' => array( + 'core/group' => array( + 'border' => array( + 'color' => true, + 'radius' => true, + 'style' => true, + 'width' => true, + ), + 'typography' => array( + 'fontStyle' => true, + 'fontWeight' => true, + 'letterSpacing' => true, + 'textDecoration' => true, + 'textTransform' => true, + ), + ), + ), + ), + 'styles' => array( + 'color' => array( + 'background' => 'purple', + ), + 'blocks' => array( + 'core/group' => array( + 'color' => array( + 'background' => 'red', + ), + 'spacing' => array( + 'padding' => array( + 'top' => '10px', + ), + ), + 'elements' => array( + 'link' => array( + 'color' => array( + 'text' => 'yellow', + ), + ), + ), + ), + ), + 'elements' => array( + 'link' => array( + 'color' => array( + 'text' => 'red', + ), + ), + ), + ), + ); + $this->assertEqualSetsWithIndex( $expected, $actual ); } } From f26f484e94458dff85e250db4fcdfcb01bcaee6d Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 11:41:38 -0600 Subject: [PATCH 17/47] Update migration docs --- .../theme-json-reference/theme-json-living.md | 9 +- .../theme-json-migrations.md | 20 ++ .../theme-json-reference/theme-json-v2.md | 332 ++++++++++++++++++ 3 files changed, 357 insertions(+), 4 deletions(-) create mode 100644 docs/reference-guides/theme-json-reference/theme-json-v2.md diff --git a/docs/reference-guides/theme-json-reference/theme-json-living.md b/docs/reference-guides/theme-json-reference/theme-json-living.md index d9389597b89da2..2f80e007112855 100644 --- a/docs/reference-guides/theme-json-reference/theme-json-living.md +++ b/docs/reference-guides/theme-json-reference/theme-json-living.md @@ -1,10 +1,11 @@ # Theme.json Version 2 -> This is the living specification for **version 2** of `theme.json`. This version works with WordPress 5.9 or later, and the latest Gutenberg plugin. +> This is the living specification for **version 3** of `theme.json`. This version works with WordPress 5.9 or later, and the latest Gutenberg plugin. > > There are some related documents that you may be interested in: -> - the [theme.json v1](/docs/reference-guides/theme-json-reference/theme-json-v1.md) specification, and -> - the [reference to migrate from theme.json v1 to v2](/docs/reference-guides/theme-json-reference/theme-json-migrations.md). +> - the [theme.json v1](/docs/reference-guides/theme-json-reference/theme-json-v1.md) specification, +> - the [theme.json v2](/docs/reference-guides/theme-json-reference/theme-json-v2.md) specification, and +> - the [reference to migrate from older theme.json versions](/docs/reference-guides/theme-json-reference/theme-json-migrations.md). This reference guide lists the settings and style properties defined in the `theme.json` schema. See the [theme.json how to guide](/docs/how-to-guides/themes/global-settings-and-styles.md) for examples and guidance on how to use the `theme.json` file in your theme. @@ -17,7 +18,7 @@ Code editors can pick up the schema and can provide helpful hints and suggestion ``` { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, ... } ``` diff --git a/docs/reference-guides/theme-json-reference/theme-json-migrations.md b/docs/reference-guides/theme-json-reference/theme-json-migrations.md index b043ca1fba52ac..0f4409f15167f1 100644 --- a/docs/reference-guides/theme-json-reference/theme-json-migrations.md +++ b/docs/reference-guides/theme-json-reference/theme-json-migrations.md @@ -63,3 +63,23 @@ Additions to styles: ### Changes to property values The default font sizes provided by core (`settings.typography.fontSizes`) have been updated. The Normal and Huge sizes (with `normal` and `huge` slugs) have been removed from the list, and Extra Large (`x-large` slug) has been added. When the UI controls show the default values provided by core, Normal and Huge will no longer be present. However, their CSS classes and CSS Custom Properties are still enqueued to make sure existing content that uses them still works as expected. + +## Migrating from v2 to v3 + +Upgrading to v3 adjusts preset defaults to be more consistent with one another. + +### How to migrate from v1 to v2: + +1. Update `version` to `3`. +2. Configure the changed defaults if you'd like. + +### Changed defaults + +#### `settings.typography.defaultFontSizes` + +In theme.json v2, the default font sizes were always merged with the theme ones. + +The new `defaultFontSizes` option differs from that behavior. + +- When set to `true` it will show the default font sizes and prevent them from being overridden by the theme. +- When set to `false` it will hide the default font sizes. diff --git a/docs/reference-guides/theme-json-reference/theme-json-v2.md b/docs/reference-guides/theme-json-reference/theme-json-v2.md new file mode 100644 index 00000000000000..271c625b1aa156 --- /dev/null +++ b/docs/reference-guides/theme-json-reference/theme-json-v2.md @@ -0,0 +1,332 @@ +# Theme.json Version 2 + +> This is the living specification for **version 2** of `theme.json`. This version works with WordPress 5.9 or later, and the latest Gutenberg plugin. +> +> There are some related documents that you may be interested in: +> - the [theme.json v1](/docs/reference-guides/theme-json-reference/theme-json-v1.md) specification, and +> - the [reference to migrate from theme.json v1 to v2](/docs/reference-guides/theme-json-reference/theme-json-migrations.md). + +This reference guide lists the settings and style properties defined in the `theme.json` schema. See the [theme.json how to guide](/docs/how-to-guides/themes/global-settings-and-styles.md) for examples and guidance on how to use the `theme.json` file in your theme. + +## Schema + +Remembering the `theme.json` settings and properties while you develop can be difficult, so a [JSON schema](https://schemas.wp.org/trunk/theme.json) was created to help. + +Code editors can pick up the schema and can provide helpful hints and suggestions such as tooltips, autocomplete, or schema validation in the editor. To use the schema in Visual Studio Code, add `$schema`: "https://schemas.wp.org/trunk/theme.json" to the beginning of your theme.json file together with a `version` corresponding to the version you wish to use, e.g.: + +``` +{ + "$schema": "https://schemas.wp.org/trunk/theme.json", + "version": 2, + ... +} +``` + +## Settings + +### appearanceTools + +Setting that enables the following UI tools: + +- background: backgroundImage +- border: color, radius, style, width +- color: link +- dimensions: aspectRatio, minHeight +- position: sticky +- spacing: blockGap, margin, padding +- typography: lineHeight + +--- + +### useRootPaddingAwareAlignments + +_**Note:** Since WordPress 6.1._ + +Enables root padding (the values from `styles.spacing.padding`) to be applied to the contents of full-width blocks instead of the root block. + +Please note that when using this setting, `styles.spacing.padding` should always be set as an object with `top`, `right`, `bottom`, `left` values declared separately. + +--- + +### border + +Settings related to borders. + +| Property | Type | Default | Props | +| --- | --- | --- |--- | +| color | boolean | false | | +| radius | boolean | false | | +| style | boolean | false | | +| width | boolean | false | | + +--- + +### shadow + +Settings related to shadows. + +| Property | Type | Default | Props | +| --- | --- | --- |--- | +| defaultPresets | boolean | true | | +| presets | array | | name, shadow, slug | + +--- + +### color + +Settings related to colors. + +| Property | Type | Default | Props | +| --- | --- | --- |--- | +| background | boolean | true | | +| custom | boolean | true | | +| customDuotone | boolean | true | | +| customGradient | boolean | true | | +| defaultDuotone | boolean | true | | +| defaultGradients | boolean | true | | +| defaultPalette | boolean | true | | +| duotone | array | | colors, name, slug | +| gradients | array | | gradient, name, slug | +| link | boolean | false | | +| palette | array | | color, name, slug | +| text | boolean | true | | +| heading | boolean | true | | +| button | boolean | true | | + +--- + +### background + +Settings related to background. + +| Property | Type | Default | Props | +| --- | --- | --- |--- | +| backgroundImage | boolean | false | | + +--- + +### dimensions + +Settings related to dimensions. + +| Property | Type | Default | Props | +| --- | --- | --- |--- | +| aspectRatio | boolean | false | | +| minHeight | boolean | false | | + +--- + +### layout + +Settings related to layout. + +| Property | Type | Default | Props | +| --- | --- | --- |--- | +| contentSize | string | | | +| wideSize | string | | | +| allowEditing | boolean | true | | +| allowCustomContentAndWideSize | boolean | true | | + +--- + +### lightbox + +Settings related to the lightbox. + +| Property | Type | Default | Props | +| --- | --- | --- |--- | +| enabled | boolean | | | +| allowEditing | boolean | | | + +--- + +### position + +Settings related to position. + +| Property | Type | Default | Props | +| --- | --- | --- |--- | +| sticky | boolean | false | | + +--- + +### spacing + +Settings related to spacing. + +| Property | Type | Default | Props | +| --- | --- | --- |--- | +| blockGap | undefined | null | | +| margin | boolean | false | | +| padding | boolean | false | | +| units | array | px,em,rem,vh,vw,% | | +| customSpacingSize | boolean | true | | +| spacingSizes | array | | name, size, slug | +| spacingScale | object | | | + +--- + +### typography + +Settings related to typography. + +| Property | Type | Default | Props | +| --- | --- | --- |--- | +| customFontSize | boolean | true | | +| fontStyle | boolean | true | | +| fontWeight | boolean | true | | +| fluid | undefined | false | | +| letterSpacing | boolean | true | | +| lineHeight | boolean | false | | +| textColumns | boolean | false | | +| textDecoration | boolean | true | | +| writingMode | boolean | false | | +| textTransform | boolean | true | | +| dropCap | boolean | true | | +| fontSizes | array | | fluid, name, size, slug | +| fontFamilies | array | | fontFace, fontFamily, name, slug | + +--- + +### custom + +Generate custom CSS custom properties of the form `--wp--custom--{key}--{nested-key}: {value};`. `camelCased` keys are transformed to `kebab-case` as to follow the CSS property naming schema. Keys at different depth levels are separated by `--`, so keys should not include `--` in the name. + +--- + +## Styles + +### border + +Border styles. + +| Property | Type | Props | +| --- | --- |--- | +| color | string, object | | +| radius | string, object | | +| style | string, object | | +| width | string, object | | +| top | object | color, style, width | +| right | object | color, style, width | +| bottom | object | color, style, width | +| left | object | color, style, width | + +--- + +### color + +Color styles. + +| Property | Type | Props | +| --- | --- |--- | +| background | string, object | | +| gradient | string, object | | +| text | string, object | | + +--- + +### dimensions + +Dimensions styles + +| Property | Type | Props | +| --- | --- |--- | +| aspectRatio | string, object | | +| minHeight | string, object | | + +--- + +### spacing + +Spacing styles. + +| Property | Type | Props | +| --- | --- |--- | +| blockGap | string, object | | +| margin | object | bottom, left, right, top | +| padding | object | bottom, left, right, top | + +--- + +### typography + +Typography styles. + +| Property | Type | Props | +| --- | --- |--- | +| fontFamily | string, object | | +| fontSize | string, object | | +| fontStyle | string, object | | +| fontWeight | string, object | | +| letterSpacing | string, object | | +| lineHeight | string, object | | +| textColumns | string | | +| textDecoration | string, object | | +| writingMode | string, object | | +| textTransform | string, object | | + +--- + +### filter + +CSS and SVG filter styles. + +| Property | Type | Props | +| --- | --- |--- | +| duotone | string, object | | + +--- + +### shadow + +Box shadow styles. + +--- + +### outline + +Outline styles. + +| Property | Type | Props | +| --- | --- |--- | +| color | string, object | | +| offset | string, object | | +| style | string, object | | +| width | string, object | | + +--- + +### css + +Sets custom CSS to apply styling not covered by other theme.json properties. + +--- + +## customTemplates + +Additional metadata for custom templates defined in the templates folder. + +Type: `object`. + +| Property | Description | Type | +| --- | --- | --- | +| name | Filename, without extension, of the template in the templates folder. | string | +| title | Title of the template, translatable. | string | +| postTypes | List of post types that can use this custom template. | array | + +## templateParts + +Additional metadata for template parts defined in the parts folder. + +Type: `object`. + +| Property | Description | Type | +| --- | --- | --- | +| name | Filename, without extension, of the template in the parts folder. | string | +| title | Title of the template, translatable. | string | +| area | The area the template part is used for. Block variations for `header` and `footer` values exist and will be used when the area is set to one of those. | string | + +## Patterns + +An array of pattern slugs to be registered from the Pattern Directory. +Type: `array`. From 4e8dd5e841cdd02ca6b8b2f53030c4e92d7f98ae Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 11:58:47 -0600 Subject: [PATCH 18/47] Update phpunit theme fixtures --- .../class-wp-rest-global-styles-controller-gutenberg-test.php | 2 +- .../themedir1/block-theme-child-with-fluid-layout/theme.json | 2 +- .../block-theme-child-with-fluid-typography-config/theme.json | 2 +- .../block-theme-child-with-fluid-typography/theme.json | 2 +- .../data/themedir1/block-theme-child/styles/variation-a.json | 2 +- .../data/themedir1/block-theme-child/styles/variation-b.json | 2 +- phpunit/data/themedir1/block-theme-child/theme.json | 2 +- phpunit/data/themedir1/block-theme/styles/variation-a.json | 2 +- phpunit/data/themedir1/block-theme/styles/variation-b.json | 2 +- phpunit/data/themedir1/block-theme/styles/variation.json | 2 +- phpunit/data/themedir1/block-theme/theme.json | 2 +- .../fonts-block-theme/styles/variation-duplicate-fonts.json | 2 +- .../fonts-block-theme/styles/variation-new-font-family.json | 2 +- .../fonts-block-theme/styles/variation-new-font-variations.json | 2 +- .../themedir1/fonts-block-theme/styles/variation-no-fonts.json | 2 +- phpunit/data/themedir1/fonts-block-theme/theme.json | 2 +- 16 files changed, 16 insertions(+), 16 deletions(-) diff --git a/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php b/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php index 568dbc276dd594..563037f41db9dc 100644 --- a/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php +++ b/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php @@ -122,7 +122,7 @@ public function test_get_theme_items() { $data = $response->get_data(); $expected = array( array( - 'version' => 2, + 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( 'color' => array( 'palette' => array( diff --git a/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json b/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json index 710ec336df70b2..813024ba8abeb6 100644 --- a/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json +++ b/phpunit/data/themedir1/block-theme-child-with-fluid-layout/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "appearanceTools": true, "layout": { diff --git a/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json b/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json index dcd3745f1630cc..3aa0560aaf0623 100644 --- a/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json +++ b/phpunit/data/themedir1/block-theme-child-with-fluid-typography-config/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "appearanceTools": true, "layout": { diff --git a/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json b/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json index 7b345242702956..b2624775a50037 100644 --- a/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json +++ b/phpunit/data/themedir1/block-theme-child-with-fluid-typography/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "appearanceTools": true, "typography": { diff --git a/phpunit/data/themedir1/block-theme-child/styles/variation-a.json b/phpunit/data/themedir1/block-theme-child/styles/variation-a.json index a9d5ade8946928..53c3ef60619b5b 100644 --- a/phpunit/data/themedir1/block-theme-child/styles/variation-a.json +++ b/phpunit/data/themedir1/block-theme-child/styles/variation-a.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "settings": { "blocks": { "core/paragraph": { diff --git a/phpunit/data/themedir1/block-theme-child/styles/variation-b.json b/phpunit/data/themedir1/block-theme-child/styles/variation-b.json index 0a8a4fcab99f61..4e949f24c7f401 100644 --- a/phpunit/data/themedir1/block-theme-child/styles/variation-b.json +++ b/phpunit/data/themedir1/block-theme-child/styles/variation-b.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "settings": { "blocks": { "core/post-title": { diff --git a/phpunit/data/themedir1/block-theme-child/theme.json b/phpunit/data/themedir1/block-theme-child/theme.json index 1157fa91280303..185437e9b81c4b 100644 --- a/phpunit/data/themedir1/block-theme-child/theme.json +++ b/phpunit/data/themedir1/block-theme-child/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "color": { "palette": [ diff --git a/phpunit/data/themedir1/block-theme/styles/variation-a.json b/phpunit/data/themedir1/block-theme/styles/variation-a.json index 42c20fc63b5925..eb08d0090c177c 100644 --- a/phpunit/data/themedir1/block-theme/styles/variation-a.json +++ b/phpunit/data/themedir1/block-theme/styles/variation-a.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "settings": { "blocks": { "core/paragraph": { diff --git a/phpunit/data/themedir1/block-theme/styles/variation-b.json b/phpunit/data/themedir1/block-theme/styles/variation-b.json index 340198ffe0b65f..efdbe8aa86650b 100644 --- a/phpunit/data/themedir1/block-theme/styles/variation-b.json +++ b/phpunit/data/themedir1/block-theme/styles/variation-b.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "settings": { "blocks": { "core/post-title": { diff --git a/phpunit/data/themedir1/block-theme/styles/variation.json b/phpunit/data/themedir1/block-theme/styles/variation.json index d0f316cb454dd9..debb3666a767bd 100644 --- a/phpunit/data/themedir1/block-theme/styles/variation.json +++ b/phpunit/data/themedir1/block-theme/styles/variation.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "title": "Block theme variation", "settings": { "color": { diff --git a/phpunit/data/themedir1/block-theme/theme.json b/phpunit/data/themedir1/block-theme/theme.json index 212ef5df78f7e6..35f0e619a672f0 100644 --- a/phpunit/data/themedir1/block-theme/theme.json +++ b/phpunit/data/themedir1/block-theme/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "title": "Block theme", "settings": { "color": { diff --git a/phpunit/data/themedir1/fonts-block-theme/styles/variation-duplicate-fonts.json b/phpunit/data/themedir1/fonts-block-theme/styles/variation-duplicate-fonts.json index 040689043379d6..c24a4a85a4f673 100644 --- a/phpunit/data/themedir1/fonts-block-theme/styles/variation-duplicate-fonts.json +++ b/phpunit/data/themedir1/fonts-block-theme/styles/variation-duplicate-fonts.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "title": "Variation: duplicate fonts", "settings": { "typography": { diff --git a/phpunit/data/themedir1/fonts-block-theme/styles/variation-new-font-family.json b/phpunit/data/themedir1/fonts-block-theme/styles/variation-new-font-family.json index 01c6027835f976..50b277f45345e3 100644 --- a/phpunit/data/themedir1/fonts-block-theme/styles/variation-new-font-family.json +++ b/phpunit/data/themedir1/fonts-block-theme/styles/variation-new-font-family.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "title": "Variation: new font family", "settings": { "typography": { diff --git a/phpunit/data/themedir1/fonts-block-theme/styles/variation-new-font-variations.json b/phpunit/data/themedir1/fonts-block-theme/styles/variation-new-font-variations.json index 81268817ade703..95cb7b88d0fb78 100644 --- a/phpunit/data/themedir1/fonts-block-theme/styles/variation-new-font-variations.json +++ b/phpunit/data/themedir1/fonts-block-theme/styles/variation-new-font-variations.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "title": "Variation: new font variations", "settings": { "typography": { diff --git a/phpunit/data/themedir1/fonts-block-theme/styles/variation-no-fonts.json b/phpunit/data/themedir1/fonts-block-theme/styles/variation-no-fonts.json index 9c98c6893fa062..fcdd368ec691b8 100644 --- a/phpunit/data/themedir1/fonts-block-theme/styles/variation-no-fonts.json +++ b/phpunit/data/themedir1/fonts-block-theme/styles/variation-no-fonts.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "title": "Variation - no fonts", "styles": { "typography": { diff --git a/phpunit/data/themedir1/fonts-block-theme/theme.json b/phpunit/data/themedir1/fonts-block-theme/theme.json index a5d40da2b5bb2e..a7946a3f11023c 100644 --- a/phpunit/data/themedir1/fonts-block-theme/theme.json +++ b/phpunit/data/themedir1/fonts-block-theme/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "appearanceTools": true, "color": { From 4f36ed0b1a4326c22ee7264b46cee511c4384be1 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 12:02:24 -0600 Subject: [PATCH 19/47] Try fixing WP_REST_Global_Styles_Controller_Gutenberg_Test failure --- .../class-wp-rest-global-styles-controller-gutenberg-test.php | 3 +++ 1 file changed, 3 insertions(+) diff --git a/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php b/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php index 563037f41db9dc..b4185a42b15c3d 100644 --- a/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php +++ b/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php @@ -135,6 +135,9 @@ public function test_get_theme_items() { ), ), ), + 'typography' => array( + 'defaultFontSizes' => 'merge', + ), ), 'styles' => array( 'blocks' => array( From 0ca202abb08cf81c51a66c0b4d7bc39b94f4094e Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 12:05:00 -0600 Subject: [PATCH 20/47] Fix PHP lint --- .../class-wp-rest-global-styles-controller-gutenberg-test.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php b/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php index b4185a42b15c3d..38fc7af6e7c70c 100644 --- a/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php +++ b/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php @@ -124,7 +124,7 @@ public function test_get_theme_items() { array( 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( - 'color' => array( + 'color' => array( 'palette' => array( 'theme' => array( array( From ed2ec35cdd1a48be402f926b8f8360910daaf0cd Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 12:09:34 -0600 Subject: [PATCH 21/47] Default missing theme.json to latest schema --- lib/class-wp-theme-json-resolver-gutenberg.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/class-wp-theme-json-resolver-gutenberg.php b/lib/class-wp-theme-json-resolver-gutenberg.php index ec0d2c6bb0181e..16b2ad184b72b2 100644 --- a/lib/class-wp-theme-json-resolver-gutenberg.php +++ b/lib/class-wp-theme-json-resolver-gutenberg.php @@ -244,7 +244,7 @@ public static function get_theme_data( $deprecated = array(), $options = array() $theme_json_data = static::read_json_file( $theme_json_file ); $theme_json_data = static::translate( $theme_json_data, $wp_theme->get( 'TextDomain' ) ); } else { - $theme_json_data = array(); + $theme_json_data = array( 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA ); } /** From 3e6aafd14b43997e3666db485d87d925f84ae19e Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 12:10:28 -0600 Subject: [PATCH 22/47] Fix living docs title --- docs/reference-guides/theme-json-reference/theme-json-living.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/reference-guides/theme-json-reference/theme-json-living.md b/docs/reference-guides/theme-json-reference/theme-json-living.md index 2f80e007112855..367070545d5c33 100644 --- a/docs/reference-guides/theme-json-reference/theme-json-living.md +++ b/docs/reference-guides/theme-json-reference/theme-json-living.md @@ -1,4 +1,4 @@ -# Theme.json Version 2 +# Theme.json Version 3 > This is the living specification for **version 3** of `theme.json`. This version works with WordPress 5.9 or later, and the latest Gutenberg plugin. > From e4d41f97bf64352356492e5098227b7b25e002c5 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 12:37:25 -0600 Subject: [PATCH 23/47] Refactor typography-panel a bit --- .../global-styles/typography-panel.js | 30 ++++++++++--------- 1 file changed, 16 insertions(+), 14 deletions(-) diff --git a/packages/block-editor/src/components/global-styles/typography-panel.js b/packages/block-editor/src/components/global-styles/typography-panel.js index 38693a2f8f7d36..1dd78e72c70f7e 100644 --- a/packages/block-editor/src/components/global-styles/typography-panel.js +++ b/packages/block-editor/src/components/global-styles/typography-panel.js @@ -123,10 +123,22 @@ function getUniqueFontSizesBySlug( settings ) { * @return {Array} The merged font sizes. */ function getMergedFontSizes( settings ) { + /* + * For backwards compatibility with presets converting from a hardcoded `false` + * for `prevent_override` to a path to a boolean (`defaultFontSizes`, for example), + * the 'merge' value for the new setting both overrides the preset and tells the + * UI to continue to display a merged set of the default values. + */ + if ( settings?.typography?.defaultFontSizes === 'merge' ) { + return getUniqueFontSizesBySlug( settings ); + } + + const fontSizes = settings?.typography?.fontSizes; + const defaultFontSizesEnabled = !! settings?.typography?.defaultFontSizes; return [ - ...( settings?.typography?.fontSizes?.custom ?? [] ), - ...( settings?.typography?.fontSizes?.theme ?? [] ), - ...( settings?.typography?.fontSizes?.default ?? [] ), + ...( fontSizes?.custom ?? [] ), + ...( fontSizes?.theme ?? [] ), + ...( defaultFontSizesEnabled ? fontSizes?.default ?? [] : [] ), ]; } @@ -203,17 +215,7 @@ export default function TypographyPanel( { // Font Size const hasFontSizeEnabled = useHasFontSizeControl( settings ); const disableCustomFontSizes = ! settings?.typography?.customFontSize; - - /* - * For backwards compatibility with presets converting from a hardcoded `false` - * for `prevent_override` to a path to a boolean (`defaultFontSizes`, for example), - * the 'merge' value for the new setting both overrides the preset and tells the - * UI to continue to display a merged set of the default values. - */ - const mergedFontSizes = - settings?.typography?.defaultFontSizes === 'merge' - ? getUniqueFontSizesBySlug( settings ) - : getMergedFontSizes( settings ); + const mergedFontSizes = getMergedFontSizes( settings ); const fontSize = decodeValue( inheritedValue?.typography?.fontSize ); const setFontSize = ( newValue, metadata ) => { From 6136799bacfae124a0045b826804ebadd431b328 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 12:38:44 -0600 Subject: [PATCH 24/47] Fix docs manifest --- docs/manifest.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/manifest.json b/docs/manifest.json index 84c7da42aa8b20..b318331550f42a 100644 --- a/docs/manifest.json +++ b/docs/manifest.json @@ -564,7 +564,7 @@ "parent": "reference-guides" }, { - "title": "Theme.json Version 2", + "title": "Theme.json Version 3", "slug": "theme-json-living", "markdown_source": "../docs/reference-guides/theme-json-reference/theme-json-living.md", "parent": "theme-json-reference" From 5148bf4a4e5ee93d21235a8383cca5e636cf6445 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 12:53:59 -0600 Subject: [PATCH 25/47] Clarify migration docs --- .../theme-json-reference/theme-json-migrations.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/reference-guides/theme-json-reference/theme-json-migrations.md b/docs/reference-guides/theme-json-reference/theme-json-migrations.md index 0f4409f15167f1..d845ba9e1fccf0 100644 --- a/docs/reference-guides/theme-json-reference/theme-json-migrations.md +++ b/docs/reference-guides/theme-json-reference/theme-json-migrations.md @@ -82,4 +82,4 @@ In theme.json v2, the default font sizes were always merged with the theme ones. The new `defaultFontSizes` option differs from that behavior. - When set to `true` it will show the default font sizes and prevent them from being overridden by the theme. -- When set to `false` it will hide the default font sizes. +- When set to `false` it will hide the default font sizes and allow the theme to use the default slugs. From c6bf6721b44c753fd37e82619201b6f8ff81dc7e Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 13:18:21 -0600 Subject: [PATCH 26/47] Revert "Remove uniqByProperty" This reverts commit c12d3a28c8b1de32a5ae205d9bcd739e1c8e3958. --- .../components/global-styles/typography-panel.js | 2 +- packages/block-editor/src/utils/object.js | 16 ++++++++++++++++ 2 files changed, 17 insertions(+), 1 deletion(-) diff --git a/packages/block-editor/src/components/global-styles/typography-panel.js b/packages/block-editor/src/components/global-styles/typography-panel.js index 1dd78e72c70f7e..7c463563c03def 100644 --- a/packages/block-editor/src/components/global-styles/typography-panel.js +++ b/packages/block-editor/src/components/global-styles/typography-panel.js @@ -22,7 +22,7 @@ import TextTransformControl from '../text-transform-control'; import TextDecorationControl from '../text-decoration-control'; import WritingModeControl from '../writing-mode-control'; import { getValueFromVariable, TOOLSPANEL_DROPDOWNMENU_PROPS } from './utils'; -import { setImmutably } from '../../utils/object'; +import { setImmutably, uniqByProperty } from '../../utils/object'; const MIN_TEXT_COLUMNS = 1; const MAX_TEXT_COLUMNS = 6; diff --git a/packages/block-editor/src/utils/object.js b/packages/block-editor/src/utils/object.js index 8f6c82a9c3991e..c78fe0e656dfef 100644 --- a/packages/block-editor/src/utils/object.js +++ b/packages/block-editor/src/utils/object.js @@ -49,3 +49,19 @@ export const getValueFromObjectPath = ( object, path, defaultValue ) => { } ); return value ?? defaultValue; }; + +/** + * Helper util to filter out objects with duplicate values for a given property. + * + * @param {Object[]} array Array of objects to filter. + * @param {string} property Property to filter unique values by. + * + * @return {Object[]} Array of objects with unique values for the specified property. + */ +export function uniqByProperty( array, property ) { + const seen = new Set(); + return array.filter( ( item ) => { + const value = item[ property ]; + return seen.has( value ) ? false : seen.add( value ); + } ); +} From 044a6f919ad6f69277bef54f06b0c79de6f1ea61 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 13:30:53 -0600 Subject: [PATCH 27/47] Fix getUniqueFontSizesBySlug --- .../src/components/global-styles/typography-panel.js | 12 ++++-------- 1 file changed, 4 insertions(+), 8 deletions(-) diff --git a/packages/block-editor/src/components/global-styles/typography-panel.js b/packages/block-editor/src/components/global-styles/typography-panel.js index 7c463563c03def..e48240a1c5a599 100644 --- a/packages/block-editor/src/components/global-styles/typography-panel.js +++ b/packages/block-editor/src/components/global-styles/typography-panel.js @@ -105,14 +105,10 @@ function useHasTextColumnsControl( settings ) { function getUniqueFontSizesBySlug( settings ) { const fontSizes = settings?.typography?.fontSizes; - const mergedFontSizes = fontSizes ? mergeOrigins( fontSizes ) : []; - const uniqueSizes = []; - for ( const currentSize of mergedFontSizes ) { - if ( ! uniqueSizes.some( ( { slug } ) => slug === currentSize.slug ) ) { - uniqueSizes.push( currentSize ); - } - } - return uniqueSizes; + const mergedFontSizes = fontSizes + ? mergeOrigins( fontSizes ).toReversed() // New array because mergeOrigins result is cached. + : []; + return uniqByProperty( mergedFontSizes, 'slug' ).reverse(); // In-place reverse to save memory. } /** From 3d2f8dfc94f69d8349e0f94fb483eb4dedc36dc7 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 14:15:10 -0600 Subject: [PATCH 28/47] Update default schema elsewhere --- lib/class-wp-theme-json-data-gutenberg.php | 2 +- lib/class-wp-theme-json-gutenberg.php | 2 +- lib/class-wp-theme-json-resolver-gutenberg.php | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/lib/class-wp-theme-json-data-gutenberg.php b/lib/class-wp-theme-json-data-gutenberg.php index 6877a209b687f5..c564016b1a7119 100644 --- a/lib/class-wp-theme-json-data-gutenberg.php +++ b/lib/class-wp-theme-json-data-gutenberg.php @@ -38,7 +38,7 @@ class WP_Theme_JSON_Data_Gutenberg { * @param array $data Array following the theme.json specification. * @param string $origin The origin of the data: default, theme, user. */ - public function __construct( $data = array(), $origin = 'theme' ) { + public function __construct( $data = array( 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA ), $origin = 'theme' ) { $this->origin = $origin; $this->theme_json = new WP_Theme_JSON_Gutenberg( $data, $this->origin ); } diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index 580ab5cc6472ea..4d2a0c5129aaa1 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -692,7 +692,7 @@ public static function get_element_class_name( $element ) { * @param string $origin Optional. What source of data this object represents. * One of 'default', 'theme', or 'custom'. Default 'theme'. */ - public function __construct( $theme_json = array(), $origin = 'theme' ) { + public function __construct( $theme_json = array( 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA ), $origin = 'theme' ) { if ( ! in_array( $origin, static::VALID_ORIGINS, true ) ) { $origin = 'theme'; } diff --git a/lib/class-wp-theme-json-resolver-gutenberg.php b/lib/class-wp-theme-json-resolver-gutenberg.php index 16b2ad184b72b2..bd7b375f18bcf8 100644 --- a/lib/class-wp-theme-json-resolver-gutenberg.php +++ b/lib/class-wp-theme-json-resolver-gutenberg.php @@ -369,7 +369,7 @@ public static function get_block_data() { return static::$blocks; } - $config = array( 'version' => 2 ); + $config = array( 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA ); foreach ( $blocks as $block_name => $block_type ) { if ( isset( $block_type->supports['__experimentalStyle'] ) ) { $config['styles']['blocks'][ $block_name ] = static::remove_json_comments( $block_type->supports['__experimentalStyle'] ); From 78c55b93454b6a8f465aa7ba5ae5bd78361a8970 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 7 Feb 2024 14:46:02 -0600 Subject: [PATCH 29/47] Order the presets default, theme, custom --- .../src/components/global-styles/typography-panel.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/block-editor/src/components/global-styles/typography-panel.js b/packages/block-editor/src/components/global-styles/typography-panel.js index e48240a1c5a599..34be7c1b710631 100644 --- a/packages/block-editor/src/components/global-styles/typography-panel.js +++ b/packages/block-editor/src/components/global-styles/typography-panel.js @@ -132,9 +132,9 @@ function getMergedFontSizes( settings ) { const fontSizes = settings?.typography?.fontSizes; const defaultFontSizesEnabled = !! settings?.typography?.defaultFontSizes; return [ - ...( fontSizes?.custom ?? [] ), - ...( fontSizes?.theme ?? [] ), ...( defaultFontSizesEnabled ? fontSizes?.default ?? [] : [] ), + ...( fontSizes?.theme ?? [] ), + ...( fontSizes?.custom ?? [] ), ]; } From 7f0577a9f122eef72870f9a58d77e81722caded4 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Fri, 9 Feb 2024 11:04:54 -0600 Subject: [PATCH 30/47] Reword the theme.json v2 backwards compatibility comment --- .../global-styles/typography-panel.js | 25 ++++++++----------- 1 file changed, 11 insertions(+), 14 deletions(-) diff --git a/packages/block-editor/src/components/global-styles/typography-panel.js b/packages/block-editor/src/components/global-styles/typography-panel.js index 34be7c1b710631..f150e72ff5df54 100644 --- a/packages/block-editor/src/components/global-styles/typography-panel.js +++ b/packages/block-editor/src/components/global-styles/typography-panel.js @@ -103,16 +103,8 @@ function useHasTextColumnsControl( settings ) { return settings?.typography?.textColumns; } -function getUniqueFontSizesBySlug( settings ) { - const fontSizes = settings?.typography?.fontSizes; - const mergedFontSizes = fontSizes - ? mergeOrigins( fontSizes ).toReversed() // New array because mergeOrigins result is cached. - : []; - return uniqByProperty( mergedFontSizes, 'slug' ).reverse(); // In-place reverse to save memory. -} - /** - * Concatenate all the font sizes. + * Concatenate all the font sizes into a single list for the font size picker. * * @param {Object} settings The global styles settings. * @@ -120,13 +112,18 @@ function getUniqueFontSizesBySlug( settings ) { */ function getMergedFontSizes( settings ) { /* - * For backwards compatibility with presets converting from a hardcoded `false` - * for `prevent_override` to a path to a boolean (`defaultFontSizes`, for example), - * the 'merge' value for the new setting both overrides the preset and tells the - * UI to continue to display a merged set of the default values. + * Backward compatibility for theme.json v2 is triggered by the 'merge' + * value added during the migration process. The old behavior that didn't + * match the other preset controls was to list the partially overridden + * default font sizes. The new behavior either shows all the default font + * sizes or none of them. */ if ( settings?.typography?.defaultFontSizes === 'merge' ) { - return getUniqueFontSizesBySlug( settings ); + const fontSizes = settings?.typography?.fontSizes; + const mergedFontSizes = fontSizes + ? mergeOrigins( fontSizes ).toReversed() // New array because mergeOrigins result is cached. + : []; + return uniqByProperty( mergedFontSizes, 'slug' ).reverse(); // In-place reverse to save memory. } const fontSizes = settings?.typography?.fontSizes; From cc530d689005c758d5a0b99aa417731d0b43ce69 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Fri, 9 Feb 2024 11:21:11 -0600 Subject: [PATCH 31/47] Update rest controller test theme --- .../class-wp-rest-global-styles-controller-gutenberg-test.php | 3 --- test/emptytheme/styles/variation.json | 2 +- test/emptytheme/theme.json | 2 +- 3 files changed, 2 insertions(+), 5 deletions(-) diff --git a/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php b/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php index 38fc7af6e7c70c..3dbb20050d7f55 100644 --- a/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php +++ b/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php @@ -135,9 +135,6 @@ public function test_get_theme_items() { ), ), ), - 'typography' => array( - 'defaultFontSizes' => 'merge', - ), ), 'styles' => array( 'blocks' => array( diff --git a/test/emptytheme/styles/variation.json b/test/emptytheme/styles/variation.json index 0ab221d087035a..06f672f6fd25d7 100644 --- a/test/emptytheme/styles/variation.json +++ b/test/emptytheme/styles/variation.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "settings": { "color": { "palette": [ diff --git a/test/emptytheme/theme.json b/test/emptytheme/theme.json index d95ed844e6b1cb..62ce296e971c34 100644 --- a/test/emptytheme/theme.json +++ b/test/emptytheme/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "settings": { "appearanceTools": true, "layout": { From b2c38828034c8fd614f828ebee2f9757596965db Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Fri, 9 Feb 2024 11:21:41 -0600 Subject: [PATCH 32/47] PHP Lint --- .../class-wp-rest-global-styles-controller-gutenberg-test.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php b/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php index 3dbb20050d7f55..563037f41db9dc 100644 --- a/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php +++ b/phpunit/class-wp-rest-global-styles-controller-gutenberg-test.php @@ -124,7 +124,7 @@ public function test_get_theme_items() { array( 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( - 'color' => array( + 'color' => array( 'palette' => array( 'theme' => array( array( From 1105ad295d8de01295ddf716c1383c40244305d8 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Fri, 9 Feb 2024 12:54:55 -0600 Subject: [PATCH 33/47] Update a few more theme.json files for tests --- test/gutenberg-test-themes/style-variations/styles/pink.json | 2 +- test/gutenberg-test-themes/style-variations/styles/yellow.json | 2 +- test/gutenberg-test-themes/style-variations/theme.json | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/test/gutenberg-test-themes/style-variations/styles/pink.json b/test/gutenberg-test-themes/style-variations/styles/pink.json index bdbf2829eb5528..c9e4ac85c1c795 100644 --- a/test/gutenberg-test-themes/style-variations/styles/pink.json +++ b/test/gutenberg-test-themes/style-variations/styles/pink.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "settings": { "color": { "palette": [ diff --git a/test/gutenberg-test-themes/style-variations/styles/yellow.json b/test/gutenberg-test-themes/style-variations/styles/yellow.json index 9bf00e21b42205..df82e52408da36 100644 --- a/test/gutenberg-test-themes/style-variations/styles/yellow.json +++ b/test/gutenberg-test-themes/style-variations/styles/yellow.json @@ -1,5 +1,5 @@ { - "version": 2, + "version": 3, "styles": { "color": { "background": "#ffef0b", diff --git a/test/gutenberg-test-themes/style-variations/theme.json b/test/gutenberg-test-themes/style-variations/theme.json index f0fc1ae54042a2..dee779a4ca0df9 100644 --- a/test/gutenberg-test-themes/style-variations/theme.json +++ b/test/gutenberg-test-themes/style-variations/theme.json @@ -1,6 +1,6 @@ { "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 2, + "version": 3, "styles": { "color": { "background": "red" From 214e8f35f294d94c606685ec56cc766ad5e52b03 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 14 Feb 2024 09:19:34 -0600 Subject: [PATCH 34/47] Remove the merge keyword that is no longer needed since #58951 --- lib/class-wp-theme-json-gutenberg.php | 10 ---------- lib/class-wp-theme-json-schema-gutenberg.php | 2 +- .../global-styles/typography-panel.js | 17 +---------------- phpunit/class-wp-theme-json-schema-test.php | 4 ++-- 4 files changed, 4 insertions(+), 29 deletions(-) diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index 4d2a0c5129aaa1..76abf3fb473a76 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -2771,16 +2771,6 @@ public function merge( $incoming ) { $prevent_override = $preset_metadata['prevent_override']; if ( is_array( $prevent_override ) ) { $prevent_override = _wp_array_get( $this->theme_json['settings'], $preset_metadata['prevent_override'] ); - - /* - * For backwards compatibility with presets converting from a hardcoded `false` - * for `prevent_override` to a path to a boolean (`defaultFontSizes`, for example), - * the 'merge' value for the new setting both overrides the preset and tells the - * UI to continue to display a merged set of the default values. - */ - if ( 'merge' === $prevent_override ) { - $prevent_override = false; - } } foreach ( static::VALID_ORIGINS as $origin ) { diff --git a/lib/class-wp-theme-json-schema-gutenberg.php b/lib/class-wp-theme-json-schema-gutenberg.php index 728dd32227798d..fcc43764264f43 100644 --- a/lib/class-wp-theme-json-schema-gutenberg.php +++ b/lib/class-wp-theme-json-schema-gutenberg.php @@ -116,7 +116,7 @@ private static function migrate_v2_to_v3( $old ) { if ( ! isset( $old['settings']['typography'] ) ) { $new['settings']['typography'] = array(); } - $new['settings']['typography']['defaultFontSizes'] = 'merge'; + $new['settings']['typography']['defaultFontSizes'] = false; // Set the new version. $new['version'] = 3; diff --git a/packages/block-editor/src/components/global-styles/typography-panel.js b/packages/block-editor/src/components/global-styles/typography-panel.js index 8ccb48c98fa90f..f0dac28335df57 100644 --- a/packages/block-editor/src/components/global-styles/typography-panel.js +++ b/packages/block-editor/src/components/global-styles/typography-panel.js @@ -22,7 +22,7 @@ import TextTransformControl from '../text-transform-control'; import TextDecorationControl from '../text-decoration-control'; import WritingModeControl from '../writing-mode-control'; import { getValueFromVariable, TOOLSPANEL_DROPDOWNMENU_PROPS } from './utils'; -import { setImmutably, uniqByProperty } from '../../utils/object'; +import { setImmutably } from '../../utils/object'; const MIN_TEXT_COLUMNS = 1; const MAX_TEXT_COLUMNS = 6; @@ -111,21 +111,6 @@ function useHasTextColumnsControl( settings ) { * @return {Array} The merged font sizes. */ function getMergedFontSizes( settings ) { - /* - * Backward compatibility for theme.json v2 is triggered by the 'merge' - * value added during the migration process. The old behavior that didn't - * match the other preset controls was to list the partially overridden - * default font sizes. The new behavior either shows all the default font - * sizes or none of them. - */ - if ( settings?.typography?.defaultFontSizes === 'merge' ) { - const fontSizes = settings?.typography?.fontSizes; - const mergedFontSizes = fontSizes - ? mergeOrigins( fontSizes ).toReversed() // New array because mergeOrigins result is cached. - : []; - return uniqByProperty( mergedFontSizes, 'slug' ).reverse(); // In-place reverse to save memory. - } - const fontSizes = settings?.typography?.fontSizes; const defaultFontSizesEnabled = !! settings?.typography?.defaultFontSizes; return [ diff --git a/phpunit/class-wp-theme-json-schema-test.php b/phpunit/class-wp-theme-json-schema-test.php index 19deb1acdfdddc..8274b1abe2f802 100644 --- a/phpunit/class-wp-theme-json-schema-test.php +++ b/phpunit/class-wp-theme-json-schema-test.php @@ -120,7 +120,7 @@ public function test_migrate_v1_to_latest() { 'width' => false, ), 'typography' => array( - 'defaultFontSizes' => 'merge', + 'defaultFontSizes' => false, 'fontStyle' => false, 'fontWeight' => false, 'letterSpacing' => false, @@ -293,7 +293,7 @@ public function test_migrate_v2_to_latest() { 'width' => false, ), 'typography' => array( - 'defaultFontSizes' => 'merge', + 'defaultFontSizes' => false, 'fontStyle' => false, 'fontWeight' => false, 'letterSpacing' => false, From b0cff007b6729b452f72dc93db94514b2eec0102 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 13 Mar 2024 18:21:45 -0500 Subject: [PATCH 35/47] Hacky way to fix DB save issues --- ...ss-wp-rest-global-styles-controller-gutenberg.php | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/lib/class-wp-rest-global-styles-controller-gutenberg.php b/lib/class-wp-rest-global-styles-controller-gutenberg.php index 79cb8af59df4f9..c3e5e452d0e4c0 100644 --- a/lib/class-wp-rest-global-styles-controller-gutenberg.php +++ b/lib/class-wp-rest-global-styles-controller-gutenberg.php @@ -335,6 +335,18 @@ protected function prepare_item_for_database( $request ) { } elseif ( isset( $existing_config['settings'] ) ) { $config['settings'] = $existing_config['settings']; } + + // TODO: Figure out where this should actually go. + if ( isset( $config['settings']['typography']['defaultFontSizes'] ) ) { + unset( $config['settings']['typography']['defaultFontSizes'] ); + if ( empty( $config['settings']['typography'] ) ) { + unset( $config['settings']['typography'] ); + if ( empty( $config['settings'] ) ) { + unset( $config['settings'] ); + } + } + } + $config['isGlobalStylesUserThemeJSON'] = true; $config['version'] = WP_Theme_JSON_Gutenberg::LATEST_SCHEMA; $changes->post_content = wp_json_encode( $config ); From a0e083176fb6f04a88229c7b6aa12e0031f5a5ee Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Mon, 18 Mar 2024 13:19:33 -0500 Subject: [PATCH 36/47] Use $new instead of $old --- lib/class-wp-theme-json-schema-gutenberg.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/class-wp-theme-json-schema-gutenberg.php b/lib/class-wp-theme-json-schema-gutenberg.php index fcc43764264f43..43309513708a94 100644 --- a/lib/class-wp-theme-json-schema-gutenberg.php +++ b/lib/class-wp-theme-json-schema-gutenberg.php @@ -110,10 +110,10 @@ private static function migrate_v2_to_v3( $old ) { $new = $old; // Overwrite the things that changed. - if ( ! isset( $old['settings'] ) ) { + if ( ! isset( $new['settings'] ) ) { $new['settings'] = array(); } - if ( ! isset( $old['settings']['typography'] ) ) { + if ( ! isset( $new['settings']['typography'] ) ) { $new['settings']['typography'] = array(); } $new['settings']['typography']['defaultFontSizes'] = false; From 14f4ae24c2d03a63d6f5a7c2ab575aff0f2bdfc4 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Mon, 18 Mar 2024 13:22:01 -0500 Subject: [PATCH 37/47] Skip defaultFontSizes migration for custom origin theme.json files --- ...est-global-styles-controller-gutenberg.php | 11 ------- lib/class-wp-theme-json-schema-gutenberg.php | 29 ++++++++++++++----- 2 files changed, 22 insertions(+), 18 deletions(-) diff --git a/lib/class-wp-rest-global-styles-controller-gutenberg.php b/lib/class-wp-rest-global-styles-controller-gutenberg.php index c3e5e452d0e4c0..ca380265873f97 100644 --- a/lib/class-wp-rest-global-styles-controller-gutenberg.php +++ b/lib/class-wp-rest-global-styles-controller-gutenberg.php @@ -336,17 +336,6 @@ protected function prepare_item_for_database( $request ) { $config['settings'] = $existing_config['settings']; } - // TODO: Figure out where this should actually go. - if ( isset( $config['settings']['typography']['defaultFontSizes'] ) ) { - unset( $config['settings']['typography']['defaultFontSizes'] ); - if ( empty( $config['settings']['typography'] ) ) { - unset( $config['settings']['typography'] ); - if ( empty( $config['settings'] ) ) { - unset( $config['settings'] ); - } - } - } - $config['isGlobalStylesUserThemeJSON'] = true; $config['version'] = WP_Theme_JSON_Gutenberg::LATEST_SCHEMA; $changes->post_content = wp_json_encode( $config ); diff --git a/lib/class-wp-theme-json-schema-gutenberg.php b/lib/class-wp-theme-json-schema-gutenberg.php index 43309513708a94..567290df665709 100644 --- a/lib/class-wp-theme-json-schema-gutenberg.php +++ b/lib/class-wp-theme-json-schema-gutenberg.php @@ -95,9 +95,9 @@ private static function migrate_v1_to_v2( $old ) { } /** - * Sets settings.typography.defaultFontSizes to false as it drives - * PRESETS_METADATA prevent_override in class-wp-theme-json.php which was - * hardcoded to false in v2 but defaults to true in v3. + * Migrates from v2 to v3. + * + * - Sets settings.typography.defaultFontSizes to false. * * @since 6.5.0 * @@ -109,7 +109,25 @@ private static function migrate_v2_to_v3( $old ) { // Copy everything. $new = $old; - // Overwrite the things that changed. + // Set the new version. + $new['version'] = 3; + + /* + * Remaining changes do not need to be applied to the custom origin, + * as they should take on the value of the theme origin. + */ + if ( + isset( $new['isGlobalStylesUserThemeJSON'] ) && + true === $new['isGlobalStylesUserThemeJSON'] + ) { + return $new; + } + + /* + * Even though defaultFontSizes is a new setting, we need to migrate + * it to false as it controls the PRESETS_METADATA prevent_override + * which controls how CSS is generated and was hardcoded to false. + */ if ( ! isset( $new['settings'] ) ) { $new['settings'] = array(); } @@ -118,9 +136,6 @@ private static function migrate_v2_to_v3( $old ) { } $new['settings']['typography']['defaultFontSizes'] = false; - // Set the new version. - $new['version'] = 3; - return $new; } From 0472561883c5edc75b1549b14c7068d0ef7f7b7b Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Tue, 16 Apr 2024 09:05:17 -0500 Subject: [PATCH 38/47] Fix missing textAlign in docs from merge --- docs/reference-guides/theme-json-reference/theme-json-v2.md | 1 + 1 file changed, 1 insertion(+) diff --git a/docs/reference-guides/theme-json-reference/theme-json-v2.md b/docs/reference-guides/theme-json-reference/theme-json-v2.md index 271c625b1aa156..ea68eb0eb5772e 100644 --- a/docs/reference-guides/theme-json-reference/theme-json-v2.md +++ b/docs/reference-guides/theme-json-reference/theme-json-v2.md @@ -178,6 +178,7 @@ Settings related to typography. | fluid | undefined | false | | | letterSpacing | boolean | true | | | lineHeight | boolean | false | | +| textAlign | boolean | true | | | textColumns | boolean | false | | | textDecoration | boolean | true | | | writingMode | boolean | false | | From 1dc4715cef02f95480235aa1e35c6dfd1c9d1139 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Tue, 16 Apr 2024 09:12:46 -0500 Subject: [PATCH 39/47] Remove empty line change --- lib/class-wp-rest-global-styles-controller-gutenberg.php | 1 - 1 file changed, 1 deletion(-) diff --git a/lib/class-wp-rest-global-styles-controller-gutenberg.php b/lib/class-wp-rest-global-styles-controller-gutenberg.php index ca380265873f97..79cb8af59df4f9 100644 --- a/lib/class-wp-rest-global-styles-controller-gutenberg.php +++ b/lib/class-wp-rest-global-styles-controller-gutenberg.php @@ -335,7 +335,6 @@ protected function prepare_item_for_database( $request ) { } elseif ( isset( $existing_config['settings'] ) ) { $config['settings'] = $existing_config['settings']; } - $config['isGlobalStylesUserThemeJSON'] = true; $config['version'] = WP_Theme_JSON_Gutenberg::LATEST_SCHEMA; $changes->post_content = wp_json_encode( $config ); From 35e8eb85a936240cd061034d7409cf24b68f7609 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 17 Apr 2024 15:03:21 -0500 Subject: [PATCH 40/47] Fix user styles not migrating correctly --- lib/class-wp-theme-json-resolver-gutenberg.php | 1 - 1 file changed, 1 deletion(-) diff --git a/lib/class-wp-theme-json-resolver-gutenberg.php b/lib/class-wp-theme-json-resolver-gutenberg.php index cd0f1170ca6f00..bff907b302988a 100644 --- a/lib/class-wp-theme-json-resolver-gutenberg.php +++ b/lib/class-wp-theme-json-resolver-gutenberg.php @@ -549,7 +549,6 @@ public static function get_user_data() { isset( $decoded_data['isGlobalStylesUserThemeJSON'] ) && $decoded_data['isGlobalStylesUserThemeJSON'] ) { - unset( $decoded_data['isGlobalStylesUserThemeJSON'] ); $config = $decoded_data; } } From a46414a9ec2888ac5212e29b23b0f22c4e0ea26c Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 17 Apr 2024 15:27:58 -0500 Subject: [PATCH 41/47] Reorder font size dropdown --- .../src/components/global-styles/typography-panel.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/block-editor/src/components/global-styles/typography-panel.js b/packages/block-editor/src/components/global-styles/typography-panel.js index f0dac28335df57..40fc692bae2dc4 100644 --- a/packages/block-editor/src/components/global-styles/typography-panel.js +++ b/packages/block-editor/src/components/global-styles/typography-panel.js @@ -114,9 +114,9 @@ function getMergedFontSizes( settings ) { const fontSizes = settings?.typography?.fontSizes; const defaultFontSizesEnabled = !! settings?.typography?.defaultFontSizes; return [ - ...( defaultFontSizesEnabled ? fontSizes?.default ?? [] : [] ), - ...( fontSizes?.theme ?? [] ), ...( fontSizes?.custom ?? [] ), + ...( fontSizes?.theme ?? [] ), + ...( defaultFontSizesEnabled ? fontSizes?.default ?? [] : [] ), ]; } From d494c2e7e4af1c363e9063ef127f351c501039bb Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 17 Apr 2024 15:49:13 -0500 Subject: [PATCH 42/47] Only run migration on themes with font sizes defined --- lib/class-wp-theme-json-schema-gutenberg.php | 20 ++++++++++++-------- 1 file changed, 12 insertions(+), 8 deletions(-) diff --git a/lib/class-wp-theme-json-schema-gutenberg.php b/lib/class-wp-theme-json-schema-gutenberg.php index 567290df665709..5b52ccc27c686e 100644 --- a/lib/class-wp-theme-json-schema-gutenberg.php +++ b/lib/class-wp-theme-json-schema-gutenberg.php @@ -125,16 +125,20 @@ private static function migrate_v2_to_v3( $old ) { /* * Even though defaultFontSizes is a new setting, we need to migrate - * it to false as it controls the PRESETS_METADATA prevent_override - * which controls how CSS is generated and was hardcoded to false. + * it as it controls the PRESETS_METADATA prevent_override which was + * previously hardcoded to false. This only needs to happen when the + * theme provided font sizes as they could match the default ones and + * affect the generated CSS. */ - if ( ! isset( $new['settings'] ) ) { - $new['settings'] = array(); - } - if ( ! isset( $new['settings']['typography'] ) ) { - $new['settings']['typography'] = array(); + if ( isset( $new['settings']['typography']['fontSizes'] ) ) { + if ( ! isset( $new['settings'] ) ) { + $new['settings'] = array(); + } + if ( ! isset( $new['settings']['typography'] ) ) { + $new['settings']['typography'] = array(); + } + $new['settings']['typography']['defaultFontSizes'] = false; } - $new['settings']['typography']['defaultFontSizes'] = false; return $new; } From 930f29727d9a49d8cfe7b42ddb3bb8baf81888e8 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 17 Apr 2024 15:52:17 -0500 Subject: [PATCH 43/47] Add more details to comment --- lib/class-wp-theme-json-schema-gutenberg.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/lib/class-wp-theme-json-schema-gutenberg.php b/lib/class-wp-theme-json-schema-gutenberg.php index 5b52ccc27c686e..553354c438ed4a 100644 --- a/lib/class-wp-theme-json-schema-gutenberg.php +++ b/lib/class-wp-theme-json-schema-gutenberg.php @@ -128,7 +128,8 @@ private static function migrate_v2_to_v3( $old ) { * it as it controls the PRESETS_METADATA prevent_override which was * previously hardcoded to false. This only needs to happen when the * theme provided font sizes as they could match the default ones and - * affect the generated CSS. + * affect the generated CSS. And in v2 we provided default font sizes + * when the theme did not provide any. */ if ( isset( $new['settings']['typography']['fontSizes'] ) ) { if ( ! isset( $new['settings'] ) ) { From ec141501fc762d265d9017b3e5b3710f114fe861 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Wed, 17 Apr 2024 17:14:02 -0500 Subject: [PATCH 44/47] Ensure isGlobalStylesUserThemeJSON is set for migrations --- lib/class-wp-theme-json-resolver-gutenberg.php | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/lib/class-wp-theme-json-resolver-gutenberg.php b/lib/class-wp-theme-json-resolver-gutenberg.php index bff907b302988a..1d27353b70a89b 100644 --- a/lib/class-wp-theme-json-resolver-gutenberg.php +++ b/lib/class-wp-theme-json-resolver-gutenberg.php @@ -554,8 +554,12 @@ public static function get_user_data() { } /** This filter is documented in wp-includes/class-wp-theme-json-resolver.php */ - $theme_json = apply_filters( 'wp_theme_json_data_user', new WP_Theme_JSON_Data_Gutenberg( $config, 'custom' ) ); - $config = $theme_json->get_data(); + $theme_json = apply_filters( 'wp_theme_json_data_user', new WP_Theme_JSON_Data_Gutenberg( $config, 'custom' ) ); + $config = $theme_json->get_data(); + + // Needs to be set for schema migrations of user data. + $config['isGlobalStylesUserThemeJSON'] = true; + static::$user = new WP_Theme_JSON_Gutenberg( $config, 'custom' ); return static::$user; From e4459f08bebc17544023f6aec9983589b5ab6e82 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Tue, 23 Apr 2024 11:37:37 -0500 Subject: [PATCH 45/47] Update tests since skipping for missing font sizes --- phpunit/class-wp-theme-json-schema-test.php | 184 +++++--------------- 1 file changed, 41 insertions(+), 143 deletions(-) diff --git a/phpunit/class-wp-theme-json-schema-test.php b/phpunit/class-wp-theme-json-schema-test.php index 8274b1abe2f802..8e8521a39a30ac 100644 --- a/phpunit/class-wp-theme-json-schema-test.php +++ b/phpunit/class-wp-theme-json-schema-test.php @@ -35,6 +35,18 @@ public function test_migrate_v1_to_latest() { 'width' => false, ), 'typography' => array( + 'fontSizes' => array( + array( + 'name' => 'Small', + 'slug' => 'small', + 'size' => 12, + ), + array( + 'name' => 'Normal', + 'slug' => 'normal', + 'size' => 16, + ), + ), 'fontStyle' => false, 'fontWeight' => false, 'letterSpacing' => false, @@ -121,6 +133,18 @@ public function test_migrate_v1_to_latest() { ), 'typography' => array( 'defaultFontSizes' => false, + 'fontSizes' => array( + array( + 'name' => 'Small', + 'slug' => 'small', + 'size' => 12, + ), + array( + 'name' => 'Normal', + 'slug' => 'normal', + 'size' => 16, + ), + ), 'fontStyle' => false, 'fontWeight' => false, 'letterSpacing' => false, @@ -185,80 +209,17 @@ public function test_migrate_v2_to_latest() { $theme_json_v2 = array( 'version' => 2, 'settings' => array( - 'color' => array( - 'palette' => array( + 'typography' => array( + 'fontSizes' => array( array( - 'name' => 'Pale Pink', - 'slug' => 'pale-pink', - 'color' => '#f78da7', + 'name' => 'Small', + 'slug' => 'small', + 'size' => 12, ), array( - 'name' => 'Vivid Red', - 'slug' => 'vivid-red', - 'color' => '#cf2e2e', - ), - ), - 'custom' => false, - 'link' => true, - ), - 'border' => array( - 'color' => false, - 'radius' => false, - 'style' => false, - 'width' => false, - ), - 'typography' => array( - 'fontStyle' => false, - 'fontWeight' => false, - 'letterSpacing' => false, - 'textDecoration' => false, - 'textTransform' => false, - ), - 'blocks' => array( - 'core/group' => array( - 'border' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - ), - 'typography' => array( - 'fontStyle' => true, - 'fontWeight' => true, - 'letterSpacing' => true, - 'textDecoration' => true, - 'textTransform' => true, - ), - ), - ), - ), - 'styles' => array( - 'color' => array( - 'background' => 'purple', - ), - 'blocks' => array( - 'core/group' => array( - 'color' => array( - 'background' => 'red', - ), - 'spacing' => array( - 'padding' => array( - 'top' => '10px', - ), - ), - 'elements' => array( - 'link' => array( - 'color' => array( - 'text' => 'yellow', - ), - ), - ), - ), - ), - 'elements' => array( - 'link' => array( - 'color' => array( - 'text' => 'red', + 'name' => 'Normal', + 'slug' => 'normal', + 'size' => 16, ), ), ), @@ -270,81 +231,18 @@ public function test_migrate_v2_to_latest() { $expected = array( 'version' => WP_Theme_JSON_Gutenberg::LATEST_SCHEMA, 'settings' => array( - 'color' => array( - 'palette' => array( - array( - 'name' => 'Pale Pink', - 'slug' => 'pale-pink', - 'color' => '#f78da7', - ), - array( - 'name' => 'Vivid Red', - 'slug' => 'vivid-red', - 'color' => '#cf2e2e', - ), - ), - 'custom' => false, - 'link' => true, - ), - 'border' => array( - 'color' => false, - 'radius' => false, - 'style' => false, - 'width' => false, - ), 'typography' => array( 'defaultFontSizes' => false, - 'fontStyle' => false, - 'fontWeight' => false, - 'letterSpacing' => false, - 'textDecoration' => false, - 'textTransform' => false, - ), - 'blocks' => array( - 'core/group' => array( - 'border' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - ), - 'typography' => array( - 'fontStyle' => true, - 'fontWeight' => true, - 'letterSpacing' => true, - 'textDecoration' => true, - 'textTransform' => true, - ), - ), - ), - ), - 'styles' => array( - 'color' => array( - 'background' => 'purple', - ), - 'blocks' => array( - 'core/group' => array( - 'color' => array( - 'background' => 'red', - ), - 'spacing' => array( - 'padding' => array( - 'top' => '10px', - ), - ), - 'elements' => array( - 'link' => array( - 'color' => array( - 'text' => 'yellow', - ), - ), + 'fontSizes' => array( + array( + 'name' => 'Small', + 'slug' => 'small', + 'size' => 12, ), - ), - ), - 'elements' => array( - 'link' => array( - 'color' => array( - 'text' => 'red', + array( + 'name' => 'Normal', + 'slug' => 'normal', + 'size' => 16, ), ), ), From b971b6e41c828576f77c785d1a71cd56dc8ed7c0 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Tue, 23 Apr 2024 11:59:02 -0500 Subject: [PATCH 46/47] Fix phpcs --- phpunit/class-wp-theme-json-schema-test.php | 36 ++++++++++----------- 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/phpunit/class-wp-theme-json-schema-test.php b/phpunit/class-wp-theme-json-schema-test.php index 8e8521a39a30ac..4259b8b5de6d4f 100644 --- a/phpunit/class-wp-theme-json-schema-test.php +++ b/phpunit/class-wp-theme-json-schema-test.php @@ -38,13 +38,13 @@ public function test_migrate_v1_to_latest() { 'fontSizes' => array( array( 'name' => 'Small', - 'slug' => 'small', - 'size' => 12, + 'slug' => 'small', + 'size' => 12, ), array( 'name' => 'Normal', - 'slug' => 'normal', - 'size' => 16, + 'slug' => 'normal', + 'size' => 16, ), ), 'fontStyle' => false, @@ -133,16 +133,16 @@ public function test_migrate_v1_to_latest() { ), 'typography' => array( 'defaultFontSizes' => false, - 'fontSizes' => array( + 'fontSizes' => array( array( 'name' => 'Small', - 'slug' => 'small', - 'size' => 12, + 'slug' => 'small', + 'size' => 12, ), array( 'name' => 'Normal', - 'slug' => 'normal', - 'size' => 16, + 'slug' => 'normal', + 'size' => 16, ), ), 'fontStyle' => false, @@ -213,13 +213,13 @@ public function test_migrate_v2_to_latest() { 'fontSizes' => array( array( 'name' => 'Small', - 'slug' => 'small', - 'size' => 12, + 'slug' => 'small', + 'size' => 12, ), array( 'name' => 'Normal', - 'slug' => 'normal', - 'size' => 16, + 'slug' => 'normal', + 'size' => 16, ), ), ), @@ -233,16 +233,16 @@ public function test_migrate_v2_to_latest() { 'settings' => array( 'typography' => array( 'defaultFontSizes' => false, - 'fontSizes' => array( + 'fontSizes' => array( array( 'name' => 'Small', - 'slug' => 'small', - 'size' => 12, + 'slug' => 'small', + 'size' => 12, ), array( 'name' => 'Normal', - 'slug' => 'normal', - 'size' => 16, + 'slug' => 'normal', + 'size' => 16, ), ), ), From c0db46ca355e7da1d65326d3ffa5ecb8f655a8b8 Mon Sep 17 00:00:00 2001 From: Alex Lende Date: Thu, 25 Apr 2024 12:10:14 -0500 Subject: [PATCH 47/47] Update migration docs --- .../theme-json-reference/theme-json-migrations.md | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/docs/reference-guides/theme-json-reference/theme-json-migrations.md b/docs/reference-guides/theme-json-reference/theme-json-migrations.md index d845ba9e1fccf0..07acf41bf2eb7f 100644 --- a/docs/reference-guides/theme-json-reference/theme-json-migrations.md +++ b/docs/reference-guides/theme-json-reference/theme-json-migrations.md @@ -71,15 +71,19 @@ Upgrading to v3 adjusts preset defaults to be more consistent with one another. ### How to migrate from v1 to v2: 1. Update `version` to `3`. -2. Configure the changed defaults if you'd like. +2. Configure the changed defaults. ### Changed defaults #### `settings.typography.defaultFontSizes` -In theme.json v2, the default font sizes were always merged with the theme ones. +In theme.json v2, the default font sizes were only shown when theme sizes were not defined. A theme providing font sizes with the same slugs as the defaults would always override them. -The new `defaultFontSizes` option differs from that behavior. +The new `defaultFontSizes` option gives control over showing default font sizes and preventing those defaults from being overridden. - When set to `true` it will show the default font sizes and prevent them from being overridden by the theme. - When set to `false` it will hide the default font sizes and allow the theme to use the default slugs. + +It is `true` by default when switching to v3. This is to be consistent with how other `default*` options work such as `settings.color.defaultPalette`. + +To keep behavior similar to v2, set this value to `false`.