@dbmb
Верстка just for fun

Как правильно в компоненте обрабатывать события с документом?

Доброго времени суток!

Только начал разбираться в реакте и вообще в компонентной разработке и возникла небольшая сложность.
На данный момент есть такой компонент, это в целом вся верхняя шапка (не уверен, верное ли это решение).
Суть в том, что нужно отслеживать ресайз окна и скроллинг для смены класов у шапки, единственное, что пришло в голову, это то, что тут представлено. Верно это или есть более удобные способы реализации данного функционала?

PS на нейминг классов стилей не обращайте внимания, буду после рефакторить.
class Header extends Component {
    constructor() {
      super();
      this.state = {
          headerClass: headerClass(),
          headerSticky: headerSticky()
      }
    };

    render() {
        const headerStateClass = this.state.headerClass;
        const headerStickyClass = this.state.headerSticky;
        const headerClasses = headerStateClass + headerStickyClass;

        return (
            <div className={headerClasses}>
                {window.onresize=()=>{this.setState({headerClass: headerClass()})}}
                {window.onscroll=()=>{this.setState({headerSticky: headerSticky()})}}
                <Grid>
                    <Row>
                        <Col sm={2} xs={6}><img src={logo} className="header-logo" alt=""/></Col>
                        <Col sm={10} xsHidden={true}>
                            <nav className="header-nav">
                                {header_links.map((anchor) => (
                                    <a href={anchor.link}>{anchor.name}</a>
                                ))}
                            </nav>
                        </Col>
                    </Row>
                </Grid>
            </div>
        );
    };
}
  • Вопрос задан
  • 54 просмотра
Решения вопроса 1
rockon404
@rockon404 Куратор тега React
Frontend Developer
Как-то так для скролла:
class Header extends Component {
  state = {
    headerClass: headerClass(),
    headerSticky: headerSticky(),
  };

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

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

  handleScroll = e => {
    this.setState({
      headerSticky: headerSticky(),
    });
  };

  render() {
    ...
  }
}


Для обработки ресайза лучше использовать applyContainerQuery из react-container-query:

import { applyContainerQuery } from 'react-container-query';
import { First, Second, Wrapper } from '../somePlace';

const myQuery = {
  hasMinWidth: {
    minWidth: 1024,
  },
};

class MyComponent extends Component {
  ...
  render() {
    const {
      containerQuery: { hasMinWidth },
    } = this.props;

    return (
      <Wrapper>
        {hasMinWidth ? <First /> : <Second />}
      </Wrapper>
    );
  }
}

export default applyContainerQuery(MyComponent, myQuery);


Так вы сможете обрабатывать ресайз во всем приложении.

Вы, конечно, можете повесить слушателя как в случае со scroll, но лучше разрулить все это с помощью applyContainerQuery так как один слушатель будет менять все компоненты приложения. Ну или можете попробовать свою реализацию этой утилиты написать.
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы