<!--
STICKY POSITIONING
A complete(?) explanation.
-->
<div>
<h1>Sticky positioning</h1>
<p>Sticky positioning is a weird amalgam of relative positioning and staying fixed in its scrollable parent (or ancestor). The <code>top, right, bottom, left</code> properties are calculated relative to the scrollable parent <em>if</em> the element can sit against that edge of the scrollable parent.</p>
<p>Having a scrollable parent is required for sticky positioning to work. If at no point does the user scroll through the parent, the sticky positioning will not work.
</div>
<section>
<h2>Vertically sticky to the top</h2>
<p>Below is an example demonstrating an element that is set to stick to the top of the scrollable parent and move in 1 rem from the left side. Review the CSS <code>.sticky</code>, <code>.to_top</code> and <code>.one_rem_left</code> classes for further comments/explanation.</p>
<p>Because this element connects with the top and left corner of the scrollable parent while scrolling you can use <code>top</code>/<code>left</code> properties in this case.</p>
<div class="scrollable_container">
<div class="tall_container">
<p class="box">This box is <em>not</em> sticky.</p>
<p class="sticky to_top one_rem_left">This box is sticky.</p>
</div>
</div>
</section>
<section>
<h2>Vertically sticky to the bottom</h2>
<p>Below is an example demonstrating an element that is set to stick to the bottom of the scrollable parent. Review the CSS <code>.sticky</code> and <code>.to_bottom</code> classes for further comments/explanation.</p>
<p>Because this element connects with the bottom and left corner of the scrollable parent while scrolling you can use <code>bottom</code>/<code>left</code>/<code>top</code> properties in this case.</p>
<div class="scrollable_container">
<div class="tall_container">
<p class="box">This box is <em>not</em> sticky.</p>
<p class="box">This box is <em>not</em> sticky.</p>
<p class="box">This box is <em>not</em> sticky.</p>
<p class="box">This box is <em>not</em> sticky.</p>
<p class="sticky to_bottom">This box is sticky.</p>
<p class="box">This box is <em>not</em> sticky.</p>
<p class="box">This box is <em>not</em> sticky.</p>
</div>
</div>
</section>
<section>
<h2>Horizontally sticky to the left</h2>
<p>Below is an example demonstrating an element that is set to stick to the left of the scrollable parent. Review the CSS <code>.sticky</code> and <code>.to_left</code> classes for further comments/explanation.</p>
<p>Because this element connects with the bottom and left corner of the scrollable parent while scrolling you can use <code>bottom</code>/<code>left</code> properties in this case.</p>
<div class="scrollable_container">
<div class="wide_container">
<p class="box">This box is <em>not</em> sticky.</p>
<p class="sticky to_left">This box is sticky.</p>
</div>
</div>
</section>
<section>
<h2>Horizontally sticky to the right</h2>
<p>Below is an example demonstrating an element that is set to stick to the right <em>and</em> left of the scrollable parent. Review the CSS <code>.sticky</code> and <code>.to_right</code> classes for further comments/explanation.</p>
<p>Because this element connects with the left and right edges of the scrollable parent while scrolling you can use <code>left</code>/<code>right</code> properties in this case. Note that because the scrollable parent is the same height as the sticky element the <code>bottom</code>/<code>top</code> properties will have no effect.</p>
<div class="scrollable_container">
<div class="wide_container">
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="sticky to_right to_left inline_block">This box is sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
<p class="box inline_block">This box is <em>not</em> sticky.</p>
</div>
</div>
</section>
xxxxxxxxxx
/* Here we create a fixed height and width container that has scrolling enabled to allow the sticky effect to be shown. */
.scrollable_container {
margin-top: 1rem;
max-height: 12rem;
max-width: 24rem;
border: 1px solid black;
overflow: scroll; /* Setting overflow to scroll means that any children that are too large for the .scrollable_container will allow the user to scroll along the larger axis. */
}
/* Here we have created some containers to put our sticky elements in. In this case a 'tall' and 'wide' container which are too big for their parent, meaning the content has to be scrolled. */
.tall_container {
min-height: 40rem;
border: 2px solid red; /* A red border has been added for visibility. */
}
.wide_container {
min-width: 100rem;
border: 2px solid red;
}
.box {
height: 5.5rem;
width: 5.5rem;
margin: 0;
padding: 0.25rem;
background-color: #DDD;
border: 1px solid white;
}
.inline_block {
display: inline-block;
}
/* This is where we specify the 'sticky' positioning */
.sticky {
position: sticky;
width: 5.5rem;
height: 5.5rem;
margin: 0;
padding: 0.25rem;
background: blue;
color: white;
border: 1px solid white;
}
/* These specify different points the box should stick to */
.sticky.to_top {
top: 0;
}
.sticky.one_rem_left {
left: 1rem;
}
.sticky.to_left {
left: 0;
}
.sticky.one_rem_bottom {
bottom: 1rem;
}
.sticky.to_bottom {
bottom: 0;
}
.sticky.to_right {
right: 0;
}
/* Some styling specifically for these additional explanations */
* {
box-sizing: border-box;
}
body {
margin: 0 auto;
padding-bottom: 6rem;
max-width: 40rem;
font-family: sans-serif;
}
h2 {
margin-top: 4rem;
}
li {
padding-bottom: 0.5rem;
}
figure {
margin: 6rem 0 0;
}
figcaption {
margin-top: 0.75rem;
position: relative;
z-index: 1;
text-shadow: 0.05rem 0.05rem 0.05rem white;
}
.further-reading {
margin-top: 10rem;
padding-bottom: 2rem;
}
img {
height: auto;
max-width: 100%;
display: block;
}
This Pen doesn't use any external CSS resources.
This Pen doesn't use any external JavaScript resources.