@smartbit4all/ng-client 4.2.42 → 4.2.44

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.
@@ -9318,7 +9318,6 @@ class UiActionButtonComponent {
9318
9318
  case UiActionButtonType.FAB:
9319
9319
  return 'mat-mdc-fab';
9320
9320
  default:
9321
- console.log(`Unhandled action button type case: ${uiActionModel.descriptor?.type}`);
9322
9321
  return `mat-button`;
9323
9322
  }
9324
9323
  }
@@ -9374,39 +9373,6 @@ class PhotoCaptureWidgetComponent {
9374
9373
  this.cameraActive = false;
9375
9374
  this.isCaptured = false;
9376
9375
  this.componentLibrary = ComponentLibrary;
9377
- this.mobileButton = {
9378
- uiAction: {
9379
- descriptor: {
9380
- type: UiActionButtonType.RAISED,
9381
- title: 'Kép készítése',
9382
- icon: 'camera',
9383
- iconPosition: IconPosition.PRE,
9384
- color: 'primary',
9385
- },
9386
- },
9387
- };
9388
- this.startCameraButton = {
9389
- uiAction: {
9390
- descriptor: {
9391
- type: UiActionButtonType.RAISED,
9392
- title: 'Kamera bekapcsolása',
9393
- icon: 'play',
9394
- iconPosition: IconPosition.PRE,
9395
- color: 'primary',
9396
- },
9397
- },
9398
- };
9399
- this.stopCameraButton = {
9400
- uiAction: {
9401
- descriptor: {
9402
- type: UiActionButtonType.RAISED,
9403
- title: 'Kamera kikapcsolása',
9404
- icon: 'stop',
9405
- iconPosition: IconPosition.PRE,
9406
- color: 'primary',
9407
- },
9408
- },
9409
- };
9410
9376
  this.captureButton = {
9411
9377
  uiAction: {
9412
9378
  descriptor: {
@@ -9414,11 +9380,11 @@ class PhotoCaptureWidgetComponent {
9414
9380
  title: 'Kép készítése',
9415
9381
  icon: 'camera',
9416
9382
  iconPosition: IconPosition.PRE,
9417
- color: 'primary',
9418
9383
  },
9419
9384
  },
9420
9385
  };
9421
9386
  this.compLib = compLib ?? ComponentLibrary.PRIMENG;
9387
+ this.updateToggleButton();
9422
9388
  }
9423
9389
  isMobile() {
9424
9390
  return /iPhone|iPad|iPod|Android/i.test(navigator.userAgent);
@@ -9429,13 +9395,15 @@ class PhotoCaptureWidgetComponent {
9429
9395
  this.videoRef.nativeElement.play();
9430
9396
  this.cameraActive = true;
9431
9397
  this.isCaptured = false;
9398
+ this.updateToggleButton();
9432
9399
  }
9433
9400
  stopCamera() {
9434
9401
  this.stream?.getTracks().forEach((track) => track.stop());
9435
9402
  this.stream = undefined;
9436
9403
  this.cameraActive = false;
9404
+ this.updateToggleButton();
9437
9405
  }
9438
- capturePhoto() {
9406
+ async capturePhoto() {
9439
9407
  const video = this.videoRef.nativeElement;
9440
9408
  const canvas = this.canvasRef.nativeElement;
9441
9409
  const context = canvas.getContext('2d');
@@ -9444,31 +9412,138 @@ class PhotoCaptureWidgetComponent {
9444
9412
  canvas.width = video.videoWidth;
9445
9413
  canvas.height = video.videoHeight;
9446
9414
  context.drawImage(video, 0, 0);
9447
- canvas.toBlob((blob) => {
9448
- if (blob) {
9449
- const file = new File([blob], `photo_${Date.now()}.png`, { type: 'image/png' });
9450
- this.photoCaptured.emit([file]);
9451
- this.isCaptured = true;
9452
- this.stopCamera();
9453
- }
9454
- }, 'image/png');
9415
+ const blob = await new Promise((resolve) => canvas.toBlob(resolve, 'image/jpeg', 0.9));
9416
+ if (!blob)
9417
+ return;
9418
+ let file = new File([blob], `photo_${Date.now()}.jpg`, { type: 'image/jpeg' });
9419
+ if (this.maxFileSize && file.size > this.maxFileSize) {
9420
+ file = await this.compressImageFile(file, this.maxFileSize);
9421
+ }
9422
+ this.photoCaptured.emit([file]);
9423
+ this.isCaptured = true;
9424
+ this.stopCamera();
9455
9425
  }
9456
9426
  getPhotoDataURL() {
9457
9427
  return this.canvasRef.nativeElement.toDataURL('image/png');
9458
9428
  }
9459
- onFileSelected(event) {
9429
+ async onFileSelected(event) {
9460
9430
  const input = event.target;
9461
- if (input.files && input.files.length > 0) {
9462
- const filesArray = Array.from(input.files);
9463
- this.photoCaptured.emit(filesArray);
9431
+ if (!input.files || input.files.length === 0)
9432
+ return;
9433
+ const maxSize = this.maxFileSize;
9434
+ const filesArray = Array.from(input.files);
9435
+ const processedFiles = [];
9436
+ for (const file of filesArray) {
9437
+ if (maxSize && file.size > maxSize && file.type.startsWith('image/')) {
9438
+ try {
9439
+ const compressed = await this.compressImageFile(file, maxSize);
9440
+ processedFiles.push(compressed);
9441
+ }
9442
+ catch {
9443
+ processedFiles.push(file);
9444
+ }
9445
+ }
9446
+ else {
9447
+ processedFiles.push(file);
9448
+ }
9449
+ }
9450
+ this.photoCaptured.emit(processedFiles);
9451
+ }
9452
+ toggleCamera() {
9453
+ if (this.cameraActive) {
9454
+ this.stopCamera();
9455
+ }
9456
+ else {
9457
+ this.startCamera();
9458
+ }
9459
+ }
9460
+ updateToggleButton() {
9461
+ let icon = this.compLib === ComponentLibrary.PRIMENG ? 'power-off' : 'power_settings_new';
9462
+ let title;
9463
+ let color;
9464
+ if (this.cameraActive) {
9465
+ title = 'Kamera kikapcsolása';
9466
+ color = this.compLib === ComponentLibrary.PRIMENG ? 'danger' : 'red';
9467
+ }
9468
+ else {
9469
+ title = 'Kamera bekapcsolása';
9470
+ color = '';
9471
+ }
9472
+ this.toggleCameraButton = {
9473
+ uiAction: {
9474
+ descriptor: {
9475
+ type: UiActionButtonType.RAISED,
9476
+ title: title,
9477
+ icon: icon,
9478
+ color,
9479
+ iconPosition: IconPosition.PRE,
9480
+ },
9481
+ },
9482
+ };
9483
+ }
9484
+ async compressImageFile(file, maxFileSize) {
9485
+ if (!file.type.startsWith('image/'))
9486
+ return file;
9487
+ const img = await new Promise((resolve, reject) => {
9488
+ const url = URL.createObjectURL(file);
9489
+ const image = new Image();
9490
+ image.onload = () => {
9491
+ URL.revokeObjectURL(url);
9492
+ resolve(image);
9493
+ };
9494
+ image.onerror = (e) => {
9495
+ URL.revokeObjectURL(url);
9496
+ reject(e);
9497
+ };
9498
+ image.src = url;
9499
+ });
9500
+ const canvas = document.createElement('canvas');
9501
+ const ctx = canvas.getContext('2d');
9502
+ if (!ctx)
9503
+ return file;
9504
+ let width = img.naturalWidth;
9505
+ let height = img.naturalHeight;
9506
+ let quality = 0.9;
9507
+ const minQuality = 0.4;
9508
+ const minDimension = 640;
9509
+ const getBlob = (q) => new Promise((resolve) => {
9510
+ canvas.width = width;
9511
+ canvas.height = height;
9512
+ ctx.clearRect(0, 0, width, height);
9513
+ ctx.drawImage(img, 0, 0, width, height);
9514
+ canvas.toBlob((blob) => {
9515
+ if (blob)
9516
+ resolve(blob);
9517
+ }, 'image/jpeg', q);
9518
+ });
9519
+ let blob = await getBlob(quality);
9520
+ while (blob.size > maxFileSize) {
9521
+ if (quality > minQuality) {
9522
+ quality -= 0.1;
9523
+ }
9524
+ else if (width > minDimension && height > minDimension) {
9525
+ width = Math.floor(width * 0.8);
9526
+ height = Math.floor(height * 0.8);
9527
+ quality = 0.9;
9528
+ }
9529
+ else {
9530
+ break;
9531
+ }
9532
+ blob = await getBlob(quality);
9533
+ }
9534
+ if (blob.size <= maxFileSize) {
9535
+ return new File([blob], file.name, { type: 'image/jpeg' });
9536
+ }
9537
+ else {
9538
+ return file;
9464
9539
  }
9465
9540
  }
9466
9541
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.11", ngImport: i0, type: PhotoCaptureWidgetComponent, deps: [{ token: COMPONENT_LIBRARY, optional: true }], target: i0.ɵɵFactoryTarget.Component }); }
9467
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "17.3.11", type: PhotoCaptureWidgetComponent, selector: "photo-capture-widget", outputs: { photoCaptured: "photoCaptured" }, viewQueries: [{ propertyName: "videoRef", first: true, predicate: ["video"], descendants: true }, { propertyName: "canvasRef", first: true, predicate: ["canvas"], descendants: true }, { propertyName: "fileInputRef", first: true, predicate: ["fileInput"], descendants: true }], ngImport: i0, template: "<div class=\"photoWidgetContainer\">\r\n <ng-container *ngIf=\"!isMobile()\">\r\n <video #video autoplay [hidden]=\"isCaptured || !cameraActive\"></video>\r\n <canvas #canvas [hidden]=\"!isCaptured || cameraActive\"></canvas>\r\n\r\n <ng-container *ngIf=\"!cameraActive && !isCaptured\">\r\n <p class=\"message\">Kapcsolja be a kamer\u00E1t a k\u00E9p k\u00E9sz\u00EDt\u00E9s\u00E9hez!</p>\r\n </ng-container>\r\n\r\n <div class=\"controls\">\r\n <!-- START CAMERA -->\r\n <ui-action-button\r\n *ngIf=\"!cameraActive\"\r\n [uiActionModel]=\"startCameraButton\"\r\n (actionClick)=\"startCamera()\"\r\n >\r\n </ui-action-button>\r\n\r\n <!-- STOP CAMERA -->\r\n <ui-action-button\r\n *ngIf=\"cameraActive\"\r\n [uiActionModel]=\"stopCameraButton\"\r\n (actionClick)=\"stopCamera()\"\r\n >\r\n </ui-action-button>\r\n\r\n <!-- CAPTURE CAMERA -->\r\n <ui-action-button\r\n [disabled]=\"!cameraActive\"\r\n [uiActionModel]=\"captureButton\"\r\n (actionClick)=\"capturePhoto()\"\r\n >\r\n </ui-action-button>\r\n </div>\r\n </ng-container>\r\n\r\n <ng-container *ngIf=\"isMobile()\">\r\n <div class=\"controls\">\r\n <input\r\n #fileInput\r\n type=\"file\"\r\n accept=\"image/*\"\r\n capture=\"environment\"\r\n (change)=\"onFileSelected($event)\"\r\n style=\"display: none\"\r\n />\r\n\r\n <ui-action-button [uiActionModel]=\"mobileButton\" (actionClick)=\"fileInput.click()\">\r\n </ui-action-button>\r\n </div>\r\n </ng-container>\r\n</div>\r\n", styles: [".photoWidgetContainer{border-radius:5px;width:100%;max-width:100%;display:flex;flex-direction:column;justify-content:center;border:1px solid #dee2e6}.message{text-align:center;color:#6b7280}video,canvas{border-top-right-radius:5px;border-top-left-radius:5px;width:100%}.controls{padding:.5rem;display:flex;gap:1rem;flex-direction:row;justify-content:center;background:#f8f9fa;border-top:1px solid #dee2e6;border-bottom-right-radius:5px;border-bottom-left-radius:5px}.controls ::ng-deep button{border-radius:3px}\n"], dependencies: [{ kind: "directive", type: i2.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: UiActionButtonComponent, selector: "ui-action-button", inputs: ["uiActionModel", "uiActionDescriptorService", "disabled"], outputs: ["actionClick", "actionDoubleClick"] }] }); }
9542
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "17.3.11", type: PhotoCaptureWidgetComponent, selector: "photo-capture-widget", inputs: { maxFileSize: "maxFileSize" }, outputs: { photoCaptured: "photoCaptured" }, viewQueries: [{ propertyName: "videoRef", first: true, predicate: ["video"], descendants: true }, { propertyName: "canvasRef", first: true, predicate: ["canvas"], descendants: true }, { propertyName: "fileInputRef", first: true, predicate: ["fileInput"], descendants: true }], ngImport: i0, template: "<div class=\"photoWidgetContainer\">\r\n <ng-container *ngIf=\"!isMobile()\">\r\n <video #video autoplay [hidden]=\"isCaptured || !cameraActive\"></video>\r\n <canvas #canvas [hidden]=\"!isCaptured || cameraActive\"></canvas>\r\n\r\n <ng-container *ngIf=\"!cameraActive && !isCaptured\">\r\n <p class=\"message\">Kapcsolja be a kamer\u00E1t a k\u00E9p k\u00E9sz\u00EDt\u00E9s\u00E9hez!</p>\r\n </ng-container>\r\n\r\n <div class=\"controls\">\r\n <!-- START CAMERA -->\r\n <ui-action-button [uiActionModel]=\"toggleCameraButton\" (actionClick)=\"toggleCamera()\">\r\n </ui-action-button>\r\n\r\n <!-- CAPTURE CAMERA -->\r\n <ui-action-button\r\n [disabled]=\"!cameraActive\"\r\n [uiActionModel]=\"captureButton\"\r\n (actionClick)=\"capturePhoto()\"\r\n >\r\n </ui-action-button>\r\n </div>\r\n </ng-container>\r\n\r\n <ng-container *ngIf=\"isMobile()\">\r\n <div class=\"controls\">\r\n <input\r\n #fileInput\r\n type=\"file\"\r\n accept=\"image/*\"\r\n capture=\"environment\"\r\n (change)=\"onFileSelected($event)\"\r\n style=\"display: none\"\r\n />\r\n\r\n <ui-action-button [uiActionModel]=\"captureButton\" (actionClick)=\"fileInput.click()\">\r\n </ui-action-button>\r\n </div>\r\n </ng-container>\r\n</div>\r\n", styles: [".photoWidgetContainer{border-radius:5px;width:100%;max-width:100%;display:flex;flex-direction:column;justify-content:center;border:1px solid #dee2e6}.message{text-align:center;color:#6b7280}video,canvas{border-top-right-radius:5px;border-top-left-radius:5px;width:100%}.controls{padding:.5rem;display:flex;gap:1rem;flex-direction:row;justify-content:center;background:#f8f9fa;border-top:1px solid #dee2e6;border-bottom-right-radius:5px;border-bottom-left-radius:5px}.controls ::ng-deep button{border-radius:3px}\n"], dependencies: [{ kind: "directive", type: i2.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: UiActionButtonComponent, selector: "ui-action-button", inputs: ["uiActionModel", "uiActionDescriptorService", "disabled"], outputs: ["actionClick", "actionDoubleClick"] }] }); }
9468
9543
  }
9469
9544
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.11", ngImport: i0, type: PhotoCaptureWidgetComponent, decorators: [{
9470
9545
  type: Component,
9471
- args: [{ selector: 'photo-capture-widget', template: "<div class=\"photoWidgetContainer\">\r\n <ng-container *ngIf=\"!isMobile()\">\r\n <video #video autoplay [hidden]=\"isCaptured || !cameraActive\"></video>\r\n <canvas #canvas [hidden]=\"!isCaptured || cameraActive\"></canvas>\r\n\r\n <ng-container *ngIf=\"!cameraActive && !isCaptured\">\r\n <p class=\"message\">Kapcsolja be a kamer\u00E1t a k\u00E9p k\u00E9sz\u00EDt\u00E9s\u00E9hez!</p>\r\n </ng-container>\r\n\r\n <div class=\"controls\">\r\n <!-- START CAMERA -->\r\n <ui-action-button\r\n *ngIf=\"!cameraActive\"\r\n [uiActionModel]=\"startCameraButton\"\r\n (actionClick)=\"startCamera()\"\r\n >\r\n </ui-action-button>\r\n\r\n <!-- STOP CAMERA -->\r\n <ui-action-button\r\n *ngIf=\"cameraActive\"\r\n [uiActionModel]=\"stopCameraButton\"\r\n (actionClick)=\"stopCamera()\"\r\n >\r\n </ui-action-button>\r\n\r\n <!-- CAPTURE CAMERA -->\r\n <ui-action-button\r\n [disabled]=\"!cameraActive\"\r\n [uiActionModel]=\"captureButton\"\r\n (actionClick)=\"capturePhoto()\"\r\n >\r\n </ui-action-button>\r\n </div>\r\n </ng-container>\r\n\r\n <ng-container *ngIf=\"isMobile()\">\r\n <div class=\"controls\">\r\n <input\r\n #fileInput\r\n type=\"file\"\r\n accept=\"image/*\"\r\n capture=\"environment\"\r\n (change)=\"onFileSelected($event)\"\r\n style=\"display: none\"\r\n />\r\n\r\n <ui-action-button [uiActionModel]=\"mobileButton\" (actionClick)=\"fileInput.click()\">\r\n </ui-action-button>\r\n </div>\r\n </ng-container>\r\n</div>\r\n", styles: [".photoWidgetContainer{border-radius:5px;width:100%;max-width:100%;display:flex;flex-direction:column;justify-content:center;border:1px solid #dee2e6}.message{text-align:center;color:#6b7280}video,canvas{border-top-right-radius:5px;border-top-left-radius:5px;width:100%}.controls{padding:.5rem;display:flex;gap:1rem;flex-direction:row;justify-content:center;background:#f8f9fa;border-top:1px solid #dee2e6;border-bottom-right-radius:5px;border-bottom-left-radius:5px}.controls ::ng-deep button{border-radius:3px}\n"] }]
9546
+ args: [{ selector: 'photo-capture-widget', template: "<div class=\"photoWidgetContainer\">\r\n <ng-container *ngIf=\"!isMobile()\">\r\n <video #video autoplay [hidden]=\"isCaptured || !cameraActive\"></video>\r\n <canvas #canvas [hidden]=\"!isCaptured || cameraActive\"></canvas>\r\n\r\n <ng-container *ngIf=\"!cameraActive && !isCaptured\">\r\n <p class=\"message\">Kapcsolja be a kamer\u00E1t a k\u00E9p k\u00E9sz\u00EDt\u00E9s\u00E9hez!</p>\r\n </ng-container>\r\n\r\n <div class=\"controls\">\r\n <!-- START CAMERA -->\r\n <ui-action-button [uiActionModel]=\"toggleCameraButton\" (actionClick)=\"toggleCamera()\">\r\n </ui-action-button>\r\n\r\n <!-- CAPTURE CAMERA -->\r\n <ui-action-button\r\n [disabled]=\"!cameraActive\"\r\n [uiActionModel]=\"captureButton\"\r\n (actionClick)=\"capturePhoto()\"\r\n >\r\n </ui-action-button>\r\n </div>\r\n </ng-container>\r\n\r\n <ng-container *ngIf=\"isMobile()\">\r\n <div class=\"controls\">\r\n <input\r\n #fileInput\r\n type=\"file\"\r\n accept=\"image/*\"\r\n capture=\"environment\"\r\n (change)=\"onFileSelected($event)\"\r\n style=\"display: none\"\r\n />\r\n\r\n <ui-action-button [uiActionModel]=\"captureButton\" (actionClick)=\"fileInput.click()\">\r\n </ui-action-button>\r\n </div>\r\n </ng-container>\r\n</div>\r\n", styles: [".photoWidgetContainer{border-radius:5px;width:100%;max-width:100%;display:flex;flex-direction:column;justify-content:center;border:1px solid #dee2e6}.message{text-align:center;color:#6b7280}video,canvas{border-top-right-radius:5px;border-top-left-radius:5px;width:100%}.controls{padding:.5rem;display:flex;gap:1rem;flex-direction:row;justify-content:center;background:#f8f9fa;border-top:1px solid #dee2e6;border-bottom-right-radius:5px;border-bottom-left-radius:5px}.controls ::ng-deep button{border-radius:3px}\n"] }]
9472
9547
  }], ctorParameters: () => [{ type: ComponentLibrary, decorators: [{
9473
9548
  type: Inject,
9474
9549
  args: [COMPONENT_LIBRARY]
@@ -9483,6 +9558,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.11", ngImpo
9483
9558
  }], fileInputRef: [{
9484
9559
  type: ViewChild,
9485
9560
  args: ['fileInput']
9561
+ }], maxFileSize: [{
9562
+ type: Input
9486
9563
  }], photoCaptured: [{
9487
9564
  type: Output
9488
9565
  }] } });
