Codestates SEB FE 42기/회고

코드스테이츠 Pre-Project 회고 (2) | 첫 Styled-Components 잘 사용하기

2realzoo 2023. 4. 1. 16:02

💅 Styled-Components

 

이번에 styled-components를 처음 써보았는데 확실히 직접 사용해보니 배우는 게 많았다.

아직 미숙한 점이 많지만 css보다 깔끔한 것 같기도 하고...

근데 내가 아직 잘 못써서 그런지 styled가 앞부분에 너무 많이 생겨버린다... ㅎㅎ

다른 분은 아예 파일을 파서 

import * as W from "./styled.js";

function Login() {
	return (
    	<W.Container>
        <W.Container />
        )
     };

이렇게 가져와서 사용하셨다. 

훨씬 깔끔해지는 듯!

 

 

1. attrs()

공식문서🔗

export const Input = styled.input.attrs({ autoComplete: "off" })`
  border: none;
  overflow: hidden;
`;

추가적인 attributes를 붙일 수 있는 메서드이다. 

이렇게 사용하면 태그들이 깔끔해지기도 하고 속성 전달 목적의 불필요한 태그가 사라진다.

attrs안에 { 속성명 : "속성" } 이렇게 넣어준다.

 

- attrs에 함수가 들어가는 예시

const Input = styled.input.attrs(props => ({
  // 정적 props 정의 가능
  type: "text",

  // 동적 props 정의 가능
  size: props.size || "1em",
}))`
  color: palevioletred;
  font-size: 1em;
  border: 2px solid palevioletred;
  border-radius: 3px;

  /* 동적으로 입력되는 prop을 사용 */
  margin: ${props => props.size};
  padding: ${props => props.size};
`;

render(
  <div>
    <Input placeholder="A small text input" />
    <br />
    <Input placeholder="A bigger text input" size="2em" />
  </div>
);

공식 문서에서 가져온 예시이다. 

함수로 가져오게 되면 동적 속성을 정의할 수 있어서 좋아보인다.

궁금한 점은 굳이 동적 props를 정의할 필요가 있느냐이다.

그냥 태그에서 넣어도 되는 부분같다.

이에 대해서는 찾아봐야 할 것 같다.

 

- attrs 속성 override

const Input = styled.input.attrs(props => ({
  type: "text",
  size: props.size || "1em",
}))`
  border: 2px solid palevioletred;
  margin: ${props => props.size};
  padding: ${props => props.size};
`;

// Input의 속성이 먼저 적용되고, 그 후 attrs가 적용된다.
const PasswordInput = styled(Input).attrs({
  type: "password",
})`
  // Input의 border가 override되어 이 속성이 적용된다.
  border: 2px solid aqua;
`;

render(
  <div>
    <Input placeholder="A bigger text input" size="2em" />
    <br />
    {/* size 속성도 여전히 사용할 수 있다 */}
    <PasswordInput placeholder="A bigger password input" size="2em" />
  </div>
);

확장된 컴포넌트를 만들 때 attrs도 확장할 수 있다.

겹치는 속성인 경우 속성이 덮어씌워진다.

 

2.  중첩

 

export const PageContainer = styled.div`
  .password-input{
  	width: 9rem;
  }
`;

PageContainer 자식 컴포넌트를 styled-components에서 중첩으로 스타일링 할 수 있다.

다양한 선택자를 사용할 수도 있다.

 

3. 다른 styled 요소 참조하기

const Link = styled.a`
  display: flex;
  align-items: center;
  padding: 5px 10px;
  background: papayawhip;
  color: palevioletred;
`;

const Icon = styled.svg`
  flex: none;
  transition: fill 0.25s;
  width: 48px;
  height: 48px;

  ${Link}:hover & {
    fill: rebeccapurple;
  }
`;

const Label = styled.span`
  display: flex;
  align-items: center;
  line-height: 1.2;

  &::before {
    content: '◀';
    margin: 0 10px;
  }
`;

render(
  <Link href="#">
    <Icon viewBox="0 0 20 20">
      <path d="M10 15h8c1 0 2-1 2-2V3c0-1-1-2-2-2H2C1 1 0 2 0 3v10c0 1 1 2 2 2h4v4l4-4zM5 7h2v2H5V7zm4 0h2v2H9V7zm4 0h2v2h-2V7z"/>
    </Icon>
    <Label>Hovering my parent changes my style!</Label>
  </Link>
);

다른 컴포넌트를 참조하여 그 컴포넌트에 속성을 추가한다.

이것도 override처럼 뒤에 덮어씌워지는 것 같다.

 

- 같은 컴포넌트를 위치에 따라 다른 스타일로 사용

const Icon = styled.svg`
  flex: none;
  transition: fill 0.25s;
  width: 48px;
  height: 48px;
`;

const Link = styled.a`
  display: flex;
  align-items: center;
  padding: 5px 10px;
  background: papayawhip;
  color: palevioletred;
  ${Icon} {
    background-color: black;
    color: white;
  }
`;

render(
  <Link href="#">
    <Icon>
      <path d="M10 15h8c1 0 2-1 2-2V3c0-1-1-2-2-2H2C1 1 0 2 0 3v10c0 1 1 2 2 2h4v4l4-4zM5 7h2v2H5V7zm4 0h2v2H9V7zm4 0h2v2h-2V7z"/>
    </Icon>
  </Link>
    <Icon>
    <path d="M10 15h8c1 0 2-1 2-2V3c0-1-1-2-2-2H2C1 1 0 2 0 3v10c0 1 1 2 2 2h4v4l4-4zM5 7h2v2H5V7zm4 0h2v2H9V7zm4 0h2v2h-2V7z"/>
    </Icon>
);

Link에서 Icon을 참조하여 스타일을 바꾸고 있다.
이럴 경우 Link안의 Icon만 background-color, color가 적용된다.