inviton-powerduck 0.0.154 → 0.0.155

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.
Files changed (60) hide show
  1. package/app/powerduck-initializer.ts +3 -3
  2. package/common/api-http.ts +20 -14
  3. package/common/css/ladda-themeless-zoomin.min.css +89 -89
  4. package/common/enum-translation/day-translator.ts +3 -2
  5. package/common/excel/excel-reader.ts +2 -9
  6. package/common/extensions/array-extensions.ts +116 -0
  7. package/common/extensions/string-extensions.ts +92 -0
  8. package/common/extensions/temporal-extensions.ts +115 -0
  9. package/common/scroll-utils.ts +2 -1
  10. package/common/temporal-helpers.ts +551 -0
  11. package/common/timezone-helper.ts +39 -29
  12. package/common/utils/cookie.ts +11 -8
  13. package/common/utils/date-localization-utils.ts +25 -19
  14. package/common/utils/date-utils.ts +37 -47
  15. package/common/utils/form-utils.ts +3 -1
  16. package/common/utils/language-utils.ts +21 -27
  17. package/common/utils/temporal-utils.ts +43 -0
  18. package/common/utils/upload-image-helper.ts +1 -1
  19. package/common/utils/utils.ts +14 -14
  20. package/common/validation.ts +17 -5
  21. package/components/chart-js/line-chart-flot.tsx +9 -9
  22. package/components/chart-js/thirdparty/flot/jquery.flot.categories.min.js +93 -93
  23. package/components/chart-js/thirdparty/flot/jquery.flot.crosshair.min.js +83 -83
  24. package/components/chart-js/thirdparty/flot/jquery.flot.navigate.min.js +270 -270
  25. package/components/chart-js/thirdparty/flot/jquery.flot.pie.min.js +507 -507
  26. package/components/chart-js/thirdparty/flot/jquery.flot.resize.js +7 -9
  27. package/components/chart-js/thirdparty/flot/jquery.flot.resize.min.js +9 -11
  28. package/components/chart-js/thirdparty/flot/jquery.flot.stack.min.js +104 -104
  29. package/components/chart-js/ts/line-chart-contracts.ts +2 -2
  30. package/components/container-with-breakpoints/ts/breakpoint-handler.ts +2 -2
  31. package/components/counter/testall.tsx +89 -75
  32. package/components/datatable/datatable.tsx +2379 -2375
  33. package/components/datatable/export-excel-modal.tsx +12 -14
  34. package/components/datatable/ts/reorder.ts +4 -2
  35. package/components/dropdown/index.tsx +48 -22
  36. package/components/dropdown/mobile/legacy_fdd.ts +10 -11
  37. package/components/dropzone/gallery-dropzone.tsx +394 -382
  38. package/components/fullcalendar/fullcalendar-draggable-event.tsx +8 -7
  39. package/components/fullcalendar/timegrid-calendar.tsx +60 -67
  40. package/components/image-crop/image-cropping-modal.tsx +9 -8
  41. package/components/image-crop/upload-and-crop.tsx +162 -162
  42. package/components/image-crop/vendor/jquery.Jcrop.min.css +344 -344
  43. package/components/import/import-mapper.tsx +2 -2
  44. package/components/input/daterange-picker.tsx +502 -521
  45. package/components/input/datetime-picker.tsx +45 -50
  46. package/components/input/plugins/daterangepicker/daterangepicker.min.css +400 -400
  47. package/components/input/plugins/daterangepicker/jquery.daterangepicker.min.js +346 -339
  48. package/components/input/plugins/daterangepicker/jquery.daterangepicker.ts +580 -402
  49. package/components/input/radio-button-group.tsx +2 -2
  50. package/components/input/ts/dateInputHelper.ts +1 -0
  51. package/components/input/wysiwig.tsx +12 -7
  52. package/components/svg/skilift-svg.tsx +6 -6
  53. package/package.json +2 -1
  54. package/common/date-wrapper.ts +0 -422
  55. package/common/utils/array-extend.ts +0 -215
  56. package/common/utils/array-remove.ts +0 -10
  57. package/common/utils/array-sort.ts +0 -56
  58. package/common/utils/capitalize-string.ts +0 -11
  59. package/common/utils/format-string.ts +0 -14
  60. package/common/utils/latinize-string.ts +0 -7
@@ -1,414 +1,426 @@
1
+ /* eslint-disable ts/no-this-alias */
2
+ /* eslint-disable no-var */
3
+ /* eslint-disable vars-on-top */
1
4
  import Dropzone from 'dropzone';
2
5
  import Sortable from 'sortablejs';
3
6
  import { Prop, toNative } from 'vue-facing-decorator';
4
7
  import PowerduckState from '../../app/powerduck-state';
5
8
  import TsxComponent, { Component } from '../../app/vuetsx';
6
- import { arrayRemove } from '../../common/utils/array-remove';
7
- import { arraySort } from '../../common/utils/array-sort';
8
9
  import StringUtils from '../../common/utils/string-utils';
9
10
  import Button from '../button/button';
10
11
  import { ButtonLayout } from '../button/button-layout';
11
12
  import 'dropzone/dist/min/dropzone.min.css';
12
13
  import './css/gallery-dropzone.css';
