Re: [csswg-drafts] [css-scoping-1] Dynamic changes of state and attributes referenced by :host-context rules are pretty hard to handle efficiently. (#1914)

Directionality and theming given as examples above are special cases, which have dedicated support in CSS (pseudo-selector and variables) already. But what would you suggest for specialising a style of a web component depending on its ancestor when both web components are in a single library?

This has been addressed by cascading before Shadow DOM and `host-context` made it available among web components. When a big widget is exposed as a web component, it will not mater, because such web component is not supposed to be affected by the rest of the page But what about web components in UI libraries, which are intended to be used as a composite of nested elements?

## Example

Let us have three levels of heading (block) elements:

```html
<e-h1>Heading 1</e-h1>
<e-h2>Heading 2</e-h2>
<e-h3>Heading 3</e-h3>
```

Styled by following stylesheets in their shadow roots:

```css
/* e-h1, e-h2 and e-h3 */
:host {
  display: block;
  line-height: 1.2;
  margin: 0.75rem 0.5rem;
  font-weight: 500;
}

:host { font-size: 1.9rem } /* e-h1 only */
:host { font-size: 1.6rem } /* e-h2 only */
:host { font-size: 1.3rem } /* e-h3 only */
```

And rendered like this:

![Bildschirmfoto 2021-05-28 um 13 22 59](https://user-images.githubusercontent.com/733193/119978250-b1562580-bfb9-11eb-99c4-23e3d58a9eeb.png)

Then, let us have an inline element for a small text:

```html
<p>This is a normal text. <e-small>This is a small text.</e-smalll></p>
```

Styled by following stylesheet in its shadow root:

```css
:host { font-size: 0.75em } /* e-small */
```

And rendered like this:

![Bildschirmfoto 2021-05-28 um 13 29 02](https://user-images.githubusercontent.com/733193/119978308-c337c880-bfb9-11eb-9398-b757e9bcabe3.png)

Finally, let us have a subheading for each of the three levels of heading elements, implemented by specialising the small-text element:

```html
<e-h1>Heading 1 <e-small>Subheading</e-small></e-h1>
<e-h2>Heading 2 <e-small>Subheading</e-small></e-h2>
<e-h3>Heading 3 <e-small>Subheading</e-small></e-h3>
```

Styled by adding the following styles to its shadow root:

```css
/* e-small */
:host { font-size: 0.75em }

:host-context(e-h1), :host-context(e-h2), :host-context(e-h3) {
  display: block;
  margin-top: -0.25rem;
}
```

And rendered like this:

![Bildschirmfoto 2021-05-28 um 13 22 32](https://user-images.githubusercontent.com/733193/119979130-d1d2af80-bfba-11eb-8195-8f3ddbd8b81a.png)

## Alternatives

If `host-context` is bad practice, how to avoid the need for cascading? Neither of the options below, that I was able to come up with, is without serious problems.

### Dedicated Elements

Instead of overriding the style for a specific ancestor, dedicated descendants can be introduced, for example:

```html
<e-h1>Heading 1 <e-sub-h1>Subheading</e-sub-h1></e-h1>
<e-h2>Heading 2 <e-sub-h2>Subheading</e-sub-h2></e-h2>
<e-h3>Heading 3 <e-sub-h3>Subheading</e-sub-h3></e-h3>
```

Increases the web component count unnecessarily, because `e-sub-h*` is obviously a child of a `e-h*`. Allows wrong using by putting `e-sub-h2` to `e-h1` or other combinations.

### Additional Attributes

Instead of overriding the style for a specific ancestor, the specifics can be represented by attributes, for example:

```html
<e-h1>Heading 1 <e-small heading=1>Subheading</e-small></e-h1>
<e-h2>Heading 2 <e-small heading=2>Subheading</e-small></e-h2>
<e-h3>Heading 3 <e-small heading=3>Subheading</e-small></e-h3>
```

Increases the verbosity unnecessarily, because `e-small` is obviously a child of a `e-h*`. Allows wrong using by using `heading=2` withing `e-h1` or other combinations.

### Extra Stylesheet

Instead of overriding the style for a specific ancestor, the style override can be applied from the outer document, if it affects only the host element for example:

```html
<e-h1>Heading 1 <e-small>Subheading</e-small></e-h1>
<e-h2>Heading 2 <e-small>Subheading</e-small></e-h2>
<e-h3>Heading 3 <e-small>Subheading</e-small></e-h3>
```

```css
e-h1 e-small, e-h2 e-small, e-h3 e-small {
  display: block;
  margin-top: -0.25rem;
}
```

Unexpected, requiring a global stylesheet to be imported in addition to the encapsulated stylesheets within the web components.

-- 
GitHub Notification of comment by prantlf
Please view or discuss this issue at https://github.com/w3c/csswg-drafts/issues/1914#issuecomment-850495924 using your GitHub account


-- 
Sent via github-notify-ml as configured in https://github.com/w3c/github-notify-ml-config

Received on Friday, 28 May 2021 15:24:41 UTC