SPACE RUMI

Hi, I am rumi. Let's Splattack!

[IT] 프로덕트 개발/React - 리액트

[React] Context api 사용해 로딩 구현하기

백루미 2022. 7. 3. 10:51
반응형

context api를 사용해 로딩화면을 간단하게 구현해보자.
context폴더에 LoadingContext 파일을 생성한다.

context/LoadingContext.tsx

import { createContext, useState } from "react";

type LoadingState = {
  setVisible: (value: boolean) => void;
};

export const LoadingContext = createContext<LoadingState>({
  setVisible: (value: boolean) => {},
});

export function LoadingContextProvider({ children }: { children: React.ReactNode }) {
  const [visible, setVisible] = useState<boolean>(false);
  
  return (
    <LoadingContext.Provider value={{ setVisible }}>
      {visible &&(
        <div className="dim">
          <div className="custom-loading">
          </div>
        </div>
        )}
      {children}
    </LoadingContext.Provider>
  );
}

로딩화면을 노출할지 말지를 결정하는 visible state를 만들어주고 마크업을 해준다.
뒤에 dim 이라는 어두운 배경을 깔고 로딩을 중앙에 노출한다.  css는 아래와 같다.

css

.dim {
    position: fixed;
    width:100vw;
    height:100vh;
    display:flex;
    align-items: center;
    top: 0;
    right: 0;
    bottom: 0;
    left: 0;
    z-index: 9999;
    background-color: rgba(0, 0, 0, 0.6);
  }
.custom-loading{
    position:relative;
    margin:0 auto;
    &::after{
        content:'Loading...';
        position:absolute;
        color:white;
        animation: motion 0.5s linear 0s infinite alternate;
        font-size:1.6rem;
    }
    @keyframes motion {
        0% {
        opacity:0}
        100% {
        opacity:1}
    }
}

 

LoadingContextProvider으로 컨텐츠(라우터) 영역을 감싸준다.

App.tsx

import React from "react";
import { BrowserRouter } from "react-router-dom";
import { GlobalNav } from "./components";
import Contents from "./routes/Routes";
import { LoadingContextProvider } from "src/contexts/LoadingContext";


function App() {
  return (
    <div className="App">
      <BrowserRouter>
          <LoadingContextProvider>
                <Contents />
          </LoadingContextProvider>
      </BrowserRouter>
    </div>
  );
}

export default App;

 

hooks/loading-context.ts

import useLoadingBarContext from "./loading-bar-context";
import useToastContext from "./toast-context";
import useTitleOperation from "./title-operation";

export { useLoadingBarContext, useToastContext, useTitleOperation };


// hooks/loading-context.ts
import { useContext } from "react";
import { LoadingContext } from "src/contexts/LoadingContext";

export default function useLoadingContext() {
  const { setVisible } = useContext(LoadingContext);
  return { setLoading: setVisible };
}

훅스를 만들어준다. 로딩은 공용으로 쓰는 컨텍스트니 훅스폴더에 따로 빼준다.
이제 원하는 컨텐츠 페이지에서 useLoadingContext를 임포트하고 setLoading을 꺼내 노출시킬 수 있다.

사용

import { useLoadingContext } from "src/hooks";

const {setLoading} = useLoadingContext();

setLoading(true)
반응형