
์ค์น
๋คํฌ๋ชจ๋๋ ๊ผญ ํ๋ก์ ํธ ์์์์ ๊ณ ๋ คํด์ฃผ๊ธฐ๋ก ํ์
- ํ์ ์คํฌ๋ฆฝํธ + ๋ฆฌ์กํธ ์ฑ๊ณผ ์คํ์ผ ์ปดํฌ๋ํธ ์ค์นํ๊ธฐ
npx create-react-app my-app --template typescript
npm i @types/styled-components
๋คํฌํ ๋ง ๋ง๋ค๊ธฐ ๐

GlobalStyles.ts
import { createGlobalStyle } from "styled-components";
import reset from "styled-reset";
export const GlobalStyle = createGlobalStyle`
${reset}
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
body, html {
font-size: 16px;
}
body {
background: ${({ theme }: { theme: any }) => theme.bgColor};
color: ${({ theme }: { theme: any }) => theme.textColor};
display: block;
width: 100%;
height: 100%;
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
}
button {
border: none;
outline: none;
color: ${({ theme }: { theme: any }) => theme.bgColor};
background-color: ${({ theme }: { theme: any }) => theme.textColor};
}
`;
- style-reset์ ๋ธ๋ผ์ฐ์ ๋ง๋ค ๊ธฐ๋ณธ์ ์ผ๋ก ์ค์น๋์ด ์๋ ์คํ์ผ์ ์ง์์ฃผ๋ Node.js ํจํค์ง์ด๋ค. ๊ทธ๋ฌ๋๊น ๊ธฐ๋ณธ ์ ๊ณต ์คํ์ผ์ ์ด๊ธฐํ์์ผ ํธํ์ฑ์ ๋ง์ถ๋ค.!
npm install style-reset ํ์ ์ฌ์ฉํ๋ฉด ๋๋น - ๊ทธ๋ฆฌ๊ณ ํ์ ์คํฌ๋ฆฝํธ๋ก ๋ง๋๋๋งํผ theme:any๋ฅผ ๊ผญ ์ง์ ํด์ค๋ค ์ํ๋ฉด ์ค๋ฅ๊ฐ ๋์ฌ~
theme.ts
export const lightTheme = {
bgColor: "#f9f9f9",
textColor: "#333333",
borderColor: "#ede7f7",
toggleColor: "#cbb5dc",
};
export const darkTheme = {
bgColor: "#000000",
textColor: "#f0eef6",
borderColor: "#a9b0c0",
toggleColor: "#e0cde3",
};
export const theme = {
darkTheme,
lightTheme,
};
๋ด ๋ง๋๋ก ํ
๋ง๋ ๋ง๋ค์ด ์ค๋ค.
๊ทธ๋ฆฌ๊ณ ๋ ์ด ์น๊ตฌ๋ค๋ ํ์
์ ๋ง๋ค์ด ์ค์ผํ๋ค.
styled.d.ts
import "styled-components";
declare module "styled-components" {
export interface DefaultTheme {
bgColor: string;
textColor: string;
borderColor: string;
toggleColor: string;
}
}
๋คํฌํ ๋ง ๊ตฌํํ๊ธฐ ๐
App.tsx
import { useState } from "react";
import Home from "./Home";
import { ThemeProvider } from "styled-components";
import { lightTheme, darkTheme } from "./style/theme";
import { GlobalStyle } from "./style/GlobalStyles";
import styled from "styled-components";
function App() {
const [theme, setTheme] = useState("dark");
const isLight = theme === "light";
const toggleTheme = () => {
if (theme === "light") {
setTheme("dark");
} else {
setTheme("light");
}
};
return (
<ThemeProvider theme={theme === "light" ? lightTheme : darkTheme}>
<>
{" "}
<GlobalStyle />
<Home />
<Button onClick={toggleTheme}>
{isLight ? "Dark ๐ " : "Light ๐"}
</Button>
</>
</ThemeProvider>
);
}
export default App;
const Button = styled.button`
width: 100px;
height: 50px;
position: absolute;
top: 10px;
right: 30px;
`;
- App.tsx ํ์ผ๋ก ๊ฐ์ ์ปดํฌ๋ํธ๋ค์ GlobalStyle ์ ์ฉ์ ํด์ฃผ๊ณ , ThemeProvider๋ก ๊ฐ์ธ์ฃผ๋ฉด ๋๋ค.
- ThemeProvider Wrapper๋ก ๊ฐ์ธ์ฃผ๊ณ theme๋ฅผ ๋๊ฒจ์ฃผ๋ฉด ์์ ์ปดํฌ๋ํธ์์ theme๊ฐ์ฒด๋ฅผ ์ฌ์ฉํ ์ ์๊ฒ ๋๋ค.
Home.tsx
import React from "react";
import styled from "styled-components";
const Home = () => {
return (
<React.Fragment>
<Header>
<div style={{ alignItems: "center" }}>
<Title>FAIRYTALE</Title>
</div>
</Header>
<Contents>๋คํฌ ๋ชจ๋ ๊ตฌํํ๊ธฐ ๐</Contents>
</React.Fragment>
);
};
export default Home;
const Header = styled.header`
width: 100%;
height: 70px;
background-color: aliceblue;
`;
const Title = styled.h1`
font-size: 64px;
color: black;
`;
const Contents = styled.div`
width: 100%;
height: 600px;
text-align: center;
position: relative;
top: 70px;
font-size: 50px;
`;