@@ -9495,7 +9572,49 @@ class VoiceRecordWidgetComponent {
9495
9572
  this.recordedBlob = null;
9496
9573
  this.time = '00:00';
9497
9574
  this.isPlaying = false;
9575
+ this.micButton = {
9576
+ uiAction: {
9577
+ descriptor: {
9578
+ type: UiActionButtonType.ICON,
9579
+ icon: 'microphone',
9580
+ iconPosition: IconPosition.PRE,
9581
+ color: this.color,
9582
+ },
9583
+ },
9584
+ };
9585
+ this.stopButton = {
9586
+ uiAction: {
9587
+ descriptor: {
9588
+ type: UiActionButtonType.ICON,
9589
+ icon: 'stop-circle',
9590
+ iconPosition: IconPosition.PRE,
9591
+ iconColor: 'red',
9592
+ color: this.color,
9593
+ },
9594
+ },
9595
+ };
9596
+ this.saveButton = {
9597
+ uiAction: {
9598
+ descriptor: {
9599
+ type: UiActionButtonType.ICON,
9600
+ icon: 'save',
9601
+ iconPosition: IconPosition.PRE,
9602
+ color: this.color,
9603
+ },
9604
+ },
9605
+ };
9606
+ this.playStopButton = {
9607
+ uiAction: {
9608
+ descriptor: {
9609
+ type: UiActionButtonType.ICON,
9610
+ icon: 'save',
9611
+ iconPosition: IconPosition.PRE,
9612
+ color: 'primary',
9613
+ },
9614
+ },
9615
+ };
9498
9616
  this.compLib = compLib ?? ComponentLibrary.PRIMENG;
9617
+ this.updatePlayStopButton();
9499
9618
  }
