Skip to content
This repository has been archived by the owner on May 24, 2024. It is now read-only.

terra-icon UX Audit #3123

Open
3 of 12 tasks
ryanthemanuel opened this issue Aug 10, 2020 · 4 comments
Open
3 of 12 tasks

terra-icon UX Audit #3123

ryanthemanuel opened this issue Aug 10, 2020 · 4 comments

Comments

@ryanthemanuel
Copy link
Contributor

ryanthemanuel commented Aug 10, 2020

terra-icon

Known Aliases

Document any known aliases of the component, decide if another name makes more sense.

  • Has known aliases
  • Requires name change

Design Standard Doc

Any documentation needed to be added to terra-ui describing the make up and usage of the component
Any doc examples that need to be updated?

  • Missing design standard documentation linkage.

Guides

Any guides needed to be added to terra-ui describing the usage of this component when used with other components.

  • Missing Guides
    • Guides on how teams can customize the color
  • Missing UX recommended Usage.
  • Deprecation guide

Accessibility Guides

  • Missing Accessibility Guides
    • Need to make sure that icons are not used directly in an interactable way. If so, use button, for example, instead.

Behaviours

  • Missing behaviours
    • Evaluate the API to see if we can somehow invert the aria label prop.
    • Add title and it should match the aria label (potentially the svg title)
    • Have human readable titles/aliases as part of the OCS repo but have option for consumers to specify as well
    • Possibly look to characterize "themeable" icons differently (e.g. customizable)
  • Contains bad practice behaviours that should be removed

Accessibility

  • Meets wcag 2.0/section 508 standards
  • Meets wcag 2.1/en 301 549 standards

Deprecation

  • Component is a bad pattern and should be deprecated.

Related Issues

Other Considerations

Possibly some general clean up of the OCS icon repository.
Need to evaluate icons to make sure they are low lighting correctly.
Look into exporting at 16 rather than 64.
Need to evaluate styling for stand-alone use (without extra styling for text alignment)

@ryanthemanuel ryanthemanuel added this to the Backlog milestone Aug 10, 2020
@ryanthemanuel ryanthemanuel changed the title terra-icon UX Audit - In Progress - In Progress Aug 12, 2020
@ryanthemanuel ryanthemanuel changed the title - In Progress terra-icon UX Audit Aug 12, 2020
@neilpfeiffer
Copy link
Member

neilpfeiffer commented Dec 10, 2020

Additional Consideration:
Need to evaluate further if icons need the ability to be provided as isIconOnly or isStandalone with the additional vertical positioning styles removed that make icons look correctly aligned with text, for use in locations where vertical and horizontal centering is critical and icons are all by themselves (e.g. terra-button which is isIconOnly).

Concerns: One of the largest concerns from a UX perspective is not all icons are going to be approved for standalone use (no text or labels beside them) based on Humans Factors recommendations and Design Standards, only certain icons that have wide/broad understanding can be used by themselves, so having a universal prop that indicates all can be used as standalone might violate Design Standards. We'll need to evaluate further how best to approach it.

@sdadn
Copy link
Contributor

sdadn commented Feb 21, 2022

Tech Design 1

Overview

According to https://a11y-101.com/development/svg , the simplest way to make svgs accessible is to use them in an img tag if they are meaningful. An img tag supports the alt property for screenreaders.

Currently, terra-icon works as follows:

attributes = {
    "viewBox":"0 0 48 48",
    "xmlns":"http://www.w3.org/2000/svg",
    "data-name":"Layer 1"
};
      
<IconBase {...attributes}>
    <path d="M48 21H27V0h-6v21H0v6h21v21h6V27h21z" ></path>
</IconBase>

Which returns the following html:

<svg 
    viewBox="0 0 48 48"
    xmlns="http://www.w3.org/2000/svg" 
    data-name="Layer 1" 
    >
    <path d="M48 21H27V0h-6v21H0v6h21v21h6V27h21z" ></path>
</svg>

In order to meet accessibility standards, the resulting html should be a img tag. Since img and svg have different attributes (e.g. img does not support child nodes), this will change the props for IconBase, resulting in an active change for this story.

Current Props

Prop Type Required Default Description
ariaLabel string optional null String that labels the current element. If aria-label is present, role is site to img and aria-hidden is removed
children node optional null Child nodes
isBidi bool optional false Should the svg mirror when dir=”rtl”
isSpin bool optional false Should the svg spin
height string optional 1em Height of SVG
width string optional 1em Width of SVG
focusable string optional false Focusable attribute

Proposed Props

Prop Type Required Default Description
alt string required "" String that labels the current element. If aria-label is present, role is site to img and aria-hidden is removed
svgSource string required null Svg input for the icon. Can be inline svg or a file
imageType enum optional “informative” Type of icon. Currently supports "decorative" and "infomative"
encoding enum optional "none" “none”: svg file , “utf8”: inline svg as Unicode, “base64": inline svg as base64
isBidi bool optional false Should the svg mirror when dir=”rtl”
isSpin bool optional false Should the svg spin
height string optional 1em Height of SVG
width string optional 1em Width of SVG
focusable string optional false Focusable attribute

This is an active change resulting in a major version bump. children and ariaLabel will be removed in the next major version.

Examples uses

  • When encoding is set to "none".
const attributes = {
    isBidi: false,
    iconType: "informative",
    alt: "plus icon",
    encoding: "none" //default value,
    svgSource: "path/to/file.svg"
};

