Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow custom settings to be placed in global styles #47990

Open
fabiankaegy opened this issue Feb 11, 2023 · 21 comments
Open

Allow custom settings to be placed in global styles #47990

fabiankaegy opened this issue Feb 11, 2023 · 21 comments
Labels
[Feature] Extensibility The ability to extend blocks or the editing experience [Focus] Blocks Adoption For issues that directly impact the ability to adopt features of Gutenberg. Global Styles Anything related to the broader Global Styles efforts, including Styles Engine and theme.json Needs Dev Ready for, and needs developer efforts [Type] Enhancement A suggestion for improvement.

Comments

@fabiankaegy
Copy link
Member

fabiankaegy commented Feb 11, 2023

What problem does this address?

For example, when building custom blocks such as an Accordion, there are more color settings than just the background & text color. Similar to how the Navigation block currently does it, we have the ability to add custom color settings to the block itself. But that means there is no way for someone to manipulate the global appearance of this block. So every instance always needs to get customized manually.

Another example is how the button block/element has special treatment. No custom block can opt into / recreate the pseudo-state global styles interface.

Block Styles Settings Sidebar

CleanShot 2023-02-11 at 12 00 13@2x

Block Global Styles Color Settings Sidebar

CleanShot 2023-02-11 at 12 02 11@2x

What is your proposed solution?

Similar to how we add custom settings to blocks themselves, there should be a way to expose custom settings in the global styles interface of individual blocks. This could work as a way to override the default value for these custom attributes.

We already add new color settings to individual spots in the inspector controls. If a block adds something in the correct group it should not just appear for the block sidebar itself but also the global styles interface.

<InspectorControls group="color">
    { // whatever gets rendered here should show both in the Inspector and in the Global Styles color options }
</InspectorControls>
@fabiankaegy fabiankaegy added [Feature] Extensibility The ability to extend blocks or the editing experience Global Styles Anything related to the broader Global Styles efforts, including Styles Engine and theme.json labels Feb 11, 2023
@fabiankaegy
Copy link
Member Author

I used additional color settings in the example here but I don't hink it should be limited to extending existing groups of global style values.

There should be a mechanism to apply any block attribute (that the block wants to) globally.

@richtabor
Copy link
Member

Custom colors should be easier to implement, and be exposed to Global Styles. Even the core/cover block does not have its Overlay color available within Global Styles.

No custom block can opt into / recreate the pseudo-state global styles interface.

Not quite following? Do you mean opting into block supports?

@fabiankaegy
Copy link
Member Author

@richtabor What I meant with that is just to enforce the statement with an example. The Button element currently has some hardcoded logic to exposing the pseudo state color settings (hover etc.) which no custom block can replicate. Not even via a simple block support setting but even building all the setings and logic out manually is not possible because there is no way ro render custom settings in the global styles interface.

And I personally see this as an issue that is larger than just color. If a custom accordion block wants to have a global setting of wheather the expand icon should be on the left or right side of the block, there should be a way to save that preference globally so it applies to all instances of the accordion or can be manually overridden on an instance basis.

@richtabor
Copy link
Member

And I personally see this as an issue that is larger than just color. If a custom accordion block wants to have a global setting of wheather the expand icon should be on the left or right side of the block, there should be a way to save that preference globally so it applies to all instances of the accordion or can be manually overridden on an instance basis.

Ah, I see. I'm not sure, but perhaps controls/attributes added to the "Styles" tab of a block should be set to display within Global Styles — i.e. counted as a "style" — #47105 (comment).

@fabiankaegy
Copy link
Member Author

@richtabor yeah exactly that would work 👍

@fabiankaegy
Copy link
Member Author

@annezazu I wanted to flag this issue to you since it is something that currently blocks the addoption of block-based themes to a certain degree in the agency world.

The struggle we have here is that there is no mechanism to configure global styles for custom settings that are not already built as part of the core global styles. And regardless of how many global styles elements core adds there will always be the need for individual block specific global styles that we would want to configure in the global styles interface so that they affect every instance of that block.

I'm flagging this to you because I know you have been sheparding the "Blocks Adoption" label and I want to talk about it before just adding the label myself :)

@annezazu annezazu added the [Focus] Blocks Adoption For issues that directly impact the ability to adopt features of Gutenberg. label Feb 15, 2023
@annezazu
Copy link
Contributor

This is fantastic feedback. Thank you. Adding in the label!

@fabiankaegy
Copy link
Member Author

@ndiego im also quite interested in your thoughts on this one :) you have built quite a few blocks that are to be used in block based templates. Have you found a good solution for this already or do you think a system like this is also needed? :)

