💅 Setting up styled components with Next.js 9.5.2
Tags: nextjs, tutorial, styledcomponent, webdev
Published: 2022-01-07 12:10:46


## Step 1 - Creating a Next.js application

I just like all my development folders to be on Desktop so i do cd Desktop

```jsx
cd Desktop
npx create-next-app
//Running this script on the folder you want to store the project folder
* Will ask you whats your project name? projectName
/*
Enter the project name and it will create a folder with that name along 
with all the neccessary files
*/
```

## Step 2 - Adding styled-components library

```jsx
yarn add styled-components
```

## Step 3 - Adding developer dependency

```jsx
yarn add -D babel-plugin-styled-components
```

-D flag is used for adding the library as a developer dependency.

## Step 4 - Creating .babelrc file

To put things into perspective when working with styled components along with SSR it creates a hash (unique names) and that can get a bit tricky while debugging. This file does the following 2 things 

1. Let's babel know that styled components is to be rendered on the server side.
2. Turns displayName to true so that you can make the className more familiar.

Full documentation of the plugin can be found here:  [https://styled-components.com/docs/tooling#babel-plugin](https://styled-components.com/docs/tooling#babel-plugin)

```jsx
{
  "presets": ["next/babel"],
  "plugins": [["styled-components", { "ssr": true, "displayName": true}]]
}
```

i have seen a environment version of the same like this :

this was used so to prevent props className warning/error but however this error pops up sometimes even after adding this file.

![className warning error](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/wwg6fsrdw51niyhcyurt.png)

You can track this issue here: [https://github.com/vercel/next.js/issues/16637](https://github.com/vercel/next.js/issues/16637)

```jsx
{
   "env": {
      "development": {
         "plugins": [
            [
               "styled-components",
               { "ssr": true, "displayName": true, "preprocess": false }
            ]
         ],
         "presets": ["next/babel"]
      },
      "production": {
         "plugins": [
            [
               "styled-components",
               { "ssr": true, "displayName": true, "preprocess": false }
            ]
         ],
         "presets": ["next/babel"]
      }
   },
   "plugins": [
      [
         "styled-components",
         { "ssr": true, "displayName": true, "preprocess": false }
      ]
   ]
}
```

## Step 5 - Creating _document.js

Create a file named "_document.js" inside your pages folder.  This overrides the default Document file that is made in 

> A custom Document is commonly used to augment your application's <html> and <body> tags. This is necessary because Next.js pages skip the definition of the surrounding document's markup.
> 

> To override the default Document, create the file ./pages/_document.js and extend the Document class as shown below:
> 

You can find more on this here: [https://nextjs.org/docs/advanced-features/custom-document](https://nextjs.org/docs/advanced-features/custom-document)

```jsx
import Document, {Html, Head, Main, NextScript } from 'next/document'
import { ServerStyleSheet } from 'styled-components'

export default class MyDocument extends Document {
  static async getInitialProps(ctx) {
    const sheet = new ServerStyleSheet()
    const originalRenderPage = ctx.renderPage

    try {
      ctx.renderPage = () =>
        originalRenderPage({
          enhanceApp: (App) => (props) =>
            sheet.collectStyles(<App {...props} />),
        })

      const initialProps = await Document.getInitialProps(ctx)
      return {
        ...initialProps,
        styles: (
          <>
            {initialProps.styles}
            {sheet.getStyleElement()}
          </>
        ),
      }
    } finally {
      sheet.seal()
    }
  }
  render() {
    return (
        <Html lang="en">
            <Head />
            <body>
                <Main />
                <NextScript />
            </body>
        </Html>
    );
}
}
```

> The collectStyles method wraps your element in a provider.
> 

> getStyleElement() method that returns an array of React elements.
> 

Know more about what is severSideRendering [https://styled-components.com/docs/advanced#server-side-rendering](https://styled-components.com/docs/advanced#server-side-rendering)

## Thats it! Test it.

Now you add the following code inside index.js 

### index.js:

```jsx
import Head from 'next/head'
import styled from  'styled-components';
// Creating a styled-component
const Test = styled.p`
  font-size: 40px;
  color: blue;
`;
export default function Home() {
  return (
    <div>
      <Head>
        <title>Create Next App</title>
        <link rel="icon" href="/favicon.ico" />
      </Head>
      <main>
				{/*Testing Styled component */}
        <Test>Hello</Test>
      </main>
    </div>
  )
};
```

Once this is added go to your terminal inside your folder and run:

```jsx
$ yarn dev
// $ just mean run it inside your bash terminal you just need to copy "yarn dev"
```

Once this is done go to [https://localhost.3000](https://localhost.3000) and see your next.js app running.

![Hello world screen on local host](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/yqnk5qiy1qv8iuy9cxza.png)


## Extras: How to use Global Styles with styled components

```jsx
import { createGlobalStyle } from "styled-components";

const GlobalStyle = createGlobalStyle`
	p {
    font-size: 20;
  }
`;

function MyApp({ Component, pageProps }) {
  return (
    <>
      <GlobalStyle />
      <Component {...pageProps} />
    </>
  );
}

export default MyApp
```

### Important Pointer:

If your are watching this in future post release of Next.js 9.5.2 and its not working for some reason this is a repository that you would want to keep an eye out for any changes : [https://github.com/vercel/next.js/tree/master/examples/with-styled-components](https://github.com/vercel/next.js/tree/master/examples/with-styled-components)
###Other resources:
[https://codesandbox.io/s/github/zeit/next.js/tree/canary/examples/with-styled-components?file=/pages/index.js](https://codesandbox.io/s/github/zeit/next.js/tree/canary/examples/with-styled-components?file=/pages/index.js)

[https://dev.to/rffaguiar/nextjs-typescript-styled-components-1i3m#bonus1](https://dev.to/rffaguiar/nextjs-typescript-styled-components-1i3m#bonus1)

[https://nextjs.org/learn/basics/assets-metadata-css/global-styles (Use this even for SVG icons)](https://nextjs.org/learn/basics/assets-metadata-css/global-styles (Use this even for SVG icons))