@visns-studio/visns-components 5.14.15 → 5.14.16
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +1 -1
- package/src/components/DataGrid.jsx +299 -212
- package/src/components/Form.jsx +13 -9
package/package.json
CHANGED
|
@@ -89,7 +89,7 @@
|
|
|
89
89
|
"react-dom": "^17.0.0 || ^18.0.0"
|
|
90
90
|
},
|
|
91
91
|
"name": "@visns-studio/visns-components",
|
|
92
|
-
"version": "5.14.
|
|
92
|
+
"version": "5.14.16",
|
|
93
93
|
"description": "Various packages to assist in the development of our Custom Applications.",
|
|
94
94
|
"main": "src/index.js",
|
|
95
95
|
"files": [
|
|
@@ -259,9 +259,10 @@ const DataGrid = forwardRef(
|
|
|
259
259
|
console.log('🔍 DataGrid settings prop changed:', {
|
|
260
260
|
settings: settings,
|
|
261
261
|
settingsLength: settings?.length || 0,
|
|
262
|
-
hasUpdateSetting:
|
|
263
|
-
|
|
264
|
-
|
|
262
|
+
hasUpdateSetting:
|
|
263
|
+
settings?.some((s) => s.id === 'update') || false,
|
|
264
|
+
settingsIds: settings?.map((s) => s.id) || [],
|
|
265
|
+
timestamp: new Date().toISOString(),
|
|
265
266
|
});
|
|
266
267
|
}, [settings]);
|
|
267
268
|
|
|
@@ -269,7 +270,7 @@ const DataGrid = forwardRef(
|
|
|
269
270
|
console.log('🔍 DataGrid form prop changed:', {
|
|
270
271
|
form: form,
|
|
271
272
|
primaryKey: form?.primaryKey,
|
|
272
|
-
timestamp: new Date().toISOString()
|
|
273
|
+
timestamp: new Date().toISOString(),
|
|
273
274
|
});
|
|
274
275
|
}, [form]);
|
|
275
276
|
|
|
@@ -311,7 +312,7 @@ const DataGrid = forwardRef(
|
|
|
311
312
|
console.log('🔍 modalOpen called:', {
|
|
312
313
|
formType: formType,
|
|
313
314
|
formId: formId,
|
|
314
|
-
timestamp: new Date().toISOString()
|
|
315
|
+
timestamp: new Date().toISOString(),
|
|
315
316
|
});
|
|
316
317
|
setModalShow(true);
|
|
317
318
|
setFormType(formType);
|
|
@@ -331,25 +332,32 @@ const DataGrid = forwardRef(
|
|
|
331
332
|
/** Table States */
|
|
332
333
|
const dataRef = useRef(null);
|
|
333
334
|
const [dSearch, setDSearch] = useState('');
|
|
334
|
-
|
|
335
|
+
|
|
335
336
|
/** Optimized refs for settings and form to avoid unnecessary re-renders */
|
|
336
337
|
const settingsRef = useRef(settings);
|
|
337
338
|
const formRef = useRef(form);
|
|
338
|
-
|
|
339
|
+
|
|
339
340
|
// Keep refs updated with current values
|
|
340
341
|
useEffect(() => {
|
|
341
342
|
settingsRef.current = settings;
|
|
342
343
|
}, [settings]);
|
|
343
|
-
|
|
344
|
+
|
|
344
345
|
useEffect(() => {
|
|
345
346
|
formRef.current = form;
|
|
346
347
|
}, [form]);
|
|
347
|
-
|
|
348
|
+
|
|
348
349
|
// Memoize settings to avoid unnecessary re-renders when array reference changes but content is same
|
|
349
|
-
const memoizedSettings = useMemo(
|
|
350
|
-
settings
|
|
351
|
-
|
|
352
|
-
|
|
350
|
+
const memoizedSettings = useMemo(
|
|
351
|
+
() => settings,
|
|
352
|
+
[
|
|
353
|
+
settings?.length,
|
|
354
|
+
settings
|
|
355
|
+
?.map(
|
|
356
|
+
(s) => `${s.id}-${s.roles?.join(',') || ''}-${s.active}`
|
|
357
|
+
)
|
|
358
|
+
.join('|'),
|
|
359
|
+
]
|
|
360
|
+
);
|
|
353
361
|
|
|
354
362
|
/** Group expansion state */
|
|
355
363
|
const [collapsedGroups, setCollapsedGroups] = useState({});
|
|
@@ -1256,7 +1264,7 @@ const DataGrid = forwardRef(
|
|
|
1256
1264
|
|
|
1257
1265
|
const handleReload = () => {
|
|
1258
1266
|
gridRef.current.paginationProps.reload();
|
|
1259
|
-
|
|
1267
|
+
|
|
1260
1268
|
// Force grid to recalculate row heights after reload
|
|
1261
1269
|
// This fixes the row height rendering issue after filter changes
|
|
1262
1270
|
setTimeout(() => {
|
|
@@ -1368,7 +1376,7 @@ const DataGrid = forwardRef(
|
|
|
1368
1376
|
// Reload grid data if needed
|
|
1369
1377
|
if (gridRef.current && gridRef.current.paginationProps) {
|
|
1370
1378
|
gridRef.current.paginationProps.reload();
|
|
1371
|
-
|
|
1379
|
+
|
|
1372
1380
|
// Force grid to recalculate row heights after reload
|
|
1373
1381
|
setTimeout(() => {
|
|
1374
1382
|
if (gridRef.current?.api) {
|
|
@@ -1512,9 +1520,9 @@ const DataGrid = forwardRef(
|
|
|
1512
1520
|
|
|
1513
1521
|
/**
|
|
1514
1522
|
* DEBUG: Row Click Analysis
|
|
1515
|
-
*
|
|
1523
|
+
*
|
|
1516
1524
|
* When row clicks aren't working, check the console for these debug messages:
|
|
1517
|
-
*
|
|
1525
|
+
*
|
|
1518
1526
|
* 1. "Row onClick triggered" - Initial row click detection
|
|
1519
1527
|
* 2. "Group row check" - Whether it's a group row (should be false for data rows)
|
|
1520
1528
|
* 3. "Cell element in row handler" - Cell element detection
|
|
@@ -1526,157 +1534,182 @@ const DataGrid = forwardRef(
|
|
|
1526
1534
|
* 9. "Update setting found" - Whether update setting exists
|
|
1527
1535
|
* 10. "Opening modal with" / "No update setting found" - Final modal decision
|
|
1528
1536
|
* 11. "modalOpen called" - Modal function execution
|
|
1529
|
-
*
|
|
1537
|
+
*
|
|
1530
1538
|
* Common issues:
|
|
1531
1539
|
* - Missing cell element: Check if click target is within grid
|
|
1532
1540
|
* - Wrong column type: Check column configuration
|
|
1533
1541
|
* - No update setting: Check config.settings for update permission
|
|
1534
1542
|
* - Group row interference: Check if data is being treated as group row
|
|
1535
1543
|
*/
|
|
1536
|
-
const onRowClick = useCallback(
|
|
1537
|
-
|
|
1538
|
-
|
|
1539
|
-
|
|
1540
|
-
|
|
1541
|
-
|
|
1542
|
-
|
|
1543
|
-
|
|
1544
|
-
const cellElement = event.target.closest(
|
|
1545
|
-
'.InovuaReactDataGrid__cell'
|
|
1546
|
-
);
|
|
1547
|
-
|
|
1548
|
-
console.log('🔍 Cell element found:', cellElement);
|
|
1544
|
+
const onRowClick = useCallback(
|
|
1545
|
+
(rowProps, event) => {
|
|
1546
|
+
console.log('🔍 DataGrid onRowClick triggered:', {
|
|
1547
|
+
rowData: rowProps.data,
|
|
1548
|
+
event: event,
|
|
1549
|
+
target: event.target,
|
|
1550
|
+
timestamp: new Date().toISOString(),
|
|
1551
|
+
});
|
|
1549
1552
|
|
|
1550
|
-
|
|
1551
|
-
|
|
1552
|
-
|
|
1553
|
-
return; // Exit early if no cell element was found
|
|
1554
|
-
}
|
|
1553
|
+
const cellElement = event.target.closest(
|
|
1554
|
+
'.InovuaReactDataGrid__cell'
|
|
1555
|
+
);
|
|
1555
1556
|
|
|
1556
|
-
|
|
1557
|
-
cellElement.parentNode.children
|
|
1558
|
-
).indexOf(cellElement);
|
|
1557
|
+
console.log('🔍 Cell element found:', cellElement);
|
|
1559
1558
|
|
|
1560
|
-
|
|
1561
|
-
|
|
1562
|
-
|
|
1563
|
-
|
|
1564
|
-
|
|
1565
|
-
|
|
1559
|
+
// Add null check to prevent errors when cellElement is null
|
|
1560
|
+
if (!cellElement) {
|
|
1561
|
+
console.warn(
|
|
1562
|
+
'⚠️ No cell element found - row click aborted'
|
|
1563
|
+
);
|
|
1564
|
+
return; // Exit early if no cell element was found
|
|
1565
|
+
}
|
|
1566
1566
|
|
|
1567
|
-
|
|
1568
|
-
|
|
1569
|
-
|
|
1570
|
-
|
|
1571
|
-
console.log('🔍
|
|
1572
|
-
|
|
1573
|
-
|
|
1574
|
-
|
|
1575
|
-
|
|
1576
|
-
|
|
1577
|
-
|
|
1578
|
-
|
|
1567
|
+
const columnIndex = Array.from(
|
|
1568
|
+
cellElement.parentNode.children
|
|
1569
|
+
).indexOf(cellElement);
|
|
1570
|
+
|
|
1571
|
+
console.log('🔍 Column analysis:', {
|
|
1572
|
+
columnIndex: columnIndex,
|
|
1573
|
+
totalColumns: rowProps.columns.length,
|
|
1574
|
+
isLastColumn: columnIndex === rowProps.columns.length - 1,
|
|
1575
|
+
columns: rowProps.columns.map((col) => ({
|
|
1576
|
+
id: col.id,
|
|
1577
|
+
type: col.type,
|
|
1578
|
+
})),
|
|
1579
1579
|
});
|
|
1580
1580
|
|
|
1581
1581
|
if (
|
|
1582
|
-
|
|
1583
|
-
|
|
1582
|
+
rowProps.columns.length > 1 &&
|
|
1583
|
+
columnIndex === rowProps.columns.length - 1
|
|
1584
1584
|
) {
|
|
1585
|
-
|
|
1586
|
-
|
|
1587
|
-
|
|
1588
|
-
|
|
1589
|
-
|
|
1590
|
-
|
|
1591
|
-
|
|
1592
|
-
|
|
1593
|
-
|
|
1594
|
-
acc ? acc[part] : undefined,
|
|
1595
|
-
obj
|
|
1596
|
-
);
|
|
1585
|
+
console.log('🔍 Last column clicked - no action');
|
|
1586
|
+
// Handle last column click
|
|
1587
|
+
} else {
|
|
1588
|
+
const column = rowProps.columns[columnIndex];
|
|
1589
|
+
console.log('🔍 Column clicked:', {
|
|
1590
|
+
columnId: column?.id,
|
|
1591
|
+
columnType: column?.type,
|
|
1592
|
+
hasLink: !!column?.link,
|
|
1593
|
+
});
|
|
1597
1594
|
|
|
1598
|
-
|
|
1599
|
-
|
|
1600
|
-
|
|
1601
|
-
|
|
1602
|
-
|
|
1603
|
-
|
|
1604
|
-
|
|
1605
|
-
)
|
|
1595
|
+
if (
|
|
1596
|
+
column.type !== 'dropdown' &&
|
|
1597
|
+
column.type !== 'input_text'
|
|
1598
|
+
) {
|
|
1599
|
+
if (column.id !== '__checkbox-column') {
|
|
1600
|
+
if (
|
|
1601
|
+
column.link &&
|
|
1602
|
+
column.link.hasOwnProperty('url')
|
|
1603
|
+
) {
|
|
1604
|
+
if (column.link.url) {
|
|
1605
|
+
// Helper function to safely retrieve nested values
|
|
1606
|
+
const getNestedValue = (obj, key) =>
|
|
1607
|
+
key
|
|
1608
|
+
.split('.')
|
|
1609
|
+
.reduce(
|
|
1610
|
+
(acc, part) =>
|
|
1611
|
+
acc ? acc[part] : undefined,
|
|
1612
|
+
obj
|
|
1613
|
+
);
|
|
1606
1614
|
|
|
1607
|
-
|
|
1608
|
-
|
|
1609
|
-
|
|
1610
|
-
|
|
1615
|
+
const fileRelationArray =
|
|
1616
|
+
column.id.split('.');
|
|
1617
|
+
const linkUrl = column.link.url;
|
|
1618
|
+
const linkKey =
|
|
1619
|
+
rowProps.columns[columnIndex].link.key;
|
|
1620
|
+
const rowData = getNestedValue(
|
|
1621
|
+
rowProps.data,
|
|
1622
|
+
linkKey
|
|
1623
|
+
);
|
|
1611
1624
|
|
|
1612
|
-
|
|
1613
|
-
|
|
1614
|
-
|
|
1615
|
-
|
|
1616
|
-
|
|
1617
|
-
|
|
1618
|
-
|
|
1619
|
-
|
|
1620
|
-
|
|
1621
|
-
|
|
1622
|
-
)
|
|
1623
|
-
|
|
1624
|
-
|
|
1625
|
+
if (column.link.hasOwnProperty('folder')) {
|
|
1626
|
+
const linkFolder =
|
|
1627
|
+
rowProps.columns[columnIndex].link
|
|
1628
|
+
.folder;
|
|
1629
|
+
|
|
1630
|
+
// Adjusted to use the nested value for checking the file relation
|
|
1631
|
+
if (
|
|
1632
|
+
getNestedValue(
|
|
1633
|
+
rowProps.data,
|
|
1634
|
+
fileRelationArray[0]
|
|
1635
|
+
)
|
|
1636
|
+
) {
|
|
1637
|
+
if (linkFolder !== '') {
|
|
1638
|
+
window.open(
|
|
1639
|
+
`${linkUrl}${rowData}/${linkFolder}`
|
|
1640
|
+
);
|
|
1641
|
+
} else {
|
|
1642
|
+
window.open(
|
|
1643
|
+
`${linkUrl}${rowData}`
|
|
1644
|
+
);
|
|
1645
|
+
}
|
|
1625
1646
|
}
|
|
1647
|
+
} else {
|
|
1648
|
+
navigate(`${linkUrl}${rowData}`);
|
|
1626
1649
|
}
|
|
1627
1650
|
} else {
|
|
1628
|
-
|
|
1629
|
-
|
|
1630
|
-
|
|
1631
|
-
|
|
1632
|
-
|
|
1633
|
-
|
|
1634
|
-
'_blank'
|
|
1635
|
-
);
|
|
1651
|
+
if (rowProps.data[column.id]) {
|
|
1652
|
+
window.open(
|
|
1653
|
+
rowProps.data[column.id],
|
|
1654
|
+
'_blank'
|
|
1655
|
+
);
|
|
1656
|
+
}
|
|
1636
1657
|
}
|
|
1637
|
-
}
|
|
1638
|
-
|
|
1639
|
-
|
|
1640
|
-
|
|
1641
|
-
rowProps.
|
|
1642
|
-
const rowData = rowProps.data[linkKey];
|
|
1643
|
-
|
|
1644
|
-
window.open(
|
|
1645
|
-
`${linkPopup}/${rowData}`,
|
|
1646
|
-
'',
|
|
1647
|
-
'width=1440,height=1024,menubar=1,resizable=1,status=1,titlebar=1,toolbar=1'
|
|
1648
|
-
);
|
|
1649
|
-
} else {
|
|
1650
|
-
console.log('🔍 Checking for update setting:', {
|
|
1651
|
-
settings: settingsRef.current,
|
|
1652
|
-
form: formRef.current,
|
|
1653
|
-
primaryKey: formRef.current?.primaryKey,
|
|
1654
|
-
rowId: rowProps.data[formRef.current?.primaryKey]
|
|
1655
|
-
});
|
|
1658
|
+
} else if (column.link && column.link.popup) {
|
|
1659
|
+
const linkPopup = column.link.popup;
|
|
1660
|
+
const linkKey =
|
|
1661
|
+
rowProps.columns[columnIndex].link.key;
|
|
1662
|
+
const rowData = rowProps.data[linkKey];
|
|
1656
1663
|
|
|
1657
|
-
|
|
1658
|
-
|
|
1659
|
-
|
|
1664
|
+
window.open(
|
|
1665
|
+
`${linkPopup}/${rowData}`,
|
|
1666
|
+
'',
|
|
1667
|
+
'width=1440,height=1024,menubar=1,resizable=1,status=1,titlebar=1,toolbar=1'
|
|
1668
|
+
);
|
|
1669
|
+
} else {
|
|
1670
|
+
console.log('🔍 Checking for update setting:', {
|
|
1671
|
+
settings: settingsRef.current,
|
|
1672
|
+
form: formRef.current,
|
|
1673
|
+
primaryKey: formRef.current?.primaryKey,
|
|
1674
|
+
rowId: rowProps.data[
|
|
1675
|
+
formRef.current?.primaryKey
|
|
1676
|
+
],
|
|
1677
|
+
});
|
|
1660
1678
|
|
|
1661
|
-
|
|
1679
|
+
const updateSetting = settingsRef.current.find(
|
|
1680
|
+
(setting) => setting.id === 'update'
|
|
1681
|
+
);
|
|
1662
1682
|
|
|
1663
|
-
|
|
1664
|
-
|
|
1665
|
-
|
|
1666
|
-
id: rowProps.data[formRef.current.primaryKey]
|
|
1667
|
-
});
|
|
1668
|
-
modalOpen(
|
|
1669
|
-
'update',
|
|
1670
|
-
rowProps.data[formRef.current.primaryKey]
|
|
1683
|
+
console.log(
|
|
1684
|
+
'🔍 Update setting found:',
|
|
1685
|
+
updateSetting
|
|
1671
1686
|
);
|
|
1672
|
-
|
|
1673
|
-
|
|
1687
|
+
|
|
1688
|
+
if (updateSetting) {
|
|
1689
|
+
console.log('✅ Opening modal with:', {
|
|
1690
|
+
type: 'update',
|
|
1691
|
+
id: rowProps.data[
|
|
1692
|
+
formRef.current.primaryKey
|
|
1693
|
+
],
|
|
1694
|
+
});
|
|
1695
|
+
modalOpen(
|
|
1696
|
+
'update',
|
|
1697
|
+
rowProps.data[
|
|
1698
|
+
formRef.current.primaryKey
|
|
1699
|
+
]
|
|
1700
|
+
);
|
|
1701
|
+
} else {
|
|
1702
|
+
console.warn(
|
|
1703
|
+
'⚠️ No update setting found - modal will not open'
|
|
1704
|
+
);
|
|
1705
|
+
}
|
|
1674
1706
|
}
|
|
1675
1707
|
}
|
|
1676
1708
|
}
|
|
1677
1709
|
}
|
|
1678
|
-
}
|
|
1679
|
-
|
|
1710
|
+
},
|
|
1711
|
+
[modalOpen, navigate]
|
|
1712
|
+
);
|
|
1680
1713
|
|
|
1681
1714
|
const onRenderRow = useCallback(
|
|
1682
1715
|
(rowProps) => {
|
|
@@ -1689,7 +1722,7 @@ const DataGrid = forwardRef(
|
|
|
1689
1722
|
rowData: rowProps.data,
|
|
1690
1723
|
event: event,
|
|
1691
1724
|
target: event.target,
|
|
1692
|
-
timestamp: new Date().toISOString()
|
|
1725
|
+
timestamp: new Date().toISOString(),
|
|
1693
1726
|
});
|
|
1694
1727
|
|
|
1695
1728
|
// Check if this is a group row - group rows should only handle expand/collapse, not onRowClick
|
|
@@ -1706,7 +1739,9 @@ const DataGrid = forwardRef(
|
|
|
1706
1739
|
console.log('🔍 Group row check:', isGroupRow);
|
|
1707
1740
|
|
|
1708
1741
|
if (isGroupRow) {
|
|
1709
|
-
console.log(
|
|
1742
|
+
console.log(
|
|
1743
|
+
'🔍 Group row detected - calling original onClick only'
|
|
1744
|
+
);
|
|
1710
1745
|
// For group rows, only allow the original onClick handler (for expand/collapse)
|
|
1711
1746
|
// Do NOT call onRowClick as it should only apply to data rows
|
|
1712
1747
|
if (onClick) {
|
|
@@ -1723,7 +1758,9 @@ const DataGrid = forwardRef(
|
|
|
1723
1758
|
|
|
1724
1759
|
// Add null check to prevent errors when cellElement is null
|
|
1725
1760
|
if (!cellElement) {
|
|
1726
|
-
console.warn(
|
|
1761
|
+
console.warn(
|
|
1762
|
+
'⚠️ No cell element found in row handler - exiting'
|
|
1763
|
+
);
|
|
1727
1764
|
return; // Exit early if no cell element was found
|
|
1728
1765
|
}
|
|
1729
1766
|
|
|
@@ -1736,11 +1773,13 @@ const DataGrid = forwardRef(
|
|
|
1736
1773
|
console.log('🔍 Row handler column analysis:', {
|
|
1737
1774
|
columnIndex: columnIndex,
|
|
1738
1775
|
columnId: column?.id,
|
|
1739
|
-
isCheckboxColumn: column?.id === '__checkbox-column'
|
|
1776
|
+
isCheckboxColumn: column?.id === '__checkbox-column',
|
|
1740
1777
|
});
|
|
1741
1778
|
|
|
1742
1779
|
if (column.id === '__checkbox-column') {
|
|
1743
|
-
console.log(
|
|
1780
|
+
console.log(
|
|
1781
|
+
'🔍 Checkbox column clicked - handling checkbox logic'
|
|
1782
|
+
);
|
|
1744
1783
|
// For checkbox column clicks, we need to handle them specially
|
|
1745
1784
|
// to ensure consistent behavior whether clicking checkbox or cell area
|
|
1746
1785
|
|
|
@@ -1786,12 +1825,17 @@ const DataGrid = forwardRef(
|
|
|
1786
1825
|
onClick(event);
|
|
1787
1826
|
}
|
|
1788
1827
|
} else {
|
|
1789
|
-
console.log(
|
|
1828
|
+
console.log(
|
|
1829
|
+
'🔍 Non-checkbox column - calling onRowClick'
|
|
1830
|
+
);
|
|
1790
1831
|
// For non-checkbox columns, handle normal row clicks
|
|
1791
1832
|
// But do NOT trigger checkbox selection
|
|
1792
1833
|
onRowClick(rowProps, event);
|
|
1793
1834
|
|
|
1794
|
-
console.log(
|
|
1835
|
+
console.log(
|
|
1836
|
+
'🔍 Calling original onClick handler:',
|
|
1837
|
+
!!onClick
|
|
1838
|
+
);
|
|
1795
1839
|
// Call the original onClick handler
|
|
1796
1840
|
if (onClick) {
|
|
1797
1841
|
onClick(event);
|
|
@@ -2073,14 +2117,6 @@ const DataGrid = forwardRef(
|
|
|
2073
2117
|
}, [search, setDSearch]);
|
|
2074
2118
|
|
|
2075
2119
|
const renderSetting = (s, d) => {
|
|
2076
|
-
console.log('🔍 renderSetting called for:', {
|
|
2077
|
-
settingId: s.id,
|
|
2078
|
-
settingRoles: s.roles,
|
|
2079
|
-
userRoles: userProfile?.roles?.map(r => r.name),
|
|
2080
|
-
settingActive: s.active,
|
|
2081
|
-
rowData: d?.id || 'unknown'
|
|
2082
|
-
});
|
|
2083
|
-
|
|
2084
2120
|
let iconStyle = {};
|
|
2085
2121
|
let allow = true;
|
|
2086
2122
|
|
|
@@ -2094,11 +2130,6 @@ const DataGrid = forwardRef(
|
|
|
2094
2130
|
);
|
|
2095
2131
|
|
|
2096
2132
|
if (!hasRequiredRole) {
|
|
2097
|
-
console.log('🔍 Setting filtered out by role permissions:', {
|
|
2098
|
-
settingId: s.id,
|
|
2099
|
-
requiredRoles: s.roles,
|
|
2100
|
-
userRoles: userProfile?.roles?.map(r => r.name)
|
|
2101
|
-
});
|
|
2102
2133
|
allow = false;
|
|
2103
2134
|
}
|
|
2104
2135
|
}
|
|
@@ -2375,21 +2406,10 @@ const DataGrid = forwardRef(
|
|
|
2375
2406
|
}
|
|
2376
2407
|
|
|
2377
2408
|
if (!tmpCheckValue) {
|
|
2378
|
-
console.log('🔍 Setting filtered out by active condition:', {
|
|
2379
|
-
settingId: s.id,
|
|
2380
|
-
activeCondition: s.active,
|
|
2381
|
-
rowData: d?.id || 'unknown'
|
|
2382
|
-
});
|
|
2383
2409
|
allow = false;
|
|
2384
2410
|
}
|
|
2385
2411
|
}
|
|
2386
2412
|
|
|
2387
|
-
console.log('🔍 renderSetting final decision:', {
|
|
2388
|
-
settingId: s.id,
|
|
2389
|
-
allowed: allow,
|
|
2390
|
-
willRender: allow ? 'YES' : 'NO'
|
|
2391
|
-
});
|
|
2392
|
-
|
|
2393
2413
|
if (allow) {
|
|
2394
2414
|
switch (s.id) {
|
|
2395
2415
|
case 'activate':
|
|
@@ -2440,7 +2460,7 @@ const DataGrid = forwardRef(
|
|
|
2440
2460
|
} else {
|
|
2441
2461
|
console.log('🔍 Setting NOT rendered (allow=false):', {
|
|
2442
2462
|
settingId: s.id,
|
|
2443
|
-
reason: 'filtered out by permissions or active conditions'
|
|
2463
|
+
reason: 'filtered out by permissions or active conditions',
|
|
2444
2464
|
});
|
|
2445
2465
|
return null;
|
|
2446
2466
|
}
|
|
@@ -3034,13 +3054,21 @@ const DataGrid = forwardRef(
|
|
|
3034
3054
|
// Function to check if any settings would be visible for any row
|
|
3035
3055
|
const hasVisibleSettings = () => {
|
|
3036
3056
|
if (memoizedSettings.length === 0) return false;
|
|
3037
|
-
|
|
3057
|
+
|
|
3038
3058
|
// Check if any setting would be visible based on role permissions
|
|
3039
|
-
return memoizedSettings.some(setting => {
|
|
3059
|
+
return memoizedSettings.some((setting) => {
|
|
3040
3060
|
// Check role-based permissions
|
|
3041
|
-
if (
|
|
3042
|
-
|
|
3043
|
-
|
|
3061
|
+
if (
|
|
3062
|
+
setting.roles &&
|
|
3063
|
+
Array.isArray(setting.roles) &&
|
|
3064
|
+
setting.roles.length > 0
|
|
3065
|
+
) {
|
|
3066
|
+
const hasRequiredRole = setting.roles.some(
|
|
3067
|
+
(requiredRole) =>
|
|
3068
|
+
userProfile?.roles?.some(
|
|
3069
|
+
(userRole) =>
|
|
3070
|
+
userRole.name === requiredRole
|
|
3071
|
+
)
|
|
3044
3072
|
);
|
|
3045
3073
|
return hasRequiredRole;
|
|
3046
3074
|
}
|
|
@@ -3305,7 +3333,7 @@ const DataGrid = forwardRef(
|
|
|
3305
3333
|
// Force reload of data
|
|
3306
3334
|
if (gridRef.current && gridRef.current.paginationProps) {
|
|
3307
3335
|
gridRef.current.paginationProps.reload();
|
|
3308
|
-
|
|
3336
|
+
|
|
3309
3337
|
// Force grid to recalculate row heights after reload
|
|
3310
3338
|
setTimeout(() => {
|
|
3311
3339
|
if (gridRef.current?.api) {
|
|
@@ -3443,37 +3471,69 @@ const DataGrid = forwardRef(
|
|
|
3443
3471
|
'';
|
|
3444
3472
|
|
|
3445
3473
|
// Check for important marker
|
|
3446
|
-
const checkGroupImportantMarker = (
|
|
3447
|
-
|
|
3474
|
+
const checkGroupImportantMarker = (
|
|
3475
|
+
groupValue,
|
|
3476
|
+
importantMarkerConfig
|
|
3477
|
+
) => {
|
|
3478
|
+
if (
|
|
3479
|
+
!importantMarkerConfig ||
|
|
3480
|
+
!dataRef.current?.length ||
|
|
3481
|
+
!ajaxSetting?.groupBy
|
|
3482
|
+
) {
|
|
3448
3483
|
return false;
|
|
3449
3484
|
}
|
|
3450
|
-
|
|
3451
|
-
const {
|
|
3452
|
-
|
|
3453
|
-
|
|
3485
|
+
|
|
3486
|
+
const {
|
|
3487
|
+
id: fieldId,
|
|
3488
|
+
value: expectedValue,
|
|
3489
|
+
} = importantMarkerConfig;
|
|
3490
|
+
const groupField =
|
|
3491
|
+
ajaxSetting.groupBy[0];
|
|
3492
|
+
|
|
3454
3493
|
// Get all rows that belong to this group
|
|
3455
|
-
const groupRows =
|
|
3456
|
-
(
|
|
3457
|
-
|
|
3458
|
-
|
|
3459
|
-
|
|
3460
|
-
|
|
3461
|
-
|
|
3494
|
+
const groupRows =
|
|
3495
|
+
dataRef.current.filter(
|
|
3496
|
+
(row) =>
|
|
3497
|
+
row[groupField] ===
|
|
3498
|
+
groupValue
|
|
3499
|
+
);
|
|
3500
|
+
|
|
3501
|
+
return groupRows.some((row) => {
|
|
3502
|
+
const fieldValue =
|
|
3503
|
+
row[fieldId];
|
|
3504
|
+
|
|
3462
3505
|
// Handle different value types
|
|
3463
|
-
if (
|
|
3464
|
-
|
|
3506
|
+
if (
|
|
3507
|
+
typeof expectedValue ===
|
|
3508
|
+
'boolean'
|
|
3509
|
+
) {
|
|
3510
|
+
return (
|
|
3511
|
+
Boolean(
|
|
3512
|
+
fieldValue
|
|
3513
|
+
) === expectedValue
|
|
3514
|
+
);
|
|
3465
3515
|
}
|
|
3466
|
-
|
|
3467
|
-
return
|
|
3516
|
+
|
|
3517
|
+
return (
|
|
3518
|
+
fieldValue ===
|
|
3519
|
+
expectedValue
|
|
3520
|
+
);
|
|
3468
3521
|
});
|
|
3469
3522
|
};
|
|
3470
3523
|
|
|
3471
|
-
const hasImportantMarker =
|
|
3472
|
-
|
|
3473
|
-
|
|
3474
|
-
|
|
3475
|
-
|
|
3476
|
-
|
|
3524
|
+
const hasImportantMarker =
|
|
3525
|
+
checkGroupImportantMarker(
|
|
3526
|
+
groupValue,
|
|
3527
|
+
ajaxSetting?.groupBySetting
|
|
3528
|
+
?.importantMarker
|
|
3529
|
+
);
|
|
3530
|
+
const importantMarkerColor =
|
|
3531
|
+
ajaxSetting?.groupBySetting
|
|
3532
|
+
?.importantMarker?.colour;
|
|
3533
|
+
const importantMarkerTooltip =
|
|
3534
|
+
ajaxSetting?.groupBySetting
|
|
3535
|
+
?.importantMarker?.tooltip ||
|
|
3536
|
+
'This group contains items that require attention';
|
|
3477
3537
|
|
|
3478
3538
|
// Use ReactDataGrid's built-in toggle functionality
|
|
3479
3539
|
const collapsed =
|
|
@@ -3554,11 +3614,29 @@ const DataGrid = forwardRef(
|
|
|
3554
3614
|
|
|
3555
3615
|
return (
|
|
3556
3616
|
<div
|
|
3557
|
-
className={`group-header-clean group-header-fixed-height ${
|
|
3558
|
-
|
|
3559
|
-
|
|
3560
|
-
|
|
3561
|
-
|
|
3617
|
+
className={`group-header-clean group-header-fixed-height ${
|
|
3618
|
+
styles.groupHeaderContainer
|
|
3619
|
+
} ${
|
|
3620
|
+
hasImportantMarker
|
|
3621
|
+
? styles.groupHeaderImportant
|
|
3622
|
+
: ''
|
|
3623
|
+
}`}
|
|
3624
|
+
style={
|
|
3625
|
+
hasImportantMarker
|
|
3626
|
+
? {
|
|
3627
|
+
borderLeftColor:
|
|
3628
|
+
importantMarkerColor ||
|
|
3629
|
+
'#FF6961',
|
|
3630
|
+
background: `linear-gradient(135deg, ${
|
|
3631
|
+
importantMarkerColor ||
|
|
3632
|
+
'#FF6961'
|
|
3633
|
+
}15 0%, ${
|
|
3634
|
+
importantMarkerColor ||
|
|
3635
|
+
'#FF6961'
|
|
3636
|
+
}08 100%)`,
|
|
3637
|
+
}
|
|
3638
|
+
: {}
|
|
3639
|
+
}
|
|
3562
3640
|
onClick={
|
|
3563
3641
|
handleGroupHeaderClick
|
|
3564
3642
|
}
|
|
@@ -3736,16 +3814,25 @@ const DataGrid = forwardRef(
|
|
|
3736
3814
|
<AlertCircle
|
|
3737
3815
|
className="important-marker"
|
|
3738
3816
|
style={{
|
|
3739
|
-
display:
|
|
3740
|
-
|
|
3741
|
-
|
|
3742
|
-
|
|
3743
|
-
|
|
3817
|
+
display:
|
|
3818
|
+
'inline-block',
|
|
3819
|
+
marginLeft:
|
|
3820
|
+
'8px',
|
|
3821
|
+
color:
|
|
3822
|
+
importantMarkerColor ||
|
|
3823
|
+
'#FF6961',
|
|
3824
|
+
position:
|
|
3825
|
+
'relative',
|
|
3826
|
+
top: '1px',
|
|
3744
3827
|
}}
|
|
3745
3828
|
size={16}
|
|
3746
|
-
title={
|
|
3829
|
+
title={
|
|
3830
|
+
importantMarkerTooltip
|
|
3831
|
+
}
|
|
3747
3832
|
data-tooltip-id="system-tooltip"
|
|
3748
|
-
data-tooltip-content={
|
|
3833
|
+
data-tooltip-content={
|
|
3834
|
+
importantMarkerTooltip
|
|
3835
|
+
}
|
|
3749
3836
|
/>
|
|
3750
3837
|
)}
|
|
3751
3838
|
</strong>
|
package/src/components/Form.jsx
CHANGED
|
@@ -322,15 +322,19 @@ function Form({
|
|
|
322
322
|
const handleSelectOption = () => {
|
|
323
323
|
updateFormData({ [id]: inputValue });
|
|
324
324
|
|
|
325
|
-
//
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
325
|
+
// Batch update version
|
|
326
|
+
const excludedKeys = new Set(['id', 'label', 'description']);
|
|
327
|
+
const updates = {};
|
|
328
|
+
|
|
329
|
+
for (const key in inputValue) {
|
|
330
|
+
if (key in formData && !excludedKeys.has(key)) {
|
|
331
|
+
updates[key] = inputValue[key];
|
|
332
|
+
}
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
if (Object.keys(updates).length > 0) {
|
|
336
|
+
updateFormData(updates);
|
|
337
|
+
}
|
|
334
338
|
|
|
335
339
|
formSettings.fields.forEach((field) => {
|
|
336
340
|
if (field.id === id && field.trigger) {
|