diff --git a/examples/with-tailwindcss-emotion/.babelrc b/examples/with-tailwindcss-emotion/.babelrc index fe1be8b87d7e9..d952dc7b6e5e3 100644 --- a/examples/with-tailwindcss-emotion/.babelrc +++ b/examples/with-tailwindcss-emotion/.babelrc @@ -1,4 +1,9 @@ { - "presets": ["next/babel"], - "plugins": [["emotion"], ["macros"]] -} + "presets": [ + "next/babel" + ], + "plugins": [ + "macros", + "@emotion/babel-plugin" + ] +} \ No newline at end of file diff --git a/examples/with-tailwindcss-emotion/README.md b/examples/with-tailwindcss-emotion/README.md index 5d5e6ac49e1c4..796cec8b50e40 100644 --- a/examples/with-tailwindcss-emotion/README.md +++ b/examples/with-tailwindcss-emotion/README.md @@ -1,6 +1,8 @@ # Tailwind CSS with Emotion.js example -This is an example of how you can add the tailwind CSS with Emotion.js in your web app. +This is an example of how you can add [tailwind CSS](https://tailwindcss.com/) with [Emotion.js](https://emotion.sh/docs/introduction) in your web app. It takes inspiration from [examples/with-tailwindcss](https://github.com/zeit/next.js/blob/canary/examples/with-tailwindcss/README.md). + +`@tailwindcssinjs/macro` is used to add tailwind classes inside Emotion by injecting the tailwind CSS into the styled component. No need to use CSS files, autoprefix, minifier, etc. You will get the full benefits of Emotion. ## Deploy your own @@ -43,10 +45,6 @@ Deploy it to the cloud with [Vercel](https://vercel.com/import?filter=next.js&ut ## Notes -This setup has inspiration from [examples/with-tailwindcss](https://github.com/zeit/next.js/blob/canary/examples/with-tailwindcss/README.md). This example will show you how to integrate [Emotion](https://emotion.sh/docs/introduction) with [tailwind](https://tailwindcss.com/). - -`tailwindcss.macros` is used to add tailwind classes inside Emotion by injecting the tailwind CSS into the styled component. No need to use CSS files, autoprefix, minifier, etc. You will get the full benefits of Emotion. - The CSS classes generated by Emotion will include the tailwind styles but not the name of the classes. For example the following component: ```jsx @@ -65,3 +63,13 @@ Will be transformed into: color: #2d3748; } ``` + +### tailwind CSS config + +Use the following command when you add a tailwind plugin that adds to tailwind's base css: + +```bash +npm run build:base-css +# or +yarn run build:base-css +``` diff --git a/examples/with-tailwindcss-emotion/babel-plugin-macros.config.js b/examples/with-tailwindcss-emotion/babel-plugin-macros.config.js deleted file mode 100644 index 24671e6d4311b..0000000000000 --- a/examples/with-tailwindcss-emotion/babel-plugin-macros.config.js +++ /dev/null @@ -1,5 +0,0 @@ -module.exports = { - tailwind: { - styled: '@emotion/styled', - }, -} diff --git a/examples/with-tailwindcss-emotion/components/ButtonCss.js b/examples/with-tailwindcss-emotion/components/ButtonCss.js new file mode 100644 index 0000000000000..68f8ddf7d3b12 --- /dev/null +++ b/examples/with-tailwindcss-emotion/components/ButtonCss.js @@ -0,0 +1,60 @@ +/* + Example with @emotion/css + + Note: configure "extractCritical" from "@emotion/server" in _document.js. + + Required packages for this component: + "@emotion/css" + "@emotion/babel-plugin" + "@emotion/server" + + These packages can be removed if you plan on only using @emotion/css API: + "@emotion/react" + "@emotion/styled" +*/ + +import { css, cx } from '@emotion/css' +import tw from '@tailwindcssinjs/macro' + +//"react native style" +const styles = { + button: css(tw` + relative + w-64 min-w-full + flex justify-center + py-2 px-4 + border border-transparent + text-sm leading-5 font-medium + rounded-md + text-white + bg-gray-600 + hover:bg-gray-500 + focus[outline-none border-gray-700 shadow-outline-gray] + active:bg-gray-700 + transition duration-150 ease-in-out + `), +} + +const ButtonCss = ({ className, children, ...props }) => ( + +) + +export default ButtonCss diff --git a/examples/with-tailwindcss-emotion/components/ButtonReact.js b/examples/with-tailwindcss-emotion/components/ButtonReact.js new file mode 100644 index 0000000000000..bc8676d6a9d10 --- /dev/null +++ b/examples/with-tailwindcss-emotion/components/ButtonReact.js @@ -0,0 +1,61 @@ +/* + Example with @emotion/react + + Required packages for this component: + "@emotion/react" + "@emotion/babel-plugin" + + These packages can be removed if you plan on only using @emotion/react API: + "@emotion/css" + "@emotion/styled" + "@emotion/server" +*/ + +/** @jsx jsx */ +import { jsx } from '@emotion/react' +import tw from '@tailwindcssinjs/macro' + +//"react native style" +const styles = { + button: tw` + relative + w-64 min-w-full + flex justify-center + py-2 px-4 + border border-transparent + text-sm leading-5 font-medium + rounded-md + text-white + bg-teal-600 + hover:bg-teal-500 + focus[outline-none border-teal-700 shadow-outline-teal] + active:bg-teal-700 + transition duration-150 ease-in-out + `, +} + +const ButtonReact = ({ className, children, ...props }) => ( + +) + +export default ButtonReact diff --git a/examples/with-tailwindcss-emotion/components/ButtonStyled.js b/examples/with-tailwindcss-emotion/components/ButtonStyled.js new file mode 100644 index 0000000000000..bf7ee608a594f --- /dev/null +++ b/examples/with-tailwindcss-emotion/components/ButtonStyled.js @@ -0,0 +1,61 @@ +/* + Example with @emotion/styled + + Required packages for this component: + "@emotion/react" + "@emotion/styled" + "@emotion/babel-plugin" + + These packages can be removed if you plan on only using @emotion/styled API: + "@emotion/css" + "@emotion/server" +*/ + +import styled from '@emotion/styled' +import tw from '@tailwindcssinjs/macro' + +const Button = styled.button(tw` + relative + w-64 min-w-full + flex justify-center + py-2 px-4 + border border-transparent + text-sm leading-5 font-medium + rounded-md + text-white + bg-indigo-600 + hover:bg-indigo-500 + focus[outline-none border-indigo-700 shadow-outline-indigo] + active:bg-indigo-700 + transition duration-150 ease-in-out +`) + +const IconWrapper = styled.span(tw` + absolute left-0 inset-y-0 + flex items-center + pl-3 +`) + +const Icon = styled.svg(tw` + h-5 w-5 + text-indigo-500 + group-hover:text-indigo-400 + transition ease-in-out duration-150 +`) + +const ButtonStyled = ({ className, children, ...props }) => ( + +) + +export default ButtonStyled diff --git a/examples/with-tailwindcss-emotion/next.config.js b/examples/with-tailwindcss-emotion/next.config.js deleted file mode 100644 index cb3db96b23bb8..0000000000000 --- a/examples/with-tailwindcss-emotion/next.config.js +++ /dev/null @@ -1,10 +0,0 @@ -module.exports = { - webpack: (config, options) => { - // Fixes npm packages that depend on `fs` module - config.node = { - fs: 'empty', - } - - return config - }, -} diff --git a/examples/with-tailwindcss-emotion/package.json b/examples/with-tailwindcss-emotion/package.json index 3cec1eaa08b39..40bfdc65e128d 100644 --- a/examples/with-tailwindcss-emotion/package.json +++ b/examples/with-tailwindcss-emotion/package.json @@ -1,23 +1,27 @@ { "name": "with-tailwindcss-emotion", - "version": "0.1.0", - "private": true, + "version": "1.0.0", "scripts": { "dev": "next dev", "build": "next build", - "start": "next start" + "start": "next start", + "build:base-css": "tailwindcss build ./styles/tailwind.base.css -o ./styles/base.css" }, "dependencies": { - "@emotion/core": "10.0.17", - "@emotion/styled": "10.0.17", + "@emotion/css": "^11.0.0-next.12", + "@emotion/react": "^11.0.0-next.12", + "@emotion/styled": "^11.0.0-next.12", "next": "latest", - "react": "16.10.1", - "react-dom": "16.10.1" + "react": "16.13.1", + "react-dom": "16.13.1" }, "devDependencies": { - "babel-plugin-emotion": "10.0.19", - "babel-plugin-macros": "2.6.1", - "tailwind.macro": "1.0.0-alpha.10", - "tailwindcss": "1.1.2" + "@babel/core": "^7.9.0", + "@emotion/babel-plugin": "^11.0.0-next.12", + "@emotion/server": "^11.0.0-next.12", + "@tailwindcss/ui": "^0.2.2", + "@tailwindcssinjs/macro": "^0.3.1", + "babel-plugin-macros": "2.8.0", + "tailwindcss": "1.3.5" } } diff --git a/examples/with-tailwindcss-emotion/pages/_app.js b/examples/with-tailwindcss-emotion/pages/_app.js new file mode 100644 index 0000000000000..6f6765667716c --- /dev/null +++ b/examples/with-tailwindcss-emotion/pages/_app.js @@ -0,0 +1,13 @@ +import Head from 'next/head' +import '../styles/base.css' + +export default function MyApp({ Component, pageProps }) { + return ( + <> + + Tailwindcss Emotion Example + + + + ) +} diff --git a/examples/with-tailwindcss-emotion/pages/_document.js b/examples/with-tailwindcss-emotion/pages/_document.js new file mode 100644 index 0000000000000..511c57db911cc --- /dev/null +++ b/examples/with-tailwindcss-emotion/pages/_document.js @@ -0,0 +1,35 @@ +// _document is only rendered on the server side and not on the client side +// Event handlers like onClick can't be added to this file + +// ./pages/_document.js +import Document, { Html, Head, Main, NextScript } from 'next/document' + +// Required for @emotion/css +import { extractCritical } from '@emotion/server' + +export default class MyDocument extends Document { + static async getInitialProps(ctx) { + const initialProps = await Document.getInitialProps(ctx) + const page = ctx.renderPage() + const styles = extractCritical(page.html) + return { ...initialProps, ...page, ...styles } + } + + render() { + return ( + + +