Skip to content

[css-pseudo][css-break] ::nth-fragment(An+b) pseudo element #7517

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

Closed
johannesodland opened this issue Jul 20, 2022 · 2 comments
Closed

[css-pseudo][css-break] ::nth-fragment(An+b) pseudo element #7517

johannesodland opened this issue Jul 20, 2022 · 2 comments

Comments

@johannesodland
Copy link

https://drafts.csswg.org/css-pseudo-4/
https://www.w3.org/TR/css-break-3/
https://www.w3.org/TR/CSS21/visuren.html#line-box

Could it be possible to target and style the nth-fragment of an element?
I know this might be a pipe dream, but I'm registering an issue here in case it is will be feasible to implement.

span::nth-fragment(2) { ... };
span::nth-fragment(odd) { ... };
span::nth-fragment(-n +2) { ... };

Motivation

We use nth-child and nth-of-type to create variation between sibling elements. Usecases are vast, but vary from changing background colors in tables, to stagger animations and transitions. There is even a proposal to make sibling-index() and sibling-count() available to make expressing these variations and staggered animations more flexible.

It would be nice if we could be able to select fragments in a similar way, even though we would have to be very restrictive when it comes to which properties should be available to change and affect inheritance.

Animations on column or text run fragments could be staggered. Backgrounds and borders on elements with box-decoration-break: clone could be varied.

At the moment authors have no way of targeting individual fragments, and need to implement the fragmenting layout in js to be able to achieve these goals. There's a GreenSock plugin that does this.

Considerations

There are more than a few considerations if we were to allow some limited styling of fragments, but I hope they can be mitigated in some way:

  1. Loops
  2. box-decoration-break: slice
  3. inheritance
  4. getComputedStyle
  5. transforms
  6. inline-box

Loops

The first issue could be mitigated by limiting which properties can be changed. Properties like background* and opacity that doesn't inherit or affect layout should be less problematic.

box-decoration-break

I have a feeling that having different background, opacity and border-colors between box fragments when using box-decoration-break: slice could be problematic. If so, could allowed properties vary between fragmented boxes with box-decoration-break: clone and box-decoration-break: slice?

inheritance

Setting properties on the nth-fragment() would override properties on the breakable box, even if they were higher in the cascade. Thus 'breaking' the cascade. Maybe we can look to ::first-line for existing solutions?

getComputedStyle

There's an open question on what getComputedStyle on a fragmentation origin should return if box fragments can be styled.

transforms

Fragmentation occurs before transforms, so each fragment is transformed individually. Transforms that keep the fragment within the fragmentainer should not be problematic, but what should happen when it is transformed outside the fragmentainer? Fragments that are transformed to span multiple pages is specified to be sliced. But it would be great if fragments could be rendered outside the fragmentainer if they are fragmented into a column-box or a line-box.

inline-box

There's no syntax for selecting text nodes unless it is wrapped in an inline element.

<p>Some text <span> some more text </span></p>
/* this would select fragments of the p, and not fragments of the text run */
p::nth-fragment(odd) {}

/* this would select fragments of the inline span box if it spans multiple line boxes */
span::nth-fragment(odd) {}

/* do we need something like this to select fragments of the whole text run? */
p::text::nth-fragment(odd) {}

Prior art

::first-line is a pseudo-element that targets the first line-box of an inline flow. It might be quirky, but experience from specifying and implementing ::first-line could inform specifying pseudo elements for nth-fragments.

GreenSock has a plugin that splits lines into divs for easy animation.

Proposal

  • Add ::nth-fragment(An+B) pseudo element syntax to select and style fragments of a box. Syntax TBB.
  • Optionally add fragment-index() syntax to make values available for calculation.
/* span would circle between inherited background and lavender background */
span::nth-fragment(odd) {background-color: lavender; }

/* Stagger the second column animation */
section {
  columns: 2;
  &::nth-fragment(2) { animation-delay: 100ms; }
}

/* Stagger in all fragments */
section {
  column-width: 400px;
  &::nth-fragment(n) { animation-delay: calc(fragment-index() * 100ms); }
}

This is quite a bit to ask and there are many considerations, but I know there are some really smart people in the CSSWG and among the implementers that might see a way to solve some of the use-cases we would like to achieve.

@Loirooriol
Copy link
Contributor

See https://drafts.csswg.org/css-overflow-4/#fragment-pseudo-element

@johannesodland
Copy link
Author

See https://drafts.csswg.org/css-overflow-4/#fragment-pseudo-element

Thank you. 🙏🏻
Sorry for opening an issue for a selector that is already being specified.
Closing the issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants