Skip to content

Commit

Permalink
a11y: more fixes for the last pass (#9396)
Browse files Browse the repository at this point in the history
* a11y: disable subscriptions input if no subscriptions available

Fixes [75832](https://fuselabs.visualstudio.com/Composer/_workitems/edit/75832/)

* a11y: fix collapse button aria

Fixes [75830](https://fuselabs.visualstudio.com/Composer/_workitems/edit/75830/)

* a11y: restore focus on toolbar menu dismiss event

Fixes [75833](https://fuselabs.visualstudio.com/Composer/_workitems/edit/75833/)

* a11y: fix code-editor properties tree aria

Fixes [75854](https://fuselabs.visualstudio.com/Composer/_workitems/edit/75854/)

* a11y: scope color adjustments to disabled forced-colors

Fixes [75828](https://fuselabs.visualstudio.com/Composer/_workitems/edit/75828/)

* Update lock files

Co-authored-by: Chris Whitten <christopher.whitten@microsoft.com>
  • Loading branch information
OEvgeny and cwhitten authored Oct 3, 2022
1 parent 7b8960d commit d2e133d
Show file tree
Hide file tree
Showing 8 changed files with 144 additions and 98 deletions.
30 changes: 16 additions & 14 deletions Composer/packages/adaptive-form/src/components/CollapseField.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,16 @@
import { css, jsx } from '@emotion/react';
import { Fragment, useState, useEffect, useLayoutEffect, useRef } from 'react';
import { FontSizes, FontWeights } from '@fluentui/react/lib/Styling';
import { IconButton } from '@fluentui/react/lib/Button';
import { Label } from '@fluentui/react/lib/Label';
import { NeutralColors } from '@fluentui/theme';
import formatMessage from 'format-message';
import { Icon } from '@fluentui/react/lib/Icon';
import styled from '@emotion/styled';

const styles = {
title: css`
font-weight: ${FontWeights.semibold};
`,
description: css`
font-size: ${FontSizes.medium};
`,
Expand All @@ -19,13 +23,20 @@ const styles = {
overflow: hidden;
`,
header: css`
appearance: none;
border: none;
background-color: #eff6fc;
display: flex;
margin: 4px -18px;
align-items: center;
`,
};

const CollapseIcon = styled(Icon)({
color: NeutralColors.gray150,
marginRight: '4px',
});

interface CollapseField {
defaultExpanded?: boolean;
description?: string;
Expand All @@ -37,28 +48,19 @@ export const CollapseField: React.FC<CollapseField> = ({ children, description,

return (
<Fragment>
<div
<button
data-is-focusable
aria-expanded={isOpen}
aria-label={typeof title === 'string' ? title : formatMessage('Field Set')}
css={styles.header}
role="presentation"
onClick={() => {
setIsOpen(!isOpen);
}}
>
<IconButton
ariaLabel={isOpen ? formatMessage('Collapse') : formatMessage('Expand')}
iconProps={{ iconName: isOpen ? 'ChevronDown' : 'ChevronRight' }}
styles={{
root: { color: NeutralColors.gray150 },
rootHovered: { backgroundColor: 'transparent' },
rootFocused: { backgroundColor: 'transparent' },
}}
/>
{title && <Label styles={{ root: { fontWeight: FontWeights.semibold } }}>{title}</Label>}
<CollapseIcon aria-hidden {...{ iconName: isOpen ? 'ChevronDown' : 'ChevronRight' }} />
{title && <Label css={styles.title}>{title}</Label>}
{description && <span css={styles.description}>&nbsp;- {description}</span>}
</div>
</button>
<div>
<CollapseContent isOpen={isOpen}>{children}</CollapseContent>
</div>
Expand Down
36 changes: 23 additions & 13 deletions Composer/packages/client/src/components/EditableField.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,13 +20,15 @@ const allowedNavigationKeys = ['ArrowDown', 'ArrowUp', 'ArrowLeft', 'ArrowRight'
const defaultContainerStyle = (hasFocus, hasErrors) => css`
display: flex;
width: 100%;
outline: ${hasErrors
? `2px solid ${SharedColors.red10}`
: hasFocus
? `2px solid ${SharedColors.cyanBlue10}`
: undefined};
background: ${hasFocus || hasErrors ? NeutralColors.white : 'inherit'};
margin-top: 2px;
@media (forced-colors: none) {
background: ${hasFocus || hasErrors ? NeutralColors.white : 'inherit'};
outline: ${hasErrors
? `2px solid ${SharedColors.red10}`
: hasFocus
? `2px solid ${SharedColors.cyanBlue10}`
: undefined};
}
:hover .ms-Button-icon,
:focus-within .ms-Button-icon {
visibility: visible;
Expand All @@ -41,6 +43,12 @@ const defaultContainerStyle = (hasFocus, hasErrors) => css`
}
`;

const requiredText = css`
@media (forced-colors: none) {
color: ${SharedColors.red20};
}
`;

// turncat to show two line.
const maxCharacterNumbers = 120;

Expand Down Expand Up @@ -270,8 +278,10 @@ const EditableField: React.FC<EditableFieldProps> = (props) => {
':hover': {
borderColor: hasFocus ? undefined : NeutralColors.gray30,
},
'.ms-TextField-field': {
background: hasFocus || hasEditingErrors ? NeutralColors.white : 'inherit',
'@media (forced-colors: none)': {
'.ms-TextField-field': {
background: hasFocus || hasEditingErrors ? NeutralColors.white : 'inherit',
},
},
},
},
Expand Down Expand Up @@ -312,17 +322,17 @@ const EditableField: React.FC<EditableFieldProps> = (props) => {
}}
styles={{
root: {
background: hasFocus ? NeutralColors.white : 'inherit',
'@media (forced-colors: none)': {
background: hasFocus ? NeutralColors.white : 'inherit',
},
},
}}
onClick={iconProps?.onClick || resetValue}
/>
)}
</div>
{hasErrors && hasBeenEdited && (
<span style={{ color: SharedColors.red20 }}>{requiredMessage || formErrors.value}</span>
)}
{error && <span style={{ color: SharedColors.red20 }}>{error}</span>}
{hasErrors && hasBeenEdited && <span css={requiredText}>{requiredMessage || formErrors.value}</span>}
{error && <span css={requiredText}>{error}</span>}
{hasErrors && hasBeenEdited && <Announced message={requiredMessage || formErrors.value} role="alert" />}
{error && <Announced message={error} role="alert" />}
</Fragment>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,12 @@ const disabledTextFieldStyle = mergeStyleSets(customFieldLabel, {
root: {
selectors: {
'.ms-TextField-field': {
background: '#ddf3db',
},
'.ms-Dropdown-title': {
background: '#ddf3db',
'@media (forced-colors: none)': {
background: '#ddf3db',
},
'.ms-Dropdown-title': {
background: '#ddf3db',
},
},
'p > span': {
width: '100%',
Expand Down
8 changes: 5 additions & 3 deletions Composer/packages/client/src/pages/knowledge-base/styles.ts
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,7 @@ export const rowDetails = {
background: NeutralColors.gray30,
selectors: {
'.ms-TextField-fieldGroup': {
background: NeutralColors.gray30,
background: 'transparent',
},
'.ms-Button--icon': {
visibility: 'visible',
Expand All @@ -117,7 +117,7 @@ export const rowDetails = {
visibility: 'visible',
},
'.ms-TextField-fieldGroup': {
background: NeutralColors.gray30,
background: 'transparent',
},
},
},
Expand All @@ -140,8 +140,10 @@ export const addAlternative = {
fontSize: 12,
paddingLeft: 0,
marginLeft: -5,
color: SharedColors.cyanBlue10,
display: 'none',
'@media (forced-colors: none)': {
color: SharedColors.cyanBlue10,
},
},
} as IButtonStyles;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,10 @@
import styled from '@emotion/styled';
import { NeutralColors } from '@fluentui/theme';
import { Icon, IIconStyles } from '@fluentui/react/lib/Icon';
import { Button } from '@fluentui/react/lib/Button';
import { Stack } from '@fluentui/react/lib/Stack';
import * as React from 'react';
import { IContextualMenuItem } from '@fluentui/react/lib/ContextualMenu';

import { PropertyItem } from '../../types';

Expand All @@ -23,7 +25,7 @@ const toggleExpandIconStyle: IIconStyles = {
fontSize: 8,
transition: 'background 250ms ease',
selectors: {
'&:hover': { background: NeutralColors.gray50 },
'&:hover, &:focus-within': { background: NeutralColors.gray50 },
'&:before': {
content: '""',
},
Expand All @@ -32,7 +34,9 @@ const toggleExpandIconStyle: IIconStyles = {
};

const Root = styled(Stack)({
width: '100%',
height: DEFAULT_TREE_ITEM_HEIGHT,
border: 'none',
});

const Content = styled(Stack)<{
Expand All @@ -42,6 +46,10 @@ const Content = styled(Stack)<{
}));

type PropertyTreeItemProps = {
onClick?: (
ev?: React.MouseEvent<HTMLElement> | React.KeyboardEvent<HTMLElement>,
item?: IContextualMenuItem
) => boolean | void;
item: PropertyItem;
level: number;
onRenderLabel: (item: PropertyItem) => React.ReactNode;
Expand All @@ -50,7 +58,7 @@ type PropertyTreeItemProps = {
};

export const PropertyTreeItem = React.memo((props: PropertyTreeItemProps) => {
const { expanded = false, item, level, onToggleExpand, onRenderLabel } = props;
const { expanded = false, item, level, onToggleExpand, onRenderLabel, ...rest } = props;

const paddingLeft = level * DEFAULT_INDENTATION_PADDING;

Expand All @@ -65,7 +73,18 @@ export const PropertyTreeItem = React.memo((props: PropertyTreeItemProps) => {
const isExpandable = !!item.children?.length && onToggleExpand;

return (
<Root horizontal style={{ paddingLeft }} title={item.name} verticalAlign="center">
<Root
horizontal
aria-expanded={isExpandable ? (expanded ? 'true' : 'false') : undefined}
as={Button}
className="ms-ContextualMenu-link"
role="menuitem"
style={{ paddingLeft }}
tabIndex={0}
title={item.name}
verticalAlign="center"
{...rest}
>
{isExpandable ? (
<Icon
iconName={expanded ? 'CaretDownSolid8' : 'CaretRightSolid8'}
Expand Down
Loading

0 comments on commit d2e133d

Please sign in to comment.