14
+ import { remove, sortBy } from '../../common/extensions/array-extensions';
13
15
 
14
16
  interface DropzoneFormItem {
15
- name: string;
16
- value: string;
17
+ name: string;
18
+ value: string;
17
19
  }
18
20
 
19
21
  interface DropzoneGalleryArgs {
20
- items: DropzoneGalleryItem[];
21
- showUploadButton?: boolean;
22
- changed?: (items: DropzoneGalleryItem[]) => void;
23
- removedFile?: (file: File) => void;
24
- uploadUrl: string;
25
- headers?: any;
26
- resizeBeforeUpload?: DropzoneResizeBeforeUploadArgs;
27
- parseNewItemFromResponse?: (resp: any) => DropzoneGalleryItem;
28
- formArr?: DropzoneFormItem[];
29
- errInvalidFileMessage: string;
30
- defaultMessage: string;
31
- errorHandler: (err: string) => void;
22
+ items: DropzoneGalleryItem[];
23
+ showUploadButton?: boolean;
24
+ changed?: (items: DropzoneGalleryItem[]) => void;
25
+ removedFile?: (file: File) => void;
26
+ uploadUrl: string;
27
+ headers?: any;
28
+ resizeBeforeUpload?: DropzoneResizeBeforeUploadArgs;
29
+ parseNewItemFromResponse?: (resp: any) => DropzoneGalleryItem;
30
+ formArr?: DropzoneFormItem[];
31
+ errInvalidFileMessage: string;
32
+ defaultMessage: string;
33
+ errorHandler: (err: string) => void;
32
34
  }
33
35
 
34
36
  interface DropzoneResizeBeforeUploadArgs {
35
- enabled: boolean;
36
- maxSize: number;
37
- quality?: number; // 0.0 - 1.0
37
+ enabled: boolean;
38
+ maxSize: number;
39
+ quality?: number; // 0.0 - 1.0
38
40
  }
39
41
 
40
42
  export interface DropzoneGalleryItem {
41
- Id: number;
42
- ImageUrl: string;
43
- SortOrder: number;
43
+ Id: number;
44
+ ImageUrl: string;
45
+ SortOrder: number;
44
46
  }
45
47
 
46
48
  @Component
