3
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

React: Window Resize イベントで React Component のサイズ取得方法

Last updated at Posted at 2022-03-16

Window Resize イベントで React Component のサイズ取得方法

  • なかなかベストプラクティスに落ち着くことができなかったので、メモとして残しておきます。
  • 特に、_.debounce() でラップしないでうまく実装する方法がなかったのか。
  • もっと良い実装があれば、アップデートしていきます。

TL,DR;

  • resize イベントハンドラー利用します。
  • ref を通じて、getBoundingClientRect() でコンポーネントのサイズを取得します。
  • state にコンポーネントのサイズを格納していきます。
  • 無闇やたらとハンドラを呼び出したくないので、Lodash の debounce を使ってます。
    • ウィンドウ最大化ボタンのためにも実は debounce は必須。

Hook 形式でも書けるけど、とりあえず Class Component 形式で紹介します。

import React from 'react';
import _ from 'lodash';

class MyComponent extends React.Component {
  state = {
    size: {
      width: 0,
      height: 0,
    },
  };

  ref = React.createRef();

  handleWindowResize = _.debounce(() => {
    const size = this.ref.current.getBoundingClientRect();
    this.setState({ size });
  });

  componentDidMount() {
    this.handleWindowResize();
    window.addEventListener('resize', this.handleWindowResize);
  }

  componentWillUnmount() {
    window.removeEventListener('resize', this.handleWindowResize);
  }

  render() {
    const { size } = this.state;
    return (
      <div ref={this.ref}>
        Component size is {size.width} x {size.height}.
      </div>
    );
  }
}

Hook API を使った場合の Function Component の実装

import React from 'react';
import _ from 'lodash';

const MyComponent = () => {
  const ref = React.useRef(null);

  const [size, setSize] = React.useState({
    width: 0,
    height: 0,
  });

  const handleWindowResize = _.debounce(() => {
    const { width, height } = ref.current.getBoundingClientRect();
    setSize({ width, height });
  }, 100);

  React.useLayoutEffect(() => {
    handleWindowResize();                                                                                         
    window.addEventListener('resize', handleWindowResize);
    return () => window.removeEventListener('resize', handleWindowResize);
  });

  return (
    <div ref={ref}>
      Component size is {size.width} x {size.height}.
    </div>
  );
};
3
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?