Skip to content

Commit 58473f5

Browse files
WesSouzaarturbien
authored andcommitted
feat(avatar): convert to TypeScript and export types
1 parent 5a69d1d commit 58473f5

File tree

5 files changed

+49
-52
lines changed

5 files changed

+49
-52
lines changed

src/Avatar/Avatar.mdx

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ name: Avatar
33
menu: Components
44
---
55

6-
import Avatar from './Avatar';
6+
import { Avatar } from './Avatar';
77

88
# Avatar
99

@@ -12,16 +12,13 @@ import Avatar from './Avatar';
1212
#### Default
1313

1414
<Playground>
15-
<Avatar src='https://sphoto.nasza-klasa.pl/33278012/1/square/2658174fbd.jpeg?v=1' />
15+
<Avatar src='https://placekitten.com/100/100' />
1616
</Playground>
1717

1818
#### No border
1919

2020
<Playground>
21-
<Avatar
22-
src='https://sphoto.nasza-klasa.pl/33278012/1/square/2658174fbd.jpeg?v=1'
23-
noBorder
24-
/>
21+
<Avatar src='https://placedog.net/100/100' noBorder />
2522
</Playground>
2623

2724
#### Lettered

src/Avatar/Avatar.spec.js renamed to src/Avatar/Avatar.spec.tsx

Lines changed: 9 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,8 @@
1-
import React from 'react';
21
import { render } from '@testing-library/react';
32

43
import { renderWithTheme, theme } from '../../test/utils';
54

6-
import Avatar from './Avatar';
5+
import { Avatar } from './Avatar';
76

