I'm trying to make a footer banner show only when user scrolls down past the header, and hide it when user scrolls up to top. My idea of how to implement this is to add an event listener for scroll event in the top component of the page. Here's my current code. But it doesn't work:
componentDidMount() {
this.nv.addEventListener('scroll', this.handleScroll);
}
handleScroll(e) {
if(window.pageYOffset > 50 && window.pageYOffset < 900) {
console.log('scrolled');
this.setState({
showBanner: true,
});
} else {
this.setState({
showBanner: false,
});
}
}
The render method of the top component:
render() {
return (
<div ref={elem => this.nv = elem}>
<Header/>
<Body
userInfo={this.props.userInfo}
history={this.props.history}
/>
{
this.state.showBanner && <Banner/>
|| null
}
</div>
)
}
I don't see any logs and the setState
is apparently not called when scrolling.
Any suggestion on how I can accomplish the intended goal?
* UPDATE *
Changed componentDidMount
to add event listener on window, now it's working.
componentDidMount() {
window.addEventListener('scroll', this.handleScroll);
}
The reason is because you are trying to add an event listener to a ref that doesn't exist yet. componentDidMount
happens BEFORE the initial render. That means that the ref you assign in render hasn't been set yet.
You can use a ref callback and attach the event listener there:
applyRef = ref => {
this.vn = ref;
this.vn.addEventListener('scroll', this.handleScroll);
}
render() {
return (
<div ref={this.applyRef}>
<Header/>
<Body
userInfo={this.props.userInfo}
history={this.props.history}
/>
{
this.state.showBanner && <Banner/>
|| null
}
</div>
)
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With