Design system

User Testing

Product Design

Inputs and selections: Text input V2

Designing for improved accessibility, consistency and ease of implementation.

My role

Lead Product Designer

The team

-

Product Manager

-

React (Web) and Flutter (App) Engineers

-

Accessibility Specialist

Background

We’re rebuilding our three-year-old text input component to address its limitations and align with modern design, accessibility, and tech standards.

The current version lacks flexibility, has accessibility gaps, and doesn’t meet today’s theming or usability needs.

 

The new version will improve performance, customisation, and developer experience - while laying the groundwork for updating other input and selection components.

This marks the first step in modernising our design system, ensuring consistency, scalability, and future readiness across components like multi-line inputs, radio buttons, and checkboxes.

Project goals

01

Flexibility

Support flexibility and scalability, allowing the component to adapt to a range of use cases.

02

Consistency and maintainability

Drive consistency across products by providing a unified, reusable component that will reduce design and development time. Ensuring a cohesive user experience that leverages existing tokens and components from the design system for easier adoption and maintainability.

03

Accessibility

Ensure full support for WCAG 2.1 and ARIA standards to provide a more inclusive experience for all users.

04

Documentation

The component needs to have new documentation on our design system guidance site, where designers (product and content) and developers can refer to for correct usage.

05

Revaluate the Form control componet

Currently used by all of our inputs and selections components that contain a label, helper text, legend and error message. This will need updating as part of this first V2 update to the component category, as it will be needed for updating the rest of the components.

The current text input component

I started by asking the design community in Slack channels to share their existing work, where they had used or detatched the current text input, created custom components or detache. I then compiled them into a file to document common themes, features and use cases.

Discovery

Identifying what our current component can’t achieve in designers work

I started by asking the design community in Slack channels to share their existing work, where they had used or detached the current text input, or even created custom components. I then compiled them into a file to document common themes, features and use cases.

-

Leading and trailing assets: I saw a lot of designers adding custom assets to the start or end of the text input container. A huge standout was designers adding a hide/show password icon button.

-

Prefix’s and suffix’s: Things like measurements and currencies had been placed before and after the input. As well as before and after the input text within the input container.

-

Optional vs Required: Arguably the most controversial pattern I had found. Although our current component uses ‘optional’, a good amount of designers had been replacing this text (at the end of label) to an asterisk. So this would only appear on required inputs and optional inputs would have no visual queue. Its often removed as its not in its own container as its in the same text line as the label - so once overridden you can’t get it back unless you reset the component.

-

Search bars: I had come across text inputs being modified into search bars, which were never their intended purpose.

-

Region flags: Being a telco, requires users a lot of the time to select their region flag at the start of the component before typing in there phone number.

-

Input formatting: Another popular one was designers wanting to have automatic spacings or dashes between chunks of text in an input. E.g: Birthdays - dd/mm/yyyy or Card details 00-00-00.

-

Multiple inputs in a row: Similar to the point above, designers were segmenting their inputs into increments. E.g Birthday [dd] [mm] [yyyy].

-

Links within labels: This was never addressed in the original/current guidance, however was a popular pattern I had been spotting.

-

Placing on all surfaces: Recently as a design system team we have tried to make our components adapt to all surfaces. Meaning components can sit on neutral light and dark surfaces as well as our coloured ones. The current component ‘should’ only sit on default and fog surfaces, which are neutral light surfaces, and are dark surfaces in dark mode.

-

PIN codes: Finally another common theme was designers using custom ‘segmented’ inputs in a row to create PIN inputs. For example a 4 digit PIN to log into the app or a number for 2 factor authentication.

-

Success state: The current component only has an error state for its ‘status states’. I had spotted one designer had created a live username authenticator.

Optional vs Required*

The proposed colour that had been put forward by brand and the agency is a blend of our ‘Fog’ surface colour (Source/Grey/01) and Primary brand colour (Source/Aqua/05).

 

Information on the specific blend wasn’t available to us, so we had to get as close to #DEE7E8 as we could ourselves.

 

However this was an opportunity to refine it and propose a more appropriate colour to be used in all of our digital journy’s on web and app.

Components use labels

-

Text input

-

Multi-line text input

-

Select field

-

Radio button

-

Checkbox

Reasons to keep optional

-

We should only be asking for necessary information, so the number of required

fields should be greater than the number of optional fields in most cases.

-

Therefore labelling optional reduces visual clutter and distraction for

users.

-

Clutter / distraction would be particularly high if fields were marked with

(required).

-

This has led to the suggestion to use an * to indicate required. However, while this would be WCAG compliant, there are reasons to believe it is not the optimum user experience. It may be confusing to some users depending on the journey squad remembering to add ‘Field marked with an * are required’ in the relevant place.

-

There are some examples (like the outlier, above) where labelling as required

could be ambiguous.

-

Introduces an element not designed for and not tested in journey squad experiences.

Additional complexities if Loop were to update current input logic:

-

If we use *, squads will need to go and add the definition to all existing forms -

realistically, this is unlikely to happen due to priorities/capacity, so the risk of

confusing users with an undefined * is high.

-

Could also cause layout issues if it makes legend go onto two lines?

If Loop releases new versions of inputs:

-

Adoption is likely to be slow, especially as squads won’t be able to ‘mix and match’ v1 and v2 inputs due to change in logic (plus planned visual style updates).

-

We may need to add the ‘hide optional label’ prop to existing components to enable

Learn and Browse, if we aren’t going to be able to decide or implement the ultimate

solution quickly

A couple of issues with optional

-

In instances where forms are obviously optional such as:

-

Entering your email to log in.

-

Or selecting a checkbox in a filtering menu.

What we chose in the end?

After evaluating the above and investigating the pros and cons of both optional and required. The benefits of keeping ‘optional’ outweighed the cons, and time, effort and resource it would require to update all of our existing components, as well as communicating these changes to hundreds of designers and developers.

 

This all means we chose to keep the optional method, however it would be restyled as an update. and have the ability to keep an input optional, but have a property to hide the word in certain scenarios like the ones outlined above. There would need to be strict guidance on how to use this.

Design exploration

During my design exploration I got an accessibility specialist involved early on to help guide and shape the design and decisions I was making.

 

