@onewelcome/react-lib-components 0.1.9-alpha → 0.1.10-alpha

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": "@onewelcome/react-lib-components",
3
- "version": "0.1.9-alpha",
3
+ "version": "0.1.10-alpha",
4
4
  "license": "Apache-2.0",
5
5
  "author": "OneWelcome B.V.",
6
6
  "main": "dist/index.js",
@@ -53,7 +53,15 @@ export const Pagination = React.forwardRef<HTMLDivElement, Props>(
53
53
  ) => {
54
54
  /** We use an internal state variable, because we don't want to fire onCurrentPageChange whenever onChange fires on the input. Rather, only when the Enter key is pressed. */
55
55
  const [internalCurrentPage, setInternalCurrentPage] = useState(currentPage?.toString() || '1');
56
- const calculateAmountOfPages = () => (totalElements ? Math.ceil(totalElements / pageSize) : 0);
56
+ const calculateAmountOfPages = () => {
57
+ if (!totalElements) return 1;
58
+
59
+ if (Math.ceil(totalElements / pageSize) < 1) {
60
+ return 1;
61
+ }
62
+
63
+ return Math.ceil(totalElements / pageSize);
64
+ };
57
65
 
58
66
  const onEnterListener = (event: React.KeyboardEvent<HTMLInputElement>) => {
59
67
  if (event.code === 'Enter') {
@@ -102,7 +110,11 @@ export const Pagination = React.forwardRef<HTMLDivElement, Props>(
102
110
  }
103
111
 
104
112
  if (string.includes('%2')) {
105
- return <div key={string}>{string.replace('%2', amountOfPages.toString())}&nbsp;</div>;
113
+ return (
114
+ <div key={string}>
115
+ <strong>{string.replace('%2', amountOfPages.toString())}</strong>&nbsp;
116
+ </div>
117
+ );
106
118
  }
107
119
 
108
120
  return <div key={string}>{string}&nbsp;</div>;
@@ -135,7 +147,7 @@ export const Pagination = React.forwardRef<HTMLDivElement, Props>(
135
147
  </div>
136
148
  )}
137
149
  <div className={classes['pagination']}>
138
- {totalElements && pageSize && (
150
+ {pageSize && (
139
151
  <div className={classes['per-page']}>
140
152
  <Label id="page-size-select-label">{translate.itemsPerPage}</Label>
141
153
  <Select
@@ -151,7 +163,7 @@ export const Pagination = React.forwardRef<HTMLDivElement, Props>(
151
163
  </div>
152
164
  )}
153
165
  <Fragment>
154
- {((currentPage && currentPage > 2) || (currentPage && currentPage > 1)) && (
166
+ {!!((currentPage && currentPage > 2) || (currentPage && currentPage > 1)) && (
155
167
  <div className={classes['previous']}>
156
168
  {currentPage > 2 && (
157
169
  <IconButton
@@ -173,12 +185,14 @@ export const Pagination = React.forwardRef<HTMLDivElement, Props>(
173
185
  )}
174
186
  </div>
175
187
  )}
176
- {totalElements && (
188
+ {totalElements && calculateAmountOfPages() && (
177
189
  <div className={classes['page']}>{renderCurrentPageTranslation()}</div>
178
190
  )}
179
191
  <div className={classes['next']}>
180
- {((currentPage && currentPage < calculateAmountOfPages()) ||
181
- (currentPage && !totalElements)) && (
192
+ {!!(
193
+ (currentPage !== undefined && currentPage < calculateAmountOfPages()!) ||
194
+ (currentPage !== undefined && !totalElements)
195
+ ) && (
182
196
  <IconButton
183
197
  title="next"
184
198
  onClick={() => onPageChangeHandler(currentPage + 1)}
@@ -187,7 +201,7 @@ export const Pagination = React.forwardRef<HTMLDivElement, Props>(
187
201
  <Icon icon={Icons.ChevronRight} />
188
202
  </IconButton>
189
203
  )}
190
- {currentPage && totalElements && currentPage < calculateAmountOfPages()! - 1 && (
204
+ {!!(currentPage && totalElements && currentPage < calculateAmountOfPages()! - 1) && (
191
205
  <IconButton
192
206
  title="last"
193
207
  onClick={() => onPageChangeHandler(totalElements / pageSize)}
@@ -0,0 +1,20 @@
1
+ @import '../mixins.module.scss';
2
+
3
+ .skeleton {
4
+ display: block;
5
+ height: auto;
6
+ @include skeletonLoading();
7
+ }
8
+
9
+ .no-height::before {
10
+ content: ' ';
11
+ white-space: pre-wrap;
12
+ }
13
+
14
+ .text {
15
+ border-radius: 0.5rem;
16
+ }
17
+
18
+ .circular {
19
+ border-radius: 50%;
20
+ }
@@ -0,0 +1,96 @@
1
+ import React, { useEffect, useRef } from 'react';
2
+ import { Skeleton, Props } from './Skeleton';
3
+ import { render } from '@testing-library/react';
4
+
5
+ const defaultParams: Props = {};
6
+
7
+ const createSkeleton = (params?: (defaultParams: Props) => Props) => {
8
+ let parameters: Props = defaultParams;
9
+ if (params) {
10
+ parameters = params(defaultParams);
11
+ }
12
+ const queries = render(<Skeleton {...parameters} data-testid="skeleton" />);
13
+ const skeleton = queries.getByTestId('skeleton');
14
+
15
+ return {
16
+ ...queries,
17
+ skeleton,
18
+ };
19
+ };
20
+
21
+ describe('Skeleton should render', () => {
22
+ it('renders without crashing', () => {
23
+ const { skeleton } = createSkeleton();
24
+
25
+ expect(skeleton).toHaveClass('skeleton text no-height', { exact: true });
26
+
27
+ expect(skeleton).toBeDefined();
28
+ });
29
+
30
+ it('renders with properties passed', () => {
31
+ const testClass = 'testclass';
32
+ const { skeleton } = createSkeleton((defaultParams) => ({
33
+ ...defaultParams,
34
+ className: testClass,
35
+ }));
36
+
37
+ expect(skeleton).toHaveClass(`skeleton text no-height ${testClass}`, { exact: true });
38
+ });
39
+
40
+ it('renders text variant with width and height', () => {
41
+ const width = '10rem';
42
+ const height = 10;
43
+ const { skeleton } = createSkeleton((defaultParams) => ({
44
+ ...defaultParams,
45
+ variant: 'text',
46
+ width,
47
+ height,
48
+ }));
49
+
50
+ expect(skeleton).toHaveClass(`skeleton text`, { exact: true });
51
+ expect(skeleton).toHaveStyle({ width, height: '10px' });
52
+ });
53
+
54
+ it('renders rectangle variant', () => {
55
+ const { skeleton } = createSkeleton((defaultParams) => ({
56
+ ...defaultParams,
57
+ variant: 'rectangle',
58
+ }));
59
+
60
+ expect(skeleton).toHaveClass(`skeleton no-height`, { exact: true });
61
+ });
62
+
63
+ it('renders circular variant', () => {
64
+ const { skeleton } = createSkeleton((defaultParams) => ({
65
+ ...defaultParams,
66
+ variant: 'circular',
67
+ }));
68
+
69
+ expect(skeleton).toHaveClass(`skeleton no-height circular`, { exact: true });
70
+ });
71
+ });
72
+
73
+ describe('ref should work', () => {
74
+ it('should give back the proper data prop, this also checks if the component propagates ...rest properly', () => {
75
+ const ExampleComponent = ({
76
+ propagateRef,
77
+ }: {
78
+ propagateRef: (ref: React.RefObject<HTMLElement>) => void;
79
+ }) => {
80
+ const ref = useRef(null);
81
+
82
+ useEffect(() => {
83
+ propagateRef(ref);
84
+ }, [ref]);
85
+
86
+ return <Skeleton {...defaultParams} data-ref="testing" ref={ref} />;
87
+ };
88
+
89
+ const refCheck = (ref: React.RefObject<HTMLElement>) => {
90
+ expect(ref.current).toHaveAttribute('data-ref', 'testing');
91
+ };
92
+
93
+ const container = document.createElement('tbody');
94
+ render(<ExampleComponent propagateRef={refCheck} />, { container });
95
+ });
96
+ });
@@ -0,0 +1,29 @@
1
+ import React, { ComponentPropsWithRef } from 'react';
2
+ import classes from './Skeleton.module.scss';
3
+
4
+ export interface Props extends Omit<ComponentPropsWithRef<'div'>, 'children'> {
5
+ variant?: 'circular' | 'rectangle' | 'text';
6
+ height?: number | string;
7
+ width?: number | string;
8
+ }
9
+
10
+ export const Skeleton = React.forwardRef<HTMLDivElement, Props>(
11
+ ({ variant = 'text', height, width, className, style, ...rest }: Props, ref) => {
12
+ const classNames = [classes['skeleton']];
13
+ !height && classNames.push(classes['no-height']);
14
+ variant === 'text' && classNames.push(classes['text']);
15
+ variant === 'circular' && classNames.push(classes['circular']);
16
+ className && classNames.push(className);
17
+
18
+ return (
19
+ <span
20
+ {...rest}
21
+ aria-busy="true"
22
+ aria-hidden="true"
23
+ ref={ref}
24
+ style={{ ...style, width, height }}
25
+ className={classNames.join(' ')}
26
+ ></span>
27
+ );
28
+ }
29
+ );
@@ -28,8 +28,6 @@ interface CSSProperties {
28
28
  snackbarBorderRadius?: string;
29
29
  dataGridRowBackgroundColor?: string;
30
30
  dataGridRowHoverBackgroundColor?: string;
31
- cardBackgroundColor?: string;
32
- cardBorderRadius?: string;
33
31
  tabsBackgroundColor?: string;
34
32
  tabBorderWidth?: string;
35
33
  tabBorderStyle?: string;
@@ -88,8 +86,6 @@ export const BaseStyling = ({ children, properties = {} }: Props) => {
88
86
  snackbarBorderRadius: '8px',
89
87
  dataGridRowBackgroundColor: 'transparent',
90
88
  dataGridRowHoverBackgroundColor: '#f5e6f0',
91
- cardBackgroundColor: '#fff',
92
- cardBorderRadius: '8px',
93
89
  tabsBackgroundColor: '#FFF',
94
90
  tabBorderWidth: '2px',
95
91
  tabBorderStyle: 'solid',
package/src/index.ts CHANGED
@@ -14,6 +14,7 @@ export { Tile, Props as TileProps } from './Tiles/Tile';
14
14
  export { Tiles, Props as TilesProps } from './Tiles/Tiles';
15
15
  export { Tooltip, Props as TooltipProps } from './Tooltip/Tooltip';
16
16
  export { Typography, Variant, Props as TypographyProps } from './Typography/Typography';
17
+ export { Skeleton, Props as SkeletonProps } from './Skeleton/Skeleton';
17
18
  export {
18
19
  Pagination,
19
20
  Props as PaginationProps,