@topconsultnpm/sdkui-react 6.20.0-dev2.45 → 6.20.0-dev2.47

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.
@@ -0,0 +1,432 @@
1
+ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
+ import React, { useEffect, useMemo } from "react";
3
+ import { PdGs, Priorities, SDK_Globals, Task_States } from "@topconsultnpm/sdk-ts";
4
+ import { FormModes } from "../../../ts";
5
+ import { calcResponsiveSizes, DateDisplayTypes, getPdgsIconMap, IconSave, SDKUI_Localizator } from "../../../helper";
6
+ import { areDifferentIDs, formatDate, getOriginLabel, getPriorityLocalizatorValue, getPriorityLocalizatorValues, getStatusLocalizatorValue } from "./TMTasksUtils";
7
+ import TMTooltip from "../../base/TMTooltip";
8
+ import TMTextBox from "../../editors/TMTextBox";
9
+ import TMUserChooser from "../../choosers/TMUserChooser";
10
+ import styled from "styled-components";
11
+ import { TMColors } from "../../../utils/theme";
12
+ import TMTextArea from "../../editors/TMTextArea";
13
+ import TMDropDown from "../../editors/TMDropDown";
14
+ import TMDateBox from "../../editors/TMDateBox";
15
+ import { useDeviceType } from "../../base/TMDeviceProvider";
16
+ import TMModal from "../../base/TMModal";
17
+ import TMButton from "../../base/TMButton";
18
+ import { ButtonNames, TMExceptionBoxManager, TMMessageBoxManager } from "../../base/TMPopUp";
19
+ import TMSpinner from "../../base/TMSpinner";
20
+ export const getCurrentUserTaskRole = (task) => {
21
+ if (!task)
22
+ return "personal";
23
+ // ID dell'utente a cui il task è assegnato
24
+ const taskToId = task.toID;
25
+ // ID dell'utente che ha creato/assegnato il task
26
+ const taskFromId = task.fromID;
27
+ // ID dell'utente attualmente loggato nella sessione
28
+ const userSessionId = SDK_Globals.tmSession?.SessionDescr?.userID;
29
+ // TRUE se il task è stato assegnato da un utente diverso da quello corrente
30
+ const isAssignedByOtherUser = areDifferentIDs(taskFromId, userSessionId);
31
+ // TRUE se il task è assegnato a un utente diverso da quello corrente
32
+ const isAssignedToOtherUser = areDifferentIDs(taskToId, userSessionId);
33
+ // Caso 1: Task personale: non è un work item, è stato creato da me, è assegnato a me
34
+ if (!isAssignedByOtherUser && !isAssignedToOtherUser) {
35
+ return "personal";
36
+ }
37
+ else if (!isAssignedByOtherUser && isAssignedToOtherUser) {
38
+ // Caso 2: Task che ho assegnato a un altro utente: creato da me, assegnato a un altro utente
39
+ return "sender";
40
+ }
41
+ else if (isAssignedByOtherUser) {
42
+ // Caso 3: il task è stato creato da un altro utente
43
+ return "receiver";
44
+ }
45
+ else {
46
+ // Default case, consider it as personal task
47
+ return "personal";
48
+ }
49
+ };
50
+ export const TaskFormAssignmentNoticeBadge = (props) => {
51
+ const { task, users } = props;
52
+ const taskRole = useMemo(() => getCurrentUserTaskRole(task), [task?.toID, task?.fromID, SDK_Globals.tmSession?.SessionDescr?.userID]);
53
+ const getMessage = () => {
54
+ const assigneeName = users.find(user => user.id === task.toID)?.name ?? '-';
55
+ if (taskRole === "personal")
56
+ return SDKUI_Localizator.PersonalTaskAssignmentMessage;
57
+ if (taskRole === "receiver")
58
+ return SDKUI_Localizator.TaskAssignedMessage.replaceParams(task.fromName ?? '');
59
+ if (taskRole === "sender")
60
+ return SDKUI_Localizator.TaskAssignedToUserMessage.replaceParams(assigneeName);
61
+ return null;
62
+ };
63
+ const message = getMessage();
64
+ if (!message)
65
+ return null;
66
+ return (_jsxs("div", { style: {
67
+ display: 'flex',
68
+ justifyContent: 'flex-end',
69
+ alignItems: 'center',
70
+ gap: 6,
71
+ width: '100%',
72
+ }, children: [_jsx("i", { className: "dx-icon-info", style: {
73
+ fontSize: 15,
74
+ color: taskRole === "receiver" ? '#A66300' : '#2559A5',
75
+ display: 'flex',
76
+ alignItems: 'center'
77
+ } }), _jsx("span", { style: {
78
+ fontSize: 13,
79
+ color: taskRole === "receiver" ? '#A66300' : '#2559A5',
80
+ lineHeight: 1
81
+ }, children: message })] }));
82
+ };
83
+ export const RenderAttachmentBlock = ({ condition, pdg, label }) => {
84
+ if (!condition || !label)
85
+ return null;
86
+ return (_jsxs("span", { style: { display: 'inline-flex', alignItems: 'center', gap: 4 }, children: [SDKUI_Localizator.Attachment, ": ", getPdgsIconMap().get(pdg), " ", label] }));
87
+ };
88
+ export const TaskFormContextualAttachments = ({ taskContext }) => {
89
+ const hasWorkingGroup = !!taskContext?.workingGroup?.id;
90
+ const hasDossier = !!taskContext?.dossier?.id;
91
+ const hasDocument = !!taskContext?.document?.tid && !!taskContext?.document?.did;
92
+ const hasWorkItem = !!taskContext?.workItem?.tid && !!taskContext?.workItem?.did;
93
+ const hasAnyAttachment = hasWorkingGroup || hasDossier || hasDocument || hasWorkItem;
94
+ return (_jsx("div", { style: { width: '100%', marginTop: 15, marginLeft: 5 }, children: !hasAnyAttachment ? (_jsxs("span", { children: [SDKUI_Localizator.Attachment, ": ", _jsx("span", { style: { color: '#6c757d', fontStyle: 'italic' }, children: 'Nessun allegato' })] })) : (_jsxs(_Fragment, { children: [_jsx(RenderAttachmentBlock, { condition: hasWorkingGroup, pdg: PdGs.WG, label: SDKUI_Localizator.WorkGroup + ' "' + getOriginLabel(PdGs.WG, taskContext?.workingGroup?.name) + '"' }), _jsx(RenderAttachmentBlock, { condition: hasDossier, pdg: PdGs.CF, label: SDKUI_Localizator.Dossier + ' "' + getOriginLabel(PdGs.CF, taskContext?.dossier?.name) + '"' }), _jsx(RenderAttachmentBlock, { condition: hasDocument, pdg: PdGs.DT, label: SDKUI_Localizator.Document + ' "' + getOriginLabel(PdGs.DT, taskContext?.document?.name) + '"' }), _jsx(RenderAttachmentBlock, { condition: hasWorkItem, pdg: PdGs.DT, label: SDKUI_Localizator.Document + ' "' + getOriginLabel(PdGs.DT, taskContext?.workItem?.name) + '"' })] })) }));
95
+ };
96
+ export const TaskPdgOriginNavigator = (props) => {
97
+ const { formMode, formData, isMobile, gotoPDGExtendedLabelClickCallback } = props;
98
+ return formMode === FormModes.Update && formData?.pdG && formData?.iD1Name && (_jsx("div", { style: { display: 'flex', flexDirection: 'row', width: '100%', gap: 16, padding: '8px 0' }, children: _jsx("div", { style: { width: "100%", display: 'flex', alignItems: 'center', justifyContent: 'center' }, children: _jsxs("div", { onClick: () => formData.pdG !== PdGs.None ? gotoPDGExtendedLabelClickCallback() : null, style: {
99
+ backgroundColor: "#C2388B",
100
+ color: "#fff",
101
+ padding: "10px 16px",
102
+ borderRadius: "20px",
103
+ display: "flex",
104
+ alignItems: "center",
105
+ justifyContent: "space-between",
106
+ cursor: "pointer",
107
+ fontWeight: 600,
108
+ transition: 'background-color 0.3s, transform 0.2s',
109
+ minWidth: "180px",
110
+ maxWidth: "100%",
111
+ flexWrap: "wrap",
112
+ gap: "8px",
113
+ }, onMouseEnter: e => {
114
+ if (formData.pdG !== PdGs.None)
115
+ e.currentTarget.style.backgroundColor = "#A12D78";
116
+ e.currentTarget.style.transform = 'scale(1.05)';
117
+ }, onMouseLeave: e => {
118
+ if (formData.pdG !== PdGs.None)
119
+ e.currentTarget.style.backgroundColor = "#C2388B";
120
+ e.currentTarget.style.transform = 'scale(1)';
121
+ }, children: [_jsxs("span", { style: {
122
+ flex: 1,
123
+ textAlign: "center",
124
+ gap: "6px",
125
+ display: "flex",
126
+ justifyContent: "center",
127
+ alignItems: "center",
128
+ }, children: [formData.pdG === PdGs.WG && _jsx("span", { children: SDKUI_Localizator.GoToWorkgroup }), formData.pdG === PdGs.CF && _jsx("span", { children: SDKUI_Localizator.GoToDossier }), formData.pdG === PdGs.DT && _jsx("span", { children: SDKUI_Localizator.GoToDocument }), (() => {
129
+ const originLabel = getOriginLabel(formData.pdG, formData.iD1Name);
130
+ if (!originLabel)
131
+ return null;
132
+ const maxLength = isMobile ? 10 : 25;
133
+ const displayText = originLabel.length > maxLength
134
+ ? originLabel.slice(0, maxLength) + "..."
135
+ : originLabel;
136
+ return _jsxs("span", { children: ["\u201C", displayText, "\u201D"] });
137
+ })()] }), _jsx(TMTooltip, { content: _jsxs("div", { style: { textAlign: "left" }, children: [formData.pdG && (_jsxs(_Fragment, { children: [_jsxs("div", { style: {
138
+ display: "flex",
139
+ alignItems: "center",
140
+ gap: "6px",
141
+ fontWeight: 600,
142
+ }, children: [_jsx("span", { style: { display: "flex", alignItems: "center" }, children: getPdgsIconMap().get(formData.pdG) }), _jsx("span", { children: formData.pdG === PdGs.WG ? SDKUI_Localizator.WorkGroup : formData.pdG === PdGs.CF ? SDKUI_Localizator.Dossier : formData.pdG === PdGs.DT ? SDKUI_Localizator.Document : "" })] }), _jsx("hr", { style: { margin: "4px 0 8px 0" } })] })), formData.iD1 != null && formData.iD1 !== 0 && (_jsxs("div", { children: [_jsx("b", { children: "ID1" }), ": ", formData.iD1.toString()] })), formData.iD1Name && (_jsxs("div", { children: [_jsx("b", { children: "ID1NAME" }), ": ", formData.iD1Name.toString()] })), formData.iD2 != null && formData.iD2 !== 0 && (_jsxs("div", { children: [_jsx("b", { children: "ID2" }), ": ", formData.iD2.toString()] }))] }), children: _jsx("i", { className: "dx-icon-info", style: { fontSize: "1.3rem", flexShrink: 0 } }) })] }) }) }));
143
+ };
144
+ export const TaskAssigneeField = (props) => {
145
+ const { formMode, formData, taskContext, validationItems, fieldsReadOnly, formDataOrig, usersList, onValueChanged, } = props;
146
+ const { isCreateMode, isUpdateMode, isAssignedByOtherUser, isAssignedToOtherUser } = useMemo(() => {
147
+ const isCreateMode = formMode === FormModes.Create;
148
+ const isUpdateMode = formMode === FormModes.Update;
149
+ const taskToId = formData?.toID;
150
+ const taskFromId = formData?.fromID;
151
+ const userSessionId = SDK_Globals.tmSession?.SessionDescr?.userID;
152
+ // Vero se il task è stato creato da un altro utente
153
+ // taskFromId = ID dell’utente che ha assegnato il task
154
+ // userSessionId = ID dell’utente attualmente loggato
155
+ const isAssignedByOtherUser = areDifferentIDs(taskFromId, userSessionId);
156
+ // Vero se il task è assegnato a un altro utente
157
+ // taskToId = ID dell’utente a cui è assegnato il task
158
+ // userSessionId = ID dell’utente attualmente loggato
159
+ const isAssignedToOtherUser = areDifferentIDs(taskToId, userSessionId);
160
+ return {
161
+ isCreateMode,
162
+ isUpdateMode,
163
+ isAssignedByOtherUser,
164
+ isAssignedToOtherUser
165
+ };
166
+ }, [formData?.toID, formData?.fromID, formMode, SDK_Globals.tmSession?.SessionDescr?.userID]);
167
+ let content = null;
168
+ if (isCreateMode || !isAssignedByOtherUser) {
169
+ content = (_jsx("div", { id: "assignedToAnotherUserField", style: { width: '100%' }, children: _jsx(TMUserChooser, { dataSource: usersList, allowShowAllUsers: !!taskContext?.dossier, allowMultipleSelection: false, label: SDKUI_Localizator.AssignedTo_Female, readOnly: fieldsReadOnly.assignedTO, values: formData?.toID ? [formData?.toID] : [], isModifiedWhen: formData?.toID !== formDataOrig?.toID, validationItems: validationItems?.filter(o => o.PropertyName === SDKUI_Localizator.AssignedTo_Female), onValueChanged: onValueChanged }) }));
170
+ }
171
+ else if (isUpdateMode) {
172
+ content = (_jsxs(_Fragment, { children: [isAssignedByOtherUser && (_jsx("div", { style: { width: '100%' }, children: _jsx(TMTextBox, { label: SDKUI_Localizator.AssignedBy, value: formData?.fromName ?? '', readOnly: true }) })), isAssignedToOtherUser && (_jsx("div", { style: { width: '100%' }, children: _jsx(TMTextBox, { label: SDKUI_Localizator.AssignedTo_Female, value: formData?.toName ?? '', readOnly: true }) }))] }));
173
+ }
174
+ return (_jsx("div", { style: { display: 'flex', flexDirection: 'row', width: '100%', gap: 10 }, children: content }));
175
+ };
176
+ const ReadOnlyFieldWrapper = styled.div `
177
+ position: relative;
178
+ width: 100%;
179
+ background: #ffffff;
180
+ border: 1px solid ${props => props.$isModifiedWhen ? '#E29000' : '#e6e6e6'};
181
+ border-radius: 10px;
182
+ padding: 12px 15px;
183
+ margin-top: 12px;
184
+ box-shadow: 0 2px 6px rgba(0,0,0,0.05);
185
+ `;
186
+ const ReadOnlyFieldLabel = styled.label `
187
+ position: absolute;
188
+ top: -9px;
189
+ left: 9px;
190
+ padding: 0 3px;
191
+ font-size: 0.9rem;
192
+ background-color: white;
193
+ color: ${props => props.$isModifiedWhen ? '#E29000' : 'rgb(80,80,80)'};
194
+ display: inline-flex;
195
+ align-items: center;
196
+ gap: 6px;
197
+ `;
198
+ const ReadOnlyFieldValue = styled.div `
199
+ font-size: 0.95rem;
200
+ color: ${props => props.$isModifiedWhen ? '#E29000' : '#525252'};
201
+ white-space: pre-wrap;
202
+
203
+ /* Limite a 4 linee con scrollbar se serve */
204
+ display: -webkit-box;
205
+ -webkit-line-clamp: 4;
206
+ -webkit-box-orient: vertical;
207
+ overflow-y: auto; /* scrollbar verticale se serve */
208
+ max-height: calc(1.2em * 4); /* altezza approssimativa di 4 linee */
209
+
210
+ /* Permette selezione testo */
211
+ user-select: text;
212
+ `;
213
+ const ResponseCommentWrapper = styled.div `
214
+ position: relative;
215
+ width: 100%;
216
+ `;
217
+ const ResponseCommentLabel = styled.label `
218
+ position: absolute;
219
+ top: -8px;
220
+ left: 12px;
221
+ background-color: white;
222
+ padding: 0 4px;
223
+ font-size: 0.9rem;
224
+ color: rgb(80,80,80);
225
+ display: inline-flex;
226
+ align-items: center;
227
+ gap: 4px;
228
+ color: ${props => props.$isModifiedWhen ? '#E29000' : 'rgb(80,80,80)'};
229
+ `;
230
+ const ResponseCommentTextArea = styled.textarea.attrs({
231
+ maxLength: 500,
232
+ }) `
233
+ width: 100%;
234
+ height: 100px;
235
+ border: 1px solid ${props => props.$isValid ? (props.$isModifiedWhen ? "#E29000" : 'rgb(80,80,80)') : TMColors.error};
236
+ border-radius: 10px;
237
+ padding: 10px;
238
+ resize: none;
239
+ cursor: ${props => props.disabled ? 'not-allowed' : 'text'};
240
+ &:focus {
241
+ outline: none;
242
+ border-bottom: 4px solid ${props => props.$isValid ? TMColors.primaryColor : TMColors.error};
243
+ }
244
+ color: ${props => props.$isModifiedWhen ? '#E29000' : 'rgb(80,80,80)'};
245
+ `;
246
+ const ResponseCommentCharacterCounter = styled.div `
247
+ text-align: right;
248
+ font-size: 0.8rem;
249
+ color: #6c757d;
250
+ margin-top: 4px;
251
+ `;
252
+ export const TaskFormResponseComment = (props) => {
253
+ const { originalResponse = "", currentResponse = "", onAnswerChange, readonly = false } = props;
254
+ return (_jsx("div", { style: { width: '100%', marginTop: 15 }, children: readonly ? (currentResponse && currentResponse.trim() !== '' ? (_jsxs(ReadOnlyFieldWrapper, { "$isModifiedWhen": currentResponse !== originalResponse, children: [_jsxs(ReadOnlyFieldLabel, { "$isModifiedWhen": currentResponse !== originalResponse, children: [SDKUI_Localizator.Answer, " "] }), _jsx(ReadOnlyFieldValue, { "$isModifiedWhen": currentResponse !== originalResponse, children: currentResponse && currentResponse.trim() !== '' ? currentResponse : "" })] })) : null) : (_jsxs(ResponseCommentWrapper, { children: [_jsx(ResponseCommentTextArea, { id: "responseId", name: "response", "$isValid": true, value: currentResponse ?? '', onChange: onAnswerChange ? onAnswerChange : undefined, "$isModifiedWhen": currentResponse !== originalResponse }), _jsx(ResponseCommentLabel, { htmlFor: "responseId", "$isModifiedWhen": currentResponse !== originalResponse, children: SDKUI_Localizator.Answer }), _jsx(ResponseCommentCharacterCounter, { children: `${500 - (currentResponse ?? '').length} ${SDKUI_Localizator.CharactersRemaining}` })] })) }));
255
+ };
256
+ // Stile comune per i container dei campi
257
+ const fieldContainerStyle = { width: '100%' };
258
+ const fieldContainerWithMarginStyle = { width: '100%', marginTop: 10 };
259
+ export const RenderNameField = ({ validationItems, setFormData, formData, formDataOrig, fieldsReadOnly }) => (_jsx("div", { style: fieldContainerStyle, children: _jsx(TMTextBox, { label: SDKUI_Localizator.Name, value: formData?.name ?? '', readOnly: fieldsReadOnly.name, autoFocus: true, maxLength: 100, isModifiedWhen: formData?.name !== formDataOrig?.name, onValueChanged: (e) => setFormData({ ...formData ?? {}, name: e.target.value }), validationItems: validationItems?.filter(o => o.PropertyName === SDKUI_Localizator.Name) }) }));
260
+ export const RenderDescriptionField = ({ validationItems, setFormData, formData, formDataOrig, fieldsReadOnly }) => (_jsx("div", { style: fieldContainerStyle, children: _jsx(TMTextArea, { label: SDKUI_Localizator.Description, value: formData?.description ?? '', maxLength: 200, readOnly: fieldsReadOnly.description, isModifiedWhen: formData?.description !== formDataOrig?.description, onValueChanged: (e) => setFormData({ ...formData ?? {}, description: e.target.value }), validationItems: validationItems?.filter(o => o.PropertyName === SDKUI_Localizator.Description), resize: false }) }));
261
+ export const RenderPriorityField = ({ formData, formDataOrig, fieldsReadOnly, onPriorityValueChange }) => (_jsx("div", { style: fieldContainerStyle, children: !fieldsReadOnly.priority ? (_jsx(TMDropDown, { label: SDKUI_Localizator.Priority, value: formData?.priority, dataSource: getPriorityLocalizatorValues(), isModifiedWhen: formData?.priority !== formDataOrig?.priority, onValueChanged: onPriorityValueChange })) : (_jsx(TMTextBox, { label: SDKUI_Localizator.Priority, value: getPriorityLocalizatorValue(formData?.priority ?? Priorities.Low), readOnly: true })) }));
262
+ export const RenderStartDateField = ({ validationItems, setFormData, formData, formDataOrig, fieldsReadOnly, onContentReady }) => (_jsx("div", { style: fieldContainerWithMarginStyle, children: !fieldsReadOnly.startDate ? (_jsx(TMDateBox, { id: "start-date", resetTimeToZeroOnKeyPress: false, label: SDKUI_Localizator.StartDate, dateDisplayType: DateDisplayTypes.DateTime, value: formData?.startTime, isModifiedWhen: formData?.startTime !== formDataOrig?.startTime, validationItems: validationItems?.filter(o => o.PropertyName === SDKUI_Localizator.ErrorStartEndDate), onContentReady: onContentReady, onValueChange: (value) => setFormData({ ...formData ?? {}, startTime: value }), showClearButton: true })) : (_jsx(TMTextBox, { label: SDKUI_Localizator.StartDate, value: formData?.startTime ? formatDate(formData?.startTime) : '', readOnly: true })) }));
263
+ export const RenderEndDateField = ({ validationItems, setFormData, formData, formDataOrig, fieldsReadOnly, onContentReady }) => (_jsx("div", { style: fieldContainerWithMarginStyle, children: !fieldsReadOnly.startDate ? (_jsx(TMDateBox, { id: "end-date", resetTimeToZeroOnKeyPress: false, label: SDKUI_Localizator.ExpirationDate, dateDisplayType: DateDisplayTypes.DateTime, value: formData?.endTime, isModifiedWhen: formData?.endTime !== formDataOrig?.endTime, validationItems: validationItems?.filter(o => o.PropertyName === SDKUI_Localizator.ErrorStartEndDate || o.PropertyName === SDKUI_Localizator.ErrorEndRemDate), onContentReady: onContentReady, onValueChange: (value) => setFormData({ ...formData ?? {}, endTime: value }), showClearButton: true, readOnly: fieldsReadOnly.endDate })) : (_jsx(TMTextBox, { label: SDKUI_Localizator.ExpirationDate, value: formData?.endTime ? formatDate(formData?.endTime) : '', readOnly: true })) }));
264
+ export const RenderRemindDateField = ({ validationItems, setFormData, formData, formDataOrig, fieldsReadOnly }) => (_jsx("div", { style: fieldContainerWithMarginStyle, children: _jsx(TMDateBox, { id: "alert-time", resetTimeToZeroOnKeyPress: false, label: SDKUI_Localizator.Reminder, dateDisplayType: DateDisplayTypes.DateTime, value: formData?.remTime ?? undefined, isModifiedWhen: formData?.remTime !== formDataOrig?.remTime, validationItems: validationItems?.filter(o => o.PropertyName === SDKUI_Localizator.ErrorEndRemDate), onValueChange: (value) => setFormData({ ...formData ?? {}, remTime: value }), showClearButton: true, readOnly: fieldsReadOnly.remTime }) }));
265
+ export const RenderTaskFormStateField = (props) => {
266
+ const { formDataOrig, formData, handleShowChangeStateForm, onSavedCallback } = props;
267
+ // Non renderizzare nulla finché i dati non sono pronti
268
+ if (!formDataOrig)
269
+ return null;
270
+ const taskRole = getCurrentUserTaskRole(formDataOrig);
271
+ // Condizione per mostrare il pulsante
272
+ const showCloseButton = taskRole === 'sender' && formDataOrig.state === Task_States.Completed;
273
+ const showModifyButton = !(taskRole === 'sender' && formDataOrig.state === Task_States.Completed);
274
+ const closeTaskCallback = () => {
275
+ if (!formData || !formData.id)
276
+ return;
277
+ const msg = `Sei sicuro voler chiudere l'attività ${formData.name ?? 'N/A'}?`;
278
+ TMMessageBoxManager.show({
279
+ title: SDKUI_Localizator.MarkAs, message: msg, buttons: [ButtonNames.YES, ButtonNames.NO],
280
+ onButtonClick: async (e) => {
281
+ if (e !== ButtonNames.YES)
282
+ return;
283
+ TMSpinner.show();
284
+ try {
285
+ const selectedTask = await SDK_Globals.tmSession?.NewTaskEngine().RetrieveAsync(formData.id);
286
+ if (!selectedTask) {
287
+ TMMessageBoxManager.show({ title: SDKUI_Localizator.Error, message: `Attività ${formData.name ?? 'N/A'} non trovata.` });
288
+ return;
289
+ }
290
+ selectedTask.state = Task_States.Closed;
291
+ await SDK_Globals.tmSession?.NewTaskEngine().UpdateAsync(selectedTask);
292
+ onSavedCallback?.(selectedTask);
293
+ }
294
+ catch (err) {
295
+ TMExceptionBoxManager.show({ exception: err });
296
+ }
297
+ finally {
298
+ TMSpinner.hide();
299
+ }
300
+ }
301
+ });
302
+ };
303
+ return (_jsx("div", { style: { width: '100%', marginTop: 15 }, children: _jsxs(ReadOnlyFieldWrapper, { "$isModifiedWhen": formDataOrig?.state !== formData?.state, style: { display: 'flex', alignItems: 'center', gap: 16 }, children: [_jsx(ReadOnlyFieldLabel, { "$isModifiedWhen": formDataOrig?.state !== formData?.state, children: SDKUI_Localizator.Status }), _jsx(ReadOnlyFieldValue, { "$isModifiedWhen": formDataOrig?.state !== formData?.state, children: getStatusLocalizatorValue(formData?.state ?? Task_States.None) }), _jsxs("div", { style: { flex: 1, display: 'flex', justifyContent: 'center' }, children: [showModifyButton && (_jsx("div", { onClick: () => handleShowChangeStateForm(true), style: {
304
+ backgroundColor: '#C2388B',
305
+ color: '#fff',
306
+ padding: '10px 16px',
307
+ borderRadius: '25px',
308
+ display: 'flex',
309
+ alignItems: 'center',
310
+ justifyContent: 'center',
311
+ cursor: 'pointer',
312
+ fontWeight: 600,
313
+ transition: 'background-color 0.3s, transform 0.2s',
314
+ }, onMouseEnter: (e) => {
315
+ e.currentTarget.style.backgroundColor = '#A12D78';
316
+ e.currentTarget.style.transform = 'scale(1.05)';
317
+ }, onMouseLeave: (e) => {
318
+ e.currentTarget.style.backgroundColor = '#C2388B';
319
+ e.currentTarget.style.transform = 'scale(1)';
320
+ }, children: _jsx("span", { style: { fontSize: '1rem', letterSpacing: '0.5px' }, children: "Modifica stato" }) })), showCloseButton && (_jsx("div", { onClick: closeTaskCallback, style: {
321
+ backgroundColor: '#C2388B',
322
+ color: '#fff',
323
+ padding: '10px 16px',
324
+ borderRadius: '25px',
325
+ display: 'flex',
326
+ alignItems: 'center',
327
+ justifyContent: 'center',
328
+ cursor: 'pointer',
329
+ fontWeight: 600,
330
+ transition: 'background-color 0.3s, transform 0.2s',
331
+ }, onMouseEnter: (e) => {
332
+ e.currentTarget.style.backgroundColor = '#A12D78';
333
+ e.currentTarget.style.transform = 'scale(1.05)';
334
+ }, onMouseLeave: (e) => {
335
+ e.currentTarget.style.backgroundColor = '#C2388B';
336
+ e.currentTarget.style.transform = 'scale(1)';
337
+ }, children: _jsx("span", { style: { fontSize: '1rem', letterSpacing: '0.5px' }, children: "Chiudi attivit\u00E0" }) }))] })] }) }));
338
+ };
339
+ export const TMChangeStateForm = (props) => {
340
+ const { formData, formDataOrig, handleShowChangeStateForm, setFormData } = props;
341
+ const deviceType = useDeviceType();
342
+ const taskRole = useMemo(() => getCurrentUserTaskRole(formData), [formData.toID, formData.fromID, SDK_Globals.tmSession?.SessionDescr?.userID]);
343
+ const [statusValue, setStatusValue] = React.useState(formData?.state ?? Task_States.None);
344
+ const [responseValue, setResponseValue] = React.useState(formData?.response ?? '');
345
+ const [dropdownValues, setDropdownValues] = React.useState([]);
346
+ useEffect(() => {
347
+ const availableTransitions = getAvailableTaskTransitions(formData?.state ?? Task_States.None, taskRole);
348
+ const values = getDropdownValuesFromTaskStates(availableTransitions, formData?.state ?? Task_States.None);
349
+ setDropdownValues(values);
350
+ if (values.length > 0) {
351
+ const currentState = formData?.state ?? Task_States.None;
352
+ const existsInDropdown = values.some(v => v.value === currentState);
353
+ setStatusValue(existsInDropdown ? currentState : values[0].value);
354
+ }
355
+ else {
356
+ setStatusValue(Task_States.NotStarted);
357
+ }
358
+ setResponseValue(formData?.response ?? '');
359
+ }, [formData, taskRole]);
360
+ const onStatusValueChange = (e) => {
361
+ if (!e?.target?.value)
362
+ return;
363
+ setStatusValue(e?.target?.value);
364
+ };
365
+ const onAnswerChange = (e) => {
366
+ setResponseValue(e.target.value ?? '');
367
+ };
368
+ const onSaveCallback = () => {
369
+ setFormData(({ ...formData ?? {}, state: statusValue, response: responseValue }));
370
+ handleShowChangeStateForm(false);
371
+ };
372
+ return _jsx(TMModal, { title: `Modifica stato: ` + getStatusLocalizatorValue(formDataOrig?.state ?? Task_States.None), width: calcResponsiveSizes(deviceType, '570px', '570px', '95%'), height: calcResponsiveSizes(deviceType, '300px', '300px', '95%'), isModal: true, resizable: false, onClose: () => handleShowChangeStateForm(false), children: _jsxs("div", { style: {
373
+ display: 'flex',
374
+ flexDirection: 'column',
375
+ gap: '5px',
376
+ padding: '5px 24px',
377
+ justifyContent: 'center',
378
+ height: '100%',
379
+ }, children: [_jsx(TMDropDown, { label: SDKUI_Localizator.Status, value: statusValue, dataSource: dropdownValues, isModifiedWhen: statusValue !== formDataOrig?.state, onValueChanged: onStatusValueChange }), _jsx(TaskFormResponseComment, { currentResponse: responseValue, originalResponse: formDataOrig?.response, onAnswerChange: onAnswerChange }), _jsx("div", { style: {
380
+ display: 'flex',
381
+ justifyContent: 'center',
382
+ gap: '10px',
383
+ marginTop: '5px'
384
+ }, children: _jsx(TMButton, { caption: SDKUI_Localizator.ApplyAndClose, advancedColor: TMColors.primary, icon: _jsx(IconSave, {}), showTooltip: false, onClick: onSaveCallback }) })] }) });
385
+ };
386
+ export const STATUS_TRANSITIONS = {
387
+ // Proprietario del task: può cambiare liberamente in qualsiasi stato
388
+ personal: {
389
+ [Task_States.NotStarted]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed, Task_States.Closed],
390
+ [Task_States.InProgress]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed, Task_States.Closed],
391
+ [Task_States.Waiting]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed, Task_States.Closed],
392
+ [Task_States.Deferred]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed, Task_States.Closed],
393
+ [Task_States.Completed]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed, Task_States.Closed],
394
+ [Task_States.Closed]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed, Task_States.Closed]
395
+ },
396
+ // Mittente del task: può modificare lo stato liberamente, ma solo riaprire o chiudere se completato
397
+ sender: {
398
+ [Task_States.NotStarted]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed],
399
+ [Task_States.InProgress]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed],
400
+ [Task_States.Waiting]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed],
401
+ [Task_States.Deferred]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed],
402
+ [Task_States.Completed]: [Task_States.Closed, Task_States.InProgress],
403
+ [Task_States.Closed]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed, Task_States.Closed]
404
+ },
405
+ // Destinatario del task: può modificare lo stato liberamente, ma solo riaprire o chiudere se completato
406
+ receiver: {
407
+ [Task_States.NotStarted]: [Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed],
408
+ [Task_States.InProgress]: [Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed],
409
+ [Task_States.Waiting]: [Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed],
410
+ [Task_States.Deferred]: [Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed],
411
+ [Task_States.Completed]: [Task_States.Closed, Task_States.InProgress],
412
+ [Task_States.Closed]: [Task_States.NotStarted, Task_States.InProgress, Task_States.Waiting, Task_States.Deferred, Task_States.Completed, Task_States.Closed]
413
+ }
414
+ };
415
+ const getAvailableTaskTransitions = (currentStatus, role) => {
416
+ const transitions = STATUS_TRANSITIONS[role];
417
+ return transitions?.[currentStatus] ?? [];
418
+ };
419
+ const getDropdownValuesFromTaskStates = (states, currentState) => {
420
+ const map = {
421
+ [Task_States.Completed]: SDKUI_Localizator.Completed,
422
+ [Task_States.Closed]: SDKUI_Localizator.Closed,
423
+ [Task_States.Deferred]: SDKUI_Localizator.Postponed,
424
+ [Task_States.InProgress]: SDKUI_Localizator.InProgress,
425
+ [Task_States.NotStarted]: SDKUI_Localizator.NewFemale,
426
+ [Task_States.Waiting]: SDKUI_Localizator.Pending,
427
+ [Task_States.None]: "",
428
+ };
429
+ return states
430
+ .filter(state => state !== Task_States.None && state !== currentState)
431
+ .map(state => ({ value: state, display: map[state] }));
432
+ };
@@ -431,6 +431,7 @@ export const formatDate = (date) => {
431
431
  // Return the formatted date string
432
432
  return `${day}/${month}/${year} ${hours}:${minutes}:${seconds}`;
433
433
  };
