Migrating from color styles to local variables in Figma

I don’t wanna do it; I don’t wanna do it…

Allie Paschal
UX Collective

--

As a designer, I quickly grow accustomed to doing things in a specific way…especially in Figma. Once a workflow is established and practiced, it’s hard to change that workflow even when you see the benefits of doing it in a new way. Overall, I just don’t want to relearn something I felt masterful in or be bad at something new.

That’s how I felt after viewing Figma’s keynote that kicked off Config 2023. Though the new features such as Local Variables aimed at Design Systems seemed to ultimately save time and reduce design exertion, I mainly viewed it as a new feature to learn and then re-establish my workflow within my Design System. *sighs in Figma*

Screen grab from Config 2023 Keynote where they demo the variables and easy swapping between light theme and dark theme
*My blood pressure increased during this Config keynote *

After viewing the demos provided during Config 2023, as well as Figma office hours on variables, which are all linked at the bottom of this article, I finally gave a shot at migrating our Native Mobile Design System from using color styles to local variables.

Image showing the thumbnail image for the 2.0 Native Mobile Design System
I decided to trial color variables in the Native Mobile Design System

Note: Our Native Mobile Design System is being revamped for a 2.0 version launch, so using variables for this Design System seemed like a good case to trial variables. If your Design System has a similar situation, I suggest trialing this migration in a non-critical portion of the system before deciding to migrate an entire Design System to variables.

Step 0: Primitives vs. Semantic variables

The Figma team is asking the users of local variables to use differentiating terms, Primitive and Semantic, when labelling colors, radii, margins, etc. that define and make up a Design System.

Primitives refer to the very foundational layer of a variable. The name is typically the base-token name, so it is more abstract and non-intuitive in its naming convention. An example of a primitive color would be ‘red-300’. Overall, primitives are not consumed directly by the system’s end users.

Semantics refer to the layer that is shown on components and designs. The name is intuitive and gives context on how the semantic variable should be used. Instead of ‘red-300’, the semantic name could be ‘background-error’ depending on the context of use for that color. Overall, semantics are directly consumed by the system’s end users.

So what’s the point of primitives?

Primitive variables are wired to the semantic variables, and act as the base of the system. This allows for different use cases of the same primitive variable.

So the primitive color, ‘red-300’, could be used in multiple semantic colors, such as ‘background-error’, ‘text-error’, ‘icon-error’, etc.

Ultimately, structuring the variables this way is best practice for designers and developers to use the semantic variables in the intended way, while the Design System only has to change one primitive variable to change all semantic variables wired down to it.

Image provided by Figma showing the breakdown of primitive and semantic layers; starting with the hex value of a blue color, to the design token name for a button.
Image provided by Figma showing the breakdown of primitive and semantic layers

I approached understanding and structuring variables this way in my Design System, and the following steps approach color migration using this framework.

Step 1: Create a Primitive color collection in the local variables

  • Go to the Figma file that houses your color styles, such as a Foundation or Style-guide file of the Design System.
  • Select the Local variables filter-looking icon button on the right panel of the canvas to pull up the variables in a non-modal.
  • Select the top-left dropdown to pull up a contextual menu.
  • Select ‘Create collection’, and name the collection Primitive Colors.
Image showing how to create and rename a Collection in the local variables in Figma
How to create a local variables collection in Figma

Tip: If you precede the collection name with a period (.) or underscore (_) the collection will not publish to the Design System consumers.

Image showing the Primitive collection in the local variables in Figma
A primitive collection creates the foundational layer of the Design System

Step 2: Migrate the established Design System color styles into the Primitive collection

  • Select “Create variable” at the bottom of the local variables non-modal.
  • Select “Color” for a new blank color to appear in the variable list.
  • Input the color token name in the ‘Name’ column, and the hex value in the right-most column from the color styles.
  • Repeat for all color styles within the base palette of the Design System, or equivalent foundational color palette.
Image showing how to create a color variable in Figma by selecting “Create variable” on the non-modal
Create a color variable in the Primitive collection

Tip: Keep the color token naming the same as the color style for ease of understanding during migration as well as keeping parity between color styles and color variables.

