스타일 컴포넌트의 상속 개념에 대해 알아보자!
styled-componets 를 사용하려면, styled.tagname 이라고 작성해야 사용이 가능하다.
하지만 JSX 문법으로 직접 만든 컴포넌트나, styled-components 를 사용해서 이미 만들어진 다른 컴포넌트에 스타일을 입히려면 어떻게 해야 할까?
이 때, 우리는 상속 기능을 사용하면 된다!
코드를 살펴보면...
import styled from "styled-components";
const SIZES = {
large: 24,
medium: 20,
small: 16
};
const Button = styled.button`
background-color: #6750a4;
border: none;
color: #ffffff;
font-size: ${({ size }) => SIZES[size] ?? SIZES["medium"]}px;
padding: 16px;
${({ round }) =>
round
? `
border-radius: 9999px;
`
: `
border-radius: 3px;
`}
&:hover,
&:active {
background-color: #463770;
}
`;
export default Button;
import styled from "styled-components";
import Button from "./Button";
const SubmitButton = styled(Button)`
background-color: #de117d;
display: block;
margin: 0 auto;
width: 200px;
&:hover {
background-color: #f5070f;
}
`;
function App() {
return (
<div>
<SubmitButton>계속하기</SubmitButton>
</div>
);
}
export default App;
화면을 확인해보면...
버튼에 마우스를 갖다대면...
색이 변하는걸 확인할 수 있다.
그럼 이제 기존의 Button 컴포넌트의 스타일을 상속해서 새로운 버튼 SubmitButton 을 만들어 주고, App 컴포넌트에 배치한 상황이다.
코드를 살펴보면 SubmitButton 컴포넌트를 만들 때, styled(Button) 이라고 작성한 걸 볼 수 있다. 이렇게 하면 SubmitButton 이 Button 의 스타일을 상속받아 스타일을 전달할 수 있다.
상속이라는 개념은 자바스크립트에서 클래스를 조금이라도 배워봤으면 알 수 있다.
말 그대로 styled-components 의 상속은 다른 컴포넌트의 스타일을 가져와서 원하는 대로 사용할 수 있는 것이라고 이해하면 쉽다.
코드 예시를 보면...
function TermsOfService() {
return (
<div>
<h1>㈜코드잇 서비스 이용약관</h1>
<p>
환영합니다.
<br />
Codeit이 제공하는 서비스를 이용해주셔서 감사합니다. 서비스를
이용하시거나 회원으로 가입하실 경우 본 약관에 동의하시게 되므로, 잠시
시간을 내셔서 주의 깊게 살펴봐 주시기 바랍니다.
</p>
<h2>제 1 조 (목적)</h2>
<p>
본 약관은 ㈜코드잇이 운영하는 기밀문서 관리 프로그램인 Codeit에서
제공하는 서비스를 이용함에 있어 이용자의 권리, 의무 및 책임사항을
규정함을 목적으로 합니다.
</p>
</div>
);
}
export default TermsOfService;
TermsOfService 는 JSX 문법을 사용해서 만든 컴포넌트이다. 이 컴포넌트를 styled( ) 함수로 감싸보겠다.
import styled from 'styled-components';
import Button from './Button';
import TermsOfService from './TermsOfService';
const StyledTermsOfService = styled(TermsOfService)`
background-color: #ededed;
border-radius: 8px;
padding: 16px;
margin: 40px auto;
width: 400px;
`;
const SubmitButton = styled(Button)`
background-color: #de117d;
display: block;
margin: 0 auto;
width: 200px;
&:hover {
background-color: #f5070f;
}
`;
function App() {
return (
<div>
<StyledTermsOfService />
<SubmitButton>계속하기</SubmitButton>
</div>
);
}
export default App;
화면을 보면...
위에서 styled-components 로 만든 버튼을 활용해서 만들어보았다. 하지만 문제점이 있다!
styled()로 지정한 스타일이 적용되지 않았다...
StyledTermsOfService에 지정한 배경색이랑 너비가 적용이 안 된 거 같다.
Styled Components 에서는 내부적으로 className 을 따로 생성한다. 그리고 자체적으로 생성된 className 부분에 styled( ) 함수의 스타일이 입혀진다.
근데 JSX 문법으로 만든 컴포넌트는 styled( ) 함수가 적용될 className 에 대한 정보가 없다.
이러한 문제점을 해결하기 위해서는 직접 만든 컴포넌트에 className prop 을 따로 내려줘야 styled( ) 를 사용할 수 있게 된다.
function TermsOfService({ className }) {
return (
<div className={className}>
<h1>㈜코드잇 서비스 이용약관</h1>
<p>
환영합니다.
<br />
Codeit이 제공하는 서비스를 이용해주셔서 감사합니다. 서비스를
이용하시거나 회원으로 가입하실 경우 본 약관에 동의하시게 되므로, 잠시
시간을 내셔서 주의 깊게 살펴봐 주시기 바랍니다.
</p>
<h2>제 1 조 (목적)</h2>
<p>
본 약관은 ㈜코드잇이 운영하는 기밀문서 관리 프로그램인 Codeit에서
제공하는 서비스를 이용함에 있어 이용자의 권리, 의무 및 책임사항을
규정함을 목적으로 합니다.
</p>
</div>
);
}
export default TermsOfService;
다시 한 번 화면을 보면...
StyledTermsOfService 스타일 컴포넌트의 스타일들이 적용된 걸 확인할 수 있다!!!
그러니까 다시 정리하면...
직접 만든 컴포넌트에 className Prop 을 따로 내려주는 건 styled( ) 함수가 적용될 부분의 className 을 별도로 정해주는 거라고 이해하면 된다.
우리 같은 경우에는 TermsOfService 컴포넌트의 div 태그에 className 을 내려줬기 때문에 styled(TermsOfService) 에서 작성한 코드는 TermsOfService 안에 있는 div 태그에 적용되는 것이다.