Browse Source

feat(avatar): a11y #205

走鹃 4 years ago
parent
commit
e1ffdf173a

+ 4 - 4
packages/semi-ui/avatar/_story/avatar.stories.js

@@ -11,7 +11,7 @@ export const Basic = () => (
   <div>
     <div>
       <Avatar>U</Avatar>
-      <Avatar size="large">U</Avatar>
+      <Avatar autoFocus size="large" onClick={() => console.log('ok')}>U</Avatar>
       <Avatar size="extra-small">U</Avatar>
       <Avatar size="small">U</Avatar>
       <Avatar size="default">U</Avatar>
@@ -45,9 +45,9 @@ export const CustomAvatar = () => (
     <Avatar color="red" size="default">
       DF
     </Avatar>
-    <Avatar src="https://zos.alipayobjects.com/rmsportal/ODTLcjxAfvqbxHnVXCYX.png" />
-    <Avatar size="default" src="https://zos.alipayobjects.com/rmsportal/ODTLcjxAfvqbxHnVXCYX.png" />
-    <Avatar size="small" src="https://zos.alipayobjects.com/rmsportal/ODTLcjxAfvqbxHnVXCYX.png" />
+    <Avatar src="https://zos.alipayobjects.com/rmsportal/ODTLcjxAfvqbxHnVXCYX.png" alt="a man" />
+    <Avatar size="default" src="https://zos.alipayobjects.com/rmsportal/ODTLcjxAfvqbxHnVXCYX.png" alt="a man" />
+    <Avatar size="small" src="https://zos.alipayobjects.com/rmsportal/ODTLcjxAfvqbxHnVXCYX.png" alt="a man" />
     <Avatar style={{ color: '#f56a00', backgroundColor: '#fde3cf' }}>U</Avatar>
     <Avatar style={{ backgroundColor: '#87d068' }}>YZ</Avatar>
   </div>

+ 1 - 1
packages/semi-ui/avatar/avatarGroup.tsx

@@ -76,6 +76,6 @@ export default class AvatarGroup extends PureComponent<AvatarGroupProps> {
 
         }
 
-        return <div className={groupCls}>{inner}</div>;
+        return <div className={groupCls} aria-label="avatar group">{inner}</div>;
     }
 }

+ 10 - 4
packages/semi-ui/avatar/index.tsx

@@ -47,6 +47,7 @@ export default class Avatar extends BaseComponent<AvatarProps, AvatarState> {
         onMouseLeave: PropTypes.func,
     };
 
+    foundation!: AvatarFoundation;
     constructor(props: AvatarProps) {
         super(props);
         this.state = {
@@ -106,12 +107,12 @@ export default class Avatar extends BaseComponent<AvatarProps, AvatarState> {
         this.foundation.destroy();
     }
 
-    onEnter() {
-        this.foundation.handleEnter();
+    onEnter(e: React.MouseEvent) {
+        this.foundation.handleEnter(e);
     }
 
-    onLeave() {
-        this.foundation.handleLeave();
+    onLeave(e: React.MouseEvent) {
+        this.foundation.handleLeave(e);
     }
 
     handleError() {
@@ -135,19 +136,24 @@ export default class Avatar extends BaseComponent<AvatarProps, AvatarState> {
         );
         let content = children;
         const hoverRender = hoverContent ? (<div className={`${prefixCls}-hover`}>{hoverContent}</div>) : null;
+        let ariaLabel;
         if (isImg) {
             content = (
                 <img src={src} srcSet={srcSet} onError={this.handleError} alt={alt} {...imgAttr} />
             );
+            ariaLabel = 'avatar';
         } else if (typeof children === 'string') {
             content = (
                 <span className={`${prefixCls}-content`}>
                     <span className={`${prefixCls}-label`}>{children}</span>
                 </span>
             );
+            ariaLabel = `avatar of ${children}`;
         }
         return (
+            // eslint-disable-next-line jsx-a11y/no-static-element-interactions,jsx-a11y/click-events-have-key-events
             <span
+                aria-label={ariaLabel}
                 {...(others as any)}
                 style={style}
                 className={avatarCls}