‘Placeholder text’ was something that I experimented with, however this use of text is not ideal for screen readers or anyone else for that matter, as it disappears when you focus on the input.

 

Currently we only have an error state, so I explored a ‘success’ state, because this was something I had seen in my discovery work. Unfortunately the squad decided that this was not a major priority and was out of scope for the first version of this new release. However it is something that could come in the future if there is a bigger demand for it.

 

Another thing I experimented with was the use of animation - In particular, having the label move to the top when focussed. This would also shrink from 16px to 12px to make it fit within the input - this was a big no also because we stick to a text size of 16px for the majority of the website and app.

Evaluating text input groups (and the rest of the input groups)

Currently there are technically two text input components: A single one and a group with a legend at the top (part of form control).

 

This is a pre assembled component in Figma and code. I wondered how used it was so I checked Figma’s (very limited) analytics, and it turns out it hadn’t been used much at all.

 

I reached out to the design community and asked what designers thoughts were on the component and their experience using it.

 

It was clear the component lacked flexibility - designers were unable to reorder the list due to Figma limitations with component auto layout. They were also unable to place two inputs side by side on a row without breaking/detaching the group.

The idea

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate competent so that designers could place at the top of the group themselves.

 

Guidance on how to assemble these groups and space the inputs would be outlined on the design system website for designers to refer to.

 

Text input group in React and Flutter already has all this flexibility so will remain, however with individual updates to the text inputs.

Refinement

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate compenent

The build

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate compenent

Dev handover and build

I created a specification document for the React and Flutter engineers along with walking them through the design, properties and highlighting what tokens were used.

 

Once built, we now had two consistent components across three platforms: Figma, React and Flutter (React=Web, and Flutter=App with light and dark mode).

 

Product designers, content designers and anyone who wanted to could now log in to the React Storybook and Flutter Playground to play around with the components and configure them in many different ways. This especially useful to use if a designer was unsure how far a component could flex in live.

 

Often Figma allows designers to flex components too much, so by adding these links in the component documentation in Figma - we were able to encourage designers to experiment outside of Figma.

Guidance documentation

All documentation is stored on our guidance site (Zeroheight) and contains all links to the component across the three platforms. Below is a few screenshots of the guidance me and the content designer created.

 

In our design system we only release a component when it is available across Figma, React, Flutter and Guidance. The same goes for any updates we make in the future.

Deprecating the old componets

With the release of the V2 components, we had to phase out the old components. We did this by marking the component names with [To be removed] and a ‘. ‘ at the start to hide from publishing.

Designers were still able to use this component in their files that it already existed in, however when they went to drag in a new one from the assets panel, only the V2 one would be available.

I also added a deprecation message in the components description in Figma, and linking to the new component and guidance.

The guidance was also deprecated as ‘legacy’ - this meant that it could still be referred to if need be, rather than removing entirely. We will most likely remove at the next major release.

The rest of Inputs and selections components updates

After creating the new version of Text input and Form control, I was tasked to uplift the rest of the component family an guidance - Here is a sneak peak.

Things that didn’t go to plan