9500
9619
  ngOnInit() {
9501
9620
  const cssPrimaryColor = getComputedStyle(document.documentElement)
@@ -9509,9 +9628,9 @@ class VoiceRecordWidgetComponent {
9509
9628
  container: this.waveformRef.nativeElement,
9510
9629
  waveColor: this.color,
9511
9630
  progressColor: this.addAlphaToColor(this.color, 0.5),
9512
- height: 35,
9513
- barWidth: 10,
9514
- barGap: 5,
9631
+ height: 45,
9632
+ barWidth: 5,
9633
+ barGap: 1,
9515
9634
  barRadius: 5,
9516
9635
  plugins: [
9517
9636
  RecordPlugin.create({
@@ -9582,6 +9701,7 @@ class VoiceRecordWidgetComponent {
9582
9701
  if (this.recordedBlob) {
9583
9702
  this.isPlaying = !this.isPlaying;
9584
9703
  this.wavesurfer.playPause();
9704
+ this.updatePlayStopButton();
9585
9705
  }
9586
9706
  }
9587
9707
  ngOnDestroy() {
@@ -9610,12 +9730,31 @@ class VoiceRecordWidgetComponent {
9610
9730
  }
9611
9731
  return hexColor;
9612
9732
  }
9733
+ updatePlayStopButton() {
9734
+ let icon = this.isPlaying ? 'stop-circle' : 'play-circle';
9735
+ if (this.compLib !== ComponentLibrary.PRIMENG) {
9736
+ icon = this.isPlaying ? 'stop_circle' : 'play_circle';
9737
+ }
9738
+ let color = this.isPlaying ? 'red' : this.iconColor;
9739
+ this.playStopButton = {
9740
+ ...this.playStopButton,
9741
+ uiAction: {
9742
+ descriptor: {
9743
+ type: UiActionButtonType.ICON,
9744
+ iconColor: color,
9745
+ icon: icon,
9746
+ iconPosition: IconPosition.PRE,
9747
+ color: this.color,
9748
+ },
9749
+ },
9750
+ };
9751
+ }
9613
9752
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.11", ngImport: i0, type: VoiceRecordWidgetComponent, deps: [{ token: COMPONENT_LIBRARY, optional: true }], target: i0.ɵɵFactoryTarget.Component }); }
9614
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "17.3.11", type: VoiceRecordWidgetComponent, selector: "voice-record-widget", inputs: { color: "color", iconColor: "iconColor" }, outputs: { recordingSaved: "recordingSaved" }, viewQueries: [{ propertyName: "waveformRef", first: true, predicate: ["waveform"], descendants: true }], ngImport: i0, template: "<div class=\"recorderContainer\">\r\n <div class=\"recorderToolbar\">\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n <!-- Start Recording -->\r\n <button\r\n *ngIf=\"!isRecording\"\r\n pButton\r\n pRipple\r\n class=\"p-button-text\"\r\n (click)=\"startRecording()\"\r\n type=\"button\"\r\n ><smart-icon [icon]=\"'microphone'\" [color]=\"iconColor\"></smart-icon\r\n ></button>\r\n\r\n <!-- Stop Recording -->\r\n <button\r\n *ngIf=\"isRecording\"\r\n pButton\r\n pRipple\r\n class=\"p-button-text\"\r\n (click)=\"stopRecording()\"\r\n type=\"button\"\r\n ><smart-icon [icon]=\"'stop-circle'\" [color]=\"'red'\"></smart-icon\r\n ></button>\r\n\r\n } @else {\r\n <!-- Start Recording -->\r\n <button\r\n *ngIf=\"!isRecording\"\r\n mat-button\r\n class=\"p-button-text\"\r\n (click)=\"startRecording()\"\r\n type=\"button\"\r\n >\r\n <mat-icon [ngStyle]=\"{ color: iconColor }\">mic</mat-icon>\r\n </button>\r\n\r\n <!-- Stop Recording -->\r\n <button\r\n *ngIf=\"isRecording\"\r\n mat-button\r\n class=\"p-button-text\"\r\n (click)=\"stopRecording()\"\r\n type=\"button\"\r\n ><mat-icon [ngStyle]=\"{ color: 'red' }\">stop_circle</mat-icon>\r\n </button>\r\n }\r\n <div class=\"progress\">{{ time }}</div>\r\n </div>\r\n <div class=\"waveform\" #waveform></div>\r\n <div class=\"recorderToolbar\">\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n <!-- Save Recording -->\r\n <button\r\n *ngIf=\"recordedBlob\"\r\n pButton\r\n pRipple\r\n class=\"p-button-text\"\r\n (click)=\"saveRecording()\"\r\n [disabled]=\"isRecording\"\r\n type=\"button\"\r\n ><smart-icon [icon]=\"'save'\" [color]=\"iconColor\"></smart-icon\r\n ></button>\r\n\r\n <!-- Start Play -->\r\n <button\r\n *ngIf=\"recordedBlob\"\r\n pButton\r\n pRipple\r\n class=\"p-button-text\"\r\n (click)=\"replayRecording()\"\r\n [disabled]=\"isRecording\"\r\n type=\"button\"\r\n ><smart-icon\r\n [icon]=\"isPlaying ? 'stop-circle' : 'play-circle'\"\r\n [color]=\"isPlaying ? 'red' : iconColor\"\r\n ></smart-icon\r\n ></button>\r\n } @else {\r\n <!-- Save Recording -->\r\n <button\r\n *ngIf=\"recordedBlob\"\r\n mat-button\r\n class=\"p-button-text\"\r\n (click)=\"saveRecording()\"\r\n [disabled]=\"isRecording\"\r\n type=\"button\"\r\n >\r\n <mat-icon [ngStyle]=\"{ color: iconColor }\">save</mat-icon>\r\n </button>\r\n\r\n <!-- Start Play -->\r\n <button\r\n *ngIf=\"recordedBlob\"\r\n mat-button\r\n class=\"p-button-text\"\r\n (click)=\"replayRecording()\"\r\n [disabled]=\"isRecording\"\r\n type=\"button\"\r\n ><mat-icon [ngStyle]=\"{ color: isPlaying ? 'warn' : iconColor }\">\r\n {{ isPlaying ? 'stop_circle' : 'play_circle' }}\r\n </mat-icon>\r\n </button>\r\n }\r\n </div>\r\n</div>\r\n", styles: [".recorderContainer{box-shadow:0 3px 1px -2px #0003,0 2px 2px #00000024,0 1px 5px #0000001f;border-radius:5px;display:flex;flex-direction:row;padding:.2rem}.waveform{flex:1;align-content:center;height:35}.recorderToolbar{display:flex;flex-direction:row;gap:.2rem;padding:0 .5rem;align-items:center}.recorderToolbar ::ng-deep .p-button.p-button-icon-only{width:fit-content;padding:.2rem}.recorderToolbar ::ng-deep .mdc-button{min-width:unset;font-size:1.5rem;margin:unset}.recorderToolbar ::ng-deep .mat-mdc-button>.mat-icon{font-size:unset;width:unset;height:unset;padding:.2rem;margin:unset}.recorderToolbar ::ng-deep .p-button-text{background-color:transparent;border:unset;box-shadow:unset;padding:.2rem}.progress{align-content:center;font-size:1rem;height:100%;color:#6b7280}\n"], dependencies: [{ kind: "directive", type: i2.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: i2.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }, { kind: "component", type: i3.MatButton, selector: " button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button] ", exportAs: ["matButton"] }, { kind: "directive", type: i4.ButtonDirective, selector: "[pButton]", inputs: ["iconPos", "loadingIcon", "label", "icon", "loading", "severity", "raised", "rounded", "text", "outlined", "size", "plain"] }, { kind: "component", type: i4$1.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: SmartIconComponent, selector: "smart-icon", inputs: ["icon", "color"] }] }); }
9753
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "17.3.11", type: VoiceRecordWidgetComponent, selector: "voice-record-widget", inputs: { color: "color", iconColor: "iconColor" }, outputs: { recordingSaved: "recordingSaved" }, viewQueries: [{ propertyName: "waveformRef", first: true, predicate: ["waveform"], descendants: true }], ngImport: i0, template: "<div class=\"recorderContainer\">\r\n <div class=\"recorderToolbar\">\r\n <!-- Start Recording -->\r\n <ui-action-button\r\n *ngIf=\"!isRecording\"\r\n [uiActionModel]=\"micButton\"\r\n (actionClick)=\"startRecording()\"\r\n >\r\n </ui-action-button>\r\n\r\n <!-- Stop Recording -->\r\n <ui-action-button\r\n *ngIf=\"isRecording\"\r\n [uiActionModel]=\"stopButton\"\r\n (actionClick)=\"stopRecording()\"\r\n >\r\n </ui-action-button>\r\n\r\n <div class=\"progress\">{{ time }}</div>\r\n </div>\r\n <div class=\"waveform\" #waveform></div>\r\n <div class=\"recorderToolbar\">\r\n <!-- Save Recording -->\r\n <ui-action-button\r\n *ngIf=\"recordedBlob\"\r\n [uiActionModel]=\"saveButton\"\r\n (actionClick)=\"saveRecording()\"\r\n >\r\n </ui-action-button>\r\n\r\n <!-- Start/Stop Play -->\r\n <ui-action-button\r\n *ngIf=\"recordedBlob\"\r\n [uiActionModel]=\"playStopButton\"\r\n (actionClick)=\"replayRecording()\"\r\n >\r\n </ui-action-button>\r\n </div>\r\n</div>\r\n", styles: [".recorderContainer{border:1px solid #dee2e6;background:#f8f9fa;border-radius:5px;display:flex;flex-direction:row;padding:.2rem}.waveform{flex:1;align-content:center;height:35}.recorderToolbar{display:flex;flex-direction:row;gap:.2rem;padding:0 .5rem;align-items:center}.recorderToolbar ::ng-deep .p-button.p-button-icon-only{width:fit-content;padding:.2rem}.recorderToolbar ::ng-deep .mdc-button{min-width:unset;font-size:1.5rem;margin:unset}.recorderToolbar ::ng-deep .mat-mdc-button>.mat-icon{font-size:unset;width:unset;height:unset;padding:.2rem;margin:unset}.recorderToolbar ::ng-deep .p-button-text{background-color:transparent;border:unset;box-shadow:unset;padding:.2rem}.progress{align-content:center;font-size:1rem;height:100%;color:#6b7280}\n"], dependencies: [{ kind: "directive", type: i2.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: UiActionButtonComponent, selector: "ui-action-button", inputs: ["uiActionModel", "uiActionDescriptorService", "disabled"], outputs: ["actionClick", "actionDoubleClick"] }] }); }
9615
9754
  }
9616
9755
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.11", ngImport: i0, type: VoiceRecordWidgetComponent, decorators: [{
9617
9756
  type: Component,
