Search code examples
javascriptreactjsreduxcomponentsstyled-components

React - How to add new styles to a component using styled-component


I am using Styled components. I have two components Navbar and Lessons

Navbar.jsx

import React, {Fragment} from 'react';
import n from './Navbar.module.css';
import logo from '../../backgrounds/myLogo2.png'
import {NavLink} from 'react-router-dom';
import styled from "styled-components";

export const NavBarPageLogoDivContainer = styled.div`
 &.LogoDivContainer {
    flex: 1;
  }
`;

export const Navbar = (props) => {
    return (
        <Fragment>
            <div>
                <header>
                    <NavBarPageLogoDivContainer className={"LogoDivContainer"}>
                        <NavLink className={n.logo} to={'/content'}>
                            <img style={{margin: 'auto', marginTop: "0", width: "150px", maxWidth: "100%"}} src={logo}
                                 alt="logo"/>
                        </NavLink>
                    </NavBarPageLogoDivContainer>
                </header>
            </div>
        </Fragment>
    );
}

Lessons.jsx

import React from 'react';
import {Navbar, NavBarPageLogoDivContainer} from "../../../Navbar/Navbar";
import styled from "styled-components";

export class Lessons extends React.Component {
    render() {
        return (
            <>
                <Navbar />
            </>
        );
    }
}

I deliberately removed the rest of the jsx from these components to make the code easier to read. Please pay attention to the "NavBarPageLogoDivContainer" in Navbar.jsx, where I specified the value "flex: 1". When I imported the Navbar into the Lesson component I want to add new styles for the "NavBarPageLogoDivContainer", for example background, border, padding. how can I do it?


Solution

  • You can use styled as a function:

    const myNewlyStyledComponent = styled(NavBarPageLogoDivContainer)`
    background-color: "red";
    height: 0%;
    `
    

    and then use the myNewlyStyledComponent in the rendering part.

    To use your new component in the snippet you should change the code:

    Navbar.jsx

    import React, {Fragment} from 'react';
    import n from './Navbar.module.css';
    import logo from '../../backgrounds/myLogo2.png'
    import {NavLink} from 'react-router-dom';
    import styled from "styled-components";
    
    export const NavBarPageLogoDivContainer = styled.div`
     &.LogoDivContainer {
        flex: 1;
      }
    `;
    
    export const Navbar = ({CustomNavBarLogoDivContainer}) => {
        const InjectedContainer = CustomNavBarLogoDivContainer ?? NavBarPageLogoDivContainer
    
        return (
            <Fragment>
                <div>
                    <header>
                        <InjectedContainer className={"LogoDivContainer"}>
                            <NavLink className={n.logo} to={'/content'}>
                                <img style={{margin: 'auto', marginTop: "0", width: "150px", maxWidth: "100%"}} src={logo}
                                     alt="logo"/>
                            </NavLink>
                        </InjectedContainer>
                    </header>
                </div>
            </Fragment>
        );
    }
    

    now you can parametrize the navbar with the enhanced component:

    Lesson.jsx

    import React from 'react';
    import {Navbar, NavBarPageLogoDivContainer} from "../../../Navbar/Navbar";
    import styled from "styled-components";
    
    const myNewlyStyledComponent = styled(NavBarPageLogoDivContainer)`
    background-color: "red";
    `
    
    export class Lessons extends React.Component {
        render() {
            return (
                <>
                    <Navbar 
                         CustonNavBarLogoDivContainer={myNewlyStyledComponent}
                    />
                </>
            );
        }
    }
    

    Here in react docs you can read briefly about composition