Due to our Loop standard of having 48x48px touch targets we were unable to make our Icon buttons (both size Medium and Small0 smaller within the input. The decision I made was to use what we had available already instead of creating anything custom. And we’ll revisit the Icon button components again at a later date.

 

The WCAG guidance states that touch targets can be as small as 24x24px, so we might want to meet half way and do some testing on 32x32px touch targets.

Let’s get to know each other.

Get in touch!

Copyright © 2025 Stefan Adams. All rights reserved.

All illustrations are created by me.

I create better experiences for People.

Design system

User Testing

Product Design

Inputs and selections: Text input V2

Designing for improved accessibility, consistency and ease of implementation.

My role

Lead Product Designer

The team

-

Product Manager

-

React (Web) and Flutter (App) Engineers

-

Accessibility Specialist

Background

We’re rebuilding our three-year-old text input component to address its limitations and align with modern design, accessibility, and tech standards.

The current version lacks flexibility, has accessibility gaps, and doesn’t meet today’s theming or usability needs.

 

The new version will improve performance, customisation, and developer experience - while laying the groundwork for updating other input and selection components.

This marks the first step in modernising our design system, ensuring consistency, scalability, and future readiness across components like multi-line inputs, radio buttons, and checkboxes.

Project goals

01

Flexibility

Support flexibility and scalability, allowing the component to adapt to a range of use cases.

02

Consistency and maintainability

Drive consistency across products by providing a unified, reusable component that will reduce design and development time. Ensuring a cohesive user experience that leverages existing tokens and components from the design system for easier adoption and maintainability.

03

Accessibility

Ensure full support for WCAG 2.1 and ARIA standards to provide a more inclusive experience for all users.

04

Documentation

The component needs to have new documentation on our design system guidance site, where designers (product and content) and developers can refer to for correct usage.

05

Revaluate the Form control componet

Currently used by all of our inputs and selections components that contain a label, helper text, legend and error message. This will need updating as part of this first V2 update to the component category, as it will be needed for updating the rest of the components.

The current text input component

I started by asking the design community in Slack channels to share their existing work, where they had used or detatched the current text input, created custom components or detache. I then compiled them into a file to document common themes, features and use cases.

Discovery

Identifying what our current component can’t achieve in designers work

I started by asking the design community in Slack channels to share their existing work, where they had used or detached the current text input, or even created custom components. I then compiled them into a file to document common themes, features and use cases.

-

Leading and trailing assets: I saw a lot of designers adding custom assets to the start or end of the text input container. A huge standout was designers adding a hide/show password icon button.

-

Prefix’s and suffix’s: Things like measurements and currencies had been placed before and after the input. As well as before and after the input text within the input container.

-

Optional vs Required: Arguably the most controversial pattern I had found. Although our current component uses ‘optional’, a good amount of designers had been replacing this text (at the end of label) to an asterisk. So this would only appear on required inputs and optional inputs would have no visual queue. Its often removed as its not in its own container as its in the same text line as the label - so once overridden you can’t get it back unless you reset the component.

-

Search bars: I had come across text inputs being modified into search bars, which were never their intended purpose.

-

Region flags: Being a telco, requires users a lot of the time to select their region flag at the start of the component before typing in there phone number.

-

Input formatting: Another popular one was designers wanting to have automatic spacings or dashes between chunks of text in an input. E.g: Birthdays - dd/mm/yyyy or Card details 00-00-00.

-

Multiple inputs in a row: Similar to the point above, designers were segmenting their inputs into increments. E.g Birthday [dd] [mm] [yyyy].

-

Links within labels: This was never addressed in the original/current guidance, however was a popular pattern I had been spotting.

-

Placing on all surfaces: Recently as a design system team we have tried to make our components adapt to all surfaces. Meaning components can sit on neutral light and dark surfaces as well as our coloured ones. The current component ‘should’ only sit on default and fog surfaces, which are neutral light surfaces, and are dark surfaces in dark mode.

-

PIN codes: Finally another common theme was designers using custom ‘segmented’ inputs in a row to create PIN inputs. For example a 4 digit PIN to log into the app or a number for 2 factor authentication.

-

Success state: The current component only has an error state for its ‘status states’. I had spotted one designer had created a live username authenticator.

Optional vs Required*

The proposed colour that had been put forward by brand and the agency is a blend of our ‘Fog’ surface colour (Source/Grey/01) and Primary brand colour (Source/Aqua/05).

 

Information on the specific blend wasn’t available to us, so we had to get as close to #DEE7E8 as we could ourselves.

 

However this was an opportunity to refine it and propose a more appropriate colour to be used in all of our digital journy’s on web and app.

Components use labels

-

Text input

-

Multi-line text input

-

Select field

-

Radio button

-

Checkbox

Reasons to keep optional

-

We should only be asking for necessary information, so the number of required

fields should be greater than the number of optional fields in most cases.

-

Therefore labelling optional reduces visual clutter and distraction for

users.

-

Clutter / distraction would be particularly high if fields were marked with

(required).

-

This has led to the suggestion to use an * to indicate required. However, while this would be WCAG compliant, there are reasons to believe it is not the optimum user experience. It may be confusing to some users depending on the journey squad remembering to add ‘Field marked with an * are required’ in the relevant place.

-

There are some examples (like the outlier, above) where labelling as required

could be ambiguous.

-

Introduces an element not designed for and not tested in journey squad experiences.

Additional complexities if Loop were to update current input logic:

-

If we use *, squads will need to go and add the definition to all existing forms -

realistically, this is unlikely to happen due to priorities/capacity, so the risk of

confusing users with an undefined * is high.

-

Could also cause layout issues if it makes legend go onto two lines?

If Loop releases new versions of inputs:

-

Adoption is likely to be slow, especially as squads won’t be able to ‘mix and match’ v1 and v2 inputs due to change in logic (plus planned visual style updates).

-

We may need to add the ‘hide optional label’ prop to existing components to enable

Learn and Browse, if we aren’t going to be able to decide or implement the ultimate

solution quickly

A couple of issues with optional

-

In instances where forms are obviously optional such as:

-

Entering your email to log in.

-

Or selecting a checkbox in a filtering menu.

What we chose in the end?

After evaluating the above and investigating the pros and cons of both optional and required. The benefits of keeping ‘optional’ outweighed the cons, and time, effort and resource it would require to update all of our existing components, as well as communicating these changes to hundreds of designers and developers.

 

This all means we chose to keep the optional method, however it would be restyled as an update. and have the ability to keep an input optional, but have a property to hide the word in certain scenarios like the ones outlined above. There would need to be strict guidance on how to use this.

Design exploration

During my design exploration I got an accessibility specialist involved early on to help guide and shape the design and decisions I was making.

 

‘Placeholder text’ was something that I experimented with, however this use of text is not ideal for screen readers or anyone else for that matter, as it disappears when you focus on the input.

 

Currently we only have an error state, so I explored a ‘success’ state, because this was something I had seen in my discovery work. Unfortunately the squad decided that this was not a major priority and was out of scope for the first version of this new release. However it is something that could come in the future if there is a bigger demand for it.

 

Another thing I experimented with was the use of animation - In particular, having the label move to the top when focussed. This would also shrink from 16px to 12px to make it fit within the input - this was a big no also because we stick to a text size of 16px for the majority of the website and app.

Evaluating text input groups (and the rest of the input groups)

Currently there are technically two text input components: A single one and a group with a legend at the top (part of form control).

 

This is a pre assembled component in Figma and code. I wondered how used it was so I checked Figma’s (very limited) analytics, and it turns out it hadn’t been used much at all.

 

I reached out to the design community and asked what designers thoughts were on the component and their experience using it.

 

It was clear the component lacked flexibility - designers were unable to reorder the list due to Figma limitations with component auto layout. They were also unable to place two inputs side by side on a row without breaking/detaching the group.

The idea

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate competent so that designers could place at the top of the group themselves.

 

Guidance on how to assemble these groups and space the inputs would be outlined on the design system website for designers to refer to.

 

Text input group in React and Flutter already has all this flexibility so will remain, however with individual updates to the text inputs.

Refinement

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate compenent

The build

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate compenent

Dev handover and build

I created a specification document for the React and Flutter engineers along with walking them through the design, properties and highlighting what tokens were used.

 

Once built, we now had two consistent components across three platforms: Figma, React and Flutter (React=Web, and Flutter=App with light and dark mode).

 

Product designers, content designers and anyone who wanted to could now log in to the React Storybook and Flutter Playground to play around with the components and configure them in many different ways. This especially useful to use if a designer was unsure how far a component could flex in live.

 

Often Figma allows designers to flex components too much, so by adding these links in the component documentation in Figma - we were able to encourage designers to experiment outside of Figma.

Guidance documentation

All documentation is stored on our guidance site (Zeroheight) and contains all links to the component across the three platforms. Below is a few screenshots of the guidance me and the content designer created.

 

In our design system we only release a component when it is available across Figma, React, Flutter and Guidance. The same goes for any updates we make in the future.

Deprecating the old componets

With the release of the V2 components, we had to phase out the old components. We did this by marking the component names with [To be removed] and a ‘. ‘ at the start to hide from publishing.

Designers were still able to use this component in their files that it already existed in, however when they went to drag in a new one from the assets panel, only the V2 one would be available.

I also added a deprecation message in the components description in Figma, and linking to the new component and guidance.

The guidance was also deprecated as ‘legacy’ - this meant that it could still be referred to if need be, rather than removing entirely. We will most likely remove at the next major release.

The rest of Inputs and selections components updates

After creating the new version of Text input and Form control, I was tasked to uplift the rest of the component family an guidance - Here is a sneak peak.

Things that didn’t go to plan

Due to our Loop standard of having 48x48px touch targets we were unable to make our Icon buttons (both size Medium and Small0 smaller within the input. The decision I made was to use what we had available already instead of creating anything custom. And we’ll revisit the Icon button components again at a later date.

 

The WCAG guidance states that touch targets can be as small as 24x24px, so we might want to meet half way and do some testing on 32x32px touch targets.

Let’s get to know each other.

Get in touch!

Copyright © 2025 Stefan Adams. All rights reserved.

All illustrations are created by me.

I create better experiences for People.

Design system

User Testing

Product Design

Inputs and selections: Text input V2

Designing for improved accessibility, consistency and ease of implementation.

My role

Lead Product Designer

The team

-

Product Manager

-

React (Web) and Flutter (App) Engineers

-

Accessibility Specialist

Background

We’re rebuilding our three-year-old text input component to address its limitations and align with modern design, accessibility, and tech standards.

The current version lacks flexibility, has accessibility gaps, and doesn’t meet today’s theming or usability needs.

 

The new version will improve performance, customisation, and developer experience - while laying the groundwork for updating other input and selection components.

This marks the first step in modernising our design system, ensuring consistency, scalability, and future readiness across components like multi-line inputs, radio buttons, and checkboxes.

Project goals

01

Flexibility

Support flexibility and scalability, allowing the component to adapt to a range of use cases.

02

Consistency and maintainability

Drive consistency across products by providing a unified, reusable component that will reduce design and development time. Ensuring a cohesive user experience that leverages existing tokens and components from the design system for easier adoption and maintainability.

03

Accessibility

Ensure full support for WCAG 2.1 and ARIA standards to provide a more inclusive experience for all users.

04

Documentation

The component needs to have new documentation on our design system guidance site, where designers (product and content) and developers can refer to for correct usage.

05

Revaluate the Form control componet

Currently used by all of our inputs and selections components that contain a label, helper text, legend and error message. This will need updating as part of this first V2 update to the component category, as it will be needed for updating the rest of the components.

The current text input component

I started by asking the design community in Slack channels to share their existing work, where they had used or detatched the current text input, created custom components or detache. I then compiled them into a file to document common themes, features and use cases.

Discovery

Identifying what our current component can’t achieve in designers work

I started by asking the design community in Slack channels to share their existing work, where they had used or detached the current text input, or even created custom components. I then compiled them into a file to document common themes, features and use cases.

-

Leading and trailing assets: I saw a lot of designers adding custom assets to the start or end of the text input container. A huge standout was designers adding a hide/show password icon button.

-

Prefix’s and suffix’s: Things like measurements and currencies had been placed before and after the input. As well as before and after the input text within the input container.

-

Optional vs Required: Arguably the most controversial pattern I had found. Although our current component uses ‘optional’, a good amount of designers had been replacing this text (at the end of label) to an asterisk. So this would only appear on required inputs and optional inputs would have no visual queue. Its often removed as its not in its own container as its in the same text line as the label - so once overridden you can’t get it back unless you reset the component.

-

Search bars: I had come across text inputs being modified into search bars, which were never their intended purpose.

-

Region flags: Being a telco, requires users a lot of the time to select their region flag at the start of the component before typing in there phone number.

-

Input formatting: Another popular one was designers wanting to have automatic spacings or dashes between chunks of text in an input. E.g: Birthdays - dd/mm/yyyy or Card details 00-00-00.

-

Multiple inputs in a row: Similar to the point above, designers were segmenting their inputs into increments. E.g Birthday [dd] [mm] [yyyy].

-

Links within labels: This was never addressed in the original/current guidance, however was a popular pattern I had been spotting.

-

Placing on all surfaces: Recently as a design system team we have tried to make our components adapt to all surfaces. Meaning components can sit on neutral light and dark surfaces as well as our coloured ones. The current component ‘should’ only sit on default and fog surfaces, which are neutral light surfaces, and are dark surfaces in dark mode.

-

PIN codes: Finally another common theme was designers using custom ‘segmented’ inputs in a row to create PIN inputs. For example a 4 digit PIN to log into the app or a number for 2 factor authentication.

-

Success state: The current component only has an error state for its ‘status states’. I had spotted one designer had created a live username authenticator.

Optional vs Required*

The proposed colour that had been put forward by brand and the agency is a blend of our ‘Fog’ surface colour (Source/Grey/01) and Primary brand colour (Source/Aqua/05).

 

Information on the specific blend wasn’t available to us, so we had to get as close to #DEE7E8 as we could ourselves.

 

However this was an opportunity to refine it and propose a more appropriate colour to be used in all of our digital journy’s on web and app.

Components use labels

-

Text input

-

Multi-line text input

-

Select field

-

Radio button

-

Checkbox

Reasons to keep optional

-

We should only be asking for necessary information, so the number of required

fields should be greater than the number of optional fields in most cases.

-

Therefore labelling optional reduces visual clutter and distraction for

users.

-

Clutter / distraction would be particularly high if fields were marked with

(required).

-

This has led to the suggestion to use an * to indicate required. However, while this would be WCAG compliant, there are reasons to believe it is not the optimum user experience. It may be confusing to some users depending on the journey squad remembering to add ‘Field marked with an * are required’ in the relevant place.

-

There are some examples (like the outlier, above) where labelling as required

could be ambiguous.

-

Introduces an element not designed for and not tested in journey squad experiences.

Additional complexities if Loop were to update current input logic:

-

If we use *, squads will need to go and add the definition to all existing forms -

realistically, this is unlikely to happen due to priorities/capacity, so the risk of

confusing users with an undefined * is high.

-

Could also cause layout issues if it makes legend go onto two lines?

If Loop releases new versions of inputs:

-

Adoption is likely to be slow, especially as squads won’t be able to ‘mix and match’ v1 and v2 inputs due to change in logic (plus planned visual style updates).

-

We may need to add the ‘hide optional label’ prop to existing components to enable

Learn and Browse, if we aren’t going to be able to decide or implement the ultimate

solution quickly

A couple of issues with optional

-

In instances where forms are obviously optional such as:

-

Entering your email to log in.

-

Or selecting a checkbox in a filtering menu.

What we chose in the end?

After evaluating the above and investigating the pros and cons of both optional and required. The benefits of keeping ‘optional’ outweighed the cons, and time, effort and resource it would require to update all of our existing components, as well as communicating these changes to hundreds of designers and developers.

 

This all means we chose to keep the optional method, however it would be restyled as an update. and have the ability to keep an input optional, but have a property to hide the word in certain scenarios like the ones outlined above. There would need to be strict guidance on how to use this.

Design exploration

During my design exploration I got an accessibility specialist involved early on to help guide and shape the design and decisions I was making.

 

‘Placeholder text’ was something that I experimented with, however this use of text is not ideal for screen readers or anyone else for that matter, as it disappears when you focus on the input.

 

Currently we only have an error state, so I explored a ‘success’ state, because this was something I had seen in my discovery work. Unfortunately the squad decided that this was not a major priority and was out of scope for the first version of this new release. However it is something that could come in the future if there is a bigger demand for it.

 

Another thing I experimented with was the use of animation - In particular, having the label move to the top when focussed. This would also shrink from 16px to 12px to make it fit within the input - this was a big no also because we stick to a text size of 16px for the majority of the website and app.

Evaluating text input groups (and the rest of the input groups)

Currently there are technically two text input components: A single one and a group with a legend at the top (part of form control).

 

This is a pre assembled component in Figma and code. I wondered how used it was so I checked Figma’s (very limited) analytics, and it turns out it hadn’t been used much at all.

 

I reached out to the design community and asked what designers thoughts were on the component and their experience using it.

 

It was clear the component lacked flexibility - designers were unable to reorder the list due to Figma limitations with component auto layout. They were also unable to place two inputs side by side on a row without breaking/detaching the group.

The idea

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate competent so that designers could place at the top of the group themselves.

 

Guidance on how to assemble these groups and space the inputs would be outlined on the design system website for designers to refer to.

 

Text input group in React and Flutter already has all this flexibility so will remain, however with individual updates to the text inputs.

Refinement

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate compenent

The build

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate compenent

Dev handover and build

I created a specification document for the React and Flutter engineers along with walking them through the design, properties and highlighting what tokens were used.

 

Once built, we now had two consistent components across three platforms: Figma, React and Flutter (React=Web, and Flutter=App with light and dark mode).

 

Product designers, content designers and anyone who wanted to could now log in to the React Storybook and Flutter Playground to play around with the components and configure them in many different ways. This especially useful to use if a designer was unsure how far a component could flex in live.

 

Often Figma allows designers to flex components too much, so by adding these links in the component documentation in Figma - we were able to encourage designers to experiment outside of Figma.

Guidance documentation

All documentation is stored on our guidance site (Zeroheight) and contains all links to the component across the three platforms. Below is a few screenshots of the guidance me and the content designer created.

 

In our design system we only release a component when it is available across Figma, React, Flutter and Guidance. The same goes for any updates we make in the future.

Deprecating the old componets

With the release of the V2 components, we had to phase out the old components. We did this by marking the component names with [To be removed] and a ‘. ‘ at the start to hide from publishing.

Designers were still able to use this component in their files that it already existed in, however when they went to drag in a new one from the assets panel, only the V2 one would be available.

I also added a deprecation message in the components description in Figma, and linking to the new component and guidance.

The guidance was also deprecated as ‘legacy’ - this meant that it could still be referred to if need be, rather than removing entirely. We will most likely remove at the next major release.

The rest of Inputs and selections components updates

After creating the new version of Text input and Form control, I was tasked to uplift the rest of the component family an guidance - Here is a sneak peak.

Things that didn’t go to plan

Due to our Loop standard of having 48x48px touch targets we were unable to make our Icon buttons (both size Medium and Small0 smaller within the input. The decision I made was to use what we had available already instead of creating anything custom. And we’ll revisit the Icon button components again at a later date.

 

The WCAG guidance states that touch targets can be as small as 24x24px, so we might want to meet half way and do some testing on 32x32px touch targets.

Let’s get to know each other.

Get in touch!

Copyright © 2025 Stefan Adams. All rights reserved. All illustrations are created by me.

I create better experiences for People.

Design system

User Testing

Product Design

Inputs and selections: Text input V2

Designing for improved accessibility, consistency and ease of implementation.

My role

Lead Product Designer

The team

-

Product Manager

-

React (Web) and Flutter (App) Engineers

-

Accessibility Specialist

Background

We’re rebuilding our three-year-old text input component to address its limitations and align with modern design, accessibility, and tech standards.

The current version lacks flexibility, has accessibility gaps, and doesn’t meet today’s theming or usability needs.

 

The new version will improve performance, customisation, and developer experience - while laying the groundwork for updating other input and selection components.

This marks the first step in modernising our design system, ensuring consistency, scalability, and future readiness across components like multi-line inputs, radio buttons, and checkboxes.

Project goals

01

Flexibility

Support flexibility and scalability, allowing the component to adapt to a range of use cases.

02

Consistency and maintainability

Drive consistency across products by providing a unified, reusable component that will reduce design and development time. Ensuring a cohesive user experience that leverages existing tokens and components from the design system for easier adoption and maintainability.

03

Accessibility

Ensure full support for WCAG 2.1 and ARIA standards to provide a more inclusive experience for all users.

04

Documentation

The component needs to have new documentation on our design system guidance site, where designers (product and content) and developers can refer to for correct usage.

05

Revaluate the Form control componet

Currently used by all of our inputs and selections components that contain a label, helper text, legend and error message. This will need updating as part of this first V2 update to the component category, as it will be needed for updating the rest of the components.

The current text input component

I started by asking the design community in Slack channels to share their existing work, where they had used or detatched the current text input, created custom components or detache. I then compiled them into a file to document common themes, features and use cases.

Discovery

Identifying what our current component can’t achieve in designers work

I started by asking the design community in Slack channels to share their existing work, where they had used or detached the current text input, or even created custom components. I then compiled them into a file to document common themes, features and use cases.

-

Leading and trailing assets: I saw a lot of designers adding custom assets to the start or end of the text input container. A huge standout was designers adding a hide/show password icon button.

-

Prefix’s and suffix’s: Things like measurements and currencies had been placed before and after the input. As well as before and after the input text within the input container.

-

Optional vs Required: Arguably the most controversial pattern I had found. Although our current component uses ‘optional’, a good amount of designers had been replacing this text (at the end of label) to an asterisk. So this would only appear on required inputs and optional inputs would have no visual queue. Its often removed as its not in its own container as its in the same text line as the label - so once overridden you can’t get it back unless you reset the component.

-

Search bars: I had come across text inputs being modified into search bars, which were never their intended purpose.

-

Region flags: Being a telco, requires users a lot of the time to select their region flag at the start of the component before typing in there phone number.

-

Input formatting: Another popular one was designers wanting to have automatic spacings or dashes between chunks of text in an input. E.g: Birthdays - dd/mm/yyyy or Card details 00-00-00.

-

Multiple inputs in a row: Similar to the point above, designers were segmenting their inputs into increments. E.g Birthday [dd] [mm] [yyyy].

-

Links within labels: This was never addressed in the original/current guidance, however was a popular pattern I had been spotting.

-

Placing on all surfaces: Recently as a design system team we have tried to make our components adapt to all surfaces. Meaning components can sit on neutral light and dark surfaces as well as our coloured ones. The current component ‘should’ only sit on default and fog surfaces, which are neutral light surfaces, and are dark surfaces in dark mode.

-

PIN codes: Finally another common theme was designers using custom ‘segmented’ inputs in a row to create PIN inputs. For example a 4 digit PIN to log into the app or a number for 2 factor authentication.

-

Success state: The current component only has an error state for its ‘status states’. I had spotted one designer had created a live username authenticator.

Optional vs Required*

The proposed colour that had been put forward by brand and the agency is a blend of our ‘Fog’ surface colour (Source/Grey/01) and Primary brand colour (Source/Aqua/05).

 

Information on the specific blend wasn’t available to us, so we had to get as close to #DEE7E8 as we could ourselves.

 

However this was an opportunity to refine it and propose a more appropriate colour to be used in all of our digital journy’s on web and app.

Components use labels

-

Text input

-

Multi-line text input

-

Select field

-

Radio button

-

Checkbox

Reasons to keep optional

-

We should only be asking for necessary information, so the number of required

fields should be greater than the number of optional fields in most cases.

-

Therefore labelling optional reduces visual clutter and distraction for

users.

-

Clutter / distraction would be particularly high if fields were marked with

(required).

-

This has led to the suggestion to use an * to indicate required. However, while this would be WCAG compliant, there are reasons to believe it is not the optimum user experience. It may be confusing to some users depending on the journey squad remembering to add ‘Field marked with an * are required’ in the relevant place.

-

There are some examples (like the outlier, above) where labelling as required

could be ambiguous.

-

Introduces an element not designed for and not tested in journey squad experiences.

Additional complexities if Loop were to update current input logic:

-

If we use *, squads will need to go and add the definition to all existing forms -

realistically, this is unlikely to happen due to priorities/capacity, so the risk of

confusing users with an undefined * is high.

-

Could also cause layout issues if it makes legend go onto two lines?

If Loop releases new versions of inputs:

-

Adoption is likely to be slow, especially as squads won’t be able to ‘mix and match’ v1 and v2 inputs due to change in logic (plus planned visual style updates).

-

We may need to add the ‘hide optional label’ prop to existing components to enable

Learn and Browse, if we aren’t going to be able to decide or implement the ultimate

solution quickly

A couple of issues with optional

-

In instances where forms are obviously optional such as:

-

Entering your email to log in.

-

Or selecting a checkbox in a filtering menu.

What we chose in the end?

After evaluating the above and investigating the pros and cons of both optional and required. The benefits of keeping ‘optional’ outweighed the cons, and time, effort and resource it would require to update all of our existing components, as well as communicating these changes to hundreds of designers and developers.

 

This all means we chose to keep the optional method, however it would be restyled as an update. and have the ability to keep an input optional, but have a property to hide the word in certain scenarios like the ones outlined above. There would need to be strict guidance on how to use this.

Evaluating text input groups (and the rest of the input groups)

Currently there are technically two text input components: A single one and a group with a legend at the top (part of form control).

 

This is a pre assembled component in Figma and code. I wondered how used it was so I checked Figma’s (very limited) analytics, and it turns out it hadn’t been used much at all.

 

I reached out to the design community and asked what designers thoughts were on the component and their experience using it.

 

It was clear the component lacked flexibility - designers were unable to reorder the list due to Figma limitations with component auto layout. They were also unable to place two inputs side by side on a row without breaking/detaching the group.

The idea

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate competent so that designers could place at the top of the group themselves.

 

Guidance on how to assemble these groups and space the inputs would be outlined on the design system website for designers to refer to.

 

Text input group in React and Flutter already has all this flexibility so will remain, however with individual updates to the text inputs.

Design exploration

During my design exploration I got an accessibility specialist involved early on to help guide and shape the design and decisions I was making.

 

‘Placeholder text’ was something that I experimented with, however this use of text is not ideal for screen readers or anyone else for that matter, as it disappears when you focus on the input.

 

Currently we only have an error state, so I explored a ‘success’ state, because this was something I had seen in my discovery work. Unfortunately the squad decided that this was not a major priority and was out of scope for the first version of this new release. However it is something that could come in the future if there is a bigger demand for it.

 

Another thing I experimented with was the use of animation - In particular, having the label move to the top when focussed. This would also shrink from 16px to 12px to make it fit within the input - this was a big no also because we stick to a text size of 16px for the majority of the website and app.

Refinement

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate compenent

The build

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate compenent

Dev handover and build

I created a specification document for the React and Flutter engineers along with walking them through the design, properties and highlighting what tokens were used.

 

Once built, we now had two consistent components across three platforms: Figma, React and Flutter (React=Web, and Flutter=App with light and dark mode).

 

Product designers, content designers and anyone who wanted to could now log in to the React Storybook and Flutter Playground to play around with the components and configure them in many different ways. This especially useful to use if a designer was unsure how far a component could flex in live.

 

Often Figma allows designers to flex components too much, so by adding these links in the component documentation in Figma - we were able to encourage designers to experiment outside of Figma.

Guidance documentation

All documentation is stored on our guidance site (Zeroheight) and contains all links to the component across the three platforms. Below is a few screenshots of the guidance me and the content designer created.

 

In our design system we only release a component when it is available across Figma, React, Flutter and Guidance. The same goes for any updates we make in the future.

Deprecating the old componets

With the release of the V2 components, we had to phase out the old components. We did this by marking the component names with [To be removed] and a ‘. ‘ at the start to hide from publishing.

Designers were still able to use this component in their files that it already existed in, however when they went to drag in a new one from the assets panel, only the V2 one would be available.

I also added a deprecation message in the components description in Figma, and linking to the new component and guidance.

The guidance was also deprecated as ‘legacy’ - this meant that it could still be referred to if need be, rather than removing entirely. We will most likely remove at the next major release.

The rest of Inputs and selections components updates

After creating the new version of Text input and Form control, I was tasked to uplift the rest of the component family an guidance - Here is a sneak peak.

Things that didn’t go to plan

Due to our Loop standard of having 48x48px touch targets we were unable to make our Icon buttons (both size Medium and Small0 smaller within the input. The decision I made was to use what we had available already instead of creating anything custom. And we’ll revisit the Icon button components again at a later date.

 

The WCAG guidance states that touch targets can be as small as 24x24px, so we might want to meet half way and do some testing on 32x32px touch targets.

Let’s get to know each other.

Get in touch!

Copyright © 2025 Stefan Adams. All rights reserved. All illustrations are created by me.

I create better experiences for People.

Design system

User Testing

Product Design

Inputs and selections: Text input V2

Designing for improved accessibility, consistency and ease of implementation.

My role

Lead Product Designer

The team

-

Product Manager

-

React (Web) and Flutter (App) Engineers

-

Accessibility Specialist

Background

We’re rebuilding our three-year-old text input component to address its limitations and align with modern design, accessibility, and tech standards.

The current version lacks flexibility, has accessibility gaps, and doesn’t meet today’s theming or usability needs.

 

The new version will improve performance, customisation, and developer experience - while laying the groundwork for updating other input and selection components.

This marks the first step in modernising our design system, ensuring consistency, scalability, and future readiness across components like multi-line inputs, radio buttons, and checkboxes.

Project goals

01

Flexibility

Support flexibility and scalability, allowing the component to adapt to a range of use cases.

02

Consistency and maintainability

Drive consistency across products by providing a unified, reusable component that will reduce design and development time. Ensuring a cohesive user experience that leverages existing tokens and components from the design system for easier adoption and maintainability.

03

Accessibility

Ensure full support for WCAG 2.1 and ARIA standards to provide a more inclusive experience for all users.

04

Documentation

The component needs to have new documentation on our design system guidance site, where designers (product and content) and developers can refer to for correct usage.

05

Revaluate the Form control component

Currently used by all of our inputs and selections components that contain a label, helper text, legend and error message. This will need updating as part of this first V2 update to the component category, as it will be needed for updating the rest of the components.

The current text input component

The current text input component is over 3 years old, and has been heavily neglected and lack enhancements and Figma updates. Properties are very limited and the flexibility isn’t there. It also only sits on 2 of our 11 surfaces - default and fog in light and dark mode.

 

It does however use a ‘shared part’ used in two other components. This is a ‘form control’ component - what this is, is the label, helper text and error message. So anything that controls the form/input.

 

There is another component called Text input group. This is also available on default and fog surfaces in light and dark mode.

Discovery

Identifying what our current component can’t achieve in designers work

I started by asking the design community in Slack channels to share their existing work, where they had used or detached the current text input, or even created custom components. I then compiled them into a file to document common themes, features and use cases.

-

Leading and trailing assets: I saw a lot of designers adding custom assets to the start or end of the text input container. A huge standout was designers adding a hide/show password icon button.

-

Prefix’s and suffix’s: Things like measurements and currencies had been placed before and after the input. As well as before and after the input text within the input container.

-

Optional vs Required: Arguably the most controversial pattern I had found. Although our current component uses ‘optional’, a good amount of designers had been replacing this text (at the end of label) to an asterisk. So this would only appear on required inputs and optional inputs would have no visual queue. Its often removed as its not in its own container as its in the same text line as the label - so once overridden you can’t get it back unless you reset the component.

-

Search bars: I had come across text inputs being modified into search bars, which were never their intended purpose.

-

Region flags: Being a telco, requires users a lot of the time to select their region flag at the start of the component before typing in there phone number.

-

Input formatting: Another popular one was designers wanting to have automatic spacings or dashes between chunks of text in an input. E.g: Birthdays - dd/mm/yyyy or Card details 00-00-00.

-

Multiple inputs in a row: Similar to the point above, designers were segmenting their inputs into increments. E.g Birthday [dd] [mm] [yyyy].

-

Links within labels: This was never addressed in the original/current guidance, however was a popular pattern I had been spotting.

-

Placing on all surfaces: Recently as a design system team we have tried to make our components adapt to all surfaces. Meaning components can sit on neutral light and dark surfaces as well as our coloured ones. The current component ‘should’ only sit on default and fog surfaces, which are neutral light surfaces, and are dark surfaces in dark mode.

-

PIN codes: Finally another common theme was designers using custom ‘segmented’ inputs in a row to create PIN inputs. For example a 4 digit PIN to log into the app or a number for 2 factor authentication.

-

Success state: The current component only has an error state for its ‘status states’. I had spotted one designer had created a live username authenticator.

Optional vs Required*

We had a steer from accessibility that we should update to use asterisks for all required inputs instead of the word optional for all optional inputs (meaning optional wouldn’t have the asterisk or the word optional).

 

However we decided to investigate the best practice ourselves, seeing that our site had much more required inputs than not, so there could be a lot of repetition there, as well as possibly confusing screen readers.

Components use labels

-

Text input

-

Multi-line text input

-

Select field

-

Radio button

-

Checkbox

Reasons to keep optional

-

We should only be asking for necessary information, so the number of required

fields should be greater than the number of optional fields in most cases.

-

Therefore labelling optional reduces visual clutter and distraction for

users.

-

Clutter / distraction would be particularly high if fields were marked with

(required).

-

This has led to the suggestion to use an * to indicate required. However, while this would be WCAG compliant, there are reasons to believe it is not the optimum user experience. It may be confusing to some users depending on the journey squad remembering to add ‘Field marked with an * are required’ in the relevant place.

-

There are some examples (like the outlier, above) where labelling as required

could be ambiguous.

-

Introduces an element not designed for and not tested in journey squad experiences.

Additional complexities if Loop were to update current input logic:

-

If we use *, squads will need to go and add the definition to all existing forms -

realistically, this is unlikely to happen due to priorities/capacity, so the risk of

confusing users with an undefined * is high.

-

Could also cause layout issues if it makes legend go onto two lines?

If Loop releases new versions of inputs:

-

Adoption is likely to be slow, especially as squads won’t be able to ‘mix and match’ v1 and v2 inputs due to change in logic (plus planned visual style updates).

-

We may need to add the ‘hide optional label’ prop to existing components to enable

Learn and Browse, if we aren’t going to be able to decide or implement the ultimate

solution quickly

A couple of issues with optional

-

In instances where forms are obviously optional such as:

-

Entering your email to log in.

-

Or selecting a checkbox in a filtering menu.

What we chose in the end?

After evaluating the above and investigating the pros and cons of both optional and required. The benefits of keeping ‘optional’ outweighed the cons, and time, effort and resource it would require to update all of our existing components, as well as communicating these changes to hundreds of designers and developers.

 

This all means we chose to keep the optional method, however it would be restyled as an update. and have the ability to keep an input optional, but have a property to hide the word in certain scenarios like the ones outlined above. There would need to be strict guidance on how to use this.

Design exploration

During my design exploration I got an accessibility specialist involved early on to help guide and shape the design and decisions I was making.

 

‘Placeholder text’ was something that I experimented with, however this use of text is not ideal for screen readers or anyone else for that matter, as it disappears when you focus on the input.

 

Currently we only have an error state, so I explored a ‘success’ state, because this was something I had seen in my discovery work. Unfortunately the squad decided that this was not a major priority and was out of scope for the first version of this new release. However it is something that could come in the future if there is a bigger demand for it.

 

Another thing I experimented with was the use of animation - In particular, having the label move to the top when focussed. This would also shrink from 16px to 12px to make it fit within the input - this was a big no also because we stick to a text size of 16px for the majority of the website and app.

Evaluating text input groups (and the rest of the input groups)

Currently there are technically two text input components: A single one and a group with a legend at the top (part of form control).

 

This is a pre assembled component in Figma and code. I wondered how used it was so I checked Figma’s (very limited) analytics, and it turns out it hadn’t been used much at all.

 

I reached out to the design community and asked what designers thoughts were on the component and their experience using it.

 

It was clear the component lacked flexibility - designers were unable to reorder the list due to Figma limitations with component auto layout. They were also unable to place two inputs side by side on a row without breaking/detaching the group.

The idea

My idea to solve these issues was to scrap the Text input group (and later the Checkbox and Radio button groups) component. Instead opting for a ‘assemble yourself’ approach - meaning designers would assemble individual text inputs into an auto layout container, giving them greater flexibility and control. I would provide the ‘legend’ part from form control as a separate competent so that designers could place at the top of the group themselves.

 

Guidance on how to assemble these groups and space the inputs would be outlined on the design system website for designers to refer to.

 

Text input group in React and Flutter already has all this flexibility so will remain, however with individual updates to the text inputs.

Refinement

Whilst refining the design I added in a clear input button. This would be optional for the designers to configure and would not replace the trailing slot. For keyboards we made it so they ignore it as those users are used to Cmd A + Deleting an input.

The build

For the final build for release, we went with the rule of having any component from Inputs and selections can only sit on our light and dark ‘neutral surfaces’. This was to keep it simple, so when the user was submitting important information, they wouldn’t be overwhelmed or distracted by colour. Having the components sitting on colour also brought contrast issues.

Dev handover and build

I created a specification document for the React and Flutter engineers along with walking them through the design, properties and highlighting what tokens were used.

 

Once built, we now had two consistent components across three platforms: Figma, React and Flutter (React=Web, and Flutter=App with light and dark mode).

 

Product designers, content designers and anyone who wanted to could now log in to the React Storybook and Flutter Playground to play around with the components and configure them in many different ways. This especially useful to use if a designer was unsure how far a component could flex in live.

 

Often Figma allows designers to flex components too much, so by adding these links in the component documentation in Figma - we were able to encourage designers to experiment outside of Figma.

Guidance documentation

All documentation is stored on our guidance site (Zeroheight) and contains all links to the component across the three platforms. Below is a few screenshots of the guidance me and the content designer created.

 

In our design system we only release a component when it is available across Figma, React, Flutter and Guidance. The same goes for any updates we make in the future.

Deprecating the old componets

With the release of the V2 components, we had to phase out the old components. We did this by marking the component names with [To be removed] and a ‘. ‘ at the start to hide from publishing.

Designers were still able to use this component in their files that it already existed in, however when they went to drag in a new one from the assets panel, only the V2 one would be available.

I also added a deprecation message in the components description in Figma, and linking to the new component and guidance.

The guidance was also deprecated as ‘legacy’ - this meant that it could still be referred to if need be, rather than removing entirely. We will most likely remove at the next major release.

The rest of Inputs and selections components updates

After creating the new version of Text input and Form control, I was tasked to uplift the rest of the component family an guidance - Here is a sneak peak.

Things that didn’t go to plan

Due to our Loop standard of having 48x48px touch targets we were unable to make our Icon buttons (both size Medium and Small0 smaller within the input. The decision I made was to use what we had available already instead of creating anything custom. And we’ll revisit the Icon button components again at a later date.

 

The WCAG guidance states that touch targets can be as small as 24x24px, so we might want to meet half way and do some testing on 32x32px touch targets.

Let’s get to know each other.

Get in touch!

Copyright © 2025 Stefan Adams. All rights reserved. All illustrations are created by me.

I create better experiences for People.