9618
- args: [{ selector: 'voice-record-widget', template: "<div class=\"recorderContainer\">\r\n <div class=\"recorderToolbar\">\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n <!-- Start Recording -->\r\n <button\r\n *ngIf=\"!isRecording\"\r\n pButton\r\n pRipple\r\n class=\"p-button-text\"\r\n (click)=\"startRecording()\"\r\n type=\"button\"\r\n ><smart-icon [icon]=\"'microphone'\" [color]=\"iconColor\"></smart-icon\r\n ></button>\r\n\r\n <!-- Stop Recording -->\r\n <button\r\n *ngIf=\"isRecording\"\r\n pButton\r\n pRipple\r\n class=\"p-button-text\"\r\n (click)=\"stopRecording()\"\r\n type=\"button\"\r\n ><smart-icon [icon]=\"'stop-circle'\" [color]=\"'red'\"></smart-icon\r\n ></button>\r\n\r\n } @else {\r\n <!-- Start Recording -->\r\n <button\r\n *ngIf=\"!isRecording\"\r\n mat-button\r\n class=\"p-button-text\"\r\n (click)=\"startRecording()\"\r\n type=\"button\"\r\n >\r\n <mat-icon [ngStyle]=\"{ color: iconColor }\">mic</mat-icon>\r\n </button>\r\n\r\n <!-- Stop Recording -->\r\n <button\r\n *ngIf=\"isRecording\"\r\n mat-button\r\n class=\"p-button-text\"\r\n (click)=\"stopRecording()\"\r\n type=\"button\"\r\n ><mat-icon [ngStyle]=\"{ color: 'red' }\">stop_circle</mat-icon>\r\n </button>\r\n }\r\n <div class=\"progress\">{{ time }}</div>\r\n </div>\r\n <div class=\"waveform\" #waveform></div>\r\n <div class=\"recorderToolbar\">\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n <!-- Save Recording -->\r\n <button\r\n *ngIf=\"recordedBlob\"\r\n pButton\r\n pRipple\r\n class=\"p-button-text\"\r\n (click)=\"saveRecording()\"\r\n [disabled]=\"isRecording\"\r\n type=\"button\"\r\n ><smart-icon [icon]=\"'save'\" [color]=\"iconColor\"></smart-icon\r\n ></button>\r\n\r\n <!-- Start Play -->\r\n <button\r\n *ngIf=\"recordedBlob\"\r\n pButton\r\n pRipple\r\n class=\"p-button-text\"\r\n (click)=\"replayRecording()\"\r\n [disabled]=\"isRecording\"\r\n type=\"button\"\r\n ><smart-icon\r\n [icon]=\"isPlaying ? 'stop-circle' : 'play-circle'\"\r\n [color]=\"isPlaying ? 'red' : iconColor\"\r\n ></smart-icon\r\n ></button>\r\n } @else {\r\n <!-- Save Recording -->\r\n <button\r\n *ngIf=\"recordedBlob\"\r\n mat-button\r\n class=\"p-button-text\"\r\n (click)=\"saveRecording()\"\r\n [disabled]=\"isRecording\"\r\n type=\"button\"\r\n >\r\n <mat-icon [ngStyle]=\"{ color: iconColor }\">save</mat-icon>\r\n </button>\r\n\r\n <!-- Start Play -->\r\n <button\r\n *ngIf=\"recordedBlob\"\r\n mat-button\r\n class=\"p-button-text\"\r\n (click)=\"replayRecording()\"\r\n [disabled]=\"isRecording\"\r\n type=\"button\"\r\n ><mat-icon [ngStyle]=\"{ color: isPlaying ? 'warn' : iconColor }\">\r\n {{ isPlaying ? 'stop_circle' : 'play_circle' }}\r\n </mat-icon>\r\n </button>\r\n }\r\n </div>\r\n</div>\r\n", styles: [".recorderContainer{box-shadow:0 3px 1px -2px #0003,0 2px 2px #00000024,0 1px 5px #0000001f;border-radius:5px;display:flex;flex-direction:row;padding:.2rem}.waveform{flex:1;align-content:center;height:35}.recorderToolbar{display:flex;flex-direction:row;gap:.2rem;padding:0 .5rem;align-items:center}.recorderToolbar ::ng-deep .p-button.p-button-icon-only{width:fit-content;padding:.2rem}.recorderToolbar ::ng-deep .mdc-button{min-width:unset;font-size:1.5rem;margin:unset}.recorderToolbar ::ng-deep .mat-mdc-button>.mat-icon{font-size:unset;width:unset;height:unset;padding:.2rem;margin:unset}.recorderToolbar ::ng-deep .p-button-text{background-color:transparent;border:unset;box-shadow:unset;padding:.2rem}.progress{align-content:center;font-size:1rem;height:100%;color:#6b7280}\n"] }]
9757
+ args: [{ selector: 'voice-record-widget', template: "<div class=\"recorderContainer\">\r\n <div class=\"recorderToolbar\">\r\n <!-- Start Recording -->\r\n <ui-action-button\r\n *ngIf=\"!isRecording\"\r\n [uiActionModel]=\"micButton\"\r\n (actionClick)=\"startRecording()\"\r\n >\r\n </ui-action-button>\r\n\r\n <!-- Stop Recording -->\r\n <ui-action-button\r\n *ngIf=\"isRecording\"\r\n [uiActionModel]=\"stopButton\"\r\n (actionClick)=\"stopRecording()\"\r\n >\r\n </ui-action-button>\r\n\r\n <div class=\"progress\">{{ time }}</div>\r\n </div>\r\n <div class=\"waveform\" #waveform></div>\r\n <div class=\"recorderToolbar\">\r\n <!-- Save Recording -->\r\n <ui-action-button\r\n *ngIf=\"recordedBlob\"\r\n [uiActionModel]=\"saveButton\"\r\n (actionClick)=\"saveRecording()\"\r\n >\r\n </ui-action-button>\r\n\r\n <!-- Start/Stop Play -->\r\n <ui-action-button\r\n *ngIf=\"recordedBlob\"\r\n [uiActionModel]=\"playStopButton\"\r\n (actionClick)=\"replayRecording()\"\r\n >\r\n </ui-action-button>\r\n </div>\r\n</div>\r\n", styles: [".recorderContainer{border:1px solid #dee2e6;background:#f8f9fa;border-radius:5px;display:flex;flex-direction:row;padding:.2rem}.waveform{flex:1;align-content:center;height:35}.recorderToolbar{display:flex;flex-direction:row;gap:.2rem;padding:0 .5rem;align-items:center}.recorderToolbar ::ng-deep .p-button.p-button-icon-only{width:fit-content;padding:.2rem}.recorderToolbar ::ng-deep .mdc-button{min-width:unset;font-size:1.5rem;margin:unset}.recorderToolbar ::ng-deep .mat-mdc-button>.mat-icon{font-size:unset;width:unset;height:unset;padding:.2rem;margin:unset}.recorderToolbar ::ng-deep .p-button-text{background-color:transparent;border:unset;box-shadow:unset;padding:.2rem}.progress{align-content:center;font-size:1rem;height:100%;color:#6b7280}\n"] }]
9619
9758
  }], ctorParameters: () => [{ type: ComponentLibrary, decorators: [{
9620
9759
  type: Inject,
9621
9760
  args: [COMPONENT_LIBRARY]
@@ -9747,6 +9886,12 @@ class UiActionFileUploadDialogComponent {
9747
9886
  this.uploadWidgetType = UploadWidgetType;
9748
9887
  this.maxSizeMb = 25;
9749
9888
  this.uploadedFiles = [];
9889
+ this.uploadFormatMap = {
9890
+ [UploadWidgetType.ALL]: [],
9891
+ [UploadWidgetType.NORMAL]: [],
9892
+ [UploadWidgetType.IMAGE]: ['image/png', 'image/jpeg', 'image/jpg', 'image/gif', 'image/webp'],
9893
+ [UploadWidgetType.SOUND]: ['audio/mpeg', 'audio/wav', 'audio/webm', 'audio/ogg'],
9894
+ };
9750
9895
  this.code = this.service.action.code;
9751
9896
  this.setUp();
9752
9897
  }
@@ -9754,10 +9899,19 @@ class UiActionFileUploadDialogComponent {
9754
9899
  this.service._destroy$.next();
9755
9900
  this.cancel();
9756
9901
  }
9902
+ isMobile() {
9903
+ return /iPhone|iPad|iPod|Android/i.test(navigator.userAgent);
9904
+ }
9757
9905
  async setUp() {
9758
9906
  this.descriptor = await this.manager.getActionDescriptor(this.service.action);
9759
9907
  this.isMultiple = this.service.isMultiple;
9760
9908
  this.maxSizeMb = Number(this.descriptor.upload?.maxSize);
9909
+ if (this.descriptor.upload?.uploadWidgetType) {
9910
+ this.descriptor.upload.formats =
9911
+ this.descriptor.upload.formats ??
9912
+ this.uploadFormatMap[this.descriptor.upload.uploadWidgetType].join(', ');
9913
+ this.fileFormats = [this.descriptor.upload.formats];
9914
+ }
9761
9915
  // fileFormats = this.descriptor.upload?.formats;
9762
9916
  this.i18n = {
9763
9917
  addFile: this.descriptor.upload?.title ?? 'dokumentum hozzáadása',
@@ -9819,9 +9973,11 @@ class UiActionFileUploadDialogComponent {
9819
9973
  for (let file of event.files) {
9820
9974
  this.uploadedFiles.push(file);
9821
9975
  }
9976
+ this.hasFiles = true;
9822
9977
  }
9823
9978
  onRemove(event) {
9824
9979
  this.uploadedFiles = [];
9980
+ this.hasFiles = false;
9825
9981
  }
9826
9982
  uploadFiles(event) {
9827
9983
  this.service.onSave(this.uploadedFiles);
@@ -9831,9 +9987,11 @@ class UiActionFileUploadDialogComponent {
9831
9987
  }
9832
9988
  uploadRecording(file) {
9833
9989
  this.loadFilesIntoWidget([file]);
9990
+ this.hasFiles = true;
9834
9991
  }
9835
9992
  uploadImage(files) {
9836
9993
  this.loadFilesIntoWidget(files);
9994
+ this.hasFiles = true;
9837
9995
  }
9838
9996
  loadFilesIntoWidget(files) {
9839
9997
  if (ComponentLibrary.PRIMENG === this.compLib) {
@@ -9854,15 +10012,12 @@ class UiActionFileUploadDialogComponent {
9854
10012
  this.fileUploadMaterial.files.push(...files);
9855
10013
  }
9856
10014
  }
9857
- getContainsFiles() {
9858
- return this.uploadedFiles.length > 0;
9859
- }
9860
10015
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.11", ngImport: i0, type: UiActionFileUploadDialogComponent, deps: [{ token: 'fileUploadDialogService' }, { token: COMPONENT_LIBRARY }, { token: UiActionDescriptorService }, { token: i0.ChangeDetectorRef }], target: i0.ɵɵFactoryTarget.Component }); }
9861
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "17.3.11", type: UiActionFileUploadDialogComponent, selector: "lib-ui-action-file-upload-dialog", viewQueries: [{ propertyName: "fileUploadPrime", first: true, predicate: ["fileUploadPrimeNg"], descendants: true }, { propertyName: "fileUploadMaterial", first: true, predicate: ["fileUploadMaterial"], descendants: true }], ngImport: i0, template: "<div class=\"folderNameDialogContainer\">\r\n <div class=\"headerContainer\">\r\n <h3 class=\"color-accent-700\">\r\n {{ getTitle() }}\r\n </h3>\r\n @if(compLib === componentLibrary.MATERIAL) {\r\n <button mat-icon-button (click)=\"cancel()\">\r\n <smart-icon [color]=\"'primary'\" [icon]=\"'X'\"></smart-icon>\r\n </button>\r\n }@else {\r\n <p-button icon=\"pi pi-times\" [rounded]=\"true\" [text]=\"true\" (click)=\"cancel()\" />\r\n }\r\n </div>\r\n <p>\r\n {{ getText() }}\r\n </p>\r\n\r\n <!-- IMAGE TYPE -->\r\n <ng-container\r\n *ngIf=\"\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.IMAGE ||\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.ALL\r\n \"\r\n >\r\n <photo-capture-widget (photoCaptured)=\"uploadImage($event)\"> </photo-capture-widget>\r\n </ng-container>\r\n\r\n <!-- SOUND TYPE -->\r\n <ng-container\r\n *ngIf=\"\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.SOUND ||\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.ALL\r\n \"\r\n >\r\n <voice-record-widget (recordingSaved)=\"uploadRecording($event)\"> </voice-record-widget>\r\n </ng-container>\r\n\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n\r\n <p-fileUpload\r\n #fileUploadPrimeNg\r\n name=\"files[]\"\r\n url=\"\"\r\n (onSend)=\"uploadFiles($event)\"\r\n (onSelect)=\"onSelect($event)\"\r\n (onRemove)=\"onRemove($event)\"\r\n [multiple]=\"isMultiple\"\r\n [accept]=\"this.descriptor?.upload?.formats ?? ''\"\r\n [maxFileSize]=\"maxSizeMb * 1024 * 1024\"\r\n uploadLabel=\"Felt\u00F6lt\u00E9s\"\r\n cancelLabel=\"M\u00E9gsem\"\r\n chooseLabel=\"V\u00E1laszt\u00E1s\"\r\n >\r\n <ng-template pTemplate=\"content\">\r\n <div class=\"uploadField\" [hidden]=\"getContainsFiles()\">\r\n <smart-icon [icon]=\"'upload'\"></smart-icon>\r\n <span class=\"message\">H\u00FAzza ide a f\u00E1jlokat.</span>\r\n </div>\r\n </ng-template>\r\n </p-fileUpload>\r\n\r\n }@else{\r\n\r\n <smartfileuploader\r\n #fileUploadMaterial\r\n [i18n]=\"i18n\"\r\n [fileFormats]=\"fileFormats\"\r\n [maxSizeMb]=\"maxSizeMb\"\r\n [uploadCallback]=\"upload.bind(this)\"\r\n [isMultiple]=\"isMultiple\"\r\n ></smartfileuploader>\r\n }\r\n\r\n <div class=\"folderNameDialogButtonsContainer\">\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n <p-button\r\n class=\"p-button-text\"\r\n (click)=\"cancel()\"\r\n type=\"button\"\r\n [label]=\"getCancelButtonLabel()\"\r\n [icon]=\"'pi pi-times'\"\r\n ></p-button>\r\n }@else{\r\n <button mat-button color=\"accent\" [color]=\"getCancelButtonColor()\" (click)=\"cancel()\">\r\n {{ getCancelButtonLabel() }}\r\n </button>\r\n <!-- <button mat-raised-button [color]=\"getActionButtonColor()\" (click)=\"upload()\">\r\n {{ getActionButtonLabel() }}\r\n </button> -->\r\n }\r\n </div>\r\n</div>\r\n", styles: [".folderNameDialogContainer{display:flex;flex-direction:column;justify-content:center;gap:1rem;min-width:30vw}photo-capture-widget{width:100%;max-width:100%;overflow:hidden;display:flex;flex-direction:column;align-items:center}.headerContainer{display:flex;flex-direction:row;justify-content:space-between;align-items:center;padding-top:1rem}.headerContainer h3{margin:0}.folderNameDialogButtonsContainer{display:flex;flex-direction:row;justify-content:flex-end;gap:.5rem}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-buttonbar{display:flex!important;flex-direction:row;justify-content:center;flex-wrap:wrap;gap:1rem}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-row>div{width:fit-content}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-content{padding:unset;min-height:5vh;align-content:center;text-align:center}.message{text-align:center;color:#6b7280}.uploadField{display:flex;flex-direction:row;justify-content:center;align-items:center;gap:1rem}\n"], dependencies: [{ kind: "directive", type: i2.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: i3.MatButton, selector: " button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button] ", exportAs: ["matButton"] }, { kind: "component", type: i3.MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "component", type: i4.Button, selector: "p-button", inputs: ["type", "iconPos", "icon", "badge", "label", "disabled", "loading", "loadingIcon", "raised", "rounded", "text", "plain", "severity", "outlined", "link", "tabindex", "size", "style", "styleClass", "badgeClass", "ariaLabel", "autofocus"], outputs: ["onClick", "onFocus", "onBlur"] }, { kind: "directive", type: i5$1.PrimeTemplate, selector: "[pTemplate]", inputs: ["type", "pTemplate"] }, { kind: "component", type: SmartIconComponent, selector: "smart-icon", inputs: ["icon", "color"] }, { kind: "component", type: i7.FileUpload, selector: "p-fileUpload", inputs: ["name", "url", "method", "multiple", "accept", "disabled", "auto", "withCredentials", "maxFileSize", "invalidFileSizeMessageSummary", "invalidFileSizeMessageDetail", "invalidFileTypeMessageSummary", "invalidFileTypeMessageDetail", "invalidFileLimitMessageDetail", "invalidFileLimitMessageSummary", "style", "styleClass", "previewWidth", "chooseLabel", "uploadLabel", "cancelLabel", "chooseIcon", "uploadIcon", "cancelIcon", "showUploadButton", "showCancelButton", "mode", "headers", "customUpload", "fileLimit", "uploadStyleClass", "cancelStyleClass", "removeStyleClass", "chooseStyleClass", "files"], outputs: ["onBeforeUpload", "onSend", "onUpload", "onError", "onClear", "onRemove", "onSelect", "onProgress", "uploadHandler", "onImageError", "onRemoveUploadedFile"] }, { kind: "component", type: SmartfileuploaderComponent, selector: "smartfileuploader", inputs: ["uploadCallback", "fileFormats", "maxSizeMb", "i18n", "useIconButton", "isMultiple"] }, { kind: "component", type: VoiceRecordWidgetComponent, selector: "voice-record-widget", inputs: ["color", "iconColor"], outputs: ["recordingSaved"] }, { kind: "component", type: PhotoCaptureWidgetComponent, selector: "photo-capture-widget", outputs: ["photoCaptured"] }] }); }
10016
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "17.3.11", type: UiActionFileUploadDialogComponent, selector: "lib-ui-action-file-upload-dialog", viewQueries: [{ propertyName: "fileUploadPrime", first: true, predicate: ["fileUploadPrimeNg"], descendants: true }, { propertyName: "fileUploadMaterial", first: true, predicate: ["fileUploadMaterial"], descendants: true }], ngImport: i0, template: "<div class=\"folderNameDialogContainer\">\r\n <div class=\"headerContainer\">\r\n <h3 class=\"color-accent-700\">\r\n {{ getTitle() }}\r\n </h3>\r\n @if(compLib === componentLibrary.MATERIAL) {\r\n <button mat-icon-button (click)=\"cancel()\">\r\n <smart-icon [color]=\"'primary'\" [icon]=\"'X'\"></smart-icon>\r\n </button>\r\n }@else {\r\n <p-button icon=\"pi pi-times\" [rounded]=\"true\" [text]=\"true\" (click)=\"cancel()\" />\r\n }\r\n </div>\r\n <p>\r\n {{ getText() }}\r\n </p>\r\n\r\n <!-- IMAGE TYPE -->\r\n <ng-container\r\n *ngIf=\"\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.IMAGE ||\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.ALL\r\n \"\r\n >\r\n <photo-capture-widget\r\n [maxFileSize]=\"maxSizeMb * 1024 * 1024\"\r\n (photoCaptured)=\"uploadImage($event)\"\r\n >\r\n </photo-capture-widget>\r\n </ng-container>\r\n\r\n <!-- SOUND TYPE -->\r\n <ng-container\r\n *ngIf=\"\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.SOUND ||\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.ALL\r\n \"\r\n >\r\n <voice-record-widget (recordingSaved)=\"uploadRecording($event)\"> </voice-record-widget>\r\n </ng-container>\r\n\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n\r\n <p-fileUpload\r\n #fileUploadPrimeNg\r\n name=\"files[]\"\r\n url=\"\"\r\n (onSend)=\"uploadFiles($event)\"\r\n (onSelect)=\"onSelect($event)\"\r\n (onRemove)=\"onRemove($event)\"\r\n [multiple]=\"isMultiple\"\r\n [accept]=\"this.descriptor?.upload?.formats ?? ''\"\r\n [maxFileSize]=\"maxSizeMb * 1024 * 1024\"\r\n uploadLabel=\"Felt\u00F6lt\u00E9s\"\r\n cancelLabel=\"M\u00E9gsem\"\r\n chooseLabel=\"V\u00E1laszt\u00E1s\"\r\n >\r\n <ng-template pTemplate=\"content\" *ngIf=\"!hasFiles && !isMobile()\">\r\n <div class=\"uploadField\">\r\n <smart-icon [icon]=\"'upload'\"></smart-icon>\r\n <span class=\"message\">H\u00FAzza ide a f\u00E1jlokat.</span>\r\n </div>\r\n </ng-template>\r\n </p-fileUpload>\r\n\r\n }@else{\r\n\r\n <smartfileuploader\r\n #fileUploadMaterial\r\n [i18n]=\"i18n\"\r\n [fileFormats]=\"fileFormats\"\r\n [maxSizeMb]=\"maxSizeMb\"\r\n [uploadCallback]=\"upload.bind(this)\"\r\n [isMultiple]=\"isMultiple\"\r\n ></smartfileuploader>\r\n }\r\n\r\n <div class=\"folderNameDialogButtonsContainer\">\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n <p-button\r\n class=\"p-button-text\"\r\n (click)=\"cancel()\"\r\n type=\"button\"\r\n [label]=\"getCancelButtonLabel()\"\r\n [icon]=\"'pi pi-times'\"\r\n ></p-button>\r\n }@else{\r\n <button mat-button color=\"accent\" [color]=\"getCancelButtonColor()\" (click)=\"cancel()\">\r\n {{ getCancelButtonLabel() }}\r\n </button>\r\n <!-- <button mat-raised-button [color]=\"getActionButtonColor()\" (click)=\"upload()\">\r\n {{ getActionButtonLabel() }}\r\n </button> -->\r\n }\r\n </div>\r\n</div>\r\n", styles: [".folderNameDialogContainer{display:flex;flex-direction:column;justify-content:center;gap:1rem;min-width:30vw}photo-capture-widget{width:100%;max-width:100%;overflow:hidden;display:flex;flex-direction:column;align-items:center}.headerContainer{display:flex;flex-direction:row;justify-content:space-between;align-items:center;padding-top:1rem}.headerContainer h3{margin:0}.folderNameDialogButtonsContainer{display:flex;flex-direction:row;justify-content:flex-end;gap:.5rem}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-buttonbar{display:flex!important;flex-direction:row;justify-content:center;flex-wrap:wrap;gap:1rem}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-row>div{width:fit-content}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-content{padding:unset;align-content:center;text-align:center}.message{text-align:center;color:#6b7280}.uploadField{display:flex;flex-direction:row;justify-content:center;align-items:center;gap:1rem;padding:1rem}.folderNameDialogContainer ::ng-deep .p-fileupload-row{border-top:1px solid #dee2e6;border-bottom:1px solid #dee2e6}@media (max-width: 900px){.folderNameDialogContainer{width:100%}}\n"], dependencies: [{ kind: "directive", type: i2.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: i3.MatButton, selector: " button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button] ", exportAs: ["matButton"] }, { kind: "component", type: i3.MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "component", type: i4.Button, selector: "p-button", inputs: ["type", "iconPos", "icon", "badge", "label", "disabled", "loading", "loadingIcon", "raised", "rounded", "text", "plain", "severity", "outlined", "link", "tabindex", "size", "style", "styleClass", "badgeClass", "ariaLabel", "autofocus"], outputs: ["onClick", "onFocus", "onBlur"] }, { kind: "directive", type: i5$1.PrimeTemplate, selector: "[pTemplate]", inputs: ["type", "pTemplate"] }, { kind: "component", type: SmartIconComponent, selector: "smart-icon", inputs: ["icon", "color"] }, { kind: "component", type: i7.FileUpload, selector: "p-fileUpload", inputs: ["name", "url", "method", "multiple", "accept", "disabled", "auto", "withCredentials", "maxFileSize", "invalidFileSizeMessageSummary", "invalidFileSizeMessageDetail", "invalidFileTypeMessageSummary", "invalidFileTypeMessageDetail", "invalidFileLimitMessageDetail", "invalidFileLimitMessageSummary", "style", "styleClass", "previewWidth", "chooseLabel", "uploadLabel", "cancelLabel", "chooseIcon", "uploadIcon", "cancelIcon", "showUploadButton", "showCancelButton", "mode", "headers", "customUpload", "fileLimit", "uploadStyleClass", "cancelStyleClass", "removeStyleClass", "chooseStyleClass", "files"], outputs: ["onBeforeUpload", "onSend", "onUpload", "onError", "onClear", "onRemove", "onSelect", "onProgress", "uploadHandler", "onImageError", "onRemoveUploadedFile"] }, { kind: "component", type: SmartfileuploaderComponent, selector: "smartfileuploader", inputs: ["uploadCallback", "fileFormats", "maxSizeMb", "i18n", "useIconButton", "isMultiple"] }, { kind: "component", type: VoiceRecordWidgetComponent, selector: "voice-record-widget", inputs: ["color", "iconColor"], outputs: ["recordingSaved"] }, { kind: "component", type: PhotoCaptureWidgetComponent, selector: "photo-capture-widget", inputs: ["maxFileSize"], outputs: ["photoCaptured"] }] }); }
9862
10017
  }
9863
10018
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.11", ngImport: i0, type: UiActionFileUploadDialogComponent, decorators: [{
9864
10019
  type: Component,
9865
- args: [{ selector: 'lib-ui-action-file-upload-dialog', template: "<div class=\"folderNameDialogContainer\">\r\n <div class=\"headerContainer\">\r\n <h3 class=\"color-accent-700\">\r\n {{ getTitle() }}\r\n </h3>\r\n @if(compLib === componentLibrary.MATERIAL) {\r\n <button mat-icon-button (click)=\"cancel()\">\r\n <smart-icon [color]=\"'primary'\" [icon]=\"'X'\"></smart-icon>\r\n </button>\r\n }@else {\r\n <p-button icon=\"pi pi-times\" [rounded]=\"true\" [text]=\"true\" (click)=\"cancel()\" />\r\n }\r\n </div>\r\n <p>\r\n {{ getText() }}\r\n </p>\r\n\r\n <!-- IMAGE TYPE -->\r\n <ng-container\r\n *ngIf=\"\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.IMAGE ||\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.ALL\r\n \"\r\n >\r\n <photo-capture-widget (photoCaptured)=\"uploadImage($event)\"> </photo-capture-widget>\r\n </ng-container>\r\n\r\n <!-- SOUND TYPE -->\r\n <ng-container\r\n *ngIf=\"\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.SOUND ||\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.ALL\r\n \"\r\n >\r\n <voice-record-widget (recordingSaved)=\"uploadRecording($event)\"> </voice-record-widget>\r\n </ng-container>\r\n\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n\r\n <p-fileUpload\r\n #fileUploadPrimeNg\r\n name=\"files[]\"\r\n url=\"\"\r\n (onSend)=\"uploadFiles($event)\"\r\n (onSelect)=\"onSelect($event)\"\r\n (onRemove)=\"onRemove($event)\"\r\n [multiple]=\"isMultiple\"\r\n [accept]=\"this.descriptor?.upload?.formats ?? ''\"\r\n [maxFileSize]=\"maxSizeMb * 1024 * 1024\"\r\n uploadLabel=\"Felt\u00F6lt\u00E9s\"\r\n cancelLabel=\"M\u00E9gsem\"\r\n chooseLabel=\"V\u00E1laszt\u00E1s\"\r\n >\r\n <ng-template pTemplate=\"content\">\r\n <div class=\"uploadField\" [hidden]=\"getContainsFiles()\">\r\n <smart-icon [icon]=\"'upload'\"></smart-icon>\r\n <span class=\"message\">H\u00FAzza ide a f\u00E1jlokat.</span>\r\n </div>\r\n </ng-template>\r\n </p-fileUpload>\r\n\r\n }@else{\r\n\r\n <smartfileuploader\r\n #fileUploadMaterial\r\n [i18n]=\"i18n\"\r\n [fileFormats]=\"fileFormats\"\r\n [maxSizeMb]=\"maxSizeMb\"\r\n [uploadCallback]=\"upload.bind(this)\"\r\n [isMultiple]=\"isMultiple\"\r\n ></smartfileuploader>\r\n }\r\n\r\n <div class=\"folderNameDialogButtonsContainer\">\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n <p-button\r\n class=\"p-button-text\"\r\n (click)=\"cancel()\"\r\n type=\"button\"\r\n [label]=\"getCancelButtonLabel()\"\r\n [icon]=\"'pi pi-times'\"\r\n ></p-button>\r\n }@else{\r\n <button mat-button color=\"accent\" [color]=\"getCancelButtonColor()\" (click)=\"cancel()\">\r\n {{ getCancelButtonLabel() }}\r\n </button>\r\n <!-- <button mat-raised-button [color]=\"getActionButtonColor()\" (click)=\"upload()\">\r\n {{ getActionButtonLabel() }}\r\n </button> -->\r\n }\r\n </div>\r\n</div>\r\n", styles: [".folderNameDialogContainer{display:flex;flex-direction:column;justify-content:center;gap:1rem;min-width:30vw}photo-capture-widget{width:100%;max-width:100%;overflow:hidden;display:flex;flex-direction:column;align-items:center}.headerContainer{display:flex;flex-direction:row;justify-content:space-between;align-items:center;padding-top:1rem}.headerContainer h3{margin:0}.folderNameDialogButtonsContainer{display:flex;flex-direction:row;justify-content:flex-end;gap:.5rem}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-buttonbar{display:flex!important;flex-direction:row;justify-content:center;flex-wrap:wrap;gap:1rem}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-row>div{width:fit-content}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-content{padding:unset;min-height:5vh;align-content:center;text-align:center}.message{text-align:center;color:#6b7280}.uploadField{display:flex;flex-direction:row;justify-content:center;align-items:center;gap:1rem}\n"] }]
10020
+ args: [{ selector: 'lib-ui-action-file-upload-dialog', template: "<div class=\"folderNameDialogContainer\">\r\n <div class=\"headerContainer\">\r\n <h3 class=\"color-accent-700\">\r\n {{ getTitle() }}\r\n </h3>\r\n @if(compLib === componentLibrary.MATERIAL) {\r\n <button mat-icon-button (click)=\"cancel()\">\r\n <smart-icon [color]=\"'primary'\" [icon]=\"'X'\"></smart-icon>\r\n </button>\r\n }@else {\r\n <p-button icon=\"pi pi-times\" [rounded]=\"true\" [text]=\"true\" (click)=\"cancel()\" />\r\n }\r\n </div>\r\n <p>\r\n {{ getText() }}\r\n </p>\r\n\r\n <!-- IMAGE TYPE -->\r\n <ng-container\r\n *ngIf=\"\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.IMAGE ||\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.ALL\r\n \"\r\n >\r\n <photo-capture-widget\r\n [maxFileSize]=\"maxSizeMb * 1024 * 1024\"\r\n (photoCaptured)=\"uploadImage($event)\"\r\n >\r\n </photo-capture-widget>\r\n </ng-container>\r\n\r\n <!-- SOUND TYPE -->\r\n <ng-container\r\n *ngIf=\"\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.SOUND ||\r\n this.descriptor?.upload?.uploadWidgetType == uploadWidgetType.ALL\r\n \"\r\n >\r\n <voice-record-widget (recordingSaved)=\"uploadRecording($event)\"> </voice-record-widget>\r\n </ng-container>\r\n\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n\r\n <p-fileUpload\r\n #fileUploadPrimeNg\r\n name=\"files[]\"\r\n url=\"\"\r\n (onSend)=\"uploadFiles($event)\"\r\n (onSelect)=\"onSelect($event)\"\r\n (onRemove)=\"onRemove($event)\"\r\n [multiple]=\"isMultiple\"\r\n [accept]=\"this.descriptor?.upload?.formats ?? ''\"\r\n [maxFileSize]=\"maxSizeMb * 1024 * 1024\"\r\n uploadLabel=\"Felt\u00F6lt\u00E9s\"\r\n cancelLabel=\"M\u00E9gsem\"\r\n chooseLabel=\"V\u00E1laszt\u00E1s\"\r\n >\r\n <ng-template pTemplate=\"content\" *ngIf=\"!hasFiles && !isMobile()\">\r\n <div class=\"uploadField\">\r\n <smart-icon [icon]=\"'upload'\"></smart-icon>\r\n <span class=\"message\">H\u00FAzza ide a f\u00E1jlokat.</span>\r\n </div>\r\n </ng-template>\r\n </p-fileUpload>\r\n\r\n }@else{\r\n\r\n <smartfileuploader\r\n #fileUploadMaterial\r\n [i18n]=\"i18n\"\r\n [fileFormats]=\"fileFormats\"\r\n [maxSizeMb]=\"maxSizeMb\"\r\n [uploadCallback]=\"upload.bind(this)\"\r\n [isMultiple]=\"isMultiple\"\r\n ></smartfileuploader>\r\n }\r\n\r\n <div class=\"folderNameDialogButtonsContainer\">\r\n @if(compLib === componentLibrary.PRIMENG) {\r\n <p-button\r\n class=\"p-button-text\"\r\n (click)=\"cancel()\"\r\n type=\"button\"\r\n [label]=\"getCancelButtonLabel()\"\r\n [icon]=\"'pi pi-times'\"\r\n ></p-button>\r\n }@else{\r\n <button mat-button color=\"accent\" [color]=\"getCancelButtonColor()\" (click)=\"cancel()\">\r\n {{ getCancelButtonLabel() }}\r\n </button>\r\n <!-- <button mat-raised-button [color]=\"getActionButtonColor()\" (click)=\"upload()\">\r\n {{ getActionButtonLabel() }}\r\n </button> -->\r\n }\r\n </div>\r\n</div>\r\n", styles: [".folderNameDialogContainer{display:flex;flex-direction:column;justify-content:center;gap:1rem;min-width:30vw}photo-capture-widget{width:100%;max-width:100%;overflow:hidden;display:flex;flex-direction:column;align-items:center}.headerContainer{display:flex;flex-direction:row;justify-content:space-between;align-items:center;padding-top:1rem}.headerContainer h3{margin:0}.folderNameDialogButtonsContainer{display:flex;flex-direction:row;justify-content:flex-end;gap:.5rem}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-buttonbar{display:flex!important;flex-direction:row;justify-content:center;flex-wrap:wrap;gap:1rem}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-row>div{width:fit-content}.folderNameDialogContainer ::ng-deep .p-fileupload .p-fileupload-content{padding:unset;align-content:center;text-align:center}.message{text-align:center;color:#6b7280}.uploadField{display:flex;flex-direction:row;justify-content:center;align-items:center;gap:1rem;padding:1rem}.folderNameDialogContainer ::ng-deep .p-fileupload-row{border-top:1px solid #dee2e6;border-bottom:1px solid #dee2e6}@media (max-width: 900px){.folderNameDialogContainer{width:100%}}\n"] }]
9866
10021
  }], ctorParameters: () => [{ type: UiActionFileUploadDialogService, decorators: [{
9867
10022
  type: Inject,
9868
10023
  args: ['fileUploadDialogService']
@@ -16493,7 +16648,7 @@ class LeafletMap extends AbstractMap {
16493
16648
  const point = this.map.latLngToContainerPoint(latLng);
16494
16649
  const text = tooltip.getContent();
16495
16650
  // Tooltip szöveg megjelenítése
16496
- ctx.font = 'bold 20px sans-serif';
16651
+ ctx.font = 'bold 30px sans-serif';
16497
16652
  ctx.fillStyle = 'black';
16498
16653
  ctx.strokeStyle = 'white';
16499
16654
  ctx.lineWidth = 4;