return ( <img src={svgSource} {... other attributes} ></img> );
  • When encoding is set to "utf8".
const attributes = {
    isBidi: false,
    iconType: "informative",
    alt: "plus icon",
    encoding: "utf8"
    svgSource: `<svg data-name="Layer 1" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 48 48"><path d="M48 21H27V0h-6v21H0v6h21v21h6V27h21z"/></svg>`,
};
const generatedSVGSource = `data:image/svg+xml;${encoding},${svgSource}`;

return ( <img  src={generatedSVGSource} {...other attributes}></img> );
  • When encoding is set to "base64".
const attributes = {
    isBidi: false,
    iconType: "informative",
    alt: "plus icon",
    encoding: "base64"
    svgSource: `PHN2ZyBkYXRhLW5hbWU9IkxheWVyIDEiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgdmlld0JveD0iMCAwIDQ4IDQ4Ij48cGF0aCBkPSJNNDggMjFIMjdWMGgtNnYyMUgwdjZoMjF2MjFoNlYyN2gyMXoiLz48L3N2Zz4=`,
};

const generatedSVGSource = `data:image/svg+xml;${encoding},${svgSource}`;

return ( <img  src={generatedSVGSource} {...other attributes}></img> );

Accessibility

In order to meet accessibility standards, the imageType prop will be used to set the type of the icon as "informative" or "decorative"which will set the attributes of the img so that it will be read/ignored by screenreaders.

if imageType="decorative":

attributes.role = presentation

otherwise

attributes.role = undefined

To Do

  • Perform testing to find out which attributes would be added to the img tag or svg tag.

@sdadn
Copy link
Contributor

sdadn commented Mar 12, 2022

As Tech Design 1 is causing complications with the existing icon coloring logic, it is being dropped for Tech Design 2.

@sdadn
Copy link
Contributor

sdadn commented Mar 12, 2022

Tech Design 2

Overview

According to https://www.deque.com/blog/creating-accessible-svgs/ , the simplest and reccommended way to make svgs accessible is to use them in an img tag if they are meaningful. An img tag supports the alt property for screenreaders. However, terra-icon is deigned so that consumers can change the color of non-static icons by simply using the font-color. In order to maintain this feature, deque's alternative recommendation which is to add a title tag to a svg will be used.

Currently, terra-icon works as follows:

attributes = {
    "viewBox":"0 0 48 48",
    "xmlns":"http://www.w3.org/2000/svg",
    "data-name":"Layer 1"
};
      
<IconBase {...attributes}>
    <path d="M48 21H27V0h-6v21H0v6h21v21h6V27h21z" ></path>
</IconBase>

Which returns the following html:

<svg 
    viewBox="0 0 48 48"
    xmlns="http://www.w3.org/2000/svg" 
    data-name="Layer 1" 
    >
    <path d="M48 21H27V0h-6v21H0v6h21v21h6V27h21z" ></path>
</svg>

In order to meet accessibility standards, the resulting svg should have a title tag like the following:

<svg 
    viewBox="0 0 48 48"
    xmlns="http://www.w3.org/2000/svg" 
    data-name="Layer 1" 
    >
    <title>icon title</title>
    <path d="M48 21H27V0h-6v21H0v6h21v21h6V27h21z" ></path>
</svg>

Solution

The default component will be updated to be meaningful. This is so that consumers will adher to accessibility standards by default. A sub-component IconDecorative will be added for consumers to utilize decorative icons.

Default Meaningful Component

The props for the component will be updated as follows:

Current Props
Prop Type Required Default Description
ariaLabel string optional null String that labels the current element; If aria-label is present, role is site to img and aria-hidden is removed
children node optional null Child nodes
isBidi bool optional false Should the svg mirror when dir=”rtl”
isSpin bool optional false Should the svg spin
height string optional 1em Height of SVG
width string optional 1em Width of SVG
focusable string optional false Focusable attribute
Proposed Props
Prop Type Required Default Description
a11yLabel string required - String that labels the current element
children node optional null Child nodes
isBidi bool optional false Should the svg mirror when dir=”rtl”
isSpin bool optional false Should the svg spin
height string optional 1em Height of SVG
width string optional 1em Width of SVG
focusable string optional false Focusable attribute

This is an active change resulting in a major version bump. children and ariaLabel will be removed in the next major version.

Resulting html

the default iconBase will return the following html

<svg 
    viewBox="0 0 48 48"
    xmlns="http://www.w3.org/2000/svg" 
    data-name="Layer 1" 
    >
    <title>icon title</title>
    <path d="M48 21H27V0h-6v21H0v6h21v21h6V27h21z" ></path>
</svg>

Decorative icon

For a decorative icon, the role is set to presentation with no title prop.

Proposed Props
Prop Type Required Default Description
children node optional null Child nodes
isBidi bool optional false Should the svg mirror when dir=”rtl”
isSpin bool optional false Should the svg spin
height string optional 1em Height of SVG
width string optional 1em Width of SVG
focusable string optional false Focusable attribute
Resulting html
<svg 
    viewBox="0 0 48 48"
    xmlns="http://www.w3.org/2000/svg" 
    data-name="Layer 1" 
    role="presentation"
    >
    <path d="M48 21H27V0h-6v21H0v6h21v21h6V27h21z" ></path>
</svg>

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

3 participants