@nuskin/foundation-ui-components 1.6.0 → 1.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +1 -1
- package/src/common/autocomplete/NsAutocomplete.styled.tsx +5 -1
- package/src/common/autocomplete/NsAutocomplete.tsx +19 -71
- package/src/common/autocomplete/helper/ClearButton.tsx +22 -0
- package/src/common/autocomplete/helper/SeeMoreButton.tsx +47 -0
- package/src/common/autocomplete/helper/renderGroupName.tsx +17 -0
- package/src/common/autocomplete/stories/ACWithoutClose.tsx +49 -0
- package/src/common/autocomplete/stories/NsAutocomplete.stories.tsx +76 -0
- package/src/common/autocomplete/stories/RenderAutoComplete.tsx +60 -0
- package/src/common/autocomplete/types.d.ts +1 -1
- package/src/common/card/NsBrandCard.tsx +94 -0
- package/src/common/card/NsCheckoutCard.tsx +92 -0
- package/src/common/card/NsHeroCardLevel1.tsx +106 -0
- package/src/common/card/NsHeroCardLevel2.tsx +126 -0
- package/src/common/card/NsIconText.tsx +153 -0
- package/src/common/card/NsLargeCard.tsx +120 -0
- package/src/common/card/NsMediumCard.tsx +64 -0
- package/src/common/card/NsPost.tsx +60 -0
- package/src/common/card/NsSmallFullCard.tsx +90 -0
- package/src/common/card/NsXLargeCard.tsx +80 -0
- package/src/common/card/cardSizes.ts +12 -0
- package/src/common/card/index.ts +10 -2
- package/src/common/card/specs/BrandLogo.spec.tsx +1 -1
- package/src/common/card/specs/NsBgCard.spec.tsx +2 -2
- package/src/common/card/specs/NsBrandCard.spec.tsx +97 -0
- package/src/common/card/specs/NsCheckoutCard.spec.tsx +50 -0
- package/src/common/card/specs/NsHeroCardLevel1.spec.tsx +48 -0
- package/src/common/card/specs/NsHeroCardLevel2.spec.tsx +51 -0
- package/src/common/card/specs/NsIconText.spec.tsx +28 -0
- package/src/common/card/specs/NsLargeCard.spec.tsx +41 -0
- package/src/common/card/specs/NsMediumCard.spec.tsx +35 -0
- package/src/common/card/specs/NsPost.spec.tsx +31 -0
- package/src/common/card/specs/NsSmallFullCard.spec.tsx +36 -0
- package/src/common/card/specs/NsXLargeCard.spec.tsx +35 -0
- package/src/common/card/stories/{NsBrandProductCard.stories.tsx → NsBrandCard.stories.tsx} +9 -4
- package/src/common/card/stories/NsCheckoutCard.stories.tsx +24 -0
- package/src/common/card/stories/NsHeroCardLevel1.stories.tsx +45 -0
- package/src/common/card/stories/NsHeroCardLevel2.stories.tsx +50 -0
- package/src/common/card/stories/NsIconText.stories.tsx +36 -0
- package/src/common/card/stories/NsLargeCard.stories.tsx +32 -0
- package/src/common/card/stories/NsMediumCard.stories.tsx +29 -0
- package/src/common/card/stories/NsPost.stories.tsx +39 -0
- package/src/common/card/stories/NsSmallFullCard.stories.tsx +29 -0
- package/src/common/card/stories/NsXLargeCard.stories.tsx +29 -0
- package/src/common/carousal/RenderBrand.tsx +3 -2
- package/src/common/input/InputWrapper.tsx +1 -1
- package/src/common/autocomplete/NsAutocomplete.stories.tsx +0 -108
- package/src/common/card/NsBrandProductCard.tsx +0 -47
- package/src/common/card/NsFfgCard.tsx +0 -24
- package/src/common/card/specs/NsBrandProductCard.spec.tsx +0 -32
- package/src/common/card/specs/NsFfgCard.spec.tsx +0 -33
- package/src/common/card/stories/NsBgCard.stories.tsx +0 -20
- package/src/common/card/stories/NsFfgCard.stories.tsx +0 -73
- package/src/common/card/styled/NsFfgStyled.tsx +0 -46
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import Box from '@mui/material/Box';
|
|
2
|
+
import { styled } from '@nuskin/foundation-theme';
|
|
3
|
+
import { NsImage, NsLink } from '../';
|
|
4
|
+
|
|
5
|
+
type NsSmallFullCardProps = {
|
|
6
|
+
title: string;
|
|
7
|
+
subtitle: string;
|
|
8
|
+
backgroundImageUrl: string;
|
|
9
|
+
backgroundImageAlt: string;
|
|
10
|
+
cardLink: { href: string; title: string };
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
const CardContainer = styled(Box)(() => {
|
|
14
|
+
return {
|
|
15
|
+
backgroundColor: '#fff',
|
|
16
|
+
display: 'flex',
|
|
17
|
+
height: '320px',
|
|
18
|
+
width: '375px',
|
|
19
|
+
position: 'relative',
|
|
20
|
+
'.image': {
|
|
21
|
+
width: '100%',
|
|
22
|
+
height: '100%',
|
|
23
|
+
objectFit: 'cover',
|
|
24
|
+
},
|
|
25
|
+
'.gradientOverlay': {
|
|
26
|
+
position: 'absolute',
|
|
27
|
+
top: 0,
|
|
28
|
+
left: 0,
|
|
29
|
+
width: '100%',
|
|
30
|
+
height: '100%',
|
|
31
|
+
background: 'linear-gradient(to top, rgba(0,0,0,0.6) 0%, transparent 50%);',
|
|
32
|
+
},
|
|
33
|
+
'.content': {
|
|
34
|
+
position: 'absolute',
|
|
35
|
+
height: '100%',
|
|
36
|
+
width: '100%',
|
|
37
|
+
padding: '40px 40px 25px 30px',
|
|
38
|
+
display: 'flex',
|
|
39
|
+
flexDirection: 'column',
|
|
40
|
+
},
|
|
41
|
+
'.subtitle': {
|
|
42
|
+
color: '#fff',
|
|
43
|
+
fontSize: '11px',
|
|
44
|
+
fontWeight: '400',
|
|
45
|
+
marginTop: 'auto',
|
|
46
|
+
},
|
|
47
|
+
'.title': {
|
|
48
|
+
color: '#fff',
|
|
49
|
+
fontSize: '26px',
|
|
50
|
+
fontWeight: '400',
|
|
51
|
+
marginTop: '20px',
|
|
52
|
+
},
|
|
53
|
+
'.action-link': {
|
|
54
|
+
display: 'flex',
|
|
55
|
+
justifyContent: 'center',
|
|
56
|
+
backgroundColor: '#252525',
|
|
57
|
+
color: '#fff',
|
|
58
|
+
marginTop: '20px',
|
|
59
|
+
borderRadius: '4px',
|
|
60
|
+
padding: '10px',
|
|
61
|
+
width: '70%',
|
|
62
|
+
':hover': {
|
|
63
|
+
textDecoration: 'none',
|
|
64
|
+
backgroundColor: '#3e3e3e',
|
|
65
|
+
},
|
|
66
|
+
},
|
|
67
|
+
};
|
|
68
|
+
});
|
|
69
|
+
|
|
70
|
+
export default function NsSmallFullCard({
|
|
71
|
+
title,
|
|
72
|
+
subtitle,
|
|
73
|
+
backgroundImageUrl,
|
|
74
|
+
backgroundImageAlt,
|
|
75
|
+
cardLink,
|
|
76
|
+
}: NsSmallFullCardProps) {
|
|
77
|
+
return (
|
|
78
|
+
<CardContainer role="small-full-card" component="div" data-testid="small-full-card">
|
|
79
|
+
<NsImage alt={backgroundImageAlt} src={backgroundImageUrl} className="image" />
|
|
80
|
+
<div className="gradientOverlay"></div>
|
|
81
|
+
<div className="content">
|
|
82
|
+
<article className="subtitle">{subtitle}</article>
|
|
83
|
+
<article className="title">{title}</article>
|
|
84
|
+
<NsLink className="action-link" href={cardLink.href}>
|
|
85
|
+
{cardLink.title}
|
|
86
|
+
</NsLink>
|
|
87
|
+
</div>
|
|
88
|
+
</CardContainer>
|
|
89
|
+
);
|
|
90
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import Box from '@mui/material/Box';
|
|
2
|
+
import { styled } from '@nuskin/foundation-theme';
|
|
3
|
+
import { NsButton, NsImage } from '..';
|
|
4
|
+
|
|
5
|
+
type NsXLargeCardProps = {
|
|
6
|
+
title: string;
|
|
7
|
+
subtitle: string;
|
|
8
|
+
backgroundImageUrl: string;
|
|
9
|
+
backgroundImageAlt: string;
|
|
10
|
+
cardLink: { href: string; title: string };
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
const CardContainer = styled(Box)(() => {
|
|
14
|
+
return {
|
|
15
|
+
backgroundColor: '#fff',
|
|
16
|
+
display: 'flex',
|
|
17
|
+
height: '545px',
|
|
18
|
+
width: '375px',
|
|
19
|
+
position: 'relative',
|
|
20
|
+
'.image': {
|
|
21
|
+
width: '100%',
|
|
22
|
+
height: '100%',
|
|
23
|
+
objectFit: 'cover',
|
|
24
|
+
},
|
|
25
|
+
'.gradientOverlay': {
|
|
26
|
+
position: 'absolute',
|
|
27
|
+
top: 0,
|
|
28
|
+
left: 0,
|
|
29
|
+
width: '100%',
|
|
30
|
+
height: '100%',
|
|
31
|
+
background: 'linear-gradient(to top, rgba(0,0,0,0.6) 0%, transparent 50%);',
|
|
32
|
+
},
|
|
33
|
+
'.content': {
|
|
34
|
+
position: 'absolute',
|
|
35
|
+
height: '100%',
|
|
36
|
+
width: '100%',
|
|
37
|
+
padding: '40px 40px 25px 30px',
|
|
38
|
+
display: 'flex',
|
|
39
|
+
flexDirection: 'column',
|
|
40
|
+
},
|
|
41
|
+
'.subtitle': {
|
|
42
|
+
color: '#fff',
|
|
43
|
+
fontSize: '11px',
|
|
44
|
+
fontWeight: '400',
|
|
45
|
+
marginTop: 'auto',
|
|
46
|
+
},
|
|
47
|
+
'.title': {
|
|
48
|
+
color: '#fff',
|
|
49
|
+
fontSize: '26px',
|
|
50
|
+
fontWeight: '400',
|
|
51
|
+
marginTop: '20px',
|
|
52
|
+
},
|
|
53
|
+
'.action-link': {
|
|
54
|
+
marginTop: '20px',
|
|
55
|
+
width: '70%',
|
|
56
|
+
},
|
|
57
|
+
};
|
|
58
|
+
});
|
|
59
|
+
|
|
60
|
+
export default function NsXLargeCard({
|
|
61
|
+
title,
|
|
62
|
+
subtitle,
|
|
63
|
+
backgroundImageUrl,
|
|
64
|
+
backgroundImageAlt,
|
|
65
|
+
cardLink,
|
|
66
|
+
}: NsXLargeCardProps) {
|
|
67
|
+
return (
|
|
68
|
+
<CardContainer role="x-large-card" component="div" data-testid="x-large-card">
|
|
69
|
+
<NsImage alt={backgroundImageAlt} src={backgroundImageUrl} className="image" />
|
|
70
|
+
<div className="gradientOverlay"></div>
|
|
71
|
+
<div className="content">
|
|
72
|
+
<article className="subtitle">{subtitle}</article>
|
|
73
|
+
<article className="title">{title}</article>
|
|
74
|
+
<NsButton className="action-link" variant="outlined" color="secondary" href={cardLink.href}>
|
|
75
|
+
{cardLink.title}
|
|
76
|
+
</NsButton>
|
|
77
|
+
</div>
|
|
78
|
+
</CardContainer>
|
|
79
|
+
);
|
|
80
|
+
}
|
package/src/common/card/index.ts
CHANGED
|
@@ -1,5 +1,13 @@
|
|
|
1
1
|
export { default as NsBrandWrapper } from './NsBrandWrapper';
|
|
2
2
|
export { default as NsBgCard } from './NsBgCard';
|
|
3
|
-
export { default as NsFfgCard } from './NsFfgCard';
|
|
4
3
|
export { default as NsBrandLogo } from './NsBrandLogo';
|
|
5
|
-
export { default as
|
|
4
|
+
export { default as NsHeroCardLevel1 } from './NsHeroCardLevel1';
|
|
5
|
+
export { default as NsHeroCardLevel2 } from './NsHeroCardLevel2';
|
|
6
|
+
export { default as NsPost } from './NsPost';
|
|
7
|
+
export { default as NsBrandCard } from './NsBrandCard';
|
|
8
|
+
export { default as NsIconText } from './NsIconText';
|
|
9
|
+
export { default as NsCheckoutCard } from './NsCheckoutCard';
|
|
10
|
+
export { default as NsSmallFullCard } from './NsSmallFullCard';
|
|
11
|
+
export { default as NsXLargeCard } from './NsXLargeCard';
|
|
12
|
+
export { default as NsLargeCard } from './NsLargeCard';
|
|
13
|
+
export { default as NsMediumCard } from './NsMediumCard';
|
|
@@ -2,7 +2,7 @@ import { render } from '@testing-library/react';
|
|
|
2
2
|
import NsBrandLogo from '../NsBrandLogo';
|
|
3
3
|
|
|
4
4
|
describe('BrandLogo component', () => {
|
|
5
|
-
it('renders with cover size', () => {
|
|
5
|
+
it('1. renders with cover size', () => {
|
|
6
6
|
const { container } = render(<NsBrandLogo component="img" />);
|
|
7
7
|
const cardElement = container.querySelector('img');
|
|
8
8
|
expect(cardElement).toHaveStyle(`
|
|
@@ -5,14 +5,14 @@ describe('NsBgCard component', () => {
|
|
|
5
5
|
const props = {
|
|
6
6
|
backgroundImageUrl: 'https://media.nuskin.com/m/6245528b8f76ad32/webimage-brand-ageLOC.png',
|
|
7
7
|
};
|
|
8
|
-
it('renders with background image', () => {
|
|
8
|
+
it('1. renders with background image', () => {
|
|
9
9
|
const { container } = render(<NsBgCard {...props} />);
|
|
10
10
|
const cardElement = container.querySelector('div');
|
|
11
11
|
expect(cardElement).toHaveStyle(`
|
|
12
12
|
background-image: url(${props.backgroundImageUrl});
|
|
13
13
|
`);
|
|
14
14
|
});
|
|
15
|
-
it('renders with cover size', () => {
|
|
15
|
+
it('2. renders with cover size', () => {
|
|
16
16
|
const { container } = render(<NsBgCard {...props} />);
|
|
17
17
|
const cardElement = container.querySelector('div');
|
|
18
18
|
expect(cardElement).toHaveStyle(`
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
|
+
import userEvent from '@testing-library/user-event';
|
|
4
|
+
import NsBrandCard from '../NsBrandCard';
|
|
5
|
+
|
|
6
|
+
describe('NsBrandCard component', () => {
|
|
7
|
+
const props = {
|
|
8
|
+
title: 'ageLOC LumiSpa',
|
|
9
|
+
backgroundImageUrl: 'https://media.nuskin.com/m/3604b5202b0b64c6/webimage-brand-lumispa-optweb.png',
|
|
10
|
+
brandImageUrl: 'https://media.nuskin.com/m/2571a0407433a6e8/webimage-brand-lumispa.png',
|
|
11
|
+
button: true,
|
|
12
|
+
};
|
|
13
|
+
|
|
14
|
+
it('1. renders with correct content and styles', () => {
|
|
15
|
+
render(<NsBrandCard {...props} />);
|
|
16
|
+
|
|
17
|
+
const brandCard = screen.getByTestId('brand-card');
|
|
18
|
+
expect(brandCard).toBeInTheDocument();
|
|
19
|
+
|
|
20
|
+
const brandTitle = screen.getByText('ageLOC LumiSpa');
|
|
21
|
+
expect(brandTitle).toBeInTheDocument();
|
|
22
|
+
|
|
23
|
+
const addToCartButton = screen.getByText('Add to Cart');
|
|
24
|
+
expect(addToCartButton).toBeInTheDocument();
|
|
25
|
+
});
|
|
26
|
+
|
|
27
|
+
it('2. does not render brand title when title is not provided', () => {
|
|
28
|
+
const { container } = render(<NsBrandCard {...{ ...props, title: undefined }} />);
|
|
29
|
+
|
|
30
|
+
const brandTitle = container.querySelector('.brand-title');
|
|
31
|
+
expect(brandTitle).toBeNull();
|
|
32
|
+
});
|
|
33
|
+
|
|
34
|
+
it('3. renders with "Add to Cart" button when button prop is true', () => {
|
|
35
|
+
render(<NsBrandCard {...props} />);
|
|
36
|
+
|
|
37
|
+
const addToCartButton = screen.getByText('Add to Cart');
|
|
38
|
+
expect(addToCartButton).toBeInTheDocument();
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
it('4. does not render button when button prop is false', () => {
|
|
42
|
+
const { container } = render(<NsBrandCard {...{ ...props, button: false }} />);
|
|
43
|
+
|
|
44
|
+
const addToCartButton = container.querySelector('.cta');
|
|
45
|
+
expect(addToCartButton).toBeNull();
|
|
46
|
+
});
|
|
47
|
+
|
|
48
|
+
it('5. calls onClick when the "Add to Cart" button is clicked', () => {
|
|
49
|
+
const onClickMock = jest.fn();
|
|
50
|
+
render(<NsBrandCard {...props} onClick={onClickMock} />);
|
|
51
|
+
|
|
52
|
+
const addToCartButton = screen.getByText('Add to Cart');
|
|
53
|
+
userEvent.click(addToCartButton);
|
|
54
|
+
|
|
55
|
+
expect(onClickMock).toHaveBeenCalled();
|
|
56
|
+
});
|
|
57
|
+
|
|
58
|
+
it('6. applies hover styles on mouseover', () => {
|
|
59
|
+
render(<NsBrandCard {...props} />);
|
|
60
|
+
|
|
61
|
+
const brandCard = screen.getByTestId('brand-card');
|
|
62
|
+
userEvent.hover(brandCard);
|
|
63
|
+
|
|
64
|
+
const brandTitle = screen.getByText('ageLOC LumiSpa');
|
|
65
|
+
expect(brandTitle).toHaveStyle('opacity: 0.7');
|
|
66
|
+
});
|
|
67
|
+
|
|
68
|
+
it('7. renders with correct styles when size is "small"', () => {
|
|
69
|
+
const { container } = render(<NsBrandCard {...props} size="small" />);
|
|
70
|
+
|
|
71
|
+
const cardContainer = container.firstChild;
|
|
72
|
+
const nsBgCardElement = cardContainer?.firstChild;
|
|
73
|
+
expect(cardContainer).toHaveStyle(`
|
|
74
|
+
width: 165px;
|
|
75
|
+
`);
|
|
76
|
+
expect(nsBgCardElement).toHaveStyle(`
|
|
77
|
+
width: 165px;
|
|
78
|
+
height: 180px;
|
|
79
|
+
`);
|
|
80
|
+
});
|
|
81
|
+
|
|
82
|
+
it('8. renders with correct styles when size is "large"', () => {
|
|
83
|
+
render(<NsBrandCard {...props} size="large" />);
|
|
84
|
+
const cardContainer = screen.getByTestId('brand-card') as HTMLElement;
|
|
85
|
+
const computedStyles = window.getComputedStyle(cardContainer);
|
|
86
|
+
|
|
87
|
+
expect(computedStyles.width).toBe('190px');
|
|
88
|
+
});
|
|
89
|
+
|
|
90
|
+
it('9. renders with default styles when size is not provided', () => {
|
|
91
|
+
render(<NsBrandCard {...props} />);
|
|
92
|
+
const cardContainer = screen.getByTestId('brand-card') as HTMLElement;
|
|
93
|
+
const computedStyles = window.getComputedStyle(cardContainer);
|
|
94
|
+
|
|
95
|
+
expect(computedStyles.width).toBe('190px');
|
|
96
|
+
});
|
|
97
|
+
});
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen, fireEvent } from '@testing-library/react';
|
|
3
|
+
import '@testing-library/jest-dom';
|
|
4
|
+
import NsCheckoutCard from '../NsCheckoutCard';
|
|
5
|
+
|
|
6
|
+
describe('NsCheckoutCard component', () => {
|
|
7
|
+
const props = {
|
|
8
|
+
title: 'Section Title',
|
|
9
|
+
address: 'Address',
|
|
10
|
+
icon: 'home' as 'home',
|
|
11
|
+
onClick: jest.fn(),
|
|
12
|
+
};
|
|
13
|
+
|
|
14
|
+
it('1. renders with correct content and styles', () => {
|
|
15
|
+
render(<NsCheckoutCard {...props} />);
|
|
16
|
+
|
|
17
|
+
const checkoutCard = screen.getByTestId('checkout-card');
|
|
18
|
+
expect(checkoutCard).toBeInTheDocument();
|
|
19
|
+
|
|
20
|
+
const titleElement = screen.getByText(props.title);
|
|
21
|
+
expect(titleElement).toBeInTheDocument();
|
|
22
|
+
|
|
23
|
+
const addressElement = screen.getByText(props.address);
|
|
24
|
+
expect(addressElement).toBeInTheDocument();
|
|
25
|
+
|
|
26
|
+
const changeLink = screen.getByText('CHANGE');
|
|
27
|
+
expect(changeLink).toBeInTheDocument();
|
|
28
|
+
});
|
|
29
|
+
|
|
30
|
+
it('2. toggles dropdown icon on click', () => {
|
|
31
|
+
render(<NsCheckoutCard {...props} />);
|
|
32
|
+
|
|
33
|
+
const dropdownIcon = screen.getByTestId('dropdown-icon');
|
|
34
|
+
|
|
35
|
+
fireEvent.click(dropdownIcon);
|
|
36
|
+
// expect(dropdownIcon).toHaveAttribute('name', 'arrowUp');
|
|
37
|
+
|
|
38
|
+
// fireEvent.click(dropdownIcon);
|
|
39
|
+
// expect(dropdownIcon).toHaveAttribute('name', 'arrowDown');
|
|
40
|
+
});
|
|
41
|
+
|
|
42
|
+
it('3. calls onClick when the card is clicked', () => {
|
|
43
|
+
render(<NsCheckoutCard {...props} />);
|
|
44
|
+
|
|
45
|
+
const checkoutCard = screen.getByTestId('checkout-card');
|
|
46
|
+
fireEvent.click(checkoutCard);
|
|
47
|
+
|
|
48
|
+
expect(props.onClick).toHaveBeenCalled();
|
|
49
|
+
});
|
|
50
|
+
});
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
|
+
import userEvent from '@testing-library/user-event';
|
|
4
|
+
import NsHeroCardLevel1 from '../NsHeroCardLevel1';
|
|
5
|
+
|
|
6
|
+
describe('NsHeroCardLevel1 component', () => {
|
|
7
|
+
const props = {
|
|
8
|
+
cardLink: {
|
|
9
|
+
href: 'https://www.forceforgood.org/',
|
|
10
|
+
title: 'SHOP NOW',
|
|
11
|
+
},
|
|
12
|
+
text: 'A skin ready for winter',
|
|
13
|
+
body: 'We have brought these discoveries to life through our powerful skin care products and supplements.',
|
|
14
|
+
backgroundImageUrl:
|
|
15
|
+
'https://media.nuskin.com/m/9734240cc191163/webimage-lash-brow-serum-carousel-image-launch.png',
|
|
16
|
+
backgroundImageAlt: 'lash brow serum carousel',
|
|
17
|
+
onClick: jest.fn(),
|
|
18
|
+
additionalProps: {
|
|
19
|
+
testid: 'hero-card-level-1',
|
|
20
|
+
},
|
|
21
|
+
};
|
|
22
|
+
|
|
23
|
+
it('1. renders with correct content and styles', () => {
|
|
24
|
+
render(<NsHeroCardLevel1 {...props} />);
|
|
25
|
+
|
|
26
|
+
const heroCard = screen.getByTestId('hero-card-level-1');
|
|
27
|
+
expect(heroCard).toBeInTheDocument();
|
|
28
|
+
|
|
29
|
+
const shopNowLink = screen.getByText('SHOP NOW');
|
|
30
|
+
expect(shopNowLink).toBeInTheDocument();
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
it('2. calls onClick when the card is clicked', () => {
|
|
34
|
+
render(<NsHeroCardLevel1 {...props} />);
|
|
35
|
+
|
|
36
|
+
const heroCard = screen.getByTestId('hero-card-level-1');
|
|
37
|
+
userEvent.click(heroCard);
|
|
38
|
+
|
|
39
|
+
expect(props.onClick).toHaveBeenCalled();
|
|
40
|
+
});
|
|
41
|
+
|
|
42
|
+
it('3. applies hover styles on mouseover', () => {
|
|
43
|
+
render(<NsHeroCardLevel1 {...props} />);
|
|
44
|
+
|
|
45
|
+
const heroCard = screen.getByTestId('hero-card-level-1');
|
|
46
|
+
userEvent.hover(heroCard);
|
|
47
|
+
});
|
|
48
|
+
});
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
|
+
import userEvent from '@testing-library/user-event';
|
|
4
|
+
import { NsHeroCardLevel2 } from '../';
|
|
5
|
+
|
|
6
|
+
describe('NsHeroCardLevel2 component', () => {
|
|
7
|
+
const props = {
|
|
8
|
+
brand: 'Beauty focus™',
|
|
9
|
+
text: 'Current shop deals',
|
|
10
|
+
body: 'Lumispa, sunscreen and more',
|
|
11
|
+
icon: 'home' as 'home',
|
|
12
|
+
cardLink: {
|
|
13
|
+
href: 'https://www.forceforgood.org/',
|
|
14
|
+
title: 'Discover more',
|
|
15
|
+
},
|
|
16
|
+
backgroundImageUrl: 'https://media.nuskin.com/m/5f1c423bb57589f0/webimage-autumn-sale-carousel.png',
|
|
17
|
+
backgroundImageAlt: 'lash brow serum carousel',
|
|
18
|
+
additionalProps: {
|
|
19
|
+
testid: 'hero-card-level-2',
|
|
20
|
+
},
|
|
21
|
+
onClick: jest.fn(),
|
|
22
|
+
};
|
|
23
|
+
|
|
24
|
+
it('1. renders with correct content and styles', () => {
|
|
25
|
+
render(<NsHeroCardLevel2 {...props} />);
|
|
26
|
+
|
|
27
|
+
const cardContainer = screen.getByTestId('hero-card-level-2');
|
|
28
|
+
expect(cardContainer).toBeInTheDocument();
|
|
29
|
+
|
|
30
|
+
const brandText = screen.getByText('Beauty focus™');
|
|
31
|
+
expect(brandText).toBeInTheDocument();
|
|
32
|
+
|
|
33
|
+
const textContent = screen.getByText('Current shop deals');
|
|
34
|
+
expect(textContent).toBeInTheDocument();
|
|
35
|
+
|
|
36
|
+
const bodyContent = screen.getByText('Lumispa, sunscreen and more');
|
|
37
|
+
expect(bodyContent).toBeInTheDocument();
|
|
38
|
+
|
|
39
|
+
const discoverMoreLink = screen.getByRole('link', { name: 'Discover more' });
|
|
40
|
+
expect(discoverMoreLink).toBeInTheDocument();
|
|
41
|
+
});
|
|
42
|
+
|
|
43
|
+
it('2. calls onClick when the card is clicked', () => {
|
|
44
|
+
render(<NsHeroCardLevel2 {...props} />);
|
|
45
|
+
|
|
46
|
+
const cardContainer = screen.getByTestId('hero-card-level-2');
|
|
47
|
+
userEvent.click(cardContainer);
|
|
48
|
+
|
|
49
|
+
expect(props.onClick).toHaveBeenCalled();
|
|
50
|
+
});
|
|
51
|
+
});
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
|
+
import { NsIconText } from '../';
|
|
4
|
+
|
|
5
|
+
describe('NsIconText component', () => {
|
|
6
|
+
const props = {
|
|
7
|
+
text: 'Lorem ipsum',
|
|
8
|
+
body: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Natoque lacus, in amet nunc. ',
|
|
9
|
+
additionalProps: {
|
|
10
|
+
testid: 'icon-text-card',
|
|
11
|
+
},
|
|
12
|
+
};
|
|
13
|
+
|
|
14
|
+
it('1. renders with correct content and styles', () => {
|
|
15
|
+
render(<NsIconText {...props} />);
|
|
16
|
+
|
|
17
|
+
const cardContainer = screen.getByTestId('icon-text-card');
|
|
18
|
+
expect(cardContainer).toBeInTheDocument();
|
|
19
|
+
|
|
20
|
+
const textContent = screen.getByText('Lorem ipsum');
|
|
21
|
+
expect(textContent).toBeInTheDocument();
|
|
22
|
+
|
|
23
|
+
const bodyContent = screen.getByText(
|
|
24
|
+
'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Natoque lacus, in amet nunc.'
|
|
25
|
+
);
|
|
26
|
+
expect(bodyContent).toBeInTheDocument();
|
|
27
|
+
});
|
|
28
|
+
});
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import { render, screen } from '@testing-library/react';
|
|
2
|
+
import userEvent from '@testing-library/user-event';
|
|
3
|
+
import { NsLargeCard } from '../';
|
|
4
|
+
|
|
5
|
+
describe('NsLargeCard component', () => {
|
|
6
|
+
const props = {
|
|
7
|
+
title: 'Title',
|
|
8
|
+
subtitle: 'Subtitle',
|
|
9
|
+
intro: 'Introduction sentence',
|
|
10
|
+
icon: 'cart' as 'cart',
|
|
11
|
+
cardLink: {
|
|
12
|
+
href: 'https://www.forceforgood.org/',
|
|
13
|
+
title: 'Button Text',
|
|
14
|
+
},
|
|
15
|
+
backgroundImageUrl: 'https://example.com/image.jpg',
|
|
16
|
+
backgroundImageAlt: 'Image Alt',
|
|
17
|
+
};
|
|
18
|
+
|
|
19
|
+
it('1. renders with correct content and styles', () => {
|
|
20
|
+
render(<NsLargeCard {...props} />);
|
|
21
|
+
|
|
22
|
+
expect(screen.getByText(props.title)).toBeInTheDocument();
|
|
23
|
+
expect(screen.getByText(props.subtitle)).toBeInTheDocument();
|
|
24
|
+
});
|
|
25
|
+
|
|
26
|
+
it('2. triggers the link when clicked', () => {
|
|
27
|
+
render(<NsLargeCard {...props} />);
|
|
28
|
+
|
|
29
|
+
userEvent.click(screen.getByRole('link'));
|
|
30
|
+
});
|
|
31
|
+
|
|
32
|
+
it('3. renders NsLink and NsIcon when isHorizontal is true', () => {
|
|
33
|
+
render(<NsLargeCard {...props} isHorizontal={true} />);
|
|
34
|
+
|
|
35
|
+
const actionLink = screen.getByText(props.cardLink.title);
|
|
36
|
+
expect(actionLink).toBeInTheDocument();
|
|
37
|
+
|
|
38
|
+
const parentDiv = actionLink.closest('.cta');
|
|
39
|
+
expect(parentDiv).toBeInTheDocument();
|
|
40
|
+
});
|
|
41
|
+
});
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
|
+
import NsMediumCard from '../NsMediumCard';
|
|
4
|
+
|
|
5
|
+
describe('NsMediumCard component', () => {
|
|
6
|
+
const props = {
|
|
7
|
+
title: 'Sample Title',
|
|
8
|
+
subtitle: 'Sample Subtitle',
|
|
9
|
+
backgroundImageUrl: 'https://example.com/image.jpg',
|
|
10
|
+
backgroundImageAlt: 'Sample Alt Text',
|
|
11
|
+
cardLink: {
|
|
12
|
+
href: 'https://www.example.com',
|
|
13
|
+
title: 'Sample Link Text',
|
|
14
|
+
},
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
it('1. renders with correct content and styles', () => {
|
|
18
|
+
render(<NsMediumCard {...props} />);
|
|
19
|
+
|
|
20
|
+
const mediumCard = screen.getByTestId('medium-card');
|
|
21
|
+
expect(mediumCard).toBeInTheDocument();
|
|
22
|
+
|
|
23
|
+
const titleElement = screen.getByText('Sample Title');
|
|
24
|
+
expect(titleElement).toBeInTheDocument();
|
|
25
|
+
|
|
26
|
+
const subtitleElement = screen.getByText('Sample Subtitle');
|
|
27
|
+
expect(subtitleElement).toBeInTheDocument();
|
|
28
|
+
|
|
29
|
+
const imageElement = screen.getByAltText('Sample Alt Text');
|
|
30
|
+
expect(imageElement).toBeInTheDocument();
|
|
31
|
+
|
|
32
|
+
const linkElement = screen.getByText('Sample Link Text');
|
|
33
|
+
expect(linkElement).toBeInTheDocument();
|
|
34
|
+
});
|
|
35
|
+
});
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
|
+
import NsPost from '../NsPost';
|
|
4
|
+
|
|
5
|
+
describe('NsPost component', () => {
|
|
6
|
+
const props = {
|
|
7
|
+
text: 'Sample Text',
|
|
8
|
+
body: 'Sample Body',
|
|
9
|
+
backgroundImageUrl: 'https://example.com/image.jpg',
|
|
10
|
+
backgroundImageAlt: 'Sample Alt Text',
|
|
11
|
+
additionalProps: {
|
|
12
|
+
testid: 'sample-post',
|
|
13
|
+
},
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
it('1. renders with correct content and styles', () => {
|
|
17
|
+
render(<NsPost {...props} />);
|
|
18
|
+
|
|
19
|
+
const postContainer = screen.getByTestId('sample-post');
|
|
20
|
+
expect(postContainer).toBeInTheDocument();
|
|
21
|
+
|
|
22
|
+
const textElement = screen.getByText('Sample Text');
|
|
23
|
+
expect(textElement).toBeInTheDocument();
|
|
24
|
+
|
|
25
|
+
const bodyElement = screen.getByText('Sample Body');
|
|
26
|
+
expect(bodyElement).toBeInTheDocument();
|
|
27
|
+
|
|
28
|
+
const imageElement = screen.getByAltText('Sample Alt Text');
|
|
29
|
+
expect(imageElement).toBeInTheDocument();
|
|
30
|
+
});
|
|
31
|
+
});
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
|
+
import NsSmallFullCard from '../NsSmallFullCard';
|
|
4
|
+
|
|
5
|
+
describe('NsSmallFullCard component', () => {
|
|
6
|
+
const props = {
|
|
7
|
+
title: 'Sample Title',
|
|
8
|
+
subtitle: 'Sample Subtitle',
|
|
9
|
+
backgroundImageUrl: 'https://example.com/image.jpg',
|
|
10
|
+
backgroundImageAlt: 'Sample Alt Text',
|
|
11
|
+
cardLink: {
|
|
12
|
+
href: 'https://www.example.com',
|
|
13
|
+
title: 'Button Text',
|
|
14
|
+
},
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
it('1. renders with correct content and styles', () => {
|
|
18
|
+
render(<NsSmallFullCard {...props} />);
|
|
19
|
+
|
|
20
|
+
const cardContainer = screen.getByTestId('small-full-card');
|
|
21
|
+
expect(cardContainer).toBeInTheDocument();
|
|
22
|
+
|
|
23
|
+
const titleElement = screen.getByText('Sample Title');
|
|
24
|
+
expect(titleElement).toBeInTheDocument();
|
|
25
|
+
|
|
26
|
+
const subtitleElement = screen.getByText('Sample Subtitle');
|
|
27
|
+
expect(subtitleElement).toBeInTheDocument();
|
|
28
|
+
|
|
29
|
+
const imageElement = screen.getByAltText('Sample Alt Text');
|
|
30
|
+
expect(imageElement).toBeInTheDocument();
|
|
31
|
+
|
|
32
|
+
const linkElement = screen.getByText('Button Text');
|
|
33
|
+
expect(linkElement).toBeInTheDocument();
|
|
34
|
+
expect(linkElement).toHaveAttribute('href', 'https://www.example.com');
|
|
35
|
+
});
|
|
36
|
+
});
|