@spokane-folio/security-incident 1.0.28
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/.eslintrc +32 -0
- package/.github/workflows/CODEOWNERS +8 -0
- package/.github/workflows/pr-validation.yml +44 -0
- package/.github/workflows/release.yml +64 -0
- package/.prettierrc +6 -0
- package/.stripesclirc +4 -0
- package/CHANGELOG.md +8 -0
- package/CONTRIBUTING.md +4 -0
- package/LICENSE +201 -0
- package/README.md +16 -0
- package/administrator-documentation/roles-and-permissions.md +65 -0
- package/administrator-documentation/track-settings-admin-guide-sketch.md +192 -0
- package/administrator-documentation/using-the-application.md +192 -0
- package/icons/app.png +0 -0
- package/icons/app.svg +1 -0
- package/icons/playButton.png +0 -0
- package/icons/profilePicThumbnail.png +0 -0
- package/jest.config.js +10 -0
- package/module-descriptor.json +75 -0
- package/output/service-worker.js +0 -0
- package/package.json +146 -0
- package/src/components/incidents/ColumnChooser.js +37 -0
- package/src/components/incidents/CreateMedia.js +132 -0
- package/src/components/incidents/CreatePane.js +1215 -0
- package/src/components/incidents/CreatePane.test.js +138 -0
- package/src/components/incidents/CreateReport.js +102 -0
- package/src/components/incidents/DetailsPane.js +1267 -0
- package/src/components/incidents/DetailsPane.test.js +150 -0
- package/src/components/incidents/EditPane.js +2334 -0
- package/src/components/incidents/EditPane.test.js +187 -0
- package/src/components/incidents/GetDetails.js +55 -0
- package/src/components/incidents/GetListDQLinkIncident.js +81 -0
- package/src/components/incidents/GetListDynamicQuery.js +66 -0
- package/src/components/incidents/GetLocations.js +57 -0
- package/src/components/incidents/GetMedia.js +98 -0
- package/src/components/incidents/GetName.js +111 -0
- package/src/components/incidents/GetNameCreatedBy.js +94 -0
- package/src/components/incidents/GetOrgLocaleSettings.js +61 -0
- package/src/components/incidents/GetPatronGroups.js +52 -0
- package/src/components/incidents/GetSelf.js +65 -0
- package/src/components/incidents/GetSummary.js +110 -0
- package/src/components/incidents/IncidentTypeCard.js +53 -0
- package/src/components/incidents/IncidentTypeCard.test.js +133 -0
- package/src/components/incidents/IncidentsPaneset.js +810 -0
- package/src/components/incidents/IncidentsPaneset.test.js +128 -0
- package/src/components/incidents/LinkedIncident.js +86 -0
- package/src/components/incidents/ModalAddMedia.js +262 -0
- package/src/components/incidents/ModalAddMedia.test.js +97 -0
- package/src/components/incidents/ModalAttentionDecOfService.js +111 -0
- package/src/components/incidents/ModalCustomWitness.js +469 -0
- package/src/components/incidents/ModalCustomWitness.test.js +147 -0
- package/src/components/incidents/ModalCustomerDetails.js +480 -0
- package/src/components/incidents/ModalCustomerDetails.test.js +116 -0
- package/src/components/incidents/ModalDescribeCustomer.js +361 -0
- package/src/components/incidents/ModalDescribeCustomer.test.js +156 -0
- package/src/components/incidents/ModalDirtyFormWarn.js +62 -0
- package/src/components/incidents/ModalLinkIncident.js +1213 -0
- package/src/components/incidents/ModalLinkIncidentStyle.css +32 -0
- package/src/components/incidents/ModalSelectIncidentTypes.js +178 -0
- package/src/components/incidents/ModalSelectIncidentTypes.test.js +273 -0
- package/src/components/incidents/ModalSelectKnownCustomer.js +395 -0
- package/src/components/incidents/ModalSelectWitness.js +406 -0
- package/src/components/incidents/ModalSelectWitness.test.js +308 -0
- package/src/components/incidents/ModalStyle.css +44 -0
- package/src/components/incidents/ModalTrespass.js +741 -0
- package/src/components/incidents/ModalViewCustomerDetails.js +241 -0
- package/src/components/incidents/ModalViewMedia.js +86 -0
- package/src/components/incidents/ModalViewTrespass.js +210 -0
- package/src/components/incidents/ResultsPane.js +437 -0
- package/src/components/incidents/ResultsPane.test.js +120 -0
- package/src/components/incidents/SearchCustomerOrWitness.js +108 -0
- package/src/components/incidents/Thumbnail.js +72 -0
- package/src/components/incidents/ThumbnailMarkRemoval.js +38 -0
- package/src/components/incidents/ThumbnailSkeleton.js +30 -0
- package/src/components/incidents/ThumbnailStyles.js +49 -0
- package/src/components/incidents/ThumbnailTempPreSave.js +71 -0
- package/src/components/incidents/UpdateReport.js +84 -0
- package/src/components/incidents/__snapshots__/CreatePane.test.js.snap +3 -0
- package/src/components/incidents/__snapshots__/DetailsPane.test.js.snap +3 -0
- package/src/components/incidents/__snapshots__/EditPane.test.js.snap +3 -0
- package/src/components/incidents/__snapshots__/IncidentTypeCard.test.js.snap +3 -0
- package/src/components/incidents/__snapshots__/IncidentsPaneset.test.js.snap +3 -0
- package/src/components/incidents/__snapshots__/ModalAddMedia.test.js.snap +3 -0
- package/src/components/incidents/__snapshots__/ModalCustomerDetails.test.js.snap +3 -0
- package/src/components/incidents/__snapshots__/ModalSelectWitness.test.js.snap +3 -0
- package/src/components/incidents/__snapshots__/ResultsPane.test.js.snap +3 -0
- package/src/components/incidents/helpers/ProfilePicture/ProfilePicture.css +5 -0
- package/src/components/incidents/helpers/ProfilePicture/ProfilePicture.js +51 -0
- package/src/components/incidents/helpers/ProfilePicture/isAValidURL.js +3 -0
- package/src/components/incidents/helpers/ProfilePicture/useProfilePicture.js +127 -0
- package/src/components/incidents/helpers/buildQueryString.js +28 -0
- package/src/components/incidents/helpers/cleanFormValues.js +53 -0
- package/src/components/incidents/helpers/computeEditedCustomers.js +124 -0
- package/src/components/incidents/helpers/convertDateIgnoringTZ.js +8 -0
- package/src/components/incidents/helpers/convertUTCISOToLocalePrettyTime.js +15 -0
- package/src/components/incidents/helpers/convertUTCISOToPrettyDate.js +19 -0
- package/src/components/incidents/helpers/decodeParamsToForm.js +20 -0
- package/src/components/incidents/helpers/deepNormalizeForComparison.js +39 -0
- package/src/components/incidents/helpers/extractFilterString.js +12 -0
- package/src/components/incidents/helpers/formatDateAndTimeToUTCISO.js +14 -0
- package/src/components/incidents/helpers/formatDateToUTCISO.js +14 -0
- package/src/components/incidents/helpers/formatTimeToUTCISO.js +28 -0
- package/src/components/incidents/helpers/getCurrentTime.js +20 -0
- package/src/components/incidents/helpers/getTodayDate.js +12 -0
- package/src/components/incidents/helpers/handlebarsHelpers.js +148 -0
- package/src/components/incidents/helpers/hasFormChangedAtCreate.js +50 -0
- package/src/components/incidents/helpers/hasTopLevelChangeAffectedDeclaration.js +90 -0
- package/src/components/incidents/helpers/hasTopLevelFormChanged.js +111 -0
- package/src/components/incidents/helpers/identifyCurrentTrespassDocs.js +109 -0
- package/src/components/incidents/helpers/isSameHtml.js +13 -0
- package/src/components/incidents/helpers/isValidDateFormat.js +14 -0
- package/src/components/incidents/helpers/isValidTimeInput.js +11 -0
- package/src/components/incidents/helpers/isValidUTCTimeFormat.js +14 -0
- package/src/components/incidents/helpers/parseMMDDYYYY.js +7 -0
- package/src/components/incidents/helpers/parseQueryString.js +16 -0
- package/src/components/incidents/helpers/sortTrespassDocuments.js +44 -0
- package/src/components/incidents/helpers/stripHTML.js +11 -0
- package/src/components/incidents/helpers/trespassDocUtils.js +197 -0
- package/src/components/incidents/helpers/validateTrespassDetails.js +37 -0
- package/src/components/incidents/usePersistedColModalLink.js +70 -0
- package/src/components/incidents/usePersistedColumns.js +70 -0
- package/src/components/incidents/usePersistedSort.js +23 -0
- package/src/components/incidents/usePersistedSortModalLink.js +23 -0
- package/src/contexts/IncidentContext.js +433 -0
- package/src/index.js +61 -0
- package/src/routes/Application.js +13 -0
- package/src/settings/GetIncidentCategories.js +56 -0
- package/src/settings/GetIncidentTypesDetails.js +88 -0
- package/src/settings/GetIncidentTypesIds.js +74 -0
- package/src/settings/GetLocationsInService.js +54 -0
- package/src/settings/GetSingleCustomLocationDetails.js +60 -0
- package/src/settings/GetSingleIncidentTypeDetails.js +60 -0
- package/src/settings/GetTrespassReasons.js +67 -0
- package/src/settings/GetTrespassTemplates.js +51 -0
- package/src/settings/IncidentCategoriesPane.js +285 -0
- package/src/settings/IncidentCategoriesPane.test.js +229 -0
- package/src/settings/IncidentTypeDetailsPane.js +215 -0
- package/src/settings/IncidentTypeDetailsPane.test.js +220 -0
- package/src/settings/IncidentTypeEditPane.js +211 -0
- package/src/settings/IncidentTypeEditPane.test.js +170 -0
- package/src/settings/IncidentTypesPaneset.js +167 -0
- package/src/settings/IncidentTypesPaneset.test.js +124 -0
- package/src/settings/LocationInServiceEditPane.js +320 -0
- package/src/settings/LocationsPaneset.js +415 -0
- package/src/settings/LocationsPaneset.test.js +106 -0
- package/src/settings/ModalDeleteCategory.js +47 -0
- package/src/settings/ModalDeleteIncidentType.js +49 -0
- package/src/settings/ModalDeleteLocationInService.js +49 -0
- package/src/settings/ModalDeleteTrespassReason.js +49 -0
- package/src/settings/ModalPreviewTrespassDoc.js +65 -0
- package/src/settings/ModalTrespassDocTokens.js +83 -0
- package/src/settings/NewIncidentTypePane.js +182 -0
- package/src/settings/PutIncidentType.js +60 -0
- package/src/settings/PutLocationsInService.js +52 -0
- package/src/settings/PutTrespassReasons.js +61 -0
- package/src/settings/PutTrespassTemplate.js +50 -0
- package/src/settings/TrespassDoc.css +17 -0
- package/src/settings/TrespassDocDetailsPane.js +215 -0
- package/src/settings/TrespassDocEditPane.js +538 -0
- package/src/settings/TrespassDocPaneset.js +581 -0
- package/src/settings/TrespassReasonDetailsPane.js +171 -0
- package/src/settings/TrespassReasonEditPane.js +221 -0
- package/src/settings/TrespassReasonsPaneset.js +282 -0
- package/src/settings/__snapshots__/IncidentCategoriesPane.test.js.snap +3 -0
- package/src/settings/__snapshots__/IncidentTypeDetailsPane.test.js.snap +3 -0
- package/src/settings/__snapshots__/IncidentTypeEditPane.test.js.snap +3 -0
- package/src/settings/__snapshots__/IncidentTypesPaneset.test.js.snap +3 -0
- package/src/settings/__snapshots__/LocationsPaneset.test.js.snap +3 -0
- package/src/settings/data/exampleJSON.json +92 -0
- package/src/settings/data/templateTokens.js +396 -0
- package/src/settings/helpers/alphabetize.js +18 -0
- package/src/settings/helpers/getCategoryTitleById.js +13 -0
- package/src/settings/helpers/makeId.js +15 -0
- package/src/settings/index.js +48 -0
- package/stripes.config.js +10 -0
- package/test/jest/__mock__/index.js +8 -0
- package/test/jest/__mock__/intl.mock.js +27 -0
- package/test/jest/__mock__/stripes.mock.js +26 -0
- package/test/jest/__mock__/stripesComponents.mock.js +151 -0
- package/test/jest/__mock__/stripesConfig.mock.js +1 -0
- package/test/jest/__mock__/stripesCore.mock.js +9 -0
- package/test/jest/__mock__/stripesIcon.mock.js +5 -0
- package/test/jest/__mock__/stripesSmartComponents.mock.js +7 -0
- package/test/jest/__mock__/stripesUtils.mock.js +3 -0
- package/test/jest/eslintrc.js +12 -0
- package/test/jest/setupFiles.js +5 -0
- package/translations/ui-security-incident/en_US.json +542 -0
- package/ui-module-acceptance-criteria.md +34 -0
|
@@ -0,0 +1,1215 @@
|
|
|
1
|
+
import React, { useState, useEffect, useMemo, useRef, useCallback } from 'react';
|
|
2
|
+
import { useIntl, FormattedMessage } from 'react-intl';
|
|
3
|
+
import { useHistory } from 'react-router-dom';
|
|
4
|
+
import DOMPurify from 'dompurify';
|
|
5
|
+
import { decode } from 'html-entities';
|
|
6
|
+
import {
|
|
7
|
+
Accordion,
|
|
8
|
+
AccordionSet,
|
|
9
|
+
Button,
|
|
10
|
+
Checkbox,
|
|
11
|
+
Col,
|
|
12
|
+
Datepicker,
|
|
13
|
+
Editor,
|
|
14
|
+
ExpandAllButton,
|
|
15
|
+
List,
|
|
16
|
+
Icon,
|
|
17
|
+
KeyValue,
|
|
18
|
+
Label,
|
|
19
|
+
LoadingPane,
|
|
20
|
+
Pane,
|
|
21
|
+
PaneHeader,
|
|
22
|
+
PaneFooter,
|
|
23
|
+
Row,
|
|
24
|
+
Select,
|
|
25
|
+
Timepicker
|
|
26
|
+
} from '@folio/stripes/components';
|
|
27
|
+
import GetLocationsInService from '../../settings/GetLocationsInService';
|
|
28
|
+
import GetIncidentTypesDetails from '../../settings/GetIncidentTypesDetails';
|
|
29
|
+
import ModalSelectIncidentTypes from './ModalSelectIncidentTypes';
|
|
30
|
+
import ModalSelectKnownCustomer from './ModalSelectKnownCustomer';
|
|
31
|
+
import ModalSelectWitness from './ModalSelectWitness';
|
|
32
|
+
import ModalDescribeCustomer from './ModalDescribeCustomer';
|
|
33
|
+
import ModalTrespass from './ModalTrespass';
|
|
34
|
+
import ModalCustomerDetails from './ModalCustomerDetails';
|
|
35
|
+
import ModalAddMedia from './ModalAddMedia';
|
|
36
|
+
import CreateMedia from './CreateMedia';
|
|
37
|
+
import GetLocations from './GetLocations';
|
|
38
|
+
import GetSelf from './GetSelf';
|
|
39
|
+
import CreateReport from './CreateReport';
|
|
40
|
+
import makeId from '../../settings/helpers/makeId';
|
|
41
|
+
import ThumbnailTempPreSave from './ThumbnailTempPreSave';
|
|
42
|
+
import ModalCustomWitness from './ModalCustomWitness';
|
|
43
|
+
import GetTrespassTemplates from '../../settings/GetTrespassTemplates';
|
|
44
|
+
import GetTrespassReasons from '../../settings/GetTrespassReasons';
|
|
45
|
+
import stripHTML from './helpers/stripHTML';
|
|
46
|
+
import getTodayDate from './helpers/getTodayDate';
|
|
47
|
+
import isValidDateFormat from './helpers/isValidDateFormat';
|
|
48
|
+
import isValidTimeInput from './helpers/isValidTimeInput';
|
|
49
|
+
import { isSameHtml } from './helpers/isSameHtml.js';
|
|
50
|
+
// format to local date at midnight and one second in UTC ISO:
|
|
51
|
+
import formatDateToUTCISO from './helpers/formatDateToUTCISO';
|
|
52
|
+
// format for dateTimeOfIncident:
|
|
53
|
+
import formatDateAndTimeToUTCISO from './helpers/formatDateAndTimeToUTCISO';
|
|
54
|
+
import getCurrentTime from './helpers/getCurrentTime';
|
|
55
|
+
import hasFormChangedAtCreate from './helpers/hasFormChangedAtCreate.js';
|
|
56
|
+
import ModalDirtyFormWarn from './ModalDirtyFormWarn.js';
|
|
57
|
+
import ModalLinkIncident from './ModalLinkIncident.js';
|
|
58
|
+
import GetSummary from './GetSummary.js';
|
|
59
|
+
import LinkedIncident from './LinkedIncident.js';
|
|
60
|
+
|
|
61
|
+
import { useIncidents } from '../../contexts/IncidentContext';
|
|
62
|
+
import {
|
|
63
|
+
generateTrespassDocuments,
|
|
64
|
+
generatePDFAttachments
|
|
65
|
+
} from './helpers/trespassDocUtils.js';
|
|
66
|
+
|
|
67
|
+
const CreatePane = () => {
|
|
68
|
+
const history = useHistory();
|
|
69
|
+
const intl = useIntl();
|
|
70
|
+
const {
|
|
71
|
+
openModalSelectTypes,
|
|
72
|
+
closeCreatePane,
|
|
73
|
+
openModalUnknownCust,
|
|
74
|
+
openModalSelectKnownCust,
|
|
75
|
+
openModalSelectWitness,
|
|
76
|
+
openModalMedia,
|
|
77
|
+
idForMediaCreate,
|
|
78
|
+
setIdForMediaCreate,
|
|
79
|
+
formDataArrayForMediaCreate,
|
|
80
|
+
setFormDataArrayForMediaCreate,
|
|
81
|
+
selectedCustomers,
|
|
82
|
+
setSelectedCustomers,
|
|
83
|
+
selectedWitnesses,
|
|
84
|
+
setSelectedWitnesses,
|
|
85
|
+
setAttachmentsData,
|
|
86
|
+
self,
|
|
87
|
+
openModalTrespass,
|
|
88
|
+
openModalCustomerDetails,
|
|
89
|
+
incidentTypesList,
|
|
90
|
+
openModalCustomWitness,
|
|
91
|
+
isCreatingReport,
|
|
92
|
+
setIsCreatingReport,
|
|
93
|
+
locationsInService,
|
|
94
|
+
trespassTemplates,
|
|
95
|
+
triggerDocumentError,
|
|
96
|
+
trespassReasons
|
|
97
|
+
} = useIncidents();
|
|
98
|
+
|
|
99
|
+
const [linkedToSummaries, setLinkedToSummaries] = useState([]);// built from 'selectedIds'
|
|
100
|
+
const [selectedIds, setSelectedIds] = useState(() => new Set());// linkedTo ids
|
|
101
|
+
const [showModalLinkIncident, setShowModalLinkIncident] = useState(false);
|
|
102
|
+
const [trespassCustomerID, setTrespassCustomerID] = useState(null);
|
|
103
|
+
const [detailsCustomerID, setDetailsCustomerID] = useState(null);
|
|
104
|
+
const [postData, setPostData] = useState({});
|
|
105
|
+
const [subLocationsDataOptions, setSubLocationsDataOptions] = useState([]);
|
|
106
|
+
const [custWitEditID, setCustWitEditID] = useState('');
|
|
107
|
+
const [isNoCustomer, setIsNoCustomer] = useState(false);
|
|
108
|
+
const [trespassTemplate, setTrespassTemplate] = useState('');
|
|
109
|
+
const [showDirtyFormModal, setShowDirtyFormModal] = useState(false);
|
|
110
|
+
const editorWasTouchedRef = useRef(false);
|
|
111
|
+
const initialFormData = useRef({
|
|
112
|
+
customerNa: false,
|
|
113
|
+
customers: [],
|
|
114
|
+
incidentLocation: '',
|
|
115
|
+
subLocation: '',
|
|
116
|
+
dateOfIncident: getTodayDate(),
|
|
117
|
+
timeOfIncident: getCurrentTime(),
|
|
118
|
+
isApproximateTime: false,
|
|
119
|
+
detailedDescriptionOfIncident: '',
|
|
120
|
+
incidentWitnesses: [],
|
|
121
|
+
incidentTypes: [],
|
|
122
|
+
attachments: [],
|
|
123
|
+
linkedTo: [],
|
|
124
|
+
id: 'abcd1234-abcd-4bcd-8def-0123456789ab',
|
|
125
|
+
}).current;
|
|
126
|
+
const [formData, setFormData] = useState(initialFormData);
|
|
127
|
+
|
|
128
|
+
const hasFormChanged = () => hasFormChangedAtCreate({
|
|
129
|
+
formData,
|
|
130
|
+
initialFormData,
|
|
131
|
+
selectedCustomers,
|
|
132
|
+
selectedWitnesses,
|
|
133
|
+
selectedIds,
|
|
134
|
+
editorWasTouched: editorWasTouchedRef.current,
|
|
135
|
+
});
|
|
136
|
+
|
|
137
|
+
const idsArray = useMemo(
|
|
138
|
+
() => Array.from(selectedIds).sort(),
|
|
139
|
+
[selectedIds]
|
|
140
|
+
);
|
|
141
|
+
|
|
142
|
+
useEffect(() => {
|
|
143
|
+
if (trespassTemplates) {
|
|
144
|
+
const defaultTemplate = trespassTemplates.find((template) => {
|
|
145
|
+
return template.isDefault === true;
|
|
146
|
+
});
|
|
147
|
+
if (defaultTemplate) {
|
|
148
|
+
const templateValue = defaultTemplate.templateValue
|
|
149
|
+
setTrespassTemplate(templateValue)
|
|
150
|
+
};
|
|
151
|
+
};
|
|
152
|
+
}, [trespassTemplates]);
|
|
153
|
+
|
|
154
|
+
// useEffect(() => {
|
|
155
|
+
// console.log("formData: ", JSON.stringify(formData, null, 2))
|
|
156
|
+
// }, [formData]);
|
|
157
|
+
|
|
158
|
+
const toggleRowChecked = useCallback((id) => {
|
|
159
|
+
setSelectedIds(prev => {
|
|
160
|
+
const nextSet = new Set(prev);
|
|
161
|
+
nextSet.has(id) ? nextSet.delete(id) : nextSet.add(id);
|
|
162
|
+
// console.log('current checked --> ', JSON.stringify([...nextSet]));
|
|
163
|
+
return nextSet;
|
|
164
|
+
})
|
|
165
|
+
}, []);
|
|
166
|
+
|
|
167
|
+
const thumbnailStyle = { width: '100px', height: 'auto', objectFit: 'cover'};
|
|
168
|
+
|
|
169
|
+
// is leveraged by UI and Handlebars 'formatLocation' helper
|
|
170
|
+
const locationDataOptions = useMemo(() => {
|
|
171
|
+
const defaultValueLabel = [{
|
|
172
|
+
value: '',
|
|
173
|
+
label: <FormattedMessage
|
|
174
|
+
id="create-pane.locationDataOptions-label-select-location"/>
|
|
175
|
+
}];
|
|
176
|
+
const formattedLocations = locationsInService
|
|
177
|
+
? locationsInService.map((loc) => ({
|
|
178
|
+
value: loc.id,
|
|
179
|
+
label: loc.location,
|
|
180
|
+
subLocations: loc.subLocations ? loc.subLocations : []
|
|
181
|
+
}))
|
|
182
|
+
: [{
|
|
183
|
+
value: '',
|
|
184
|
+
label: <FormattedMessage
|
|
185
|
+
id="create-pane.locationDataOptions-label-no-loaded"/>
|
|
186
|
+
}];
|
|
187
|
+
// console.log("formattedLocations: ", JSON.stringify(formattedLocations, null, 2))
|
|
188
|
+
return [
|
|
189
|
+
...defaultValueLabel,
|
|
190
|
+
...formattedLocations,
|
|
191
|
+
];
|
|
192
|
+
}, [locationsInService]);
|
|
193
|
+
|
|
194
|
+
const runSubLocationsSelect = (value) => {
|
|
195
|
+
let subLocs;
|
|
196
|
+
let options;
|
|
197
|
+
const noSubLocationOption = [
|
|
198
|
+
{
|
|
199
|
+
value: 'No sub-location',
|
|
200
|
+
label: <FormattedMessage
|
|
201
|
+
id="create-pane.subLocations-label-default-no-sub-location"/>
|
|
202
|
+
},
|
|
203
|
+
];
|
|
204
|
+
const noValueLabel = [
|
|
205
|
+
{
|
|
206
|
+
value: 'No sub-location',
|
|
207
|
+
label: <FormattedMessage
|
|
208
|
+
id="create-pane.subLocations-label-no-sub-location-available"
|
|
209
|
+
/>
|
|
210
|
+
},
|
|
211
|
+
];
|
|
212
|
+
const currentValue = locationDataOptions.find((loc) => loc.value === value);
|
|
213
|
+
|
|
214
|
+
if (currentValue && currentValue.subLocations && currentValue.subLocations.length > 0) {
|
|
215
|
+
subLocs = currentValue.subLocations.map((sub) => {
|
|
216
|
+
return { value: sub.name, label: `${sub.name} - ${sub.description}` };
|
|
217
|
+
});
|
|
218
|
+
options = [...noSubLocationOption, ...subLocs];
|
|
219
|
+
} else {
|
|
220
|
+
options = [...noValueLabel];
|
|
221
|
+
}
|
|
222
|
+
setSubLocationsDataOptions(options);
|
|
223
|
+
};
|
|
224
|
+
|
|
225
|
+
const handleChange = (eventOrValue) => {
|
|
226
|
+
let name;
|
|
227
|
+
let value;
|
|
228
|
+
if (eventOrValue && eventOrValue.target) {
|
|
229
|
+
({ name, value } = eventOrValue.target);
|
|
230
|
+
} else {
|
|
231
|
+
// handles if no 'target' property in custom component, such as
|
|
232
|
+
// ( has array of selected options, not event object)
|
|
233
|
+
name = 'incidentWitnesses';
|
|
234
|
+
value = eventOrValue;
|
|
235
|
+
}
|
|
236
|
+
if (name === 'incidentWitnesses') {
|
|
237
|
+
const selectedRoles = value.map((item) => item.value);
|
|
238
|
+
const updatedWitnesses = formData.incidentWitnesses.map((witness) => ({
|
|
239
|
+
...witness,
|
|
240
|
+
selected: selectedRoles.includes(witness.role),
|
|
241
|
+
}));
|
|
242
|
+
setFormData((prev) => ({
|
|
243
|
+
...prev,
|
|
244
|
+
incidentWitnesses: updatedWitnesses,
|
|
245
|
+
}));
|
|
246
|
+
}
|
|
247
|
+
if (name === 'incidentLocation') {
|
|
248
|
+
runSubLocationsSelect(value);
|
|
249
|
+
setFormData((prev) => ({
|
|
250
|
+
...prev,
|
|
251
|
+
[name]: value,
|
|
252
|
+
}));
|
|
253
|
+
} if (name === 'isApproximateTime') {
|
|
254
|
+
setFormData((prev) => ({
|
|
255
|
+
...prev,
|
|
256
|
+
[name]: eventOrValue.target.checked,
|
|
257
|
+
}));
|
|
258
|
+
} else {
|
|
259
|
+
setFormData((prev) => ({
|
|
260
|
+
...prev,
|
|
261
|
+
[name]: value,
|
|
262
|
+
}));
|
|
263
|
+
}
|
|
264
|
+
};
|
|
265
|
+
|
|
266
|
+
/*
|
|
267
|
+
Keep current HTML in a ref so keystrokes update w/out setting state.
|
|
268
|
+
This prevents react-quill's cleanup <-> setState feedback loop that otherwise
|
|
269
|
+
causes maximum update depth exceeded error when links are present in editor.
|
|
270
|
+
*/
|
|
271
|
+
// local unsanitized buffer - doesn't trigger React re-renders
|
|
272
|
+
const draftRef = useRef(formData.detailedDescriptionOfIncident);
|
|
273
|
+
|
|
274
|
+
// fire on every key-press but only mutautes the ref
|
|
275
|
+
const handleEditorChange = (content) => {
|
|
276
|
+
draftRef.current = content;
|
|
277
|
+
if (!editorWasTouchedRef.current && content && content.trim() !== '') {
|
|
278
|
+
editorWasTouchedRef.current = true;
|
|
279
|
+
}
|
|
280
|
+
};
|
|
281
|
+
|
|
282
|
+
// commits once, with sanitized HTML
|
|
283
|
+
const handleEditorBlur = () => {
|
|
284
|
+
const sanitizedContent = DOMPurify.sanitize(draftRef.current);
|
|
285
|
+
setFormData(prev =>
|
|
286
|
+
isSameHtml(prev.detailedDescriptionOfIncident, sanitizedContent)
|
|
287
|
+
? prev
|
|
288
|
+
: { ...prev, detailedDescriptionOfIncident: sanitizedContent}
|
|
289
|
+
);
|
|
290
|
+
};
|
|
291
|
+
|
|
292
|
+
const handleCustomerNa = (event) => {
|
|
293
|
+
setFormData((prev) => ({
|
|
294
|
+
...prev,
|
|
295
|
+
customerNa: event.target.checked,
|
|
296
|
+
}));
|
|
297
|
+
setIsNoCustomer(prev => !prev );
|
|
298
|
+
};
|
|
299
|
+
|
|
300
|
+
const handleDismiss = () => {
|
|
301
|
+
if (hasFormChanged()) {
|
|
302
|
+
setShowDirtyFormModal(true);
|
|
303
|
+
} else {
|
|
304
|
+
handleCloseOnCancelDismiss();
|
|
305
|
+
}
|
|
306
|
+
};
|
|
307
|
+
|
|
308
|
+
const handleKeepEditing = () => {
|
|
309
|
+
setShowDirtyFormModal(false);
|
|
310
|
+
};
|
|
311
|
+
|
|
312
|
+
const handleDismissOnDirty = () => {
|
|
313
|
+
handleCloseOnCancelDismiss();
|
|
314
|
+
};
|
|
315
|
+
|
|
316
|
+
const handleCloseOnCancelDismiss = () => {
|
|
317
|
+
setIdForMediaCreate(null);
|
|
318
|
+
setFormDataArrayForMediaCreate(null);
|
|
319
|
+
setAttachmentsData([]);
|
|
320
|
+
setSelectedCustomers([]);
|
|
321
|
+
setSelectedWitnesses([]);
|
|
322
|
+
closeCreatePane();
|
|
323
|
+
history.push('/incidents');
|
|
324
|
+
};
|
|
325
|
+
|
|
326
|
+
const handleCloseNewOnSuccess = (id) => {
|
|
327
|
+
closeCreatePane();
|
|
328
|
+
history.push(`/incidents/${id}`);
|
|
329
|
+
};
|
|
330
|
+
|
|
331
|
+
const handleSubmit = async () => {
|
|
332
|
+
try {
|
|
333
|
+
const formattedCustomers = selectedCustomers.map((cust) => {
|
|
334
|
+
const customer = {
|
|
335
|
+
id: cust.id,
|
|
336
|
+
barcode: cust.barcode,
|
|
337
|
+
firstName: cust.firstName,
|
|
338
|
+
lastName: cust.lastName,
|
|
339
|
+
description: cust.description ? cust.description : '',
|
|
340
|
+
registered: cust.registered,
|
|
341
|
+
};
|
|
342
|
+
if (cust.trespass) {
|
|
343
|
+
customer.trespass = cust.trespass;
|
|
344
|
+
}
|
|
345
|
+
if (cust.details) {
|
|
346
|
+
customer.details = cust.details;
|
|
347
|
+
}
|
|
348
|
+
return customer;
|
|
349
|
+
});
|
|
350
|
+
|
|
351
|
+
const formattedWitnesses = selectedWitnesses.map((cust) => {
|
|
352
|
+
return {
|
|
353
|
+
id: cust.id,
|
|
354
|
+
firstName: cust.firstName,
|
|
355
|
+
lastName: cust.lastName,
|
|
356
|
+
...(cust.barcode && { barcode: cust.barcode }),
|
|
357
|
+
...(cust.role && { role: cust.role }),
|
|
358
|
+
...(cust.phone && { phone: cust.phone }),
|
|
359
|
+
...(cust.email && { email: cust.email }),
|
|
360
|
+
...(cust.isCustom && { isCustom: cust.isCustom })
|
|
361
|
+
};
|
|
362
|
+
});
|
|
363
|
+
|
|
364
|
+
const customersList =
|
|
365
|
+
formattedCustomers.length > 0 ? formattedCustomers : [];
|
|
366
|
+
|
|
367
|
+
const allCustomersSet = customersList.map((cust) => {
|
|
368
|
+
let updatedCustomer = { ...cust };
|
|
369
|
+
if (cust.trespass) {
|
|
370
|
+
const trespassDescriptionRaw = cust.trespass.description || '';
|
|
371
|
+
const sanitizedCustomDesc = DOMPurify.sanitize(trespassDescriptionRaw);
|
|
372
|
+
const rawText = decode(sanitizedCustomDesc)
|
|
373
|
+
.replace(/<\/?[^>]+>/g, '')
|
|
374
|
+
.trim();
|
|
375
|
+
|
|
376
|
+
const useCustomDescription = rawText !== '';
|
|
377
|
+
if (!useCustomDescription && cust.trespass.description) {
|
|
378
|
+
// remove unused key
|
|
379
|
+
delete cust.trespass.description
|
|
380
|
+
}
|
|
381
|
+
updatedCustomer = {
|
|
382
|
+
...updatedCustomer,
|
|
383
|
+
trespass: {
|
|
384
|
+
...cust.trespass,
|
|
385
|
+
...(cust.trespass.dateOfBirth
|
|
386
|
+
? { dateOfBirth: formatDateToUTCISO(cust.trespass.dateOfBirth) }
|
|
387
|
+
: {}),
|
|
388
|
+
dateOfOccurrence: formatDateToUTCISO(formData.dateOfIncident),
|
|
389
|
+
...(cust.trespass.endDateOfTrespass
|
|
390
|
+
? {
|
|
391
|
+
endDateOfTrespass: formatDateToUTCISO(cust.trespass.endDateOfTrespass, 1),
|
|
392
|
+
}
|
|
393
|
+
: {}),
|
|
394
|
+
...(cust.trespass.declarationOfService
|
|
395
|
+
? {
|
|
396
|
+
declarationOfService: {
|
|
397
|
+
...cust.trespass.declarationOfService,
|
|
398
|
+
date: formatDateToUTCISO(
|
|
399
|
+
cust.trespass.declarationOfService.date
|
|
400
|
+
),
|
|
401
|
+
},
|
|
402
|
+
}
|
|
403
|
+
: {}),
|
|
404
|
+
/*
|
|
405
|
+
Use custom 'trespass.description' if it has meaningful text,
|
|
406
|
+
otherwise default to top level key 'detailedDescriptionOfIncident' for populating 'descriptionOfOccurrence'.
|
|
407
|
+
*/
|
|
408
|
+
descriptionOfOccurrence: useCustomDescription
|
|
409
|
+
? sanitizedCustomDesc
|
|
410
|
+
: formData.detailedDescriptionOfIncident,
|
|
411
|
+
...(useCustomDescription && { description: sanitizedCustomDesc }),
|
|
412
|
+
witnessedBy: formattedWitnesses,
|
|
413
|
+
},
|
|
414
|
+
};
|
|
415
|
+
}
|
|
416
|
+
|
|
417
|
+
|
|
418
|
+
if (cust.details) {
|
|
419
|
+
const { dateOfBirth, ...restDetails } = cust.details;
|
|
420
|
+
|
|
421
|
+
updatedCustomer = {
|
|
422
|
+
...updatedCustomer,
|
|
423
|
+
details: {
|
|
424
|
+
...restDetails,
|
|
425
|
+
...(dateOfBirth ?
|
|
426
|
+
{ dateOfBirth: formatDateToUTCISO(cust.details.dateOfBirth) }
|
|
427
|
+
: {}),
|
|
428
|
+
},
|
|
429
|
+
};
|
|
430
|
+
}
|
|
431
|
+
// console.log("updatedCustomer: ", JSON.stringify(updatedCustomer, null, 2))
|
|
432
|
+
return updatedCustomer;
|
|
433
|
+
});
|
|
434
|
+
|
|
435
|
+
const readyToBeSaved = formData.attachments.map((mediaObj) => {
|
|
436
|
+
const {id, file, description, contentType} = mediaObj
|
|
437
|
+
return {
|
|
438
|
+
contentType: contentType,
|
|
439
|
+
description: description,
|
|
440
|
+
id: id,
|
|
441
|
+
file: file,
|
|
442
|
+
}
|
|
443
|
+
});
|
|
444
|
+
|
|
445
|
+
const linkedToArray = Array.from(selectedIds);
|
|
446
|
+
|
|
447
|
+
const data = {
|
|
448
|
+
...formData,
|
|
449
|
+
linkedTo: linkedToArray,
|
|
450
|
+
attachments: readyToBeSaved,
|
|
451
|
+
customers: allCustomersSet,
|
|
452
|
+
dateTimeOfIncident: formatDateAndTimeToUTCISO(formData.dateOfIncident, formData.timeOfIncident),
|
|
453
|
+
incidentWitnesses: formattedWitnesses,
|
|
454
|
+
createdBy: {
|
|
455
|
+
barcode: self.barcode ? self.barcode : '',
|
|
456
|
+
id: self.id,
|
|
457
|
+
lastName: self.lastName,
|
|
458
|
+
firstName: self.firstName,
|
|
459
|
+
},
|
|
460
|
+
};
|
|
461
|
+
|
|
462
|
+
const helperDeps = { locationDataOptions, trespassReasons, self, triggerDocumentError};
|
|
463
|
+
|
|
464
|
+
// generate trespass documents
|
|
465
|
+
let readyTrespassDocuments = [];
|
|
466
|
+
try {
|
|
467
|
+
readyTrespassDocuments = generateTrespassDocuments(
|
|
468
|
+
allCustomersSet,
|
|
469
|
+
data,
|
|
470
|
+
trespassTemplate,
|
|
471
|
+
helperDeps
|
|
472
|
+
);
|
|
473
|
+
} catch (error) {
|
|
474
|
+
console.error(`Error at readyTrespassDocuments: ${error}`);
|
|
475
|
+
// triggerDocumentError(`Error in generateTrespassDocuments: ${error}`)
|
|
476
|
+
const errorMsg = error.message;
|
|
477
|
+
triggerDocumentError(<FormattedMessage
|
|
478
|
+
id="generate-trespass.error-doc-readyTrespassDocuments"
|
|
479
|
+
values={{ error: errorMsg }}
|
|
480
|
+
/>)
|
|
481
|
+
readyTrespassDocuments = [];
|
|
482
|
+
};
|
|
483
|
+
|
|
484
|
+
let trespassDocumentPDFs = [];
|
|
485
|
+
try {
|
|
486
|
+
trespassDocumentPDFs = await generatePDFAttachments(
|
|
487
|
+
readyTrespassDocuments,
|
|
488
|
+
triggerDocumentError
|
|
489
|
+
);
|
|
490
|
+
} catch (error) {
|
|
491
|
+
console.error(`Unexpected error in PDF generation: ${error}`);
|
|
492
|
+
// triggerDocumentError(`Unexpected error in PDF generation: ${error}`)
|
|
493
|
+
const errorMsg = error.message;
|
|
494
|
+
triggerDocumentError(<FormattedMessage
|
|
495
|
+
id="generate-trespass.error-doc-unexpected-error"
|
|
496
|
+
values={{ error: errorMsg }}
|
|
497
|
+
/>)
|
|
498
|
+
trespassDocumentPDFs = [];
|
|
499
|
+
};
|
|
500
|
+
|
|
501
|
+
const finalMergedAttachments = [...readyToBeSaved, ...trespassDocumentPDFs];
|
|
502
|
+
|
|
503
|
+
delete data.dateOfIncident;
|
|
504
|
+
delete data.timeOfIncident;
|
|
505
|
+
|
|
506
|
+
const finalData = {
|
|
507
|
+
...data,
|
|
508
|
+
// CreateReport will unpack attachments and pass to CreateMedia on POST success
|
|
509
|
+
attachments: finalMergedAttachments
|
|
510
|
+
};
|
|
511
|
+
|
|
512
|
+
if (formData.incidentTypes && formData.incidentTypes.length > 0) {
|
|
513
|
+
data.incidentTypes = formData.incidentTypes;
|
|
514
|
+
}
|
|
515
|
+
// console.log("@CREATE - finalData at save: ", JSON.stringify(finalData, null, 2))
|
|
516
|
+
setIsCreatingReport(true);
|
|
517
|
+
setPostData(finalData);
|
|
518
|
+
setSelectedCustomers([]);
|
|
519
|
+
setSelectedWitnesses([]);
|
|
520
|
+
} catch (error) {
|
|
521
|
+
console.error('error in submit. error: ', error)
|
|
522
|
+
};
|
|
523
|
+
};
|
|
524
|
+
|
|
525
|
+
const parseMMDDYYYY = (dateString) => {
|
|
526
|
+
const [month, day, year] = dateString.split('/').map((val) => parseInt(val, 10));
|
|
527
|
+
return new Date(year, month - 1, day);
|
|
528
|
+
};
|
|
529
|
+
|
|
530
|
+
const dateIsNotInFuture = (dateString) => {
|
|
531
|
+
const todayString = getTodayDate();
|
|
532
|
+
const todayDate = parseMMDDYYYY(todayString);
|
|
533
|
+
|
|
534
|
+
todayDate.setHours(0,0,0,0);
|
|
535
|
+
|
|
536
|
+
const formDataDate = parseMMDDYYYY(dateString);
|
|
537
|
+
|
|
538
|
+
if (formDataDate <= todayDate) {
|
|
539
|
+
return true
|
|
540
|
+
} else if (formDataDate > todayDate){
|
|
541
|
+
return false
|
|
542
|
+
};
|
|
543
|
+
};
|
|
544
|
+
|
|
545
|
+
const isFormDataValid = () => {
|
|
546
|
+
const isCustomersPresent =
|
|
547
|
+
selectedCustomers && selectedCustomers.length > 0 || isNoCustomer === true;
|
|
548
|
+
|
|
549
|
+
const isIncidentDetailsPresent = formData.incidentLocation &&
|
|
550
|
+
formData.incidentLocation !== '' &&
|
|
551
|
+
formData.dateOfIncident && isValidDateFormat(formData.dateOfIncident) && dateIsNotInFuture(formData.dateOfIncident) &&
|
|
552
|
+
stripHTML(formData.detailedDescriptionOfIncident);
|
|
553
|
+
|
|
554
|
+
const isIncidentTypeSelected =
|
|
555
|
+
formData.incidentTypes && formData.incidentTypes.length > 0;
|
|
556
|
+
|
|
557
|
+
const isWitnessSelected = selectedWitnesses && selectedWitnesses.length > 0;
|
|
558
|
+
|
|
559
|
+
const isTimeValid = formData.timeOfIncident &&
|
|
560
|
+
formData.timeOfIncident !== '' && isValidTimeInput(formData.timeOfIncident);
|
|
561
|
+
|
|
562
|
+
return (
|
|
563
|
+
isCustomersPresent &&
|
|
564
|
+
isIncidentDetailsPresent &&
|
|
565
|
+
isIncidentTypeSelected &&
|
|
566
|
+
isWitnessSelected &&
|
|
567
|
+
isTimeValid
|
|
568
|
+
);
|
|
569
|
+
};
|
|
570
|
+
|
|
571
|
+
const handleIncidentTypeToggle = (type) => {
|
|
572
|
+
setFormData((prevFormData) => {
|
|
573
|
+
const currentTypes = new Set(prevFormData.incidentTypes.map(t => t.id));
|
|
574
|
+
if(currentTypes.has(type.id)) {
|
|
575
|
+
return {
|
|
576
|
+
...prevFormData,
|
|
577
|
+
incidentTypes: prevFormData.incidentTypes.filter(t => t.id !== type.id)
|
|
578
|
+
};
|
|
579
|
+
} else {
|
|
580
|
+
return {
|
|
581
|
+
...prevFormData,
|
|
582
|
+
incidentTypes: [...prevFormData.incidentTypes, type]
|
|
583
|
+
}
|
|
584
|
+
}
|
|
585
|
+
})
|
|
586
|
+
};
|
|
587
|
+
|
|
588
|
+
// handle rendering inc type 'title' via associated key of 'id'
|
|
589
|
+
// instead of the instance's inc type 'title'
|
|
590
|
+
const preparedIncidentTypes = useMemo(() => {
|
|
591
|
+
return formData.incidentTypes.map(incidentType => {
|
|
592
|
+
const foundType = incidentTypesList.find(type => type.id === incidentType.id);
|
|
593
|
+
return {
|
|
594
|
+
id: incidentType.id,
|
|
595
|
+
title: foundType ? foundType.title : "unknown"
|
|
596
|
+
};
|
|
597
|
+
});
|
|
598
|
+
}, [formData.incidentTypes, incidentTypesList]);
|
|
599
|
+
|
|
600
|
+
const handleRemoveType = (typeId) => {
|
|
601
|
+
const updatedIncidentTypes = formData.incidentTypes.filter(
|
|
602
|
+
(type) => type.id !== typeId
|
|
603
|
+
);
|
|
604
|
+
setFormData((prevFormData) => {
|
|
605
|
+
return {
|
|
606
|
+
...prevFormData,
|
|
607
|
+
incidentTypes: updatedIncidentTypes,
|
|
608
|
+
};
|
|
609
|
+
});
|
|
610
|
+
};
|
|
611
|
+
|
|
612
|
+
const handleRemoveSelectedCustomer = (id) => {
|
|
613
|
+
const updatedSelectedCustomers = selectedCustomers.filter(
|
|
614
|
+
(cust) => cust.id !== id
|
|
615
|
+
);
|
|
616
|
+
setSelectedCustomers(updatedSelectedCustomers);
|
|
617
|
+
};
|
|
618
|
+
|
|
619
|
+
const handleRemoveSelectedWitness = (id) => {
|
|
620
|
+
const updatedSelectedWitnesses = selectedWitnesses.filter(
|
|
621
|
+
(cust) => cust.id !== id
|
|
622
|
+
);
|
|
623
|
+
setSelectedWitnesses(updatedSelectedWitnesses);
|
|
624
|
+
};
|
|
625
|
+
|
|
626
|
+
const handleOpenModalLinkIncident = () => {
|
|
627
|
+
setShowModalLinkIncident(true)
|
|
628
|
+
};
|
|
629
|
+
|
|
630
|
+
const handleCloseModalLinkIncident = () => {
|
|
631
|
+
setShowModalLinkIncident(false)
|
|
632
|
+
};
|
|
633
|
+
|
|
634
|
+
const handleTrashLinkedIncident = (toDeleteId) => {
|
|
635
|
+
toggleRowChecked(toDeleteId)
|
|
636
|
+
};
|
|
637
|
+
|
|
638
|
+
const handleAddMediaAtCreate = (mediaObj) => {
|
|
639
|
+
const readyMediaObj = {
|
|
640
|
+
...mediaObj,
|
|
641
|
+
id: makeId(mediaObj.description),
|
|
642
|
+
description: mediaObj.description.trim(),
|
|
643
|
+
};
|
|
644
|
+
setFormData((prevFormData) => ({
|
|
645
|
+
...prevFormData,
|
|
646
|
+
attachments: [...prevFormData.attachments, readyMediaObj]
|
|
647
|
+
}))
|
|
648
|
+
};
|
|
649
|
+
|
|
650
|
+
const handleRemoveUnsavedMediaCreate = (unsavedId) => {
|
|
651
|
+
setFormData((prevFormData) => ({
|
|
652
|
+
...prevFormData,
|
|
653
|
+
attachments: prevFormData.attachments.filter((obj) => obj.id !== unsavedId)
|
|
654
|
+
}))
|
|
655
|
+
};
|
|
656
|
+
|
|
657
|
+
const handleShowTrespassFormModal = (id) => {
|
|
658
|
+
setTrespassCustomerID(id);
|
|
659
|
+
openModalTrespass();
|
|
660
|
+
};
|
|
661
|
+
|
|
662
|
+
const handleShowCustomerDetailsFormModal = (id) => {
|
|
663
|
+
setDetailsCustomerID(id);
|
|
664
|
+
openModalCustomerDetails();
|
|
665
|
+
};
|
|
666
|
+
|
|
667
|
+
const handleAddSelfAsWitness = () => {
|
|
668
|
+
setSelectedWitnesses((prevState) => {
|
|
669
|
+
const isSelfAlreadyWitness = prevState.some(
|
|
670
|
+
wit => wit.id === self.id
|
|
671
|
+
);
|
|
672
|
+
if(isSelfAlreadyWitness) {
|
|
673
|
+
return prevState;
|
|
674
|
+
};
|
|
675
|
+
return [...prevState, self];
|
|
676
|
+
});
|
|
677
|
+
};
|
|
678
|
+
|
|
679
|
+
const itemFormatterIncidentType = (item) => {
|
|
680
|
+
return (
|
|
681
|
+
<li key={item.id}>
|
|
682
|
+
{item.title}
|
|
683
|
+
<button
|
|
684
|
+
style={{ paddingLeft: '8px' }}
|
|
685
|
+
onClick={() => handleRemoveType(item.id)}
|
|
686
|
+
aria-label={`Remove ${item.title}`}
|
|
687
|
+
type="button"
|
|
688
|
+
>
|
|
689
|
+
<Icon icon="trash" size="medium" />
|
|
690
|
+
</button>
|
|
691
|
+
</li>
|
|
692
|
+
);
|
|
693
|
+
};
|
|
694
|
+
|
|
695
|
+
const itemFormatterSelectedCustomers = (item) => {
|
|
696
|
+
const notAvailable = intl.formatMessage({ id: "unknown-name-placeholder" });
|
|
697
|
+
const firstName = item.firstName === '' ? notAvailable : item.firstName;
|
|
698
|
+
const lastName = item.lastName === '' ? notAvailable : item.lastName;
|
|
699
|
+
return (
|
|
700
|
+
<li key={item.id}>
|
|
701
|
+
{lastName}, {firstName}
|
|
702
|
+
<button
|
|
703
|
+
style={{ paddingLeft: '25px' }}
|
|
704
|
+
onClick={() => handleRemoveSelectedCustomer(item.id)}
|
|
705
|
+
type="button"
|
|
706
|
+
>
|
|
707
|
+
<Icon icon="trash" size="medium" /> <FormattedMessage id="remove-button"/>
|
|
708
|
+
</button>
|
|
709
|
+
{item.details || item.description ? (
|
|
710
|
+
<button
|
|
711
|
+
style={{ paddingLeft: '15px' }}
|
|
712
|
+
onClick={() => handleShowCustomerDetailsFormModal(item.id)}
|
|
713
|
+
type="button"
|
|
714
|
+
>
|
|
715
|
+
<Icon icon="report" size="medium" />
|
|
716
|
+
<FormattedMessage id="edit-details-button"/>
|
|
717
|
+
</button>
|
|
718
|
+
) : (
|
|
719
|
+
<button
|
|
720
|
+
style={{ paddingLeft: '15px' }}
|
|
721
|
+
onClick={() => handleShowCustomerDetailsFormModal(item.id)}
|
|
722
|
+
type="button"
|
|
723
|
+
>
|
|
724
|
+
<Icon icon="plus-sign" size="medium" />
|
|
725
|
+
<FormattedMessage id="add-details-button"/>
|
|
726
|
+
</button>
|
|
727
|
+
)}
|
|
728
|
+
{item.trespass ? (
|
|
729
|
+
<button
|
|
730
|
+
style={{ paddingLeft: '15px' }}
|
|
731
|
+
onClick={() => handleShowTrespassFormModal(item.id)}
|
|
732
|
+
type="button"
|
|
733
|
+
>
|
|
734
|
+
<Icon icon="report" size="medium" />
|
|
735
|
+
<FormattedMessage id="edit-trespass-button"/>
|
|
736
|
+
</button>
|
|
737
|
+
) : (
|
|
738
|
+
<button
|
|
739
|
+
style={{ paddingLeft: '15px' }}
|
|
740
|
+
onClick={() => handleShowTrespassFormModal(item.id)}
|
|
741
|
+
type="button"
|
|
742
|
+
>
|
|
743
|
+
<Icon icon="plus-sign" size="medium" />
|
|
744
|
+
<FormattedMessage id="add-trespass-button"/>
|
|
745
|
+
</button>
|
|
746
|
+
)}
|
|
747
|
+
</li>
|
|
748
|
+
);
|
|
749
|
+
};
|
|
750
|
+
|
|
751
|
+
const handleEditCustomWit = (witId) => {
|
|
752
|
+
setCustWitEditID(witId)
|
|
753
|
+
openModalCustomWitness()
|
|
754
|
+
};
|
|
755
|
+
|
|
756
|
+
const handleOpenCustomWitness = () => {
|
|
757
|
+
openModalCustomWitness()
|
|
758
|
+
};
|
|
759
|
+
|
|
760
|
+
const itemFormatterSelectedWitnesses = (item) => {
|
|
761
|
+
const isCustom = item.isCustom;
|
|
762
|
+
return (
|
|
763
|
+
<li key={item.id}>
|
|
764
|
+
{item.lastName}, {item.firstName}
|
|
765
|
+
<button
|
|
766
|
+
style={{ paddingLeft: '8px' }}
|
|
767
|
+
onClick={() => handleRemoveSelectedWitness(item.id)}
|
|
768
|
+
aria-label={`Remove ${item.lastName}, ${item.firstName}`}
|
|
769
|
+
type="button"
|
|
770
|
+
>
|
|
771
|
+
<Icon icon="trash" size="medium" />
|
|
772
|
+
</button>
|
|
773
|
+
{isCustom && (
|
|
774
|
+
<button
|
|
775
|
+
style={{ paddingLeft: '12px' }}
|
|
776
|
+
onClick={() => handleEditCustomWit(item.id)}
|
|
777
|
+
aria-label={`Edit ${item.lastName}, ${item.firstName}`}
|
|
778
|
+
type="button"
|
|
779
|
+
>
|
|
780
|
+
<FormattedMessage id="edit-button"/>
|
|
781
|
+
</button>)
|
|
782
|
+
}
|
|
783
|
+
</li>
|
|
784
|
+
);
|
|
785
|
+
};
|
|
786
|
+
|
|
787
|
+
const handleOpenModalMedia = () => {
|
|
788
|
+
openModalMedia();
|
|
789
|
+
};
|
|
790
|
+
|
|
791
|
+
const customersListLabel = intl.formatMessage(
|
|
792
|
+
{ id: 'customers-list-label' },
|
|
793
|
+
{ count: selectedCustomers.length }
|
|
794
|
+
);
|
|
795
|
+
|
|
796
|
+
const incidentTypesListLabel = intl.formatMessage(
|
|
797
|
+
{ id: 'incident-types-list-label' },
|
|
798
|
+
{ count: preparedIncidentTypes.length }
|
|
799
|
+
);
|
|
800
|
+
|
|
801
|
+
const witnessesListLabel = intl.formatMessage(
|
|
802
|
+
{ id: 'witnesses-list-label' },
|
|
803
|
+
{ count: selectedWitnesses.length,
|
|
804
|
+
bold: (chunks) => (
|
|
805
|
+
<strong style={{ color: '#A12A2A' }}>{chunks}</strong>
|
|
806
|
+
),
|
|
807
|
+
},
|
|
808
|
+
);
|
|
809
|
+
|
|
810
|
+
const footer = (
|
|
811
|
+
<PaneFooter
|
|
812
|
+
renderStart={
|
|
813
|
+
<Button onClick={handleDismiss}>
|
|
814
|
+
<FormattedMessage id="cancel-button" />
|
|
815
|
+
</Button>
|
|
816
|
+
}
|
|
817
|
+
renderEnd={
|
|
818
|
+
<Button
|
|
819
|
+
buttonStyle="primary"
|
|
820
|
+
onClick={handleSubmit}
|
|
821
|
+
disabled={!isFormDataValid()}
|
|
822
|
+
>
|
|
823
|
+
<FormattedMessage id="save-and-close-button" />
|
|
824
|
+
</Button>
|
|
825
|
+
}
|
|
826
|
+
/>
|
|
827
|
+
);
|
|
828
|
+
|
|
829
|
+
return (
|
|
830
|
+
<>
|
|
831
|
+
{idForMediaCreate && formDataArrayForMediaCreate && (
|
|
832
|
+
<CreateMedia
|
|
833
|
+
context="new"
|
|
834
|
+
id={idForMediaCreate}
|
|
835
|
+
formDataArray={formDataArrayForMediaCreate}
|
|
836
|
+
handleCloseNewOnSuccess={handleCloseNewOnSuccess}
|
|
837
|
+
/>
|
|
838
|
+
)}
|
|
839
|
+
{postData && (
|
|
840
|
+
<CreateReport
|
|
841
|
+
data={postData}
|
|
842
|
+
handleCloseNewOnSuccess={handleCloseNewOnSuccess}
|
|
843
|
+
/>
|
|
844
|
+
)}
|
|
845
|
+
|
|
846
|
+
{showDirtyFormModal && (
|
|
847
|
+
<ModalDirtyFormWarn
|
|
848
|
+
handleKeepEditing={handleKeepEditing}
|
|
849
|
+
handleDismissOnDirty={handleDismissOnDirty}
|
|
850
|
+
/>
|
|
851
|
+
)}
|
|
852
|
+
|
|
853
|
+
{isCreatingReport ? (
|
|
854
|
+
<LoadingPane
|
|
855
|
+
defaultWidth="fill"
|
|
856
|
+
paneTitle={<FormattedMessage id="create-pane.loading-pane-submit-paneTitle" />}
|
|
857
|
+
/>
|
|
858
|
+
) : (
|
|
859
|
+
<Pane
|
|
860
|
+
dismissible
|
|
861
|
+
defaultWidth="100%"
|
|
862
|
+
paneTitle={<FormattedMessage id="create-pane.paneTitle" />}
|
|
863
|
+
renderHeader={(renderProps) => (
|
|
864
|
+
<PaneHeader
|
|
865
|
+
{...renderProps}
|
|
866
|
+
dismissible
|
|
867
|
+
onClose={handleDismiss}
|
|
868
|
+
/>
|
|
869
|
+
)}
|
|
870
|
+
footer={footer}
|
|
871
|
+
>
|
|
872
|
+
|
|
873
|
+
<ModalAddMedia
|
|
874
|
+
context='create'
|
|
875
|
+
handleAddMediaAtCreate={handleAddMediaAtCreate}
|
|
876
|
+
/>
|
|
877
|
+
<ModalDescribeCustomer />
|
|
878
|
+
<ModalSelectKnownCustomer />
|
|
879
|
+
<ModalSelectWitness />
|
|
880
|
+
<GetSelf />
|
|
881
|
+
<ModalCustomWitness
|
|
882
|
+
custWitEditID={custWitEditID}
|
|
883
|
+
/>
|
|
884
|
+
|
|
885
|
+
<GetTrespassTemplates />
|
|
886
|
+
<GetTrespassReasons />
|
|
887
|
+
<GetLocations />
|
|
888
|
+
<GetLocationsInService />
|
|
889
|
+
<GetIncidentTypesDetails context='incidents'/>
|
|
890
|
+
<ModalSelectIncidentTypes
|
|
891
|
+
handleIncidentTypeToggle={handleIncidentTypeToggle}
|
|
892
|
+
formDataIncidentTypes={formData.incidentTypes}
|
|
893
|
+
/>
|
|
894
|
+
{trespassCustomerID &&
|
|
895
|
+
<ModalTrespass
|
|
896
|
+
customerID={trespassCustomerID}
|
|
897
|
+
modalContext='create-mode'
|
|
898
|
+
/>
|
|
899
|
+
}
|
|
900
|
+
{detailsCustomerID && (
|
|
901
|
+
<ModalCustomerDetails customerID={detailsCustomerID} />
|
|
902
|
+
)}
|
|
903
|
+
|
|
904
|
+
{showModalLinkIncident && (
|
|
905
|
+
<ModalLinkIncident
|
|
906
|
+
toggleRowChecked={toggleRowChecked}
|
|
907
|
+
ids={selectedIds}
|
|
908
|
+
setIds={setSelectedIds}
|
|
909
|
+
handleCloseModalLinkIncident={handleCloseModalLinkIncident}
|
|
910
|
+
/>
|
|
911
|
+
)}
|
|
912
|
+
|
|
913
|
+
<GetSummary
|
|
914
|
+
ids={idsArray}
|
|
915
|
+
onResult={setLinkedToSummaries}
|
|
916
|
+
/>
|
|
917
|
+
|
|
918
|
+
<AccordionSet>
|
|
919
|
+
<ExpandAllButton />
|
|
920
|
+
<Accordion
|
|
921
|
+
label={<FormattedMessage id="accordion-label-customer-information" />}
|
|
922
|
+
>
|
|
923
|
+
{selectedCustomers.length > 0 ? null
|
|
924
|
+
: <Row>
|
|
925
|
+
<Col xs={2} style={{ marginTop: '10px', marginLeft: '10px', marginBottom: '10px'}}>
|
|
926
|
+
<Checkbox
|
|
927
|
+
label={<FormattedMessage id="customer-not-available"/>}
|
|
928
|
+
name='customerNa'
|
|
929
|
+
onChange={handleCustomerNa}
|
|
930
|
+
/>
|
|
931
|
+
</Col>
|
|
932
|
+
</Row>}
|
|
933
|
+
|
|
934
|
+
{!isNoCustomer && (
|
|
935
|
+
<>
|
|
936
|
+
<Row>
|
|
937
|
+
<Col xs={3}>
|
|
938
|
+
<Button
|
|
939
|
+
onClick={openModalSelectKnownCust}
|
|
940
|
+
style={{ marginTop: '10px' }}
|
|
941
|
+
>
|
|
942
|
+
<FormattedMessage id="select-add-known-customer-button" />
|
|
943
|
+
</Button>
|
|
944
|
+
</Col>
|
|
945
|
+
</Row>
|
|
946
|
+
|
|
947
|
+
<Row>
|
|
948
|
+
<Col xs={3} style={{ marginTop: '10px' }}>
|
|
949
|
+
<Button onClick={openModalUnknownCust}>
|
|
950
|
+
<FormattedMessage id="describe-add-unknown-customer-button" />
|
|
951
|
+
</Button>
|
|
952
|
+
</Col>
|
|
953
|
+
</Row>
|
|
954
|
+
|
|
955
|
+
<Row>
|
|
956
|
+
<Col xs={9}>
|
|
957
|
+
<Label style={{ marginTop: '5px' }} size="medium" tag="h2">
|
|
958
|
+
<b>{customersListLabel}</b>
|
|
959
|
+
</Label>
|
|
960
|
+
<List
|
|
961
|
+
listStyle="bullets"
|
|
962
|
+
label={customersListLabel}
|
|
963
|
+
items={selectedCustomers}
|
|
964
|
+
isEmptyMessage={
|
|
965
|
+
<FormattedMessage
|
|
966
|
+
id="customers-list-is-empty-message"
|
|
967
|
+
values={{
|
|
968
|
+
bold: (chunks) => (
|
|
969
|
+
<strong style={{ color: '#A12A2A' }}>{chunks}</strong>
|
|
970
|
+
),
|
|
971
|
+
}}
|
|
972
|
+
/>
|
|
973
|
+
}
|
|
974
|
+
itemFormatter={itemFormatterSelectedCustomers}
|
|
975
|
+
/>
|
|
976
|
+
</Col>
|
|
977
|
+
</Row>
|
|
978
|
+
</>
|
|
979
|
+
)}
|
|
980
|
+
</Accordion>
|
|
981
|
+
|
|
982
|
+
<Accordion label={<FormattedMessage id="accordion-label-incident" />}>
|
|
983
|
+
<Row>
|
|
984
|
+
<Col xs={3}>
|
|
985
|
+
<Select
|
|
986
|
+
required
|
|
987
|
+
label={
|
|
988
|
+
<FormattedMessage id="create-pane.location-select-label" />
|
|
989
|
+
}
|
|
990
|
+
name="incidentLocation"
|
|
991
|
+
value={formData.incidentLocation}
|
|
992
|
+
dataOptions={locationDataOptions}
|
|
993
|
+
onChange={handleChange}
|
|
994
|
+
/>
|
|
995
|
+
</Col>
|
|
996
|
+
|
|
997
|
+
<Col xs={3}>
|
|
998
|
+
<Select
|
|
999
|
+
label={
|
|
1000
|
+
<FormattedMessage id="create-pane.sub-location-select-label" />
|
|
1001
|
+
}
|
|
1002
|
+
name="subLocation"
|
|
1003
|
+
value={formData.subLocation}
|
|
1004
|
+
dataOptions={subLocationsDataOptions}
|
|
1005
|
+
onChange={handleChange}
|
|
1006
|
+
/>
|
|
1007
|
+
</Col>
|
|
1008
|
+
</Row>
|
|
1009
|
+
|
|
1010
|
+
<Row style={{ marginTop: '25px' }}>
|
|
1011
|
+
<Col xs={3}>
|
|
1012
|
+
<Datepicker
|
|
1013
|
+
required
|
|
1014
|
+
name="dateOfIncident"
|
|
1015
|
+
value={formData.dateOfIncident}
|
|
1016
|
+
label={
|
|
1017
|
+
<FormattedMessage id="create-pane.date-of-incident-date-picker-label" />
|
|
1018
|
+
}
|
|
1019
|
+
onChange={handleChange}
|
|
1020
|
+
/>
|
|
1021
|
+
</Col>
|
|
1022
|
+
|
|
1023
|
+
<Col xs={2}>
|
|
1024
|
+
<Timepicker
|
|
1025
|
+
required
|
|
1026
|
+
name="timeOfIncident"
|
|
1027
|
+
value={formData.timeOfIncident}
|
|
1028
|
+
label={
|
|
1029
|
+
<FormattedMessage id="create-pane.time-of-incident-date-picker-label" />
|
|
1030
|
+
}
|
|
1031
|
+
onChange={handleChange}
|
|
1032
|
+
/>
|
|
1033
|
+
</Col>
|
|
1034
|
+
|
|
1035
|
+
<Col xs={2} style={{ marginTop: '25px' }}>
|
|
1036
|
+
<Checkbox
|
|
1037
|
+
label='Approximate time'
|
|
1038
|
+
name='isApproximateTime'
|
|
1039
|
+
onChange={handleChange}
|
|
1040
|
+
/>
|
|
1041
|
+
</Col>
|
|
1042
|
+
</Row>
|
|
1043
|
+
|
|
1044
|
+
<Row>
|
|
1045
|
+
<Col xs={4}>
|
|
1046
|
+
<Button
|
|
1047
|
+
onClick={openModalSelectTypes}
|
|
1048
|
+
style={{ marginTop: '15px' }}
|
|
1049
|
+
>
|
|
1050
|
+
<FormattedMessage id="create-pane.select-add-incident-type-button" />
|
|
1051
|
+
</Button>
|
|
1052
|
+
</Col>
|
|
1053
|
+
</Row>
|
|
1054
|
+
|
|
1055
|
+
<Row>
|
|
1056
|
+
<Col xs={4} style={{ paddingLeft: '20px' }}>
|
|
1057
|
+
<Label style={{ marginTop: '5px' }} size="medium" tag="h2">
|
|
1058
|
+
<b>{incidentTypesListLabel}</b>
|
|
1059
|
+
</Label>
|
|
1060
|
+
<List
|
|
1061
|
+
listStyle="bullets"
|
|
1062
|
+
label={incidentTypesListLabel}
|
|
1063
|
+
items={preparedIncidentTypes}
|
|
1064
|
+
isEmptyMessage={
|
|
1065
|
+
<FormattedMessage
|
|
1066
|
+
id="incident-types-list-is-empty-message"
|
|
1067
|
+
values={{
|
|
1068
|
+
bold: (chunks) => (
|
|
1069
|
+
<strong style={{ color: '#A12A2A' }}>{chunks}</strong>
|
|
1070
|
+
),
|
|
1071
|
+
}}
|
|
1072
|
+
/>
|
|
1073
|
+
}
|
|
1074
|
+
itemFormatter={itemFormatterIncidentType}
|
|
1075
|
+
/>
|
|
1076
|
+
</Col>
|
|
1077
|
+
</Row>
|
|
1078
|
+
|
|
1079
|
+
<Row style={{ marginTop: '25px' }}>
|
|
1080
|
+
<Col xs={6}>
|
|
1081
|
+
<Editor
|
|
1082
|
+
required
|
|
1083
|
+
label={<FormattedMessage id="create-pane-detailedDescriptionIncident-editor-label"/>}
|
|
1084
|
+
value={draftRef.current}
|
|
1085
|
+
onChange={handleEditorChange}
|
|
1086
|
+
onBlur={handleEditorBlur}
|
|
1087
|
+
/>
|
|
1088
|
+
</Col>
|
|
1089
|
+
</Row>
|
|
1090
|
+
|
|
1091
|
+
<Row>
|
|
1092
|
+
<Col xs={2} style={{ paddingTop: '25px' }}>
|
|
1093
|
+
<Button onClick={openModalSelectWitness}>
|
|
1094
|
+
<FormattedMessage id="select-add-witness-button" />
|
|
1095
|
+
</Button>
|
|
1096
|
+
</Col>
|
|
1097
|
+
|
|
1098
|
+
</Row>
|
|
1099
|
+
|
|
1100
|
+
<Row>
|
|
1101
|
+
<Col xs={2} style={{ paddingTop: '25px' }}>
|
|
1102
|
+
<Button onClick={handleAddSelfAsWitness}>
|
|
1103
|
+
<FormattedMessage id="add-self-witness-button" />
|
|
1104
|
+
</Button>
|
|
1105
|
+
</Col>
|
|
1106
|
+
</Row>
|
|
1107
|
+
|
|
1108
|
+
<Row>
|
|
1109
|
+
<Col xs={2} style={{ paddingTop: '25px' }}>
|
|
1110
|
+
<Button
|
|
1111
|
+
onClick={handleOpenCustomWitness}
|
|
1112
|
+
>
|
|
1113
|
+
<FormattedMessage id="add-custom-witness-button" />
|
|
1114
|
+
</Button>
|
|
1115
|
+
</Col>
|
|
1116
|
+
</Row>
|
|
1117
|
+
|
|
1118
|
+
<Row>
|
|
1119
|
+
<Col xs={2} style={{ paddingTop: '25px' }}>
|
|
1120
|
+
<Button onClick={handleOpenModalLinkIncident}>
|
|
1121
|
+
<FormattedMessage id="link-to-button" />
|
|
1122
|
+
</Button>
|
|
1123
|
+
</Col>
|
|
1124
|
+
</Row>
|
|
1125
|
+
|
|
1126
|
+
<Row>
|
|
1127
|
+
<Col xs={6} style={{ paddingTop: '20px' }}>
|
|
1128
|
+
<Label style={{ marginTop: '5px' }} size="medium" tag="h2">
|
|
1129
|
+
<FormattedMessage
|
|
1130
|
+
id="witnesses-list-label"
|
|
1131
|
+
values={{
|
|
1132
|
+
count: selectedWitnesses.length,
|
|
1133
|
+
bold: (chunks) => <strong>{chunks}</strong>,
|
|
1134
|
+
}}
|
|
1135
|
+
/>
|
|
1136
|
+
</Label>
|
|
1137
|
+
|
|
1138
|
+
<List
|
|
1139
|
+
listStyle="bullets"
|
|
1140
|
+
label={witnessesListLabel}
|
|
1141
|
+
items={selectedWitnesses}
|
|
1142
|
+
isEmptyMessage={
|
|
1143
|
+
<FormattedMessage
|
|
1144
|
+
id="witnesses-list-is-empty-message"
|
|
1145
|
+
values={{
|
|
1146
|
+
bold: (chunks) => (
|
|
1147
|
+
<strong style={{ color: '#A12A2A' }}>{chunks}</strong>
|
|
1148
|
+
),
|
|
1149
|
+
}}
|
|
1150
|
+
/>
|
|
1151
|
+
}
|
|
1152
|
+
itemFormatter={itemFormatterSelectedWitnesses}
|
|
1153
|
+
/>
|
|
1154
|
+
</Col>
|
|
1155
|
+
</Row>
|
|
1156
|
+
|
|
1157
|
+
{linkedToSummaries.length > 0 ? (
|
|
1158
|
+
<Row style={{ marginTop: '25px' }}>
|
|
1159
|
+
<Col xs={2}>
|
|
1160
|
+
<KeyValue
|
|
1161
|
+
label={<FormattedMessage id="linked-incidents-label"/>}
|
|
1162
|
+
value={
|
|
1163
|
+
<div style={{ display: 'grid', rowGap: '10px' }}>
|
|
1164
|
+
{linkedToSummaries.map((ltS) => (
|
|
1165
|
+
<LinkedIncident
|
|
1166
|
+
key={ltS.id}
|
|
1167
|
+
summaryObj={ltS}
|
|
1168
|
+
onDelete={handleTrashLinkedIncident}
|
|
1169
|
+
renderContext='create-edit'
|
|
1170
|
+
/>
|
|
1171
|
+
))}
|
|
1172
|
+
</div>
|
|
1173
|
+
}
|
|
1174
|
+
/>
|
|
1175
|
+
</Col>
|
|
1176
|
+
</Row>
|
|
1177
|
+
) : null}
|
|
1178
|
+
</Accordion>
|
|
1179
|
+
|
|
1180
|
+
<Accordion label={<FormattedMessage id="accordion-label-media" />}>
|
|
1181
|
+
<Row style={{ margin: '25px' }}>
|
|
1182
|
+
<Col xs={1} style={{ visibility: 'hidden' }}></Col>
|
|
1183
|
+
{formData.attachments.map((attachment) => (
|
|
1184
|
+
<Col xs={2} key={attachment.id}>
|
|
1185
|
+
<ThumbnailTempPreSave
|
|
1186
|
+
context='create'
|
|
1187
|
+
contentType={attachment.contentType}
|
|
1188
|
+
handleRemoveUnsavedMediaCreate={handleRemoveUnsavedMediaCreate}
|
|
1189
|
+
key={attachment.id}
|
|
1190
|
+
mediaId={attachment.id}
|
|
1191
|
+
src={attachment.filePreviewUrl}
|
|
1192
|
+
alt={attachment.description}
|
|
1193
|
+
imageDescription={attachment.description}
|
|
1194
|
+
style={thumbnailStyle}
|
|
1195
|
+
/>
|
|
1196
|
+
</Col>
|
|
1197
|
+
))}
|
|
1198
|
+
</Row>
|
|
1199
|
+
|
|
1200
|
+
<Row style={{ marginTop: '25px' }}>
|
|
1201
|
+
<Col xs={2}>
|
|
1202
|
+
<Button onClick={handleOpenModalMedia}>
|
|
1203
|
+
<FormattedMessage id="add-media-button" />
|
|
1204
|
+
</Button>
|
|
1205
|
+
</Col>
|
|
1206
|
+
</Row>
|
|
1207
|
+
</Accordion>
|
|
1208
|
+
</AccordionSet>
|
|
1209
|
+
</Pane>
|
|
1210
|
+
)}
|
|
1211
|
+
</>
|
|
1212
|
+
);
|
|
1213
|
+
};
|
|
1214
|
+
|
|
1215
|
+
export default CreatePane;
|