diff --git a/src/components/DataTable/ColumnsSelector.tsx b/src/components/DataTable/ColumnsSelector.tsx
index 6b72f438..8a384dbc 100644
--- a/src/components/DataTable/ColumnsSelector.tsx
+++ b/src/components/DataTable/ColumnsSelector.tsx
@@ -14,7 +14,7 @@
// You should have received a copy of the GNU Affero General Public License
// along with this program. If not, see .
-import React, { FC, useEffect, useState } from "react";
+import React, { useEffect, useState } from "react";
import styled, { CSSObject } from "styled-components";
import get from "lodash/get";
import debounce from "lodash/debounce";
@@ -38,7 +38,7 @@ const SelectorBox = styled.div(
backgroundColor: get(
theme,
"dropdownSelector.backgroundColor",
- lightColors.white,
+ lightColors.white
),
border: `1px solid ${get(theme, "borderColor", lightColors.borderColor)}`,
padding: "10px 10px",
@@ -53,7 +53,7 @@ const SelectorBox = styled.div(
borderBottom: `1px solid ${get(
theme,
"borderColor",
- lightColors.borderColor,
+ lightColors.borderColor
)}`,
marginBottom: 5,
color: get(theme, "fontColor", lightColors.defaultFontColor),
@@ -66,7 +66,7 @@ const SelectorBox = styled.div(
overflowY: "auto",
},
...overridePropsParse(sx, theme),
- }),
+ })
);
const calcElementPosition = (anchorEl: (EventTarget & HTMLElement) | null) => {
@@ -86,14 +86,14 @@ const calcElementPosition = (anchorEl: (EventTarget & HTMLElement) | null) => {
};
};
-const ColumnsSelector: FC = ({
+const ColumnsSelector = ({
columns,
selectedOptionIDs,
onSelect,
closeTriggerAction,
open,
anchorEl = null,
-}) => {
+}: ColumnSelectorProps): JSX.Element | null => {
const [coords, setCoords] = useState(null);
useEffect(() => {
@@ -120,7 +120,14 @@ const ColumnsSelector: FC = ({
window.addEventListener("scroll", () => {
scrollResize(anchorEl);
});
- });
+
+ return () => {
+ window.removeEventListener("resize", handleResize);
+ window.removeEventListener("scroll", () => {
+ scrollResize(anchorEl);
+ });
+ };
+ }, [anchorEl, closeTriggerAction]);
if (!open || !coords) {
return null;
@@ -128,7 +135,7 @@ const ColumnsSelector: FC = ({
if (!anchorEl) {
console.warn(
- "AnchorEl not set. Element will be rendered on the top of the page",
+ "AnchorEl not set. Element will be rendered on the top of the page"
);
}
@@ -143,18 +150,18 @@ const ColumnsSelector: FC = ({
>
Shown Columns
- {columns.map((column: IColumns) => {
+ {columns.map((column: IColumns) => {
return (
element === column.elementKey,
+ (element) => element === column.elementKey
) >= 0
}
onChange={() => {
- onSelect(column.elementKey || "");
+ onSelect((column.elementKey as keyof T) || ("" as keyof T));
}}
id={`chbox-${column.label}`}
name={`chbox-${column.label}`}
@@ -165,7 +172,7 @@ const ColumnsSelector: FC = ({
,
- document.body,
+ document.body
);
};
diff --git a/src/components/DataTable/DataTable.stories.tsx b/src/components/DataTable/DataTable.stories.tsx
index 8ced64eb..f62db2f0 100644
--- a/src/components/DataTable/DataTable.stories.tsx
+++ b/src/components/DataTable/DataTable.stories.tsx
@@ -23,26 +23,40 @@ import GlobalStyles from "../GlobalStyles/GlobalStyles";
import Grid from "../Grid/Grid";
import CheckIcon from "../Icons/NewDesignIcons/CheckIcon";
+// Define the structure of the records
+type RecordType = {
+ id?: number;
+ field1: string;
+ field2?: string;
+ field3?: string;
+};
+
export default {
title: "MDS/Information/DataTable",
- component: DataTable,
+ component: DataTable as unknown as React.ComponentType<
+ DataTableProps
+ >,
argTypes: {},
-} as Meta;
+} as Meta;
-const Template: Story = (args) => {
- const [selected, setSelected] = useState([]);
- const [selectedColumns, setSelectedColumns] = useState(["field1"]);
+const Template: Story> = (args) => {
+ const [selected, setSelected] = useState>(
+ []
+ );
+ const [selectedColumns, setSelectedColumns] = useState<
+ Array
+ >(["field1"]);
const onSelectFunction = (e: React.ChangeEvent) => {
const targetD = e.target;
const value = targetD.value;
const checked = targetD.checked;
- let elements: string[] = [...selected]; // We clone the selected array
+ let elements: Array = [...selected]; // Clone the selected array
if (checked) {
// If the user has checked this field we need to push this to elements selection list
- elements.push(value);
+ elements.push(value as keyof RecordType | string[]);
} else {
// User has unchecked this field, we need to remove it from the list
elements = elements.filter((element) => element !== value);
@@ -58,7 +72,7 @@ const Template: Story = (args) => {
}
const allItems = args.records.map(
- (element) => `${element[`${args.idField}`]}`,
+ (element) => `${element[`${args.field1Field}`]}`
);
setSelected(allItems);
};
@@ -77,15 +91,15 @@ const Template: Story = (args) => {
extraFunc = {
...extraFunc,
columnsShown: selectedColumns,
- onColumnChange: (columnKey) => {
+ onColumnChange: (columnKey: keyof RecordType) => {
const itemFound = selectedColumns.findIndex(
- (item) => item === columnKey,
+ (item) => item === columnKey
);
// Item Exists, we remove it
if (itemFound >= 0) {
setSelectedColumns(
- selectedColumns.filter((item) => item !== columnKey),
+ selectedColumns.filter((item) => item !== columnKey)
);
} else {
setSelectedColumns([...selectedColumns, columnKey]);
@@ -99,7 +113,7 @@ const Template: Story = (args) => {
-
+ {...args} {...extraFunc} />
@@ -110,9 +124,12 @@ export const Default = Template.bind({});
Default.args = {
disabled: false,
entityName: "Elements",
- records: ["Element1", "Element2", "Element3"],
- columns: [{ label: "Elements List" }],
- onSelect: undefined,
+ records: [
+ { field1: "Element1" },
+ { field1: "Element2" },
+ { field1: "Element3" },
+ ],
+ columns: [{ label: "Elements List", elementKey: "field1" }],
};
export const MultiColumn = Template.bind({});
@@ -122,25 +139,14 @@ MultiColumn.args = {
idField: "field1",
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
{ field1: "Value1-2", field2: "Value2-2", field3: "Value3-2" },
- {
- field1: "Value1-3",
- field2: "Value2-3",
- field3: "Value3-3",
- },
+ { field1: "Value1-3", field2: "Value2-3", field3: "Value3-3" },
],
columns: [
{ label: "Column1", elementKey: "field1" },
{ label: "Column2", elementKey: "field2" },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
};
@@ -151,19 +157,12 @@ CustomColumnsWidth.args = {
idField: "field1",
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
],
columns: [
{ label: "Column1", elementKey: "field1", width: 200 },
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
};
@@ -174,19 +173,12 @@ CustomRowStyle.args = {
idField: "field1",
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
],
columns: [
{ label: "Column1", elementKey: "field1", width: 200 },
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
rowStyle: ({ index }) => (index === 1 ? "deleted" : ""),
};
@@ -199,19 +191,12 @@ BackgroundEnabled.args = {
noBackground: false,
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
],
columns: [
{ label: "Column1", elementKey: "field1", width: 200 },
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
};
@@ -223,19 +208,12 @@ CustomPaperHeight.args = {
customPaperHeight: "250px",
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
],
columns: [
{ label: "Column1", elementKey: "field1", width: 200 },
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
};
@@ -247,19 +225,12 @@ CustomStyles.args = {
customPaperHeight: "250px",
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
],
columns: [
{ label: "Column1", elementKey: "field1", width: 200 },
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
sx: {
backgroundColor: "#f09",
@@ -275,17 +246,9 @@ WithSorting.args = {
customPaperHeight: "250px",
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
{ field1: "An Item", field2: "A Second Item", field3: "A ThirdItem" },
- {
- field1: "One Value",
- field2: "Two Values",
- field3: "Three Values",
- },
+ { field1: "One Value", field2: "Two Values", field3: "Three Values" },
{
field1: "Some Other thing",
field2: "Some Other thing",
@@ -304,10 +267,7 @@ WithSorting.args = {
width: 200,
},
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
sortEnabled: true,
};
@@ -318,12 +278,10 @@ SortingOnSingleValue.args = {
entityName: "Elements",
idField: "field1",
customPaperHeight: "250px",
- records: ["A Value", "B Value", "C Value", "Z Value"],
- columns: [
- {
- label: "Only Column",
- },
- ],
+ records: ["A Value", "B Value", "C Value", "Z Value"].map((field1) => ({
+ field1,
+ })),
+ columns: [{ label: "Only Column", elementKey: "field1" }],
sortEnabled: true,
};
@@ -335,17 +293,9 @@ SortSomeColumnsOnly.args = {
customPaperHeight: "250px",
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
{ field1: "An Item", field2: "A Second Item", field3: "A ThirdItem" },
- {
- field1: "One Value",
- field2: "Two Values",
- field3: "Three Values",
- },
+ { field1: "One Value", field2: "Two Values", field3: "Three Values" },
{
field1: "Some Other thing",
field2: "Some Other thing",
@@ -364,10 +314,7 @@ SortSomeColumnsOnly.args = {
width: 200,
},
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
sortEnabled: ["field1", "field3"],
};
@@ -380,17 +327,9 @@ ManualControlledSort.args = {
customPaperHeight: "250px",
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
{ field1: "An Item", field2: "A Second Item", field3: "A ThirdItem" },
- {
- field1: "One Value",
- field2: "Two Values",
- field3: "Three Values",
- },
+ { field1: "One Value", field2: "Two Values", field3: "Three Values" },
{
field1: "Some Other thing",
field2: "Some Other thing",
@@ -414,10 +353,7 @@ ManualControlledSort.args = {
width: 100,
enableSort: false,
},
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
sortEnabled: {
currentSort: "field1",
@@ -438,52 +374,42 @@ WithItemActions.args = {
itemActions: [
{
type: "edit",
- onClick: (itemID: string) => {
- alert(itemID);
+ onClick: (item: RecordType) => {
+ alert(item.field1);
},
- sendOnlyId: true,
tooltip: "Edit",
- isDisabled: true,
+ isDisabled: (value: RecordType) => value.field1 === "Value1",
},
{
type: "delete",
- onClick: (deleteItem) => {
- console.log("DELETE", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("DELETE", deleteItem.field1);
},
- tooltip: "Delete, Disabled if Column 1 is Value1",
- isDisabled: (value) => value.field1 === "Value1",
+ tooltip: "Delete",
},
{
type: "preview",
- onClick: (deleteItem) => {
- console.log("PREVIEW", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("PREVIEW", deleteItem.field1);
},
tooltip: "Preview",
},
{
type: "cloud",
- onClick: (deleteItem) => {
- console.log("DELETE", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("CLOUD", deleteItem.field1);
},
- tooltip: "Delete, Disabled if Column 1 is Value1",
- showLoader: (value) => value.field1 === "Value1",
+ tooltip: "Cloud",
},
],
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
],
columns: [
{ label: "Column1", elementKey: "field1", width: 200 },
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
sortConfig: {
currentSort: "field1",
@@ -503,105 +429,97 @@ FullItemsActions.args = {
itemActions: [
{
type: "edit",
- onClick: (itemID: string) => {
- alert(itemID);
+ onClick: (item: RecordType) => {
+ alert(item.field1);
},
- sendOnlyId: true,
tooltip: "Edit",
},
{
type: "delete",
- onClick: (deleteItem) => {
- console.log("DELETE", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("DELETE", deleteItem.field1);
},
tooltip: "Delete",
},
{
type: "console",
- onClick: (deleteItem) => {
- console.log("CONSOLE", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("CONSOLE", deleteItem.field1);
},
tooltip: "Console",
},
{
type: "description",
- onClick: (deleteItem) => {
- console.log("DESCRIPTION", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("DESCRIPTION", deleteItem.field1);
},
tooltip: "Description",
},
{
type: "cloud",
- onClick: (deleteItem) => {
- console.log("CLOUD", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("CLOUD", deleteItem.field1);
},
tooltip: "Cloud",
},
{
type: "view",
- onClick: (deleteItem, index) => {
- console.log("VIEW", deleteItem, "INDEX", index);
+ onClick: (deleteItem: RecordType, index: number) => {
+ console.log("VIEW", deleteItem.field1, "INDEX", index);
},
tooltip: "View",
},
{
type: "disable",
- onClick: (deleteItem) => {
- console.log("DISABLE", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("DISABLE", deleteItem.field1);
},
tooltip: "Disable",
},
{
type: "download",
- onClick: (deleteItem) => {
- console.log("DOWNLOAD", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("DOWNLOAD", deleteItem.field1);
},
tooltip: "Download",
},
{
type: "format",
- onClick: (deleteItem) => {
- console.log("FORMAT", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("FORMAT", deleteItem.field1);
},
tooltip: "Format",
},
{
type: "preview",
- onClick: (deleteItem) => {
- console.log("PREVIEW", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("PREVIEW", deleteItem.field1);
},
tooltip: "Preview",
},
{
type: "share",
- onClick: (deleteItem) => {
- console.log("SHARE", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("SHARE", deleteItem.field1);
},
tooltip: "Share",
},
{
type: ,
- onClick: (deleteItem) => {
- console.log("DELETE", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("DELETE", deleteItem.field1);
},
tooltip: "Custom Icon",
},
],
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
],
columns: [
{ label: "Column1", elementKey: "field1", width: 200 },
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
sortConfig: {
currentSort: "field1",
@@ -621,27 +539,20 @@ SingleItemsAction.args = {
itemActions: [
{
type: "delete",
- onClick: (deleteItem) => {
- console.log("DELETE", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("DELETE", deleteItem.field1);
},
tooltip: "Delete",
},
],
records: [
{ field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
],
columns: [
{ label: "Column1", elementKey: "field1", width: 200 },
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
sortConfig: {
currentSort: "field1",
@@ -662,16 +573,15 @@ ColumnsSelector.args = {
itemActions: [
{
type: "edit",
- onClick: (itemID: string) => {
- alert(itemID);
+ onClick: (item: RecordType) => {
+ alert(item.field1);
},
- sendOnlyId: true,
label: "Edit",
},
{
type: "delete",
- onClick: (deleteItem) => {
- console.log("DELETE", deleteItem);
+ onClick: (deleteItem: RecordType) => {
+ console.log("DELETE", deleteItem.field1);
},
label: "Delete",
},
@@ -709,28 +619,16 @@ ColumnsSelector.args = {
columns: [
{ label: "Column1", elementKey: "field1", width: 200 },
{ label: "Column2", elementKey: "field2", width: 100 },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
{ label: "Column4", elementKey: "field4", width: 200 },
{ label: "Column5", elementKey: "field5", width: 100 },
- {
- label: "Column6",
- elementKey: "field6",
- },
+ { label: "Column6", elementKey: "field6" },
{ label: "Column7", elementKey: "field7", width: 200 },
{ label: "Column8", elementKey: "field8", width: 100 },
- {
- label: "Column9",
- elementKey: "field9",
- },
+ { label: "Column9", elementKey: "field9" },
{ label: "Column10", elementKey: "field10", width: 200 },
{ label: "Column11", elementKey: "field11", width: 100 },
- {
- label: "Column12",
- elementKey: "field12",
- },
+ { label: "Column12", elementKey: "field12" },
],
};
@@ -741,28 +639,15 @@ NumericIDs.args = {
idField: "id",
records: [
{ id: 1, field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- id: 2,
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { id: 2, field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
{ id: 3, field1: "Value1-2", field2: "Value2-2", field3: "Value3-2" },
- {
- id: 4,
- field1: "Value1-3",
- field2: "Value2-3",
- field3: "Value3-3",
- },
+ { id: 4, field1: "Value1-3", field2: "Value2-3", field3: "Value3-3" },
],
columns: [
{ label: "ID", elementKey: "id" },
{ label: "Column1", elementKey: "field1" },
{ label: "Column2", elementKey: "field2" },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
};
@@ -773,19 +658,9 @@ LongTitles.args = {
idField: "id",
records: [
{ id: 1, field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- id: 2,
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { id: 2, field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
{ id: 3, field1: "Value1-2", field2: "Value2-2", field3: "Value3-2" },
- {
- id: 4,
- field1: "Value1-3",
- field2: "Value2-3",
- field3: "Value3-3",
- },
+ { id: 4, field1: "Value1-3", field2: "Value2-3", field3: "Value3-3" },
],
columns: [
{ label: "ID", elementKey: "id" },
@@ -794,10 +669,7 @@ LongTitles.args = {
elementKey: "field1",
},
{ label: "Column2", elementKey: "field2" },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
};
@@ -808,19 +680,9 @@ SelectOptions.args = {
idField: "id",
records: [
{ id: 1, field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- id: 2,
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { id: 2, field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
{ id: 3, field1: "Value1-2", field2: "Value2-2", field3: "Value3-2" },
- {
- id: 4,
- field1: "Value1-3",
- field2: "Value2-3",
- field3: "Value3-3",
- },
+ { id: 4, field1: "Value1-3", field2: "Value2-3", field3: "Value3-3" },
],
columns: [
{ label: "ID", elementKey: "id" },
@@ -829,10 +691,7 @@ SelectOptions.args = {
elementKey: "field1",
},
{ label: "Column2", elementKey: "field2" },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
};
@@ -844,19 +703,9 @@ CustomRowHeight.args = {
rowHeight: 80,
records: [
{ id: 1, field1: "Value1", field2: "Value2", field3: "Value3" },
- {
- id: 2,
- field1: "Value1-1",
- field2: "Value2-1",
- field3: "Value3-1",
- },
+ { id: 2, field1: "Value1-1", field2: "Value2-1", field3: "Value3-1" },
{ id: 3, field1: "Value1-2", field2: "Value2-2", field3: "Value3-2" },
- {
- id: 4,
- field1: "Value1-3",
- field2: "Value2-3",
- field3: "Value3-3",
- },
+ { id: 4, field1: "Value1-3", field2: "Value2-3", field3: "Value3-3" },
],
columns: [
{ label: "ID", elementKey: "id" },
@@ -865,10 +714,7 @@ CustomRowHeight.args = {
elementKey: "field1",
},
{ label: "Column2", elementKey: "field2" },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
};
@@ -887,9 +733,6 @@ CustomEmptyMessage.args = {
elementKey: "field1",
},
{ label: "Column2", elementKey: "field2" },
- {
- label: "Column3",
- elementKey: "field3",
- },
+ { label: "Column3", elementKey: "field3" },
],
};
diff --git a/src/components/DataTable/DataTable.tsx b/src/components/DataTable/DataTable.tsx
index a2de94de..b3a1b499 100644
--- a/src/components/DataTable/DataTable.tsx
+++ b/src/components/DataTable/DataTable.tsx
@@ -14,7 +14,7 @@
// You should have received a copy of the GNU Affero General Public License
// along with this program. If not, see .
-import React, { FC, Fragment, useState } from "react";
+import React, { Fragment, useState } from "react";
import {
AutoSizer,
Column,
@@ -24,7 +24,6 @@ import {
} from "react-virtualized";
import styled from "styled-components";
import get from "lodash/get";
-import isString from "lodash/isString";
import Checkbox from "../Checkbox/Checkbox";
import Loader from "../Loader/Loader";
import Grid from "../Grid/Grid";
@@ -78,14 +77,14 @@ const DataTableWrapper = styled.div(
color: get(
theme,
"dataTable.titleColor",
- themeColors["Color/Neutral/Text/colorTextLabel"].lightMode,
+ themeColors["Color/Neutral/Text/colorTextLabel"].lightMode
),
fontSize: 12,
padding: 10,
borderBottom: `${get(
theme,
"dataTable.border",
- "#E2E2E2",
+ "#E2E2E2"
)} 1px solid`,
width: "100%",
},
@@ -108,7 +107,7 @@ const DataTableWrapper = styled.div(
backgroundColor: get(
theme,
"dataTable.hoverColor",
- themeColors["Color/Brand/Control/colorBgActive"].lightMode,
+ themeColors["Color/Brand/Control/colorBgActive"].lightMode
),
"&.canClick": {
cursor: "pointer",
@@ -124,14 +123,14 @@ const DataTableWrapper = styled.div(
color: get(
theme,
"dataTable.selected",
- themeColors["Color/Neutral/Text/colorTextHeading"].lightMode,
+ themeColors["Color/Neutral/Text/colorTextHeading"].lightMode
),
},
"&.deleted .selected": {
color: get(
theme,
"dataTable.itemDisabled",
- themeColors["Color/Neutral/Text/colorTextDisabled"].lightMode,
+ themeColors["Color/Neutral/Text/colorTextDisabled"].lightMode
),
},
},
@@ -230,7 +229,7 @@ const DataTableWrapper = styled.div(
height: 30,
},
...overridePropsParse(sx, theme),
- }),
+ })
);
const TableRowPredefStyles: any = {
@@ -244,11 +243,11 @@ const TableRowPredefStyles: any = {
};
// Main function to render the Table Wrapper
-const DataTable: FC = ({
+const DataTable = ({
itemActions,
columns,
onSelect,
- records,
+ records = [] as T[],
isLoading,
loadingMessage = Loading...
,
entityName,
@@ -259,7 +258,7 @@ const DataTable: FC = ({
columnsSelector = false,
textSelectable = false,
columnsShown = [],
- onColumnChange = (column: string) => {},
+ onColumnChange = () => {},
infiniteScrollConfig,
autoScrollToBottom = false,
disabled = false,
@@ -270,16 +269,16 @@ const DataTable: FC = ({
rowHeight = 36,
sortEnabled = false,
sortCallBack,
-}) => {
+}: DataTableProps) => {
const [columnSelectorOpen, setColumnSelectorOpen] = useState(false);
const [currentSortColumn, setCurrentSortColumn] = useState<
- string | undefined
+ keyof T | undefined
>(undefined);
const [currentSortDirection, setCurrentSortDirection] =
useState("ASC");
-
const [anchorEl, setAnchorEl] = useState(null);
- const rowIDField = idField || "";
+
+ const rowIDField = idField || ("" as keyof T);
const findView = itemActions
? itemActions.find((el) => el.type === "view")
@@ -290,10 +289,9 @@ const DataTable: FC = ({
typeof sortEnabled === "object" &&
!Array.isArray(sortEnabled);
- const clickAction = (rowItem: any, index: number) => {
+ const clickAction = (rowItem: T, index: number) => {
if (findView) {
- const valueClick =
- findView.sendOnlyId && idField ? rowItem[rowIDField] : rowItem;
+ const valueClick = rowItem;
let disabled = false;
@@ -321,7 +319,7 @@ const DataTable: FC = ({
setAnchorEl(null);
};
- const columnsSelection = (columns: IColumns[]) => {
+ const columnsSelection = (columns: IColumns[]) => {
return (
= ({
);
};
- let tableSort: ((val: ITableSortInfo) => any) | undefined = undefined;
- let tableSortBy: string | undefined = undefined;
- let tableSortDirection: SortDirectionType | undefined = undefined;
-
const onSortClick = (sort: ITableSortInfo) => {
- const newSortDirection = get(sort, "sortDirection", "DESC");
- setCurrentSortColumn(sort.sortBy);
+ const newSortDirection = get(
+ sort,
+ "sortDirection",
+ "DESC"
+ ) as SortDirectionType;
+ setCurrentSortColumn(sort.sortBy as keyof T);
setCurrentSortDirection(newSortDirection);
if (sortCallBack) {
@@ -362,10 +360,14 @@ const DataTable: FC = ({
}
};
+ let tableSort: ((val: ITableSortInfo) => any) | undefined = undefined;
+ let tableSortBy: keyof T | undefined = undefined;
+ let tableSortDirection: SortDirectionType | undefined = undefined;
+
if (sortEnabled) {
if (manualSortEnabled) {
tableSort = sortEnabled.onSortClick;
- tableSortBy = sortEnabled.currentSort;
+ tableSortBy = sortEnabled.currentSort as keyof T;
tableSortDirection = sortEnabled.currentDirection;
} else {
tableSort = onSortClick;
@@ -379,8 +381,8 @@ const DataTable: FC = ({
if (sortEnabled && currentSortColumn && !manualSortEnabled) {
sortedRecords = sortRecords(
records,
- currentSortColumn,
- currentSortDirection,
+ currentSortColumn as string,
+ currentSortDirection
);
}
@@ -412,7 +414,6 @@ const DataTable: FC = ({
{columnsSelection(columns)}
)}
{sortedRecords && !isLoading && sortedRecords.length > 0 ? (
- // @ts-ignore
!!sortedRecords[index]}
loadMoreRows={
@@ -427,14 +428,13 @@ const DataTable: FC = ({
}
>
{({ onRowsRendered, registerChild }) => (
- // @ts-ignore
{({ width, height }: any) => {
const optionsWidth = calculateOptionsSize(
width,
itemActions
? itemActions.filter((el) => el.type !== "view").length
- : 0,
+ : 0
);
const hasSelect: boolean = !!(onSelect && selectedItems);
const hasOptions: boolean = !!(
@@ -444,7 +444,6 @@ const DataTable: FC = ({
itemActions[0].type !== "view")
);
return (
- // @ts-ignore
= ({
}
onRowsRendered={onRowsRendered}
sort={tableSort}
- sortBy={tableSortBy}
+ sortBy={tableSortBy ? String(tableSortBy) : undefined}
sortDirection={tableSortDirection}
scrollToIndex={
autoScrollToBottom ? sortedRecords.length - 1 : -1
@@ -493,7 +492,6 @@ const DataTable: FC = ({
}}
>
{hasSelect && (
- // @ts-ignore
(
@@ -516,25 +514,17 @@ const DataTable: FC = ({
)}
)}
- dataKey={`select-${rowIDField}`}
+ dataKey={`select-${String(rowIDField)}`}
width={selectWidth}
disableSort
cellRenderer={({ rowData }) => {
const isSelected = selectedItems
- ? selectedItems.includes(
- isString(rowData)
- ? rowData
- : `${rowData[rowIDField]}`,
- )
+ ? selectedItems.includes(rowData[rowIDField])
: false;
return (
= ({
columnsSelector,
columnsShown,
sortEnabled,
- tableSortBy || "",
- tableSortDirection,
+ tableSortBy,
+ tableSortDirection
)}
{hasOptions && (
- // @ts-ignore
= ({
className="optionsAlignment"
cellRenderer={({ rowData }) => {
const isSelected = selectedItems
- ? selectedItems.includes(
- isString(rowData)
- ? rowData
- : `${rowData[rowIDField]}`,
- )
+ ? selectedItems.includes(rowData[rowIDField])
: false;
return elementActions(
itemActions || [],
rowData,
isSelected,
- rowIDField,
+ String(rowIDField)
);
}}
/>
diff --git a/src/components/DataTable/DataTable.types.ts b/src/components/DataTable/DataTable.types.ts
index 3318e7e6..76ef7822 100644
--- a/src/components/DataTable/DataTable.types.ts
+++ b/src/components/DataTable/DataTable.types.ts
@@ -34,27 +34,30 @@ export const actionsTypes = [
export type PredefinedActionTypes = (typeof actionsTypes)[number];
-export interface ItemActions {
+export interface ItemActions {
tooltip?: string;
type: PredefinedActionTypes | React.ReactNode;
- sendOnlyId?: boolean;
- isDisabled?: boolean | ((itemValue: any) => boolean);
- showLoader?: boolean | ((itemValue: any) => boolean);
- onClick?(valueToSend: any, index?: number): any;
+ isDisabled?: boolean | ((itemValue: T) => boolean);
+ showLoader?: boolean | ((itemValue: T) => boolean);
+ onClick?(valueToSend: T, index?: number): any;
}
-export interface IColumns {
+type Column = {
label: string;
- elementKey?: string;
- renderFunction?: (input: any) => any;
- renderFullObject?: boolean;
+ elementKey?: K;
globalClass?: any;
rowClass?: any;
width?: number;
headerTextAlign?: string;
contentTextAlign?: string;
enableSort?: boolean;
-}
+ renderFunction?: (input: T[K]) => React.ReactNode | string;
+ renderFullObjectFunction?: (input: T) => React.ReactNode | string;
+};
+
+export type IColumns = {
+ [K in keyof T]: Column;
+}[keyof T];
export interface IInfiniteScrollConfig {
loadMoreRecords: (indexElements: {
@@ -75,23 +78,23 @@ export interface ISortConfig {
currentDirection: "ASC" | "DESC" | undefined;
}
-export interface DataTableProps {
- itemActions?: ItemActions[] | null;
- columns: IColumns[];
+export interface DataTableProps {
+ itemActions?: ItemActions[];
+ columns: IColumns[];
onSelect?: (e: React.ChangeEvent) => void;
- idField?: string;
+ idField?: K;
isLoading?: boolean;
loadingMessage?: React.ReactNode;
- records: any[];
+ records: T[];
entityName?: string;
- selectedItems?: string[];
+ selectedItems?: Array | string[];
customEmptyMessage?: string;
customPaperHeight?: string;
noBackground?: boolean;
columnsSelector?: boolean;
textSelectable?: boolean;
- columnsShown?: string[];
- onColumnChange?: (column: string) => any;
+ columnsShown?: Array;
+ onColumnChange?: (column: K) => void;
autoScrollToBottom?: boolean;
infiniteScrollConfig?: IInfiniteScrollConfig;
disabled?: boolean;
@@ -104,7 +107,7 @@ export interface DataTableProps {
parentClassName?: string;
sx?: OverrideTheme;
rowHeight?: number;
- sortEnabled?: boolean | string[] | ISortConfig;
+ sortEnabled?: boolean | Array | ISortConfig;
sortCallBack?: (info: ITableSortInfo) => void;
}
@@ -116,23 +119,20 @@ export interface DataTableWrapperProps extends HTMLAttributes {
rowHeight: number;
}
-export interface IActionButton {
+export interface IActionButton {
tooltip?: string;
type: PredefinedActionTypes | React.ReactNode;
- onClick?: (valueToSend: any, index?: number) => any;
- valueToSend: any;
+ onClick?: (valueToSend: T, index?: number) => any;
+ valueToSend: T;
selected: boolean;
- sendOnlyId?: boolean;
- idField: string;
disabled: boolean;
}
-
-export interface ColumnSelectorProps {
+export interface ColumnSelectorProps {
open: boolean;
closeTriggerAction: () => void;
- onSelect: (column: string) => void;
- columns: IColumns[];
- selectedOptionIDs: string[];
+ onSelect: (column: K) => void;
+ columns: IColumns[];
+ selectedOptionIDs: Array;
sx?: OverrideTheme;
anchorEl?: (EventTarget & HTMLElement) | null;
}
diff --git a/src/components/DataTable/DataTable.utils.tsx b/src/components/DataTable/DataTable.utils.tsx
index d106f8d8..ca36a726 100644
--- a/src/components/DataTable/DataTable.utils.tsx
+++ b/src/components/DataTable/DataTable.utils.tsx
@@ -15,8 +15,6 @@
// along with this program. If not, see .
import React, { Fragment } from "react";
-import get from "lodash/get";
-import isString from "lodash/isString";
import isPlainObject from "lodash/isPlainObject";
import { Column, SortDirectionType } from "react-virtualized";
import { IColumns, ISortConfig, ItemActions } from "./DataTable.types";
@@ -29,43 +27,44 @@ import ChevronDownIcon from "../Icons/NewDesignIcons/ChevronDownIcon";
export const selectWidth = 45;
// Function to render elements in table
-const subRenderFunction = (
- rowData: any,
- column: IColumns,
- isSelected: boolean,
+const subRenderFunction = (
+ rowData: T,
+ column: IColumns,
+ isSelected: boolean
) => {
- const itemElement = isString(rowData)
- ? rowData
- : get(rowData, column.elementKey || "", null); // If the element is just a string, we render it as it is
- const renderConst = column.renderFullObject ? rowData : itemElement;
-
- const renderElement = column.renderFunction
- ? column.renderFunction(renderConst)
- : renderConst; // If render function is set, we send the value to the function.
-
- return (
-
- {renderElement}
-
- );
+ let content: React.ReactNode;
+
+ if (column.renderFullObjectFunction) {
+ content = column.renderFullObjectFunction(rowData);
+ } else if (column.renderFunction && column.elementKey) {
+ const value = rowData[column.elementKey];
+ content = column.renderFunction(value);
+ } else if (column.elementKey) {
+ const value = rowData[column.elementKey];
+ content = value?.toString() ?? "-";
+ } else {
+ content = "-";
+ }
+
+ return {content};
};
// Function to calculate common column width for elements with no with size
-const calculateColumnRest = (
- columns: IColumns[],
+const calculateColumnRest = (
+ columns: IColumns[],
containerWidth: number,
actionsWidth: number,
hasSelect: boolean,
hasActions: boolean,
columnsSelector: boolean,
- columnsShown: string[],
+ columnsShown: string[]
) => {
if (columns) {
let colsItems = [...columns];
if (columnsSelector) {
colsItems = columns.filter((column) =>
- columnsShown.includes(column.elementKey!),
+ columnsShown.includes(String(column.elementKey!))
);
}
@@ -90,19 +89,19 @@ const calculateColumnRest = (
};
// Function that renders Columns in table
-export const generateColumnsMap = (
- columns: IColumns[],
+export const generateColumnsMap = (
+ columns: IColumns[],
containerWidth: number,
actionsWidth: number,
hasSelect: boolean,
hasActions: boolean,
- selectedItems: string[],
- idField: string,
+ selectedItems: Array | string[],
+ idField: keyof T,
columnsSelector: boolean,
- columnsShown: string[],
- sortColumns: boolean | string[] | ISortConfig,
- currentSortColumn: string | undefined,
- currentSortDirection: "ASC" | "DESC" | undefined,
+ columnsShown: Array,
+ sortColumns: boolean | Array | ISortConfig,
+ currentSortColumn: keyof T | undefined,
+ currentSortDirection: "ASC" | "DESC" | undefined
) => {
const manualSortEnabled =
sortColumns &&
@@ -116,10 +115,13 @@ export const generateColumnsMap = (
hasSelect,
hasActions,
columnsSelector,
- columnsShown,
+ columnsShown.map((key) => key.toString()) // Convert keys to strings
);
- return columns.map((column: IColumns, index: number) => {
- if (columnsSelector && !columnsShown.includes(column.elementKey!)) {
+
+ return columns.map((column: IColumns, index: number) => {
+ const columnKey = column.elementKey as keyof T;
+
+ if (columnsSelector && !columnsShown.includes(columnKey)) {
return null;
}
@@ -130,14 +132,12 @@ export const generateColumnsMap = (
const disableSort =
!sortColumns ||
(manualSortEnabled && !manualColumnSortEnabled) ||
- (Array.isArray(sortColumns) &&
- !sortColumns.includes(column?.elementKey || ""));
+ (Array.isArray(sortColumns) && !sortColumns.includes(columnKey));
return (
- // @ts-ignore
{sortColumns ||
- (Array.isArray(sortColumns) &&
- sortColumns.includes(column.elementKey)) ? (
+ (Array.isArray(sortColumns) && sortColumns.includes(columnKey)) ? (
- {currentSortColumn === column.elementKey ||
+ {currentSortColumn === columnKey ||
(columns.length === 1 && currentSortColumn === "column-0") ? (
{currentSortDirection === "ASC" ? (
@@ -186,11 +185,9 @@ export const generateColumnsMap = (
}
cellRenderer={({ rowData }) => {
const isSelected = selectedItems
- ? selectedItems.includes(
- isString(rowData) ? rowData : `${rowData[idField]}`,
- )
+ ? selectedItems.includes(rowData[idField])
: false;
- return subRenderFunction(rowData, column, isSelected);
+ return subRenderFunction(rowData as T, column, isSelected);
}}
width={column.width || commonRestWidth}
disableSort={disableSort}
@@ -201,13 +198,13 @@ export const generateColumnsMap = (
};
// Function to render the action buttons
-export const elementActions = (
- actions: ItemActions[],
+export const elementActions = (
+ actions: ItemActions[],
valueToSend: any,
selected: boolean,
- idField: string,
+ idField: string
) => {
- return actions.map((action: ItemActions, index: number) => {
+ return actions.map((action: ItemActions, index: number) => {
if (action.type === "view") {
return null;
}
@@ -246,8 +243,6 @@ export const elementActions = (
valueToSend={valueToSend}
selected={selected}
key={`actions-${action.type}-${index.toString()}`}
- idField={idField}
- sendOnlyId={!!action.sendOnlyId}
disabled={disabled}
/>
);
@@ -257,7 +252,7 @@ export const elementActions = (
// Function to calculate the options column width according elements inside
export const calculateOptionsSize = (
containerWidth: number,
- totalOptions: number,
+ totalOptions: number
) => {
const minContainerSize = 36;
const sizeOptions = totalOptions * 36;
@@ -277,7 +272,7 @@ export const calculateOptionsSize = (
export const sortRecords = (
records: any[],
sortColumn: string | undefined,
- sortDirection: SortDirectionType,
+ sortDirection: SortDirectionType
) => {
const sortedRecords = records;
diff --git a/src/components/DataTable/TableActionButton.tsx b/src/components/DataTable/TableActionButton.tsx
index 9882de50..61bd3ffa 100644
--- a/src/components/DataTable/TableActionButton.tsx
+++ b/src/components/DataTable/TableActionButton.tsx
@@ -52,13 +52,13 @@ const TableActionCustomIcon = styled.button(({ theme }) => {
background: get(
theme,
`dataTable.actionButton.background`,
- lightV2.plainIconButtonBG,
+ lightV2.plainIconButtonBG
),
"& svg": {
color: get(
theme,
`dataTable.actionButton.iconColor`,
- lightV2.plainIconButtonColor,
+ lightV2.plainIconButtonColor
),
margin: "calc(25% - 2px)",
},
@@ -66,24 +66,24 @@ const TableActionCustomIcon = styled.button(({ theme }) => {
background: get(
theme,
`dataTable.actionButton.hoverBackground`,
- lightV2.plainIconButtonBG,
+ lightV2.plainIconButtonBG
),
borderColor: get(
theme,
`dataTable.actionButton.hoverBorder`,
- lightV2.plainIconButtonBorder,
+ lightV2.plainIconButtonBorder
),
},
"&:active:not(:disabled)": {
background: get(
theme,
`dataTable.actionButton.activeBackground`,
- lightV2.plainIconButtonBG,
+ lightV2.plainIconButtonBG
),
borderColor: get(
theme,
`dataTable.actionButton.activeBorder`,
- lightV2.plainIconButtonBorder,
+ lightV2.plainIconButtonBorder
),
},
"&:disabled": {
@@ -91,18 +91,18 @@ const TableActionCustomIcon = styled.button(({ theme }) => {
background: get(
theme,
`dataTable.actionButton.disabledBackground`,
- "transparent",
+ "transparent"
),
borderColor: get(
theme,
`dataTable.actionButton.disabledBorder`,
- lightV2.disabledSecondary,
+ lightV2.disabledSecondary
),
"& svg": {
color: get(
theme,
`dataTable.actionButton.disabledIconColor`,
- lightV2.disabledSecondaryText,
+ lightV2.disabledSecondaryText
),
},
},
@@ -141,17 +141,13 @@ const defineIcon = (type: PredefinedActionTypes) => {
return null;
};
-const TableActionButton: FC = ({
+const TableActionButton = ({
type,
onClick,
valueToSend,
- idField,
- sendOnlyId = false,
disabled = false,
tooltip,
-}) => {
- const valueClick = sendOnlyId ? valueToSend[idField] : valueToSend;
-
+}: IActionButton) => {
const icon = isPredefinedAction(type) ? defineIcon(type) : type;
let buttonElement = (
= ({
? (e) => {
e.stopPropagation();
if (!disabled) {
- onClick(valueClick);
+ onClick(valueToSend);
} else {
e.preventDefault();
}