@fabiankaegy
Copy link
Member Author

@scruffian @ramonjd @aaronrobertshaw As I'm digging deeper into the feasibility of this, I would love better to understand the limitations from your all's perspective.

Is there a specific reason why the global styles API currently is a private API without points for extensibility? 🤔

CC: @youknowriad @mtias

(sorry for the direct pings)

@youknowriad
Copy link
Contributor

I think the main reason for limiting the extensibility APIs so far is the fact that UI is very much in flux. (We just recently revamped the whole block global styles sidebar for instance). That said, we're starting to think about ways to open some extensibility APIs there. @ntsekouras was looking as some slots there (initially at the root level).

@mtias
Copy link
Member

mtias commented May 9, 2023

Yes, use cases like this are useful in helping extract intention from implementation. We want to avoid slot contracts that are loosely held by positional semantics as much as possible. But things are too restricted right now, and we should provide more extensibility points soon.

@ntsekouras
Copy link
Contributor

The struggle we have here is that there is no mechanism to configure global styles for custom settings that are not already built as part of the core global styles.

I'll also cc @oandregal about this, as this is the main issue compared to adding an extensibility point like a slot there.

@oandregal
Copy link
Member

This is a topic that has been discussed in some places, there's #35114 and #33255 that link to past conversations, which can be useful to know what the common thinking was back then. The TLDR is that the efforts to bring extensibility to this were paused due to

  1. UI being in flux (G2 work, site editor, site editor shell)
  2. A desire to develop a common set of design tokens, to avoid the incompatibility between them. For example, if link colors are expressed as "custom design tokens" by blocks, users don't have the ability to style "all link colors" at once at the top-level.
  3. A desire to give time to develop the block API and avoid people short-circuiting it. For example, not using inner blocks for complex blocks because the UI doesn't present the style controls of the children in the parent.

@oandregal
Copy link
Member

Going back to the original proposal of the issue:

