Как оптимизировать сайт на react
При создании сайта на react я столкнулся с проблемой. В компонентах я использую useEffect для отрисовки элементов в зависимости от ширины экрана:
const [sizeChange, setSizeChange] = useState(false);
useEffect(() => {
const handleResize = () => {
if (window.innerWidth <= 800) {
setScreenReduced(true);
} else {
setScreenReduced(false);
}
};
handleResize();
window.addEventListener('resize', handleResize);
return () => {
window.removeEventListener('resize', handleResize);
};
},[]);
return (
{sizeChange? (<div className='пример-one'></div>) : (<div className='пример-two'></div>)}
)
Компонентов с подобным useEffect на странице 6 штук, но проблемными являются двое из них c похожей структурой внутри:
{sizeChange ? (
<Swiper className='impressions-swiper'
slidesPerView={'auto'}
loop={false}
spaceBetween={24}
centeredSlides={false}
breakpoints={{
500: {
slidesPerView: 'auto',
loop: true,
spaceBetween: 24,
centeredSlides: true
}
}}
>
{impressions.map((photo) => (
<SwiperSlide className={`impressions-swiper-slide`} key={photo.id} style={{
backgroundImage: `url(${photo.img})`,
}}>
<Link to={`/impressions/${photo.id}`}>
<svg className='close-up' width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M21.0002 21.0002L16.6572 16.6572M16.6572 16.6572C17.4001 15.9143 17.9894 15.0324 18.3914 14.0618C18.7935 13.0911 19.0004 12.0508 19.0004 11.0002C19.0004 9.9496 18.7935 8.90929 18.3914 7.93866C17.9894 6.96803 17.4001 6.08609 16.6572 5.34321C15.9143 4.60032 15.0324 4.01103 14.0618 3.60898C13.0911 3.20693 12.0508 3 11.0002 3C9.9496 3 8.90929 3.20693 7.93866 3.60898C6.96803 4.01103 6.08609 4.60032 5.34321 5.34321C3.84288 6.84354 3 8.87842 3 11.0002C3 13.122 3.84288 15.1569 5.34321 16.6572C6.84354 18.1575 8.87842 19.0004 11.0002 19.0004C13.122 19.0004 15.1569 18.1575 16.6572 16.6572ZM11.0002 8.00021V14.0002M8.00021 11.0002H14.0002" stroke="white" strokeWidth="1.5" strokeLinecap="round" strokeLinejoin="round"/>
</svg>
</Link>
</SwiperSlide>
))}
</Swiper>
) : (
<div className='impressions-grid'>
{impressions.map((photo) => (
<Link to={`/impressions/${photo.id}`} className={`${photo.gridType} photo-grid-el`} key={photo.id} style={{
backgroundImage: `url(${photo.img})`,
backgroundRepeat: 'no-repeat',
backgroundSize: 'cover'
}}>
<svg className='close-up' width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M21.0002 21.0002L16.6572 16.6572M16.6572 16.6572C17.4001 15.9143 17.9894 15.0324 18.3914 14.0618C18.7935 13.0911 19.0004 12.0508 19.0004 11.0002C19.0004 9.9496 18.7935 8.90929 18.3914 7.93866C17.9894 6.96803 17.4001 6.08609 16.6572 5.34321C15.9143 4.60032 15.0324 4.01103 14.0618 3.60898C13.0911 3.20693 12.0508 3 11.0002 3C9.9496 3 8.90929 3.20693 7.93866 3.60898C6.96803 4.01103 6.08609 4.60032 5.34321 5.34321C3.84288 6.84354 3 8.87842 3 11.0002C3 13.122 3.84288 15.1569 5.34321 16.6572C6.84354 18.1575 8.87842 19.0004 11.0002 19.0004C13.122 19.0004 15.1569 18.1575 16.6572 16.6572ZM11.0002 8.00021V14.0002M8.00021 11.0002H14.0002" stroke="white" strokeWidth="1.5" strokeLinecap="round" strokeLinejoin="round"/>
</svg>
</Link>
))}
</div>
)}
второй
{sizeChange? (
<div className='swiper'>
<div className='research-holder-slide2 slide-hover'>
<Link>
<img className='play-icon' src={play} alt="play" />
</Link>
</div>
</div>
) : (
<Swiper className='swiper'
grabCursor={true}
loop={true}
modules={[EffectCreative, Autoplay]}
autoplay={{
delay: 5000,
pauseOnMouseEnter: true
}}
effect='creative'
creativeEffect={{
next:{
translate:[-130, -130, 0]
},
prev: {
translate:[-130, -130, 0]
}
}}
>
<SwiperSlide className='research-holder-slide1 slide-hover'>
<Link target='_blank' to={'https://youtu.be/FiU29CHsQpo?si=kH7wbZfmjmzQH_nj'}>
<img className='play-icon' src={play} alt="play" />
</Link>
</SwiperSlide>
<SwiperSlide className='research-holder-slide2 slide-hover'>
<Link target='_blank' to={'https://youtu.be/FiU29CHsQpo?si=kH7wbZfmjmzQH_nj'}>
<img className='play-icon' src={play} alt="play" />
</Link>
</SwiperSlide>
</Swiper>
)}
</div>
на пк все работает отлично, но на мобильном устройстве получается так, что эти элементы изменяются с задержкой, что ломает структуру странички. Первый элемент используется почти сразу, второй у футера. Если пролистать сайт до конца, то изменение применится почти моментально к обоим.
Я думаю что задержка в перестройке этих элементов связана с тем, что в них используется Swiper (тк другие компоненты с useEffect не использующие Swiper или не заменяющие Swiper на обычный div работают стабильно), но как это исправить понятия не имею. Какие есть способы для избежания подобного? Как можно оптимизировать эту конструкцию в целом? Если есть статьи про правильную оптимизацию и структурирование сайта на react для быстрой загрузки и подобными тематиками буду благодарен. Заранее спасибо.
Ответы (1 шт):
Использовал react-responsive и все начала работать как надо, Swiper слишком много ресурсов съедал при рендере.