From 9372ce0ec7a26714db1c529a33331dc2bbed2b33 Mon Sep 17 00:00:00 2001 From: Nidhi Kumari Date: Thu, 13 Oct 2022 04:52:21 +0530 Subject: [PATCH] added AvatarFavicon component (#16135) * added AvatarFavicon component * updated AvatarFavicon Readme * updated avatar favicon component * added fallback props to avatar favicon * updated test for avatar favicon * updated avatar favicon component * updated typo --- .../avatar-favicon/README.mdx | 44 ++++++++++ .../avatar-favicon/avatar-favicon.js | 82 +++++++++++++++++++ .../avatar-favicon/avatar-favicon.scss | 5 ++ .../avatar-favicon/avatar-favicon.stories.js | 57 +++++++++++++ .../avatar-favicon/avatar-favicon.test.js | 46 +++++++++++ .../component-library/avatar-favicon/index.js | 1 + .../component-library-components.scss | 1 + 7 files changed, 236 insertions(+) create mode 100644 ui/components/component-library/avatar-favicon/README.mdx create mode 100644 ui/components/component-library/avatar-favicon/avatar-favicon.js create mode 100644 ui/components/component-library/avatar-favicon/avatar-favicon.scss create mode 100644 ui/components/component-library/avatar-favicon/avatar-favicon.stories.js create mode 100644 ui/components/component-library/avatar-favicon/avatar-favicon.test.js create mode 100644 ui/components/component-library/avatar-favicon/index.js diff --git a/ui/components/component-library/avatar-favicon/README.mdx b/ui/components/component-library/avatar-favicon/README.mdx new file mode 100644 index 000000000..adcaabc69 --- /dev/null +++ b/ui/components/component-library/avatar-favicon/README.mdx @@ -0,0 +1,44 @@ +import { Story, Canvas, ArgsTable } from '@storybook/addon-docs'; + +import { AvatarFavicon } from './avatar-favicon'; + +# AvatarFavicon + +The `AvatarFavicon` is an image component that renders an icon that is provided in the form of a URL. + + + + + +## Props + +The `AvatarFavicon` accepts all props below as well as all [Box](/docs/ui-components-ui-box-box-stories-js--default-story) component props + + + +### Size + +Use the `size` prop to set the size of the `AvatarFavicon`. + +Possible sizes include: + +- `xs` 16px +- `sm` 24px +- `md` 32px +- `lg` 40px +- `xl` 48px + +Defaults to `md` + + + + + +### Image Source + +Use the `imageSource` prop to set the image to be rendered of the `AvatarFavicon`. + +### Fallback Icon Props + +If there is no `imageSource` then in that case an [icon](/docs/ui-components-component-library-icon-icon-stories-js--default-story) will be used as the fallback display and it can be customised via `fallbackIconProps`. + diff --git a/ui/components/component-library/avatar-favicon/avatar-favicon.js b/ui/components/component-library/avatar-favicon/avatar-favicon.js new file mode 100644 index 000000000..2f460685f --- /dev/null +++ b/ui/components/component-library/avatar-favicon/avatar-favicon.js @@ -0,0 +1,82 @@ +import React from 'react'; +import PropTypes from 'prop-types'; +import classnames from 'classnames'; +import { BaseAvatar } from '../base-avatar'; +import Box from '../../ui/box/box'; +import { ICON_NAMES, Icon } from '../icon'; +import { + COLORS, + BORDER_COLORS, + SIZES, + DISPLAY, + ALIGN_ITEMS, + JUSTIFY_CONTENT, +} from '../../../helpers/constants/design-system'; + +export const AvatarFavicon = ({ + size = SIZES.MD, + imageSource, + imgAlt = 'avatar-favicon', + className, + fallbackIconProps, + borderColor = BORDER_COLORS.TRANSPARENT, + ...props +}) => { + return ( + + {imageSource ? ( + {imgAlt} + ) : ( + + )} + + ); +}; + +AvatarFavicon.propTypes = { + /** + * The imageSource accepts the string of the image to be rendered + */ + imageSource: PropTypes.string, + /** + * The alt text for the favicon avatar to be rendered + */ + imgAlt: PropTypes.string, + /** + * Props for the fallback icon. All Icon props can be used + */ + fallbackIconProps: PropTypes.shape(Icon.PropTypes), + /** + * The size of the AvatarFavicon + * Possible values could be 'SIZES.XS', 'SIZES.SM', 'SIZES.MD', 'SIZES.LG', 'SIZES.XL' + * Defaults to SIZES.MD + */ + size: PropTypes.oneOf(Object.values(SIZES)), + /** + * The border color of the AvatarFavicon + * Defaults to COLORS.TRANSPARENT + */ + borderColor: Box.propTypes.borderColor, + /** + * Additional classNames to be added to the AvatarFavicon + */ + className: PropTypes.string, + /** + * AvatarFavicon also accepts all Box props including but not limited to + * className, as(change root element of HTML element) and margin props + */ + ...Box.propTypes, +}; diff --git a/ui/components/component-library/avatar-favicon/avatar-favicon.scss b/ui/components/component-library/avatar-favicon/avatar-favicon.scss new file mode 100644 index 000000000..f9d461c63 --- /dev/null +++ b/ui/components/component-library/avatar-favicon/avatar-favicon.scss @@ -0,0 +1,5 @@ +.avatar-favicon { + &__image { + width: 100%; + } +} diff --git a/ui/components/component-library/avatar-favicon/avatar-favicon.stories.js b/ui/components/component-library/avatar-favicon/avatar-favicon.stories.js new file mode 100644 index 000000000..92e6b3175 --- /dev/null +++ b/ui/components/component-library/avatar-favicon/avatar-favicon.stories.js @@ -0,0 +1,57 @@ +import React from 'react'; +import { + SIZES, + DISPLAY, + ALIGN_ITEMS, + BORDER_COLORS, +} from '../../../helpers/constants/design-system'; + +import Box from '../../ui/box/box'; + +import README from './README.mdx'; +import { AvatarFavicon } from './avatar-favicon'; + +export default { + title: 'Components/ComponentLibrary/AvatarFavicon', + id: __filename, + component: AvatarFavicon, + parameters: { + docs: { + page: README, + }, + }, + argTypes: { + size: { + control: 'select', + options: Object.values(SIZES), + }, + imageSource: { + control: 'text', + }, + borderColor: { + options: Object.values(BORDER_COLORS), + control: 'select', + }, + }, + args: { + imageSource: 'https://uniswap.org/favicon.ico', + size: SIZES.MD, + }, +}; + +const Template = (args) => { + return ; +}; + +export const DefaultStory = Template.bind({}); +DefaultStory.storyName = 'Default'; + +export const Size = (args) => ( + + + + + + + +); diff --git a/ui/components/component-library/avatar-favicon/avatar-favicon.test.js b/ui/components/component-library/avatar-favicon/avatar-favicon.test.js new file mode 100644 index 000000000..f23bef224 --- /dev/null +++ b/ui/components/component-library/avatar-favicon/avatar-favicon.test.js @@ -0,0 +1,46 @@ +/* eslint-disable jest/require-top-level-describe */ +import { render, screen } from '@testing-library/react'; +import React from 'react'; + +import { AvatarFavicon } from './avatar-favicon'; + +describe('AvatarFavicon', () => { + const args = { + imageSource: './images/eth_logo.svg', + }; + + it('should render correctly', () => { + const { getByTestId } = render( + , + ); + expect(getByTestId('avatar-favicon')).toBeDefined(); + }); + + it('should render image of Avatar Favicon', () => { + render(); + const image = screen.getByRole('img'); + expect(image).toBeDefined(); + expect(image).toHaveAttribute('src', args.imageSource); + }); + + it('should render fallback image if no ImageSource is provided', () => { + const { container } = render( + , + ); + expect(container.getElementsByClassName('icon')).toHaveLength(1); + }); + + it('should render fallback image with custom fallbackIconProps if no ImageSource is provided', () => { + const container = ( + + ); + expect(container.props.fallbackIconProps['data-testid']).toStrictEqual( + 'fallback-icon', + ); + }); +}); diff --git a/ui/components/component-library/avatar-favicon/index.js b/ui/components/component-library/avatar-favicon/index.js new file mode 100644 index 000000000..5d080ad57 --- /dev/null +++ b/ui/components/component-library/avatar-favicon/index.js @@ -0,0 +1 @@ +export { AvatarFavicon } from './avatar-favicon'; diff --git a/ui/components/component-library/component-library-components.scss b/ui/components/component-library/component-library-components.scss index ba86f58f0..260ed6d73 100644 --- a/ui/components/component-library/component-library-components.scss +++ b/ui/components/component-library/component-library-components.scss @@ -1,5 +1,6 @@ /** Please import your files in alphabetical order **/ @import 'avatar-account/avatar-account'; +@import 'avatar-favicon/avatar-favicon'; @import 'avatar-network/avatar-network'; @import 'avatar-token/avatar-token'; @import 'avatar-with-badge/avatar-with-badge';