Why including padding to the nearest scrollport changes the threshold position of the sticky element where it sticks?
As per my understanding, for Sticky Positioning Scheme, the CSS spec defines that the insets applied to an sticky element is relative to the edges of the nearest scrollport which then forms the Sticky View Rectangle (SVR). And so, the edges of the SVR determines the threshold at which the sticky element actually sticks.
Sticky positioning is similar to relative positioning except the offsets are automatically calculated in reference to the nearest scrollport. For a sticky positioned box, the inset properties represent insets from the respective edges of the nearest scrollport, defining the sticky view rectangle used to constrain the box’s position.
Also, the CSS spec defines scrollport and nearest scrollport as follows:
The visual “viewport” of a scroll container (through which the scrollable overflow area can be viewed) coincides with its padding box, and is called the scrollport. A box’s nearest scrollport is the scrollport of its nearest scroll container ancestor.
The fillers in the code are just there so that the sticky and scrolling behaviour of the .sticky
element can be clearly seen.
Consider the following code snippet:
Show code snippet
For the above code, as the top
and bottom
insets are set to 0px
, the edges of the SVR coincides with the scrollport. Hence, when the threshold is met, the .sticky
element sticks until either it reaches its normal position (for bottom: 0px
) or it reaches the boundary of its container (for top: 0px
) after which, it scrolls with its container.
Now, consider the following snippet with padding
added to the .scrollport
element.
Show code snippet
As one can notice that when top and bottom padding
are added to the .scrollport
, the .sticky
element doesn't stick at the given threshold.
The edges of the SVR do not coincide with the edges of the scrollport. The top padding pushes down the top edge of the SVR whereas the bottom padding pushes the bottom edge of the SVR up.
As quoted already above, to form the SVR, the insets are applied relative to the respective edges of the nearest scrollport and the scrollport coincides with the padding box of the scroll container.
This means that the added padding to the scrollport should not affect the position of the SVR. In either cases, as top: 0px
and bottom: 0px
, the SVR position should coincide with the scrollport (or in other words, its padding box).
Instead, the insets are applied after taking padding into account. Hence, the insets effectively positions the SVR relative to the content box of the scrollport and not to the padding box of the scrollport.
Question
So, isn't this behaviour in the Sticky Positioning Scheme of forming the SVR contradicts what actually is stated in the CSS spec? Or is it just that I am interpreting the spec wrongly and this behaviour is expected? If this is the case, can anyone please explain where I am going wrong? Also, is it documented anywhere in the spec?
Answers
The behavior you're observing with sticky positioning and padding in CSS can seem counterintuitive, but it is indeed consistent with the CSS specifications.
Let's clarify a few points:
-
Scrollport vs. Padding Box: According to the CSS specifications, the scrollport of a scroll container coincides with its padding box. This means that any padding applied to the scroll container directly affects the scrollport, including the positioning of sticky elements within it.
-
Insets Relative to Scrollport: The CSS spec defines that the insets applied to a sticky element are relative to the edges of the nearest scrollport. However, it's important to note that this is after considering any padding applied to the scroll container.
-
Sticky View Rectangle (SVR): The SVR is formed based on the edges of the nearest scrollport, which includes any padding. Therefore, if padding is present, the SVR will be adjusted accordingly.
In your example, when padding is added to the .scrollport
element, it affects the position of the SVR because the padding box of the scroll container defines the scrollport. This aligns with the CSS spec's definition.
To address your questions:
-
Contradiction with CSS Spec: No, the behavior you're observing is consistent with the CSS specifications. The spec defines how sticky positioning should interact with scroll containers and their padding.
-
Interpretation of the Spec: Your interpretation of the spec seems correct. The insets applied to a sticky element are indeed relative to the edges of the nearest scrollport, but this includes any padding applied to the scroll container.
-
Documentation in the Spec: The behavior you're observing may not be explicitly documented in the CSS spec in the way you've described it. However, the definitions of scrollport, sticky positioning, and the interaction with padding are all consistent with the behavior you've observed.
In conclusion, the behavior you're observing with sticky positioning and padding aligns with the CSS specifications, which define how these features should interact. While it may seem unexpected at first, understanding the relationship between scrollports, padding, and sticky elements can help clarify the behavior.