Step 3: Create groups within the Primitives collection as needed

After migrating all base color styles, you’re going to have a lot of color variables hanging out in the collection that probably has some applicable organization structure. Yes, even the primitive collection needs some level of organizing for sanity purposes.

Tip: Instead of using the modes functionality in the primitive collection, I used grouping because primitive color tokens should not be hidden by a mode at the foundational layer.

  • Select all related variables from the list, then right-click.
  • Select “New group with selection”.
  • Name the group according to previous grouping conventions or however best works for your Design System.
Image showing how to create a group within a collection of variables by right-clicking and selecting New group with selection
Organize the collection by using groups and sub-groups

Tip: Add parent-child relationships in groupings by using the forward-slash (/) to create groups and sub-groups.

Image showing that by using forward-slash in collections, you can automatically create groups and subgroups
Light theme/ Base Palette adds a group and a sub-group

Step 4: Wire the equivalent color styles to the new primitive variables

  • Return to the color styles within the Foundation or Style-guide Figma file, and edit each color style that corresponds to its color variable counterpart. I.E., ‘red-300’ color style should now be wired to the equivalent ‘red-300’ color variable.
  • Select the filter-looking icon button to pull up a non-modal with the color’s attributes.
  • Select the color box at the bottom-left of the non-modal under the “Properties” subtitle.
Image showing how to map an existing color style to a color variable by editing the color style and selecting the Properties
Map existing color styles to color variables
  • Select “Libraries” from the top-view switcher.
  • Find and select the corresponding color variable from the group you just created.
Image showing how to map existing color styles to color variables by selecting the variable from the library
Map existing color styles to color variables

Tip: Variables are distinguished in Figma by a square shape, and styles are distinguished through circle shapes.

Step 5: Repeat Step 4 as needed

After selecting the variable in Step 4, the variable and style are mapped together. So to change the color style, you must change the variable.

  • Repeat this process until all existing color styles are mapped to its corresponding Primitive color variable.

Reminder: The color styles being wired to the Primitive variables are within a base palette or foundational palette within the Design System.

Image showing that the existing color style is mapped to a variable rather than the explicit hex value
Each color style will be linked to the variable rather than an explicit hex value

Step 6: Create a Semantic color collection in local variables

  • In the same Figma file the primitive color collection is housed, create a new collection and name it ‘Semantic colors’, following Step 1.
Image showing the Semantic color collection in the local variables in Figma
Introducing the Semantic color collection

Step 7: Add semantic colors and map them to the primitive variables

  • In the same process as Step 2, add color variables to the Semantic collection and name each accordingly.
  • Instead of adding the specific hex value for the color, select the color box, then select “Libraries” at the top-switcher.
  • Find the corresponding primitive color variable and select it to map the variable to the semantic variable.
  • Repeat for all semantic colors as needed.
Image showing that the semantic variables are wired directly to primitive colors so the semantic values are not explicit hex values
Wire the Semantic colors to the Primitive colors - no hex values here!

Step 8: Create groups in the Semantic collection

This step is dependent on how you have your Design System set up to support color-specifics for icons, type, background, etc.

  • Create a group in the collection as needed, such as icons and typography.
Image showing the groups within the semantic color collection such as icons, typography, background, and greyscale
Create groups in the Semantic collection that fit your Design Systems needs

Tip: Keep naming conventions as they were in the color styles to maintain parity between variables and styles. This will help when mapping colors to components as seen in Step 13.

Step 9: Add modes to the Semantic collection per each group

The most common use case for a mode for color would be to swap between light theme and dark theme (maybe a high-contrast mode).

  • Select the plus icon button (+) at the top-right next to the column header names.
  • Name the new mode accordingly, such as ‘Dark theme’, and repeat Step 7 for the new column of variables.

Tip: The left-most mode (Light theme) will be the default or auto mode.

Image showing how to create a new mode within a collection by selecting a (+) icon button and naming the new mode to your specific needs
Select the (+) at the top-right to create a new mode for the collection

Tip: The collection must have the same modes throughout, so the groups within the collection cannot have different modes. So choose wisely and ensure the modes are scalable for the entire collection or create a new collection.

