Emotion
1. ์์ : ๊ณต์๋ฌธ์ ๋ฐ๋ผํด๋ณด๊ธฐ
1$ npm i @emotion/styled @emotion/react
2. ์์ 1 : ๊ธฐ๋ณธ ์ฌ์ฉ๋ฒ
2.1 App.js
1import './App.css'2import EmotionExample from './components/EmotionExample/EmotionExample'3// import StyledComponentsExample from './components/StyledComponentsExample/StyledComponentsExample';45export default function App() {6return (7<div className="App">8<EmotionExample />9{/* <StyledComponentsExample /> */}10</div>11)12}
2.2 EmotionExample
1// src/components/EmotionExample/EmotionExample.jsx2/** @jsxImportSource @emotion/react */3import { css } from '@emotion/react'4import styled from '@emotion/styled'56const Button = styled.button`7padding: 32px;8background-color: hotpink;9font-size: 24px;10border-radius: 4px;11color: black;12font-weight: bold;13&:hover {14color: white;15}16`1718const color = 'white'1920const style = css`21color: hotpink;22`2324const SomeComponent = ({ children }) => (25<div css={style}>26Some hotpink text.27{children}28</div>29)3031const anotherStyle = css({32textDecoration: 'underline',33})3435const P = props => (36<p37css={{38margin: 0,39fontSize: 12,40lineHeight: '1.5',41fontFamily: 'Sans-Serif',42color: 'black',43}}44{...props} // <- props contains the `className` prop45/>46)4748const ArticleText = props => (49<P50css={{51fontSize: 14,52fontFamily: 'Georgia, serif',53color: 'darkgray',54}}55{...props} // <- props contains the `className` prop56/>57)5859const AnotherComponent = () => <div css={[anotherStyle, style]}>Some text with an underline.</div>6061const danger = css`62color: red;63`6465const base = css`66background-color: darkgreen;67color: turquoise;68`6970export default function EmotionExample() {71return (72<>73<div74css={css`75padding: 32px;76background-color: hotpink;77font-size: 24px;78border-radius: 4px;79&:hover {80color: ${color};81}82`}83>84Hover to change color.85</div>86<Button>Hello</Button>87<SomeComponent />88<AnotherComponent />89<P>PPPPP</P>90<ArticleText>Article</ArticleText>91<div>92<div css={base}>This will be turquoise</div>93<div css={[danger, base]}>94This will be also be turquoise since the base styles overwrite the danger styles.95</div>96<div css={[base, danger]}>This will be red</div>97</div>98</>99)100}
- react์ ํนํ : @emotion/react
- css props : jsx๋ฅผ ๋์ฒด
- styled components : styled-component + @
- composition : css์์์ css ์ฌ์ฉ
3. ์์ 2 : Media Queries
https://emotion.sh/docs/media-queries
1// src/components/EmotionExample/EmotionExample.jsx2/** @jsxImportSource @emotion/react */3import { css } from '@emotion/react'45export default function EmotionExample() {6return (7<>8<p9css={css`10font-size: 30px;11@media (min-width: 420px) {12font-size: 50px;13}14`}15>16Some text!17</p>18</>19)20}
4. ์์ 3 : Global Styles
https://emotion.sh/docs/globals
1// src/components/EmotionExample/EmotionExample.jsx2/** @jsxImportSource @emotion/react */3import { Global, css } from '@emotion/react'45export default function EmotionExample() {6return (7<>8<p9css={css`10font-size: 30px;11@media (min-width: 420px) {12font-size: 50px;13}14`}15>16<Global17styles={css`18p {19color: hotpink !important;20}21`}22/>23Some text!24</p>25<p>Hello, world!</p>26</>27)28}
5. ์์ 4 : Keyframes
1// src/components/EmotionExample/EmotionExample.jsx2/** @jsxImportSource @emotion/react */3import { Global, css, keyframes } from '@emotion/react'45const bounce = keyframes`6from, 20%, 53%, 80%, to {7transform: translate3d(0,0,0);8}91040%, 43% {11transform: translate3d(0, -30px, 0);12}131470% {15transform: translate3d(0, -15px, 0);16}171890% {19transform: translate3d(0,-4px,0);20}21`2223export default function EmotionExample() {24return (25<>26<p27css={css`28font-size: 30px;29@media (min-width: 420px) {30font-size: 50px;31}32`}33>34<Global35styles={css`36p {37color: hotpink !important;38}39`}40/>41Some text!42</p>43<p>Hello, world!</p>44<div45css={css`46animation: ${bounce} 2s ease infinite;47`}48>49some bouncing text!50</div>51</>52)53}
6. ์์ 5 : Class Names
https://emotion.sh/docs/class-names
1// src/components/EmotionExample/EmotionExample.jsx2/** @jsxImportSource @emotion/react */3import { Global, css, keyframes, ClassNames } from '@emotion/react'45const bounce = keyframes`6from, 20%, 53%, 80%, to {7transform: translate3d(0,0,0);8}91040%, 43% {11transform: translate3d(0, -30px, 0);12}131470% {15transform: translate3d(0, -15px, 0);16}171890% {19transform: translate3d(0,-4px,0);20}21`2223// this might be a component from npm that accepts a wrapperClassName prop24let SomeComponent = props => (25<div className={props.wrapperClassName}>26in the wrapper!27<div className={props.className}>{props.children}</div>28</div>29)3031export default function EmotionExample() {32return (33<>34<p35css={css`36font-size: 30px;37@media (min-width: 420px) {38font-size: 50px;39}40`}41>42<Global43styles={css`44p {45color: hotpink !important;46}47`}48/>49Some text!50</p>51<p>Hello, world!</p>52<div53css={css`54animation: ${bounce} 2s ease infinite;55`}56>57some bouncing text!58</div>59<ClassNames>60{({ css, cx }) => (61<SomeComponent62wrapperClassName={css({ color: 'green' })}63className={css`64color: hotpink;65`}66>67from children!!68</SomeComponent>69)}70</ClassNames>71</>72)73}
7. Styled Component vs Emotion
- ๊ธฐ๋ฅ : Fallbacks, &, Global, keyframes
- styled-component, Emotion ๋ผ์ด๋ธ๋ฌ๋ฆฌ ์ฒ์์๋ ์กฐ๊ธ ๋ฌ๋์ง๋ง, ์ด์ ๊ฑฐ์ ์ ์ฌํด์ก๋ค.
- https://github.com/jsjoeio/styled-components-vs-emotion
- https://npmtrends.com/@emotion/core-vs-@emotion/react-vs-styled-components
- trend : emotion์ด ์ฐ์ธ
- ์ฌ์ด์ฆ / ์๋ : emotion์ด ์ฐ์ธ
- styled-components๋ css๋ฅผ ์ํฌํธ