Как динамически отобразить элемент после прокрутки до определенной позиции на странице? - PullRequest
1 голос
/ 18 апреля 2020

Я бы хотел, чтобы мой компонент "emailForm" отображался на моем Navbar после того, как пользователь прокрутил до начала раздела "laun dry", кто-нибудь знает, как это сделать?

Я пытался {window.scrollY > 500px ? EmailForm : "" } Но это не работает, я еще не очень знаком с реакцией, так что, может быть, вы могли бы помочь мне найти правильный метод для его достижения?

Контейнер:

<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>

import React, {Component} from 'react';


// Components
import Section from '../components/styledComponents/section';
import EmailForm from "../components/emailForm"
import Navbar from './containers/navbar';

export default class Individuals extends Component {


	render() {
		const { iconStyle } = this;
		return (
      <NavBar/>
			<main className="individuals">
				{/*Header section*/}
				<Section height="100vh" usedScreen="84px" className="your-laundromat-connected">
							<div className="title">
								<h1>
									Title</span>.
								</h1>
							</div>
						</div>
						<div className="subscribe-container">
						<div className="catchphrase-input">Prévenez-moi :</div>
						<EmailForm/>
						</div>
					</div>
				</Section>

				{/*Laundry section*/}
				<div className="container-laverie">
				<h2>Votre temps est précieux. Utilisez-le autrement.</h2>
                <p>Finie l'attente interminable à la laverie... grâce à l'application Lavigo vous reprenez le contrôle sur votre emploi du temps.</p>
					{/* </div>	 */}
				</div>
			</main>

		);
	}
}

Компонент NavBar:

<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>

import React from 'react';
import INavbarState from '../containers/interfaces/Inavbar';
//Librairies
import $ from 'jquery'
import EmailForm from '../components/emailForm'


export default class Individuals extends React.PureComponent<{}, INavbarState | any> {
	constructor(props: INavbarState | any) {
		super(props);
		this.state = {
		  showMenu: false,
		  scrollTop: true
		};
	}

	componentDidMount() {
		const that = this;
		let $win = $(window);
	
		$win.scroll(function () {
		  if ($win.scrollTop() == 0) {
			if (!that.state.scrollTop) {
			  that.setState({ scrollTop: true })
			}
		  } else {
			if (that.state.scrollTop) {
			  that.setState({ scrollTop: false })
			}
		  }
		});

		if(window.innerWidth <= 1024)
		{
		  that.setState({showMenu:false})
			// hide menubar
		}else{
		  that.setState({showMenu:true})
		   // show menubar
		}

	  window.onresize = function(event:any) {
		if(window.innerWidth <= 1024)
		{
		  that.setState({showMenu:false})
			// hide menubar
		}else{
		  that.setState({showMenu:true})
		   // show menubar
		}

	   if (window.scrollY > 1000) {

	   }  
	  };



	  ontoggle = () => {
		if(window.innerWidth <= 1024)
		  {
			this.setState({ showMenu: !this.state.showMenu })
			  // hide menubar
		  }else{
			this.setState({showMenu:true})
			 // show menubar
		  }
	  }
	}

	render() {
	return (
		<nav className="nav">
			<div className="d-flex align-items-center">
				<div className="container-email">
				<EmailForm/> 
				</div>
			</div>
		</nav>
	);
  };
}

Ответы [ 3 ]

1 голос
/ 18 апреля 2020

Здравствуйте, проверьте этот ScrollExample и ScrollChild Component. Я использовал ScrollChild в ScrollExample Component. При прокрутке вниз до 200 на экране появится компонент ScrollChild.

Компонент ScrollExample

import * as React from "react";
import ScrollChild from "./ScrollChild";

export default class ScrollExample extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
            isChildActive: false
        }
    }

    componentDidMount() {
        window.addEventListener('scroll', this.handleScroll);
    }

    componentWillUnmount() {
        window.removeEventListener('scroll', this.handleScroll);
    }

    handleScroll = (event) => {
        let scrollTop = window.scrollY;

        if (scrollTop > 200)
            this.setState({isChildActive: true});
        else
            this.setState({isChildActive: false});
    };

    render() {
        return (
            <div style={{height: 2000}}>
                Scroll down to show the EmailForm
                {
                    this.state.isChildActive ? <ScrollChild/> : null
                }
            </div>
        );
    }
}

Компонент ScrollChild

import React, {useEffect, useState} from 'react';

