@iotready/nextjs-components-library 1.0.0-preview25 → 1.0.0-preview26
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.
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { Theme } from "@emotion/react";
|
|
2
2
|
import { UserType, AssetType, DevicePositionType, TrackleDeviceType } from "../../types";
|
|
3
|
-
declare const GroupsDevices: ({ userInfo, handleGetUsersList, handleAddUserToGroup, handleRemoveUserFromGroup, handleGetGroups, handleGetUsersGroup, handleGetDevices, handleUpdateDevice, handleGetPositions, handleAddDevicesToGroup, handleRemoveDevicesFromGroup, handleCreateGroup, handleDeleteGroup, handleUpdateGroup, group, columnsArray, containerDataGrid, props, propsDatagrid, loadingComponent, containerProps, enableMaps, mapsHeight, mapsClickCallback, theme, confirmMui, propsHeaderGroups, forceGetDevices, groupsLabelAll }: {
|
|
3
|
+
declare const GroupsDevices: ({ userInfo, handleGetUsersList, handleAddUserToGroup, handleRemoveUserFromGroup, handleGetGroups, handleGetUsersGroup, handleGetDevices, handleUpdateDevice, handleGetPositions, handleAddDevicesToGroup, handleRemoveDevicesFromGroup, handleCreateGroup, handleDeleteGroup, handleUpdateGroup, group, columnsArray, containerDataGrid, props, propsDatagrid, loadingComponent, containerProps, enableMaps, mapsHeight, mapsClickCallback, theme, confirmMui, propsHeaderGroups, forceGetDevices, customToolbar, groupsLabelAll }: {
|
|
4
4
|
userInfo: UserType;
|
|
5
5
|
handleGetUsersList: ({ page, pageSize }: {
|
|
6
6
|
page: number;
|
|
@@ -33,7 +33,8 @@ declare const GroupsDevices: ({ userInfo, handleGetUsersList, handleAddUserToGro
|
|
|
33
33
|
mapsClickCallback?: (position: DevicePositionType) => void;
|
|
34
34
|
theme: Theme;
|
|
35
35
|
confirmMui?: (options?: any) => Promise<void>;
|
|
36
|
-
forceGetDevices
|
|
36
|
+
forceGetDevices?: number;
|
|
37
|
+
customToolbar?: string[];
|
|
37
38
|
groupsLabelAll?: string;
|
|
38
39
|
}) => string | number | bigint | boolean | import("react/jsx-runtime").JSX.Element | Iterable<import("react").ReactNode> | Promise<import("react").AwaitedReactNode> | null;
|
|
39
40
|
export default GroupsDevices;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
3
3
|
import { Box, CircularProgress, Autocomplete, TextField, Input, IconButton, Button, Card, CardContent, CardHeader, Modal, Typography, Stack, Tab } from "@mui/material";
|
|
4
|
-
import { cloneElement, isValidElement, useEffect, useMemo, useState } from "react";
|
|
4
|
+
import { cloneElement, isValidElement, useEffect, useMemo, useRef, useState } from "react";
|
|
5
5
|
import AddIcon from '@mui/icons-material/Add';
|
|
6
6
|
import PlaylistAddIcon from '@mui/icons-material/PlaylistAdd';
|
|
7
7
|
import EditIcon from '@mui/icons-material/Edit';
|
|
@@ -10,12 +10,12 @@ import ReadMoreIcon from '@mui/icons-material/ReadMore';
|
|
|
10
10
|
import PlaylistRemoveIcon from '@mui/icons-material/PlaylistRemove';
|
|
11
11
|
import CloseIcon from '@mui/icons-material/Close';
|
|
12
12
|
import { LoadingButton, TabContext, TabList, TabPanel } from "@mui/lab";
|
|
13
|
-
import { DataGrid, GridToolbar } from "@mui/x-data-grid";
|
|
13
|
+
import { DataGrid, GridToolbar, GridToolbarExport, GridToolbarQuickFilter } from "@mui/x-data-grid";
|
|
14
14
|
import GroupUpdate from "./GroupUpdate";
|
|
15
15
|
import BackIcon from '@mui/icons-material/ArrowBack';
|
|
16
16
|
import dynamic from "next/dynamic";
|
|
17
17
|
import { ThemeProvider } from '@mui/material/styles';
|
|
18
|
-
const GroupsDevices = ({ userInfo, handleGetUsersList, handleAddUserToGroup, handleRemoveUserFromGroup, handleGetGroups, handleGetUsersGroup, handleGetDevices, handleUpdateDevice, handleGetPositions, handleAddDevicesToGroup, handleRemoveDevicesFromGroup, handleCreateGroup, handleDeleteGroup, handleUpdateGroup, group = 'all', columnsArray = [], containerDataGrid = 'Card', props = {}, propsDatagrid = {}, loadingComponent = _jsx(CircularProgress, {}), containerProps = {}, enableMaps = true, mapsHeight = '400px', mapsClickCallback = () => { }, theme, confirmMui, propsHeaderGroups, forceGetDevices, groupsLabelAll }) => {
|
|
18
|
+
const GroupsDevices = ({ userInfo, handleGetUsersList, handleAddUserToGroup, handleRemoveUserFromGroup, handleGetGroups, handleGetUsersGroup, handleGetDevices, handleUpdateDevice, handleGetPositions, handleAddDevicesToGroup, handleRemoveDevicesFromGroup, handleCreateGroup, handleDeleteGroup, handleUpdateGroup, group = 'all', columnsArray = [], containerDataGrid = 'Card', props = {}, propsDatagrid = {}, loadingComponent = _jsx(CircularProgress, {}), containerProps = {}, enableMaps = true, mapsHeight = '400px', mapsClickCallback = () => { }, theme, confirmMui, propsHeaderGroups, forceGetDevices, customToolbar, groupsLabelAll }) => {
|
|
19
19
|
const [devices, setDevices] = useState([]);
|
|
20
20
|
const [positions, setPositions] = useState([]);
|
|
21
21
|
const [loadingDevices, setLoadingDevices] = useState(false);
|
|
@@ -24,6 +24,7 @@ const GroupsDevices = ({ userInfo, handleGetUsersList, handleAddUserToGroup, han
|
|
|
24
24
|
const [editGroup, setEditGroup] = useState(false);
|
|
25
25
|
const [checkboxSelection, setCheckboxSelection] = useState(false);
|
|
26
26
|
const [devicesToAdd, setDevicesToAdd] = useState([]);
|
|
27
|
+
const [deviceSelectedObjs, setDeviceSelectedObjs] = useState([]);
|
|
27
28
|
const [currentGroup, setCurrentGroup] = useState(group);
|
|
28
29
|
const [selectedGroup, setSelectedGroup] = useState(group);
|
|
29
30
|
const [groups, setGroups] = useState(null);
|
|
@@ -35,6 +36,7 @@ const GroupsDevices = ({ userInfo, handleGetUsersList, handleAddUserToGroup, han
|
|
|
35
36
|
const [description, setDescription] = useState('');
|
|
36
37
|
const [groupUpdateVisible, setGroupUpdateVisible] = useState(false);
|
|
37
38
|
const [valueTab, setValueTab] = useState('1');
|
|
39
|
+
const clickedIdRef = useRef(null);
|
|
38
40
|
const handleChangeTab = (event, newValue) => {
|
|
39
41
|
setValueTab(newValue);
|
|
40
42
|
};
|
|
@@ -178,8 +180,7 @@ const GroupsDevices = ({ userInfo, handleGetUsersList, handleAddUserToGroup, han
|
|
|
178
180
|
const addToSelectedGroup = async () => {
|
|
179
181
|
setLoadingGroups(true);
|
|
180
182
|
try {
|
|
181
|
-
|
|
182
|
-
await handleAddDevicesToGroup(userInfo, selectedGroup, devicesToPatch);
|
|
183
|
+
await handleAddDevicesToGroup(userInfo, selectedGroup, deviceSelectedObjs);
|
|
183
184
|
setLoadingGroups(false);
|
|
184
185
|
setCurrentGroup(selectedGroup);
|
|
185
186
|
setDevicesToAdd([...[]]);
|
|
@@ -195,8 +196,7 @@ const GroupsDevices = ({ userInfo, handleGetUsersList, handleAddUserToGroup, han
|
|
|
195
196
|
const removeFromCurrentGroup = async () => {
|
|
196
197
|
setLoadingGroups(true);
|
|
197
198
|
try {
|
|
198
|
-
|
|
199
|
-
await handleRemoveDevicesFromGroup(userInfo, selectedGroup, devicesToRemove);
|
|
199
|
+
await handleRemoveDevicesFromGroup(userInfo, selectedGroup, deviceSelectedObjs);
|
|
200
200
|
setLoadingGroups(false);
|
|
201
201
|
setDevicesToAdd([]);
|
|
202
202
|
fetchDevices(currentGroup, selectedGroup);
|
|
@@ -216,14 +216,62 @@ const GroupsDevices = ({ userInfo, handleGetUsersList, handleAddUserToGroup, han
|
|
|
216
216
|
setCheckboxSelection(!checkboxSelection);
|
|
217
217
|
};
|
|
218
218
|
const renderMaps = (_jsx(Map, { positions: positions, mapsClickCallback: mapsClickCallback, height: mapsHeight }));
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
219
|
+
useEffect(() => {
|
|
220
|
+
if (devicesToAdd.length <= 0) {
|
|
221
|
+
setDeviceSelectedObjs([]);
|
|
222
|
+
}
|
|
223
|
+
}, [devicesToAdd]);
|
|
224
|
+
const CustomToolbar = () => (_jsxs("div", { style: { display: 'flex', padding: '8px', justifyContent: 'space-between', paddingTop: '2px' }, children: [_jsxs("div", { style: { display: 'flex', gap: 8, marginRight: '20px' }, children: [customToolbar && customToolbar.includes('filters') ?
|
|
225
|
+
_jsx(GridToolbarExport, { sx: { mr: 2 } })
|
|
226
|
+
: '', customToolbar && customToolbar.includes('export') ?
|
|
227
|
+
_jsx(GridToolbarExport, {})
|
|
228
|
+
: ''] }), customToolbar && customToolbar.includes('quickfilter') && _jsx(GridToolbarQuickFilter, {})] }));
|
|
229
|
+
const renderDataGrid = (_jsx("div", { style: { display: 'flex', flexDirection: 'column', minHeight: 323 }, children: _jsx(DataGrid, { checkboxSelection: checkboxSelection,
|
|
230
|
+
// Se siamo in modalità aggiunta, includi gli ID già nel gruppo
|
|
231
|
+
rowSelectionModel: (checkboxSelection && currentGroup === 'all')
|
|
232
|
+
? [
|
|
233
|
+
...devices
|
|
234
|
+
.filter(d => d.groups?.includes(selectedGroup))
|
|
235
|
+
.map(d => d.id.toString()),
|
|
236
|
+
...devicesToAdd,
|
|
237
|
+
]
|
|
238
|
+
: devicesToAdd,
|
|
239
|
+
// Se siamo in modalità aggiunta, disabilita la selezione per i già nel gruppo
|
|
240
|
+
isRowSelectable: params => {
|
|
241
|
+
return (checkboxSelection && currentGroup === 'all')
|
|
242
|
+
? !params.row.groups?.includes(selectedGroup)
|
|
243
|
+
: true;
|
|
244
|
+
}, onCellClick: (params) => {
|
|
245
|
+
clickedIdRef.current = params.id.toString(); // aggiornamento immediato
|
|
246
|
+
}, onRowSelectionModelChange: (ids) => {
|
|
247
|
+
if (!checkboxSelection || !clickedIdRef.current)
|
|
248
|
+
return;
|
|
249
|
+
const clickedId = clickedIdRef.current;
|
|
250
|
+
clickedIdRef.current = null; // resetta subito dopo l’uso
|
|
251
|
+
setDevicesToAdd(prevIds => {
|
|
252
|
+
const updated = prevIds.includes(clickedId)
|
|
253
|
+
? prevIds.filter(id => id !== clickedId)
|
|
254
|
+
: [...prevIds, clickedId];
|
|
255
|
+
return updated;
|
|
256
|
+
});
|
|
257
|
+
setDeviceSelectedObjs(prevObjs => {
|
|
258
|
+
const isDeselecting = prevObjs.some(d => d.id.toString() === clickedId);
|
|
259
|
+
if (isDeselecting) {
|
|
260
|
+
return prevObjs.filter(d => d.id.toString() !== clickedId);
|
|
261
|
+
}
|
|
262
|
+
else {
|
|
263
|
+
const device = devices.find(d => d.id.toString() === clickedId);
|
|
264
|
+
return device ? [...prevObjs, device] : prevObjs;
|
|
265
|
+
}
|
|
266
|
+
});
|
|
267
|
+
}, disableDensitySelector: true, disableColumnSelector: true, disableRowSelectionOnClick: true, loading: loadingDevices, rows: devices, columns: checkboxSelection
|
|
268
|
+
? columnsArray.filter(col => col.field !== 'id')
|
|
269
|
+
: columnsArray, slots: {
|
|
270
|
+
noRowsOverlay: () => (_jsx(Stack, { height: "100%", alignItems: "center", justifyContent: "center", children: currentGroup !== 'all'
|
|
271
|
+
? (_jsxs(_Fragment, { children: [_jsx(Box, { children: "No devices in group" }), editGroup && (_jsxs(Button, { onClick: addDevicesToCurrentGroup, variant: "outlined", color: "primary", size: "small", sx: { mt: 2 }, children: [_jsx(PlaylistAddIcon, { fontSize: "small", sx: { mr: 1 } }), "Add devices"] }))] }))
|
|
272
|
+
: "No devices" })),
|
|
225
273
|
noResultsOverlay: () => (_jsx(Stack, { height: "100%", alignItems: "center", justifyContent: "center", children: "Filter returns no result" })),
|
|
226
|
-
toolbar: GridToolbar,
|
|
274
|
+
toolbar: customToolbar && customToolbar.length ? CustomToolbar : GridToolbar,
|
|
227
275
|
}, slotProps: {
|
|
228
276
|
toolbar: {
|
|
229
277
|
showQuickFilter: true,
|
|
@@ -234,7 +282,7 @@ const GroupsDevices = ({ userInfo, handleGetUsersList, handleAddUserToGroup, han
|
|
|
234
282
|
sorting: {
|
|
235
283
|
sortModel: [{ field: 'online', sort: 'desc' }],
|
|
236
284
|
},
|
|
237
|
-
pagination: { paginationModel: { pageSize: 100 } }
|
|
285
|
+
pagination: { paginationModel: { pageSize: 100 } },
|
|
238
286
|
}, ...propsDatagrid }) }));
|
|
239
287
|
const renderTabContext = (_jsxs(TabContext, { value: valueTab, children: [_jsx(Box, { sx: { borderBottom: 1, borderColor: 'divider' }, children: _jsxs(TabList, { onChange: handleChangeTab, sx: { minHeight: 20 }, children: [_jsx(Tab, { label: "List", value: "1", sx: { minHeight: 20 } }), _jsx(Tab, { label: "Map", value: "2", sx: { minHeight: 20 } })] }) }), _jsx(TabPanel, { value: "1", sx: { p: 0 }, children: renderDataGrid }), _jsx(TabPanel, { value: "2", sx: { p: 0 }, children: renderMaps })] }));
|
|
240
288
|
const renderDatagridAndMaps = (enableMaps ?
|
|
@@ -4,6 +4,7 @@ import { createElement, useState } from "react";
|
|
|
4
4
|
import { Box, Card, CardContent, List, ListItemButton, ListItemText, styled, ThemeProvider } from "@mui/material";
|
|
5
5
|
import Grid from "@mui/material/Grid2";
|
|
6
6
|
import NavigateNextIcon from "@mui/icons-material/NavigateNext";
|
|
7
|
+
import React from "react";
|
|
7
8
|
const ListItemButtonSettings = styled(ListItemButton)(({ theme, selected }) => ({
|
|
8
9
|
backgroundColor: theme.palette.primary.main,
|
|
9
10
|
color: theme.palette.primary.contrastText,
|
|
@@ -37,6 +38,6 @@ const DynamicMenu = ({ menuItems, selectedIndex = null, theme }) => {
|
|
|
37
38
|
const handleMenuClick = (index) => {
|
|
38
39
|
setSelected(index); // Assicurati di non chiamarlo nel rendering
|
|
39
40
|
};
|
|
40
|
-
return (_jsx(ThemeProvider, { theme: theme, children: _jsx(Grid, { container: true, spacing: 2, sx: { width: '100%' }, children: _jsx(Grid, { size: { xs: 12, lg: 9 }, children: _jsx(Card, { sx: { borderRadius: 2 }, children: _jsx(CardContent, { sx: { p: 0, "&:last-child": { p: 0 } }, children: _jsxs(Grid, { container: true, spacing: 2, children: [_jsx(Grid, { size: { xs: 12, sm: 4 }, sx: { display: { xs: selected !== null ? 'none' : 'block', sm: 'block' } }, children: _jsx(List, { sx: { p: 0, height: "100%", backgroundColor: "primary.main" }, children: menuItems.map((item, index) => (_jsxs(ListItemButtonSettings, { selected: selected === index, onClick: () => handleMenuClick(index), children: [item.icon && _jsx(Box, { sx: { mr: 2 }, children: item.icon }), _jsx(ListItemText, { primary: _jsx("b", { children: item.name }), secondary: item.description }), _jsx(NavigateNextIcon, { sx: { display: { xs: "block", sm: "none" } } })] }, index))) }) }), _jsx(Grid, { size: { xs: 12, sm: 8, md: 6 }, sx: { display: { xs: selected === null ? 'none' : 'block', sm: 'block' } }, children: _jsx(Box, { component: "div", sx: { p: { xs: 2 }, py: { sm: 3 } }, children: selected !== null ? createElement(menuItems[selected].page, { handleBack: () => { setSelected(null); } }) : "" }) })] }) }) }) }) }) }));
|
|
41
|
+
return (_jsx(ThemeProvider, { theme: theme, children: _jsx(Grid, { container: true, spacing: 2, sx: { width: '100%' }, children: _jsx(Grid, { size: { xs: 12, lg: 9 }, children: _jsx(Card, { sx: { borderRadius: 2 }, children: _jsx(CardContent, { sx: { p: 0, "&:last-child": { p: 0 } }, children: _jsxs(Grid, { container: true, spacing: 2, children: [_jsx(Grid, { size: { xs: 12, sm: 4 }, sx: { display: { xs: selected !== null ? 'none' : 'block', sm: 'block' } }, children: _jsx(List, { sx: { p: 0, height: "100%", backgroundColor: "primary.main" }, children: menuItems.map((item, index) => (_jsxs(ListItemButtonSettings, { selected: selected === index, onClick: () => handleMenuClick(index), children: [item.icon && _jsx(Box, { sx: { mr: 2 }, children: React.isValidElement(item.icon) ? item.icon : null }), _jsx(ListItemText, { primary: _jsx("b", { children: item.name }), secondary: item.description }), _jsx(NavigateNextIcon, { sx: { display: { xs: "block", sm: "none" } } })] }, index))) }) }), _jsx(Grid, { size: { xs: 12, sm: 8, md: 6 }, sx: { display: { xs: selected === null ? 'none' : 'block', sm: 'block' } }, children: _jsx(Box, { component: "div", sx: { p: { xs: 2 }, py: { sm: 3 } }, children: selected !== null ? createElement(menuItems[selected].page, { handleBack: () => { setSelected(null); } }) : "" }) })] }) }) }) }) }) }));
|
|
41
42
|
};
|
|
42
43
|
export default DynamicMenu;
|
package/package.json
CHANGED