+ ์ด๋ฏธ์ง ์ฝ์ ํ๊ธฐ ๐ธ
๋คํฌ๋ชจ๋, ๋ผ์ดํธ๋ชจ๋์ผ ๋ ๋ค๋ฅธ ์ด๋ฏธ์ง๋ฅผ ๋ฃ์ผ๋ ค๊ณ ํ๋๋ฐ
์๊ฐ๋ณด๋ค ๊ฐ๋จํ ์ค ์์๋ ์์
์ด ์ค๋ฅ๊ฐ ๋๋๋ผ
๊ทธ๋ฌ๋๋ฐ ํด๊ฒฐ์ ์ฌ๊ธฐ์ ์ฐพ์๋ค (https://www.carlrippon.com/using-images-react-typescript-with-webpack5/)
styled.d.ts
declare module "*.png";
๋น์ฐํ์ง๋ง ๋ค๋ฅธ ํ์ฅ์๋ฅผ ์ธ ์๋ ์์ผ๋
ํ์์ ํ๋ก์ ํธํ ๋๋ ๋ชจ๋ ์ด๋ฏธ์ง ํ์ฅ์๋ฅผ ๋ฃ์ด๋์ผ๋ฉด ๋๋น
App.tsx
<IMG>
{isLight ? (
<img src="./Flurry.png" alt="๋ฝ์ผ๋ฏธ" width={"200px"} />
) : (
<img src="./Hamphrey.png" alt="ํ์ฅ" width={"200px"} />
)}
</IMG>

ํ ๊ท์ฌ์.. ์ง์ง... (๋น์์ด)
์์ฃผ ๊ฐ๋ณ๊ฒ ๋คํฌ๋ชจ๋ ๋ง๋๋ ๋ฒ์ ์์๋ดค๋ค!
๊ฐ๋ณ๊ฒ ์์ํ๋๋ฐ ์๊ฐ์ง๋ ๋ชปํ๋ ์ค๋ฅ๋ฅผ ๋ง๋ฅ๋จ๋ ค์ ์์๋ณด๋ค ์ค๋ ๊ฑธ๋ ธ์ง๋ง,
๊ทธ ์ค๋ฅ๋ ํด๊ฒฐํ๊ณ ์๋ฌดํผ๊ฐ ์์ฑ!
์ด์ ๋๋ ์ด๋ค ํ ์ดํ๋ก์ ํธ๋ฅผ ํ๋ ๊ฐ์ ๋คํฌ๋ชจ๋๋ ๋ง๋ค์ด๋ณด๋ ค๊ณ ํ๋ค ใ
_ใ
(๋ผ์ดํธ ๋ชจ๋๋ง ์ฐ๋ ์ฌ๋)
'TIL > Typescript' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
[TIL] TypeScript์์ Record ํ์ ํ์ฉ (0) | 2023.11.05 |
---|---|
[TypeScript + React] ์นด์นด์ค ๋งต ์ด์ฉํ๊ธฐ (0) | 2023.05.20 |
[TIL] Class + TS (1) | 2023.05.20 |
[TIL] TypeScript ํ์ ํ์ ํ๊ธฐ <Narrowing> (1) | 2023.05.20 |
Typescript ์์ ์ ํจ๊ป ์ต์ํด์ง๊ธฐ : part 1 (1) | 2023.05.19 |