87
describe('<Avatar />', () => {
98
it('should render component', () => {
@@ -14,16 +13,16 @@ describe('<Avatar />', () => {
1413

1514
it('should render children', () => {
1615
const { container } = render(<Avatar>Avatar children</Avatar>);
17-
const avatarEl = container.firstChild;
16+
const avatarEl = container.firstElementChild;
1817

19-
expect(avatarEl.innerHTML).toBe('Avatar children');
18+
expect(avatarEl && avatarEl.innerHTML).toBe('Avatar children');
2019
});
2120

2221
it('should handle border properly', () => {
2322
const { container, rerender } = renderWithTheme(
2423
<Avatar noBorder={false} />
2524
);
26-
const avatarEl = container.firstChild;
25+
const avatarEl = container.firstElementChild;
2726

2827
expect(avatarEl).toHaveStyleRule(
2928
'border-top',
@@ -37,7 +36,7 @@ describe('<Avatar />', () => {
3736

3837
it('should handle square properly', () => {
3938
const { container, rerender } = render(<Avatar square />);
40-
const avatarEl = container.firstChild;
39+
const avatarEl = container.firstElementChild;
4140

4241
expect(avatarEl).toHaveStyleRule('border-radius', '0');
4342

@@ -49,9 +48,9 @@ describe('<Avatar />', () => {
4948
it('should render with source', async () => {
5049
const catGif = 'https://cdn2.thecatapi.com/images/1ac.gif';
5150
const { findByAltText } = render(<Avatar src={catGif} alt='cat avatar' />);
52-
const imageEl = await findByAltText('cat avatar');
51+
const imageEl = (await findByAltText('cat avatar')) as HTMLImageElement;
5352

54-
expect(imageEl.src).toBe(catGif);
53+
expect(imageEl && imageEl.src).toBe(catGif);
5554
});
5655

5756
it('should render source with priority over children', async () => {
@@ -69,15 +68,15 @@ describe('<Avatar />', () => {
6968
describe('prop: size', () => {
7069
it('should set proper size', () => {
7170
const { container } = renderWithTheme(<Avatar size='85%' />);
72-
const avatarEl = container.firstChild;
71+
const avatarEl = container.firstElementChild;
7372

7473
expect(avatarEl).toHaveStyleRule('width', '85%');
7574
expect(avatarEl).toHaveStyleRule('height', '85%');
7675
});
7776

7877
it('when passed a number, sets size in px', () => {
7978
const { container } = renderWithTheme(<Avatar size={25} />);
80-
const avatarEl = container.firstChild;
79+
const avatarEl = container.firstElementChild;
8180

8281
expect(avatarEl).toHaveStyleRule('width', '25px');
8382
expect(avatarEl).toHaveStyleRule('height', '25px');

src/Avatar/Avatar.stories.js renamed to src/Avatar/Avatar.stories.tsx

Lines changed: 5 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
1-
import React from 'react';
2-
import styled from 'styled-components';
1+
import { ComponentMeta } from '@storybook/react';
32
import { Avatar } from 'react95';
3+
import styled from 'styled-components';
44

55
const Wrapper = styled.div`
66
padding: 5rem;
@@ -14,16 +14,13 @@ export default {
1414
title: 'Avatar',
1515
component: Avatar,
1616
decorators: [story => <Wrapper>{story()}</Wrapper>]
17-
};
18-
19-
const imageSrc =
20-
'https://sphoto.nasza-klasa.pl/33278012/1/square/2658174fbd.jpeg?v=1';
17+
} as ComponentMeta<typeof Avatar>;
2118

2219
export function Default() {
2320
return (
2421
<div style={{ display: 'inline-flex' }}>
25-
<Avatar size={50} src={imageSrc} />
26-
<Avatar noBorder size={50} src={imageSrc} />
22+
<Avatar size={50} src='https://placekitten.com/100/100' />
23+
<Avatar noBorder size={50} src='https://placedog.net/100/100' />
2724
<Avatar size={50} style={{ background: 'palevioletred' }}>
2825
AK
2926
</Avatar>
Lines changed: 31 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,21 @@
1-
import React from 'react';
2-
import propTypes from 'prop-types';
1+
import React, { forwardRef } from 'react';
32
import styled from 'styled-components';
43
import { getSize } from '../common/utils';
4+
import { CommonStyledProps } from '../types';
55

6-
const StyledAvatar = styled.div`
6+
type AvatarProps = {
7+
alt?: string;
8+
children?: React.ReactNode;
9+
noBorder?: boolean;
10+
size?: string | number;
11+
square?: boolean;
12+
src?: string;
13+
} & React.HTMLAttributes<HTMLDivElement> &
14+
CommonStyledProps;
15+
16+
const StyledAvatar = styled.div<
17+
Pick<AvatarProps, 'noBorder' | 'square' | 'src'> & { size?: string }
18+
>`
719
display: inline-block;
820
box-sizing: border-box;
921
object-fit: contain;
@@ -34,45 +46,37 @@ const StyledAvatar = styled.div`
3446
`}
3547
`;
3648

37-
const SlyledAvatarIMG = styled.img`
49+
const StyledAvatarImg = styled.img`
3850
display: block;
3951
object-fit: contain;
4052
width: 100%;
4153
height: 100%;
4254
`;
4355

44-
const Avatar = React.forwardRef(function Avatar(props, ref) {
45-
const { alt, children, noBorder, size, square, src, ...otherProps } = props;
46-
56+
const Avatar = forwardRef<HTMLDivElement, AvatarProps>(function Avatar(
57+
{
58+
alt = '',
59+
children,
60+
noBorder = false,
61+
size = 35,
62+
square = false,
63+
src,
64+
...otherProps
65+
},
66+
ref
67+
) {
4768
return (
4869
<StyledAvatar
4970
noBorder={noBorder}
5071
ref={ref}
5172
size={getSize(size)}
5273
square={square}
74+
src={src}
5375
{...otherProps}
5476
>
55-
{src ? <SlyledAvatarIMG src={src} alt={alt} /> : children}
77+
{src ? <StyledAvatarImg src={src} alt={alt} /> : children}
5678
</StyledAvatar>
5779
);
5880
});
5981

60-
Avatar.defaultProps = {
61-
alt: '',
62-
children: null,
63-
noBorder: false,
64-
size: 35,
65-
square: false,
66-
src: undefined
67-
};
68-
69-
Avatar.propTypes = {
70-
alt: propTypes.string,
71-
children: propTypes.node,
72-
noBorder: propTypes.bool,
73-
size: propTypes.oneOfType([propTypes.string, propTypes.number]),
74-
square: propTypes.bool,
75-
src: propTypes.string
76-
};
77-
78-
export default Avatar;
82+
export { Avatar, AvatarProps };

src/index.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ export { createScrollbars } from './common/index';
55
/* components */
66
export * from './Anchor/Anchor';
77
export { default as AppBar } from './AppBar/AppBar';
8-
export { default as Avatar } from './Avatar/Avatar';
8+
export * from './Avatar/Avatar';
99
export * from './Bar/Bar';
1010
export { default as Button } from './Button/Button';
1111
export { default as Checkbox } from './Checkbox/Checkbox';

0 commit comments

Comments
 (0)