<InspectorControls group="color">
    { // whatever gets rendered here should show both in the Inspector and in the Global Styles color options }
</InspectorControls>

I like this idea, though I worry that it is too block-centric.

From the data structure POV: style structure for blocks and theme.json is not consolidated yet AFAIK. From the data flow POV: the controls within InspectorControls are passed the setAttributes function to control "block attributes" while Global styles lives elsewhere, not attached to a block. Blocks don't represent the full space of global styles either: there is top-level styles/settings that are not attached to any given block, elements are not represented at the block level either, etc. I haven't explored this option fully, but it sounds there are some technical issues to make both things work together.

@oandregal
Copy link
Member

Some ways forward:

  • Allowing blocks to define their own custom block supports in block.json. There was a prototype for this by @aaronrobertshaw at [WIP] Block Support: Custom secondary colors support #33157
  • Expand the elements API at the block level, so there's more "design space" for blocks in a way that can be understood by the block inspector and the global styles ui. The elements API is something that only works at the global styles level at the moment. If it was made available at the block-level, it could absorb some of these use cases.
  • Block inspector controls: make it so the UI controls of the block hierarchy are represented together, so users don't have to go block by block to tweak the styles, helping to leverage the full power of inner blocks.

Additionally, we may still want to create a specific API for registering custom global styles. Something akin to what people had in the customizer. My thinking is that, if we do this, it should be declarative: the extenders shouldn't have to deal with the data flow, which is the most complex aspect. This should be available in the server, otherwise, the info won't be available to render the styles in the front-end, for kses sanitization, etc. Throwing a potential quick example of the data bits we'd need using a PHP function, though there could be more options for this API:

register_global_control( array(
  slot: 'root', // Where it goes in the UI and in the theme.json schema. It could be "root", or "blocks.core/paragraph", etc.
  type: 'color', // Which section belongs to. Used to render the UI component for colors, position in the theme.json schema, etc.
  handle: 'my/control-handle', // Namespace to avoid conflicts between custom controls.
  name: "Expanded Text", // The label for the user in the UI.
  css: 'background-color', // The CSS property to be used to render the value, also by kses to sanitize it, etc.
) )

@aaronrobertshaw
Copy link
Contributor

To add just a little to @oandregal's last comment, the recently stabilized Selectors API might help when implementing a solution.

At a basic level, the reason we need to add extra controls, such as additional colors, is that we are trying to style multiple elements. The Selectors API could be extended to assist in applying custom registered controls' styles to the correct elements.

A block's custom selectors are currently defined within its block.json. Would it be better to keep all the configuration of additional controls, their selectors etc, in a single location i.e. block.json?

@sethrubenstein
Copy link
Contributor

I really like this idea, it would go a long way to allowing greater customization of core blocks without having to recreate them just to add additional color styles. Hopefully the greater style engine would be aware of additional color controls as currently there doesnt seem to be a way to define additional color attributes and have those visible in things like the Style Book.

@hadamlenz
Copy link

this is great and much needed, please allow for opting in/out so it's backward compatible with the blocks that are already doing something

<InspectorControls group="color" global="true">

or

<InspectorControls group="color" global="false">

@ramonjd
Copy link
Member

ramonjd commented Nov 18, 2024

Sorry, very unfashionably late to the party. I'm thinking out loud here with no filter.

As others have alluded to, adding controls is not so much the issue. It's hooking those controls up to the current style parsing, output and saving mechanisms that'll bite.

The Selectors API could be extended to assist in applying custom registered controls' styles to the correct elements.
A block's custom selectors are currently defined within its block.json. Would it be better to keep all the configuration of additional controls, their selectors etc, in a single location i.e. block.json?

If we were just sticking to block, then I'd +1 this.

though I worry that it is too block-centric.

So is the idea that we open up the entire global styles panel to extension? I'm thinking top-level style categories (typography, color, etc) + layout, and then at the block level?

Where would the styles be stored?

I suspect there would be styles that global styles does not support, and, furthermore, whose selectors the current global styles system is unable to express. We'd still need a selector if I'm not mistaken, e.g., if an extend wants to create a control for <any-element />.

There would need to be some imposed structure in order to store and access the styles. I suppose such styles would be stored in the user global styles custom post type, which is in theme.json format. I'm not sure whether it should be separate from theme.json handling however. Do we care about validating against the theme.json schema?
Or is the idea to limit styles and settings to those already handled by theme.json and its associated PHP classes?

@aaronrobertshaw
Copy link
Contributor

Do we care about validating against the theme.json schema?

FWIW there's some validation against a schema when a user doesn't have unfiltered_html caps. The resulting styles are also then passed through safecss_filter_attr. The result means a lot of newer or more complex CSS values etc are getting stripped out in that process. Generally, the fix there is a simple patch to core and a temporary plugin/theme filter but it's still an issue that might be run into more often if we're aiming to allow everything and the kitchen sink in the global styles CPT/theme.json.

@hadamlenz
Copy link

in the current form this ticket says setting and not styles, so I assume these don't necessarily need to always be styles. for example, the heading tag of a block defaults to h2, but could be h3-h4 depending on where it's placed. Knowing that a site will almost always need an h3 would make the site author's job a bit less obnoxious if it could be set to h3.

it would be global block settings... or the ability to set the default attributes via gui. So that when the example block is placed the heading tag is h3. let what happens to those attributes be handled by the block dev (please)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
[Feature] Extensibility The ability to extend blocks or the editing experience [Focus] Blocks Adoption For issues that directly impact the ability to adopt features of Gutenberg. Global Styles Anything related to the broader Global Styles efforts, including Styles Engine and theme.json Needs Dev Ready for, and needs developer efforts [Type] Enhancement A suggestion for improvement.
Projects
Development

No branches or pull requests