Step 10: Add scopes to the Semantic variables

As of today, 8/21 (I think), Figma variables now supports scoping. So you can control what exact elements color variables are being used.

  • Select the filter-looking icon button on the right-side of the semantic variable row.
  • Select what elements the color can be used. I.E. typography will only be used for text, so fill and stroke can be unselected.
Image showing the scoping rules you can add to a semantic color and how you can restrict a typography color to only be used for text and not for a fill or stroke color
Scoping allows for additional rules on color usage

Step 11: Wire the equivalent color styles to the new semantic variables

  • Return to the color styles within the Foundation or Style-guide Figma file, and edit each color style that corresponds to its color variable counterpart. I.E., ‘icon-error’ color style should now be wired to the equivalent ‘icon-error’ semantic variable.
  • Repeat the sub-steps from Steps 4 and 5 to wire equivalent color styles to the semantic variables.
Image showing the icon-red color style being mapped to the semantic variable for the red version for icon colors
The icon-red color style is now mapped to the Icons/red semantic variable

Note that the semantic variables are still wired to the primitive variables, so the primitive level must be changed in order to change the semantic variable once this step is done.

Step 12: Publish the local variables

  • Publish the Figma file that houses the local variables to push the changes to files wired down to the file housing the styles and variables.
  • Accept file updates that are pushed in the applicable design files.

Note that this will only publish the Semantic variables and not the Primitive variables.

Image showing how to publish your design system file housing the local variables by selecting the dropdown next to the file name at the top of the Figma canvas in the header
* This file was up-to-date so no publishing was needed *

Step 13: Test and use local variables in designs

  • Select the component or design layer to map colors to Semantic color variables.
  • Go to “Libraries” and select the corresponding color (in the square).
Image showing how to assign layers in the design to color variables
Assign layers in the design to color variables
  • Repeat as needed for each design layer.

You can see the new Variables icon on the layer section in the right-panel in Figma. Once a design layer has been assigned to the Semantic variables, you will be able to swap between the established modes.

Image showing how you can see the modes that are defined in the design on the right panel in Figma and allows you to swap between the modes through a dropdown
The modes of the layer selected will appear in the Layer section of the right panel

Tip: Keep all child layers of a frame or design on “Auto”. Only the parent frame should have the mode defined. This way, you only have to swap to the wanted mode once for the entire parent frame to swap altogether. If each layer has the mode defined, each layer will have to be swapped to the specific mode individually.

Gif showing a button component being switched between the light mode and dark mode through the right panel on the canvas in Figma
Now I can easily swap between Light theme & Dark theme

Plug-ins exist to automate this process

To start, there are multiple plug-ins available in Figma that automates the process, such as “Styles to Variable Converter” by Marcin Ukleja. But if your company does not allow external plug-ins in Figma, like mine, I provide this step-by-step guide on the manual process of migrating color styles to local variables above.

Since I haven’t used this plug-in for my Design System, I can’t specify how much re-work is needed to organize the variables to fit within your Design System’s needs. But it has been downloaded over 8,000 times at the time of this article posting, so I will give some credibility from that number.

Image showing the thumbnail of the Figma plug-in called “Styles to variables converter” which can be accessed in Figma community
Styles to Variables Converter plug-in is available in the Figma Community

Figma is not deprecating styles… for now

I wanted to clarify that Figma is not deprecating styles or forcing you to swap to variables right here, right now. Figma is still slowly rolling certain capabilities of variables out. As of now, variables do not support typography or effects like shadows, so Figma understands some teams will not want to migrate to only using variables until these features are supported.

Since variables seems like a heavily supported new feature in Figma, I don’t want to be late to the party in understanding and migrating styles to variables.

In closing

As we saw in Config 2023, variables are super powerful and have the chance to really change future design workflows in Figma. I personally didn’t think my design system should ignore variables, but you should use and do whatever works best for your Design System and your system users.

Happy variable creating!

Image showing the variables icon button in Figma with a dropdown showing the different types of variable collection that are included in the design file being viewed
Maybe variables aren’t as scary…

--

--

UX UI | Design Systems | Enterprise Products | Accessibility a11y | Figma