diff --git a/lib/block-supports/custom-classname.php b/lib/block-supports/custom-classname.php new file mode 100644 index 00000000000000..c8b8b8c3bd5eed --- /dev/null +++ b/lib/block-supports/custom-classname.php @@ -0,0 +1,47 @@ +supports, array( 'customClassName' ), true ); + if ( $has_custom_classname_support ) { + if ( ! $block_type->attributes ) { + $block_type->attributes = array(); + } + + if ( ! array_key_exists( 'className', $block_type->attributes ) ) { + $block_type->attributes['className'] = array( + 'type' => 'string', + ); + } + } +} + +/** + * Add the custom classnames to the output. + * + * @param array $attributes comprehensive list of attributes to be applied. + * @param array $block_attributes block attributes. + * @param array $block_type Block Type. + * @return array Block CSS classes and inline styles. + */ +function gutenberg_apply_custom_classname_support( $attributes, $block_attributes, $block_type ) { + $has_custom_classname_support = gutenberg_experimental_get( $block_type->supports, array( 'customClassName' ), true ); + if ( $has_custom_classname_support ) { + $has_custom_classnames = array_key_exists( 'className', $block_attributes ); + + if ( $has_custom_classnames ) { + $attributes['css_classes'][] = $block_attributes['className']; + } + } + + return $attributes; +} diff --git a/lib/block-supports/index.php b/lib/block-supports/index.php index 4fd6460234d3f6..e000c04891eec5 100644 --- a/lib/block-supports/index.php +++ b/lib/block-supports/index.php @@ -17,6 +17,7 @@ function gutenberg_register_block_supports() { gutenberg_register_alignment_support( $block_type ); gutenberg_register_colors_support( $block_type ); gutenberg_register_typography_support( $block_type ); + gutenberg_register_custom_classname_support( $block_type ); } } @@ -44,6 +45,7 @@ function gutenberg_apply_block_supports( $block_content, $block ) { $attributes = gutenberg_apply_colors_support( $attributes, $block['attrs'], $block_type ); $attributes = gutenberg_apply_typography_support( $attributes, $block['attrs'], $block_type ); $attributes = gutenberg_apply_alignment_support( $attributes, $block['attrs'], $block_type ); + $attributes = gutenberg_apply_custom_classname_support( $attributes, $block['attrs'], $block_type ); if ( ! count( $attributes ) ) { return $block_content; diff --git a/lib/load.php b/lib/load.php index 9f20014bf8e0e4..026a18c9cea523 100644 --- a/lib/load.php +++ b/lib/load.php @@ -110,3 +110,4 @@ function gutenberg_is_experiment_enabled( $name ) { require dirname( __FILE__ ) . '/block-supports/align.php'; require dirname( __FILE__ ) . '/block-supports/colors.php'; require dirname( __FILE__ ) . '/block-supports/typography.php'; +require dirname( __FILE__ ) . '/block-supports/custom-classname.php'; diff --git a/lib/utils.php b/lib/utils.php index 9d38be7a762a29..b5cdef7f999a99 100644 --- a/lib/utils.php +++ b/lib/utils.php @@ -24,7 +24,7 @@ function gutenberg_experimental_get( $array, $path, $default = array() ) { $path_length = count( $path ); for ( $i = 0; $i < $path_length; ++$i ) { - if ( empty( $array[ $path[ $i ] ] ) ) { + if ( ! isset( $array[ $path[ $i ] ] ) ) { return $default; } $array = $array[ $path[ $i ] ]; diff --git a/packages/block-library/src/archives/block.json b/packages/block-library/src/archives/block.json index b869126a43bb93..14a9451e1b0d89 100644 --- a/packages/block-library/src/archives/block.json +++ b/packages/block-library/src/archives/block.json @@ -2,9 +2,6 @@ "name": "core/archives", "category": "widgets", "attributes": { - "className": { - "type": "string" - }, "displayAsDropdown": { "type": "boolean", "default": false diff --git a/packages/block-library/src/archives/index.php b/packages/block-library/src/archives/index.php index b2a8b12b61f9d4..7fb3cf8968b577 100644 --- a/packages/block-library/src/archives/index.php +++ b/packages/block-library/src/archives/index.php @@ -19,10 +19,6 @@ function render_block_core_archives( $attributes ) { $class = 'wp-block-archives'; - if ( isset( $attributes['className'] ) ) { - $class .= " {$attributes['className']}"; - } - if ( ! empty( $attributes['displayAsDropdown'] ) ) { $class .= ' wp-block-archives-dropdown'; diff --git a/packages/block-library/src/calendar/block.json b/packages/block-library/src/calendar/block.json index b74c46f49a32af..698140a33354ba 100644 --- a/packages/block-library/src/calendar/block.json +++ b/packages/block-library/src/calendar/block.json @@ -2,9 +2,6 @@ "name": "core/calendar", "category": "widgets", "attributes": { - "className": { - "type": "string" - }, "month": { "type": "integer" }, diff --git a/packages/block-library/src/calendar/index.php b/packages/block-library/src/calendar/index.php index d45ebad36e9d64..41d18c010ab1c0 100644 --- a/packages/block-library/src/calendar/index.php +++ b/packages/block-library/src/calendar/index.php @@ -31,11 +31,9 @@ function render_block_core_calendar( $attributes ) { } } - $custom_class_name = empty( $attributes['className'] ) ? '' : ' ' . $attributes['className']; - $output = sprintf( '
%2$s
', - esc_attr( 'wp-block-calendar' . $custom_class_name ), + esc_attr( 'wp-block-calendar' ), get_calendar( true, false ) ); diff --git a/packages/block-library/src/categories/block.json b/packages/block-library/src/categories/block.json index 0194ee9c62971c..d4fee5e0649515 100644 --- a/packages/block-library/src/categories/block.json +++ b/packages/block-library/src/categories/block.json @@ -2,9 +2,6 @@ "name": "core/categories", "category": "widgets", "attributes": { - "className": { - "type": "string" - }, "displayAsDropdown": { "type": "boolean", "default": false diff --git a/packages/block-library/src/categories/index.php b/packages/block-library/src/categories/index.php index 14201f495a970a..4880ff56434094 100644 --- a/packages/block-library/src/categories/index.php +++ b/packages/block-library/src/categories/index.php @@ -43,10 +43,6 @@ function render_block_core_categories( $attributes ) { $class = "wp-block-categories wp-block-categories-{$type}"; - if ( isset( $attributes['className'] ) ) { - $class .= " {$attributes['className']}"; - } - return sprintf( $wrapper_markup, esc_attr( $class ), diff --git a/packages/block-library/src/latest-comments/block.json b/packages/block-library/src/latest-comments/block.json index 751efa9d270625..dd208ee7266979 100644 --- a/packages/block-library/src/latest-comments/block.json +++ b/packages/block-library/src/latest-comments/block.json @@ -2,9 +2,6 @@ "name": "core/latest-comments", "category": "widgets", "attributes": { - "className": { - "type": "string" - }, "commentsToShow": { "type": "number", "default": 5, diff --git a/packages/block-library/src/latest-comments/index.php b/packages/block-library/src/latest-comments/index.php index 150c586cfd6b05..cf5b62aff3ff3a 100644 --- a/packages/block-library/src/latest-comments/index.php +++ b/packages/block-library/src/latest-comments/index.php @@ -117,9 +117,6 @@ function render_block_core_latest_comments( $attributes = array() ) { } $class = 'wp-block-latest-comments'; - if ( ! empty( $attributes['className'] ) ) { - $class .= ' ' . $attributes['className']; - } if ( $attributes['displayAvatar'] ) { $class .= ' has-avatars'; } diff --git a/packages/block-library/src/latest-posts/block.json b/packages/block-library/src/latest-posts/block.json index 8ecb71a666db46..bf363c7718f64d 100644 --- a/packages/block-library/src/latest-posts/block.json +++ b/packages/block-library/src/latest-posts/block.json @@ -2,9 +2,6 @@ "name": "core/latest-posts", "category": "widgets", "attributes": { - "className": { - "type": "string" - }, "categories": { "type": "array", "items": { diff --git a/packages/block-library/src/latest-posts/index.php b/packages/block-library/src/latest-posts/index.php index 4dc1efa1514815..fc900fbacf22b7 100644 --- a/packages/block-library/src/latest-posts/index.php +++ b/packages/block-library/src/latest-posts/index.php @@ -162,10 +162,6 @@ function render_block_core_latest_posts( $attributes ) { $class .= ' has-author'; } - if ( isset( $attributes['className'] ) ) { - $class .= ' ' . $attributes['className']; - } - return sprintf( '', esc_attr( $class ), diff --git a/packages/block-library/src/navigation/block.json b/packages/block-library/src/navigation/block.json index 050e31f3fffdc1..1c0abeeee1aed1 100644 --- a/packages/block-library/src/navigation/block.json +++ b/packages/block-library/src/navigation/block.json @@ -5,9 +5,6 @@ "orientation": { "type": "string" }, - "className": { - "type": "string" - }, "textColor": { "type": "string" }, diff --git a/packages/block-library/src/navigation/index.php b/packages/block-library/src/navigation/index.php index d7babf262c30a2..4f763e70180bc9 100644 --- a/packages/block-library/src/navigation/index.php +++ b/packages/block-library/src/navigation/index.php @@ -131,7 +131,6 @@ function render_block_core_navigation( $attributes, $content, $block ) { $colors['css_classes'], $font_sizes['css_classes'], array( 'wp-block-navigation' ), - isset( $attributes['className'] ) ? array( $attributes['className'] ) : array(), ( isset( $attributes['orientation'] ) && 'vertical' === $attributes['orientation'] ) ? array( 'is-vertical' ) : array(), isset( $attributes['itemsJustification'] ) ? array( 'items-justified-' . $attributes['itemsJustification'] ) : array() ); diff --git a/packages/block-library/src/rss/block.json b/packages/block-library/src/rss/block.json index 947ee295651b45..88ad78c5963852 100644 --- a/packages/block-library/src/rss/block.json +++ b/packages/block-library/src/rss/block.json @@ -2,9 +2,6 @@ "name": "core/rss", "category": "widgets", "attributes": { - "className": { - "type": "string" - }, "columns": { "type": "number", "default": 2 diff --git a/packages/block-library/src/rss/index.php b/packages/block-library/src/rss/index.php index 3f1e85ae1c407d..6c8792aa448d66 100644 --- a/packages/block-library/src/rss/index.php +++ b/packages/block-library/src/rss/index.php @@ -88,10 +88,6 @@ function render_block_core_rss( $attributes ) { $class .= ' columns-' . $attributes['columns']; } - if ( isset( $attributes['className'] ) ) { - $class .= ' ' . $attributes['className']; - } - return sprintf( '', esc_attr( $class ), $list_items ); } diff --git a/packages/block-library/src/search/block.json b/packages/block-library/src/search/block.json index ea0e247ae9e534..0a2f217aca34b7 100644 --- a/packages/block-library/src/search/block.json +++ b/packages/block-library/src/search/block.json @@ -2,9 +2,6 @@ "name": "core/search", "category": "widgets", "attributes": { - "className": { - "type": "string" - }, "label": { "type": "string" }, diff --git a/packages/block-library/src/search/index.php b/packages/block-library/src/search/index.php index d7209352ba6a90..7a224fa2eed3da 100644 --- a/packages/block-library/src/search/index.php +++ b/packages/block-library/src/search/index.php @@ -60,9 +60,6 @@ function render_block_core_search( $attributes ) { } $class = 'wp-block-search'; - if ( isset( $attributes['className'] ) ) { - $class .= ' ' . $attributes['className']; - } return sprintf( '', diff --git a/packages/block-library/src/tag-cloud/block.json b/packages/block-library/src/tag-cloud/block.json index 6d90c6acc2057d..7116bb43ddf16a 100644 --- a/packages/block-library/src/tag-cloud/block.json +++ b/packages/block-library/src/tag-cloud/block.json @@ -2,9 +2,6 @@ "name": "core/tag-cloud", "category": "widgets", "attributes": { - "className": { - "type": "string" - }, "taxonomy": { "type": "string", "default": "post_tag" diff --git a/packages/block-library/src/tag-cloud/index.php b/packages/block-library/src/tag-cloud/index.php index 12d2a288217bda..667c09a325651f 100644 --- a/packages/block-library/src/tag-cloud/index.php +++ b/packages/block-library/src/tag-cloud/index.php @@ -14,12 +14,7 @@ */ function render_block_core_tag_cloud( $attributes ) { $class = 'wp-block-tag-cloud'; - - if ( isset( $attributes['className'] ) ) { - $class .= ' ' . $attributes['className']; - } - - $args = array( + $args = array( 'echo' => false, 'taxonomy' => $attributes['taxonomy'], 'show_count' => $attributes['showTagCounts'], diff --git a/phpunit/class-block-supported-styles-test.php b/phpunit/class-block-supported-styles-test.php index f0589e3d151001..39b7f5eece35fe 100644 --- a/phpunit/class-block-supported-styles-test.php +++ b/phpunit/class-block-supported-styles-test.php @@ -687,4 +687,60 @@ function test_render_callback_required() { $this->assert_content_and_styles_and_classes_match( $block, $expected_classes, $expected_styles ); } + + /** + * Tests custom classname server-side block support. + */ + function test_custom_classnames_support() { + $block_type_settings = array( + 'attributes' => array(), + 'supports' => array(), + 'render_callback' => true, + ); + $this->register_block_type( 'core/example', $block_type_settings ); + + $block = array( + 'blockName' => 'core/example', + 'attrs' => array( + 'className' => 'my-custom-classname', + ), + 'innerBlock' => array(), + 'innerContent' => array(), + 'innerHTML' => array(), + ); + + $expected_styles = 'test:style; '; + $expected_classes = 'wp-block-example foo-bar-class my-custom-classname'; + + $this->assert_content_and_styles_and_classes_match( $block, $expected_classes, $expected_styles ); + } + + /** + * Tests custom classname server-side block support opt-out. + */ + function test_custom_classnames_support_opt_out() { + $block_type_settings = array( + 'attributes' => array(), + 'supports' => array( + 'customClassName' => false, + ), + 'render_callback' => true, + ); + $this->register_block_type( 'core/example', $block_type_settings ); + + $block = array( + 'blockName' => 'core/example', + 'attrs' => array( + 'className' => 'my-custom-classname', + ), + 'innerBlock' => array(), + 'innerContent' => array(), + 'innerHTML' => array(), + ); + + $expected_styles = 'test:style;'; + $expected_classes = 'wp-block-example foo-bar-class'; + + $this->assert_content_and_styles_and_classes_match( $block, $expected_classes, $expected_styles ); + } }