function ScrollChild(props) {
    return (
        <div style={{backgroundColor: '#1569C7', color: '#ffffff', width: 500, marginTop: 300, padding: 20}}>
            THIS IS A DUMMY TEXT
            <h1>How to dynamically render an element after scrolling to a certain position in a page?</h1>

            I would like my "emailForm" component to render on my Navbar after user scrolled to beginning of
            "laundry section", does someone know how to do that?

            I tried window.scrollY > 500px ? EmailForm : "" But it doesn't work, I am not very familiar yet with
            react so maybe you could help me figure out the right method to achieve it?

            I would like my "emailForm" component to render on my Navbar after user scrolled to beginning of
            "laundry section", does someone know how to do that?

            I tried window.scrollY > 500px ? EmailForm : "" But it doesn't work, I am not very familiar yet with
            react so maybe you could help me figure out the right method to achieve it?

            I would like my "emailForm" component to render on my Navbar after user scrolled to beginning of
            "laundry section", does someone know how to do that?

            I tried window.scrollY > 500px ? EmailForm : "" But it doesn't work, I am not very familiar yet with
            react so maybe you could help me figure out the right method to achieve it?

            I would like my "emailForm" component to render on my Navbar after user scrolled to beginning of
            "laundry section", does someone know how to do that?

            I tried window.scrollY > 500px ? EmailForm : "" But it doesn't work, I am not very familiar yet with
            react so maybe you could help me figure out the right method to achieve it?
        </div>
    );
}

export default ScrollChild;
0 голосов
/ 18 апреля 2020

Каждый раз, когда ваше состояние изменяется, оно вызывает рендеринг вашего компонента. Тем не менее, в вашем рендере ничего не изменится, потому что ваш рендеринг не зависит от this.state.scrollTop

. Чтобы исправить это, вам нужно сделать две вещи: 1. Обновить состояние, когда пользователь прокручивает порог (500px). ) 2. Используйте это новое значение состояния в вашем методе render() для повторного рендеринга компонента.

Я создал пример, где я изменяю прозрачность формы при изменении this.state.showEmailForm. Вы можете увидеть и ниже пример:

class App extends React.Component {
  constructor(props) {
super(props);
this.state = {
  showEmailForm: false,
};
  }

  componentDidMount = () => {
window.addEventListener("scroll", this.onScroll);
  };

  componentWillUnmount = () => {
window.removeEventListener("scroll", this.onScroll);
  };

  onScroll = () => {
this.setState({
  showEmailForm: window.scrollY > 500,
});
  };

  render() {
return (
  <div className="app">
    <p>
      {" "}
      Lorem ipsum dolor sit amet, consectetur adipiscing elit.Sed aliquet
      iaculis tellus id faucibus.Sed pellentesque sit amet tortor a
      mattis.Nullam ligula ante, condimentum eget ipsum vitae, fringilla
      consequat lorem.Aliquam vitae enim sem.Morbi consequat quam vel
      faucibus blandit.Fusce tempus fringilla neque sit amet eleifend.Nullam
      enim augue, facilisis a vehicula id, malesuada ut sapien.Curabitur vel
      dui ut risus placerat eleifend.Maecenas pulvinar magna ante, a congue
      nibh laoreet id.In consectetur viverra ligula, a mattis dolor blandit
      id.Aliquam ante massa, sollicitudin eget augue id, malesuada fringilla
      sem.Sed viverra pretium dignissim.Morbi ut volutpat ante, sed
      tincidunt quam.Praesent placerat, ipsum commodo venenatis sodales,
      tellus ante pellentesque ante, ac ultrices massa velit et velit.{" "}
    </p>
    <form
      style={{
        opacity: this.state.showEmailForm ? 1 : 0,
      }}
    >
      <label>
        Name <br />
        <input type="text" />
      </label>

      <label>
        Email <br />
        <input type="email" />
      </label>

      <input type="submit" value="Submit" />
    </form>
  </div>
);
  }
}

const rootElement = document.querySelector("#container");
ReactDOM.render(<App />, rootElement);
.app {
  height: 1000vh;
  background: palevioletred;
  padding: 1em;
  display: flex;
}

p {
  font-size: 2em;
  width: 50%;
}

input {
  display: block;
}

label {
  font-weight: bold;
}

form {
  padding: 1em;
  position: fixed;
  top: 1em;
  right: 1em;
  transition: opacity 0.5s;
}
<div id="container"></div>

<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>
0 голосов
/ 18 апреля 2020

У меня сейчас нет примера кода, но вы можете сделать что-то вроде этого: При прокрутке вы можете проверить, видим ли элемент (с позицией и позицией прокрутки). Если это так, вы можете сделать jQuery анимацию

...