From d3b6a514b9c69843d90fb75c39052fe992071baf Mon Sep 17 00:00:00 2001 From: Aaron Robertshaw <60436221+aaronrobertshaw@users.noreply.github.com> Date: Wed, 1 Sep 2021 16:07:23 +1000 Subject: [PATCH 1/9] Remove custom prefix from border theme.json settings --- .../themes/create-block-theme.md | 34 ++++++++--------- docs/how-to-guides/themes/theme-json.md | 16 ++++---- lib/class-wp-theme-json-gutenberg.php | 8 ++-- lib/class-wp-theme-json-schema-v0.php | 37 +++++++++++++++++++ lib/theme.json | 18 ++++----- packages/block-editor/src/hooks/border.js | 19 ++++------ .../components/global-styles/border-panel.js | 8 ++-- .../class-wp-theme-json-schema-v0-test.php | 8 +++- 8 files changed, 94 insertions(+), 54 deletions(-) diff --git a/docs/how-to-guides/themes/create-block-theme.md b/docs/how-to-guides/themes/create-block-theme.md index 45df340c1e19df..12e724ea399e9a 100644 --- a/docs/how-to-guides/themes/create-block-theme.md +++ b/docs/how-to-guides/themes/create-block-theme.md @@ -85,7 +85,7 @@ Optionally, create a `functions.php` file. In this file, you can enqueue `style.css`, include additional files, enable an editor stylesheet and add theme support.
-You will add most of the theme support in the `theme.json` file. The title tag is already enabled for all block themes, and it is no longer necessarry to enqueue the comment reply script because it is included with the comments block. +You will add most of the theme support in the `theme.json` file. The title tag is already enabled for all block themes, and it is no longer necessary to enqueue the comment reply script because it is included with the comments block.
```php @@ -439,10 +439,10 @@ To enable border styles, add a `border` object under `settings` with the followi "version": 1, "settings": { "border": { - "customColor": true, - "customRadius": true, - "customStyle": true, - "customWidth": true + "color": true, + "radius": true, + "style": true, + "width": true } } } @@ -455,10 +455,10 @@ To enable link colors, add a `color` setting and set `link` to true: "version": 1, "settings": { "border": { - "customColor": true, - "customRadius": true, - "customStyle": true, - "customWidth": true + "color": true, + "radius": true, + "style": true, + "width": true }, "color": { "link": true, @@ -474,10 +474,10 @@ To enable padding, margin and custom spacing units, include a setting for spacin "version": 1, "settings": { "border": { - "customColor": true, - "customRadius": true, - "customStyle": true, - "customWidth": true + "color": true, + "radius": true, + "style": true, + "width": true }, "color": { "link": true @@ -500,10 +500,10 @@ If you want to disable gradients, which are enabled by default, set `gradient` t "version": 1, "settings": { "border": { - "customColor": true, - "customRadius": true, - "customStyle": true, - "customWidth": true + "color": true, + "radius": true, + "style": true, + "width": true }, "color": { "link": true, diff --git a/docs/how-to-guides/themes/theme-json.md b/docs/how-to-guides/themes/theme-json.md index 0eb28f9a29e0e4..8e31cb73a3e4ac 100644 --- a/docs/how-to-guides/themes/theme-json.md +++ b/docs/how-to-guides/themes/theme-json.md @@ -216,10 +216,10 @@ The settings section has the following structure: "version": 1, "settings": { "border": { - "customColor": false, - "customRadius": false, - "customStyle": false, - "customWidth": false + "color": false, + "radius": false, + "style": false, + "width": false }, "color": { "background": true, @@ -528,7 +528,7 @@ Note that the name of the variable is created by adding `--` in between each nes "blocks": { "core/button": { "border": { - "customRadius": false + "radius": false } } } @@ -779,7 +779,7 @@ body { Styles found within a block will be enqueued using the block selector. -By default, the block selector is generated based on its name such as `.wp-block-`. For example, `.wp-block-group` for the `core/group` block. There are some blocks that want to opt-out from this default behavior. They can do so by explicitely telling the system which selector to use for them via the `__experimentalSelector` key within the `supports` section of its `block.json` file. +By default, the block selector is generated based on its name such as `.wp-block-`. For example, `.wp-block-group` for the `core/group` block. There are some blocks that want to opt-out from this default behavior. They can do so by explicitly telling the system which selector to use for them via the `__experimentalSelector` key within the `supports` section of its `block.json` file. {% codetabs %} {% Input %} @@ -995,8 +995,8 @@ One thing you may have noticed is the naming schema used for the CSS Custom Prop The `--` as a separator has two functions: -- Readibility, for human understanding. It can be thought as similar to the BEM naming schema, it separates "categories". -- Parseability, for machine understanding. Using a defined structure allows machines to understand the meaning of the property `--wp--preset--color--black`: it's a value bounded to the color preset whose slug is "black", which then gives us room to do more things with them. +- Readability, for human understanding. It can be thought as similar to the BEM naming schema, it separates "categories". +- Parsability, for machine understanding. Using a defined structure allows machines to understand the meaning of the property `--wp--preset--color--black`: it's a value bounded to the color preset whose slug is "black", which then gives us room to do more things with them. ### Why using `--` as a separator? diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index f84696e019d23a..0efbd82c89ea44 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -82,10 +82,10 @@ class WP_Theme_JSON_Gutenberg { const VALID_SETTINGS = array( 'border' => array( - 'customColor' => null, - 'customRadius' => null, - 'customStyle' => null, - 'customWidth' => null, + 'color' => null, + 'radius' => null, + 'style' => null, + 'width' => null, ), 'color' => array( 'background' => null, diff --git a/lib/class-wp-theme-json-schema-v0.php b/lib/class-wp-theme-json-schema-v0.php index 30a0578178c7f5..b95c769cf6c0de 100644 --- a/lib/class-wp-theme-json-schema-v0.php +++ b/lib/class-wp-theme-json-schema-v0.php @@ -184,6 +184,13 @@ private static function process_settings( $settings ) { array( 'custom' ), ); + $renamed_paths = array( + 'border.customColor' => 'border.color', + 'border.customRadius' => 'border.radius', + 'border.customStyle' => 'border.style', + 'border.customWidth' => 'border.width', + ); + // 'defaults' settings become top-level. if ( isset( $settings[ self::ALL_BLOCKS_NAME ] ) ) { $new = $settings[ self::ALL_BLOCKS_NAME ]; @@ -219,6 +226,18 @@ private static function process_settings( $settings ) { return $new; } + // Process any renamed/moved paths within settings. + foreach ( $renamed_paths as $original => $renamed ) { + $original_path = explode( '.', $original ); + $renamed_path = explode( '.', $renamed ); + $current_value = _wp_array_get( $new, $original_path, null ); + + if ( null !== $current_value ) { + gutenberg_experimental_set( $new, $renamed_path, $current_value ); + self::unset_setting_by_path( $new, $original_path ); + } + } + /* * At this point, it only contains block's data. * However, some block data we need to consolidate @@ -254,6 +273,24 @@ private static function process_settings( $settings ) { return $new; } + /** + * Removes a property from within the provided settings by its path. + * + * @param array $settings Reference to the current settings array. + * @param array $path Path to the property to be removed. + * + * @return void + */ + private static function unset_setting_by_path( &$settings, $path ) { + $tmp_settings = &$settings; // phpcs:ignore VariableAnalysis.CodeAnalysis.VariableAnalysis.UnusedVariable + $last_key = array_pop( $path ); + foreach ( $path as $key ) { + $tmp_settings = &$tmp_settings[ $key ]; + } + + unset( $tmp_settings[ $last_key ] ); + } + /** * Processes the styles subtree. * diff --git a/lib/theme.json b/lib/theme.json index f32734b6efe0f4..6bb204f54a3273 100644 --- a/lib/theme.json +++ b/lib/theme.json @@ -219,23 +219,23 @@ "units": [ "px", "em", "rem", "vh", "vw", "%" ] }, "border": { - "customColor": false, - "customRadius": false, - "customStyle": false, - "customWidth": false + "color": false, + "radius": false, + "style": false, + "width": false }, "blocks": { "core/button": { "border": { - "customRadius": true + "radius": true } }, "core/pullquote": { "border": { - "customColor": true, - "customRadius": true, - "customStyle": true, - "customWidth": true + "color": true, + "radius": true, + "style": true, + "width": true } } } diff --git a/packages/block-editor/src/hooks/border.js b/packages/block-editor/src/hooks/border.js index 64872c5c470f01..761c04200a5319 100644 --- a/packages/block-editor/src/hooks/border.js +++ b/packages/block-editor/src/hooks/border.js @@ -23,20 +23,17 @@ export function BorderPanel( props ) { const isSupported = hasBorderSupport( props.name ); const isColorSupported = - useSetting( 'border.customColor' ) && - hasBorderSupport( props.name, 'color' ); + useSetting( 'border.color' ) && hasBorderSupport( props.name, 'color' ); const isRadiusSupported = - useSetting( 'border.customRadius' ) && + useSetting( 'border.radius' ) && hasBorderSupport( props.name, 'radius' ); const isStyleSupported = - useSetting( 'border.customStyle' ) && - hasBorderSupport( props.name, 'style' ); + useSetting( 'border.style' ) && hasBorderSupport( props.name, 'style' ); const isWidthSupported = - useSetting( 'border.customWidth' ) && - hasBorderSupport( props.name, 'width' ); + useSetting( 'border.width' ) && hasBorderSupport( props.name, 'width' ); if ( isDisabled || ! isSupported ) { return null; @@ -113,10 +110,10 @@ export function shouldSkipSerialization( blockType ) { */ const useIsBorderDisabled = () => { const configs = [ - ! useSetting( 'border.customColor' ), - ! useSetting( 'border.customRadius' ), - ! useSetting( 'border.customStyle' ), - ! useSetting( 'border.customWidth' ), + ! useSetting( 'border.color' ), + ! useSetting( 'border.radius' ), + ! useSetting( 'border.style' ), + ! useSetting( 'border.width' ), ]; return configs.every( Boolean ); diff --git a/packages/edit-site/src/components/global-styles/border-panel.js b/packages/edit-site/src/components/global-styles/border-panel.js index 2dd6675debe239..14ce8e798cdc74 100644 --- a/packages/edit-site/src/components/global-styles/border-panel.js +++ b/packages/edit-site/src/components/global-styles/border-panel.js @@ -38,7 +38,7 @@ export function useHasBorderPanel( name ) { function useHasBorderColorControl( name ) { const supports = getSupportedGlobalStylesPanels( name ); return ( - useSetting( 'border.customColor', name )[ 0 ] && + useSetting( 'border.color', name )[ 0 ] && supports.includes( 'borderColor' ) ); } @@ -46,7 +46,7 @@ function useHasBorderColorControl( name ) { function useHasBorderRadiusControl( name ) { const supports = getSupportedGlobalStylesPanels( name ); return ( - useSetting( 'border.customRadius', name )[ 0 ] && + useSetting( 'border.radius', name )[ 0 ] && supports.includes( 'borderRadius' ) ); } @@ -54,7 +54,7 @@ function useHasBorderRadiusControl( name ) { function useHasBorderStyleControl( name ) { const supports = getSupportedGlobalStylesPanels( name ); return ( - useSetting( 'border.customStyle', name )[ 0 ] && + useSetting( 'border.style', name )[ 0 ] && supports.includes( 'borderStyle' ) ); } @@ -62,7 +62,7 @@ function useHasBorderStyleControl( name ) { function useHasBorderWidthControl( name ) { const supports = getSupportedGlobalStylesPanels( name ); return ( - useSetting( 'border.customWidth', name )[ 0 ] && + useSetting( 'border.width', name )[ 0 ] && supports.includes( 'borderWidth' ) ); } diff --git a/phpunit/class-wp-theme-json-schema-v0-test.php b/phpunit/class-wp-theme-json-schema-v0-test.php index 02e35eaf4fce33..cb7a78e129981c 100644 --- a/phpunit/class-wp-theme-json-schema-v0-test.php +++ b/phpunit/class-wp-theme-json-schema-v0-test.php @@ -56,7 +56,10 @@ function test_parse() { 'link' => true, ), 'border' => array( + 'customColor' => false, 'customRadius' => false, + 'customStyle' => false, + 'customWidth' => false, ), ), 'core/paragraph' => array( @@ -108,7 +111,10 @@ function test_parse() { 'link' => true, ), 'border' => array( - 'customRadius' => false, + 'color' => false, + 'radius' => false, + 'style' => false, + 'width' => false, ), 'blocks' => array( 'core/paragraph' => array( From edb6e5755538a8e96070e980c4e4b816e2f7b88b Mon Sep 17 00:00:00 2001 From: Aaron Robertshaw <60436221+aaronrobertshaw@users.noreply.github.com> Date: Wed, 1 Sep 2021 17:37:11 +1000 Subject: [PATCH 2/9] Remove custom prefix from typography theme.json settings The `customTextDecorations` and `customTextTransforms` properties needed to be mapped to the singular versions `textDecoration` and `textTransform` respectively in order to avoid conflicts with i18n of presets for them. --- docs/how-to-guides/themes/theme-json.md | 8 ++++---- lib/class-wp-theme-json-gutenberg.php | 20 +++++++++---------- lib/class-wp-theme-json-schema-v0.php | 12 +++++++---- lib/theme.json | 10 +++++----- .../block-editor/src/hooks/font-appearance.js | 4 ++-- .../block-editor/src/hooks/letter-spacing.js | 2 +- .../block-editor/src/hooks/text-decoration.js | 2 +- .../block-editor/src/hooks/text-transform.js | 2 +- .../global-styles/typography-panel.js | 10 +++++----- .../class-wp-theme-json-schema-v0-test.php | 20 +++++++++++++++---- 10 files changed, 53 insertions(+), 37 deletions(-) diff --git a/docs/how-to-guides/themes/theme-json.md b/docs/how-to-guides/themes/theme-json.md index 8e31cb73a3e4ac..febd3b09d4ab9d 100644 --- a/docs/how-to-guides/themes/theme-json.md +++ b/docs/how-to-guides/themes/theme-json.md @@ -244,12 +244,12 @@ The settings section has the following structure: }, "typography": { "customFontSize": true, - "customFontStyle": true, - "customFontWeight": true, "customLineHeight": false, - "customTextDecorations": true, - "customTextTransforms": true, "dropCap": true, + "fontStyle": true, + "fontWeight": true, + "textDecoration": true, + "textTransform": true, "fontFamilies": [], "fontSizes": [] }, diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index 0efbd82c89ea44..e8ef8cbac095c7 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -110,16 +110,16 @@ class WP_Theme_JSON_Gutenberg { 'units' => null, ), 'typography' => array( - 'customFontSize' => null, - 'customFontStyle' => null, - 'customFontWeight' => null, - 'customLetterSpacing' => null, - 'customLineHeight' => null, - 'customTextDecorations' => null, - 'customTextTransforms' => null, - 'dropCap' => null, - 'fontFamilies' => null, - 'fontSizes' => null, + 'customFontSize' => null, + 'customLineHeight' => null, + 'dropCap' => null, + 'fontFamilies' => null, + 'fontSizes' => null, + 'fontStyle' => null, + 'fontWeight' => null, + 'letterSpacing' => null, + 'textDecoration' => null, + 'textTransform' => null, ), ); diff --git a/lib/class-wp-theme-json-schema-v0.php b/lib/class-wp-theme-json-schema-v0.php index b95c769cf6c0de..81ba3e9a5cb333 100644 --- a/lib/class-wp-theme-json-schema-v0.php +++ b/lib/class-wp-theme-json-schema-v0.php @@ -185,10 +185,14 @@ private static function process_settings( $settings ) { ); $renamed_paths = array( - 'border.customColor' => 'border.color', - 'border.customRadius' => 'border.radius', - 'border.customStyle' => 'border.style', - 'border.customWidth' => 'border.width', + 'border.customColor' => 'border.color', + 'border.customRadius' => 'border.radius', + 'border.customStyle' => 'border.style', + 'border.customWidth' => 'border.width', + 'typography.customFontStyle' => 'typography.fontStyle', + 'typography.customFontWeight' => 'typography.fontWeight', + 'typography.customTextDecorations' => 'typography.textDecoration', + 'typography.customTextTransforms' => 'typography.textTransform', ); // 'defaults' settings become top-level. diff --git a/lib/theme.json b/lib/theme.json index 6bb204f54a3273..085848be6cf282 100644 --- a/lib/theme.json +++ b/lib/theme.json @@ -179,11 +179,11 @@ "dropCap": true, "customFontSize": true, "customLineHeight": false, - "customFontStyle": true, - "customFontWeight": true, - "customTextTransforms": true, - "customTextDecorations": true, - "customLetterSpacing": true, + "fontStyle": true, + "fontWeight": true, + "textTransform": true, + "textDecoration": true, + "letterSpacing": true, "fontSizes": [ { "name": "Small", diff --git a/packages/block-editor/src/hooks/font-appearance.js b/packages/block-editor/src/hooks/font-appearance.js index 44c26d432bddfd..b398ef58dc28c4 100644 --- a/packages/block-editor/src/hooks/font-appearance.js +++ b/packages/block-editor/src/hooks/font-appearance.js @@ -73,7 +73,7 @@ export function FontAppearanceEdit( props ) { */ export function useIsFontStyleDisabled( { name: blockName } = {} ) { const styleSupport = hasBlockSupport( blockName, FONT_STYLE_SUPPORT_KEY ); - const hasFontStyles = useSetting( 'typography.customFontStyle' ); + const hasFontStyles = useSetting( 'typography.fontStyle' ); return ! styleSupport || ! hasFontStyles; } @@ -89,7 +89,7 @@ export function useIsFontStyleDisabled( { name: blockName } = {} ) { */ export function useIsFontWeightDisabled( { name: blockName } = {} ) { const weightSupport = hasBlockSupport( blockName, FONT_WEIGHT_SUPPORT_KEY ); - const hasFontWeights = useSetting( 'typography.customFontWeight' ); + const hasFontWeights = useSetting( 'typography.fontWeight' ); return ! weightSupport || ! hasFontWeights; } diff --git a/packages/block-editor/src/hooks/letter-spacing.js b/packages/block-editor/src/hooks/letter-spacing.js index 01446ef4024324..51dbe207f52ccb 100644 --- a/packages/block-editor/src/hooks/letter-spacing.js +++ b/packages/block-editor/src/hooks/letter-spacing.js @@ -60,7 +60,7 @@ export function useIsLetterSpacingDisabled( { name: blockName } = {} ) { blockName, LETTER_SPACING_SUPPORT_KEY ); - const hasLetterSpacing = useSetting( 'typography.customLetterSpacing' ); + const hasLetterSpacing = useSetting( 'typography.letterSpacing' ); return notSupported || ! hasLetterSpacing; } diff --git a/packages/block-editor/src/hooks/text-decoration.js b/packages/block-editor/src/hooks/text-decoration.js index 942f0924eea555..65f0aadf77d1e1 100644 --- a/packages/block-editor/src/hooks/text-decoration.js +++ b/packages/block-editor/src/hooks/text-decoration.js @@ -62,7 +62,7 @@ export function useIsTextDecorationDisabled( { name: blockName } = {} ) { blockName, TEXT_DECORATION_SUPPORT_KEY ); - const hasTextDecoration = useSetting( 'typography.customTextDecorations' ); + const hasTextDecoration = useSetting( 'typography.textDecoration' ); return notSupported || ! hasTextDecoration; } diff --git a/packages/block-editor/src/hooks/text-transform.js b/packages/block-editor/src/hooks/text-transform.js index fabbebc1c00020..b2710b5f654b59 100644 --- a/packages/block-editor/src/hooks/text-transform.js +++ b/packages/block-editor/src/hooks/text-transform.js @@ -62,7 +62,7 @@ export function useIsTextTransformDisabled( { name: blockName } = {} ) { blockName, TEXT_TRANSFORM_SUPPORT_KEY ); - const hasTextTransforms = useSetting( 'typography.customTextTransforms' ); + const hasTextTransforms = useSetting( 'typography.textTransform' ); return notSupported || ! hasTextTransforms; } diff --git a/packages/edit-site/src/components/global-styles/typography-panel.js b/packages/edit-site/src/components/global-styles/typography-panel.js index 723d2fee1c2298..9480748a902b1e 100644 --- a/packages/edit-site/src/components/global-styles/typography-panel.js +++ b/packages/edit-site/src/components/global-styles/typography-panel.js @@ -38,10 +38,10 @@ function useHasLineHeightControl( name ) { function useHasAppearanceControl( name ) { const supports = getSupportedGlobalStylesPanels( name ); const hasFontStyles = - useSetting( 'typography.customFontStyle', name )[ 0 ] && + useSetting( 'typography.fontStyle', name )[ 0 ] && supports.includes( 'fontStyle' ); const hasFontWeights = - useSetting( 'typography.customFontWeight', name )[ 0 ] && + useSetting( 'typography.fontWeight', name )[ 0 ] && supports.includes( 'fontWeight' ); return hasFontStyles || hasFontWeights; } @@ -49,7 +49,7 @@ function useHasAppearanceControl( name ) { function useHasLetterSpacingControl( name ) { const supports = getSupportedGlobalStylesPanels( name ); return ( - useSetting( 'typography.customLetterSpacing', name )[ 0 ] && + useSetting( 'typography.letterSpacing', name )[ 0 ] && supports.includes( 'letterSpacing' ) ); } @@ -63,10 +63,10 @@ export default function TypographyPanel( { name } ) { )[ 0 ]; const [ fontFamilies ] = useSetting( 'typography.fontFamilies', name ); const hasFontStyles = - useSetting( 'typography.customFontStyle', name )[ 0 ] && + useSetting( 'typography.fontStyle', name )[ 0 ] && supports.includes( 'fontStyle' ); const hasFontWeights = - useSetting( 'typography.customFontWeight', name )[ 0 ] && + useSetting( 'typography.fontWeight', name )[ 0 ] && supports.includes( 'fontWeight' ); const hasLineHeightEnabled = useHasLineHeightControl( name ); const hasAppearanceControl = useHasAppearanceControl( name ); diff --git a/phpunit/class-wp-theme-json-schema-v0-test.php b/phpunit/class-wp-theme-json-schema-v0-test.php index cb7a78e129981c..e47bef52b14ed0 100644 --- a/phpunit/class-wp-theme-json-schema-v0-test.php +++ b/phpunit/class-wp-theme-json-schema-v0-test.php @@ -12,7 +12,7 @@ function test_parse() { $theme_json_v0 = array( 'settings' => array( 'defaults' => array( - 'color' => array( + 'color' => array( 'palette' => array( array( 'name' => 'Black', @@ -38,6 +38,12 @@ function test_parse() { 'custom' => false, 'link' => false, ), + 'typography' => array( + 'customFontStyle' => false, + 'customFontWeight' => false, + 'customTextDecorations' => false, + 'customTextTransforms' => false, + ), ), 'root' => array( 'color' => array( @@ -94,7 +100,7 @@ function test_parse() { $expected = array( 'version' => 1, 'settings' => array( - 'color' => array( + 'color' => array( 'palette' => array( array( 'name' => 'Pale Pink', @@ -110,13 +116,19 @@ function test_parse() { 'custom' => false, 'link' => true, ), - 'border' => array( + 'border' => array( 'color' => false, 'radius' => false, 'style' => false, 'width' => false, ), - 'blocks' => array( + 'typography' => array( + 'fontStyle' => false, + 'fontWeight' => false, + 'textDecoration' => false, + 'textTransform' => false, + ), + 'blocks' => array( 'core/paragraph' => array( 'typography' => array( 'dropCap' => false, From f66b770c720ab8c4b1af571343ac7b3240cf2996 Mon Sep 17 00:00:00 2001 From: Aaron Robertshaw <60436221+aaronrobertshaw@users.noreply.github.com> Date: Tue, 26 Oct 2021 15:04:43 +1000 Subject: [PATCH 3/9] Add backwards compatibility bridges for prefixed properties --- lib/class-wp-theme-json-gutenberg.php | 12 + lib/class-wp-theme-json-schema-v1.php | 206 ++++++++++++++++++ lib/load.php | 1 + .../src/components/use-setting/index.js | 64 +++++- .../class-wp-theme-json-schema-v1-test.php | 178 +++++++++++++++ 5 files changed, 453 insertions(+), 8 deletions(-) create mode 100644 lib/class-wp-theme-json-schema-v1.php create mode 100644 phpunit/class-wp-theme-json-schema-v1-test.php diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index e8ef8cbac095c7..8fda80457d9f47 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -292,6 +292,12 @@ public function __construct( $theme_json = array(), $origin = 'theme' ) { $theme_json = WP_Theme_JSON_Schema_V0::parse( $theme_json ); } + // Provide backwards compatibility for settings that did not land in 5.8 + // and have had their `custom` prefixed removed since. + if ( 1 === $theme_json['version'] ) { + $theme_json = WP_Theme_JSON_Schema_V1::parse( $theme_json ); + } + $valid_block_names = array_keys( self::get_blocks_metadata() ); $valid_element_names = array_keys( self::ELEMENTS ); $this->theme_json = self::sanitize( $theme_json, $valid_block_names, $valid_element_names ); @@ -1434,6 +1440,12 @@ public static function remove_insecure_properties( $theme_json ) { $theme_json = WP_Theme_JSON_Schema_V0::parse( $theme_json ); } + // Provide backwards compatibility for settings that did not land in 5.8 + // and have had their `custom` prefixed removed since. + if ( 1 === $theme_json['version'] ) { + $theme_json = WP_Theme_JSON_Schema_V1::parse( $theme_json ); + } + $valid_block_names = array_keys( self::get_blocks_metadata() ); $valid_element_names = array_keys( self::ELEMENTS ); $theme_json = self::sanitize( $theme_json, $valid_block_names, $valid_element_names ); diff --git a/lib/class-wp-theme-json-schema-v1.php b/lib/class-wp-theme-json-schema-v1.php new file mode 100644 index 00000000000000..8de8d41fe234ef --- /dev/null +++ b/lib/class-wp-theme-json-schema-v1.php @@ -0,0 +1,206 @@ + null, + 'templateParts' => null, + 'styles' => array( + 'border' => array( + 'radius' => null, + 'color' => null, + 'style' => null, + 'width' => null, + ), + 'color' => array( + 'background' => null, + 'gradient' => null, + 'link' => null, + 'text' => null, + ), + 'spacing' => array( + 'padding' => array( + 'top' => null, + 'right' => null, + 'bottom' => null, + 'left' => null, + ), + ), + 'typography' => array( + 'fontFamily' => null, + 'fontSize' => null, + 'fontStyle' => null, + 'fontWeight' => null, + 'lineHeight' => null, + 'textDecoration' => null, + 'textTransform' => null, + ), + ), + 'settings' => array( + 'border' => array( + 'radius' => null, + 'color' => null, + 'style' => null, + 'width' => null, + ), + 'color' => array( + 'custom' => null, + 'customGradient' => null, + 'gradients' => null, + 'link' => null, + 'palette' => null, + ), + 'spacing' => array( + 'customPadding' => null, + 'units' => null, + ), + 'typography' => array( + 'customFontSize' => null, + 'customLineHeight' => null, + 'dropCap' => null, + 'fontFamilies' => null, + 'fontSizes' => null, + 'fontStyle' => null, + 'fontWeight' => null, + 'textDecorations' => null, + 'textTransforms' => null, + ), + 'custom' => null, + 'layout' => null, + ), + ); + + /** + * Maps old properties to their new location within the schema's settings. + * This will be applied at both the defaults and individual block levels. + */ + const RENAMED_PATHS = array( + 'border.customColor' => 'border.color', + 'border.customRadius' => 'border.radius', + 'border.customStyle' => 'border.style', + 'border.customWidth' => 'border.width', + 'typography.customFontStyle' => 'typography.fontStyle', + 'typography.customFontWeight' => 'typography.fontWeight', + 'typography.customTextDecorations' => 'typography.textDecoration', + 'typography.customTextTransforms' => 'typography.textTransform', + ); + + /** + * Converts a v0 schema into the latest. + * + * @param array $old Data in v0 schema. + * + * @return array Data in the latest schema. + */ + public static function parse( $old ) { + // Copy everything. + $new = $old; + + // Overwrite the things that change. + if ( isset( $old['settings'] ) ) { + $new['settings'] = self::process_settings( $old['settings'] ); + } + + $new['version'] = WP_Theme_JSON_Gutenberg::LATEST_SCHEMA; + + return $new; + } + + /** + * Processes the settings subtree. + * + * @param array $settings Array to process. + * + * @return array The settings in the new format. + */ + private static function process_settings( $settings ) { + $new_settings = $settings; + + // Process any renamed/moved paths within default settings. + self::rename_settings( $new_settings ); + + // Process individual block settings. + if ( is_array( $new_settings['blocks'] ) ) { + foreach ( $new_settings['blocks'] as &$block_settings ) { + self::rename_settings( $block_settings ); + } + } + + return $new_settings; + } + + /** + * Processes a settings array, renaming or moving properties according to + * `self::RENAMED_PATHS`. + * + * @param array $settings Reference to settings either defaults or an individual block's. + * @return void + */ + private static function rename_settings( &$settings ) { + foreach ( self::RENAMED_PATHS as $original => $renamed ) { + $original_path = explode( '.', $original ); + $renamed_path = explode( '.', $renamed ); + $current_value = _wp_array_get( $settings, $original_path, null ); + + if ( null !== $current_value ) { + gutenberg_experimental_set( $settings, $renamed_path, $current_value ); + self::unset_setting_by_path( $settings, $original_path ); + } + } + } + + /** + * Removes a property from within the provided settings by its path. + * + * @param array $settings Reference to the current settings array. + * @param array $path Path to the property to be removed. + * + * @return void + */ + private static function unset_setting_by_path( &$settings, $path ) { + $tmp_settings = &$settings; // phpcs:ignore VariableAnalysis.CodeAnalysis.VariableAnalysis.UnusedVariable + $last_key = array_pop( $path ); + foreach ( $path as $key ) { + $tmp_settings = &$tmp_settings[ $key ]; + } + + unset( $tmp_settings[ $last_key ] ); + } +} diff --git a/lib/load.php b/lib/load.php index 55ce6a575b1aac..59c7da519f56b3 100644 --- a/lib/load.php +++ b/lib/load.php @@ -96,6 +96,7 @@ function gutenberg_is_experiment_enabled( $name ) { // as well as global styles. require __DIR__ . '/interface-wp-theme-json-schema.php'; require __DIR__ . '/class-wp-theme-json-schema-v0.php'; +require __DIR__ . '/class-wp-theme-json-schema-v1.php'; require __DIR__ . '/class-wp-theme-json-gutenberg.php'; require __DIR__ . '/class-wp-theme-json-resolver-gutenberg.php'; diff --git a/packages/block-editor/src/components/use-setting/index.js b/packages/block-editor/src/components/use-setting/index.js index 74f03a3545cdd6..e6090bf15d82c2 100644 --- a/packages/block-editor/src/components/use-setting/index.js +++ b/packages/block-editor/src/components/use-setting/index.js @@ -50,14 +50,45 @@ const deprecatedFlags = { 'spacing.customPadding': ( settings ) => settings.enableCustomSpacing, }; +// The following provide continued support for `custom` prefixed properties. +// This will be removed once third party devs have had sufficient time to update +// themes, plugins, etc. This is also separate to the deprecated flags as there +// will be some overlap e.g. `typography.customLineHeight`. +// See: https://github.com/WordPress/gutenberg/pull/34485 +const prefixedFlags = { + 'border.customColor': 'border.color', + 'border.customRadius': 'border.radius', + 'border.customStyle': 'border.style', + 'border.customWidth': 'border.width', + 'typography.customFontStyle': 'typography.fontStyle', + 'typography.customFontWeight': 'typography.fontWeight', + 'typography.customLetterSpacing': 'typography.letterSpacing', + 'typography.customTextDecorations': 'typography.textDecoration', + 'typography.customTextTransforms': 'typography.textTransform', +}; + +/** + * Retrieve editor setting value. The block specific setting is preferred + * otherwise falls back to the generic setting path. + * + * @param {Object} settings Editor settings. + * @param {string} blockName Block to retrieve setting for. + * @param {string} path Path to desired value in settings. + * @return {any} The value for defined setting. + */ +const getSetting = ( settings, blockName, path ) => { + const blockPath = `__experimentalFeatures.blocks.${ blockName }.${ path }`; + const defaultsPath = `__experimentalFeatures.${ path }`; + + return get( settings, blockPath ) ?? get( settings, defaultsPath ); +}; + /** * Hook that retrieves the editor setting. * It works with nested objects using by finding the value at path. * * @param {string} path The path to the setting. - * * @return {any} Returns the value defined for the setting. - * * @example * ```js * const isEnabled = useSetting( 'typography.dropCap' ); @@ -72,10 +103,12 @@ export default function useSetting( path ) { // 1 - Use __experimental features, if available. // We cascade to the all value if the block one is not available. - const defaultsPath = `__experimentalFeatures.${ path }`; - const blockPath = `__experimentalFeatures.blocks.${ blockName }.${ path }`; - const experimentalFeaturesResult = - get( settings, blockPath ) ?? get( settings, defaultsPath ); + const experimentalFeaturesResult = getSetting( + settings, + blockName, + path + ); + if ( experimentalFeaturesResult !== undefined ) { if ( PATHS_WITH_MERGE[ path ] ) { return ( @@ -87,7 +120,22 @@ export default function useSetting( path ) { return experimentalFeaturesResult; } - // 2 - Use deprecated settings, otherwise. + // 2 - Handle `custom` prefixed settings. + const pathWithoutPrefix = prefixedFlags[ path ]; + + if ( pathWithoutPrefix ) { + const settingsValue = getSetting( + settings, + blockName, + pathWithoutPrefix + ); + + if ( settingsValue !== undefined ) { + return settingsValue; + } + } + + // 3 - Use deprecated settings, otherwise. const deprecatedSettingsValue = deprecatedFlags[ path ] ? deprecatedFlags[ path ]( settings ) : undefined; @@ -95,7 +143,7 @@ export default function useSetting( path ) { return deprecatedSettingsValue; } - // 3 - Fall back for typography.dropCap: + // 4 - Fall back for typography.dropCap: // This is only necessary to support typography.dropCap. // when __experimentalFeatures are not present (core without plugin). // To remove when __experimentalFeatures are ported to core. diff --git a/phpunit/class-wp-theme-json-schema-v1-test.php b/phpunit/class-wp-theme-json-schema-v1-test.php new file mode 100644 index 00000000000000..5af251fb92dabb --- /dev/null +++ b/phpunit/class-wp-theme-json-schema-v1-test.php @@ -0,0 +1,178 @@ + 1, + '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( + 'customColor' => false, + 'customRadius' => false, + 'customStyle' => false, + 'customWidth' => false, + ), + 'typography' => array( + 'customFontStyle' => false, + 'customFontWeight' => false, + 'customTextDecorations' => false, + 'customTextTransforms' => false, + ), + 'blocks' => array( + 'core/group' => array( + 'border' => array( + 'customColor' => true, + 'customRadius' => true, + 'customStyle' => true, + 'customWidth' => true, + ), + 'typography' => array( + 'customFontStyle' => true, + 'customFontWeight' => true, + 'customTextDecorations' => true, + 'customTextTransforms' => 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', + ), + ), + ), + ), + ); + + $actual = WP_Theme_JSON_Schema_V1::parse( $theme_json_v1 ); + + $expected = array( + 'version' => 1, + '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( + 'fontStyle' => false, + 'fontWeight' => 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, + '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 2e7149430dee7d6e6c84f4270a41b810ae95e82a Mon Sep 17 00:00:00 2001 From: Aaron Robertshaw <60436221+aaronrobertshaw@users.noreply.github.com> Date: Tue, 26 Oct 2021 19:13:58 +1000 Subject: [PATCH 4/9] Reinstate customRadius flag The customRadius flag did actually land in 5.8 and must be maintained until we switch to a full v2 of the theme.json schema. --- docs/how-to-guides/themes/create-block-theme.md | 8 ++++---- docs/how-to-guides/themes/theme-json.md | 4 ++-- lib/class-wp-theme-json-gutenberg.php | 8 ++++---- lib/class-wp-theme-json-schema-v0.php | 1 - lib/class-wp-theme-json-schema-v1.php | 1 - lib/theme.json | 6 +++--- .../src/components/use-setting/index.js | 1 - packages/block-editor/src/hooks/border.js | 4 ++-- .../src/components/global-styles/border-panel.js | 2 +- phpunit/class-wp-theme-json-schema-v0-test.php | 8 ++++---- phpunit/class-wp-theme-json-schema-v1-test.php | 16 ++++++++-------- 11 files changed, 28 insertions(+), 31 deletions(-) diff --git a/docs/how-to-guides/themes/create-block-theme.md b/docs/how-to-guides/themes/create-block-theme.md index 12e724ea399e9a..104c52fa9bce25 100644 --- a/docs/how-to-guides/themes/create-block-theme.md +++ b/docs/how-to-guides/themes/create-block-theme.md @@ -440,7 +440,7 @@ To enable border styles, add a `border` object under `settings` with the followi "settings": { "border": { "color": true, - "radius": true, + "customRadius": true, "style": true, "width": true } @@ -456,7 +456,7 @@ To enable link colors, add a `color` setting and set `link` to true: "settings": { "border": { "color": true, - "radius": true, + "customRadius": true, "style": true, "width": true }, @@ -475,7 +475,7 @@ To enable padding, margin and custom spacing units, include a setting for spacin "settings": { "border": { "color": true, - "radius": true, + "customRadius": true, "style": true, "width": true }, @@ -501,7 +501,7 @@ If you want to disable gradients, which are enabled by default, set `gradient` t "settings": { "border": { "color": true, - "radius": true, + "customRadius": true, "style": true, "width": true }, diff --git a/docs/how-to-guides/themes/theme-json.md b/docs/how-to-guides/themes/theme-json.md index febd3b09d4ab9d..0fe56af3d3c9bc 100644 --- a/docs/how-to-guides/themes/theme-json.md +++ b/docs/how-to-guides/themes/theme-json.md @@ -217,7 +217,7 @@ The settings section has the following structure: "settings": { "border": { "color": false, - "radius": false, + "customRadius": false, "style": false, "width": false }, @@ -528,7 +528,7 @@ Note that the name of the variable is created by adding `--` in between each nes "blocks": { "core/button": { "border": { - "radius": false + "customRadius": false } } } diff --git a/lib/class-wp-theme-json-gutenberg.php b/lib/class-wp-theme-json-gutenberg.php index 8fda80457d9f47..4ae644e25b15bd 100644 --- a/lib/class-wp-theme-json-gutenberg.php +++ b/lib/class-wp-theme-json-gutenberg.php @@ -82,10 +82,10 @@ class WP_Theme_JSON_Gutenberg { const VALID_SETTINGS = array( 'border' => array( - 'color' => null, - 'radius' => null, - 'style' => null, - 'width' => null, + 'color' => null, + 'customRadius' => null, + 'style' => null, + 'width' => null, ), 'color' => array( 'background' => null, diff --git a/lib/class-wp-theme-json-schema-v0.php b/lib/class-wp-theme-json-schema-v0.php index 81ba3e9a5cb333..7d2f7f45628dea 100644 --- a/lib/class-wp-theme-json-schema-v0.php +++ b/lib/class-wp-theme-json-schema-v0.php @@ -186,7 +186,6 @@ private static function process_settings( $settings ) { $renamed_paths = array( 'border.customColor' => 'border.color', - 'border.customRadius' => 'border.radius', 'border.customStyle' => 'border.style', 'border.customWidth' => 'border.width', 'typography.customFontStyle' => 'typography.fontStyle', diff --git a/lib/class-wp-theme-json-schema-v1.php b/lib/class-wp-theme-json-schema-v1.php index 8de8d41fe234ef..1c0107c2c6dd19 100644 --- a/lib/class-wp-theme-json-schema-v1.php +++ b/lib/class-wp-theme-json-schema-v1.php @@ -113,7 +113,6 @@ class WP_Theme_JSON_Schema_V1 implements WP_Theme_JSON_Schema { */ const RENAMED_PATHS = array( 'border.customColor' => 'border.color', - 'border.customRadius' => 'border.radius', 'border.customStyle' => 'border.style', 'border.customWidth' => 'border.width', 'typography.customFontStyle' => 'typography.fontStyle', diff --git a/lib/theme.json b/lib/theme.json index 085848be6cf282..514af202649c7b 100644 --- a/lib/theme.json +++ b/lib/theme.json @@ -220,20 +220,20 @@ }, "border": { "color": false, - "radius": false, + "customRadius": false, "style": false, "width": false }, "blocks": { "core/button": { "border": { - "radius": true + "customRadius": true } }, "core/pullquote": { "border": { "color": true, - "radius": true, + "customRadius": true, "style": true, "width": true } diff --git a/packages/block-editor/src/components/use-setting/index.js b/packages/block-editor/src/components/use-setting/index.js index e6090bf15d82c2..b796c7046ed6bf 100644 --- a/packages/block-editor/src/components/use-setting/index.js +++ b/packages/block-editor/src/components/use-setting/index.js @@ -57,7 +57,6 @@ const deprecatedFlags = { // See: https://github.com/WordPress/gutenberg/pull/34485 const prefixedFlags = { 'border.customColor': 'border.color', - 'border.customRadius': 'border.radius', 'border.customStyle': 'border.style', 'border.customWidth': 'border.width', 'typography.customFontStyle': 'typography.fontStyle', diff --git a/packages/block-editor/src/hooks/border.js b/packages/block-editor/src/hooks/border.js index 761c04200a5319..674059b569e22b 100644 --- a/packages/block-editor/src/hooks/border.js +++ b/packages/block-editor/src/hooks/border.js @@ -26,7 +26,7 @@ export function BorderPanel( props ) { useSetting( 'border.color' ) && hasBorderSupport( props.name, 'color' ); const isRadiusSupported = - useSetting( 'border.radius' ) && + useSetting( 'border.customRadius' ) && hasBorderSupport( props.name, 'radius' ); const isStyleSupported = @@ -111,7 +111,7 @@ export function shouldSkipSerialization( blockType ) { const useIsBorderDisabled = () => { const configs = [ ! useSetting( 'border.color' ), - ! useSetting( 'border.radius' ), + ! useSetting( 'border.customRadius' ), ! useSetting( 'border.style' ), ! useSetting( 'border.width' ), ]; diff --git a/packages/edit-site/src/components/global-styles/border-panel.js b/packages/edit-site/src/components/global-styles/border-panel.js index 14ce8e798cdc74..13cd69733f07fd 100644 --- a/packages/edit-site/src/components/global-styles/border-panel.js +++ b/packages/edit-site/src/components/global-styles/border-panel.js @@ -46,7 +46,7 @@ function useHasBorderColorControl( name ) { function useHasBorderRadiusControl( name ) { const supports = getSupportedGlobalStylesPanels( name ); return ( - useSetting( 'border.radius', name )[ 0 ] && + useSetting( 'border.customRadius', name )[ 0 ] && supports.includes( 'borderRadius' ) ); } diff --git a/phpunit/class-wp-theme-json-schema-v0-test.php b/phpunit/class-wp-theme-json-schema-v0-test.php index e47bef52b14ed0..dbc2dd112cd2fc 100644 --- a/phpunit/class-wp-theme-json-schema-v0-test.php +++ b/phpunit/class-wp-theme-json-schema-v0-test.php @@ -117,10 +117,10 @@ function test_parse() { 'link' => true, ), 'border' => array( - 'color' => false, - 'radius' => false, - 'style' => false, - 'width' => false, + 'color' => false, + 'customRadius' => false, + 'style' => false, + 'width' => false, ), 'typography' => array( 'fontStyle' => false, diff --git a/phpunit/class-wp-theme-json-schema-v1-test.php b/phpunit/class-wp-theme-json-schema-v1-test.php index 5af251fb92dabb..228ded2fcb520d 100644 --- a/phpunit/class-wp-theme-json-schema-v1-test.php +++ b/phpunit/class-wp-theme-json-schema-v1-test.php @@ -112,10 +112,10 @@ function test_parse() { 'link' => true, ), 'border' => array( - 'color' => false, - 'radius' => false, - 'style' => false, - 'width' => false, + 'color' => false, + 'customRadius' => false, + 'style' => false, + 'width' => false, ), 'typography' => array( 'fontStyle' => false, @@ -126,10 +126,10 @@ function test_parse() { 'blocks' => array( 'core/group' => array( 'border' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, + 'color' => true, + 'customRadius' => true, + 'style' => true, + 'width' => true, ), 'typography' => array( 'fontStyle' => true, From f7f3e5a8c411270f2d1a3b09d2a85caace57dc0c Mon Sep 17 00:00:00 2001 From: Aaron Robertshaw <60436221+aaronrobertshaw@users.noreply.github.com> Date: Wed, 27 Oct 2021 14:06:15 +1000 Subject: [PATCH 5/9] Add letter spacing to v1 custom prefix removal --- lib/class-wp-theme-json-schema-v1.php | 2 ++ phpunit/class-wp-theme-json-schema-v1-test.php | 4 ++++ 2 files changed, 6 insertions(+) diff --git a/lib/class-wp-theme-json-schema-v1.php b/lib/class-wp-theme-json-schema-v1.php index 1c0107c2c6dd19..0a99fbe2daa693 100644 --- a/lib/class-wp-theme-json-schema-v1.php +++ b/lib/class-wp-theme-json-schema-v1.php @@ -99,6 +99,7 @@ class WP_Theme_JSON_Schema_V1 implements WP_Theme_JSON_Schema { 'fontSizes' => null, 'fontStyle' => null, 'fontWeight' => null, + 'letterSpacing' => null, 'textDecorations' => null, 'textTransforms' => null, ), @@ -117,6 +118,7 @@ class WP_Theme_JSON_Schema_V1 implements WP_Theme_JSON_Schema { 'border.customWidth' => 'border.width', 'typography.customFontStyle' => 'typography.fontStyle', 'typography.customFontWeight' => 'typography.fontWeight', + 'typography.customLetterSpacing' => 'typography.letterSpacing', 'typography.customTextDecorations' => 'typography.textDecoration', 'typography.customTextTransforms' => 'typography.textTransform', ); diff --git a/phpunit/class-wp-theme-json-schema-v1-test.php b/phpunit/class-wp-theme-json-schema-v1-test.php index 228ded2fcb520d..498a7b03becea0 100644 --- a/phpunit/class-wp-theme-json-schema-v1-test.php +++ b/phpunit/class-wp-theme-json-schema-v1-test.php @@ -37,6 +37,7 @@ function test_parse() { 'typography' => array( 'customFontStyle' => false, 'customFontWeight' => false, + 'customLetterSpacing' => false, 'customTextDecorations' => false, 'customTextTransforms' => false, ), @@ -51,6 +52,7 @@ function test_parse() { 'typography' => array( 'customFontStyle' => true, 'customFontWeight' => true, + 'customLetterSpacing' => true, 'customTextDecorations' => true, 'customTextTransforms' => true, ), @@ -120,6 +122,7 @@ function test_parse() { 'typography' => array( 'fontStyle' => false, 'fontWeight' => false, + 'letterSpacing' => false, 'textDecoration' => false, 'textTransform' => false, ), @@ -134,6 +137,7 @@ function test_parse() { 'typography' => array( 'fontStyle' => true, 'fontWeight' => true, + 'letterSpacing' => true, 'textDecoration' => true, 'textTransform' => true, ), From e6cb6a0ba5a46110768e17bde55a3b4bf662fd30 Mon Sep 17 00:00:00 2001 From: Aaron Robertshaw <60436221+aaronrobertshaw@users.noreply.github.com> Date: Wed, 27 Oct 2021 15:02:06 +1000 Subject: [PATCH 6/9] Preprocess path to remove custom prefixes --- .../src/components/use-setting/index.js | 56 ++++++------------- 1 file changed, 18 insertions(+), 38 deletions(-) diff --git a/packages/block-editor/src/components/use-setting/index.js b/packages/block-editor/src/components/use-setting/index.js index b796c7046ed6bf..54f6fc261c7092 100644 --- a/packages/block-editor/src/components/use-setting/index.js +++ b/packages/block-editor/src/components/use-setting/index.js @@ -50,11 +50,6 @@ const deprecatedFlags = { 'spacing.customPadding': ( settings ) => settings.enableCustomSpacing, }; -// The following provide continued support for `custom` prefixed properties. -// This will be removed once third party devs have had sufficient time to update -// themes, plugins, etc. This is also separate to the deprecated flags as there -// will be some overlap e.g. `typography.customLineHeight`. -// See: https://github.com/WordPress/gutenberg/pull/34485 const prefixedFlags = { 'border.customColor': 'border.color', 'border.customStyle': 'border.style', @@ -67,19 +62,19 @@ const prefixedFlags = { }; /** - * Retrieve editor setting value. The block specific setting is preferred - * otherwise falls back to the generic setting path. + * Remove `custom` prefixes for flags that did not land in 5.8. * - * @param {Object} settings Editor settings. - * @param {string} blockName Block to retrieve setting for. - * @param {string} path Path to desired value in settings. - * @return {any} The value for defined setting. + * This provides continued support for `custom` prefixed properties. It will + * be removed once third party devs have had sufficient time to update themes, + * plugins, etc. + * + * @see https://github.com/WordPress/gutenberg/pull/34485 + * + * @param {string} path Path to desired value in settings. + * @return {string} The value for defined setting. */ -const getSetting = ( settings, blockName, path ) => { - const blockPath = `__experimentalFeatures.blocks.${ blockName }.${ path }`; - const defaultsPath = `__experimentalFeatures.${ path }`; - - return get( settings, blockPath ) ?? get( settings, defaultsPath ); +const removeCustomPrefixes = ( path ) => { + return prefixedFlags[ path ] || path; }; /** @@ -102,11 +97,11 @@ export default function useSetting( path ) { // 1 - Use __experimental features, if available. // We cascade to the all value if the block one is not available. - const experimentalFeaturesResult = getSetting( - settings, - blockName, - path - ); + const normalizedPath = removeCustomPrefixes( path ); + const defaultsPath = `__experimentalFeatures.${ normalizedPath }`; + const blockPath = `__experimentalFeatures.blocks.${ blockName }.${ normalizedPath }`; + const experimentalFeaturesResult = + get( settings, blockPath ) ?? get( settings, defaultsPath ); if ( experimentalFeaturesResult !== undefined ) { if ( PATHS_WITH_MERGE[ path ] ) { @@ -119,22 +114,7 @@ export default function useSetting( path ) { return experimentalFeaturesResult; } - // 2 - Handle `custom` prefixed settings. - const pathWithoutPrefix = prefixedFlags[ path ]; - - if ( pathWithoutPrefix ) { - const settingsValue = getSetting( - settings, - blockName, - pathWithoutPrefix - ); - - if ( settingsValue !== undefined ) { - return settingsValue; - } - } - - // 3 - Use deprecated settings, otherwise. + // 2 - Use deprecated settings, otherwise. const deprecatedSettingsValue = deprecatedFlags[ path ] ? deprecatedFlags[ path ]( settings ) : undefined; @@ -142,7 +122,7 @@ export default function useSetting( path ) { return deprecatedSettingsValue; } - // 4 - Fall back for typography.dropCap: + // 3 - Fall back for typography.dropCap: // This is only necessary to support typography.dropCap. // when __experimentalFeatures are not present (core without plugin). // To remove when __experimentalFeatures are ported to core. From 7efa5d6f5970a62b898229835439c548559387ae Mon Sep 17 00:00:00 2001 From: Aaron Robertshaw <60436221+aaronrobertshaw@users.noreply.github.com> Date: Wed, 27 Oct 2021 15:07:45 +1000 Subject: [PATCH 7/9] Make v1 schema reflect theme-json.md and fix copy paste errors --- lib/class-wp-theme-json-schema-v1.php | 98 ++++++++++----------------- 1 file changed, 37 insertions(+), 61 deletions(-) diff --git a/lib/class-wp-theme-json-schema-v1.php b/lib/class-wp-theme-json-schema-v1.php index 0a99fbe2daa693..68275123083fd3 100644 --- a/lib/class-wp-theme-json-schema-v1.php +++ b/lib/class-wp-theme-json-schema-v1.php @@ -11,68 +11,11 @@ * a given structure in v0 schema to the latest one. */ class WP_Theme_JSON_Schema_V1 implements WP_Theme_JSON_Schema { - /** - * Data schema of each block within a theme.json. - * - * Example: - * - * { - * 'block-one': { - * 'styles': { - * 'color': { - * 'background': 'color' - * } - * }, - * 'settings': { - * 'color': { - * 'custom': true - * } - * } - * }, - * 'block-two': { - * 'styles': { - * 'color': { - * 'link': 'color' - * } - * } - * } - * } + * Data schema for v1 theme.json. */ const SCHEMA = array( - 'customTemplates' => null, - 'templateParts' => null, - 'styles' => array( - 'border' => array( - 'radius' => null, - 'color' => null, - 'style' => null, - 'width' => null, - ), - 'color' => array( - 'background' => null, - 'gradient' => null, - 'link' => null, - 'text' => null, - ), - 'spacing' => array( - 'padding' => array( - 'top' => null, - 'right' => null, - 'bottom' => null, - 'left' => null, - ), - ), - 'typography' => array( - 'fontFamily' => null, - 'fontSize' => null, - 'fontStyle' => null, - 'fontWeight' => null, - 'lineHeight' => null, - 'textDecoration' => null, - 'textTransform' => null, - ), - ), + 'version' => 1, 'settings' => array( 'border' => array( 'radius' => null, @@ -106,6 +49,39 @@ class WP_Theme_JSON_Schema_V1 implements WP_Theme_JSON_Schema { 'custom' => null, 'layout' => null, ), + 'styles' => array( + 'border' => array( + 'radius' => null, + 'color' => null, + 'style' => null, + 'width' => null, + ), + 'color' => array( + 'background' => null, + 'gradient' => null, + 'link' => null, + 'text' => null, + ), + 'spacing' => array( + 'padding' => array( + 'top' => null, + 'right' => null, + 'bottom' => null, + 'left' => null, + ), + ), + 'typography' => array( + 'fontFamily' => null, + 'fontSize' => null, + 'fontStyle' => null, + 'fontWeight' => null, + 'lineHeight' => null, + 'textDecoration' => null, + 'textTransform' => null, + ), + ), + 'customTemplates' => null, + 'templateParts' => null, ); /** @@ -124,9 +100,9 @@ class WP_Theme_JSON_Schema_V1 implements WP_Theme_JSON_Schema { ); /** - * Converts a v0 schema into the latest. + * Converts a v1 schema into the latest. * - * @param array $old Data in v0 schema. + * @param array $old Data in v1 schema. * * @return array Data in the latest schema. */ From 6bd8ec9dff5fb70bdf5c81e914543ba2506e9696 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Andr=C3=A9?= <583546+oandregal@users.noreply.github.com> Date: Wed, 27 Oct 2021 10:05:09 +0200 Subject: [PATCH 8/9] Protect against unexisting blocks key --- lib/class-wp-theme-json-schema-v1.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/class-wp-theme-json-schema-v1.php b/lib/class-wp-theme-json-schema-v1.php index 68275123083fd3..87ef54847a98a8 100644 --- a/lib/class-wp-theme-json-schema-v1.php +++ b/lib/class-wp-theme-json-schema-v1.php @@ -134,7 +134,7 @@ private static function process_settings( $settings ) { self::rename_settings( $new_settings ); // Process individual block settings. - if ( is_array( $new_settings['blocks'] ) ) { + if ( isset( $new_settings['blocks'] ) && is_array( $new_settings['blocks'] ) ) { foreach ( $new_settings['blocks'] as &$block_settings ) { self::rename_settings( $block_settings ); } From 4b9bd05947af35aa8de49424d156bb005fa3b13b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Andr=C3=A9?= <583546+oandregal@users.noreply.github.com> Date: Wed, 27 Oct 2021 10:06:20 +0200 Subject: [PATCH 9/9] Use normalize path everywhere --- packages/block-editor/src/components/use-setting/index.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/packages/block-editor/src/components/use-setting/index.js b/packages/block-editor/src/components/use-setting/index.js index 54f6fc261c7092..b517c903508706 100644 --- a/packages/block-editor/src/components/use-setting/index.js +++ b/packages/block-editor/src/components/use-setting/index.js @@ -104,7 +104,7 @@ export default function useSetting( path ) { get( settings, blockPath ) ?? get( settings, defaultsPath ); if ( experimentalFeaturesResult !== undefined ) { - if ( PATHS_WITH_MERGE[ path ] ) { + if ( PATHS_WITH_MERGE[ normalizedPath ] ) { return ( experimentalFeaturesResult.user ?? experimentalFeaturesResult.theme ?? @@ -115,8 +115,8 @@ export default function useSetting( path ) { } // 2 - Use deprecated settings, otherwise. - const deprecatedSettingsValue = deprecatedFlags[ path ] - ? deprecatedFlags[ path ]( settings ) + const deprecatedSettingsValue = deprecatedFlags[ normalizedPath ] + ? deprecatedFlags[ normalizedPath ]( settings ) : undefined; if ( deprecatedSettingsValue !== undefined ) { return deprecatedSettingsValue; @@ -126,7 +126,7 @@ export default function useSetting( path ) { // This is only necessary to support typography.dropCap. // when __experimentalFeatures are not present (core without plugin). // To remove when __experimentalFeatures are ported to core. - return path === 'typography.dropCap' ? true : undefined; + return normalizedPath === 'typography.dropCap' ? true : undefined; }, [ blockName, path ] );