Custom CSS for global styles and per block

Global Custom CSSCSS Cascading Style Sheets.

A custom CSS input box has been added to the Global Styles settings in the Site Editor. This provides similar functionality to the custom CSS input available in CustomizerCustomizer Tool built into WordPress core that hooks into most modern themes. You can use it to preview and modify many of your site’s appearance settings. for classic themes. This option appears under the global styles actions menu: (#46141)

Screenshot of location of Additional CSS menu item.

Ideally, this input should be seen as a last resort fallback to add styling that can not yet be implemented with the other editor design tools. Some other important things to note are:

  • This custom CSS does not use the same custom_css CPT as the Customizer custom CSS, but instead is part of the existing Global Styles wp_global_styles CPT
  • As with the other user custom global styles, the custom CSS is specific to the current theme
  • To support custom CSS as part of Global Styles a new property has been added to theme.jsonJSON JSON, or JavaScript Object Notation, is a minimal, readable format for structuring data. It is used primarily to transmit data between a server and web application, as an alternative to XML.styles.css
  • While the addition of the styles.css property to theme.json does allow theme authors to use it to include custom CSS strings in their themes, as with the user input for this property ideally themes should only use this as a last resort fallback to add styling that can’t yet be implemented with the other editor design tools
  • Theme authors should note that users’ custom CSS can completely override or remove any theme custom CSS set in the theme.json, so in cases where theme authors do not want users to easily wipe custom CSS they should consider including it via the existing style sheet enqueuing methods
  • Because the standard global styles flow is for user data to override theme data, it would be possible for users to inadvertently override a key theme custom CSS setting, eg. add a custom image background to a group and in the process wipe a background that the theme was adding to headings. For this reason, when a user first edits the custom CSS the theme CSS is shown in the input box to allow the user to selectively and knowingly override/remove any theme custom CSS

Per BlockBlock Block is the abstract term used to describe units of markup that, composed together, form the content or layout of a webpage using the WordPress editor. The idea combines concepts of what in the past may have achieved with shortcodes, custom HTML, and embed discovery into a single consistent API and user experience. Custom CSS

When a theme that has support for the Site Editor is activated, users do not have easy access to adding additional CSS via the Customizer. In WordPress 6.2, there are two new ways to add per-block custom CSS: Via the Styles interface in the Site Editor and theme.json. (#46571)

To add CSS via the interface:

  • open the Styles sidebarSidebar A sidebar in WordPress is referred to a widget-ready area used by WordPress themes to display information that is not a part of the main content. It is not always a vertical column on the side. It can be a horizontal rectangle below or above the content area, footer, header, or any where in the theme. in the Site Editor
  • Next, open the blocks panel and
  • select a block
  • Click on Additional block CSS to open the block CSS panel

Screenshot on where to find "Original Theme Custom CSS"

CSS added in this panel applies to all occurrences of the block.
In this panel, you can also see if the active theme adds CSS using theme.json:

You can add per-block custom CSS in theme.json as a string in styles.blocks.block.css.
Basic example:

"styles": {
	"blocks": {
		"core/button": {
			"css": "background: purple"

In addition, the use of & is supported for nested elements & pseudo-selectors, both in the theme.json file and the custom CSS input in global styles.

"styles": {
	"blocks": {
		"core/group": {
			"css": "background:var(--wp--preset--color--base); & .cta { background:#fafafa; padding:var(--wp--preset--spacing--40); } & .wp-element-button { background-color:purple; color: white; } & .wp-element-button:hover { opacity: 0.9; }"

Props to @poena for co-authoring and to @bph and @webcommsat for reviews.

#6-1, #dev-notes, #dev-notes-6-2