Customizing the Semantic UI React library with Styled Components đ«
Why:
I was trying to make some changes to a Semantic header component. Certain changes were going just fine, but other things like hover styling were giving me trouble. This led me to believe that Semantic has some !important tags under the hood, and after I went digging, I was right. Rather than change Semanticâs style rules and risk weird and unintended consequences, I (begrudgingly) settled on using an !important tag. Given the problems that those tags can cause, I knew there had to be a better way.
(Good news! There is! đ)
âïžimportant: donât use !important.
Before we can understand why we shouldnât be using !important, we first need to go over a little CSS background. CSS follows the source order rule, which refers to the order in which your style rules are read by the browser. For example:
<div class=example>
<p>This is the text inside the div</p>
</div>
HTML
.example {
color: bisque;
background: bisque;
}.example {
color: chocolate;
}
CSS
As you can see, the second instance of .example overrides the previous color rule and we get chocolate text. đ«
Now imagine you are working on a huge app with CSS scattered all over the place or buried in a style library. If our .example class has an !important tag after the bisque color, weâre stuck with bisque on bisque. While that might not be so bad on a cold winter day, it doesnât make for great web design.
So what can we do to fix this? You might think adding an !important tag to chocolate would fix things, and youâre not wrong. But youâre also not right. When multiple conflicting CSS rules have !important tags on them, it falls back to the source order rule â when everything is important, nothing is important. Youâre just digging yourself deeper into the hole.
So⊠what can we do to fix this?
As the article title suggests, one option (amongst many) is to use Styled Components. Iâll get into that in a bit. The other strategy relies on another property of CSS: specificity. Another example:
<div class=example>
<h1>This is the header tag</h1>
<p>This is just a p tag</p>
<p id=specific-id>This is a p tag with a specific ID</p>
<div/>
HTML
.example {
background: bisque;
color: bisque;
}p {
color: chocolate;
}#specific-id {
font-size: 1.5rem;
}
CSS
As you can see, the more specific our CSS gets, the finer control we have over what gets rendered. A few things are going on here:
- The h1 is getting rendered, but the text color matches the background.
- More specifically, we have told all p tags to render in chocolate color.
- Even more specific than that, anything with the #specific-id will render at a larger font size.
Take note, however, that unless we override a style rule as we get more specific, the rule will be inherited from the parent. This is why our #specific-id is still chocolate-colored, even though we didnât set that as an ID specific rule.
This strategy works fine in a pinch, but creating and managing dozens of IDs is not scalable, nor is it my idea of fun.
Styled Components đ
Styled Components is a library that âremoves the mapping between components and stylesâ. When you create a style using Styled Components, itâs just creating a normal React component with a unique style sheet. A couple of things to keep in mind:
- Each styled component you make will have a unique class that is listed after the inherited classes of the original object (if there were any). This is important, because of source order â Styled Components (aka you) get the last say in what goes on.
- Because each class is unique to the styled component, we are no longer in trouble if we need to use the !important tag. It will be scoped specifically to that component, and none other.
In practice this looks like:
Weâve used the !important tag to change the buttonâs color to chocolate, but since Styled Components manages unique class names for us, we donât need to worry about it affecting anything other buttons. All we needed to do was import the Semantic components we needed into our styledComponent.js file, and pass them into styled(). From there we can make all the changes we need, throw around !importantâs to override anything we donât want, and rest easy knowing that they won't wreak havoc on other styles.
Other bonuses:
- Just like any other component, Styled Components can be reused.
- Existing props will still work (i.e. onClick, mapping, etc.).
- They work with media queries and selectors for mobile-friendly and dynamic styling.
Did I miss anything?
This was just a brief overview of what you can do with Styled Components, but if I missed anything important, let me know! Leave a comment or tweet your answer to @serverlessgurux on Twitter.
Ben Kirby
Developer | Serverless Guru
To find out more about Serverless Guru, follow us on Medium, Twitter, Instagram, Facebook, or LinkedIn!
Thanks for reading đž