Skip to content

UI Node Decorations #20103

Open
Open
@viridia

Description

@viridia

What problem does this solve or what need does it fill?

This came up during the discussion of using Outline for widget focus rings (#20047): you can only have one Outline component, but widgets often have multiple uses by multiple authors, who may want to add outlines for different purposes.

There is a similar issue around drop shadows: currently you can only have one BoxShadow component, although the component contains a Vec of multiple shadows. This works fine if all the shadows are created by a single author, but requires coordination if multiple authors are adding shadows for different purposes. (Admittedly, this is rare, since the most common use case for multiple shadows is to get a smoother fall-off by blending multiple shadows together. However, one could envision dynamic "glows" as a highlighting effect.)

Both outlines and box shadows fall into a group of 2D layering effects: that is, they are additional geometric primitives which are rendered either above or below the base entity. They both take up no space in the layout and have no effect on picking.

There are potentially other kinds of effects which could fall in the same category. One of these is the "alpha pattern", a repeating checkerboard drawn behind the node, as a way to show the user that the background color is not completely opaque. (Admittedly this is a fairly obscure use cases which is solvable by other means, but I'm trying to come up with examples.)

What solution would you like?

The proposal is to generalize 2D layering effects using relations. Under this scheme, a node could have any number of "decorations", and each decoration would be an entity. Because they are entities, they can be added, removed, re-ordered, queried, and have marker components as needed.

Decorations would have a much smaller overhead than regular UI nodes. They would not need layout information (they are always the same size as their base entity) so would not need a Node component, nor Transform, GlobalTransform and so on.

Decorations are not children, and should not be treated as such. Instead, we would define a new relation, DecorationOf, and it's corresponding relationship target, Decorations.

Both Outline and BoxShadow would be decorations. BoxShadow would be simplified to hold a single shadow, without the Vec - if you want multiple shadows, you can spawn multiple decorations.

Decorations can have a Z-index, which is relative to the base entity.

It's an open question as to whether new kinds of decorations could be added by users without changing Bevy.

What alternative(s) have you considered?

Everything that I propose here is already doable with absolutely-positioned child entities, albeit at the cost of additional overhead. (Although I am not sure that a child can draw behind its parent.)

Additional context

My main interest in proposing this is to break free from the shackles of the CSS-centric world view, by offering a model for effects which goes beyond what is possible in CSS. This proposal is somewhat speculative; I mainly introduce it here for purposes of discussion.

@alice-i-cecile
@ickshonpe

Metadata

Metadata

Assignees

No one assigned

    Labels

    A-UIGraphical user interfaces, styles, layouts, and widgetsC-FeatureA new feature, making something new possibleS-Needs-DesignThis issue requires design work to think about how it would best be accomplishedX-ContentiousThere are nontrivial implications that should be thought through

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions