The Ultimate Guide to the Emotion CSS Library in MUI v5

MUI v5’s new styling system is built on emotion, a CSS library for writing CSS with JavaScript. I’ll show the difference in styling components using Emotion, the sx prop, and the styled API. However, there is fundamentally no difference because sx and styled both use emotion ‘under the hood’.

Here are the TextFields we’ll create. The only code difference is slight syntax variations:

TextFields styled using emotion, sx, and styled API

Here are additional useful resources:

What is Emotion CSS Library?

Emotion’s goal is to make CSS in JavaScript simple as well as bring powerful syntax tools to CSS. Here are a few examples:

  • Global Styles
  • CSS or JS syntax
  • Testing Utilities
  • Composition (my favorite)

Below is an example of style composition. We can compose individual element styling from commonly used styling objects:

const standardDiv= css`
  color: blue;
`

//JSX
<div
    css={css`
      ${standardDiv};
      background-color: gold;
    `}
  >

Why Does MUI Use Emotion CSS?

It is wise for MUI to build on top of an existing and popular CSS library. This reduces the MUI team’s development time and the amount of code they need to maintain, while giving them significant capabilities that are well tested.

MUI provides their sx and styled APIs as wrappers around Emotion. This means MUI has enhanced their APIs with MUI-specific needs (like supporting the MUI system and shorthand).

Material-UI v4 used JSS as their primary third-party CSS library. In v5 they transitioned to Emotion. Both packages are excellent, but here’s my best ideas as to why they changed:

  • 4.7 million weekly download vs 2.7 million (week of 6-14-2022)
  • Enhanced support for the styled API
  • The Emotion docs are a lot more polished

Emotion CSS in MUI Example

Emotion supports CSS syntax (using a string) and JavaScript object syntax. In the example below, I show both examples.

Here is the code for creating an MUI TextField with a gold border on hover using emotion:

import { css } from "@emotion/react";

<TextField
  // css={css`
  //   margin-bottom: 8px;
  //   & .MuiOutlinedInput-root:hover {
  //     & > fieldset {
  //       border-color: gold;
  //     },
  //   },
  // `}
  css={{
    marginBottom: "8px",
    "& .MuiOutlinedInput-root:hover": {
      "& > fieldset": {
        borderColor: "gold",
      },
    },
  }}
  id="outlined-sx"
  label="outlined tfield"
  variant="outlined"
/>

MUI Emotion vs MUI SX

Here is the sx syntax for creating the same gold border on hover:

sx={{
  marginBottom: 1,
  "& .MuiOutlinedInput-root:hover": {
    "& > fieldset": {
      borderColor: "gold",
    },
  },
}}

The code is almost identical to the object syntax with emotion. This is because sx is using emotion. However, the sx prop provides nice shorthands such as marginBottom: 1 actually applying a margin of 8px.

Another nice shorthand is access to the theme. For example, I could have used borderColor: 'secondary.main' instead of a literal color value.

MUI Emotion vs MUI Styled Components

Emotion supports styled components, and MUI has a wrapper around Emotion’s styled API. Here’s example code for creating the same gold border on hover:

const StyledTextField = styled(TextField, {
  name: "StyledTextField",
})({
  "& .MuiOutlinedInput-root:hover": {
    "& > fieldset": {
      borderColor: "gold",
    },
  },
});

//JSX
<StyledTextField variant="outlined" label="outlined tfield" />

The MUI styled API adds additional value with the options that can be passed to it. For example, we can disable the sx prop on styled components, change the labels and name of the element in the DOM, and more.

MUI’s styled components do not have quick access to the system shorthands like sx does.

Share this post:

Leave a Comment

This site uses Akismet to reduce spam. Learn how your comment data is processed.