Created
November 15, 2016 19:29
-
-
Save nathanlogan/941f296aee7f3fa59689666382101d9f to your computer and use it in GitHub Desktop.
Emulate URL anchor page scroll functionality in a React component
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React, { Component } from 'react' | |
class MyTopLevelComponent extends Component { | |
componentDidMount () { | |
this.scrollToHashId() | |
} | |
componentDidUpdate () { | |
this.scrollToHashId() | |
} | |
// emulate URL anchor page scroll functionality | |
scrollToHashId () { | |
const removeHash = this.removeHash | |
// get URL hash (minus the hash mark) | |
const hash = window.location.hash.substring(1) | |
// if there's a hash, scroll to that ID | |
if (hash && hash.length) { | |
// setTimeout and requestAnimationFrame help ensure a true DOM repaint/reflow before we try to scroll | |
// - reference: http://stackoverflow.com/a/34999925 | |
setTimeout( | |
window.requestAnimationFrame(function () { | |
const el = document.getElementById(hash) | |
el.scrollIntoView() | |
// clean up the hash, so we don't scroll on every prop update | |
removeHash() | |
}), | |
0 | |
) | |
} | |
} | |
// borrowed from http://stackoverflow.com/questions/1397329/how-to-remove-the-hash-from-window-location-with-javascript-without-page-refresh/5298684#5298684 | |
removeHash () { | |
const loc = window.location | |
const hist = window.history | |
// use modern browser history API | |
if (hist && 'pushState' in hist) { | |
hist.replaceState('', document.title, loc.pathname + loc.search) | |
// fallback for older browsers | |
} else { | |
// prevent scrolling by storing the page's current scroll offset | |
const scrollV = document.body.scrollTop | |
const scrollH = document.body.scrollLeft | |
loc.hash = '' | |
// restore the scroll offset, should be flicker free | |
document.body.scrollTop = scrollV | |
document.body.scrollLeft = scrollH | |
} | |
} | |
render () { | |
<p>Render here...</p> | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment