question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Context:

  • MUI v5 beta 4
  • Nextjs
  • Using makeStyles with tss-react

I’m used to passing classes to MUI components in a classes object in order to overwrite styles. However, the Material UI default classes always seems to be appended later, causing the custom styles to be ignored.

For example:

const useStyles = makeStyles()((theme: Theme) => ({
  myButtonRoot: {
    backgroundColor: "green",
  },
}));

...

const { classes } = useStyles();

<Button color="primary" classes={{ root: classes.myButtonRoot  }}  />;

The resulting css will list that green background, but it will be overwritten by the own MUI Button styling, since that has a background of the primary theme color.

The custom makeStyles classes should come after/have priority over the default ones of that component.

Issue Analytics

  • State:closed
  • Created 2 years ago
  • Reactions:1
  • Comments:27 (16 by maintainers)

github_iconTop GitHub Comments

1reaction
janus-reithcommented, Sep 1, 2021

Hey @garronej, thanks, yes it seems to be the solution that I also found in the meantime and described above. https://github.com/garronej/tss-react/issues/17#issuecomment-904727465

That one issue however still remains unsolved if I’m not mistaken:

Before in MUIv4 with makeStyles: I could pass a root class for a Button, e.g. containing background: "red", within classes. Now if I also pass a className to that Button, with the class also being created using makeStyles, which e.g. has background: "blue", that one would have priority over what is defined within classes.

Edit: So I just verified, that only comes up when using a different cache. Using the same cache, I have the original error of classes not taking priority over MUI ones, but the className works as expected and also correctly has priority over the MUI classes.

Since emotion will derive the priority of styles based on where in the three they are defined, that still doesn’t work. Here is a simple example: My component, lets call it MyCustomButton, is a wrapper around the MUI Button and passed some classes, like a root one that defines that the Button by default is “green”. That custom component MyCustomButton just passes down all other props to the Button.

Now, I have some outer component that actually uses this Button, lets call it MyCustomPage. MyCustomPage will make use of MyCustomButton, but instead of the default green, wants it to be blue. So it defines a class with styles for a blue Button, and passes it: <MyCustomButton className={classes.blueButton}.

In v4 that would work fine. But now, the resulting button will still be green - A class definition with styles for the original green button comes later, since first the Outer styles of MyCustomPage are defined, afterwards the inner ones of MyCustomButton.

While easy to work around this in a new project, this can make things quite hard with an existing codebase and is a dealbreaker for a simple transition from v4 to v5 if that pattern was used before.

One workaround that can help: On the outer class defined in MyCustomPage, add “&&” so it gets more priority:

myClassName: {
 "&&": {
      backgroundColor: "blue"
   }
}

Looks a bit weird, but probably better than using !important on each declaration. It would end up in the resulting css as myClassName.myClassName

In a bigger project, the workflow for this can be like this:

  1. Spot all Components that use MUI components and pass classes
  2. Check each of them if they also add className, if yes add “&&”.
  3. Check each use of these components that wrap MUI Components, within order Components, if they pass props, maybe including className, and also add “&&” there.

This could cover usual usecases, but certainly not all of them. There could be situations where you have composition of multiple levels of nested styles, this could probably be covered using “&&&”, “&&&&” and so on, you get the idea.

1reaction
garronejcommented, Aug 30, 2021

I, however, opened another issue on the material-ui repo following up yours.

Read more comments on GitHub >

github_iconTop Results From Across the Web

What is the order of precedence for CSS? - Stack Overflow
A css rule with !important always takes precedence. ... The order in which the classes appear in the html element does not matter, ......
Read more >
CSS Precedence - Jenkov.com
The term CSS Precedence covers the semantics for which CSS rules takes precedence over others, when multiple CSS rules target the same HTML ......
Read more >
Specificity - CSS: Cascading Style Sheets - MDN Web Docs
Precedence over third-party CSS ... Leveraging cascade layers is the standard way of enabling one set of styles to take precedence over another ......
Read more >
Class Precedence - MATLAB & Simulink - MathWorks
MATLAB ® uses class precedence to determine which method to call when multiple classes have the same method. You can specify the relative...
Read more >
Precedence in CSS (When Order of CSS Matters)
In a preprocessor, they can. Say you want to style a thing with a variation: <div class=" ...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found