[Main Project] UDog / 구현하기 - 탭 구현하기

soohyunee·2023년 3월 14일
0

[Main Project] UDog

목록 보기
7/18
post-thumbnail

1. 구현하기

진행 상황

  • 탭 메뉴바 구현
  • 미용실 상세 페이지 CSS
  • 로그인 하러가기 모달

진행 예정

  • 좋아요 기능

2. TIL

2-1. 탭 구현하기

리덕스 활용하여 탭 구현

예전에 스프린트로 리액트의 useState를 활용해서 탭을 구현한 적이 있다. 그래서 이번에는 리덕스를 활용하여 탭을 구현하고자 했다.

시도한 방법

클릭 이벤트가 발생한 li 요소에 selected라는 클래스네임을 할당하여 css가 입혀지게 하고 싶었다.

const initialState = {
	tab: 0,
	isOn: null,
};

reducers: {
  activeTab: (state, action) => {
    state.tab = action.payload;
    state.isOn = true;
  },
},
<S.Li key={idx} onClick={() => dispatch(activeTab(idx))} className={isOn ? 'selected' : ''}>

위와 같이 코드를 작성했지만 결과는 내가 원하던 대로 나오지 않았다. 클릭하면 selected class가 잘 들어가지만 다른 탭을 클릭한 후에는 기존의 selected가 사라질 줄 알았는데 사라지지 않았다.

해결 방법

isOn을 배열의 형테로 만들어주었다. 초기값으로 첫 번째 탭이 선택된 상태로 설정하고 map을 사용하여 선택된 탭에는 true, 선택되지 않은 탭에는 null 값을 부여해주었다. isOn 값을 배열로 관리하여 각 탭에 true 또는 null 값을 부여하고 activeTab reducer 함수에서는 선택된 탭에는 true 값을, 선택되지 않은 탭에는 null 값을 부여하도록 구현했다.

const initialState = {
  tab: 0,
  isOn: [true, null, null], 
};

activeTab: (state, action) => {
      state.tab = action.payload;
      state.isOn = state.isOn.map((_, index) => index === action.payload ? true : null);
    },
  },
  <S.Li key={idx} onClick={() => dispatch(activeTab(idx))} className={isOn[idx] ? 'selected' : ''}>

2-2. 로딩 상태 처리하기

useFetch와 undefined

const {id} = useParams();
const data = useFetch(`/hairshop/${id}`);

위와 같은 코드로 useFetch 커스텀훅으로 get요청을 통해 받아온 데이터를 data라는 변수에 할당하였고, 콘솔로그로 확인해보니 처음에 undefined가 뜬 후 이후에 데이터가 들어왔다. 이 때문인지 data에 string 메서드를 사용하려고 하면 에러가 떴다.

시도한 방법

useFetch hook이 비동기적으로 데이터를 가져오는 작업을 수행하고, 그 결과는 data 변수에 할당되는데 데이터를 가져오는 작업이 완료되기 전에 console.log가 실행되면, data 변수는 아직 데이터가 할당되기 전에 undefined로 설정되어 있다.
그래서 useFetch hook에 로딩중이라는 컴포넌트를 띄우는 로직을 추가하였다.

useEffect(() => {
	if (window) window.scrollTo(0, 0);
	dispatch(setLoading(true));

	API.get(url)
		.then((res) => {
		setData(res.data);
		})
		.catch((err) => {
		console.log(err);
		})
		.finally(() => {
		dispatch(setLoading(false));
		});
	}, [url, dispatch]);

	return data;
}

axios로 값을 가져오기전 로딩 상태를 true, 값을 가져온 후에는 false 바꿔주었고 상태는 리덕스로 관리하였다. 하지만 여전히 string 메서드를 사용하려고 하면 같은 에러가 나타났다.

해결 방법

아무래도 data가 초기값인 [] 때문에 string 메서드가 사용이 되지 않는 것 같았다. 그래서 삼항연산자를 사용하여 undefined가 아닐 때만 메서드를 적용하게끔 조건을 걸어주었더니 잘 적용됐다.

{data.like !== undefined ? data.like.toLocaleString() : data.like}
profile
FrontEnd Developer

0개의 댓글