drf-react-by-schema
Version:
Components and Tools for building a React App having Django Rest Framework (DRF) as server
760 lines (759 loc) • 41.6 kB
JavaScript
;
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || (function () {
var ownKeys = function(o) {
ownKeys = Object.getOwnPropertyNames || function (o) {
var ar = [];
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
return ar;
};
return ownKeys(o);
};
return function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
__setModuleDefault(result, mod);
return result;
};
})();
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
const react_1 = __importStar(require("react"));
const dayjs_1 = __importDefault(require("dayjs"));
const x_data_grid_1 = require("@mui/x-data-grid");
const Box_1 = __importDefault(require("@mui/material/Box"));
const CircularProgress_1 = __importDefault(require("@mui/material/CircularProgress"));
const Edit_1 = __importDefault(require("@mui/icons-material/Edit"));
const Bolt_1 = __importDefault(require("@mui/icons-material/Bolt"));
const Visibility_1 = __importDefault(require("@mui/icons-material/Visibility"));
const Clear_1 = __importDefault(require("@mui/icons-material/Clear"));
const Check_1 = __importDefault(require("@mui/icons-material/Check"));
const Undo_1 = __importDefault(require("@mui/icons-material/Undo"));
const string_mask_1 = __importDefault(require("string-mask"));
const styles_1 = require("../../styles");
const api_1 = require("../../api");
const utils_1 = require("../../utils");
const DRFReactBySchemaContext_1 = require("../../context/DRFReactBySchemaContext");
const utils_2 = require("./utils");
const CustomToolbar_1 = require("./CustomToolbar");
const SelectEditInputCell_1 = require("./SelectEditInputCell");
const GridDateInput_1 = require("./GridDateInput");
const GridDecimalInput_1 = require("./GridDecimalInput");
const GridPatternInput_1 = require("./GridPatternInput");
const BooleanInputCell_1 = require("./BooleanInputCell");
const FooterToolbar_1 = require("./FooterToolbar");
const APIWrapperContext_1 = require("../../context/APIWrapperContext");
const DataGridDesktop = (0, react_1.forwardRef)(({ schema, dataGrid, setDataGrid, rowCount = 0, columns, model, name = Math.floor(Math.random() * 1000000).toString(), indexField = 'nome', addExistingModel, indexFieldMinWidth = 350, indexFieldBasePath = '', indexFieldViewBasePath, stateToLink = {}, minWidth = 80, loading, modelParent, modelParentId, customColumnOperations, customFieldFormLayouts, customLinkDestination, LinkComponent, onProcessRow, onDataChange, onEditModel, isEditable = false, hasBulkSelect = false, onSelectActions, isAutoHeight = false, hideFooterPagination = false, setVisibleRows, paginationModel = undefined, setPaginationModel = undefined, hideFooterComponent, hideToolbarComponent, tableAutoHeight, actions = ['editInline', 'remove'], customActions, hideColumnsButton, hideFilterButton, hideDensityButton, hideExportButton, hideQuickFilterBar, optionsAC: optionsACExternal, emptyItem, handleDeleteClick, setSnackBar, }, _) => {
const { serverEndPoint } = (0, DRFReactBySchemaContext_1.useDRFReactBySchema)();
const apiContext = (0, APIWrapperContext_1.useAPIWrapper)();
const [preparedColumns, setPreparedColumns] = (0, react_1.useState)(null);
const [dataGridLoading, setDataGridLoading] = (0, react_1.useState)(false);
const [rowModesModel, setRowModesModel] = (0, react_1.useState)();
const [selectionModel, setSelectionModel] = (0, react_1.useState)([]);
const [selectionModelIds, setSelectionModelIds] = (0, react_1.useState)([]);
const optionsAC = (0, react_1.useRef)(null);
const yupValidationSchema = (0, react_1.useRef)(null);
const processingRow = (0, react_1.useRef)(null);
const visibleRows = (0, react_1.useRef)('');
if (!onEditModel) {
onEditModel = apiContext.onEditModel;
}
const updateOptionsAC = () => __awaiter(void 0, void 0, void 0, function* () {
optionsAC.current = {};
for (const col of columns) {
if (optionsACExternal && col.field in optionsACExternal) {
optionsAC.current[col.field] = optionsACExternal[col.field];
continue;
}
if (!schema[col.field]) {
continue;
}
if (['field', 'nested object'].includes(schema[col.field].type) &&
!(col.field in optionsAC.current)) {
const options = yield (0, api_1.getAutoComplete)({
model: col.field,
serverEndPoint,
});
if (options) {
optionsAC.current[col.field] = options;
continue;
}
console.log(`Couldn't load autocomplete options from '${col.field}'`);
continue;
}
if (schema[col.field].type === 'choice' && !(col.field in optionsAC.current)) {
optionsAC.current[col.field] = schema[col.field].choices;
continue;
}
if (col.field === indexField && addExistingModel && !optionsAC.current[col.field]) {
const options = yield (0, api_1.getAutoComplete)({
model: addExistingModel,
serverEndPoint,
});
if (options) {
optionsAC.current[col.field] = options;
continue;
}
if (!(col.field in optionsAC.current)) {
delete optionsAC.current[col.field];
}
}
}
});
const initColumns = () => __awaiter(void 0, void 0, void 0, function* () {
const actionCols = [];
if (isEditable) {
const handleSaveClick = (id) => () => {
if (id) {
setRowModesModel(Object.assign(Object.assign({}, rowModesModel), { [id]: { mode: x_data_grid_1.GridRowModes.View } }));
}
};
const handleCancelClick = (id) => () => {
if (id) {
setRowModesModel(Object.assign(Object.assign({}, rowModesModel), { [id]: { mode: x_data_grid_1.GridRowModes.View, ignoreModifications: true } }));
}
setDataGrid((currentDataGrid) => {
const editedRow = currentDataGrid.data.find((row) => row.id === id);
if (editedRow && editedRow.isNew) {
return Object.assign(Object.assign({}, currentDataGrid), { data: currentDataGrid.data.filter((row) => row.id !== id) });
}
return currentDataGrid;
});
};
const handleEditInlineClick = (id) => () => {
if (id) {
setRowModesModel(Object.assign(Object.assign({}, rowModesModel), { [id]: { mode: x_data_grid_1.GridRowModes.Edit } }));
}
};
actionCols.push({
field: 'actions',
headerName: '',
type: 'actions',
getActions: ({ id }) => {
var _a;
if (!id) {
return [];
}
const isInEditMode = ((_a = rowModesModel === null || rowModesModel === void 0 ? void 0 : rowModesModel[id]) === null || _a === void 0 ? void 0 : _a.mode) === x_data_grid_1.GridRowModes.Edit;
if (isInEditMode) {
return [
react_1.default.createElement(x_data_grid_1.GridActionsCellItem, { key: `save_${id}`, icon: react_1.default.createElement(Check_1.default, null), label: "Salvar", onClick: handleSaveClick(id), color: "success", showInMenu: false, placeholder: "", onResize: () => undefined, onResizeCapture: () => undefined, onPointerEnterCapture: () => undefined, onPointerLeaveCapture: () => undefined }),
react_1.default.createElement(x_data_grid_1.GridActionsCellItem, { key: `cancel_${id}`, icon: react_1.default.createElement(Undo_1.default, null), label: "Cancelar", onClick: handleCancelClick(id), color: "inherit", showInMenu: false, placeholder: "", onResize: () => undefined, onResizeCapture: () => undefined, onPointerEnterCapture: () => undefined, onPointerLeaveCapture: () => undefined }),
];
}
const actionItems = [];
actions.forEach((action) => {
switch (action) {
case 'editInline':
actionItems.push(react_1.default.createElement(x_data_grid_1.GridActionsCellItem, { key: `editInline_${id}`, icon: actions.includes('edit') ? react_1.default.createElement(Bolt_1.default, null) : react_1.default.createElement(Edit_1.default, null), label: "Edit inline", onClick: handleEditInlineClick(id), color: "inherit", showInMenu: false, placeholder: "", onResize: () => undefined, onResizeCapture: () => undefined, onPointerEnterCapture: () => undefined, onPointerLeaveCapture: () => undefined }));
break;
case 'remove':
actionItems.push(react_1.default.createElement(x_data_grid_1.GridActionsCellItem, { key: `remove_${id}`, icon: react_1.default.createElement(Clear_1.default, null), label: "Delete", onClick: handleDeleteClick(id), color: "error", showInMenu: false, placeholder: "", onResize: () => undefined, onResizeCapture: () => undefined, onPointerEnterCapture: () => undefined, onPointerLeaveCapture: () => undefined }));
break;
case 'edit':
if (!LinkComponent) {
console.log('you must pass LinkComponent prop to navigate externally');
break;
}
actionItems.push(react_1.default.createElement(LinkComponent, { key: `edit_${id}`, to: `${indexFieldBasePath}${id}`, state: stateToLink },
react_1.default.createElement(x_data_grid_1.GridActionsCellItem, { icon: react_1.default.createElement(Edit_1.default, null), label: "Edit", color: "inherit", showInMenu: false, placeholder: "", onResize: () => undefined, onResizeCapture: () => undefined, onPointerEnterCapture: () => undefined, onPointerLeaveCapture: () => undefined })));
break;
case 'view':
if (!LinkComponent) {
console.log('you must pass LinkComponent prop to navigate externally');
break;
}
if (!indexFieldViewBasePath) {
console.log('For view action to work, you must supply indexFieldViewBasePath prop!');
break;
}
actionItems.push(react_1.default.createElement(LinkComponent, { key: `view_${id}`, to: `${indexFieldViewBasePath}${id}`, state: stateToLink },
react_1.default.createElement(x_data_grid_1.GridActionsCellItem, { icon: react_1.default.createElement(Visibility_1.default, null), label: "View", color: "inherit", showInMenu: false, placeholder: "", onResize: () => undefined, onResizeCapture: () => undefined, onPointerEnterCapture: () => undefined, onPointerLeaveCapture: () => undefined })));
break;
}
});
// React.ReactElement<any, string | React.JSXElementConstructor<any>>
// React.ReactElement<any, string | React.JSXElementConstructor<any>>
if (customActions) {
customActions.forEach((customAction) => {
actionItems.push(react_1.default.createElement(x_data_grid_1.GridActionsCellItem, { key: `${customAction.key}_${id}`, icon: customAction.icon, label: customAction.label, onClick: () => customAction.handleClick(dataGrid.data.find((row) => row.id === id)), showInMenu: false, placeholder: "", onResize: () => undefined, onResizeCapture: () => undefined, onPointerEnterCapture: () => undefined, onPointerLeaveCapture: () => undefined }));
});
}
return actionItems;
},
});
}
const cols = [...actionCols, ...columns];
const colsPromises = cols.map((col) => __awaiter(void 0, void 0, void 0, function* () {
if (!schema[col.field]) {
return col;
}
const isIndexField = indexField !== '' && col.field === indexField;
let column = col;
if (isIndexField) {
col.isIndexField = true;
}
column.editable =
isEditable &&
!col.disabled &&
(!schema[col.field].read_only ||
['field', 'nested object'].includes(schema[col.field].type));
if (['field', 'nested object'].includes(schema[col.field].type)) {
column.creatable =
'related_editable' in schema[col.field]
? schema[col.field].related_editable
: column.creatable;
}
switch (schema[col.field].type) {
case 'date':
column.type = 'date';
const dateFormat = (0, utils_1.buildDateFormatBySchema)(schema[col.field].date_views);
column.valueFormatter = (params) => params.value ? (0, dayjs_1.default)(params.value).format(dateFormat) : '';
column.filterOperators = (0, utils_2.quantityOnlyOperators)({
type: 'date',
});
if (isEditable && !col.disabled) {
column.renderEditCell = (params) => (react_1.default.createElement(GridDateInput_1.GridDateInput, Object.assign({}, params, { column: column, dateViews: schema[col.field].date_views })));
break;
}
break;
case 'datetime':
column.type = 'dateTime';
column.minWidth = 180;
column.valueFormatter = (params) => params.value ? (0, dayjs_1.default)(params.value).format('DD/MM/YYYY HH:mm') : '';
column.filterOperators = (0, utils_2.quantityOnlyOperators)({
type: 'date',
});
break;
case 'nested object':
column.minWidth = 150;
if (isEditable && !col.disabled) {
column.valueFormatter = (params) => {
return !params.value ? '' : params.value.label;
};
// column.filterable = false;
column.sortComparator = (v1, v2, param1, param2) => {
return (0, x_data_grid_1.gridStringOrNumberComparator)(v1.label, v2.label, param1, param2);
};
column.renderEditCell = (params) => (react_1.default.createElement(SelectEditInputCell_1.SelectEditInputCell, Object.assign({}, params, { column: column, type: schema[col.field].type, options: optionsAC.current && col.field in optionsAC.current
? optionsAC.current[col.field]
: [], isIndexField: isIndexField, onEditModel: onEditModel, fieldsLayout: customFieldFormLayouts && col.field in customFieldFormLayouts
? customFieldFormLayouts[col.field]
: undefined, setDialog: apiContext.setDialog })));
break;
}
column.valueGetter = (params) => {
return !params.value ? '' : params.value.label;
};
break;
case 'field':
column.orderable = false;
if (isEditable && !col.disabled) {
column.minWidth = 300;
column.valueFormatter = (params) => {
return !params.value || !Array.isArray(params.value)
? ''
: params.value.map((val) => val.label).join(', ');
};
column.filterable = false;
column.renderEditCell = (params) => (react_1.default.createElement(SelectEditInputCell_1.SelectEditInputCell, Object.assign({}, params, { column: column, type: schema[col.field].type, options: optionsAC.current && col.field in optionsAC.current
? optionsAC.current[col.field]
: [], isIndexField: isIndexField, multiple: schema[col.field].many || false, setDialog: apiContext.setDialog })));
break;
}
column.valueGetter = (params) => {
return !params.value || !Array.isArray(params.value)
? ''
: params.value.map((val) => val.label).join(', ');
};
break;
case 'choice':
if (isEditable && !col.disabled) {
column.minWidth = 150;
column.valueFormatter = (params) => {
return !params.value ? '' : params.value.display_name;
};
column.filterable = false;
column.sortComparator = (v1, v2, param1, param2) => {
return (0, x_data_grid_1.gridStringOrNumberComparator)(v1.display_name, v2.display_name, param1, param2);
};
column.renderEditCell = (params) => (react_1.default.createElement(SelectEditInputCell_1.SelectEditInputCell, Object.assign({}, params, { column: column, type: schema[col.field].type, options: optionsAC.current && col.field in optionsAC.current
? optionsAC.current[col.field]
: [], isIndexField: isIndexField, setDialog: apiContext.setDialog })));
break;
}
column.valueGetter = (params) => {
return !params.value ? '' : params.value.display_name;
};
break;
case 'boolean':
if (isEditable && !col.disabled) {
column.valueFormatter = (params) => {
return params.value ? 'Sim' : 'Não';
};
column.renderEditCell = (params) => react_1.default.createElement(BooleanInputCell_1.BooleanInputCell, Object.assign({}, params, { column: column }));
break;
}
column.valueGetter = (params) => {
return params.value ? 'Sim' : 'Não';
};
break;
case 'decimal':
case 'float':
const decimalScale = schema[col.field].decimal_places || 2;
const prefix = schema[col.field].prefix || '';
const suffix = schema[col.field].suffix || '';
const isCurrency = schema[col.field].is_currency;
column.type = 'number';
column.valueFormatter = (params) => {
return !params.value
? ''
: parseFloat(params.value).toLocaleString('pt-BR', {
minimumFractionDigits: decimalScale,
maximumFractionDigits: decimalScale,
});
};
if (isEditable && !col.disabled) {
column.renderEditCell = (params) => (react_1.default.createElement(GridDecimalInput_1.GridDecimalInput, Object.assign({}, params, { decimalPlaces: decimalScale, isCurrency: isCurrency, prefix: prefix, suffix: suffix, column: column })));
}
column.filterOperators = (0, utils_2.quantityOnlyOperators)({
type: 'float',
});
break;
case 'number':
case 'integer':
column.type = 'number';
column.filterOperators = (0, utils_2.quantityOnlyOperators)({
type: 'number',
});
break;
}
if (indexFieldMinWidth && !column.minWidth) {
column.minWidth = col.field === indexField ? indexFieldMinWidth : minWidth;
}
if (indexField) {
if (col.field === indexField) {
column.flex = 1;
column.renderCell = (params) => {
if (LinkComponent && customLinkDestination && !actions.includes('edit')) {
return (react_1.default.createElement(LinkComponent, { to: `${customLinkDestination(params)}`, state: stateToLink }, params.formattedValue));
}
if (!LinkComponent ||
!indexFieldBasePath ||
actions.includes('edit') ||
(['field', 'nested object'].includes(schema[col.field].type) &&
(!params.row[col.field] || !params.row[col.field].id))) {
return react_1.default.createElement(react_1.default.Fragment, null, params.formattedValue);
}
const targetId = ['field', 'nested object'].includes(schema[col.field].type)
? params.row[col.field].id.toString()
: params.row.id.toString();
return (react_1.default.createElement(LinkComponent, { to: `${indexFieldBasePath}${targetId}`, state: stateToLink }, params.formattedValue));
};
if (isEditable &&
!col.disabled &&
optionsAC.current &&
col.field in optionsAC.current &&
addExistingModel) {
column.renderEditCell = (params) => {
if (!(0, utils_1.isTmpId)(params.id)) {
return react_1.default.createElement(x_data_grid_1.GridEditInputCell, Object.assign({}, params));
}
return (react_1.default.createElement(SelectEditInputCell_1.SelectEditInputCell, Object.assign({}, params, { column: column, type: schema[col.field].type, options: optionsAC.current && col.field in optionsAC.current
? optionsAC.current[col.field]
: [], isIndexField: true, setDialog: apiContext.setDialog })));
};
}
}
}
// format numbers:
if (column.patternFormat) {
column.valueFormatter = (params) => {
if (!params.value || typeof params.value !== 'string') {
return params.value;
}
const formattedValue = new string_mask_1.default(column.patternFormat, {}).apply(params.value);
return formattedValue;
};
if (isEditable && !col.disabled) {
column.renderEditCell = (params) => (react_1.default.createElement(GridPatternInput_1.GridPatternInput, Object.assign({}, params, { patternFormat: column.patternFormat })));
}
}
// Custom column operations:
if (customColumnOperations) {
column = yield customColumnOperations(column);
}
// Finally!
return column;
}));
const finalCols = yield Promise.all(colsPromises);
setPreparedColumns(finalCols);
});
const handleAddItems = (numberOfRows = 1) => {
const newRows = [];
for (let i = 0; i < numberOfRows; i++) {
const id = (0, utils_1.getTmpId)();
newRows.push(Object.assign(Object.assign({}, emptyItem), { id }));
}
const newData = tableAutoHeight
? [...dataGrid.data, ...newRows]
: [...newRows, ...dataGrid.data];
setDataGrid({
data: newData,
});
setRowModesModel((oldModel) => {
const newModel = Object.assign({}, oldModel);
newRows.map((newRow) => {
newModel[newRow.id] = { mode: x_data_grid_1.GridRowModes.Edit, fieldToFocus: indexField };
});
return newModel;
});
if (!tableAutoHeight) {
// Ugly hack to scroll to top, since scroll to cell is only available in Pro
const el = document.querySelector(`.dataGrid_${name} .MuiDataGrid-virtualScroller`);
if (el) {
el.scrollTop = 0;
setTimeout(() => {
el.scrollTop = 0;
}, 10);
}
}
};
const bulkUpdateData = (newData) => __awaiter(void 0, void 0, void 0, function* () {
const promises = [];
const ids = [];
newData.map((item) => {
promises.push((0, api_1.updateDataBySchema)({
model,
modelObjectId: item.id,
serverEndPoint,
data: item,
schema,
}));
ids.push(item.id);
});
const results = yield Promise.all(promises);
setSelectionModel([]);
setSelectionModelIds([]);
setDataGrid((currentData) => {
const updatedData = currentData.data.map((item) => {
const index = ids.indexOf(item.id);
return index === -1 ? item : newData[index];
});
return {
data: updatedData,
};
});
setSnackBar({
open: true,
severity: 'success',
msg: 'Alterações salvas com sucesso',
});
return results.map((result, index) => {
return {
id: ids[index],
success: 'isAxiosError' in result,
};
});
});
const bulkDeleteData = (ids) => __awaiter(void 0, void 0, void 0, function* () {
const promises = [];
ids.map((id) => {
promises.push((0, api_1.deleteData)(model, serverEndPoint, id));
});
setDataGridLoading(true);
const results = yield Promise.all(promises);
setSelectionModel([]);
setSelectionModelIds([]);
setDataGrid({
data: dataGrid.data.filter((item) => !ids.includes(item.id)),
});
setDataGridLoading(false);
setSnackBar({
open: true,
severity: 'success',
msg: 'Itens apagados com sucesso',
});
return results.map((result, index) => {
return {
id: ids[index],
success: result === true,
};
});
});
const bulkCreateData = (ids) => __awaiter(void 0, void 0, void 0, function* () {
handleAddItems(ids.length);
setSelectionModel([]);
setSelectionModelIds([]);
setSnackBar({
open: true,
severity: 'success',
msg: 'Linhas adicionadas com sucesso',
});
});
(0, react_1.useEffect)(() => {
updateOptionsAC().then(() => {
initColumns();
});
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [rowModesModel, JSON.stringify(columns)]);
const processRowUpdate = (editedRow) => __awaiter(void 0, void 0, void 0, function* () {
if (!preparedColumns || !yupValidationSchema.current) {
return false;
}
setDataGridLoading(true);
const indexCol = preparedColumns.find((col) => col.field === indexField);
processingRow.current = editedRow.id;
yield yupValidationSchema.current.validate(editedRow);
const onlyAddExisting = indexField &&
(0, utils_1.isTmpId)(editedRow.id) &&
editedRow[indexField] &&
!(0, utils_1.isTmpId)(editedRow[indexField].id) &&
(!indexCol || !indexCol.valueFormatter);
const createNewItem = indexField &&
(0, utils_1.isTmpId)(editedRow.id) &&
editedRow[indexField] &&
(0, utils_1.isTmpId)(editedRow[indexField].id);
if (onlyAddExisting) {
const row = {};
row.id_to_add = editedRow[indexField].id;
for (const [key, value] of Object.entries(editedRow[indexField])) {
if (key === 'id') {
row[key] = editedRow.id;
continue;
}
row[key] = value;
}
editedRow = Object.assign({}, row);
}
if (createNewItem && editedRow[indexField]) {
if (editedRow[indexField].inputValue) {
editedRow[indexField] = editedRow[indexField].inputValue;
}
if (addExistingModel) {
editedRow[indexField] = editedRow[indexField].label;
}
}
if (modelParent && modelParentId && apiContext) {
const response = yield apiContext.onEditRelatedModelSave({
model: modelParent,
id: modelParentId,
relatedModel: model,
relatedModelId: editedRow.id,
newRow: editedRow,
schema,
onlyAddExisting,
});
if (response !== false && (onlyAddExisting || createNewItem || !onlyAddExisting)) {
updateOptionsAC();
const data = [...dataGrid.data];
const newRow = 'data' in response && 'schema' in response ? response.data : response;
for (const i in data) {
if (data[i].id === editedRow.id) {
data[i] = newRow;
// This is for cases where users want to do custom operations after saving the row,
// like for example make calculations among columns.
if (onProcessRow) {
onProcessRow(data[i]);
}
// Reflect the changes to the outside, for example for global calculations over all data
if (onDataChange) {
onDataChange(data);
}
setDataGrid({ data });
break;
}
}
setDataGridLoading(false);
return newRow;
}
setDataGridLoading(false);
return false;
}
const response = yield apiContext.onEditModelDataGridSave({
model,
id: editedRow.id,
newRow: editedRow,
schema,
});
setDataGridLoading(false);
if (response !== false) {
updateOptionsAC();
const data = [...dataGrid.data];
const newRow = response;
for (const i in data) {
if (data[i].id === editedRow.id) {
data[i] = newRow;
// This is for cases where users want to do custom operations after saving the row,
// like for example make calculations among columns.
if (onProcessRow) {
onProcessRow(data[i]);
}
// Reflect the changes to the outside, for example for global calculations over all data
if (onDataChange) {
onDataChange(data);
}
setDataGrid({ data });
break;
}
}
return newRow;
}
return false;
});
const customPaddings = isAutoHeight
? {
'&.MuiDataGrid-root--densityCompact .MuiDataGrid-cell': {
py: '8px',
},
'&.MuiDataGrid-root--densityStandard .MuiDataGrid-cell': {
py: '15px',
},
'&.MuiDataGrid-root--densityComfortable .MuiDataGrid-cell': {
py: '22px',
},
}
: undefined;
const checkboxSelection = hasBulkSelect ? true : undefined;
const disableRowSelectionOnClick = hasBulkSelect ? true : undefined;
return (react_1.default.createElement(Box_1.default, { className: `dataGrid_${name}`, sx: { height: '100%' } }, preparedColumns === null ? (react_1.default.createElement(Box_1.default, { sx: styles_1.Layout.loadingBox },
react_1.default.createElement(CircularProgress_1.default, null))) : (react_1.default.createElement(x_data_grid_1.DataGrid, { rows: dataGrid.data, columns: preparedColumns, autoHeight: tableAutoHeight, onStateChange: (state) => {
if (setVisibleRows) {
const newVisibleRows = Object.entries(state.filter.visibleRowsLookup)
.filter((entry) => {
return entry[1] === true;
})
.map((entry) => {
return entry[0];
});
const newVisibleRowsJSON = JSON.stringify(newVisibleRows);
if (newVisibleRowsJSON !== visibleRows.current) {
setVisibleRows(newVisibleRows);
visibleRows.current = newVisibleRowsJSON;
}
}
}, editMode: "row", loading: dataGridLoading || loading, hideFooterPagination: hideFooterPagination, getRowHeight: () => {
if (isAutoHeight) {
return 'auto';
}
return null;
}, isCellEditable: (params) => {
var _a;
const isRowInEditMode = ((_a = rowModesModel === null || rowModesModel === void 0 ? void 0 : rowModesModel[params.row.id]) === null || _a === void 0 ? void 0 : _a.mode) === x_data_grid_1.GridRowModes.Edit;
const isPermanentRow = !(0, utils_1.isTmpId)(params.row.id);
const isIndexField = params.field === indexField;
const indexColumn = preparedColumns.find((col) => col.field === indexField);
const hasValueFormatter = (indexColumn === null || indexColumn === void 0 ? void 0 : indexColumn.valueFormatter) !== undefined;
const isIndexFieldEditable = !optionsAC.current || !(indexField in optionsAC.current) || hasValueFormatter;
return (isRowInEditMode &&
(isPermanentRow ||
((0, utils_1.isTmpId)(params.row.id) && (isIndexField || isIndexFieldEditable))));
}, checkboxSelection: checkboxSelection, onSelectionModelChange: (newSelectionModel) => {
const selectedData = dataGrid.data.filter((item) => newSelectionModel.includes(item.id));
setSelectionModel(selectedData);
setSelectionModelIds(newSelectionModel);
}, selectionModel: selectionModelIds, disableSelectionOnClick: disableRowSelectionOnClick, rowModesModel: rowModesModel, onRowEditStart: (params, event) => {
event.defaultMuiPrevented = true;
}, onRowEditStop: (params, event) => {
event.defaultMuiPrevented = true;
}, processRowUpdate: processRowUpdate, onProcessRowUpdateError: (e) => {
setDataGridLoading(false);
if (processingRow.current) {
setRowModesModel(Object.assign(Object.assign({}, rowModesModel), { [processingRow.current]: {
mode: x_data_grid_1.GridRowModes.Edit,
} }));
}
const msg = `Erro em "${e.path}": ${e.errors}`;
setSnackBar({
open: true,
severity: 'error',
msg,
});
console.log(e);
}, components: {
Toolbar: hideToolbarComponent ? () => react_1.default.createElement(react_1.default.Fragment, null) : CustomToolbar_1.CustomToolbar,
Footer: hideFooterComponent ? () => react_1.default.createElement(react_1.default.Fragment, null) : FooterToolbar_1.FooterToolbar,
}, componentsProps: {
toolbar: {
preparedColumns,
setPreparedColumns,
showQuickFilter: true,
quickFilterProps: { debounceMs: 500 },
// getRowsToExport: () => {
// return [];
// },
selectionModel,
onSelectActions,
bulkUpdateData,
bulkDeleteData,
bulkCreateData,
hideColumnsButton,
hideFilterButton,
hideDensityButton,
hideExportButton,
hideQuickFilterBar,
},
footer: {
isEditable,
handleAddItem: () => {
handleAddItems();
},
},
filterPanel: {
sx: {
'& .MuiDataGrid-filterFormValueInput': {
width: 300,
},
},
},
}, experimentalFeatures: { newEditingApi: isEditable }, sx: customPaddings, paginationMode: paginationModel ? 'server' : 'client', onPageChange: (newPage) => {
if (setPaginationModel && paginationModel) {
setPaginationModel(Object.assign(Object.assign({}, paginationModel), { page: newPage }));
}
}, onPageSizeChange: (newPageSize) => {
if (setPaginationModel && paginationModel) {
setPaginationModel(Object.assign(Object.assign({}, paginationModel), { pageSize: newPageSize }));
}
}, rowCount: paginationModel && typeof rowCount !== 'undefined' ? rowCount : undefined, pageSize: paginationModel ? paginationModel.pageSize : 100, rowsPerPageOptions: paginationModel ? [paginationModel.pageSize] : [5, 10, 25, 50, 100], filterMode: paginationModel ? 'server' : 'client', onFilterModelChange: paginationModel
? (newFilter) => {
if (setPaginationModel && paginationModel) {
setPaginationModel(Object.assign(Object.assign({}, paginationModel), { filter: newFilter }));
}
}
: undefined, sortingMode: paginationModel ? 'server' : 'client', onSortModelChange: paginationModel
? (newSorting) => {
if (setPaginationModel && paginationModel) {
setPaginationModel(Object.assign(Object.assign({}, paginationModel), { sort: newSorting }));
}
}
: undefined }))));
});
DataGridDesktop.displayName = 'DataGridDesktop';
exports.default = DataGridDesktop;