HTML&CSS&Javascript/CSS

[CSS-in-JS] Styled Component의 theme에 관하여

킹우현 2023. 2. 16. 22:10

Styled Component의 Theme 이란 ?

스타일링을 시작하기 앞서, 자주 사용하게 될 색상 코드, 사이즈, 폰트, 미디어 쿼리 등의 정보를 변수로 생성해 사용하면 일관적인 스타일 관리가 가능합니다.

 

styled-component에선 전반적으로 프로젝트 전체에서 사용할 목적의 변수 모음 객체 theme이라고 부릅니다.

 

const margins = {
  sm: ".5rem",
  base: "1rem",
  lg: "2rem",
  xl: "3rem",
};

const paddings = {
  sm: ".5rem",
  base: "1rem",
  lg: "2rem",
  xl: "3rem",
};

const fonts = {
  family: {
    base: `'Noto Sans KR', sans-serif`,
    title: `'Merriweather', serif`,
  },
  size: {
    sm: "1.4rem",
    base: "1.6rem",
    lg: "2rem",
    xl: "2.5rem",
    title: "6rem",
  },
  weight: {
    light: 100,
    normal: 400,
    bold: 700,
  },
};

const colors = {
  red: "#ff4d4d",
  yellow: "#ffff4d",
  blue: "#0099ff",
};

const size = {
  mobile: "425px",
  tablet: "768px",
  desktop: "1440px",
};

// 미디어 쿼리의 중복 코드를 줄이기위해 정의된 변수입니다
const device = {
  mobile: `@media only screen and (max-width: ${size.mobile})`,
  tablet: `@media only screen and (max-width: ${size.tablet})`,
  desktopL: `@media only screen and (max-width: ${size.desktop})`,
};

//테마에 따라 다른 값을 갖는 색상 값입니다 
const lightThemeColors = {
  ...colors,
  primary: "#333",
  secondary: "#fff",
  tertiary: "#808080",
};

const darkThemeColors = {
  ...colors,
  primary: "#fff",
  secondary: "#333",
  tertiary: "#d4d0c4",
};

// 테마와 관련없이 공통으로 사용되는 변수들입니다
const defalutTheme = {
  margins,
  paddings,
  fonts,
  device,
};

// 각 테마는 공통 변수와 함께, 각기 다른 색상 값들을 갖습니다.
export const darkTheme = {
  ...defalutTheme,
  colors: darkThemeColors,
};

export const lightTheme = {
  ...defalutTheme,
  colors: lightThemeColors,
};

이렇게 생성한 theme 객체는 각 Component마다 import해 사용 할 수도 있지만, 더 간단하게 사용할 수 있는 방법이 있습니다.

 

import React, { useState } from "react";
import { ThemeProvider } from "styled-components";
import { darkTheme, lightTheme } from "../styles/Theme";
import Header from "./Header";
import Container from "./Container";

const App = () => {
  const [theme, setTheme] = useState(lightTheme);
  const [currentThemeText, setCurrentThemeText] = useState("Light Theme");

  // 각 theme은 state로 관리되며 버튼 클릭 이벤트 시 변경됩니다.
  const switchTheme = () => {
    const nextTheme = theme === lightTheme ? darkTheme : lightTheme;
    setTheme(nextTheme);
    const nextThemeText = theme === lightTheme ? "Dark Theme" : "Light Theme";
    setCurrentThemeText(nextThemeText);
  };

  return (
    //ThemeProvider는 반드시 theme을 사용 할 하위 Component를 감싸고 있어야 합니다.
    <ThemeProvider theme={theme}>
      <Header switchTheme={switchTheme} />
      <Container currentThemeText={currentThemeText} />
    </ThemeProvider>
  );
};

export default App;

 

바로 styled-components가 지원하는 ThemeProvider를 사용하는 것입니다.

ThemeProvider : 반드시 theme 속성을 갖는 컴포넌트. theme 속성의 값으로 설정된 객체를 모든 하위 컴포넌트들의 props로 전달합니다. ⭐️⭐️

이렇게 ThemeProvider를 사용하면 굳이 props나 useContext를 사용하지 않아도 모든 컴포넌트에서 theme 객체에 간편하게 접근 할 수 있습니다.

 

또 사용자 theme 변경 이벤트가 발생 했을시, Provider의 theme 속성 값만 변경하는 것으로 간단하게 테마 변경을 구현 할 수 있습니다.

 

( 출처 : https://dkje.github.io/2020/10/13/StyledComponents/ )

 

[React] Styled Components 사용기 - 어? 쓰흡... 하아.... | Dev X

이 글은 styled components에 대해 공부하며 정리하는 목적으로 작성 되었습니다. 잘못된 정보는 지적해주시면 바로 정정하겠습니다!

dkje.github.io