diff --git a/packages/react/src/components/Image/Image.tsx b/packages/react/src/components/Image/Image.tsx index 805bc7a780..cd5aa65f70 100644 --- a/packages/react/src/components/Image/Image.tsx +++ b/packages/react/src/components/Image/Image.tsx @@ -17,14 +17,13 @@ import * as React from 'react' import { ThemeContext } from 'react-fela' import { createShorthandFactory, UIComponentProps, commonPropTypes } from '../../utils' -import { - FluentComponentStaticProps, - ProviderContextPrepared, - WithAsProp, - withSafeTypeForAs, -} from '../../types' +import { PropsOfElement, ProviderContextPrepared } from '../../types' + +export interface ImageOwnProps + extends UIComponentProps, + ImageBehaviorProps { + as?: E -export interface ImageProps extends UIComponentProps, ImageBehaviorProps { /** Alternative text. */ alt?: string @@ -46,7 +45,25 @@ export interface ImageProps extends UIComponentProps, ImageBehaviorProps { src?: string } -const Image: React.FC> & FluentComponentStaticProps = props => { +export type ImageStrictProps = ImageOwnProps & + Omit, keyof ImageOwnProps> + +export type ImageProps = ImageStrictProps + +/** + * An Image is a graphic representation of something. + * + * @accessibility + * If image should be visible to screen readers, textual representation needs to be provided in 'alt' property. + * + * Other considerations: + * - when alt property is empty, then Narrator in scan mode navigates to image and narrates it as empty paragraph. + * - when image has role='presentation' then screen readers navigate to the element in scan/virtual mode. To avoid this, the attribute "aria-hidden='true'" is applied by the default image behavior. + * - when alt property is used in combination with aria-label, arialabbeledby or title, additional screen readers verification is needed as each screen reader handles this combination differently. + */ +function Image( + props: ImageStrictProps, +): React.ReactElement { const context: ProviderContextPrepared = React.useContext(ThemeContext) const { setStart, setEnd } = useTelemetry(Image.displayName, context.telemetry) setStart() @@ -102,11 +119,11 @@ const Image: React.FC> & FluentComponentStaticProps(Image) +export default Image diff --git a/packages/react/src/types.ts b/packages/react/src/types.ts index c979941e51..650f79c810 100644 --- a/packages/react/src/types.ts +++ b/packages/react/src/types.ts @@ -19,6 +19,11 @@ export type DebounceResultFn = T & { // Utilities // ======================================================== +// Source: https://github.com/emotion-js/emotion/blob/master/packages/styled-base/types/helper.d.ts +export type PropsOfElement< + E extends keyof JSX.IntrinsicElements | React.JSXElementConstructor +> = JSX.LibraryManagedAttributes> + export type ResultOf = T extends (...arg: any[]) => infer TResult ? TResult : never export type ObjectOf = { [key: string]: T } diff --git a/packages/react/test/specs/components/Image/Image-test.tsx b/packages/react/test/specs/components/Image/Image-test.tsx index ff7c14a120..6d8c7cd8fc 100644 --- a/packages/react/test/specs/components/Image/Image-test.tsx +++ b/packages/react/test/specs/components/Image/Image-test.tsx @@ -5,9 +5,7 @@ import Image from 'src/components/Image/Image' import { mountWithProviderAndGetComponent } from 'test/utils' describe('Image', () => { - isConformant(Image, { - constructorName: 'Image', - }) + isConformant(Image) describe('accessibility', () => { handlesAccessibility(Image, { diff --git a/yarn.lock b/yarn.lock index a2ec702472..9e5dea8917 100644 --- a/yarn.lock +++ b/yarn.lock @@ -5203,9 +5203,9 @@ "@types/react" "*" "@types/react@*", "@types/react@^16.8.10": - version "16.8.10" - resolved "https://registry.yarnpkg.com/@types/react/-/react-16.8.10.tgz#1ccb6fde17f71a62ef055382ec68bdc379d4d8d9" - integrity sha512-7bUQeZKP4XZH/aB4i7k1i5yuwymDu/hnLMhD9NjVZvQQH7ZUgRN3d6iu8YXzx4sN/tNr0bj8jgguk8hhObzGvA== + version "16.9.20" + resolved "https://registry.yarnpkg.com/@types/react/-/react-16.9.20.tgz#e83285766340fb1a7fafe7e5c4708c53832e3641" + integrity sha512-jRrWBr25zzEVNa4QbESKLPluvrZ3W6Odfwrfe2F5vzbrDuNvlpnHa/xbZcXg8RH5D4CE181J5VxrRrLvzRH+5A== dependencies: "@types/prop-types" "*" csstype "^2.2.0"