@synerise/ds-table 0.43.8 → 0.44.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/CHANGELOG.md +26 -0
- package/README.md +53 -38
- package/dist/Cell/AvatarLabel/AvatarLabel.js +3 -2
- package/dist/Cell/AvatarLabel/AvatarLabel.styles.d.ts +3 -1
- package/dist/Cell/AvatarLabel/AvatarLabel.styles.js +3 -1
- package/dist/Cell/StatusLabel/StatusLabel.types.d.ts +1 -1
- package/dist/ColumnSortMenu/SortRenderer.d.ts +2 -1
- package/dist/ColumnSortMenu/columnWithSortButtons.d.ts +3 -3
- package/dist/ColumnSortMenu/columnWithSortButtons.js +7 -5
- package/dist/ColumnSortMenu/useSortState.js +2 -2
- package/dist/DefaultTable/DefaultTable.d.ts +1 -1
- package/dist/DefaultTable/DefaultTable.js +67 -97
- package/dist/GroupTable/GroupTableBody/GroupTableBody.js +9 -8
- package/dist/RowSelection/RowSelectionColumn.d.ts +4 -0
- package/dist/RowSelection/RowSelectionColumn.js +100 -0
- package/dist/RowSelection/RowSelectionColumn.types.d.ts +13 -0
- package/dist/{hooks/useRowStar.types.js → RowSelection/RowSelectionColumn.types.js} +0 -0
- package/dist/RowSelection/index.d.ts +1 -0
- package/dist/RowSelection/index.js +1 -0
- package/dist/Table.d.ts +1 -1
- package/dist/Table.types.d.ts +5 -2
- package/dist/TableHeader/TableSelection.js +33 -19
- package/dist/VirtualTable/VirtualTable.d.ts +1 -1
- package/dist/VirtualTable/VirtualTable.js +91 -131
- package/dist/VirtualTable/VirtualTable.styles.js +1 -1
- package/dist/VirtualTable/VirtualTableRow.d.ts +5 -4
- package/dist/VirtualTable/VirtualTableRow.js +62 -63
- package/dist/hooks/useRowKey/index.d.ts +1 -0
- package/dist/hooks/useRowKey/index.js +1 -0
- package/dist/hooks/useRowKey/useRowKey.d.ts +7 -0
- package/dist/hooks/useRowKey/useRowKey.js +13 -0
- package/dist/hooks/useRowStar/index.d.ts +2 -0
- package/dist/hooks/useRowStar/index.js +2 -0
- package/dist/hooks/useRowStar/useRowStar.d.ts +2 -0
- package/dist/hooks/{useRowStar.js → useRowStar/useRowStar.js} +11 -10
- package/dist/hooks/useRowStar/useRowStar.types.d.ts +21 -0
- package/dist/hooks/useRowStar/useRowStar.types.js +1 -0
- package/dist/utils/__specs__/getValueFromPath.spec.d.ts +1 -0
- package/dist/utils/getValueFromPath.d.ts +1 -0
- package/dist/utils/getValueFromPath.js +7 -0
- package/dist/utils/index.d.ts +3 -0
- package/dist/utils/index.js +3 -0
- package/package.json +12 -11
- package/dist/hooks/useRowStar.d.ts +0 -3
- package/dist/hooks/useRowStar.types.d.ts +0 -17
|
@@ -4,14 +4,13 @@ function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { va
|
|
|
4
4
|
|
|
5
5
|
function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
|
|
6
6
|
|
|
7
|
-
function _inheritsLoose(subClass, superClass) { subClass.prototype = Object.create(superClass.prototype); subClass.prototype.constructor = subClass; subClass.__proto__ = superClass; }
|
|
8
|
-
|
|
9
7
|
import * as React from 'react';
|
|
10
8
|
import classNames from 'classnames';
|
|
9
|
+
import { areEqual } from 'react-window';
|
|
11
10
|
import InfiniteLoaderItem from '../InfiniteScroll/InfiniteLoaderItem';
|
|
12
11
|
import { EXPANDED_ROW_PROPERTY } from './VirtualTable';
|
|
13
12
|
import * as S from './VirtualTable.styles';
|
|
14
|
-
import { calculatePixels } from '../utils
|
|
13
|
+
import { getValueFromPath, calculatePixels } from '../utils';
|
|
15
14
|
|
|
16
15
|
var isColumnSortingActive = function isColumnSortingActive(columns, column) {
|
|
17
16
|
return !!columns.find(function (c) {
|
|
@@ -23,65 +22,65 @@ var calculateToPixelsIfDefined = function calculateToPixelsIfDefined(value) {
|
|
|
23
22
|
return value ? calculatePixels(value) : value;
|
|
24
23
|
};
|
|
25
24
|
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
selection = data.selection,
|
|
43
|
-
dataSource = data.dataSource,
|
|
44
|
-
cellHeight = data.cellHeight,
|
|
45
|
-
infiniteScroll = data.infiniteScroll,
|
|
46
|
-
defaultTableProps = data.defaultTableProps;
|
|
47
|
-
var rowData = dataSource[index];
|
|
48
|
-
return (
|
|
49
|
-
/*#__PURE__*/
|
|
50
|
-
// eslint-disable-next-line jsx-a11y/click-events-have-key-events,jsx-a11y/no-static-element-interactions
|
|
51
|
-
React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(S.RowWrapper, {
|
|
52
|
-
className: classNames('virtual-table-row', {
|
|
53
|
-
'ds-expanded-row': rowData[EXPANDED_ROW_PROPERTY]
|
|
54
|
-
}),
|
|
55
|
-
style: style,
|
|
56
|
-
onClick: function onClick() {
|
|
57
|
-
return onRowClick && onRowClick(rowData);
|
|
58
|
-
}
|
|
59
|
-
}, mergedColumns.map(function (column, columnIndex) {
|
|
60
|
-
return /*#__PURE__*/React.createElement(S.ColWrapper, {
|
|
61
|
-
className: classNames('virtual-table-cell', {
|
|
62
|
-
'virtual-table-cell-last': columnIndex === mergedColumns.length - 1,
|
|
63
|
-
'ant-table-selection-column': columnIndex === 0 && selection,
|
|
64
|
-
'ds-expanded-row-first': rowData[EXPANDED_ROW_PROPERTY] && columnIndex === 0,
|
|
65
|
-
'ds-expanded-row-data': rowData[EXPANDED_ROW_PROPERTY] && (columnIndex === 1 && selection || columnIndex === 0 && !selection)
|
|
66
|
-
}, isColumnSortingActive((defaultTableProps == null ? void 0 : defaultTableProps.columns) || [], column) && 'ant-table-column-sort', column.className),
|
|
67
|
-
key: "row-" + index + "-column-" + (column.dataIndex || column.key),
|
|
68
|
-
minWidth: calculateToPixelsIfDefined(column == null ? void 0 : column.minWidth),
|
|
69
|
-
width: column.width,
|
|
70
|
-
maxWidth: calculateToPixelsIfDefined(column == null ? void 0 : column.maxWidth)
|
|
71
|
-
}, column.render ? column.render(rowData[column.dataIndex], rowData) : rowData[column.dataIndex]);
|
|
72
|
-
})), infiniteScroll && index === dataSource.length - 1 && /*#__PURE__*/React.createElement(S.RowWrapper, {
|
|
73
|
-
style: _objectSpread({}, style, {
|
|
74
|
-
top: Number(style.top) + cellHeight + "px",
|
|
75
|
-
height: '64px',
|
|
76
|
-
padding: '16px 24px'
|
|
77
|
-
})
|
|
78
|
-
}, /*#__PURE__*/React.createElement(InfiniteLoaderItem, {
|
|
79
|
-
infiniteScroll: infiniteScroll
|
|
80
|
-
})))
|
|
81
|
-
);
|
|
82
|
-
};
|
|
25
|
+
function VirtualTableRow(_ref) {
|
|
26
|
+
var index = _ref.index,
|
|
27
|
+
style = _ref.style,
|
|
28
|
+
_ref$data = _ref.data,
|
|
29
|
+
mergedColumns = _ref$data.mergedColumns,
|
|
30
|
+
onRowClick = _ref$data.onRowClick,
|
|
31
|
+
selection = _ref$data.selection,
|
|
32
|
+
rowStar = _ref$data.rowStar,
|
|
33
|
+
dataSource = _ref$data.dataSource,
|
|
34
|
+
cellHeight = _ref$data.cellHeight,
|
|
35
|
+
infiniteScroll = _ref$data.infiniteScroll,
|
|
36
|
+
defaultTableProps = _ref$data.defaultTableProps;
|
|
37
|
+
var renderColumn = React.useCallback(function (column, rowData, columnIndex) {
|
|
38
|
+
if (rowData[EXPANDED_ROW_PROPERTY] && column.childRender) {
|
|
39
|
+
return column.childRender(getValueFromPath(rowData, column.dataIndex), rowData, columnIndex);
|
|
40
|
+
}
|
|
83
41
|
|
|
84
|
-
|
|
85
|
-
}
|
|
42
|
+
return column.render ? column.render(getValueFromPath(rowData, column.dataIndex), rowData, columnIndex) : getValueFromPath(rowData, column.dataIndex);
|
|
43
|
+
}, []);
|
|
44
|
+
var rowData = React.useMemo(function () {
|
|
45
|
+
return dataSource[index];
|
|
46
|
+
}, [dataSource, index]);
|
|
47
|
+
var infiniteLoader = React.useMemo(function () {
|
|
48
|
+
return infiniteScroll && index === dataSource.length - 1 && /*#__PURE__*/React.createElement(S.RowWrapper, {
|
|
49
|
+
style: _objectSpread({}, style, {
|
|
50
|
+
top: Number(style.top) + cellHeight + "px",
|
|
51
|
+
height: '64px',
|
|
52
|
+
padding: '16px 24px'
|
|
53
|
+
})
|
|
54
|
+
}, /*#__PURE__*/React.createElement(InfiniteLoaderItem, {
|
|
55
|
+
infiniteScroll: infiniteScroll
|
|
56
|
+
}));
|
|
57
|
+
}, [cellHeight, dataSource.length, index, infiniteScroll, style]);
|
|
58
|
+
return /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(S.RowWrapper, {
|
|
59
|
+
className: classNames('virtual-table-row', {
|
|
60
|
+
'ds-expanded-row': rowData[EXPANDED_ROW_PROPERTY]
|
|
61
|
+
}),
|
|
62
|
+
style: style,
|
|
63
|
+
onClick: function onClick(event) {
|
|
64
|
+
event.stopPropagation();
|
|
65
|
+
onRowClick && onRowClick(rowData);
|
|
66
|
+
}
|
|
67
|
+
}, mergedColumns.map(function (column, columnIndex) {
|
|
68
|
+
var firstWithSelectionAndStar = selection && rowStar && columnIndex === 2;
|
|
69
|
+
var firstWithSelectionOrStar = (selection || rowStar) && columnIndex === 1;
|
|
70
|
+
var firstWithoutSelectionAndStar = columnIndex === 0 && !selection && !rowStar;
|
|
71
|
+
return /*#__PURE__*/React.createElement(S.ColWrapper, {
|
|
72
|
+
className: classNames('virtual-table-cell', {
|
|
73
|
+
'virtual-table-cell-last': columnIndex === mergedColumns.length - 1,
|
|
74
|
+
'ant-table-selection-column': columnIndex === 0 && selection,
|
|
75
|
+
'ds-expanded-row-first': rowData[EXPANDED_ROW_PROPERTY] && columnIndex === 0,
|
|
76
|
+
'ds-expanded-row-data': rowData[EXPANDED_ROW_PROPERTY] && (firstWithoutSelectionAndStar || firstWithSelectionOrStar || firstWithSelectionAndStar)
|
|
77
|
+
}, isColumnSortingActive((defaultTableProps == null ? void 0 : defaultTableProps.columns) || [], column) && 'ant-table-column-sort', column.className),
|
|
78
|
+
key: "row-" + index + "-column-" + (column.dataIndex || column.key),
|
|
79
|
+
minWidth: calculateToPixelsIfDefined(column == null ? void 0 : column.minWidth),
|
|
80
|
+
width: column.width,
|
|
81
|
+
maxWidth: calculateToPixelsIfDefined(column == null ? void 0 : column.maxWidth)
|
|
82
|
+
}, renderColumn(column, rowData, columnIndex));
|
|
83
|
+
})), infiniteLoader);
|
|
84
|
+
}
|
|
86
85
|
|
|
87
|
-
export default VirtualTableRow;
|
|
86
|
+
export default React.memo(VirtualTableRow, areEqual);
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from './useRowKey';
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from './useRowKey';
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import * as React from 'react'; // eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
2
|
+
|
|
3
|
+
// eslint-disable-next-line import/prefer-default-export
|
|
4
|
+
export var useRowKey = function useRowKey(rowKey) {
|
|
5
|
+
var getRowKey = React.useCallback(function (row) {
|
|
6
|
+
if (typeof rowKey === 'function') return rowKey(row);
|
|
7
|
+
if (typeof rowKey === 'string') return row[rowKey];
|
|
8
|
+
return row.key || undefined;
|
|
9
|
+
}, [rowKey]);
|
|
10
|
+
return {
|
|
11
|
+
getRowKey: getRowKey
|
|
12
|
+
};
|
|
13
|
+
};
|
|
@@ -10,14 +10,16 @@ var createRowStarColumn = function createRowStarColumn(_ref) {
|
|
|
10
10
|
return function (_ref2) {
|
|
11
11
|
var locale = _ref2.locale,
|
|
12
12
|
rowStar = _ref2.rowStar,
|
|
13
|
-
selection = _ref2.selection
|
|
13
|
+
selection = _ref2.selection,
|
|
14
|
+
getRowKey = _ref2.getRowKey;
|
|
14
15
|
return {
|
|
15
16
|
key: '_row-star',
|
|
16
17
|
className: ((rowStar == null ? void 0 : rowStar.className) || '') + " ds-table-star-column",
|
|
17
18
|
width: !!selection && !!rowStar ? STAR_COL_WIDTH_SELECTON : STAR_COL_WIDTH_SINGLE,
|
|
18
|
-
render: (rowStar == null ? void 0 : rowStar.renderCell) || function (value,
|
|
19
|
-
var
|
|
20
|
-
var keyString = String(
|
|
19
|
+
render: (rowStar == null ? void 0 : rowStar.renderCell) || function (value, record) {
|
|
20
|
+
var expandedChild = record.expandedChild;
|
|
21
|
+
var keyString = String(getRowKey(record));
|
|
22
|
+
if (expandedChild && rowStar != null && rowStar.disableForExpandedRows) return null;
|
|
21
23
|
return /*#__PURE__*/React.createElement(Tooltip, {
|
|
22
24
|
title: locale == null ? void 0 : locale.starRowTooltip
|
|
23
25
|
}, /*#__PURE__*/React.createElement(Button.Star, {
|
|
@@ -27,7 +29,7 @@ var createRowStarColumn = function createRowStarColumn(_ref) {
|
|
|
27
29
|
var newStarredRowKeys = toggleStarred(keyString);
|
|
28
30
|
|
|
29
31
|
if (typeof (rowStar == null ? void 0 : rowStar.onChange) === 'function') {
|
|
30
|
-
rowStar.onChange(newStarredRowKeys);
|
|
32
|
+
rowStar.onChange(newStarredRowKeys, keyString, isStarred(keyString));
|
|
31
33
|
}
|
|
32
34
|
|
|
33
35
|
if (typeof (rowStar == null ? void 0 : rowStar.onClick) === 'function') {
|
|
@@ -38,9 +40,10 @@ var createRowStarColumn = function createRowStarColumn(_ref) {
|
|
|
38
40
|
}
|
|
39
41
|
};
|
|
40
42
|
};
|
|
41
|
-
};
|
|
43
|
+
}; // eslint-disable-next-line import/prefer-default-export
|
|
42
44
|
|
|
43
|
-
|
|
45
|
+
|
|
46
|
+
export var useRowStar = function useRowStar(initialStarredKeys) {
|
|
44
47
|
var starredKeys = React.useRef(new Set(initialStarredKeys));
|
|
45
48
|
|
|
46
49
|
var getStarredRowKeys = function getStarredRowKeys() {
|
|
@@ -71,6 +74,4 @@ var useRowStar = function useRowStar(initialStarredKeys) {
|
|
|
71
74
|
toggleStarred: toggleStarred,
|
|
72
75
|
getRowStarColumn: getRowStarColumn
|
|
73
76
|
};
|
|
74
|
-
};
|
|
75
|
-
|
|
76
|
-
export default useRowStar;
|
|
77
|
+
};
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import * as React from 'react';
|
|
2
|
+
import { ColumnType } from 'antd/lib/table';
|
|
3
|
+
import { DSTableProps, DSColumnType } from '../../Table.types';
|
|
4
|
+
export interface RowStar<T> {
|
|
5
|
+
className?: string;
|
|
6
|
+
starredRowKeys: string[];
|
|
7
|
+
renderCell?: ColumnType<T>['render'];
|
|
8
|
+
onClick?: (e: React.MouseEvent<HTMLElement, MouseEvent>) => void;
|
|
9
|
+
onChange?: (starredRowKeys: string[], starredKey: string, isStarred: boolean) => void;
|
|
10
|
+
disableForExpandedRows?: boolean;
|
|
11
|
+
}
|
|
12
|
+
export declare type AnyRecordType = any;
|
|
13
|
+
export interface UseStarredApi {
|
|
14
|
+
getStarredKeys: () => string[];
|
|
15
|
+
isStarred: (key: string) => boolean;
|
|
16
|
+
toggleStarred: (key: string) => string[];
|
|
17
|
+
getRowStarColumn: (dsTableProps: CreateRowStarColumnProps) => DSColumnType<AnyRecordType>;
|
|
18
|
+
}
|
|
19
|
+
export declare type CreateRowStarColumnProps = DSTableProps<AnyRecordType> & {
|
|
20
|
+
getRowKey: (row: AnyRecordType) => React.ReactText | undefined;
|
|
21
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const getValueFromPath: (object: object, valuePath?: string | number | (string | number)[] | undefined) => string | number | boolean;
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import { path } from 'ramda'; // eslint-disable-next-line import/prefer-default-export
|
|
2
|
+
|
|
3
|
+
export var getValueFromPath = function getValueFromPath(object, valuePath) {
|
|
4
|
+
if (typeof valuePath === 'string') return object[valuePath];
|
|
5
|
+
if (Array.isArray(valuePath)) return path(valuePath, object) || '';
|
|
6
|
+
return '';
|
|
7
|
+
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@synerise/ds-table",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.44.0",
|
|
4
4
|
"description": "Table UI Component for the Synerise Design System",
|
|
5
5
|
"license": "ISC",
|
|
6
6
|
"repository": "synerise/synerise-design",
|
|
@@ -35,27 +35,28 @@
|
|
|
35
35
|
"@synerise/ds-alert": "^0.5.2",
|
|
36
36
|
"@synerise/ds-button": "^0.17.1",
|
|
37
37
|
"@synerise/ds-button-group": "^0.6.8",
|
|
38
|
-
"@synerise/ds-checkbox": "^0.11.
|
|
39
|
-
"@synerise/ds-column-manager": "^0.10.
|
|
40
|
-
"@synerise/ds-dropdown": "^0.17.
|
|
38
|
+
"@synerise/ds-checkbox": "^0.11.7",
|
|
39
|
+
"@synerise/ds-column-manager": "^0.10.8",
|
|
40
|
+
"@synerise/ds-dropdown": "^0.17.13",
|
|
41
41
|
"@synerise/ds-flag": "^0.3.2",
|
|
42
42
|
"@synerise/ds-icon": "^0.48.0",
|
|
43
43
|
"@synerise/ds-input": "^0.18.9",
|
|
44
|
-
"@synerise/ds-loader": "^0.2.
|
|
45
|
-
"@synerise/ds-menu": "^0.
|
|
44
|
+
"@synerise/ds-loader": "^0.2.7",
|
|
45
|
+
"@synerise/ds-menu": "^0.13.0",
|
|
46
46
|
"@synerise/ds-pagination": "^0.7.8",
|
|
47
|
-
"@synerise/ds-search": "^0.7.
|
|
47
|
+
"@synerise/ds-search": "^0.7.7",
|
|
48
48
|
"@synerise/ds-search-bar": "^0.5.10",
|
|
49
49
|
"@synerise/ds-select": "^0.14.10",
|
|
50
|
-
"@synerise/ds-skeleton": "^0.2.
|
|
51
|
-
"@synerise/ds-status": "^0.5.
|
|
52
|
-
"@synerise/ds-tags": "^0.6.
|
|
50
|
+
"@synerise/ds-skeleton": "^0.2.7",
|
|
51
|
+
"@synerise/ds-status": "^0.5.13",
|
|
52
|
+
"@synerise/ds-tags": "^0.6.13",
|
|
53
53
|
"@synerise/ds-tooltip": "^0.11.8",
|
|
54
54
|
"@synerise/ds-typography": "^0.12.2",
|
|
55
55
|
"@synerise/ds-utils": "^0.19.0",
|
|
56
56
|
"@types/react-window": "^1.8.2",
|
|
57
57
|
"classnames": "^2.2.6",
|
|
58
58
|
"copy-to-clipboard": "^3.3.1",
|
|
59
|
+
"ramda": "0.27.0",
|
|
59
60
|
"rc-resize-observer": "^0.2.1",
|
|
60
61
|
"react-window": "^1.8.6",
|
|
61
62
|
"unit-to-px": "^1.0.5"
|
|
@@ -65,5 +66,5 @@
|
|
|
65
66
|
"antd": "^4",
|
|
66
67
|
"react": ">=16.9.0 < 17.0.0"
|
|
67
68
|
},
|
|
68
|
-
"gitHead": "
|
|
69
|
+
"gitHead": "7f696cdfd31f36bbeeb750df44b0f6d2010d0c9d"
|
|
69
70
|
}
|
|
@@ -1,17 +0,0 @@
|
|
|
1
|
-
/// <reference types="react" />
|
|
2
|
-
import { ColumnType } from 'antd/lib/table';
|
|
3
|
-
import { DSTableProps, DSColumnType } from '../Table.types';
|
|
4
|
-
export interface RowStar<T> {
|
|
5
|
-
className?: string;
|
|
6
|
-
starredRowKeys: string[];
|
|
7
|
-
renderCell?: ColumnType<T>['render'];
|
|
8
|
-
onClick?: (e: React.MouseEvent<HTMLElement, MouseEvent>) => void;
|
|
9
|
-
onChange?: (starredRowKeys: string[]) => void;
|
|
10
|
-
}
|
|
11
|
-
export declare type AnyRecordType = any;
|
|
12
|
-
export interface UseStarredApi {
|
|
13
|
-
getStarredKeys: () => string[];
|
|
14
|
-
isStarred: (key: string) => boolean;
|
|
15
|
-
toggleStarred: (key: string) => string[];
|
|
16
|
-
getRowStarColumn: (dsTableProps: DSTableProps<AnyRecordType>) => DSColumnType<AnyRecordType>;
|
|
17
|
-
}
|