@nuskin/react-loyalty-elements 1.1.0-loyalty-mvp.3 → 1.1.0-loyalty-exclude.1

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 CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nuskin/react-loyalty-elements",
3
- "version": "1.1.0-loyalty-mvp.3",
3
+ "version": "1.1.0-loyalty-exclude.1",
4
4
  "description": "A React based component library for reusable Nextgen Loyalty component",
5
5
  "main": "src/common/index.ts",
6
6
  "repository": {
@@ -30,9 +30,7 @@
30
30
  "dependencies": {
31
31
  "@types/react": "^18.2.0",
32
32
  "@types/react-dom": "^18.2.0",
33
- "react-dom": "^18.2.0",
34
- "react-icons": "^4.0.0",
35
- "react-circular-progressbar": "^2.1.0"
33
+ "react-dom": "^18.2.0"
36
34
  },
37
35
  "devDependencies": {
38
36
  "@babel/core": "^7.23.2",
package/src/index.ts CHANGED
@@ -1,5 +1,4 @@
1
1
  export * from './SampleComponent';
2
2
  export * from './SubscriptionRewardModal';
3
3
  export * from './SubscriptionRewardBanner';
4
- export * from './CircularProgressBar';
5
4
  export * from './Icons';
@@ -1,157 +0,0 @@
1
- import { styled } from '@nuskin/foundation-theme';
2
-
3
- export const RewardProgressBarContainer = styled.div`
4
- display: flex;
5
- flex-direction: row;
6
- justify-content: space-between;
7
- align-items: center;
8
- align-content: center;
9
- background-color: #f5f5f5;
10
- border: 1px solid #e0e0e0;
11
- border-radius: 10px;
12
- padding: 1.5rem;
13
- margin-bottom: 20px;
14
- height: 50%;
15
- margin: auto;
16
-
17
- @media (max-width: 950px) {
18
- flex-direction: column;
19
- }
20
- `;
21
-
22
- export const LoyaltyProgressSubcontainer = styled.div`
23
- display: flex;
24
- flex-direction: row;
25
- justify-content: space-between;
26
- align-items: center;
27
- align-content: center;
28
-
29
- .reward-logo {
30
- width: 200px;
31
- margin-bottom: 12px;
32
- }
33
-
34
- .reward-progress {
35
- height: 150px;
36
- width: 150px;
37
- }
38
- .progress-bar {
39
- background-color: #e0e0e0;
40
- height: 100%;
41
- }
42
-
43
- @media (max-width: 950px) {
44
- flex-direction: column;
45
-
46
- .info-container {
47
- margin-left: 0px;
48
- align-items: center;
49
- }
50
- .reward-progress-total-div {
51
- margin-top: 10px;
52
- }
53
- }
54
- `;
55
- export const StyledCard = styled.div`
56
- display: flex;
57
- flex-direction: column;
58
- align-items: flex-start;
59
- margin-left: 16px;
60
-
61
- .info-item {
62
- margin: 5px 0;
63
- font-weight: 600;
64
- }
65
- `;
66
- export const Learn3XLink = styled.div`
67
- font-size: 12px;
68
- font-weight: 600;
69
- cursor: pointer;
70
- `;
71
- export const ProgressBarCenter = styled.div`
72
- position: absolute;
73
- top: 50%;
74
- left: 50%;
75
- transform: translate(-50%, -50%);
76
- text-align: center;
77
- color: black;
78
-
79
- .center-value-progress-bar-price {
80
- margin: 0;
81
- }
82
- .center-value-progress-bar-voucher {
83
- margin: 0;
84
- letter-spacing: 0.01em;
85
- }
86
- `;
87
- export const RewardProgressTotalContainer = styled.div`
88
- display: flex;
89
- flex-direction: column;
90
- justify-content: center;
91
- align-items: center;
92
-
93
- .total-button {
94
- display: flex;
95
- align-items: center;
96
- background-color: #e5edf6;
97
- border-radius: 20px;
98
- font-size: 14px;
99
- font-weight: 400;
100
- line-height: 20px;
101
- }
102
- .reward-subtitle {
103
- letter-spacing: 0;
104
- display: flex;
105
- }
106
-
107
- @media (max-width: 950px) {
108
- margin-top: 10px;
109
- }
110
- `;
111
-
112
- export const RewardProgressTotalButtonWithIcon = styled.div`
113
- display: flex;
114
- align-items: center;
115
- background-color: #e5edf6;
116
- border-radius: 20px;
117
- font-size: 14px;
118
- font-weight: 400;
119
- line-height: 20px;
120
- padding: 1rem;
121
- margin-bottom: 14px;
122
-
123
- @media (max-width: 950px) {
124
- margin-top: 14px;
125
- }
126
- `;
127
-
128
- export const IconContainer = styled.span`
129
- .info-icon {
130
- margin-left: 6px !important;
131
- }
132
- .loyalty-icon {
133
- height: 19px !important;
134
- width: 19px !important;
135
- margin-left: 6px !important;
136
- }
137
- .loyalty-warning-icon {
138
- height: 19px !important;
139
- width: 19px !important;
140
- margin-right: 6px !important;
141
- }
142
- .outline-exclamation-icon {
143
- height: 48px !important;
144
- width: 48px !important;
145
- }
146
- `;
147
-
148
- export const SeparatorCard = styled.div`
149
- position: absolute;
150
- height: 100%;
151
- `;
152
-
153
- export const SeparatorInnerCard = styled.div`
154
- background: #fff;
155
- width: 6px;
156
- height: 13%;
157
- `;
@@ -1,38 +0,0 @@
1
- import React from 'react';
2
- import { render } from '@testing-library/react';
3
- import RadialSeparators from './RadialSeprator';
4
- import { SeparatorCard, SeparatorInnerCard } from './CircularProgressBar.styled';
5
-
6
- // Mock the styled components to avoid rendering issues
7
- jest.mock('./CircularProgressBar.styled', () => ({
8
- SeparatorCard: ({ style, children }: any) => <div data-testid="separator-card" style={style}>{children}</div>,
9
- SeparatorInnerCard: () => <div data-testid="separator-inner-card" />,
10
- }));
11
-
12
- describe('RadialSeparators', () => {
13
- it('renders the correct number of separators', () => {
14
- const { getAllByTestId } = render(<RadialSeparators count={5} />);
15
- const separators = getAllByTestId('separator-card');
16
- expect(separators.length).toBe(5);
17
- });
18
-
19
- it('applies the correct rotation to each separator', () => {
20
- const { getAllByTestId } = render(<RadialSeparators count={4} />);
21
- const separators = getAllByTestId('separator-card');
22
-
23
- separators.forEach((separator, index) => {
24
- const expectedRotation = `${index * (1 / 4)}turn`;
25
- expect(separator).toHaveStyle(`transform: rotate(${expectedRotation})`);
26
- });
27
- });
28
-
29
- it('renders SeparatorInnerCard inside each SeparatorCard', () => {
30
- const { getAllByTestId } = render(<RadialSeparators count={3} />);
31
- const separators = getAllByTestId('separator-card');
32
-
33
- separators.forEach((separator) => {
34
- const innerCard = separator.querySelector('[data-testid="separator-inner-card"]');
35
- expect(innerCard).toBeInTheDocument();
36
- });
37
- });
38
- });
@@ -1,27 +0,0 @@
1
- import React from 'react';
2
- import _ from 'lodash';
3
- import { SeparatorCard, SeparatorInnerCard } from './CircularProgressBar.styled';
4
-
5
- function Separator(props: { turns: any; style: React.CSSProperties | undefined }) {
6
- return (
7
- <SeparatorCard
8
- style={{
9
- transform: `rotate(${props.turns}turn)`,
10
- }}
11
- >
12
- <SeparatorInnerCard />
13
- </SeparatorCard>
14
- );
15
- }
16
-
17
- function RadialSeparators(props: { count: number }) {
18
- const turns = 1 / props.count;
19
- return _.range(props.count).map((index) => (
20
- <Separator
21
- key={index}
22
- turns={index * turns} style={undefined}
23
- />
24
- ));
25
- }
26
-
27
- export default RadialSeparators;
@@ -1,59 +0,0 @@
1
- import React from 'react';
2
- import { render, screen } from '@testing-library/react';
3
- import RewardProgressBar from './RewardProgressBar';
4
-
5
- describe('RewardProgressBar Component', () => {
6
- const mockProps = {
7
- value: 3,
8
- title: 'Monthly Reward',
9
- voucherValue: 50,
10
- maxMonths: 6,
11
- handleOpenSubscriptionRewardPopup: jest.fn(),
12
- notQualifyForRewardThisMonth: false,
13
- };
14
-
15
- test('renders correctly with given props', () => {
16
- render(<RewardProgressBar {...mockProps} />);
17
-
18
- // Check if the voucher value is displayed
19
- expect(screen.getByText('$ 50')).toBeInTheDocument();
20
- // Check if the title is displayed
21
- expect(screen.getByText('Monthly Reward')).toBeInTheDocument();
22
- });
23
-
24
- test('displays the correct progress value', () => {
25
- render(<RewardProgressBar {...mockProps} />);
26
-
27
- // Check if the CircularProgressbar is rendered with the correct value
28
- const progressBar = screen.getByRole('progressbar');
29
- expect(progressBar).toHaveAttribute('aria-valuenow', '50'); // 3/6 = 50%
30
- });
31
-
32
- test('shows SubscriptionVoucherIcon when maxMonths is reached', () => {
33
- const props = { ...mockProps, value: 6, notQualifyForRewardThisMonth: false };
34
- render(<RewardProgressBar {...props} />);
35
-
36
- // Check if the SubscriptionVoucherIcon is rendered
37
- expect(screen.getByTestId('subscription-voucher-icon')).toBeInTheDocument();
38
- });
39
-
40
- test('shows warning icon when not qualifying for reward', () => {
41
- const props = { ...mockProps, notQualifyForRewardThisMonth: true };
42
- render(<RewardProgressBar {...props} />);
43
-
44
- // Check if the warning icon is rendered using its class name
45
- const warningIcon = screen.getByRole('img', { hidden: true }); // Assuming the icon is rendered as an <img>
46
- expect(warningIcon).toHaveClass('outline-exclamation-icon'); // Check for the specific class
47
- });
48
-
49
- test('calls handleOpenSubscriptionRewardPopup when clicked', () => {
50
- render(<RewardProgressBar {...mockProps} />);
51
-
52
- // Simulate a click event on the RewardSubscriptionMonthDescription
53
- const descriptionElement = screen.getByText('Monthly Reward'); // Adjust this to match the actual text
54
- descriptionElement.click();
55
-
56
- // Check if the function was called
57
- expect(mockProps.handleOpenSubscriptionRewardPopup).toHaveBeenCalled();
58
- });
59
- });
@@ -1,86 +0,0 @@
1
- import React from 'react';
2
- import { CircularProgressbarWithChildren, buildStyles } from 'react-circular-progressbar';
3
- import 'react-circular-progressbar/dist/styles.css';
4
- import RadialSeparators from './RadialSeprator';
5
- import { FaExclamationTriangle } from 'react-icons/fa';
6
- import SubscriptionVoucherIcon from '../Icons/SubscriptionVoucherIcon';
7
- import { IconContainer, LoyaltyProgressSubcontainer, ProgressBarCenter } from './CircularProgressBar.styled';
8
- import RewardSubscriptionMonthDescription from './RewardSubscriptionMonthDescription';
9
- import { NsTypography } from '@nuskin/foundation-ui-components';
10
- import { RewardProgressBarProps } from './type';
11
-
12
- class RewardProgressBar extends React.Component<RewardProgressBarProps> {
13
- constructor(props: RewardProgressBarProps) {
14
- super(props);
15
- }
16
-
17
- render() {
18
- const {
19
- value,
20
- title,
21
- voucherValue,
22
- maxMonths,
23
- handleOpenSubscriptionRewardPopup,
24
- notQualifyForRewardThisMonth,
25
- } = this.props;
26
- return (
27
- <>
28
- <LoyaltyProgressSubcontainer>
29
- <div className="reward-progress">
30
- <CircularProgressbarWithChildren
31
- value={(value / maxMonths) * 100}
32
- strokeWidth={12}
33
- background
34
- styles={buildStyles({
35
- strokeLinecap: 'butt',
36
- backgroundColor:
37
- value === maxMonths && !notQualifyForRewardThisMonth
38
- ? 'rgb(195 240 194)'
39
- : notQualifyForRewardThisMonth
40
- ? '#fff'
41
- : '#fff',
42
- pathColor: '#6BC56A',
43
- trailColor: '#E0E0E0',
44
- })}
45
- >
46
- <RadialSeparators count={maxMonths} />
47
- {value === maxMonths && !notQualifyForRewardThisMonth ? (
48
- <SubscriptionVoucherIcon />
49
- ) : notQualifyForRewardThisMonth ? (
50
- <IconContainer>
51
- <FaExclamationTriangle className="outline-exclamation-icon" color="#91ACC8" />
52
- </IconContainer>
53
- ) : (
54
- <ProgressBarCenter>
55
- <NsTypography
56
- component="div"
57
- className="center-value-progress-bar-price"
58
- variant="title-l"
59
- weight="bold"
60
- >{`$ ${voucherValue}`}</NsTypography>
61
- <NsTypography
62
- variant="label-s"
63
- weight="bold"
64
- component="div"
65
- className="center-value-progress-bar-voucher"
66
- >
67
- {title}
68
- </NsTypography>
69
- </ProgressBarCenter>
70
- )}
71
- </CircularProgressbarWithChildren>
72
- </div>
73
- <RewardSubscriptionMonthDescription
74
- value={value}
75
- voucherValue={voucherValue}
76
- handleOpenSubscriptionRewardPopup={handleOpenSubscriptionRewardPopup}
77
- maxMonths={maxMonths}
78
- />
79
- </LoyaltyProgressSubcontainer>
80
- </>
81
- );
82
- }
83
- }
84
-
85
- export default RewardProgressBar;
86
- export { RewardProgressBar };
@@ -1,34 +0,0 @@
1
- import React from 'react';
2
- import { render, fireEvent } from '@testing-library/react';
3
- import RewardSubscriptionMonthDescription from './RewardSubscriptionMonthDescription';
4
-
5
- describe('RewardSubscriptionMonthDescription', () => {
6
- const defaultProps = {
7
- value: 3,
8
- voucherValue: 50,
9
- maxMonths: 6,
10
- handleOpenSubscriptionRewardPopup: jest.fn(),
11
- };
12
-
13
- it('renders without crashing', () => {
14
- const { getByAltText } = render(<RewardSubscriptionMonthDescription {...defaultProps} />);
15
- expect(getByAltText('Rewards Logo')).toBeInTheDocument();
16
- });
17
-
18
- it('displays the correct message when the voucher is earned', () => {
19
- const { getByText } = render(<RewardSubscriptionMonthDescription {...{ ...defaultProps, value: 6 }} />);
20
- expect(getByText('Congrats, you earned a $50 voucher!')).toBeInTheDocument();
21
- });
22
-
23
- it('displays the correct message when the voucher is not yet earned', () => {
24
- const { getByText } = render(<RewardSubscriptionMonthDescription {...defaultProps} />);
25
- expect(getByText('3 of 6 Months Completed')).toBeInTheDocument();
26
- });
27
-
28
- it('calls handleOpenSubscriptionRewardPopup when the link is clicked', () => {
29
- const { getByText } = render(<RewardSubscriptionMonthDescription {...defaultProps} />);
30
- const link = getByText('Learn how to 3x your voucher!');
31
- fireEvent.click(link);
32
- expect(defaultProps.handleOpenSubscriptionRewardPopup).toHaveBeenCalledTimes(1);
33
- });
34
- });
@@ -1,31 +0,0 @@
1
- import React from 'react';
2
- import rewardsLogoBlack from 'src/Images/rewards-logo-black.png';
3
- import { Learn3XLink, StyledCard } from './CircularProgressBar.styled';
4
- import { RewardSubscriptionMonthDescriptionProps } from './type';
5
-
6
- class RewardSubscriptionMonthDescription extends React.Component<RewardSubscriptionMonthDescriptionProps> {
7
- constructor(props: RewardSubscriptionMonthDescriptionProps) {
8
- super(props);
9
- }
10
-
11
- render() {
12
- const { value, voucherValue, maxMonths, handleOpenSubscriptionRewardPopup } = this.props;
13
-
14
- return (
15
- <StyledCard>
16
- <img className="reward-logo" src={rewardsLogoBlack} alt="Rewards Logo" />
17
- {value === maxMonths ? (
18
- <div className="info-item">{`Congrats, you earned a $${voucherValue} voucher!`}</div>
19
- ) : (
20
- <div className="info-item">{`${value} of ${maxMonths} Months Completed`}</div>
21
- )}
22
- <Learn3XLink onClick={handleOpenSubscriptionRewardPopup}>
23
- <u>{'Learn how to 3x your voucher!'}</u>
24
- </Learn3XLink>
25
- </StyledCard>
26
- );
27
- }
28
- }
29
-
30
- export default RewardSubscriptionMonthDescription;
31
- export { RewardSubscriptionMonthDescription };
@@ -1,42 +0,0 @@
1
- import React from 'react';
2
- import { render, screen } from '@testing-library/react';
3
- import RewardSubscriptionTotal from './RewardSubscriptionTotal';
4
-
5
- describe('RewardSubscriptionTotal', () => {
6
- const defaultProps = {
7
- value: 1,
8
- title: 'Reward Title',
9
- voucherValue: 100,
10
- maxMonths: 12,
11
- handleOpenSubscriptionRewardPopup: jest.fn(),
12
- notQualifyForRewardThisMonth: false,
13
- };
14
-
15
- test('renders the component with reward information when qualified', () => {
16
- render(<RewardSubscriptionTotal {...defaultProps} />);
17
-
18
- expect(screen.getByText(/Approximate Monthly Total:/i)).toBeInTheDocument();
19
- expect(screen.getByText(/\$157.56/i)).toBeInTheDocument();
20
- expect(screen.getByText(/You’re currently on track for a \$ 100 voucher!/i)).toBeInTheDocument();
21
- });
22
-
23
- test('renders warning message when not qualified for rewards', () => {
24
- render(<RewardSubscriptionTotal {...defaultProps} notQualifyForRewardThisMonth={true} />);
25
-
26
- expect(screen.getByText(/You may not qualify for rewards this month!/i)).toBeInTheDocument();
27
- expect(screen.getByText(/This month’s approximate total:/i)).toBeInTheDocument();
28
- expect(screen.getByText(/\$157.56/i)).toBeInTheDocument();
29
- });
30
-
31
- test('does not show voucher information when max months are reached', () => {
32
- render(<RewardSubscriptionTotal {...defaultProps} value={12} />);
33
-
34
- expect(screen.queryByText(/You’re currently on track for a/i)).not.toBeInTheDocument();
35
- });
36
-
37
- test('renders the correct voucher value', () => {
38
- render(<RewardSubscriptionTotal {...defaultProps} voucherValue={200} />);
39
-
40
- expect(screen.getByText(/You’re currently on track for a \$ 200 voucher!/i)).toBeInTheDocument();
41
- });
42
- });
@@ -1,100 +0,0 @@
1
- import React from 'react';
2
- import { AiOutlineExclamationCircle } from 'react-icons/ai';
3
- import { FaExclamationTriangle } from 'react-icons/fa';
4
- import {
5
- IconContainer,
6
- RewardProgressTotalButtonWithIcon,
7
- RewardProgressTotalContainer,
8
- } from './CircularProgressBar.styled';
9
- import { NsTypography } from '@nuskin/foundation-ui-components';
10
- import { RewardProgressBarProps } from './type';
11
- import Info from '../Icons/Info';
12
- class RewardSubscriptionTotal extends React.Component<RewardProgressBarProps> {
13
- constructor(props: RewardProgressBarProps) {
14
- super(props);
15
- }
16
-
17
- render() {
18
- const {
19
- value,
20
- title,
21
- voucherValue,
22
- maxMonths,
23
- handleOpenSubscriptionRewardPopup,
24
- notQualifyForRewardThisMonth,
25
- } = this.props;
26
- return (
27
- <>
28
- <RewardProgressTotalContainer>
29
- <RewardProgressTotalButtonWithIcon>
30
- {notQualifyForRewardThisMonth ? (
31
- <>
32
- <IconContainer>
33
- <FaExclamationTriangle className="loyalty-warning-icon" color="#4A6987" />
34
- </IconContainer>
35
- <NsTypography
36
- variant="body-s"
37
- weight="normal"
38
- className="reward-subtitle"
39
- colorOverride="#293A4A"
40
- noSpacing
41
- >
42
- You may not qualify for rewards this month!
43
- </NsTypography>
44
- </>
45
- ) : (
46
- <>
47
- <NsTypography
48
- variant="body-s"
49
- weight="normal"
50
- colorOverride="#252525"
51
- className="reward-subtitle"
52
- component="span"
53
- noSpacing
54
- >
55
- Approximate Monthly Total:{' '}
56
- </NsTypography>{' '}
57
- <NsTypography weight="bold" className="button-price" variant="body-s" component="span">
58
- $157.56
59
- </NsTypography>
60
- <IconContainer>
61
- <span className="info-icon">
62
- <Info />
63
- </span>
64
- </IconContainer>
65
- </>
66
- )}
67
- </RewardProgressTotalButtonWithIcon>
68
- {value === maxMonths ? (
69
- ''
70
- ) : notQualifyForRewardThisMonth ? (
71
- <NsTypography
72
- variant="body-s"
73
- weight="normal"
74
- className="reward-subtitle"
75
- colorOverride="#252525"
76
- component="div"
77
- >
78
- This month’s approximate total:{' '}
79
- <NsTypography component="span" className="button-price" variant="body-s" weight="bold">
80
- $157.56
81
- </NsTypography>
82
- </NsTypography>
83
- ) : (
84
- <NsTypography
85
- variant="body-s"
86
- weight="bold"
87
- className="reward-subtitle"
88
- colorOverride="#252525"
89
- >
90
- {`You’re currently on track for a $ ${voucherValue} voucher!*`}
91
- </NsTypography>
92
- )}
93
- </RewardProgressTotalContainer>
94
- </>
95
- );
96
- }
97
- }
98
-
99
- export default RewardSubscriptionTotal;
100
- export { RewardSubscriptionTotal };
@@ -1,77 +0,0 @@
1
- import React from 'react';
2
- import { render, screen } from '@testing-library/react';
3
- import SubscriptionReward from './SubscriptionReward';
4
- import { application } from '../Utils/application';
5
-
6
- // Mock the child components
7
- jest.mock('./RewardProgressBar', () => () => <div>RewardProgressBar</div>);
8
- jest.mock('./RewardSubscriptionTotal', () => () => <div>RewardSubscriptionTotal</div>);
9
- jest.mock('./SubscriptionRewardMobile', () => () => <div>SubscriptionRewardMobile</div>);
10
-
11
- describe('SubscriptionReward Component', () => {
12
- const mockHandleOpenSubscriptionRewardPopup = jest.fn();
13
- const props = {
14
- title: 'Test Title',
15
- handleOpenSubscriptionRewardPopup: mockHandleOpenSubscriptionRewardPopup,
16
- notQualifyForRewardThisMonth: false,
17
- value: 1, // Add the required value prop
18
- voucherValue: 50, // Add the required voucherValue prop
19
- maxMonths: 3, // Add the required maxMonths prop
20
- };
21
-
22
- beforeEach(() => {
23
- jest.clearAllMocks();
24
- });
25
-
26
- it('renders correctly in mobile view', () => {
27
- // Mock application.isMobile to return true
28
- jest.spyOn(application, 'isMobile', 'get').mockReturnValue(true);
29
-
30
- render(<SubscriptionReward {...props} />);
31
-
32
- expect(screen.getByText('SubscriptionRewardMobile')).toBeInTheDocument();
33
- expect(screen.queryByText('RewardProgressBar')).not.toBeInTheDocument();
34
- expect(screen.queryByText('RewardSubscriptionTotal')).not.toBeInTheDocument();
35
- });
36
-
37
- it('renders correctly in desktop view', () => {
38
- // Mock application.isMobile to return false
39
- jest.spyOn(application, 'isMobile', 'get').mockReturnValue(false);
40
-
41
- render(<SubscriptionReward {...props} />);
42
-
43
- expect(screen.getByText('RewardProgressBar')).toBeInTheDocument();
44
- expect(screen.getByText('RewardSubscriptionTotal')).toBeInTheDocument();
45
- expect(screen.queryByText('SubscriptionRewardMobile')).not.toBeInTheDocument();
46
- });
47
-
48
- it('updates value correctly', () => {
49
- jest.spyOn(application, 'isMobile', 'get').mockReturnValue(false);
50
- const { rerender } = render(<SubscriptionReward {...props} />);
51
-
52
- // Check initial value
53
- expect(screen.getByText('RewardProgressBar')).toBeInTheDocument();
54
-
55
- // Simulate updating the value
56
- // Note: You may need to adjust this part based on how you want to test the updateValue method
57
- // This is a placeholder for how you might simulate a value change
58
- // You may need to expose the updateValue method or use a different approach to test state changes
59
-
60
- // Rerender to check if the value has updated
61
- rerender(<SubscriptionReward {...props} />);
62
- // Check if the state has updated (this part may need adjustment based on your implementation)
63
- });
64
-
65
- it('does not update value beyond maxMonths', () => {
66
- jest.spyOn(application, 'isMobile', 'get').mockReturnValue(false);
67
- const { rerender } = render(<SubscriptionReward {...props} />);
68
-
69
- // Simulate an attempt to set value beyond maxMonths
70
- // This is a placeholder for how you might simulate a value change
71
- // You may need to expose the updateValue method or use a different approach to test state changes
72
-
73
- // Rerender to check if the value has not updated
74
- rerender(<SubscriptionReward {...props} />);
75
- // Check if the state has not updated (this part may need adjustment based on your implementation)
76
- });
77
- });
@@ -1,75 +0,0 @@
1
- import React from 'react';
2
- import RewardProgressBar from './RewardProgressBar';
3
- import RewardSubscriptionTotal from './RewardSubscriptionTotal';
4
- import { RewardProgressBarContainer } from './CircularProgressBar.styled';
5
- import { RewardProgressBarProps } from './type';
6
- import SubscriptionRewardMobile from './SubscriptionRewardMobile';
7
- import {application} from '../Utils/application'
8
-
9
-
10
- interface SubscriptionRewardState {
11
- value: number;
12
- voucherValue: number;
13
- }
14
-
15
- class SubscriptionReward extends React.Component<RewardProgressBarProps, SubscriptionRewardState> {
16
- constructor(props: RewardProgressBarProps) {
17
- super(props);
18
- this.state = {
19
- value: 1,
20
- voucherValue: 50,
21
- };
22
- }
23
-
24
- updateValue = (newValue: number) => {
25
- const maxMonths = 3;
26
- // const maxMonths = APPConfig?.getAppConfig()?.subscriptionRewardMonths;
27
- if (newValue >= 0 && newValue <= maxMonths) {
28
- this.setState({ value: newValue });
29
- }
30
- };
31
-
32
- render() {
33
- const { title, handleOpenSubscriptionRewardPopup, notQualifyForRewardThisMonth } = this.props;
34
- const { value, voucherValue } = this.state;
35
- const maxMonths = 3;
36
- // const maxMonths = APPConfig?.getAppConfig()?.subscriptionRewardMonths;
37
- console.log(application.isMobile,'application.isMobile')
38
- return (
39
- <RewardProgressBarContainer>
40
- {application.isMobile ? (
41
- <SubscriptionRewardMobile
42
- value={value}
43
- title={title}
44
- voucherValue={voucherValue}
45
- maxMonths={maxMonths}
46
- handleOpenSubscriptionRewardPopup={handleOpenSubscriptionRewardPopup}
47
- notQualifyForRewardThisMonth={notQualifyForRewardThisMonth}
48
- />
49
- ):(
50
- <>
51
- <RewardProgressBar
52
- value={value}
53
- title={title}
54
- notQualifyForRewardThisMonth={notQualifyForRewardThisMonth}
55
- maxMonths={maxMonths}
56
- voucherValue={voucherValue}
57
- handleOpenSubscriptionRewardPopup={handleOpenSubscriptionRewardPopup}
58
- />
59
- <RewardSubscriptionTotal
60
- notQualifyForRewardThisMonth={notQualifyForRewardThisMonth}
61
- value={value}
62
- voucherValue={voucherValue}
63
- maxMonths={maxMonths}
64
- title={title}
65
- handleOpenSubscriptionRewardPopup={handleOpenSubscriptionRewardPopup}
66
- />
67
- </>
68
- )}
69
- </RewardProgressBarContainer>
70
- );
71
- }
72
- }
73
-
74
- export default SubscriptionReward;
75
- export { SubscriptionReward };
@@ -1,72 +0,0 @@
1
- import React from 'react';
2
- import { render, screen, fireEvent } from '@testing-library/react';
3
- import SubscriptionRewardMobile from './SubscriptionRewardMobile';
4
- import { RewardProgressBarProps } from './type';
5
-
6
- describe('SubscriptionRewardMobile', () => {
7
- const mockHandleOpenSubscriptionRewardPopup = jest.fn();
8
-
9
- const defaultProps: RewardProgressBarProps = {
10
- title: 'Monthly Reward',
11
- handleOpenSubscriptionRewardPopup: mockHandleOpenSubscriptionRewardPopup,
12
- notQualifyForRewardThisMonth: false,
13
- value: 0,
14
- voucherValue: 0,
15
- maxMonths: 0
16
- };
17
-
18
- beforeEach(() => {
19
- jest.clearAllMocks();
20
- });
21
-
22
- test('renders correctly with default props', () => {
23
- render(<SubscriptionRewardMobile {...defaultProps} />);
24
-
25
- expect(screen.getByText('Monthly Reward')).toBeInTheDocument();
26
- expect(screen.getByText('0 of 3 Months Completed')).toBeInTheDocument();
27
- expect(screen.getByText('You’re currently on track for a $ 50 voucher!*')).toBeInTheDocument();
28
- expect(screen.getByText('Learn how to 3x your voucher!')).toBeInTheDocument();
29
- });
30
-
31
- test('displays the correct message when all months are completed', () => {
32
- const { rerender } = render(<SubscriptionRewardMobile {...defaultProps} />);
33
-
34
- // Simulate completing all months
35
- rerender(<SubscriptionRewardMobile {...defaultProps} />);
36
- const instance = screen.getByText('Congrats, you earned a $50 voucher!');
37
-
38
- expect(instance).toBeInTheDocument();
39
- });
40
-
41
- test('displays warning message when not qualifying for rewards', () => {
42
- const propsWithWarning = {
43
- ...defaultProps,
44
- notQualifyForRewardThisMonth: true,
45
- };
46
-
47
- render(<SubscriptionRewardMobile {...propsWithWarning} />);
48
-
49
- expect(screen.getByText('You may not qualify for rewards this month!')).toBeInTheDocument();
50
- expect(screen.getByText('This month’s approximate total:')).toBeInTheDocument();
51
- });
52
-
53
- test('calls handleOpenSubscriptionRewardPopup when Learn link is clicked', () => {
54
- render(<SubscriptionRewardMobile {...defaultProps} />);
55
-
56
- const learnLink = screen.getByText('Learn how to 3x your voucher!');
57
- fireEvent.click(learnLink);
58
-
59
- expect(mockHandleOpenSubscriptionRewardPopup).toHaveBeenCalledTimes(1);
60
- });
61
-
62
- test('updates the progress value correctly', () => {
63
- const { rerender } = render(<SubscriptionRewardMobile {...defaultProps} />);
64
-
65
- // Simulate updating the value to 3
66
- rerender(<SubscriptionRewardMobile {...defaultProps} />);
67
-
68
- // Check if the progress reflects the new value
69
- expect(screen.getByText('3 of 3 Months Completed')).toBeInTheDocument();
70
- expect(screen.getByText('Congrats, you earned a $50 voucher!')).toBeInTheDocument();
71
- });
72
- });
@@ -1,178 +0,0 @@
1
- import React from 'react';
2
- import {
3
- IconContainer,
4
- Learn3XLink,
5
- LoyaltyProgressSubcontainer,
6
- ProgressBarCenter,
7
- StyledCard,
8
- } from './CircularProgressBar.styled';
9
- import { RewardProgressBarProps } from './type';
10
- import RadialSeparators from './RadialSeprator';
11
- import SubscriptionVoucherIcon from '../Icons/SubscriptionVoucherIcon';
12
- import { FaExclamationTriangle } from 'react-icons/fa';
13
- import { NsTypography } from '@nuskin/foundation-ui-components';
14
- import { CircularProgressbarWithChildren, buildStyles } from 'react-circular-progressbar';
15
- import rewardsLogoBlack from 'src/Images/rewards-logo-black.png';
16
- import { RewardProgressTotalButtonWithIcon, RewardProgressTotalContainer } from './CircularProgressBar.styled';
17
- import Info from '../Icons/Info';
18
-
19
- interface SubscriptionRewardState {
20
- value: number;
21
- voucherValue: number;
22
- }
23
-
24
- class SubscriptionRewardMobile extends React.Component<RewardProgressBarProps, SubscriptionRewardState> {
25
- constructor(props: RewardProgressBarProps) {
26
- super(props);
27
- this.state = {
28
- value: 1,
29
- voucherValue: 50,
30
- };
31
- }
32
-
33
- updateValue = (newValue: number) => {
34
- const maxMonths = 3;
35
- // const maxMonths = APPConfig?.getAppConfig()?.subscriptionRewardMonths;
36
- if (newValue >= 0 && newValue <= maxMonths) {
37
- this.setState({ value: newValue });
38
- }
39
- };
40
-
41
- render() {
42
- const { title, handleOpenSubscriptionRewardPopup, notQualifyForRewardThisMonth } = this.props;
43
- const { value, voucherValue } = this.state;
44
- const maxMonths = 3;
45
- // const maxMonths = APPConfig?.getAppConfig()?.subscriptionRewardMonths;
46
-
47
- return (
48
- <LoyaltyProgressSubcontainer>
49
- <StyledCard>
50
- <img className="reward-logo" src={rewardsLogoBlack} alt="Rewards Logo" />
51
- </StyledCard>
52
- <div className="reward-progress">
53
- <CircularProgressbarWithChildren
54
- value={(value / maxMonths) * 100}
55
- strokeWidth={12}
56
- background
57
- styles={buildStyles({
58
- strokeLinecap: 'butt',
59
- backgroundColor:
60
- value === maxMonths && !notQualifyForRewardThisMonth
61
- ? 'rgb(195 240 194)'
62
- : notQualifyForRewardThisMonth
63
- ? '#fff'
64
- : '#fff',
65
- pathColor: '#6BC56A',
66
- trailColor: '#E0E0E0',
67
- })}
68
- >
69
- <RadialSeparators count={maxMonths} />
70
- {value === maxMonths && !notQualifyForRewardThisMonth ? (
71
- <SubscriptionVoucherIcon />
72
- ) : notQualifyForRewardThisMonth ? (
73
- <IconContainer>
74
- <FaExclamationTriangle className="outline-exclamation-icon" color="#91ACC8" />
75
- </IconContainer>
76
- ) : (
77
- <ProgressBarCenter>
78
- <NsTypography
79
- component="div"
80
- className="center-value-progress-bar-price"
81
- variant="title-l"
82
- weight="bold"
83
- >{`$ ${voucherValue}`}</NsTypography>
84
- <NsTypography
85
- variant="label-s"
86
- weight="bold"
87
- component="div"
88
- className="center-value-progress-bar-voucher"
89
- >
90
- {title}
91
- </NsTypography>
92
- </ProgressBarCenter>
93
- )}
94
- </CircularProgressbarWithChildren>
95
- </div>
96
- {value === maxMonths ? (
97
- <div className="info-item">{`Congrats, you earned a $${voucherValue} voucher!`}</div>
98
- ) : (
99
- <div className="info-item">{`${value} of ${maxMonths} Months Completed`}</div>
100
- )}
101
-
102
- <RewardProgressTotalContainer>
103
- {value === maxMonths ? (
104
- ''
105
- ) : notQualifyForRewardThisMonth ? (
106
- <NsTypography
107
- variant="body-s"
108
- weight="normal"
109
- className="reward-subtitle"
110
- colorOverride="#252525"
111
- component="div"
112
- >
113
- This month’s approximate total:{' '}
114
- <NsTypography component="span" className="button-price" variant="body-s" weight="bold">
115
- $157.56
116
- </NsTypography>
117
- </NsTypography>
118
- ) : (
119
- <NsTypography
120
- variant="body-s"
121
- weight="bold"
122
- className="reward-subtitle"
123
- colorOverride="#252525"
124
- >
125
- {`You’re currently on track for a $ ${voucherValue} voucher!*`}
126
- </NsTypography>
127
- )}
128
- <RewardProgressTotalButtonWithIcon>
129
- {notQualifyForRewardThisMonth ? (
130
- <>
131
- <IconContainer>
132
- <FaExclamationTriangle className="loyalty-warning-icon" color="#4A6987" />
133
- </IconContainer>
134
- <NsTypography
135
- variant="body-s"
136
- weight="normal"
137
- className="reward-subtitle"
138
- colorOverride="#293A4A"
139
- noSpacing
140
- >
141
- You may not qualify for rewards this month!
142
- </NsTypography>
143
- </>
144
- ) : (
145
- <>
146
- <NsTypography
147
- variant="body-s"
148
- weight="normal"
149
- colorOverride="#252525"
150
- className="reward-subtitle"
151
- component="span"
152
- noSpacing
153
- >
154
- Approximate Monthly Total:{' '}
155
- </NsTypography>{' '}
156
- <NsTypography weight="bold" className="button-price" variant="body-s" component="span">
157
- $157.56
158
- </NsTypography>
159
- <IconContainer>
160
- <span className="info-icon">
161
- <Info />
162
- </span>
163
- </IconContainer>
164
- </>
165
- )}
166
- </RewardProgressTotalButtonWithIcon>
167
- </RewardProgressTotalContainer>
168
-
169
- <Learn3XLink onClick={handleOpenSubscriptionRewardPopup}>
170
- <u>{'Learn how to 3x your voucher!'}</u>
171
- </Learn3XLink>
172
- </LoyaltyProgressSubcontainer>
173
- );
174
- }
175
- }
176
-
177
- export default SubscriptionRewardMobile;
178
- export { SubscriptionRewardMobile };
@@ -1,6 +0,0 @@
1
- export { default as RadialSeprator } from './RadialSeprator';
2
- export { default as RewardProgressBar } from './RewardProgressBar';
3
- export { default as RewardSubscriptionMonthDescription } from './RewardSubscriptionMonthDescription';
4
- export { default as RewardSubscriptionTotal } from './RewardSubscriptionTotal';
5
- export { default as SubscriptionReward } from './SubscriptionReward';
6
- export { default as SubscriptionRewardMobile } from './SubscriptionRewardMobile';
@@ -1,15 +0,0 @@
1
- export type RewardProgressBarProps = {
2
- value: number;
3
- title: string;
4
- voucherValue: number;
5
- maxMonths: number;
6
- handleOpenSubscriptionRewardPopup: () => void;
7
- notQualifyForRewardThisMonth: boolean;
8
- };
9
-
10
- export type RewardSubscriptionMonthDescriptionProps = {
11
- value: number;
12
- voucherValue: number;
13
- maxMonths: number;
14
- handleOpenSubscriptionRewardPopup: () => void;
15
- };