React でウィンドウサイズが小さいときだけスライドショー表示をする方法
ピンポイントな小ネタですが、 React で「ウィンドウサイズが大きいときは画像をそのまま並べて、ウィンドウサイズが小さいときは画像をスライドショー表示する方法」についてです。
今回はスライドショーの例ですが、この方法は「画面幅によって出力コンポーネントを切り替える方法」として一般化することもできます。
今回は以下のパッケージを使用します。
react
17.x.xreact-slick
0.27.14slick-carousel
1.8.1
実現するには大きく 2 つのことを行う必要があります。
- ウィンドウサイズによって出力コンポーネントを切り替える
- スライドショーを生成する
1 は、 useState()
と useEffect()
と window
オブジェクトの resize
イベントを使って、ウィンドウサイズのしきい値で処理を分岐すれば OK です。
2 は単純にスライドショーを作ります。
自作でもよいですが react-slick
等の定番ライブラリを使うと高品質なものがかんたん確実に作れます。
この 1 と 2 を実現する ImageGallery
コンポーネントを作ってみると次のようになります:
/**
* ImageGallery
*/
import React, { useState, useEffect } from "react"
import Slider from "react-slick"
import "slick-carousel/slick/slick.css"
import "slick-carousel/slick/slick-theme.css"
// 画面幅がこの値に満たないときはスライドショー表示する
WIDTH_THRESHOLD = 768
const ImageGallery = ({ images }) => {
const [width, setWidth] = useState(null)
const updateWidth = (event) => {
setWidth(window.innerWidth)
}
useEffect(() => {
window.addEventListener(`resize`, updateWidth, {
capture: false,
passive: true,
})
return () => window.removeEventListener(`resize`, updateWidth)
})
// 初期表示時に画面幅に合わないコンポーネントが一瞬表示されてしまうのを防ぐ
if (width === null) {
return ``
}
if (width < WIDTH_THRESHOLD) {
// 画像をスライドショー表示する
return (
<Slider>
{images.map((image) => (
<div key={image.src}>
<img src={image.src} alt={image.alt} />
</div>
))}
</Slider>
)
}
// 画像をそのまま並べる
return (
...
)
}
width
を定義している useState(null)
のところは、もしここで window
オブジェクトに確実にアクセスできるようであれば useState(window.innerWidth)
と書いてしまってもよいと思います。
そうした場合 if (width === null)
の部分は削除可能です。
以上です。