ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • TIL-2024.05.06 - React - 012. Styled Component - basic- 1
    > Frontend/React 2024. 5. 8. 07:07

     

     

     

    질문

    1. Styled Component ( Css-in-JS) 에 대해 좀 더 자세히 알려줘 

     

     

    참조 사이트:

    https://styled-components.com/docs/basics#motivation

     

    styled-components: Basics

    Get Started with styled-components basics.

    styled-components.com

     

     

     

    시작하기

    - styled-components는 태그드 템플릿 리터럴을 사용하여 컴포넌트를 스타일링합니다. 

    - 이를 통해 컴포넌트와 스타일 간의 매핑을 제거합니다.

    - 즉, 스타일을 정의할 때 실제로는 스타일이 적용된 일반적인 리액트 컴포넌트를 생성합니다.

    - 다음 예제는 스타일이 적용된 두 가지 간단한 컴포넌트, 래퍼(wrapper)와 타이틀(title)을 만드는 방법을 보여줍니다.

     

     

    예제

    import styled, {css} from "styled-components";
    
    const GettingStarted = () => {
        // Create a Wrapper component that'll render a <section> tag with some styles
        const Wrapper = styled.section`
            padding: 4em;
            background: papayawhip;
        `;
    
        // Create a Title component that'll render an <h1> tag with some styles
        const Title = styled.h1`
            font-size: 1.5em;
            text-align: center;
            color: #BF4F74;
        `;
    
    
        // Use Title and Wrapper like any other React component – except they're styled!
        return (
            <Wrapper> {/*위에서 설정된 Section Tag 로 설정 */}
                <Title> {/*위에서 설정된 h1 Tag 로 설정 */}
                    Hello World!
                </Title>
            </Wrapper>);
    };
    
    export default GettingStarted;

     

     

    Prop 에 따라 적용

    - 스타일드 컴포넌트의 템플릿 리터럴에 함수("보간")를 전달하여 프롭에 따라 적응할 수 있습니다.

    - 이 버튼 컴포넌트는 기본 상태(primary)에 따라 색상이 변경됩니다.

    - $primary 프롭을 true로 설정하면 배경색과 텍스트 색상이 바뀝니다.

     

     

    예제

    import styled, {css} from "styled-components";
    
    
    const AdaptingProps = () => {
        const Button = styled.button`
            /* Adapt the colors based on primary prop */
            background: ${props => props.$primary ? "#BF4F74" : "white"};
            color: ${props => {return props.$primary ? "white" : "#BF4F74" }};
            // 해당 버튼이 $primary prop을 가지고 있는지 여부를 나타냄
    
            font-size: 1em;
            margin: 1em;
            padding: 0.25em 1em;
            border: 2px solid #BF4F74;
            border-radius: 3px;
        `;
        return (<div>
            <Button>Normal</Button>
            <Button $primary>Primary</Button> {/* 여기서 $primary 로 전달 */}
        </div>);
    };
    
    export default AdaptingProps;

     

     

     

    스타일 확장 

    - 가끔은 컴포넌트를 사용하지만 특정한 경우에는 약간 수정해야 할 때가 있습니다. 

    - 다른 컴포넌트의 스타일을 상속하는 새로운 컴포넌트를 쉽게 만들려면, 해당 컴포넌트를 styled() 생성자로 래핑하면 됩니다.

    - 여기서는 이전 섹션에서 사용한 버튼을 가져와 색상 관련 스타일을 추가하여 특별한 버튼을 만듭니다.

     

    - 또한, 때로는 styled-components가 렌더링하는 요소나 컴포넌트를 변경하고 싶을 수 있습니다. 

    - 예를 들어 내비게이션 바를 구성할 때, 앵커 링크와 버튼이 혼합되어 있지만 모두 동일하게 스타일이 적용되어야 하는 경우가 있습니다.

    - 이러한 상황에 대비하여 탈출구가 있습니다. "as" 다형성 프롭을 사용하여 작성한 스타일을 받는 요소를 동적으로 바꿀 수 있습니다.

    - 커스텀 컴포넌트에서도 정상 작동

     

     

    예제

    import styled, {css} from "styled-components";
    
    const ExtendingProps = () => {
        // The Button from the last section without the interpolations
        const Button = styled.button`
            color: #BF4F74;
            font-size: 1em;
            margin: 1em;
            padding: 0.25em 1em;
            border: 2px solid #BF4F74;
            border-radius: 3px;
        `;
    
        // A new component based on Button, but with some override styles
        const TomatoButton = styled(Button)`
            color: tomato;
            border-color: tomato;
        `;
    
        //  ReversedButton 함수는 주어진 Button 컴포넌트를 사용하며, props를 전달하고 children prop의 문자열을 반전시킵니다.
        // 중요 포인트
        // 1. ReversedButton 함수는 props를 매개변수로 받아, 기존에 설정된 Button 컴포넌트를 사용하여 새로운 버튼을 생성.
        // 2. ReversedButton 함수는 children prop을 반전
        const ReversedButton = props => {
            // props: {children : "Custom Button", className : "sc-ispPvw hKckZl"}
            return <Button {...props} children={props.children.split('').reverse()}/>;
        };
    
        return (<div>
            <Button>Normal Button</Button>
            {/* "as" 다형성(prop)을 사용해 스타일이 적용되는 요소 또는 컴포넌트를 변경 > button tag -> a tag 로 변경하되, css 유지*/}
            <Button as="a" href="#">Link with Button styles</Button>
            <TomatoButton as={ReversedButton}>Reversed Custom Button</TomatoButton>
            <TomatoButton>Tomato Button</TomatoButton>
        </div>);
    };
    
    
    export default ExtendingProps;

     

     

     

    모든 컴포넌트 Styling

    - styled 메서드는 사용자가 직접 만든 컴포넌트나 서드파티 컴포넌트 모두에 완벽하게 작동합니다.

    - 단, 해당 컴포넌트가 전달된 className prop을 DOM 요소에 첨부해야 합니다.

     

    import styled, {css} from "styled-components";
    
    const StylingAnyComponent = () => {
        // This could be react-router-dom's Link for example
        const Link = ({className, children}) => (
            <a className={className}>
                {children}
            </a>
        );
    
        const StyledLink = styled(Link)`
            color: #BF4F74;
            font-weight: bold;
        `;
    
        return (<div>
            <Link>Unstyled, boring Link</Link>
            <br/>
            <StyledLink>Styled, exciting Link</StyledLink>
        </div>);
    };
    
    
    export default StylingAnyComponent;

     

     

     

    애니메이션 

    - CSS 애니메이션인 @keyframes는 단일 컴포넌트에 범위가 지정되지 않지만 이름 충돌을 피하기 위해 전역이 되어서는 안됩니다. 

    - 이것이 우리가 고유한 인스턴스를 생성하여 앱 전체에서 사용할 수 있는 keyframes 도우미를 내보내는 이유입니다.

     

    예제 1

    import styled, {css, keyframes} from "styled-components";
    
    const Animation = () => {
        // Create the keyframes
        const rotate = keyframes`
            from {
                transform: rotate(0deg);
            }
            to {
                transform: rotate(360deg);
            }
        `;
    
        // Here we create a component that will rotate everything we pass in over two seconds
        const Rotate = styled.div`
            display: inline-block;
            animation: ${rotate} 2s linear infinite;
            padding: 2rem 1rem;
            font-size: 1.2rem;
        `;
    
        return (<Rotate>&lt; 💅🏾 &gt;</Rotate>);
    };
    
    export default Animation;

     

     

     

    - keyframes는 사용될 때 지연되어 주입되므로 코드 분할이 가능하며, 따라서 공유 스타일 조각에 대해서는 css 도우미를 사용해야 함

     

     

     

    예제2

    import styled, {keyframes, css} from 'styled-components';
    
    const Animation2 = () => {
        // Create the keyframes
        const rotate = keyframes`
            from {
                transform: rotate(0deg);
            }
    
            to {
                transform: rotate(360deg);
            }
        `;
    
        // ❌ This will throw an error!
        // const styles = `
        //   animation: ${rotate} 2s linear infinite;
        // `
    
        // ✅ This will work as intended
        const styles = css`
            animation: ${rotate} 2s linear infinite;
        `;
    
        // Here we create a component that will rotate everything we pass in over two seconds
        const Rotate = styled.div`
            display: inline-block;
            ${styles}
            padding: 2rem 1rem;
            font-size: 1.2rem;
        `;
    
        return (<Rotate>&lt; 💅🏾 &gt;</Rotate>);
    
    };
    
    export default Animation2;
     

     

     

     

     

    댓글

Designed by Tistory.