Skip to content

Commit

Permalink
[css-scroll-snap-2] Specify scroll-start-target (#10227)
Browse files Browse the repository at this point in the history
* Specify scroll-start-target

This adds details to the scroll-snap-2 spec[1] to specify
scroll-start-target.

[1] https://drafts.csswg.org/css-scroll-snap-2

* [css-scroll-snap-2]] Specify scroll-start-target

* [css-scroll-snap-2] Specify scroll-start-target

Define initial scroll position precedence in css-overflow-3.
De-vaguify post-first layout scroll-start-target & point to document
update process.
Extract scroll-view position algorithm for standalone use.

* [css-scroll-snap-2] Specify scroll-start-target

Remove slight duplication.

* [css-scroll-snap-2] Specify scroll-start-target

Replace scroll-view with scroll-into-view.
Mention and link css properties that change initial scroll position.

---------

Co-authored-by: David Awogbemila <David Awogbemila>
Co-authored-by: David Awogbemila <awogbemila@chromium.org>
Co-authored-by: Tab Atkins Jr <jackalmage@gmail.com>
  • Loading branch information
3 people committed Jun 21, 2024
1 parent c021927 commit 2c40247
Show file tree
Hide file tree
Showing 4 changed files with 99 additions and 67 deletions.
3 changes: 3 additions & 0 deletions css-align-3/Overview.bs
Original file line number Diff line number Diff line change
Expand Up @@ -1173,6 +1173,9 @@ Overflow and Scroll Positions</h3>
of the <a>scroll container</a>
satisfies the [[#alignment-values|expected alignment]]
of the <a>alignment subject</a> and <a>alignment container</a>.
However, the [[css-scroll-snap-2#scroll-start-target-with-place-content|scroll-start-target]]
property, when present, overrides the <a>content-distribution properties</a>
in determining the <a>initial scroll position</a>.

Note: The presence of scrollbars can change the size of the [=scroll container’s=] content box,
and thus the size of the [=alignment container=]
Expand Down
4 changes: 2 additions & 2 deletions css-overflow-3/Overview.bs
Original file line number Diff line number Diff line change
Expand Up @@ -341,8 +341,8 @@ Scrolling Overflow</h3>
is typically dependent on the [=scroll container=]’s [=writing mode=],
and, unless otherwise specified,
coincides with its [=scroll origin position=].
However, the 'align-content' and 'justify-content' properties [[!CSS-ALIGN-3]]
can be used to change the [=initial scroll position=],
However, the 'align-content' and 'justify-content' properties [[!CSS-ALIGN-3]] as well as the
'scroll-start-target' property [[!CSS-SCROLL-SNAP-2]] can be used to change the [=initial scroll position=],
see [[css-align-3#overflow-scroll-position]].

A <dfn export>scroll position</dfn> is a particular alignment
Expand Down
137 changes: 77 additions & 60 deletions css-scroll-snap-2/Overview.bs
Original file line number Diff line number Diff line change
Expand Up @@ -58,13 +58,13 @@ First Layout {#first-layout}

<!-- Big Text: examples

█████▌ █ █ ███▌ █ █ ████▌ █▌ █████▌ ███▌
█████▌ █ █ ███▌ █ █ ████▌ █▌ █████▌ ███▌
█▌ █ █ ▐█ ▐█ ██ ██ █▌ █▌ █▌ █▌ █▌ █▌
█▌ █ █ █▌ █▌ █▌█ █▐█ █▌ █▌ █▌ █▌ █▌
████ █ █▌ █▌ █▌ █ ▐█ ████▌ █▌ ████ ███▌
█▌ █ █ █▌ █▌ █▌█ █▐█ █▌ █▌ █▌ █▌ █▌
████ █ █▌ █▌ █▌ █ ▐█ ████▌ █▌ ████ ███▌
█▌ █ █ █████▌ █▌ ▐█ █▌ █▌ █▌ █▌
█▌ █ █ █▌ █▌ █▌ ▐█ █▌ █▌ █▌ █▌ █▌
█████▌ █ █ █▌ █▌ █▌ ▐█ █▌ █████ █████▌ ███▌
█████▌ █ █ █▌ █▌ █▌ ▐█ █▌ █████ █████▌ ███▌
-->

Motivating Examples {#examples}
Expand Down Expand Up @@ -227,37 +227,87 @@ Interaction with RTL and LTR</h4>
The 'scroll-start-target' property {#scroll-start-target}
-------------------------------------------

<h4 dfn export id="initial-scroll-target">
Initial scroll target</h4>

The [=initial scroll target=] of a <a>scroll container</a> |scrollcontainer|
is an element or pseudo-element
whose 'scroll-start-target'property is non-''scroll-start-target/none''
and whose nearest <a>scroll container</a> is |scrollcontainer|.
When multiple such elements or pseudo-elements exist,
user-agents should select the one
which comes first in [=tree order=].
When no such element or pseudo-element exists,
|scrollcontainer|’s <a>initial scroll target</a> is null.

<div algorithm="determine the initial scroll position from an initial scroll target">
If the <a>initial scroll target</a> of a <a>scroll container</a> is not null,
it should be used to determine the <a>initial scroll position</a> of |scrollcontainer|
by running the following steps:

1. Let |target| be the <a>initial scroll target</a> for |scrollcontainer|.
1. Let |position| be the result of running the steps to
<a spec="cssom-view-1">determine the scroll-into-view position</a> of |target|
with <var ignore>behavior</var> set to "auto",
<var ignore>block</var> set to "start",
<var ignore>inline</var> set to "nearest",
and <var ignore>scrolling box</var> set to |scrollcontainer|.
1. Set |scrollcontainer|'s <a>initial scroll position</a> to |position|.
</div>


<h4 id="scroll-start-target-shorthand">
The scroll-start-target shorthand</h4>

<pre class="propdef shorthand">
Name: scroll-start-target
Value: [ none | auto ]{1,2}
Name: scroll-start-target
Value: [ none | auto ]
Initial: ''none''
Applies to: all elements
Inherited: no
Percentages: N/A
Computed Value: see individual properties
Animation type: none
</pre>

This property is a shorthand property that sets all of the scroll-start-target-* longhands in one declaration.
The first value defines the scroll starting point in the block axis,
the second sets it in the inline axis.
If the second value is omitted, it defaults to ''scroll-start-target/none''.

Values are defined as follows:

<dl dfn-type=value dfn-for="scroll-start-target, scroll-start-target-x, scroll-start-target-y, scroll-start-target-block, scroll-start-target-inline">
<dl dfn-type=value dfn-for="scroll-start-target, scroll-start-target-block, scroll-start-target-inline, scroll-start-target-x, scroll-start-target-y">
<dt><dfn>none</dfn>
<dd>Element is not a ''scroll-start-target''.
<dd>The element is not an [=initial scroll target=].
<dt><dfn>auto</dfn>
<dd>Element is used to calculate the 'scroll-start' position,
taking into account ''scroll-padding'' or ''scroll-margin'' ,
same as a ''scroll-snap'' target.
<dd>The element is potentially an [=initial scroll target=]
for its nearest [=scroll container=] ancestor.
</dl>

<h4 id="scroll-start-target-with-place-content">
Interaction with 'place-content'</h4>

If a [=scroll container's=] [=initial scroll position=]
is potentially set by both a [=content-distribution property=]
and by 'scroll-start-target' on a descendant,
'scroll-start-target' wins.

<!-- Big Text: :snapped
<h4 id="scroll-start-fragment-navigation">
Post-first layout arrivals</h4>

█▌ ███▌ █ █▌ ███▌ ████▌ ████▌ █████▌ ████▌
While the document is being [[html#updating-the-document|updated],
a <a>scroll container's</a> [=initial scroll target=] might arrive
after that <a>scroll container</a> has been laid out.
If this happens,
user agents should still scroll to the [=initial scroll target=]
unless the user agent has reason to believe
the user is no longer interested
in scrolling to the <a>initial scroll position</a>.


<!-- Big Text: :snapped

█▌ ███▌ █ █▌ ███▌ ████▌ ████▌ █████▌ ████▌
███▌ █▌ █▌ █▌ █▌ ▐█ ▐█ █▌ █▌ █▌ █▌ █▌ █▌ █▌
█▌ █▌ ██▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌
███▌ █▌▐█ █▌ █▌ █▌ ████▌ ████▌ ████ █▌ █▌
█▌ █▌ █▌ ██▌ █████▌ █▌ █▌ █▌ █▌ █▌
███▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌
█▌ ███▌ █▌ ▐▌ █▌ █▌ █▌ █▌ █████▌ ████▌
█▌ ███▌ █▌ ▐▌ █▌ █▌ █▌ █▌ █████▌ ████▌
-->

Styling Snapped Items {#styling-snapped}
Expand Down Expand Up @@ -300,13 +350,13 @@ Snap Events {#snap-events}

<!-- Big Text: events

█████▌ █▌ █▌ █████▌ █ █▌ █████▌ ███▌
█████▌ █▌ █▌ █████▌ █ █▌ █████▌ ███▌
█▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌
█▌ █▌ █▌ █▌ ██▌ █▌ █▌ █▌
████ ▐▌ █ ████ █▌▐█ █▌ █▌ ███▌
█▌ █▌ █▌ █▌ ██▌ █▌ █▌ █▌
████ ▐▌ █ ████ █▌▐█ █▌ █▌ ███▌
█▌ █ ▐▌ █▌ █▌ ██▌ █▌ █▌
█▌ ▐▌ █ █▌ █▌ █▌ █▌ █▌ █▌
█████▌ ▐█ █████▌ █▌ ▐▌ █▌ ███▌
█████▌ ▐█ █████▌ █▌ ▐▌ █▌ ███▌
-->

{{scrollsnapchange}} and {{scrollsnapchanging}} {#scrollsnapchange-and-scrollsnapchanging}
Expand Down Expand Up @@ -591,13 +641,13 @@ when the scrolling operation ends.

<!-- Big Text: Longhand

█▌ ███▌ █ █▌ ███▌ █▌ █▌ ███▌ █ █▌ ████▌
█▌ ███▌ █ █▌ ███▌ █▌ █▌ ███▌ █ █▌ ████▌
█▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ ▐█ ▐█ █▌ █▌ █▌ █▌
█▌ █▌ █▌ ██▌ █▌ █▌ █▌ █▌ █▌ █▌ ██▌ █▌ █▌ █▌
█▌ █▌ █▌ █▌▐█ █▌ █▌ ██▌ █████▌ █▌ █▌ █▌▐█ █▌ █▌ █▌
█▌ █▌ █▌ █▌ ██▌ █▌ █▌ █▌ █▌ █████▌ █▌ ██▌ █▌ █▌
█▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌ █▌
█████ ███▌ █▌ ▐▌ ███▌ █▌ █▌ █▌ █▌ █▌ ▐▌ ████▌
█████ ███▌ █▌ ▐▌ ███▌ █▌ █▌ █▌ █▌ █▌ ▐▌ ████▌
-->

Appendix A: Longhands {#longhands}
Expand Down Expand Up @@ -638,39 +688,6 @@ Flow-relative Longhands for 'scroll-start' {#scroll-start-longhands-logical}
Animation type: by computed value type
</pre>

...
Flow-relative Longhands for 'scroll-start-target' {#scroll-start-target-longhands-logical}
--------------------------------------------------------------------------

<pre class="propdef">
Name: scroll-start-target-block, scroll-start-target-inline
Value: auto | none
Initial: none
Applies to: all elements
Inherited: no
Logical property group: scroll-start-target
Percentages: n/a
Computed Value: either of the keywords "none" or "auto"
Animation type: not animatable
</pre>

...

Physical Longhands for 'scroll-start-target' {#scroll-start-target-longhands-physical}
----------------------------------------------------------------------

<pre class="propdef">
Name: scroll-start-target-x, scroll-start-target-y
Value: none | auto
Initial: none
Applies to: all elements
Inherited: no
Logical property group: scroll-start-target
Percentages: n/a
Computed value: either of the keywords "none" or "auto"
Animation type: not animatable
</pre>

...

Appendix B: Event Handlers {#event-handlers}
Expand Down
22 changes: 17 additions & 5 deletions cssom-view-1/Overview.bs
Original file line number Diff line number Diff line change
Expand Up @@ -1445,14 +1445,14 @@ The <dfn attribute for=Element>currentCSSZoom</dfn> attribute must return the

<h3 id=element-scrolling-members>{{Element}} Scrolling Members</h3>

To <dfn export>scroll a target into view</dfn> <var>target</var>, which is an <a for="/">Element</a> or <a>Range</a>,

To <dfn export>determine the scroll-into-view position</dfn> of a <var>target</var>, which is an <a for="/">Element</a> or <a>Range</a>,
with a scroll behavior <var>behavior</var>,
a block flow direction position <var>block</var>,
and an inline base direction position <var>inline</var>,
means to run these steps for each ancestor element or <a>viewport</a> that establishes
a <a>scrolling box</a> <var>scrolling box</var>, in order of innermost to outermost <a>scrolling box</a>:
an inline base direction position <var>inline</var>,
and a <a>scrolling box</a> <var>scrolling box</var>,
run the following steps:

1. If the {{Document}} associated with <var>target</var> is not <a>same origin</a> with the {{Document}} associated with the element or <a>viewport</a> associated with <var>scrolling box</var>, terminate these steps.
1. Let <var>target bounding border box</var> be the box represented by the return value of invoking Element's {{Element/getBoundingClientRect()}}, if <var>target</var> is an <a for="/">Element</a>, or Range's {{Range/getBoundingClientRect()}}, if <var>target</var> is a <a>Range</a>.
1. Let <var>scrolling box edge A</var> be the <a>beginning edge</a> in the <a>block flow direction</a> of <var>scrolling box</var>, and let <var>element edge A</var> be <var>target bounding border box</var>'s edge on the same physical side as that of <var>scrolling box edge A</var>.
1. Let <var>scrolling box edge B</var> be the <a>ending edge</a> in the <a>block flow direction</a> of <var>scrolling box</var>, and let <var>element edge B</var> be <var>target bounding border box</var>'s edge on the same physical side as that of <var>scrolling box edge B</var>.
Expand Down Expand Up @@ -1496,7 +1496,19 @@ a <a>scrolling box</a> <var>scrolling box</var>, in order of innermost to outerm
<dt>If <var>element edge D</var> is outside <var>scrolling box edge D</var> and <var>element width</var> is less than <var>scrolling box width</var>
<dd>Align <var>element edge D</var> with <var>scrolling box edge D</var>.
</dl>
1. Return <var>position</var>.


To <dfn export>scroll a target into view</dfn> <var>target</var>, which is an <a for="/">Element</a> or <a>Range</a>,
with a scroll behavior <var>behavior</var>,
a block flow direction position <var>block</var>,
and an inline base direction position <var>inline</var>,
means to run these steps for each ancestor element or <a>viewport</a> that establishes
a <a>scrolling box</a> <var>scrolling box</var>, in order of innermost to outermost <a>scrolling box</a>:

1. If the {{Document}} associated with <var>target</var> is not <a>same origin</a> with the {{Document}} associated with the element or <a>viewport</a> associated with <var>scrolling box</var>, terminate these steps.
1. Let <var>position</var> be the scroll position resulting from running the steps to <a>determine the scroll-into-view position</a> of <var>target</var> with <var>behavior</var> as the |scroll behavior|,
<var>block</var> as the |block flow position|, <var>inline</var> as the |inline base direction position| and <var>scrolling box</var> as the |scrolling box|.
1. If <var>position</var> is the same as <var>scrolling box</var>'s current scroll position, and <var>scrolling box</var> does not have an ongoing <a>smooth scroll</a>, then return.
1. <dl class=switch>
<dt>If <var>scrolling box</var> is associated with an element
Expand Down

0 comments on commit 2c40247

Please sign in to comment.