Nicer Anchors
If you've ever written an FAQ or long-body-format web page, you'll undoubtedly have used anchor tags for deep-linking.
Generally we use href="much-link.htm"
every day for hyperlinks to other pages, but we'll also link to headings or sections of our own body when it is called for; href="#wow"
.
There's a small aesthetic issue when using href="#so-anchor"
though, and that's to do with the way browsers handle it; they move the top of the element exactly to the top of the viewport — as demonstrated below.
See the Pen heading-anchor-bad by Simon Goellner (@simeydotme) on CodePen.
You wouldn't put your header against the top of the page normally, so why do it when deep-linking?
It's also exacerbated or just unusable if we have any kind of fixed-header. So the general way people try to get around this aesthetic issue is by using javascript
to smooth-scroll the element in to view and then scroll up a little bit more with a calculation.
I propose a method without any javascript, see below;
See the Pen heading-anchor-gooder by Simon Goellner (@simeydotme) on CodePen.
How?
We'll use pseudo-elements and pseudo-classes to apply a "padding" above the currently targetted anchor.
Firstly let's make use of the :target
pseudo-class which allows us to style any element which has the same href="#"
as the hash in the url. It's available from IE9 as shown on caniuse
.anchor:target {}
We then use this to append a pseudo-element to the anchor which will give us a set amount of space above the anchor:
.anchor:target:before {
/* first we need to give it layout */
content: "";
display: block;
/* then dimensions */
height: 1em;
margin-top: -1em;
width: 0;
}
Now the 1em
value is up to you, I find it works nice as it's always proprtional to the heading size. We also use width: 0;
so that the browser doesn't draw a nasty outline
around the pseudo-element when we're focussed on it. Finally margin-top: -1em;
is used to remove the extra whitespace created above the heading.
such attract.
Why not go one step further and inspect the code for this blog's headings — you'll see the :target
being used to paint a fancy icon and change the colour of headings. Try it out by clicking here.