Architecting your iconography — A developer’s perspective
In a well-organized team with a dedicated UI/UX Engineer, we often layout ground rules about icons and iconography in general, however in actual implementation, we often find a wide variety of code smells varying from defining different CSS rules for each and every icon to outright being reliant on what the library provides out of the box to us.
Why does architecting this matter?
Icons play a huge role in any modern-day web application, providing quick context to the user, as a result, different parts of the system display icons in a different manner based on different contexts (based on the application state)
Having a wide variety of rules written ad-hoc at different places just means now your frontend is very difficult to change and new developers will often find it difficult to ensure that changes at one place don’t affect other places OR they outright will be unaware of all the different CSS files they need to touch in order to make an application-wide rule change.
How does one actually go about doing this
This article will be laying out one of several different ways of having your iconography architected in a rather sustainable fashion, but with any software architectural pattern, there will be some downsides associated with it & we will touch on the downsides of this particular technique towards the end of this article.
We start off by defining the global Icons.sass file (I am using SASS for this example)
Icons can vary in mainly three different forms -
- Size (This also includes padding and margins)
- Color
- Interactions
We want our Icons.sass to encompass all of these elements in a single source of truth.
Let us start off by defining the root and all the parameters,
.icon /** Icon Colors */
&__delete
color: insert-color-variable-here
&__info
color: insert-color-variable-here
&__action
color: insert-color-variable-here/** Icon Sizes */
&__small
height: insert-size-variable-here
width: insert-size-variable-here
&__medium
height: insert-size-variable-here
width: insert-size-variable-here/** Icon Spacing */
&__button
padding: insert-spacing-variable-here/** Interactions */
&__clickable
cursor: pointer
Thus we define a few different types of icons and some sizing variables here.
We can now use these variables for any icon across the application like
<MyIcon className="icon__small icon__info icon__clickable" />
This essentially defines a small icon, which is of the “info” type and is clickable.
There are some noticeable upsides to this right-off the bat -
- Readability is fairly high, all that I need to know about this icon’s properties is right there in front of me
- Icons across the app are consistent, no developer can accidentally make a small icon that’s different than the app-wide standard.
- If large UI rehauls are necessary, changing iconography rules entails just changing details in one file and you’re golden!
- Other SASS files don’t have to necessarily deal with adding specific code blocks dedicated to the icons that the page serves, thereby reducing the amount of code to be written (and thus maintained)
As I mentioned though, there are some inherent downsides to this
- Your JSX for fairly complicated Icons will be large since you now need to write in multiple class names
- For icons that are outliers altogether, you might still have to write separate rules (Although at this point you might also want to have a chat with your designer)
All in all, this is still a great way to reduce code debt for your iconography and if slightly large jsx elements don’t bother you, this would be worth giving a shot!