434
+ // Funzione per confrontare due ID e verificare se sono diversi
434
435
  export const areDifferentIDs = (fromID, userID) => {
435
436
  if (fromID && userID) {
436
437
  return fromID !== userID;
@@ -29,11 +29,4 @@ export declare const treeFilterDataSource: (allTasks: Array<TaskDescriptor>) =>
29
29
  expanded?: boolean;
30
30
  tooltipContent?: ReactNode;
31
31
  }>;
32
- type RenderContextBlockParams = {
33
- condition: boolean;
34
- pdg: PdGs;
35
- label: string | undefined;
36
- isMobile: boolean;
37
- };
38
- export declare const renderContextBlock: ({ condition, pdg, label, isMobile }: RenderContextBlockParams) => JSX.Element | null;
39
32
  export {};
@@ -2,7 +2,7 @@ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-run
2
2
  import { useState } from "react";
3
3
  import { PdGs, Priorities, SDK_Globals, Task_States } from '@topconsultnpm/sdk-ts';
4
4
  import { Extended_Task_States, FilterCategoryId, filterTreeTask, gotoPDGExtendedLabel, prioritiesResourceData, taskIsExpiringSoon } from "./TMTasksUtils";
5
- import { getPdgsIconMap, SDKUI_Localizator, TMConditionalWrapper } from "../../../helper";
5
+ import { getPdgsIconMap, SDKUI_Localizator } from "../../../helper";
6
6
  import { FormModes } from "../../../ts";
7
7
  import TMTooltip from "../../base/TMTooltip";
8
8
  const taskStateIconClassMap = () => {
@@ -131,14 +131,3 @@ export const treeFilterDataSource = (allTasks) => {
131
131
  { id: FilterCategoryId.High, label: SDKUI_Localizator.High + " (" + highLength + ")", value: Priorities.High, categoryId: FilterCategoryId.AllPriorities },
132
132
  ];
133
133
  };
134
- export const renderContextBlock = ({ condition, pdg, label, isMobile }) => {
135
- if (!condition || !label)
136
- return null;
137
- return (_jsx(TMConditionalWrapper, { condition: !isMobile, wrapper: (children) => (_jsx("div", { style: { display: 'flex', flexDirection: 'row', width: '100%', gap: 10 }, children: children })), children: _jsx("div", { style: {
138
- width: isMobile ? '100%' : '50%',
139
- display: 'flex',
140
- alignItems: 'center',
141
- color: "#2559A5",
142
- marginTop: 10
143
- }, children: _jsxs(TMTooltip, { content: label, children: [_jsx("span", { children: getPdgsIconMap().get(pdg) }), "\u00A0", _jsx("span", { children: label })] }) }) }));
144
- };
@@ -5,7 +5,7 @@ import { TabPanel, Item } from 'devextreme-react/tab-panel';
5
5
  import { Priorities, ResultTypes, SDK_Globals, Task_States } from "@topconsultnpm/sdk-ts";
6
6
  import { calculateNumberOfDays, renderTaskIcons } from "./TMTasksUtilsView";
7
7
  import { getPriorityLocalizatorValue } from "../tasks/TMTasksUtils";
8
- import { calcResponsiveSizes, getExceptionMessage, SDKUI_Localizator, StyledTabItem, TMCountBadge } from "../../../helper";
8
+ import { getExceptionMessage, SDKUI_Localizator, StyledTabItem, taskModalSizes, TMCountBadge } from "../../../helper";
9
9
  import { useDeviceType } from "../../base/TMDeviceProvider";
10
10
  import { FormModes } from "../../../ts";
11
11
  import TMDataGrid from "../../base/TMDataGrid";
@@ -545,7 +545,7 @@ const TMTasksView = (props) => {
545
545
  _jsxs(_Fragment, { children: [activeComponent === TaskView.CALENDAR_TASK && getFromOrToCalendarElement(visualizedTasks, false, true), activeComponent === TaskView.AGENDA_TASK && getFromOrToAgendaElement(visualizedTasks, false, true), activeComponent === TaskView.LIST_TASK && getFromOrToDatagridElement(visualizedTasks, false, true)] }) : '' }), _jsx(Item, { title: SDKUI_Localizator.AllFemale, icon: "fields", tabRender: (params) => {
546
546
  return _jsxs(StyledTabItem, { "$isSelected": activeTabIndex === AssignedTab.All, children: [_jsxs(TMTooltip, { content: SDKUI_Localizator.AllFemale, children: [_jsx("i", { className: `dx-icon-${params.icon}` }), "\u00A0", params.title, " ", (allTasksFilteredCount > 0) ? `(${allTasksFilteredCount})` : ''] }), newTaskCount > 0 && (_jsx(TMTooltip, { content: SDKUI_Localizator.NewAssignedActivitiesNumber + ": " + newTaskCount, children: _jsx(TMCountBadge, { children: newTaskCount }) }))] });
547
547
  }, render: () => activeTabIndex === AssignedTab.All ?
548
- _jsxs(_Fragment, { children: [activeComponent === TaskView.CALENDAR_TASK && getFromOrToCalendarElement(visualizedTasks, true, true), activeComponent === TaskView.AGENDA_TASK && getFromOrToAgendaElement(visualizedTasks, true, true), activeComponent === TaskView.LIST_TASK && getFromOrToDatagridElement(visualizedTasks, true, true)] }) : '' })] }) }), showTaskForm && _jsx(TMTaskForm, { id: currentTask?.id ?? -1, width: calcResponsiveSizes(deviceType, '700px', '700px', '95%'), height: calcResponsiveSizes(deviceType, '700px', '700px', '95%'), title: isContextualCreate ? SDKUI_Localizator.ContextualTask : SDKUI_Localizator.Widget_Activities, isModal: true, formMode: formMode ?? FormModes.Create, visualizedTasks: visualizedTasks, currentTask: currentTask, setCurrentTask: setCurrentTask, isContextualCreate: isContextualCreate, selectedRowKeys: selectedRowKeys, handleFocusedRowKeyChange: handleFocusedRowChange, taskContext: taskContext, usersList: usersList, onStatusChanged: () => { }, onClose: closeTaskFormCallback, onCancel: closeTaskFormCallback, showBackButton: false, onSaved: onSavedCallback, startDate: calendarStartDate, endDate: calendarEndDate, onOpenS4TViewerRequest: onOpenS4TViewerRequest, s4TViewerDialogComponent: s4TViewerDialogComponent, allTasks: allTasks, getAllTasks: getAllTasks, deleteTaskByIdsCallback: deleteTaskByIdsCallback, addTaskCallback: addTaskCallback, editTaskCallback: editTaskCallback, handleNavigateToWGs: handleNavigateToWGsWrapper, handleNavigateToDossiers: handleNavigateToDossiersWrapper }), _jsx("button", { style: {
548
+ _jsxs(_Fragment, { children: [activeComponent === TaskView.CALENDAR_TASK && getFromOrToCalendarElement(visualizedTasks, true, true), activeComponent === TaskView.AGENDA_TASK && getFromOrToAgendaElement(visualizedTasks, true, true), activeComponent === TaskView.LIST_TASK && getFromOrToDatagridElement(visualizedTasks, true, true)] }) : '' })] }) }), showTaskForm && _jsx(TMTaskForm, { id: currentTask?.id ?? -1, width: taskModalSizes(deviceType, formMode ?? FormModes.Create).width, height: taskModalSizes(deviceType, formMode ?? FormModes.Create).height, title: isContextualCreate ? SDKUI_Localizator.ContextualTask : SDKUI_Localizator.Widget_Activities, isModal: true, formMode: formMode ?? FormModes.Create, visualizedTasks: visualizedTasks, currentTask: currentTask, setCurrentTask: setCurrentTask, isContextualCreate: isContextualCreate, selectedRowKeys: selectedRowKeys, handleFocusedRowKeyChange: handleFocusedRowChange, taskContext: taskContext, usersList: usersList, onStatusChanged: () => { }, onClose: closeTaskFormCallback, onCancel: closeTaskFormCallback, showBackButton: false, onSaved: onSavedCallback, startDate: calendarStartDate, endDate: calendarEndDate, onOpenS4TViewerRequest: onOpenS4TViewerRequest, s4TViewerDialogComponent: s4TViewerDialogComponent, allTasks: allTasks, getAllTasks: getAllTasks, deleteTaskByIdsCallback: deleteTaskByIdsCallback, addTaskCallback: addTaskCallback, editTaskCallback: editTaskCallback, handleNavigateToWGs: handleNavigateToWGsWrapper, handleNavigateToDossiers: handleNavigateToDossiersWrapper }), _jsx("button", { style: {
549
549
  position: 'absolute',
550
550
  bottom: hasFilters ? '90px' : '18px',
551
551
  right: '20px',
@@ -11,7 +11,7 @@ import { TMColors } from '../../utils/theme';
11
11
  import TMValidationItemsList from '../grids/TMValidationItemsList';
12
12
  import TMModal from '../base/TMModal';
13
13
  import { DeviceType, useDeviceType } from '../base/TMDeviceProvider';
14
- const TMSaveForm = ({ id, formMode = FormModes.Update, showToolbar = true, skipIsModifiedCheck = false, title, children, isModal, exception, customToolbarElements, hasNavigation, showSaveButton = true, customSaveButton, customTooltipSaveButton, showBackButton, showWarningsCount = true, showErrorCount = true, showUndoButton = true, onClose, onSaveAsync, onNext, onPrev, canNext, canPrev, isModified, onShowList, validationItems = [], onUndo, onCancel, width, height, askClosingConfirm = false, showTitleFormMode = true, showCloseButton = true }) => {
14
+ const TMSaveForm = ({ id, formMode = FormModes.Update, showToolbar = true, skipIsModifiedCheck = false, title, children, isModal, exception, customToolbarElements, hasNavigation, showSaveButton = true, customSaveButton, customTooltipSaveButton, showBackButton, showWarningsCount = true, showErrorCount = true, showUndoButton = true, onClose, onSaveAsync, onNext, onPrev, canNext, canPrev, isModified, onShowList, validationItems = [], onUndo, onCancel, width, height, askClosingConfirm = false, showTitleFormMode = true, showCloseButton = true, resizable = true }) => {
15
15
  const [showList, setShowList] = useState(true);
16
16
  const [showErrorGrid, setShowErrorGrid] = useState(false);
17
17
  const deviceType = useDeviceType();
@@ -65,26 +65,74 @@ const TMSaveForm = ({ id, formMode = FormModes.Update, showToolbar = true, skipI
65
65
  }
66
66
  });
67
67
  };
68
- const doClose = () => {
68
+ const doClose = async () => {
69
+ // Se non ci sono modifiche o vogliamo ignorare il controllo delle modifiche
69
70
  if (!isModified || skipIsModifiedCheck) {
70
71
  onClose?.();
71
- deviceType === DeviceType.MOBILE && setShowList(true), onShowList?.(true);
72
+ // Se il dispositivo è mobile, mostra di nuovo la lista
73
+ if (deviceType === DeviceType.MOBILE) {
74
+ setShowList(true);
75
+ onShowList?.(true);
76
+ }
72
77
  return;
73
78
  }
79
+ // Determina il messaggio e i pulsanti da mostrare in base alla presenza di errori
80
+ const hasValidationErrors = validationItems.length > 0;
81
+ const message = (isModified && hasValidationErrors) ? SDKUI_Localizator.FormErrorsProceedQuestion : SDKUI_Localizator.SaveQuestion;
82
+ const buttons = hasValidationErrors
83
+ ? [ButtonNames.YES, ButtonNames.NO]
84
+ : [ButtonNames.YES, ButtonNames.NO, ButtonNames.CANCEL];
85
+ // Mostra il messaggio di conferma
74
86
  TMMessageBoxManager.show({
75
- parentId: isModal ? "TMSaveFormShowConfirmForClose-" + id : undefined,
76
- message: SDKUI_Localizator.SaveQuestion, buttons: [ButtonNames.YES, ButtonNames.NO, ButtonNames.CANCEL],
77
- onButtonClick: async (e) => {
87
+ parentId: isModal ? `TMSaveFormShowConfirmForClose-${id}` : undefined,
88
+ message,
89
+ buttons,
90
+ onButtonClick: async (buttonClicked) => {
78
91
  try {
79
- if (e == ButtonNames.CANCEL)
80
- return;
81
- if (e == ButtonNames.NO)
82
- deviceType === DeviceType.MOBILE && (onUndo(), setShowList(true), onShowList?.(true));
83
- if (e == ButtonNames.YES)
84
- deviceType === DeviceType.MOBILE ? (await onSaveAsync?.(), setShowList(true), onShowList?.(true)) : await onSaveAsync?.();
92
+ // Caso con errori di validazione
93
+ if (hasValidationErrors) {
94
+ if (buttonClicked === ButtonNames.NO)
95
+ return; // Non fare nulla
96
+ if (buttonClicked === ButtonNames.YES) {
97
+ if (deviceType === DeviceType.MOBILE) {
98
+ onUndo();
99
+ setShowList(true);
100
+ onShowList?.(true);
101
+ }
102
+ else {
103
+ onUndo();
104
+ }
105
+ }
106
+ }
107
+ else {
108
+ // Caso senza errori
109
+ switch (buttonClicked) {
110
+ case ButtonNames.CANCEL:
111
+ return; // Non fare nulla
112
+ case ButtonNames.NO:
113
+ if (deviceType === DeviceType.MOBILE) {
114
+ onUndo();
115
+ setShowList(true);
116
+ onShowList?.(true);
117
+ }
118
+ break;
119
+ case ButtonNames.YES:
120
+ if (deviceType === DeviceType.MOBILE) {
121
+ await onSaveAsync?.();
122
+ setShowList(true);
123
+ onShowList?.(true);
124
+ }
125
+ else {
126
+ await onSaveAsync?.();
127
+ }
128
+ break;
129
+ }
130
+ }
131
+ // Chiude il form/modal
85
132
  onClose?.();
86
133
  }
87
134
  catch (ex) {
135
+ // Mostra eventuali eccezioni
88
136
  TMExceptionBoxManager.show({ exception: ex });
89
137
  }
90
138
  }
@@ -102,7 +150,7 @@ const TMSaveForm = ({ id, formMode = FormModes.Update, showToolbar = true, skipI
102
150
  _jsx("div", { style: { width: '100%', height: '100%', marginTop: '50px', display: 'flex', alignItems: 'center', justifyContent: 'center', flexDirection: 'column', color: getColor('error') }, children: 'Si è verificato un errore' })
103
151
  : _jsx(_Fragment, { children: children }) }), showErrorGrid && validationItems.length > 0 ? _jsx(TMCard, { scrollY: true, padding: false, showBorder: false, children: _jsx(TMValidationItemsList, { validationItems: validationItems }) }) : _jsx(_Fragment, {})] }) }), (isModal && onClose) && _jsx("div", { id: "TMSaveFormShowConfirmForClose-" + id })] }));
104
152
  };
105
- return (_jsx(_Fragment, { children: (isModal && onClose) ? _jsx(_Fragment, { children: _jsx(TMModal, { title: `${title}${showTitleFormMode ? ` - ${LocalizeFormModes(formMode)}` : ''}`, onClose: doClose, width: width ?? '100%', height: height ?? '100%', hidePopup: false, askClosingConfirm: askClosingConfirm, showCloseButton: showCloseButton, children: _jsx("div", { style: { width: "100%", height: "100%", display: 'block' }, children: renderSaveForm() }) }) })
153
+ return (_jsx(_Fragment, { children: (isModal && onClose) ? _jsx(_Fragment, { children: _jsx(TMModal, { title: `${title}${showTitleFormMode ? ` - ${LocalizeFormModes(formMode)}` : ''}`, onClose: doClose, width: width ?? '100%', height: height ?? '100%', hidePopup: false, askClosingConfirm: askClosingConfirm, showCloseButton: showCloseButton, resizable: resizable, children: _jsx("div", { style: { width: "100%", height: "100%", display: 'block' }, children: renderSaveForm() }) }) })
106
154
  : renderSaveForm() }));
107
155
  };
108
156
  export default TMSaveForm;