47
49
  class DropzoneGalleryComponent extends TsxComponent<DropzoneGalleryArgs> implements DropzoneGalleryArgs {
48
- instance: any;
49
- @Prop() items: DropzoneGalleryItem[];
50
- @Prop() errorHandler: (err: string) => void;
51
- @Prop() uploadUrl: string;
52
- @Prop() headers: any;
53
- @Prop({ default: true }) showUploadButton?: boolean;
54
- @Prop() resizeBeforeUpload?: DropzoneResizeBeforeUploadArgs;
55
- @Prop() formArr?: DropzoneFormItem[];
56
- @Prop() parseNewItemFromResponse?: (resp: any) => DropzoneGalleryItem;
57
- @Prop() defaultMessage: string;
58
- @Prop() errInvalidFileMessage: string;
59
- @Prop() changed?: (items: DropzoneGalleryItem[]) => void;
60
- @Prop() removedFile?: (file: File) => void;
61
-
62
- mounted() {
63
- this.bindScript();
64
- }
65
-
66
- beforeUnmount() {
67
- try {
68
- (this.$refs.galleryDropzone as any).dropzone.destroy();
69
- } catch (error) { }
70
- }
71
-
72
- updateSortOrder(itemArr?: DropzoneGalleryItem[]) {
73
- let applySort = false;
74
- if (itemArr == null) {
75
- applySort = true;
76
- itemArr = arraySort(itemArr || [...this.items], p => p.SortOrder);
77
- }
78
-
79
- itemArr.forEach((item, i) => {
80
- if (item != null) {
81
- item.SortOrder = i;
82
- }
83
- });
84
-
85
- if (applySort) {
86
- itemArr = arraySort(itemArr, p => p.SortOrder);
87
- }
88
-
89
- if (this.changed != null) {
90
- this.changed(itemArr);
91
- }
92
- }
93
-
94
- bindScript() {
95
- const mySelf = this;
96
- this.instance = ($(this.$refs.galleryDropzone) as any).dropzone({
97
- // autoProcessQueue: true,
98
- url: mySelf.uploadUrl,
99
- headers: mySelf.headers,
100
- previewTemplate: '<div class="dz-preview dz-file-preview">\n <div class="dz-image"><div data-dz-thumbnail /></div>\n <div class="dz-details">\n <div class="dz-size"><span data-dz-size></span></div>\n <div class="dz-filename"><span data-dz-name></span></div>\n </div>\n <div class="dz-progress"><span class="dz-upload" data-dz-uploadprogress></span></div>\n <div class="dz-error-message"><span data-dz-errormessage></span></div>\n <div class="dz-success-mark">\n <svg width="54px" height="54px" viewBox="0 0 54 54" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:sketch="http://www.bohemiancoding.com/sketch/ns">\n <title>Check</title>\n <defs></defs>\n <g id="Page-1" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" sketch:type="MSPage">\n <path d="M23.5,31.8431458 L17.5852419,25.9283877 C16.0248253,24.3679711 13.4910294,24.366835 11.9289322,25.9289322 C10.3700136,27.4878508 10.3665912,30.0234455 11.9283877,31.5852419 L20.4147581,40.0716123 C20.5133999,40.1702541 20.6159315,40.2626649 20.7218615,40.3488435 C22.2835669,41.8725651 24.794234,41.8626202 26.3461564,40.3106978 L43.3106978,23.3461564 C44.8771021,21.7797521 44.8758057,19.2483887 43.3137085,17.6862915 C41.7547899,16.1273729 39.2176035,16.1255422 37.6538436,17.6893022 L23.5,31.8431458 Z M27,53 C41.3594035,53 53,41.3594035 53,27 C53,12.6405965 41.3594035,1 27,1 C12.6405965,1 1,12.6405965 1,27 C1,41.3594035 12.6405965,53 27,53 Z" id="Oval-2" stroke-opacity="0.198794158" stroke="#747474" fill-opacity="0.816519475" fill="#FFFFFF" sketch:type="MSShapeGroup"></path>\n </g>\n </svg>\n </div>\n <div class="dz-error-mark">\n <svg width="54px" height="54px" viewBox="0 0 54 54" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:sketch="http://www.bohemiancoding.com/sketch/ns">\n <title>Error</title>\n <defs></defs>\n <g id="Page-1" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" sketch:type="MSPage">\n <g id="Check-+-Oval-2" sketch:type="MSLayerGroup" stroke="#747474" stroke-opacity="0.198794158" fill="#FFFFFF" fill-opacity="0.816519475">\n <path d="M32.6568542,29 L38.3106978,23.3461564 C39.8771021,21.7797521 39.8758057,19.2483887 38.3137085,17.6862915 C36.7547899,16.1273729 34.2176035,16.1255422 32.6538436,17.6893022 L27,23.3431458 L21.3461564,17.6893022 C19.7823965,16.1255422 17.2452101,16.1273729 15.6862915,17.6862915 C14.1241943,19.2483887 14.1228979,21.7797521 15.6893022,23.3461564 L21.3431458,29 L15.6893022,34.6538436 C14.1228979,36.2202479 14.1241943,38.7516113 15.6862915,40.3137085 C17.2452101,41.8726271 19.7823965,41.8744578 21.3461564,40.3106978 L27,34.6568542 L32.6538436,40.3106978 C34.2176035,41.8744578 36.7547899,41.8726271 38.3137085,40.3137085 C39.8758057,38.7516113 39.8771021,36.2202479 38.3106978,34.6538436 L32.6568542,29 Z M27,53 C41.3594035,53 53,41.3594035 53,27 C53,12.6405965 41.3594035,1 27,1 C12.6405965,1 1,12.6405965 1,27 C1,41.3594035 12.6405965,53 27,53 Z" id="Oval-2" sketch:type="MSShapeGroup"></path>\n </g>\n </g>\n </svg>\n </div>\n</div>',
101
- maxFilesize: 5, // MB
102
- accept(file, done) {
103
- const _this = this;
104
- const extension = file.name.split('.').pop();
105
-
106
- if ($.inArray(extension.toLowerCase(), [
107
- 'jpg',
108
- 'jpeg',
109
- 'png',
110
- ]) > -1) {
111
- done();
112
- } else {
113
- done(`${file.name} - ${mySelf.errInvalidFileMessage}`);
114
- _this.removeFile(file);
115
- }
116
- },
117
- thumbnail: function thumbnail(
118
- file,
119
- dataUrl,
120
- sortOrder,
121
- ) {
122
- if (file.previewElement) {
123
- file.previewElement.classList.remove('dz-file-preview');
124
- for (var _iterator6 = file.previewElement.querySelectorAll('[data-dz-thumbnail]'), _isArray6 = true, _i6 = 0, _iterator6 = _isArray6 ? _iterator6 : _iterator6[Symbol.iterator](); ;) {
125
- var _ref5;
126
-
127
- if (_isArray6) {
128
- if (_i6 >= _iterator6.length) { break; }
129
-
130
- _ref5 = _iterator6[_i6++];
131
- } else {
132
- _i6 = _iterator6.next();
133
- if ((_i6 as any).done) { break; }
134
-
135
- _ref5 = (_i6 as any).value;
136
- }
137
-
138
- const thumbnailElement = _ref5;
139
- sortOrder = mySelf.items.length + 1;
140
-
141
- thumbnailElement.setAttribute('sortOrder', sortOrder);
142
- thumbnailElement.style.width = '100%';
143
- thumbnailElement.style.height = '100%';
144
- thumbnailElement.style.backgroundImage = `url('${dataUrl}')`;
145
- thumbnailElement.style.backgroundSize = 'cover';
146
- thumbnailElement.style.backgroundRepeat = 'no-repeat';
147
- thumbnailElement.style.backgroundPosition = 'center center';
148
- }
149
-
150
- return setTimeout(() => {
151
- return file.previewElement.classList.add('dz-image-preview');
152
- }, 1);
153
- }
154
- },
155
- init() {
156
- const addFile = this.addFile;
157
- this.addFile = async (file: File) => {
158
- if (mySelf.resizeBeforeUpload?.enabled == true) {
159
- const result = await scaleImageBeforeUpload(
160
- file,
161
- mySelf.resizeBeforeUpload.maxSize,
162
- mySelf.resizeBeforeUpload.quality,
163
- );
164
-
165
- if (result.resized) {
166
- addFile.call(this, result.fileBlob);
167
- } else {
168
- addFile.call(this, file);
169
- }
170
- } else {
171
- addFile.call(this, file);
172
- }
173
- };
174
-
175
- this.on('addedfile', function (this: any, file) {
176
- // hide display initial dz-message
177
- (document.querySelector('.dz-message') as HTMLElement).style.display = 'none';
178
- // Create the remove button
179
- const removeButton = Dropzone.createElement('<a class="dz-gallery-remove-button" href="javascript:" style="cursor:pointer; font-size: 20px; font-weight: bold; color: black">X</a>');
180
- // var removeButton = Dropzone.createElement('<a class="dz-gallery-remove-button" href="javascript:" style="cursor:pointer; font-size: 20px; font-weight: bold; color: black"><i class="fa fa-trash"></i></a>');
181
-
182
- const _this = this;
183
- // remove image from dropzone and adjust new sortorder attribute
184
- removeButton.addEventListener('click', (e) => {
185
- e.preventDefault();
186
- e.stopPropagation();
187
-
188
- let removeItem;
189
- const matchingArr = mySelf.items.filter(p => p.ImageUrl == file.url);
190
-
191
- if (matchingArr.length == 1) {
192
- removeItem = matchingArr[0];
193
- } else {
194
- removeItem = mySelf.items.find((item) => {
195
- if ((item as any)._uuid != null) {
196
- return (item as any)._uuid == file.uuid;
197
- } else if (item.Id > 0) {
198
- return item.Id == file.uuid;
199
- }
200
- });
201
- }
202
-
203
- mySelf.items.splice(mySelf.items.indexOf(removeItem), 1);
204
- // Remove the file preview.
205
- _this.removeFile(file);
206
- mySelf.removedFile(removeItem);
207
- mySelf.updateSortOrder();
208
- // show init dropzone message only if there is no image
209
- if (document.getElementsByClassName('dz-preview').length == 0) {
210
- (document.querySelector('.dz-message') as HTMLElement).style.display = 'block';
211
- } else {
212
- (document.querySelector('.dz-message') as HTMLElement).style.display = 'none';
213
- }
214
- });
215
- // Add the button to the file preview element.
216
- file.previewElement.getElementsByClassName('dz-details')[0].appendChild(removeButton);
217
- });
218
-
219
- this.on('success', (file, response) => {
220
- let newItem: DropzoneGalleryItem;
221
- if (mySelf.parseNewItemFromResponse != null) {
222
- newItem = mySelf.parseNewItemFromResponse(response);
223
- }
224
-
225
- if (newItem == null) {
226
- newItem = {
227
- Id: 0,
228
- ImageUrl: response,
229
- SortOrder: mySelf.items.length + 1,
230
- };
231
- }
232
-
233
- (newItem as any)._uuid = (Math.floor(Math.random() * 2000000000)) * (-1);
234
- file.uuid = (newItem as any)._uuid;
235
- mySelf.items.push(newItem);
236
-
237
- if (mySelf.changed != null) {
238
- mySelf.changed(mySelf.items);
239
- }
240
- });
241
-
242
- this.on('error', (
243
- file,
244
- error,
245
- xhr,
246
- ) => {
247
- mySelf.errorHandler(error);
248
- });
249
-
250
- const self = this;
251
-
252
- // initialization of existing images into dropzone area
253
- if (mySelf.items != null && mySelf.items.length > 0) {
254
- const eventGallery = arraySort([...mySelf.items], p => p.SortOrder);
255
- for (let i = 0; i < eventGallery.length; i++) {
256
- let id = eventGallery[i].Id;
257
- if (id < 1 && (eventGallery[i] as any)._uuid == null) {
258
- (eventGallery[i] as any)._uuid = (Math.floor(Math.random() * 2000000000)) * (-1);
259
- id = (eventGallery[i] as any)._uuid;
260
- }
261
-
262
- const mock = {
263
- name: eventGallery[i].Id,
264
- size: 12345,
265
- type: 'image/jpeg',
266
- url: eventGallery[i].ImageUrl,
267
- sortOrder: eventGallery[i].SortOrder,
268
- uuid: id,
269
- };
270
- self.emit('addedfile', mock);
271
- self.emit(
272
- 'thumbnail',
273
- mock,
274
- mock.url,
275
- mock.sortOrder,
276
- );
277
- self.emit('complete', mock);
278
- }
279
-
280
- (document.querySelector('.dz-message') as HTMLElement).style.display = 'none';
281
- } else {
282
- (document.querySelector('.dz-message') as HTMLElement).style.display = 'block';
283
- }
284
- },
285
- });
286
-
287
- new Sortable(this.$refs.galleryDropzone, {
288
- animation: 150,
289
- onEnd: (evt) => {
290
- const oldIndex = evt.oldIndex - 2;
291
- const newIndex = evt.newIndex - 2;
292
- const itemArr = arraySort([...this.items], p => p.SortOrder);
293
- const item = itemArr[oldIndex];
294
-
295
- arrayRemove(itemArr, item);
296
- itemArr.splice(
297
- newIndex,
298
- 0,
299
- item,
300
- );
301
- this.updateSortOrder(itemArr);
302
- },
303
- });
304
- }
305
-
306
- render(h) {
307
- return (
308
- <div class="gallery-dropzone">
309
- {this.showUploadButton
310
- && (
311
- <div class="clearfix">
312
- <Button
313
- text={PowerduckState.getResourceValue('uploadImage')}
314
- layout={ButtonLayout.Secondary}
315
- cssClass="mb-3 float-end"
316
- clicked={() => { $(this.$refs.galleryDropzone).trigger('click'); }}
317
- />
318
- </div>
319
- )}
320
-
321
- <form class="dropzone" ref="galleryDropzone">
322
- {this.formArr != null && this.formArr.map(p =>
323
- <input type="hidden" name={p.name} value={p.value} />)}
324
-
325
- <div class="dz-message" style="display: block" data-dz-message>
326
- <i class="far fa-image fa-3x" aria-hidden="true"></i>
327
- <br />
328
- <span class="gallery-insert-image">
329
- &nbsp;
330
- {this.defaultMessage}
331
- </span>
332
- </div>
333
- </form>
334
- </div>
335
- );
336
- }
50
+ instance: any;
51
+ @Prop() items: DropzoneGalleryItem[];
52
+ @Prop() errorHandler: (err: string) => void;
53
+ @Prop() uploadUrl: string;
54
+ @Prop() headers: any;
55
+ @Prop({ default: true }) showUploadButton?: boolean;
56
+ @Prop() resizeBeforeUpload?: DropzoneResizeBeforeUploadArgs;
57
+ @Prop() formArr?: DropzoneFormItem[];
58
+ @Prop() parseNewItemFromResponse?: (resp: any) => DropzoneGalleryItem;
59
+ @Prop() defaultMessage: string;
60
+ @Prop() errInvalidFileMessage: string;
61
+ @Prop() changed?: (items: DropzoneGalleryItem[]) => void;
62
+ @Prop() removedFile?: (file: File) => void;
63
+
64
+ mounted() {
65
+ this.bindScript();
66
+ }
67
+
68
+ beforeUnmount() {
69
+ try {
70
+ (this.$refs.galleryDropzone as any).dropzone.destroy();
71
+ } catch (error) { }
72
+ }
73
+
74
+ updateSortOrder(itemArr?: DropzoneGalleryItem[]) {
75
+ let applySort = false;
76
+ if (itemArr == null) {
77
+ applySort = true;
78
+ itemArr = (itemArr || [...this.items])[sortBy](p => p.SortOrder);
79
+ }
80
+
81
+ itemArr.forEach((item, i) => {
82
+ if (item != null) {
83
+ item.SortOrder = i;
84
+ }
85
+ });
86
+
87
+ if (applySort) {
88
+ itemArr = itemArr[sortBy](p => p.SortOrder);
89
+ }
90
+
91
+ if (this.changed != null) {
92
+ this.changed(itemArr);
93
+ }
94
+ }
95
+
96
+ bindScript() {
97
+ const mySelf = this;
98
+ this.instance = ($(this.$refs.galleryDropzone) as any).dropzone({
99
+ // autoProcessQueue: true,
100
+ url: mySelf.uploadUrl,
101
+ headers: mySelf.headers,
102
+ previewTemplate: '<div class="dz-preview dz-file-preview">\n <div class="dz-image"><div data-dz-thumbnail /></div>\n <div class="dz-details">\n <div class="dz-size"><span data-dz-size></span></div>\n <div class="dz-filename"><span data-dz-name></span></div>\n </div>\n <div class="dz-progress"><span class="dz-upload" data-dz-uploadprogress></span></div>\n <div class="dz-error-message"><span data-dz-errormessage></span></div>\n <div class="dz-success-mark">\n <svg width="54px" height="54px" viewBox="0 0 54 54" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:sketch="http://www.bohemiancoding.com/sketch/ns">\n <title>Check</title>\n <defs></defs>\n <g id="Page-1" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" sketch:type="MSPage">\n <path d="M23.5,31.8431458 L17.5852419,25.9283877 C16.0248253,24.3679711 13.4910294,24.366835 11.9289322,25.9289322 C10.3700136,27.4878508 10.3665912,30.0234455 11.9283877,31.5852419 L20.4147581,40.0716123 C20.5133999,40.1702541 20.6159315,40.2626649 20.7218615,40.3488435 C22.2835669,41.8725651 24.794234,41.8626202 26.3461564,40.3106978 L43.3106978,23.3461564 C44.8771021,21.7797521 44.8758057,19.2483887 43.3137085,17.6862915 C41.7547899,16.1273729 39.2176035,16.1255422 37.6538436,17.6893022 L23.5,31.8431458 Z M27,53 C41.3594035,53 53,41.3594035 53,27 C53,12.6405965 41.3594035,1 27,1 C12.6405965,1 1,12.6405965 1,27 C1,41.3594035 12.6405965,53 27,53 Z" id="Oval-2" stroke-opacity="0.198794158" stroke="#747474" fill-opacity="0.816519475" fill="#FFFFFF" sketch:type="MSShapeGroup"></path>\n </g>\n </svg>\n </div>\n <div class="dz-error-mark">\n <svg width="54px" height="54px" viewBox="0 0 54 54" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:sketch="http://www.bohemiancoding.com/sketch/ns">\n <title>Error</title>\n <defs></defs>\n <g id="Page-1" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" sketch:type="MSPage">\n <g id="Check-+-Oval-2" sketch:type="MSLayerGroup" stroke="#747474" stroke-opacity="0.198794158" fill="#FFFFFF" fill-opacity="0.816519475">\n <path d="M32.6568542,29 L38.3106978,23.3461564 C39.8771021,21.7797521 39.8758057,19.2483887 38.3137085,17.6862915 C36.7547899,16.1273729 34.2176035,16.1255422 32.6538436,17.6893022 L27,23.3431458 L21.3461564,17.6893022 C19.7823965,16.1255422 17.2452101,16.1273729 15.6862915,17.6862915 C14.1241943,19.2483887 14.1228979,21.7797521 15.6893022,23.3461564 L21.3431458,29 L15.6893022,34.6538436 C14.1228979,36.2202479 14.1241943,38.7516113 15.6862915,40.3137085 C17.2452101,41.8726271 19.7823965,41.8744578 21.3461564,40.3106978 L27,34.6568542 L32.6538436,40.3106978 C34.2176035,41.8744578 36.7547899,41.8726271 38.3137085,40.3137085 C39.8758057,38.7516113 39.8771021,36.2202479 38.3106978,34.6538436 L32.6568542,29 Z M27,53 C41.3594035,53 53,41.3594035 53,27 C53,12.6405965 41.3594035,1 27,1 C12.6405965,1 1,12.6405965 1,27 C1,41.3594035 12.6405965,53 27,53 Z" id="Oval-2" sketch:type="MSShapeGroup"></path>\n </g>\n </g>\n </svg>\n </div>\n</div>',
103
+ maxFilesize: 5, // MB
104
+ accept(file, done) {
105
+ const _this = this;
106
+ const extension = file.name.split('.').pop();
107
+
108
+ if ($.inArray(extension.toLowerCase(), [
109
+ 'jpg',
110
+ 'jpeg',
111
+ 'png',
112
+ ]) > -1) {
113
+ done();
114
+ } else {
115
+ done(`${file.name} - ${mySelf.errInvalidFileMessage}`);
116
+ _this.removeFile(file);
117
+ }
118
+ },
119
+ thumbnail: function thumbnail(
120
+ file,
121
+ dataUrl,
122
+ sortOrder,
123
+ ) {
124
+ if (file.previewElement) {
125
+ file.previewElement.classList.remove('dz-file-preview');
126
+ // eslint-disable-next-line ts/no-redeclare
127
+ for (var _iterator6 = file.previewElement.querySelectorAll('[data-dz-thumbnail]'), _isArray6 = true, _i6 = 0, _iterator6 = _isArray6 ? _iterator6 : _iterator6[Symbol.iterator](); ;) {
128
+ var _ref5;
129
+
130
+ if (_isArray6) {
131
+ if (_i6 >= _iterator6.length) {
132
+ break;
133
+ }
134
+
135
+ _ref5 = _iterator6[_i6++];
136
+ } else {
137
+ _i6 = _iterator6.next();
138
+ if ((_i6 as any).done) {
139
+ break;
140
+ }
141
+
142
+ _ref5 = (_i6 as any).value;
143
+ }
144
+
145
+ const thumbnailElement = _ref5;
146
+ sortOrder = mySelf.items.length + 1;
147
+
148
+ thumbnailElement.setAttribute('sortOrder', sortOrder);
149
+ thumbnailElement.style.width = '100%';
150
+ thumbnailElement.style.height = '100%';
151
+ thumbnailElement.style.backgroundImage = `url('${dataUrl}')`;
152
+ thumbnailElement.style.backgroundSize = 'cover';
153
+ thumbnailElement.style.backgroundRepeat = 'no-repeat';
154
+ thumbnailElement.style.backgroundPosition = 'center center';
155
+ }
156
+
157
+ return setTimeout(() => {
158
+ return file.previewElement.classList.add('dz-image-preview');
159
+ }, 1);
160
+ }
161
+ },
162
+ init() {
163
+ const addFile = this.addFile;
164
+ this.addFile = async (file: File) => {
165
+ if (mySelf.resizeBeforeUpload?.enabled == true) {
166
+ const result = await scaleImageBeforeUpload(
167
+ file,
168
+ mySelf.resizeBeforeUpload.maxSize,
169
+ mySelf.resizeBeforeUpload.quality,
170
+ );
171
+
172
+ if (result.resized) {
173
+ addFile.call(this, result.fileBlob);
174
+ } else {
175
+ addFile.call(this, file);
176
+ }
177
+ } else {
178
+ addFile.call(this, file);
179
+ }
180
+ };
181
+
182
+ this.on('addedfile', function (this: any, file) {
183
+ // hide display initial dz-message
184
+ (document.querySelector('.dz-message') as HTMLElement).style.display = 'none';
185
+ // Create the remove button
186
+ const removeButton = Dropzone.createElement('<a class="dz-gallery-remove-button" href="javascript:" style="cursor:pointer; font-size: 20px; font-weight: bold; color: black">X</a>');
187
+ // var removeButton = Dropzone.createElement('<a class="dz-gallery-remove-button" href="javascript:" style="cursor:pointer; font-size: 20px; font-weight: bold; color: black"><i class="fa fa-trash"></i></a>');
188
+
189
+ const _this = this;
190
+ // remove image from dropzone and adjust new sortorder attribute
191
+ removeButton.addEventListener('click', (e) => {
192
+ e.preventDefault();
193
+ e.stopPropagation();
194
+
195
+ let removeItem;
196
+ const matchingArr = mySelf.items.filter(p => p.ImageUrl == file.url);
197
+
198
+ if (matchingArr.length == 1) {
199
+ removeItem = matchingArr[0];
200
+ } else {
201
+ removeItem = mySelf.items.find((item) => {
202
+ if ((item as any)._uuid != null) {
203
+ return (item as any)._uuid == file.uuid;
204
+ } else if (item.Id > 0) {
205
+ return item.Id == file.uuid;
206
+ } else {
207
+ return false;
208
+ }
209
+ });
210
+ }
211
+
212
+ mySelf.items.splice(mySelf.items.indexOf(removeItem), 1);
213
+ // Remove the file preview.
214
+ _this.removeFile(file);
215
+ mySelf.removedFile(removeItem);
216
+ mySelf.updateSortOrder();
217
+ // show init dropzone message only if there is no image
218
+ if (document.getElementsByClassName('dz-preview').length == 0) {
219
+ (document.querySelector('.dz-message') as HTMLElement).style.display = 'block';
220
+ } else {
221
+ (document.querySelector('.dz-message') as HTMLElement).style.display = 'none';
222
+ }
223
+ });
224
+ // Add the button to the file preview element.
225
+ file.previewElement.getElementsByClassName('dz-details')[0].appendChild(removeButton);
226
+ });
227
+
228
+ this.on('success', (file, response) => {
229
+ let newItem: DropzoneGalleryItem;
230
+ if (mySelf.parseNewItemFromResponse != null) {
231
+ newItem = mySelf.parseNewItemFromResponse(response);
232
+ }
233
+
234
+ if (newItem == null) {
235
+ newItem = {
236
+ Id: 0,
237
+ ImageUrl: response,
238
+ SortOrder: mySelf.items.length + 1,
239
+ };
240
+ }
241
+
242
+ (newItem as any)._uuid = (Math.floor(Math.random() * 2000000000)) * (-1);
243
+ file.uuid = (newItem as any)._uuid;
244
+ mySelf.items.push(newItem);
245
+
246
+ if (mySelf.changed != null) {
247
+ mySelf.changed(mySelf.items);
248
+ }
249
+ });
250
+
251
+ this.on('error', (
252
+ file,
253
+ error,
254
+ xhr,
255
+ ) => {
256
+ mySelf.errorHandler(error);
257
+ });
258
+
259
+ const self = this;
260
+
261
+ // initialization of existing images into dropzone area
262
+ if (mySelf.items != null && mySelf.items.length > 0) {
263
+ const eventGallery = [...mySelf.items][sortBy](p => p.SortOrder);
264
+ for (let i = 0; i < eventGallery.length; i++) {
265
+ let id = eventGallery[i].Id;
266
+ if (id < 1 && (eventGallery[i] as any)._uuid == null) {
267
+ (eventGallery[i] as any)._uuid = (Math.floor(Math.random() * 2000000000)) * (-1);
268
+ id = (eventGallery[i] as any)._uuid;
269
+ }
270
+
271
+ const mock = {
272
+ name: eventGallery[i].Id,
273
+ size: 12345,
274
+ type: 'image/jpeg',
275
+ url: eventGallery[i].ImageUrl,
276
+ sortOrder: eventGallery[i].SortOrder,
277
+ uuid: id,
278
+ };
279
+ self.emit('addedfile', mock);
280
+ self.emit(
281
+ 'thumbnail',
282
+ mock,
283
+ mock.url,
284
+ mock.sortOrder,
285
+ );
286
+ self.emit('complete', mock);
287
+ }
288
+
289
+ (document.querySelector('.dz-message') as HTMLElement).style.display = 'none';
290
+ } else {
291
+ (document.querySelector('.dz-message') as HTMLElement).style.display = 'block';
292
+ }
293
+ },
294
+ });
295
+
296
+ // eslint-disable-next-line no-new
297
+ new Sortable(this.$refs.galleryDropzone, {
298
+ animation: 150,
299
+ onEnd: (evt) => {
300
+ const oldIndex = evt.oldIndex - 2;
301
+ const newIndex = evt.newIndex - 2;
302
+ const itemArr = [...this.items][sortBy](p => p.SortOrder);
303
+ const item = itemArr[oldIndex];
304
+
305
+ itemArr[remove](item);
306
+ itemArr.splice(
307
+ newIndex,
308
+ 0,
309
+ item,
310
+ );
311
+ this.updateSortOrder(itemArr);
312
+ },
313
+ });
314
+ }
315
+
316
+ render(h) {
317
+ return (
318
+ <div class="gallery-dropzone">
319
+ {this.showUploadButton
320
+ && (
321
+ <div class="clearfix">
322
+ <Button
323
+ text={PowerduckState.getResourceValue('uploadImage')}
324
+ layout={ButtonLayout.Secondary}
325
+ cssClass="mb-3 float-end"
326
+ clicked={() => { $(this.$refs.galleryDropzone).trigger('click'); }}
327
+ />
328
+ </div>
329
+ )}
330
+
331
+ <form class="dropzone" ref="galleryDropzone">
332
+ {this.formArr != null && this.formArr.map(p =>
333
+ <input type="hidden" name={p.name} value={p.value} />)}
334
+
335
+ <div class="dz-message" style="display: block" data-dz-message>
336
+ <i class="far fa-image fa-3x" aria-hidden="true"></i>
337
+ <br />
338
+ <span class="gallery-insert-image">
339
+ &nbsp;
340
+ {this.defaultMessage}
341
+ </span>
342
+ </div>
343
+ </form>
344
+ </div>
345
+ );
346
+ }
337
347
  }
