scrollIntoView Scrolls just too far

Position Anchor By Absolute Method

Another way to do this is to position your anchors exactly where you want on the page rather than relying on scrolling by offset. I find it allows better control for each element (eg. if you want a different offset for certain elements), and may also be more resistant to browser API changes/differences.

<div id="title-element" style="position: relative;">
  <div id="anchor-name" style="position: absolute; top: -100px; left: 0"></div>
</div>

Now the offset is specified as -100px relative to the element. Create a function to create this anchor for code reuse, or if you are using a modern JS framework such as React do this by creating a component that renders your anchor, and pass in the anchor name and alignment for each element, which may or may not be the same.

Then just use :

const element = document.getElementById('anchor-name')
element.scrollIntoView({ behavior: 'smooth', block: 'start' });

For smooth scrolling with an offset of 100px.


Smooth scroll to the proper position (Outdated)

There is the better answer which uses scroll-margin and scroll-padding css rules. getBoundingClientRect in this solution triggers additional forced layout and may cause unnecessary performance issues.

Get correct y coordinate and use window.scrollTo({top: y, behavior: 'smooth'})

const id = 'profilePhoto';
const yOffset = -10; 
const element = document.getElementById(id);
const y = element.getBoundingClientRect().top + window.pageYOffset + yOffset;

window.scrollTo({top: y, behavior: 'smooth'});