react에서 styled-components에 있는
ThemeProvider를 사용하여 다크 모드를 만들 수 있다.
최상위 컴포넌트
// ThemeProvider 가져오기
import { ThemeProvider } from 'styled-components';
import React, { useState } from 'react';
const lightTheme = {
backgroundColor: '#fff',
textColor: '#000',
};
const darkTheme = {
backgroundColor: '#000',
textColor: '#fff',
};
function App() {
// 상태를 하나 만들기
const [dark, setDark] = useState(false);
return (
<div className="App">
// dark가 true일 땐 darkTheme, false일 땐 lightTheme을 적용
<ThemeProvider theme={dark ? darkTheme : lightTheme}>
<Nav dark={dark} setDark={setDark} />
<Main />
</ThemeProvider>
</div>
);
}
자식 컴포넌트
/* Main.js */
import styled from 'styled-components';
// 이렇게 적용이 가능하다.
const Button = styled.button`
background-color: ${props => props.theme.backgroundColor};
color: ${props => props.theme.textColor};
padding: 8px 16px;
border: none;
border-radius: 4px;
cursor: pointer;
`;
filter를 사용하면 된다.
(원하는 색상의 filter 값은 CSS filter generator to convert from black to target hex color에서 찾으면 됨)
const lightTheme = {
backgroundColor: "#e9e9e9",
mainTxtColor: "#222222",
textColor: "#222222",
smallTxtColor: "#fff",
logoFilter: `invert(9%) sepia(2%) saturate(0%) hue-rotate(359deg) brightness(101%) contrast(90%)`,
};
const darkTheme = {
backgroundColor: "#1B2430",
mainTxtColor: "#FFFAE7",
textColor: "#6e7e97",
smallTxtColor: "#fffffb",
logoFilter: `invert(99%) sepia(63%) saturate(447%) hue-rotate(309deg) brightness(102%) contrast(103%)`,
};
-----
/* Main.js */
const LogoIcon = styled.div`
filter: ${(props) => props.theme.logoFilter};
`;
function BackgroundColor() {
const { pathname } = useLocation();
let backgroundColor;
switch (pathname) {
case '/':
backgroundColor = '#EBEEFF';
break;
default:
backgroundColor = '#FFF';
}
return <GlobalStyled $backgroundColor={backgroundColor} />;
}
export default BackgroundColor;
const GlobalStyled = createGlobalStyle<{ $backgroundColor: string; }>`
body {
margin: 0;
padding: 0;
height: 100vh;
background-color: ${({ $backgroundColor }) => $backgroundColor || '#FFF'};
}
`;