Intro
React-Router does not have built in functionality to handle Hash Links, also known as Anchor Links. Hash links navigate to a specific element on a page by targeting the element id.
Previously this issue was dealt with using a package called react-router-hash-link.
That package doesn’t appear to be compatible with react-router-v6 however.
Because i’m not a fan of installing unnecessary packages anyways, i’ve created a component that solves this issue.
Scrolling itself is provided by the native browser method Element.scrollIntoView()
I’ve created a Github repo for this component: github: Ncoughlin: ScrollToHashElement
So please check there to make sure you are getting the most recent version of this component, it’s possible there will be improvements on this over time.
Component
import { useMemo, useEffect } from "react";
import { useLocation } from "react-router-dom";
const ScrollToHashElement = () => {
let location = useLocation();
let hashElement = useMemo(() => {
let hash = location.hash;
const removeHashCharacter = (str) => {
const result = str.slice(1);
return result;
};
if (hash) {
let element = document.getElementById(removeHashCharacter(hash));
return element;
} else {
return null;
}
}, [location]);
useEffect(() => {
if (hashElement) {
hashElement.scrollIntoView({
behavior: "smooth",
// block: "end",
inline: "nearest",
});
}
}, [hashElement]);
return null;
};
export default ScrollToHashElement;
Installation
Just place this component anywhere in the application and it will work passively in the background.
import React from "react";
// components
import ScrollToHashElement from "./ScrollToHashElement";
import Header from "./Header";
import Content from "./Content";
const App = () => {
return (
<div className="grid">
<ScrollToHashElement />
<Header />
<Content />
</div>
);
};
export default App;
React-Router Links
You can create React-Router links as you normally would. For example a link to a hash element on the homepage would look like this
<Link to="/#delightful-visualization">Delightful Visualization</Link>
or this
<Link to="#delightful-visualization">Delightful Visualization</Link>
a sub page like this
<Link to="/about#story">Our Story</Link>
Scroll Behavior
Scroll behavior such as smooth scroll can be easily modified by changing the options in the useEffect portion of the component
hashElement.scrollIntoView({
behavior: "smooth",
// block: "end",
inline: "nearest",
});