[Error] swiper content update 시 정상적으로 스와이프 되지 않는 현상

Seung-a·2021년 2월 23일
4
post-thumbnail

💬 들어가며

react로 프론트 개발 중 content를 가로로 스와이프 하는 컴포넌트를 구현하게 되었다.

일반적인 carousel과 유사하지만 이벤트 한 번에 여러 content가 이동하는 게 아니라 사용자가 드래그한 만큼 이동하는 slider에 좀 더 가까운(?) 애니메이션을 보여주어야 했다. 🤔

이를 위해 react-swiper를 이용해 props로 배열(plants)을 받아 아래처럼 출력만 해주는 Slider 컴포넌트를 구현하여 사용하고 있었다.

(SwiperSlide에 자체 설정된 width를 제거하기 위해 style을 따로 설정했다.)

/* Silder.jsx */

import React from 'react';
import styled from 'styled-components';

import {Swiper, SwiperSlide} from 'swiper/react';
import 'swiper/swiper.scss';

function Slider({plants}) {
  return (
    <StyledSlider freeMode={true} freeModeMomentum={false} slidesPerView={'auto'}>
      {plants.map((plant) => (
        <SwiperSlide key={plant.id}>
          <div>
            <p>아이디: {plant.id}</p>
            <p>이름: {plant.name}</p>
            <p>종류: {plant.type}</p>
          </div>
        </SwiperSlide>
      ))}
    </StyledSlider>
  );
}

const StyledSlider = styled(Swiper)`
  cursor: pointer;

  .swiper-slide {
    width: max-content !important;
  }
`;

export default Slider;

swiper 라이브러리를 사용했지만 프로젝트에서 개발 시 slider라고 지칭했기 때문에 컴포넌트 이름은 Slider로 설정했다.

❓ 문제 상황

plants의 내용이 업데이트 될 때, 즉 Slidercontent의 개수가 바뀔 때 정상적으로 스와이프 되지 않는 에러가 발생했다.

  1. content가 없어도 계속 스와이프가 되는 에러 (흰 화면에서 계속 드래그가 됨)
  2. content가 있는데 스와이프가 되지 않는 에러

개발자 도구로 확인해보니, plants가 업데이트 되어도 SwiperSlide의 개수는 처음 받았던 plants의 length에서 변하지 않아서 에러가 발생한 것 같았다.

💡 문제 해결

stackoverflow에서 react-swiper 컴포넌트 방식으로 특정 option을 추가하는 방법이 몇 개 있길래 시도해봤는데 안 됐다. 😂 (댓글을 보니 다른 사람들도 작동하지 않는 듯)

이렇게 삽질을 하다가..

결국 swiper api 공식 문서를 통해 react 컴포넌트보다는 js 자체로 접근해서 해결했다! 핵심은 다음과 같다.

  1. swiper 객체에 접근한다.
  2. content가 바뀔 때마다 swiper.update()를 실행하여 swiper와 content를 갱신한다.
  3. (추가) 나는 이미 많이 스와이프 한 상황에서 내용이 바뀔 때 처음부터 보여줬으면 좋겠어서 swiper.slideTo를 통해 처음 요소로 스크롤이 돌아가도록 해 주었다.

코드는 아래와 같다.

/* Silder.jsx */

import React, {useLayoutEffect} from 'react';
import styled from 'styled-components';

import {Swiper, SwiperSlide} from 'swiper/react';
import 'swiper/swiper.scss';
import {isEmptyArr} from '../lib/handler'; // 빈 배열인 지 확인

function Slider({plants}) {
  useLayoutEffect(() => {
    if (!isEmptyArr(plants)) { // plants가 빈 배열이 아니면
      const swiper = document.querySelector('.swiper-container').swiper;
      swiper.update();
      swiper.slideTo(0);
      // update 후 스크롤이 맨 처음 content 위치로 이동
    }
  }, [plants]);
  
  return (
    <StyledSlider freeMode={true} freeModeMomentum={false} slidesPerView={'auto'}>
      {plants.map((plant) => (
        <SwiperSlide key={plant.id}>
          <div>
            <p>아이디: {plant.id}</p>
            <p>이름: {plant.name}</p>
            <p>종류: {plant.type}</p>
          </div>
        </SwiperSlide>
      ))}
    </StyledSlider>
  );
}

const StyledSlider = styled(Swiper)`
  cursor: pointer;

  .swiper-slide {
    width: max-content !important;
  }
`

export default Slider;

위 방법을 적용해서 구현한 결과는 여기 키워드 검색 부분에서 확인할 수 있다!
(곧 완성하고 회고할 프로젝트 🏃‍♀️)

📚 마치며

공식 문서의 중요성을 다시금 깨달았다.

라이브러리 사용 시 안 되는 부분이 있으면 구글링으로 빠르게 방법을 찾는 것도 좋겠지만, 다른 이들의 경험에 무조건 의존(?)하기 전에 공식 문서에서 여러 상황에서 가이드를 제공하고 있는 지 꼼꼼히 살펴봐야겠다. 😤

이런 상황이 올 때마다 몇년 전 교수님이 해주신 말씀이 생각난다

#소프트웨어는 #문서가생명이다

🔗 참고

피드백은 언제나 환영합니다 ❤

0개의 댓글