338
348
 
349
+ // eslint-disable-next-line func-style
339
350
  export async function scaleImageBeforeUpload(
340
- file: File,
341
- maxSize: number,
342
- quality?: number,
351
+ file: File,
352
+ maxSize: number,
353
+ quality?: number,
343
354
  ): Promise<{ resized: boolean; fileBlob: File }> {
344
- // ensure the file is an image
345
- if (!file.type.match(/image.*/)) {
346
- return {
347
- resized: false,
348
- fileBlob: null,
349
- };
350
- }
351
-
352
- const image = new Image();
353
- image.src = URL.createObjectURL(file);
354
-
355
- await new Promise<Event>(res => (image.onload = res));
356
- const canvas = document.createElement('canvas');
357
- const context = canvas.getContext('2d', { alpha: true });
358
-
359
- let width = image.width;
360
- let height = image.height;
361
- if (width > height) {
362
- if (width > maxSize) {
363
- height *= maxSize / width;
364
- width = maxSize;
365
- } else {
366
- return {
367
- resized: false,
368
- fileBlob: null,
369
- };
370
- }
371
- } else {
372
- if (height > maxSize) {
373
- width *= maxSize / height;
374
- height = maxSize;
375
- } else {
376
- return {
377
- resized: false,
378
- fileBlob: null,
379
- };
380
- }
381
- }
382
-
383
- canvas.width = width;
384
- canvas.height = height;
385
- context.drawImage(
386
- image,
387
- 0,
388
- 0,
389
- width,
390
- height,
391
- );
392
-
393
- let blob: Blob;
394
- if (quality != null) {
395
- blob = await new Promise(res => canvas.toBlob(
396
- res,
397
- file.type,
398
- quality,
399
- ));
400
- } else {
401
- blob = await new Promise(res => canvas.toBlob(res));
402
- }
403
-
404
- (blob as any).name = StringUtils.normalizeFileName(file.name);
405
- (blob as any).lastModifiedDate = new Date();
406
- (blob as any).lastModified = (blob as any).lastModifiedDate.getTime();
407
-
408
- return {
409
- resized: true,
410
- fileBlob: blob as any,
411
- };
355
+ // ensure the file is an image
356
+ if (!file.type.match(/image.*/)) {
357
+ return {
358
+ resized: false,
359
+ fileBlob: null,
360
+ };
361
+ }
362
+
363
+ const image = new Image();
364
+ image.src = URL.createObjectURL(file);
365
+
366
+ await new Promise<Event>(res => (image.onload = res));
367
+ const canvas = document.createElement('canvas');
368
+ const context = canvas.getContext('2d', { alpha: true });
369
+
370
+ let width = image.width;
371
+ let height = image.height;
372
+ if (width > height) {
373
+ if (width > maxSize) {
374
+ height *= maxSize / width;
375
+ width = maxSize;
376
+ } else {
377
+ return {
378
+ resized: false,
379
+ fileBlob: null,
380
+ };
381
+ }
382
+ } else {
383
+ if (height > maxSize) {
384
+ width *= maxSize / height;
385
+ height = maxSize;
386
+ } else {
387
+ return {
388
+ resized: false,
389
+ fileBlob: null,
390
+ };
391
+ }
392
+ }
393
+
394
+ canvas.width = width;
395
+ canvas.height = height;
396
+ context.drawImage(
397
+ image,
398
+ 0,
399
+ 0,
400
+ width,
401
+ height,
402
+ );
403
+
404
+ let blob: Blob;
405
+ if (quality != null) {
406
+ blob = await new Promise(res => canvas.toBlob(
407
+ res,
408
+ file.type,
409
+ quality,
410
+ ));
411
+ } else {
412
+ blob = await new Promise(res => canvas.toBlob(res));
413
+ }
414
+
415
+ (blob as any).name = StringUtils.normalizeFileName(file.name);
416
+ // eslint-disable-next-line no-restricted-syntax
417
+ (blob as any).lastModifiedDate = new Date();
418
+ (blob as any).lastModified = (blob as any).lastModifiedDate.getTime();
419
+
420
+ return {
421
+ resized: true,
422
+ fileBlob: blob as any,
423
+ };
412
424
  }
413
425
 
414
426
  const DropzoneGallery = toNative(DropzoneGalleryComponent);