@sumaris-net/ngx-components 18.17.6 → 18.17.7-rc1

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 (154) hide show
  1. package/doc/changelog.md +3 -3
  2. package/esm2022/src/app/admin/users/users-select.modal.mjs +1 -1
  3. package/esm2022/src/app/admin/users/users.mjs +1 -1
  4. package/esm2022/src/app/core/about/about.modal.mjs +1 -1
  5. package/esm2022/src/app/core/account/account.page.mjs +1 -1
  6. package/esm2022/src/app/core/account/new-token.form.mjs +1 -1
  7. package/esm2022/src/app/core/account/new-token.modal.mjs +1 -1
  8. package/esm2022/src/app/core/account/password/change-password.form.mjs +1 -1
  9. package/esm2022/src/app/core/account/password/change-password.page.mjs +1 -1
  10. package/esm2022/src/app/core/account/token.table.mjs +1 -1
  11. package/esm2022/src/app/core/auth/auth.form.mjs +1 -1
  12. package/esm2022/src/app/core/auth/auth.modal.mjs +1 -1
  13. package/esm2022/src/app/core/auth/reset-password.modal.mjs +1 -1
  14. package/esm2022/src/app/core/form/array/testing/form-array.test.mjs +1 -1
  15. package/esm2022/src/app/core/form/buttons/form-buttons-bar.component.mjs +1 -1
  16. package/esm2022/src/app/core/form/entity/entity-metadata.component.mjs +1 -1
  17. package/esm2022/src/app/core/form/list/list.form.mjs +1 -1
  18. package/esm2022/src/app/core/form/properties/properties.form.mjs +1 -1
  19. package/esm2022/src/app/core/form/properties/properties.table.mjs +1 -1
  20. package/esm2022/src/app/core/form/properties/testing/properties-form.test.mjs +1 -1
  21. package/esm2022/src/app/core/form/text-popover/testing/text-popover.testing.mjs +1 -1
  22. package/esm2022/src/app/core/form/text-popover/text-popover.component.mjs +1 -1
  23. package/esm2022/src/app/core/form/username/username.form.mjs +1 -1
  24. package/esm2022/src/app/core/home/home.mjs +1 -1
  25. package/esm2022/src/app/core/icon/icon.component.mjs +1 -1
  26. package/esm2022/src/app/core/install/install-upgrade-card.component.mjs +1 -1
  27. package/esm2022/src/app/core/menu/menu.component.mjs +1 -1
  28. package/esm2022/src/app/core/menu/sub-menu-tab.directive.mjs +1 -1
  29. package/esm2022/src/app/core/menu/testing/menu-other.testing.mjs +1 -1
  30. package/esm2022/src/app/core/menu/testing/menu.testing.mjs +1 -1
  31. package/esm2022/src/app/core/offline/update-offline-mode-card.component.mjs +1 -1
  32. package/esm2022/src/app/core/peer/select-peer.modal.mjs +1 -1
  33. package/esm2022/src/app/core/register/register-confirm.page.mjs +1 -1
  34. package/esm2022/src/app/core/register/register.form.mjs +1 -1
  35. package/esm2022/src/app/core/register/register.modal.mjs +1 -1
  36. package/esm2022/src/app/core/services/local-settings.service.mjs +33 -33
  37. package/esm2022/src/app/core/services/model/config.model.mjs +1 -1
  38. package/esm2022/src/app/core/services/pipes/account.pipes.mjs +1 -1
  39. package/esm2022/src/app/core/services/pipes/department-to-string.pipe.mjs +1 -1
  40. package/esm2022/src/app/core/services/pipes/person-to-string.pipe.mjs +1 -1
  41. package/esm2022/src/app/core/services/pipes/referential-to-string.pipe.mjs +1 -1
  42. package/esm2022/src/app/core/services/pipes/usage-mode.pipes.mjs +1 -1
  43. package/esm2022/src/app/core/settings/settings.page.mjs +1 -1
  44. package/esm2022/src/app/core/table/column/actions-column.component.mjs +1 -1
  45. package/esm2022/src/app/core/table/column/nav-actions-column.component.mjs +1 -1
  46. package/esm2022/src/app/core/table/column/row-field.component.mjs +1 -1
  47. package/esm2022/src/app/core/table/table-select-columns.component.mjs +1 -1
  48. package/esm2022/src/app/core/table/table.pipes.mjs +1 -1
  49. package/esm2022/src/app/core/table/table.utils.mjs +1 -1
  50. package/esm2022/src/app/core/table/testing/table.testing.mjs +1 -1
  51. package/esm2022/src/app/core/table/testing/table2.testing.mjs +1 -1
  52. package/esm2022/src/app/shared/audio/audio.testing.mjs +1 -1
  53. package/esm2022/src/app/shared/debug/debug.component.mjs +1 -1
  54. package/esm2022/src/app/shared/directives/autofocus.directive.mjs +1 -1
  55. package/esm2022/src/app/shared/directives/autoresize.directive.mjs +1 -1
  56. package/esm2022/src/app/shared/directives/autotitle.directive.mjs +1 -1
  57. package/esm2022/src/app/shared/directives/drag-and-drop.directive.mjs +1 -1
  58. package/esm2022/src/app/shared/directives/ng-var.directive.mjs +1 -1
  59. package/esm2022/src/app/shared/directives/resizable/resizable.component.mjs +1 -1
  60. package/esm2022/src/app/shared/directives/resizable/resizable.directive.mjs +1 -1
  61. package/esm2022/src/app/shared/directives/throttled-click.directive.mjs +1 -1
  62. package/esm2022/src/app/shared/form/field.component.mjs +1 -1
  63. package/esm2022/src/app/shared/form/loading-spinner.mjs +11 -11
  64. package/esm2022/src/app/shared/hotkeys/dialog/hotkeys-dialog.component.mjs +1 -1
  65. package/esm2022/src/app/shared/image/gallery/image-gallery.component.mjs +3 -3
  66. package/esm2022/src/app/shared/image/gallery/testing/gallery.testing.mjs +1 -1
  67. package/esm2022/src/app/shared/markdown/markdown.component.mjs +17 -17
  68. package/esm2022/src/app/shared/markdown/markdown.directive.mjs +1 -1
  69. package/esm2022/src/app/shared/markdown/markdown.modal.mjs +1 -1
  70. package/esm2022/src/app/shared/markdown/markdown.service.mjs +1 -1
  71. package/esm2022/src/app/shared/markdown/testing/markdown.test.mjs +1 -1
  72. package/esm2022/src/app/shared/material/autocomplete/material.autocomplete.mjs +1 -1
  73. package/esm2022/src/app/shared/material/autocomplete/testing/autocomplete.test.mjs +1 -1
  74. package/esm2022/src/app/shared/material/badge/badge.directive.mjs +1 -1
  75. package/esm2022/src/app/shared/material/badge/badge.test.mjs +3 -3
  76. package/esm2022/src/app/shared/material/boolean/material.boolean.mjs +1 -1
  77. package/esm2022/src/app/shared/material/boolean/testing/boolean.test.page.mjs +1 -1
  78. package/esm2022/src/app/shared/material/chips/material.chips.mjs +1 -1
  79. package/esm2022/src/app/shared/material/chips/testing/chips.test.mjs +1 -1
  80. package/esm2022/src/app/shared/material/datetime/material.date.mjs +1 -1
  81. package/esm2022/src/app/shared/material/datetime/material.dateshort.mjs +1 -1
  82. package/esm2022/src/app/shared/material/datetime/material.datetime.mjs +3 -3
  83. package/esm2022/src/app/shared/material/datetime/testing/mat-date-time.test.mjs +1 -1
  84. package/esm2022/src/app/shared/material/datetime/testing/mat-date.test.mjs +1 -1
  85. package/esm2022/src/app/shared/material/datetime/testing/mat-dateshort.test.mjs +1 -1
  86. package/esm2022/src/app/shared/material/duration/material.duration.mjs +1 -1
  87. package/esm2022/src/app/shared/material/duration/testing/mat-duration.test.mjs +1 -1
  88. package/esm2022/src/app/shared/material/latlong/material.latlong-input.mjs +1 -1
  89. package/esm2022/src/app/shared/material/latlong/material.latlong.mjs +1 -1
  90. package/esm2022/src/app/shared/material/latlong/testing/latlong.test.mjs +1 -1
  91. package/esm2022/src/app/shared/material/swipe/material.swipe.mjs +1 -1
  92. package/esm2022/src/app/shared/material/swipe/testing/swipe.test.mjs +1 -1
  93. package/esm2022/src/app/shared/material/test/test-component.mjs +43 -43
  94. package/esm2022/src/app/shared/material/testing/common.test.mjs +1 -1
  95. package/esm2022/src/app/shared/material/text/testing/text-form.testing.mjs +1 -1
  96. package/esm2022/src/app/shared/material/text/text-form.component.mjs +1 -1
  97. package/esm2022/src/app/shared/named-filter/named-filter-selector.component.mjs +1 -1
  98. package/esm2022/src/app/shared/named-filter/testing/named-filter-selector.testing.mjs +1 -1
  99. package/esm2022/src/app/shared/pipes/arrays.pipe.mjs +1 -1
  100. package/esm2022/src/app/shared/pipes/badge.pipes.mjs +1 -1
  101. package/esm2022/src/app/shared/pipes/colors.pipe.mjs +1 -1
  102. package/esm2022/src/app/shared/pipes/date-diff-duration.pipe.mjs +1 -1
  103. package/esm2022/src/app/shared/pipes/date-format.pipe.mjs +1 -1
  104. package/esm2022/src/app/shared/pipes/date-from-now.pipe.mjs +1 -1
  105. package/esm2022/src/app/shared/pipes/dates.pipe.mjs +1 -1
  106. package/esm2022/src/app/shared/pipes/display-with.pipe.mjs +1 -1
  107. package/esm2022/src/app/shared/pipes/duration.pipe.mjs +1 -1
  108. package/esm2022/src/app/shared/pipes/file-size.pipe.mjs +1 -1
  109. package/esm2022/src/app/shared/pipes/form.pipes.mjs +1 -1
  110. package/esm2022/src/app/shared/pipes/highlight.pipe.mjs +1 -1
  111. package/esm2022/src/app/shared/pipes/html.pipes.mjs +1 -1
  112. package/esm2022/src/app/shared/pipes/latlong-format.pipe.mjs +1 -1
  113. package/esm2022/src/app/shared/pipes/maps.pipe.mjs +1 -1
  114. package/esm2022/src/app/shared/pipes/maskito.pipe.mjs +1 -1
  115. package/esm2022/src/app/shared/pipes/math.pipes.mjs +1 -1
  116. package/esm2022/src/app/shared/pipes/ng-init.pipe.mjs +1 -1
  117. package/esm2022/src/app/shared/pipes/number-format.pipe.mjs +1 -1
  118. package/esm2022/src/app/shared/pipes/observable.pipes.mjs +1 -1
  119. package/esm2022/src/app/shared/pipes/property.pipes.mjs +1 -1
  120. package/esm2022/src/app/shared/pipes/selection.pipes.mjs +1 -1
  121. package/esm2022/src/app/shared/pipes/string.pipes.mjs +1 -1
  122. package/esm2022/src/app/shared/pipes/translate-context.pipe.mjs +1 -1
  123. package/esm2022/src/app/shared/pipes/types.pipes.mjs +1 -1
  124. package/esm2022/src/app/shared/pipes/url.pipes.mjs +1 -1
  125. package/esm2022/src/app/shared/storage/storage-explorer.component.mjs +1 -1
  126. package/esm2022/src/app/shared/testing/maskito.test.mjs +1 -1
  127. package/esm2022/src/app/shared/testing/observable.test.mjs +1 -1
  128. package/esm2022/src/app/shared/testing/tests.page.mjs +1 -1
  129. package/esm2022/src/app/shared/toast/toast.testing.mjs +1 -1
  130. package/esm2022/src/app/shared/toolbar/modal-toolbar.mjs +1 -1
  131. package/esm2022/src/app/shared/toolbar/toolbar.mjs +1 -1
  132. package/esm2022/src/app/shared/upload-file/testing/upload-file.testing.mjs +1 -1
  133. package/esm2022/src/app/shared/upload-file/upload-file-popover.component.mjs +1 -1
  134. package/esm2022/src/app/shared/upload-file/upload-file.component.mjs +1 -1
  135. package/esm2022/src/app/social/feed/feed.component.mjs +3 -3
  136. package/esm2022/src/app/social/feed/feed.directive.mjs +1 -1
  137. package/esm2022/src/app/social/feed/feed.page.mjs +1 -1
  138. package/esm2022/src/app/social/feed/testing/feed.testing.mjs +1 -1
  139. package/esm2022/src/app/social/job/progression/job-progression.component.mjs +1 -1
  140. package/esm2022/src/app/social/job/progression/job-progression.icon.mjs +1 -1
  141. package/esm2022/src/app/social/job/progression/job-progression.list.mjs +1 -1
  142. package/esm2022/src/app/social/job/testing/job-progression.testing.mjs +1 -1
  143. package/esm2022/src/app/social/message/message.form.mjs +1 -1
  144. package/esm2022/src/app/social/message/message.modal.mjs +1 -1
  145. package/esm2022/src/app/social/user-event/notification/user-event-notification.icon.mjs +1 -1
  146. package/esm2022/src/app/social/user-event/notification/user-event-notification.list.mjs +1 -1
  147. package/esm2022/src/app/social/user-event/notification/user-event-notification.modal.mjs +1 -1
  148. package/esm2022/src/app/social/user-event/testing/user-event.testing.mjs +1 -1
  149. package/fesm2022/sumaris-net.ngx-components.mjs +108 -108
  150. package/fesm2022/sumaris-net.ngx-components.mjs.map +1 -1
  151. package/package.json +1 -1
  152. package/src/app/core/services/local-settings.service.d.ts +1 -0
  153. package/src/app/shared/inputs.d.ts +1 -1
  154. package/src/theme/_ngx-components.scss +1009 -1009
@@ -11195,11 +11195,11 @@ class MatDateTime {
11195
11195
  this.cd.markForCheck();
11196
11196
  }
11197
11197
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: MatDateTime, deps: [{ token: i1.MomentDateAdapter }, { token: i1$1.TranslateService }, { token: i1$3.UntypedFormBuilder }, { token: i0.Renderer2 }, { token: i0.ChangeDetectorRef }, { token: i1$3.FormGroupDirective, optional: true }, { token: MAT_FORM_FIELD_DEFAULT_OPTIONS }], target: i0.ɵɵFactoryTarget.Component });
11198
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.13", type: MatDateTime, selector: "mat-date-time-field", inputs: { logPrefix: "logPrefix", placeholder: "placeholder", floatLabel: "floatLabel", mobile: ["mobile", "mobile", booleanAttribute], compact: ["compact", "compact", booleanAttribute], autofocus: ["autofocus", "autofocus", booleanAttribute], clearable: ["clearable", "clearable", booleanAttribute], startDate: "startDate", datePickerFilter: "datePickerFilter", allowNoTime: ["allowNoTime", "allowNoTime", booleanAttribute], dottedMinutesInGap: ["dottedMinutesInGap", "dottedMinutesInGap", booleanAttribute], timeHoursOnly: ["timeHoursOnly", "timeHoursOnly", booleanAttribute], debug: ["debug", "debug", booleanAttribute], appearance: "appearance", subscriptSizing: "subscriptSizing", formControl: "formControl", formControlName: "formControlName", required: "required", readonly: "readonly", tabindex: "tabindex" }, outputs: { focused: "focus", blurred: "blur", keydownEscape: "keydown.escape", keyupEnter: "keyup.enter" }, providers: [DEFAULT_VALUE_ACCESSOR$2], viewQueries: [{ propertyName: "datePicker", first: true, predicate: ["datePicker"], descendants: true }, { propertyName: "timePicker", first: true, predicate: ["timePicker"], descendants: true }, { propertyName: "_matInputs", predicate: ["matInput"], descendants: true }], ngImport: i0, template: "<!-- readonly -->\n@if (readonly) {\n <mat-form-field\n [floatLabel]=\"floatLabel | asFloatLabelType\"\n [appearance]=\"appearance\"\n [subscriptSizing]=\"subscriptSizing\"\n class=\"mat-form-field-disabled\"\n >\n <div matPrefix>\n <ng-container *ngTemplateOutlet=\"matPrefixTemplate\"></ng-container>\n </div>\n\n @if (floatLabel !== 'never' && !!placeholder) {\n <mat-label>{{ placeholder }}</mat-label>\n }\n\n <input matInput hidden type=\"text\" readonly [formControl]=\"_formControl\" />\n <ion-text>{{ _formControl.value | dateFormat: { pattern: displayPattern } }}</ion-text>\n\n <div matSuffix>\n <ng-container *ngTemplateOutlet=\"matSuffixTemplate\"></ng-container>\n </div>\n\n <!-- hints -->\n <mat-hint [class.cdk-visually-hidden]=\"_formControl.invalid\">\n <ng-container *ngTemplateOutlet=\"matHintTemplate\"></ng-container>\n </mat-hint>\n </mat-form-field>\n} @else {\n <!-- writable + time -->\n <ion-grid class=\"ion-no-padding {{ appearance }}\">\n <ion-row class=\"ion-no-padding no-wrap\">\n <!-- Day -->\n <ion-col class=\"day ion-no-padding\" [style.--button-count]=\"clearable ? 2 : 1\">\n <mat-form-field\n [floatLabel]=\"floatLabel | asFloatLabelType\"\n [appearance]=\"appearance\"\n [subscriptSizing]=\"'dynamic'\"\n [class.mdc-text-field--invalid]=\"_formControl.touched && (dateControl.invalid || _formControl.invalid)\"\n (click)=\"_openDatePickerIfMobile($event, datePicker)\"\n (focus)=\"_openDatePickerIfMobile($event, datePicker)\"\n >\n <div matPrefix>\n <ng-container *ngTemplateOutlet=\"matPrefixTemplate\"></ng-container>\n </div>\n\n @if (floatLabel !== 'never' && !!placeholder) {\n <mat-label>{{ placeholder }}</mat-label>\n }\n\n <!-- Day input (mobile) -->\n @if (mobile) {\n <input\n #matInput\n autocomplete=\"off\"\n type=\"text\"\n class=\"mat-mdc-form-field-input-control mdc-text-field__input\"\n [formControl]=\"dateControl\"\n [required]=\"required\"\n [tabindex]=\"tabindex\"\n readonly\n />\n <input\n matInput\n hidden\n type=\"text\"\n readonly\n [formControl]=\"_formControl\"\n [matDatepicker]=\"datePicker\"\n [matDatepickerFilter]=\"datePickerFilter\"\n (dateChange)=\"_onDatePickerChange($event)\"\n />\n } @else {\n <!-- Day input (desktop) -->\n <input\n matInput\n #matInput\n autocomplete=\"off\"\n type=\"text\"\n class=\"mat-input-element\"\n [maskito]=\"maskitoDateOptions\"\n [formControl]=\"dateControl\"\n [placeholder]=\"datePlaceholder | translate\"\n (focus)=\"filterInputTextFocusEvent($event)\"\n (blur)=\"filterInputTextBlurEvent($event)\"\n (keyup.enter)=\"keyupEnter.emit($event)\"\n (keyup.arrowDown)=\"openDatePicker($event, datePicker)\"\n (keyup.escape)=\"_preventEvent($event)\"\n [required]=\"required\"\n [tabindex]=\"tabindex\"\n [appAutofocus]=\"autofocus\"\n />\n <input\n type=\"text\"\n [formControl]=\"_formControl\"\n hidden\n [matDatepicker]=\"datePicker\"\n [matDatepickerFilter]=\"datePickerFilter\"\n (dateChange)=\"_onDatePickerChange($event)\"\n readonly\n />\n }\n\n <button\n type=\"button\"\n mat-icon-button\n tabindex=\"-1\"\n matSuffix\n (click)=\"openDatePicker($event, datePicker)\"\n [disabled]=\"_formControl.disabled\"\n >\n <mat-icon>{{ mobile ? 'date_range' : 'keyboard_arrow_down' }}</mat-icon>\n </button>\n @if (clearable) {\n <button\n matSuffix\n mat-icon-button\n tabindex=\"-1\"\n type=\"button\"\n (click)=\"clear($event)\"\n [hidden]=\"_formControl.disabled || !_formControl.value\"\n >\n <mat-icon>close</mat-icon>\n </button>\n }\n </mat-form-field>\n\n <!-- The date picker -->\n <mat-datepicker #datePicker\n [touchUi]=\"mobile\" [disabled]=\"disabled\"\n [startAt]=\"startDate\"\n [xPosition]=\"!mobile ? 'end' : undefined\">\n <!-- Date picker buttons -->\n @if (mobile) {\n <mat-datepicker-actions>\n <!-- Cancel button -->\n <ion-button fill=\"clear\" color=\"dark\" matDatepickerCancel>\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\n </ion-button>\n <!-- Apply button -->\n <ion-button fill=\"solid\" color=\"tertiary\" matDatepickerApply>\n <ion-label>{{ timeControl.value || ('COMMON.TIME' | translate) }}</ion-label>\n <ion-icon slot=\"end\" name=\"chevron-forward\"></ion-icon>\n </ion-button>\n </mat-datepicker-actions>\n }\n </mat-datepicker>\n </ion-col>\n\n <!-- Hour -->\n <ion-col class=\"hour ion-no-padding\" [style.--button-count]=\"compact ? 0 : 1\">\n <mat-form-field\n [floatLabel]=\"floatLabel | asFloatLabelType\"\n [appearance]=\"appearance\"\n [subscriptSizing]=\"'dynamic'\"\n [class.mdc-text-field--invalid]=\"_formControl.touched && (timeControl.invalid || _formControl.invalid)\"\n >\n @if (floatLabel !== 'never' && !!placeholder) {\n <mat-label translate>COMMON.TIME</mat-label>\n }\n\n <!-- Hour input (mobile) -->\n @if (mobile) {\n <input\n #matInput\n type=\"text\"\n class=\"mat-mdc-form-field-input-control mdc-text-field__input\"\n [formControl]=\"timeControl\"\n [required]=\"requiredTime\"\n (click)=\"openTimePicker($event)\"\n readonly\n />\n\n <!-- Hide the final (hidden) input -->\n <input\n matInput\n hidden\n type=\"text\"\n readonly\n [formControl]=\"timeControl\"\n [required]=\"required\"\n [ngxMatTimepicker]=\"timePicker\"\n [format]=\"24\"\n />\n } @else {\n <!-- Hour input (desktop) -->\n <input\n matInput\n #matInput\n type=\"text\"\n [formControl]=\"timeControl\"\n [maskito]=\"maskitoTimeOptions\"\n class=\"mat-input-element\"\n autocomplete=\"off\"\n [placeholder]=\"timePlaceholder | translate\"\n [required]=\"requiredTime\"\n (keyup.enter)=\"keyupEnter.emit($event)\"\n (keyup.arrowDown)=\"openTimePicker($event)\"\n (keyup.escape)=\"_preventEvent($event)\"\n (focus)=\"filterInputTextFocusEvent($event)\"\n (blur)=\"filterInputTextBlurEvent($event)\"\n [tabindex]=\"tabindex !== undefined ? tabindex + 1 : undefined\"\n />\n <!-- Hide the final (hidden) input -->\n <input\n hidden\n type=\"text\"\n readonly\n [formControl]=\"timeControl\"\n [required]=\"requiredTime\"\n [ngxMatTimepicker]=\"timePicker\"\n [format]=\"24\"\n />\n }\n\n @if (!compact) {\n <button\n matSuffix\n type=\"button\"\n mat-icon-button\n tabindex=\"-1\"\n [disabled]=\"_formControl.disabled\"\n (click)=\"openTimePicker($event)\"\n >\n <mat-icon>{{ !compact && mobile ? 'access_time' : 'keyboard_arrow_down' }}</mat-icon>\n </button>\n }\n <ngx-mat-timepicker\n #timePicker\n [isEsc]=\"!mobile\"\n [defaultTime]=\"'00:00'\"\n [cancelBtnTmpl]=\"timePickerCancelButton\"\n [confirmBtnTmpl]=\"timePickerOkButton\"\n [preventOverlayClick]=\"mobile\"\n [enableKeyboardInput]=\"!mobile\"\n [dottedMinutesInGap]=\"dottedMinutesInGap\"\n [hoursOnly]=\"timeHoursOnly\"\n [appendToInput]=\"!mobile\"\n (timeSet)=\"_onTimePickerChanged($event)\"\n color=\"accent\"\n ></ngx-mat-timepicker>\n </mat-form-field>\n </ion-col>\n </ion-row>\n </ion-grid>\n\n <!-- Do the same as MatFormField since angular 15 (see component source)-->\n <div\n class=\"mat-mdc-form-field-subscript-wrapper\"\n [class.mat-mdc-form-field-bottom-align]=\"subscriptSizing === 'fixed'\"\n [class.mat-mdc-form-field-subscript-dynamic-size]=\"subscriptSizing === 'dynamic'\"\n >\n @if (_formControl.touched && _formControl.errors; as errors) {\n <!-- errors -->\n <div class=\"mat-mdc-form-field-error-wrapper\">\n @if (errors | mapKeys | arrayFirst; as errorKey) {\n @switch (errorKey) {\n @case ('required') {\n <mat-error translate>ERROR.FIELD_REQUIRED</mat-error>\n }\n @case ('validDate') {\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_TIME</mat-error>\n }\n @case ('dateIsAfter') {\n <mat-error>\n {{ 'ERROR.FIELD_NOT_VALID_DATE_AFTER' | translate: _formControl.errors.dateIsAfter }}\n </mat-error>\n }\n @case ('dateIsBefore') {\n <mat-error>\n {{ 'ERROR.FIELD_NOT_VALID_DATE_BEFORE' | translate: _formControl.errors.dateIsBefore }}\n </mat-error>\n }\n @case ('dateRange') {\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_RANGE</mat-error>\n }\n @case ('dateMaxDuration') {\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_MAX_DURATION</mat-error>\n }\n @case ('dateMinDuration') {\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_MIN_DURATION</mat-error>\n }\n @case ('msg') {\n <mat-error>\n {{\n _formControl.errors.msg?.key || _formControl.errors.msg | translate: _formControl.errors.msg?.params\n }}\n </mat-error>\n }\n @default {\n <ng-container *ngTemplateOutlet=\"matErrorTemplate\"></ng-container>\n }\n }\n } @else {\n <ng-container *ngTemplateOutlet=\"matErrorTemplate\"></ng-container>\n }\n </div>\n } @else {\n <!-- hints -->\n <ng-container *ngTemplateOutlet=\"matHintTemplate\"></ng-container>\n }\n </div>\n}\n\n<!-- cancel button -->\n<ng-template #timePickerCancelButton>\n <ion-button fill=\"clear\" color=\"dark\">\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\n </ion-button>\n</ng-template>\n\n<!-- confirm button -->\n<ng-template #timePickerOkButton>\n <ion-button fill=\"solid\" color=\"tertiary\">\n <ion-label translate>COMMON.BTN_VALIDATE</ion-label>\n </ion-button>\n</ng-template>\n\n<ng-template #matPrefixTemplate>\n <ng-content select=\"[matPrefix]\"></ng-content>\n</ng-template>\n\n<ng-template #matSuffixTemplate>\n <ng-content select=\"[matSuffix]\"></ng-content>\n</ng-template>\n\n<ng-template #matErrorTemplate>\n <ng-content select=\"mat-error,[matError]\"></ng-content>\n</ng-template>\n\n<ng-template #matHintTemplate>\n <div class=\"mat-mdc-form-field-hint-wrapper\">\n <ng-content select=\"mat-hint:not([align='end']),[matHint]\"></ng-content>\n <div class=\"mat-mdc-form-field-hint-spacer\"></div>\n <ng-content select=\"mat-hint[align='end']\"></ng-content>\n </div>\n</ng-template>\n", styles: [":host{display:inline-block;width:100%;position:relative;--ion-grid-column-padding: 0}input[type=number]::-webkit-inner-spin-button,input[type=number]::-webkit-outer-spin-button{-webkit-appearance:none;margin:0}mat-form-field input[readonly]{-webkit-user-select:none!important;user-select:none!important}mat-form-field .datetime-md{padding:0!important}mat-form-field button[hidden]{display:none}ion-row.no-wrap{flex-wrap:nowrap}ion-grid ion-col{--button-width: calc(var(--button-count, 0px) * 24px)}ion-grid.fill ion-col.day{--min-width: calc(100px + var(--button-width, 0px));min-width:var(--min-width)}ion-grid.fill ion-col.hour{--min-width: calc(55px + var(--button-width, 0px));--max-width: calc(65px + var(--button-width, 0px));min-width:var(--min-width);max-width:var(--max-width)}ion-grid.fill ion-col.hour mat-form-field{width:100%}ion-grid.fill ion-col.hour mat-form-field mat-label,ion-grid.fill ion-col.hour mat-form-field input[type=text]{text-align:left;min-width:52px}ion-grid.outline ion-col.day{min-width:calc(110px + var(--button-width))}ion-grid.outline ion-col.hour{--min-width: calc(65px + var(--button-width));--max-width: calc(75px + var(--button-width))}mat-form-field.mat-form-field-disabled ion-col.day{min-width:150px}.hour mat-form-field.mat-mdc-form-field-should-float .mat-mdc-form-field-placeholder{max-width:inherit}\n"], dependencies: [{ kind: "directive", type: i3$1.NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "component", type: i2$1.IonButton, selector: "ion-button", inputs: ["buttonType", "color", "disabled", "download", "expand", "fill", "form", "href", "mode", "rel", "routerAnimation", "routerDirection", "shape", "size", "strong", "target", "type"] }, { kind: "component", type: i2$1.IonCol, selector: "ion-col", inputs: ["offset", "offsetLg", "offsetMd", "offsetSm", "offsetXl", "offsetXs", "pull", "pullLg", "pullMd", "pullSm", "pullXl", "pullXs", "push", "pushLg", "pushMd", "pushSm", "pushXl", "pushXs", "size", "sizeLg", "sizeMd", "sizeSm", "sizeXl", "sizeXs"] }, { kind: "component", type: i2$1.IonGrid, selector: "ion-grid", inputs: ["fixed"] }, { kind: "component", type: i2$1.IonIcon, selector: "ion-icon", inputs: ["color", "flipRtl", "icon", "ios", "lazy", "md", "mode", "name", "sanitize", "size", "src"] }, { kind: "component", type: i2$1.IonLabel, selector: "ion-label", inputs: ["color", "mode", "position"] }, { kind: "component", type: i2$1.IonRow, selector: "ion-row" }, { kind: "component", type: i2$1.IonText, selector: "ion-text", inputs: ["color", "mode"] }, { kind: "directive", type: i1$3.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$3.RequiredValidator, selector: ":not([type=checkbox])[required][formControlName],:not([type=checkbox])[required][formControl],:not([type=checkbox])[required][ngModel]", inputs: ["required"] }, { kind: "directive", type: i1$3.FormControlDirective, selector: "[formControl]", inputs: ["formControl", "disabled", "ngModel"], outputs: ["ngModelChange"], exportAs: ["ngForm"] }, { kind: "component", type: i3.MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: i3.MatLabel, selector: "mat-label" }, { kind: "directive", type: i3.MatHint, selector: "mat-hint", inputs: ["align", "id"] }, { kind: "directive", type: i3.MatError, selector: "mat-error, [matError]", inputs: ["id"] }, { kind: "directive", type: i3.MatPrefix, selector: "[matPrefix], [matIconPrefix], [matTextPrefix]", inputs: ["matTextPrefix"] }, { kind: "directive", type: i3.MatSuffix, selector: "[matSuffix], [matIconSuffix], [matTextSuffix]", inputs: ["matTextSuffix"] }, { kind: "directive", type: i4.MatInput, selector: "input[matInput], textarea[matInput], select[matNativeControl], input[matNativeControl], textarea[matNativeControl]", inputs: ["disabled", "id", "placeholder", "name", "required", "type", "errorStateMatcher", "aria-describedby", "value", "readonly"], exportAs: ["matInput"] }, { kind: "component", type: i6$1.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i9.MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "component", type: i10.MatDatepicker, selector: "mat-datepicker", exportAs: ["matDatepicker"] }, { kind: "directive", type: i10.MatDatepickerInput, selector: "input[matDatepicker]", inputs: ["matDatepicker", "min", "max", "matDatepickerFilter"], exportAs: ["matDatepickerInput"] }, { kind: "component", type: i10.MatDatepickerActions, selector: "mat-datepicker-actions, mat-date-range-picker-actions" }, { kind: "directive", type: i10.MatDatepickerCancel, selector: "[matDatepickerCancel], [matDateRangePickerCancel]" }, { kind: "directive", type: i10.MatDatepickerApply, selector: "[matDatepickerApply], [matDateRangePickerApply]" }, { kind: "directive", type: i11.MaskitoDirective, selector: "[maskito]", inputs: ["maskito", "maskitoElement"] }, { kind: "directive", type: i1$1.TranslateDirective, selector: "[translate],[ngx-translate]", inputs: ["translate", "translateParams"] }, { kind: "directive", type: AutofocusDirective, selector: "[autofocus], input[appAutofocus]", inputs: ["appAutofocus", "autofocusDelay"] }, { kind: "component", type: i13.NgxMatTimepickerComponent, selector: "ngx-mat-timepicker", inputs: ["appendToInput", "color", "dottedMinutesInGap", "enableKeyboardInput", "format", "minutesGap", "cancelBtnTmpl", "confirmBtnTmpl", "defaultTime", "disableAnimation", "editableHintTmpl", "hoursOnly", "isEsc", "max", "min", "preventOverlayClick", "timepickerClass"], outputs: ["closed", "hourSelected", "opened", "timeChanged", "timeSet"] }, { kind: "directive", type: i13.NgxMatTimepickerDirective, selector: "[ngxMatTimepicker]", inputs: ["format", "max", "min", "ngxMatTimepicker", "value", "disableClick", "disabled"] }, { kind: "pipe", type: DateFormatPipe, name: "dateFormat" }, { kind: "pipe", type: ArrayFirstPipe, name: "arrayFirst" }, { kind: "pipe", type: MapKeysPipe, name: "mapKeys" }, { kind: "pipe", type: AsFloatLabelTypePipe, name: "asFloatLabelType" }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
11198
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.13", type: MatDateTime, selector: "mat-date-time-field", inputs: { logPrefix: "logPrefix", placeholder: "placeholder", floatLabel: "floatLabel", mobile: ["mobile", "mobile", booleanAttribute], compact: ["compact", "compact", booleanAttribute], autofocus: ["autofocus", "autofocus", booleanAttribute], clearable: ["clearable", "clearable", booleanAttribute], startDate: "startDate", datePickerFilter: "datePickerFilter", allowNoTime: ["allowNoTime", "allowNoTime", booleanAttribute], dottedMinutesInGap: ["dottedMinutesInGap", "dottedMinutesInGap", booleanAttribute], timeHoursOnly: ["timeHoursOnly", "timeHoursOnly", booleanAttribute], debug: ["debug", "debug", booleanAttribute], appearance: "appearance", subscriptSizing: "subscriptSizing", formControl: "formControl", formControlName: "formControlName", required: "required", readonly: "readonly", tabindex: "tabindex" }, outputs: { focused: "focus", blurred: "blur", keydownEscape: "keydown.escape", keyupEnter: "keyup.enter" }, providers: [DEFAULT_VALUE_ACCESSOR$2], viewQueries: [{ propertyName: "datePicker", first: true, predicate: ["datePicker"], descendants: true }, { propertyName: "timePicker", first: true, predicate: ["timePicker"], descendants: true }, { propertyName: "_matInputs", predicate: ["matInput"], descendants: true }], ngImport: i0, template: "<!-- readonly -->\r\n@if (readonly) {\r\n <mat-form-field\r\n [floatLabel]=\"floatLabel | asFloatLabelType\"\r\n [appearance]=\"appearance\"\r\n [subscriptSizing]=\"subscriptSizing\"\r\n class=\"mat-form-field-disabled\"\r\n >\r\n <div matPrefix>\r\n <ng-container *ngTemplateOutlet=\"matPrefixTemplate\"></ng-container>\r\n </div>\r\n\r\n @if (floatLabel !== 'never' && !!placeholder) {\r\n <mat-label>{{ placeholder }}</mat-label>\r\n }\r\n\r\n <input matInput hidden type=\"text\" readonly [formControl]=\"_formControl\" />\r\n <ion-text>{{ _formControl.value | dateFormat: { pattern: displayPattern } }}</ion-text>\r\n\r\n <div matSuffix>\r\n <ng-container *ngTemplateOutlet=\"matSuffixTemplate\"></ng-container>\r\n </div>\r\n\r\n <!-- hints -->\r\n <mat-hint [class.cdk-visually-hidden]=\"_formControl.invalid\">\r\n <ng-container *ngTemplateOutlet=\"matHintTemplate\"></ng-container>\r\n </mat-hint>\r\n </mat-form-field>\r\n} @else {\r\n <!-- writable + time -->\r\n <ion-grid class=\"ion-no-padding {{ appearance }}\">\r\n <ion-row class=\"ion-no-padding no-wrap\">\r\n <!-- Day -->\r\n <ion-col class=\"day ion-no-padding\" [style.--button-count]=\"clearable ? 2 : 1\">\r\n <mat-form-field\r\n [floatLabel]=\"floatLabel | asFloatLabelType\"\r\n [appearance]=\"appearance\"\r\n [subscriptSizing]=\"'dynamic'\"\r\n [class.mdc-text-field--invalid]=\"_formControl.touched && (dateControl.invalid || _formControl.invalid)\"\r\n (click)=\"_openDatePickerIfMobile($event, datePicker)\"\r\n (focus)=\"_openDatePickerIfMobile($event, datePicker)\"\r\n >\r\n <div matPrefix>\r\n <ng-container *ngTemplateOutlet=\"matPrefixTemplate\"></ng-container>\r\n </div>\r\n\r\n @if (floatLabel !== 'never' && !!placeholder) {\r\n <mat-label>{{ placeholder }}</mat-label>\r\n }\r\n\r\n <!-- Day input (mobile) -->\r\n @if (mobile) {\r\n <input\r\n #matInput\r\n autocomplete=\"off\"\r\n type=\"text\"\r\n class=\"mat-mdc-form-field-input-control mdc-text-field__input\"\r\n [formControl]=\"dateControl\"\r\n [required]=\"required\"\r\n [tabindex]=\"tabindex\"\r\n readonly\r\n />\r\n <input\r\n matInput\r\n hidden\r\n type=\"text\"\r\n readonly\r\n [formControl]=\"_formControl\"\r\n [matDatepicker]=\"datePicker\"\r\n [matDatepickerFilter]=\"datePickerFilter\"\r\n (dateChange)=\"_onDatePickerChange($event)\"\r\n />\r\n } @else {\r\n <!-- Day input (desktop) -->\r\n <input\r\n matInput\r\n #matInput\r\n autocomplete=\"off\"\r\n type=\"text\"\r\n class=\"mat-input-element\"\r\n [maskito]=\"maskitoDateOptions\"\r\n [formControl]=\"dateControl\"\r\n [placeholder]=\"datePlaceholder | translate\"\r\n (focus)=\"filterInputTextFocusEvent($event)\"\r\n (blur)=\"filterInputTextBlurEvent($event)\"\r\n (keyup.enter)=\"keyupEnter.emit($event)\"\r\n (keyup.arrowDown)=\"openDatePicker($event, datePicker)\"\r\n (keyup.escape)=\"_preventEvent($event)\"\r\n [required]=\"required\"\r\n [tabindex]=\"tabindex\"\r\n [appAutofocus]=\"autofocus\"\r\n />\r\n <input\r\n type=\"text\"\r\n [formControl]=\"_formControl\"\r\n hidden\r\n [matDatepicker]=\"datePicker\"\r\n [matDatepickerFilter]=\"datePickerFilter\"\r\n (dateChange)=\"_onDatePickerChange($event)\"\r\n readonly\r\n />\r\n }\r\n\r\n <button\r\n type=\"button\"\r\n mat-icon-button\r\n tabindex=\"-1\"\r\n matSuffix\r\n (click)=\"openDatePicker($event, datePicker)\"\r\n [disabled]=\"_formControl.disabled\"\r\n >\r\n <mat-icon>{{ mobile ? 'date_range' : 'keyboard_arrow_down' }}</mat-icon>\r\n </button>\r\n @if (clearable) {\r\n <button\r\n matSuffix\r\n mat-icon-button\r\n tabindex=\"-1\"\r\n type=\"button\"\r\n (click)=\"clear($event)\"\r\n [hidden]=\"_formControl.disabled || !_formControl.value\"\r\n >\r\n <mat-icon>close</mat-icon>\r\n </button>\r\n }\r\n </mat-form-field>\r\n\r\n <!-- The date picker -->\r\n <mat-datepicker #datePicker\r\n [touchUi]=\"mobile\" [disabled]=\"disabled\"\r\n [startAt]=\"startDate\"\r\n [xPosition]=\"!mobile ? 'end' : undefined\">\r\n <!-- Date picker buttons -->\r\n @if (mobile) {\r\n <mat-datepicker-actions>\r\n <!-- Cancel button -->\r\n <ion-button fill=\"clear\" color=\"dark\" matDatepickerCancel>\r\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\r\n </ion-button>\r\n <!-- Apply button -->\r\n <ion-button fill=\"solid\" color=\"tertiary\" matDatepickerApply>\r\n <ion-label>{{ timeControl.value || ('COMMON.TIME' | translate) }}</ion-label>\r\n <ion-icon slot=\"end\" name=\"chevron-forward\"></ion-icon>\r\n </ion-button>\r\n </mat-datepicker-actions>\r\n }\r\n </mat-datepicker>\r\n </ion-col>\r\n\r\n <!-- Hour -->\r\n <ion-col class=\"hour ion-no-padding\" [style.--button-count]=\"compact ? 0 : 1\">\r\n <mat-form-field\r\n [floatLabel]=\"floatLabel | asFloatLabelType\"\r\n [appearance]=\"appearance\"\r\n [subscriptSizing]=\"'dynamic'\"\r\n [class.mdc-text-field--invalid]=\"_formControl.touched && (timeControl.invalid || _formControl.invalid)\"\r\n >\r\n @if (floatLabel !== 'never' && !!placeholder) {\r\n <mat-label translate>COMMON.TIME</mat-label>\r\n }\r\n\r\n <!-- Hour input (mobile) -->\r\n @if (mobile) {\r\n <input\r\n #matInput\r\n type=\"text\"\r\n class=\"mat-mdc-form-field-input-control mdc-text-field__input\"\r\n [formControl]=\"timeControl\"\r\n [required]=\"requiredTime\"\r\n (click)=\"openTimePicker($event)\"\r\n readonly\r\n />\r\n\r\n <!-- Hide the final (hidden) input -->\r\n <input\r\n matInput\r\n hidden\r\n type=\"text\"\r\n readonly\r\n [formControl]=\"timeControl\"\r\n [required]=\"required\"\r\n [ngxMatTimepicker]=\"timePicker\"\r\n [format]=\"24\"\r\n />\r\n } @else {\r\n <!-- Hour input (desktop) -->\r\n <input\r\n matInput\r\n #matInput\r\n type=\"text\"\r\n [formControl]=\"timeControl\"\r\n [maskito]=\"maskitoTimeOptions\"\r\n class=\"mat-input-element\"\r\n autocomplete=\"off\"\r\n [placeholder]=\"timePlaceholder | translate\"\r\n [required]=\"requiredTime\"\r\n (keyup.enter)=\"keyupEnter.emit($event)\"\r\n (keyup.arrowDown)=\"openTimePicker($event)\"\r\n (keyup.escape)=\"_preventEvent($event)\"\r\n (focus)=\"filterInputTextFocusEvent($event)\"\r\n (blur)=\"filterInputTextBlurEvent($event)\"\r\n [tabindex]=\"tabindex !== undefined ? tabindex + 1 : undefined\"\r\n />\r\n <!-- Hide the final (hidden) input -->\r\n <input\r\n hidden\r\n type=\"text\"\r\n readonly\r\n [formControl]=\"timeControl\"\r\n [required]=\"requiredTime\"\r\n [ngxMatTimepicker]=\"timePicker\"\r\n [format]=\"24\"\r\n />\r\n }\r\n\r\n @if (!compact) {\r\n <button\r\n matSuffix\r\n type=\"button\"\r\n mat-icon-button\r\n tabindex=\"-1\"\r\n [disabled]=\"_formControl.disabled\"\r\n (click)=\"openTimePicker($event)\"\r\n >\r\n <mat-icon>{{ !compact && mobile ? 'access_time' : 'keyboard_arrow_down' }}</mat-icon>\r\n </button>\r\n }\r\n <ngx-mat-timepicker\r\n #timePicker\r\n [isEsc]=\"!mobile\"\r\n [defaultTime]=\"'00:00'\"\r\n [cancelBtnTmpl]=\"timePickerCancelButton\"\r\n [confirmBtnTmpl]=\"timePickerOkButton\"\r\n [preventOverlayClick]=\"mobile\"\r\n [enableKeyboardInput]=\"!mobile\"\r\n [dottedMinutesInGap]=\"dottedMinutesInGap\"\r\n [hoursOnly]=\"timeHoursOnly\"\r\n [appendToInput]=\"!mobile\"\r\n (timeSet)=\"_onTimePickerChanged($event)\"\r\n color=\"accent\"\r\n ></ngx-mat-timepicker>\r\n </mat-form-field>\r\n </ion-col>\r\n </ion-row>\r\n </ion-grid>\r\n\r\n <!-- Do the same as MatFormField since angular 15 (see component source)-->\r\n <div\r\n class=\"mat-mdc-form-field-subscript-wrapper\"\r\n [class.mat-mdc-form-field-bottom-align]=\"subscriptSizing === 'fixed'\"\r\n [class.mat-mdc-form-field-subscript-dynamic-size]=\"subscriptSizing === 'dynamic'\"\r\n >\r\n @if (_formControl.touched && _formControl.errors; as errors) {\r\n <!-- errors -->\r\n <div class=\"mat-mdc-form-field-error-wrapper\">\r\n @if (errors | mapKeys | arrayFirst; as errorKey) {\r\n @switch (errorKey) {\r\n @case ('required') {\r\n <mat-error translate>ERROR.FIELD_REQUIRED</mat-error>\r\n }\r\n @case ('validDate') {\r\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_TIME</mat-error>\r\n }\r\n @case ('dateIsAfter') {\r\n <mat-error>\r\n {{ 'ERROR.FIELD_NOT_VALID_DATE_AFTER' | translate: _formControl.errors.dateIsAfter }}\r\n </mat-error>\r\n }\r\n @case ('dateIsBefore') {\r\n <mat-error>\r\n {{ 'ERROR.FIELD_NOT_VALID_DATE_BEFORE' | translate: _formControl.errors.dateIsBefore }}\r\n </mat-error>\r\n }\r\n @case ('dateRange') {\r\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_RANGE</mat-error>\r\n }\r\n @case ('dateMaxDuration') {\r\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_MAX_DURATION</mat-error>\r\n }\r\n @case ('dateMinDuration') {\r\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_MIN_DURATION</mat-error>\r\n }\r\n @case ('msg') {\r\n <mat-error>\r\n {{\r\n _formControl.errors.msg?.key || _formControl.errors.msg | translate: _formControl.errors.msg?.params\r\n }}\r\n </mat-error>\r\n }\r\n @default {\r\n <ng-container *ngTemplateOutlet=\"matErrorTemplate\"></ng-container>\r\n }\r\n }\r\n } @else {\r\n <ng-container *ngTemplateOutlet=\"matErrorTemplate\"></ng-container>\r\n }\r\n </div>\r\n } @else {\r\n <!-- hints -->\r\n <ng-container *ngTemplateOutlet=\"matHintTemplate\"></ng-container>\r\n }\r\n </div>\r\n}\r\n\r\n<!-- cancel button -->\r\n<ng-template #timePickerCancelButton>\r\n <ion-button fill=\"clear\" color=\"dark\">\r\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\r\n </ion-button>\r\n</ng-template>\r\n\r\n<!-- confirm button -->\r\n<ng-template #timePickerOkButton>\r\n <ion-button fill=\"solid\" color=\"tertiary\">\r\n <ion-label translate>COMMON.BTN_VALIDATE</ion-label>\r\n </ion-button>\r\n</ng-template>\r\n\r\n<ng-template #matPrefixTemplate>\r\n <ng-content select=\"[matPrefix]\"></ng-content>\r\n</ng-template>\r\n\r\n<ng-template #matSuffixTemplate>\r\n <ng-content select=\"[matSuffix]\"></ng-content>\r\n</ng-template>\r\n\r\n<ng-template #matErrorTemplate>\r\n <ng-content select=\"mat-error,[matError]\"></ng-content>\r\n</ng-template>\r\n\r\n<ng-template #matHintTemplate>\r\n <div class=\"mat-mdc-form-field-hint-wrapper\">\r\n <ng-content select=\"mat-hint:not([align='end']),[matHint]\"></ng-content>\r\n <div class=\"mat-mdc-form-field-hint-spacer\"></div>\r\n <ng-content select=\"mat-hint[align='end']\"></ng-content>\r\n </div>\r\n</ng-template>\r\n", styles: [":host{display:inline-block;width:100%;position:relative;--ion-grid-column-padding: 0}input[type=number]::-webkit-inner-spin-button,input[type=number]::-webkit-outer-spin-button{-webkit-appearance:none;margin:0}mat-form-field input[readonly]{-webkit-user-select:none!important;user-select:none!important}mat-form-field .datetime-md{padding:0!important}mat-form-field button[hidden]{display:none}ion-row.no-wrap{flex-wrap:nowrap}ion-grid ion-col{--button-width: calc(var(--button-count, 0px) * 24px)}ion-grid.fill ion-col.day{--min-width: calc(100px + var(--button-width, 0px));min-width:var(--min-width)}ion-grid.fill ion-col.hour{--min-width: calc(55px + var(--button-width, 0px));--max-width: calc(65px + var(--button-width, 0px));min-width:var(--min-width);max-width:var(--max-width)}ion-grid.fill ion-col.hour mat-form-field{width:100%}ion-grid.fill ion-col.hour mat-form-field mat-label,ion-grid.fill ion-col.hour mat-form-field input[type=text]{text-align:left;min-width:52px}ion-grid.outline ion-col.day{min-width:calc(110px + var(--button-width))}ion-grid.outline ion-col.hour{--min-width: calc(65px + var(--button-width));--max-width: calc(75px + var(--button-width))}mat-form-field.mat-form-field-disabled ion-col.day{min-width:150px}.hour mat-form-field.mat-mdc-form-field-should-float .mat-mdc-form-field-placeholder{max-width:inherit}\n"], dependencies: [{ kind: "directive", type: i3$1.NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "component", type: i2$1.IonButton, selector: "ion-button", inputs: ["buttonType", "color", "disabled", "download", "expand", "fill", "form", "href", "mode", "rel", "routerAnimation", "routerDirection", "shape", "size", "strong", "target", "type"] }, { kind: "component", type: i2$1.IonCol, selector: "ion-col", inputs: ["offset", "offsetLg", "offsetMd", "offsetSm", "offsetXl", "offsetXs", "pull", "pullLg", "pullMd", "pullSm", "pullXl", "pullXs", "push", "pushLg", "pushMd", "pushSm", "pushXl", "pushXs", "size", "sizeLg", "sizeMd", "sizeSm", "sizeXl", "sizeXs"] }, { kind: "component", type: i2$1.IonGrid, selector: "ion-grid", inputs: ["fixed"] }, { kind: "component", type: i2$1.IonIcon, selector: "ion-icon", inputs: ["color", "flipRtl", "icon", "ios", "lazy", "md", "mode", "name", "sanitize", "size", "src"] }, { kind: "component", type: i2$1.IonLabel, selector: "ion-label", inputs: ["color", "mode", "position"] }, { kind: "component", type: i2$1.IonRow, selector: "ion-row" }, { kind: "component", type: i2$1.IonText, selector: "ion-text", inputs: ["color", "mode"] }, { kind: "directive", type: i1$3.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$3.RequiredValidator, selector: ":not([type=checkbox])[required][formControlName],:not([type=checkbox])[required][formControl],:not([type=checkbox])[required][ngModel]", inputs: ["required"] }, { kind: "directive", type: i1$3.FormControlDirective, selector: "[formControl]", inputs: ["formControl", "disabled", "ngModel"], outputs: ["ngModelChange"], exportAs: ["ngForm"] }, { kind: "component", type: i3.MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: i3.MatLabel, selector: "mat-label" }, { kind: "directive", type: i3.MatHint, selector: "mat-hint", inputs: ["align", "id"] }, { kind: "directive", type: i3.MatError, selector: "mat-error, [matError]", inputs: ["id"] }, { kind: "directive", type: i3.MatPrefix, selector: "[matPrefix], [matIconPrefix], [matTextPrefix]", inputs: ["matTextPrefix"] }, { kind: "directive", type: i3.MatSuffix, selector: "[matSuffix], [matIconSuffix], [matTextSuffix]", inputs: ["matTextSuffix"] }, { kind: "directive", type: i4.MatInput, selector: "input[matInput], textarea[matInput], select[matNativeControl], input[matNativeControl], textarea[matNativeControl]", inputs: ["disabled", "id", "placeholder", "name", "required", "type", "errorStateMatcher", "aria-describedby", "value", "readonly"], exportAs: ["matInput"] }, { kind: "component", type: i6$1.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i9.MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "component", type: i10.MatDatepicker, selector: "mat-datepicker", exportAs: ["matDatepicker"] }, { kind: "directive", type: i10.MatDatepickerInput, selector: "input[matDatepicker]", inputs: ["matDatepicker", "min", "max", "matDatepickerFilter"], exportAs: ["matDatepickerInput"] }, { kind: "component", type: i10.MatDatepickerActions, selector: "mat-datepicker-actions, mat-date-range-picker-actions" }, { kind: "directive", type: i10.MatDatepickerCancel, selector: "[matDatepickerCancel], [matDateRangePickerCancel]" }, { kind: "directive", type: i10.MatDatepickerApply, selector: "[matDatepickerApply], [matDateRangePickerApply]" }, { kind: "directive", type: i11.MaskitoDirective, selector: "[maskito]", inputs: ["maskito", "maskitoElement"] }, { kind: "directive", type: i1$1.TranslateDirective, selector: "[translate],[ngx-translate]", inputs: ["translate", "translateParams"] }, { kind: "directive", type: AutofocusDirective, selector: "[autofocus], input[appAutofocus]", inputs: ["appAutofocus", "autofocusDelay"] }, { kind: "component", type: i13.NgxMatTimepickerComponent, selector: "ngx-mat-timepicker", inputs: ["appendToInput", "color", "dottedMinutesInGap", "enableKeyboardInput", "format", "minutesGap", "cancelBtnTmpl", "confirmBtnTmpl", "defaultTime", "disableAnimation", "editableHintTmpl", "hoursOnly", "isEsc", "max", "min", "preventOverlayClick", "timepickerClass"], outputs: ["closed", "hourSelected", "opened", "timeChanged", "timeSet"] }, { kind: "directive", type: i13.NgxMatTimepickerDirective, selector: "[ngxMatTimepicker]", inputs: ["format", "max", "min", "ngxMatTimepicker", "value", "disableClick", "disabled"] }, { kind: "pipe", type: DateFormatPipe, name: "dateFormat" }, { kind: "pipe", type: ArrayFirstPipe, name: "arrayFirst" }, { kind: "pipe", type: MapKeysPipe, name: "mapKeys" }, { kind: "pipe", type: AsFloatLabelTypePipe, name: "asFloatLabelType" }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
11199
11199
  }
11200
11200
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: MatDateTime, decorators: [{
11201
11201
  type: Component,
11202
- args: [{ selector: 'mat-date-time-field', providers: [DEFAULT_VALUE_ACCESSOR$2], changeDetection: ChangeDetectionStrategy.OnPush, template: "<!-- readonly -->\n@if (readonly) {\n <mat-form-field\n [floatLabel]=\"floatLabel | asFloatLabelType\"\n [appearance]=\"appearance\"\n [subscriptSizing]=\"subscriptSizing\"\n class=\"mat-form-field-disabled\"\n >\n <div matPrefix>\n <ng-container *ngTemplateOutlet=\"matPrefixTemplate\"></ng-container>\n </div>\n\n @if (floatLabel !== 'never' && !!placeholder) {\n <mat-label>{{ placeholder }}</mat-label>\n }\n\n <input matInput hidden type=\"text\" readonly [formControl]=\"_formControl\" />\n <ion-text>{{ _formControl.value | dateFormat: { pattern: displayPattern } }}</ion-text>\n\n <div matSuffix>\n <ng-container *ngTemplateOutlet=\"matSuffixTemplate\"></ng-container>\n </div>\n\n <!-- hints -->\n <mat-hint [class.cdk-visually-hidden]=\"_formControl.invalid\">\n <ng-container *ngTemplateOutlet=\"matHintTemplate\"></ng-container>\n </mat-hint>\n </mat-form-field>\n} @else {\n <!-- writable + time -->\n <ion-grid class=\"ion-no-padding {{ appearance }}\">\n <ion-row class=\"ion-no-padding no-wrap\">\n <!-- Day -->\n <ion-col class=\"day ion-no-padding\" [style.--button-count]=\"clearable ? 2 : 1\">\n <mat-form-field\n [floatLabel]=\"floatLabel | asFloatLabelType\"\n [appearance]=\"appearance\"\n [subscriptSizing]=\"'dynamic'\"\n [class.mdc-text-field--invalid]=\"_formControl.touched && (dateControl.invalid || _formControl.invalid)\"\n (click)=\"_openDatePickerIfMobile($event, datePicker)\"\n (focus)=\"_openDatePickerIfMobile($event, datePicker)\"\n >\n <div matPrefix>\n <ng-container *ngTemplateOutlet=\"matPrefixTemplate\"></ng-container>\n </div>\n\n @if (floatLabel !== 'never' && !!placeholder) {\n <mat-label>{{ placeholder }}</mat-label>\n }\n\n <!-- Day input (mobile) -->\n @if (mobile) {\n <input\n #matInput\n autocomplete=\"off\"\n type=\"text\"\n class=\"mat-mdc-form-field-input-control mdc-text-field__input\"\n [formControl]=\"dateControl\"\n [required]=\"required\"\n [tabindex]=\"tabindex\"\n readonly\n />\n <input\n matInput\n hidden\n type=\"text\"\n readonly\n [formControl]=\"_formControl\"\n [matDatepicker]=\"datePicker\"\n [matDatepickerFilter]=\"datePickerFilter\"\n (dateChange)=\"_onDatePickerChange($event)\"\n />\n } @else {\n <!-- Day input (desktop) -->\n <input\n matInput\n #matInput\n autocomplete=\"off\"\n type=\"text\"\n class=\"mat-input-element\"\n [maskito]=\"maskitoDateOptions\"\n [formControl]=\"dateControl\"\n [placeholder]=\"datePlaceholder | translate\"\n (focus)=\"filterInputTextFocusEvent($event)\"\n (blur)=\"filterInputTextBlurEvent($event)\"\n (keyup.enter)=\"keyupEnter.emit($event)\"\n (keyup.arrowDown)=\"openDatePicker($event, datePicker)\"\n (keyup.escape)=\"_preventEvent($event)\"\n [required]=\"required\"\n [tabindex]=\"tabindex\"\n [appAutofocus]=\"autofocus\"\n />\n <input\n type=\"text\"\n [formControl]=\"_formControl\"\n hidden\n [matDatepicker]=\"datePicker\"\n [matDatepickerFilter]=\"datePickerFilter\"\n (dateChange)=\"_onDatePickerChange($event)\"\n readonly\n />\n }\n\n <button\n type=\"button\"\n mat-icon-button\n tabindex=\"-1\"\n matSuffix\n (click)=\"openDatePicker($event, datePicker)\"\n [disabled]=\"_formControl.disabled\"\n >\n <mat-icon>{{ mobile ? 'date_range' : 'keyboard_arrow_down' }}</mat-icon>\n </button>\n @if (clearable) {\n <button\n matSuffix\n mat-icon-button\n tabindex=\"-1\"\n type=\"button\"\n (click)=\"clear($event)\"\n [hidden]=\"_formControl.disabled || !_formControl.value\"\n >\n <mat-icon>close</mat-icon>\n </button>\n }\n </mat-form-field>\n\n <!-- The date picker -->\n <mat-datepicker #datePicker\n [touchUi]=\"mobile\" [disabled]=\"disabled\"\n [startAt]=\"startDate\"\n [xPosition]=\"!mobile ? 'end' : undefined\">\n <!-- Date picker buttons -->\n @if (mobile) {\n <mat-datepicker-actions>\n <!-- Cancel button -->\n <ion-button fill=\"clear\" color=\"dark\" matDatepickerCancel>\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\n </ion-button>\n <!-- Apply button -->\n <ion-button fill=\"solid\" color=\"tertiary\" matDatepickerApply>\n <ion-label>{{ timeControl.value || ('COMMON.TIME' | translate) }}</ion-label>\n <ion-icon slot=\"end\" name=\"chevron-forward\"></ion-icon>\n </ion-button>\n </mat-datepicker-actions>\n }\n </mat-datepicker>\n </ion-col>\n\n <!-- Hour -->\n <ion-col class=\"hour ion-no-padding\" [style.--button-count]=\"compact ? 0 : 1\">\n <mat-form-field\n [floatLabel]=\"floatLabel | asFloatLabelType\"\n [appearance]=\"appearance\"\n [subscriptSizing]=\"'dynamic'\"\n [class.mdc-text-field--invalid]=\"_formControl.touched && (timeControl.invalid || _formControl.invalid)\"\n >\n @if (floatLabel !== 'never' && !!placeholder) {\n <mat-label translate>COMMON.TIME</mat-label>\n }\n\n <!-- Hour input (mobile) -->\n @if (mobile) {\n <input\n #matInput\n type=\"text\"\n class=\"mat-mdc-form-field-input-control mdc-text-field__input\"\n [formControl]=\"timeControl\"\n [required]=\"requiredTime\"\n (click)=\"openTimePicker($event)\"\n readonly\n />\n\n <!-- Hide the final (hidden) input -->\n <input\n matInput\n hidden\n type=\"text\"\n readonly\n [formControl]=\"timeControl\"\n [required]=\"required\"\n [ngxMatTimepicker]=\"timePicker\"\n [format]=\"24\"\n />\n } @else {\n <!-- Hour input (desktop) -->\n <input\n matInput\n #matInput\n type=\"text\"\n [formControl]=\"timeControl\"\n [maskito]=\"maskitoTimeOptions\"\n class=\"mat-input-element\"\n autocomplete=\"off\"\n [placeholder]=\"timePlaceholder | translate\"\n [required]=\"requiredTime\"\n (keyup.enter)=\"keyupEnter.emit($event)\"\n (keyup.arrowDown)=\"openTimePicker($event)\"\n (keyup.escape)=\"_preventEvent($event)\"\n (focus)=\"filterInputTextFocusEvent($event)\"\n (blur)=\"filterInputTextBlurEvent($event)\"\n [tabindex]=\"tabindex !== undefined ? tabindex + 1 : undefined\"\n />\n <!-- Hide the final (hidden) input -->\n <input\n hidden\n type=\"text\"\n readonly\n [formControl]=\"timeControl\"\n [required]=\"requiredTime\"\n [ngxMatTimepicker]=\"timePicker\"\n [format]=\"24\"\n />\n }\n\n @if (!compact) {\n <button\n matSuffix\n type=\"button\"\n mat-icon-button\n tabindex=\"-1\"\n [disabled]=\"_formControl.disabled\"\n (click)=\"openTimePicker($event)\"\n >\n <mat-icon>{{ !compact && mobile ? 'access_time' : 'keyboard_arrow_down' }}</mat-icon>\n </button>\n }\n <ngx-mat-timepicker\n #timePicker\n [isEsc]=\"!mobile\"\n [defaultTime]=\"'00:00'\"\n [cancelBtnTmpl]=\"timePickerCancelButton\"\n [confirmBtnTmpl]=\"timePickerOkButton\"\n [preventOverlayClick]=\"mobile\"\n [enableKeyboardInput]=\"!mobile\"\n [dottedMinutesInGap]=\"dottedMinutesInGap\"\n [hoursOnly]=\"timeHoursOnly\"\n [appendToInput]=\"!mobile\"\n (timeSet)=\"_onTimePickerChanged($event)\"\n color=\"accent\"\n ></ngx-mat-timepicker>\n </mat-form-field>\n </ion-col>\n </ion-row>\n </ion-grid>\n\n <!-- Do the same as MatFormField since angular 15 (see component source)-->\n <div\n class=\"mat-mdc-form-field-subscript-wrapper\"\n [class.mat-mdc-form-field-bottom-align]=\"subscriptSizing === 'fixed'\"\n [class.mat-mdc-form-field-subscript-dynamic-size]=\"subscriptSizing === 'dynamic'\"\n >\n @if (_formControl.touched && _formControl.errors; as errors) {\n <!-- errors -->\n <div class=\"mat-mdc-form-field-error-wrapper\">\n @if (errors | mapKeys | arrayFirst; as errorKey) {\n @switch (errorKey) {\n @case ('required') {\n <mat-error translate>ERROR.FIELD_REQUIRED</mat-error>\n }\n @case ('validDate') {\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_TIME</mat-error>\n }\n @case ('dateIsAfter') {\n <mat-error>\n {{ 'ERROR.FIELD_NOT_VALID_DATE_AFTER' | translate: _formControl.errors.dateIsAfter }}\n </mat-error>\n }\n @case ('dateIsBefore') {\n <mat-error>\n {{ 'ERROR.FIELD_NOT_VALID_DATE_BEFORE' | translate: _formControl.errors.dateIsBefore }}\n </mat-error>\n }\n @case ('dateRange') {\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_RANGE</mat-error>\n }\n @case ('dateMaxDuration') {\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_MAX_DURATION</mat-error>\n }\n @case ('dateMinDuration') {\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_MIN_DURATION</mat-error>\n }\n @case ('msg') {\n <mat-error>\n {{\n _formControl.errors.msg?.key || _formControl.errors.msg | translate: _formControl.errors.msg?.params\n }}\n </mat-error>\n }\n @default {\n <ng-container *ngTemplateOutlet=\"matErrorTemplate\"></ng-container>\n }\n }\n } @else {\n <ng-container *ngTemplateOutlet=\"matErrorTemplate\"></ng-container>\n }\n </div>\n } @else {\n <!-- hints -->\n <ng-container *ngTemplateOutlet=\"matHintTemplate\"></ng-container>\n }\n </div>\n}\n\n<!-- cancel button -->\n<ng-template #timePickerCancelButton>\n <ion-button fill=\"clear\" color=\"dark\">\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\n </ion-button>\n</ng-template>\n\n<!-- confirm button -->\n<ng-template #timePickerOkButton>\n <ion-button fill=\"solid\" color=\"tertiary\">\n <ion-label translate>COMMON.BTN_VALIDATE</ion-label>\n </ion-button>\n</ng-template>\n\n<ng-template #matPrefixTemplate>\n <ng-content select=\"[matPrefix]\"></ng-content>\n</ng-template>\n\n<ng-template #matSuffixTemplate>\n <ng-content select=\"[matSuffix]\"></ng-content>\n</ng-template>\n\n<ng-template #matErrorTemplate>\n <ng-content select=\"mat-error,[matError]\"></ng-content>\n</ng-template>\n\n<ng-template #matHintTemplate>\n <div class=\"mat-mdc-form-field-hint-wrapper\">\n <ng-content select=\"mat-hint:not([align='end']),[matHint]\"></ng-content>\n <div class=\"mat-mdc-form-field-hint-spacer\"></div>\n <ng-content select=\"mat-hint[align='end']\"></ng-content>\n </div>\n</ng-template>\n", styles: [":host{display:inline-block;width:100%;position:relative;--ion-grid-column-padding: 0}input[type=number]::-webkit-inner-spin-button,input[type=number]::-webkit-outer-spin-button{-webkit-appearance:none;margin:0}mat-form-field input[readonly]{-webkit-user-select:none!important;user-select:none!important}mat-form-field .datetime-md{padding:0!important}mat-form-field button[hidden]{display:none}ion-row.no-wrap{flex-wrap:nowrap}ion-grid ion-col{--button-width: calc(var(--button-count, 0px) * 24px)}ion-grid.fill ion-col.day{--min-width: calc(100px + var(--button-width, 0px));min-width:var(--min-width)}ion-grid.fill ion-col.hour{--min-width: calc(55px + var(--button-width, 0px));--max-width: calc(65px + var(--button-width, 0px));min-width:var(--min-width);max-width:var(--max-width)}ion-grid.fill ion-col.hour mat-form-field{width:100%}ion-grid.fill ion-col.hour mat-form-field mat-label,ion-grid.fill ion-col.hour mat-form-field input[type=text]{text-align:left;min-width:52px}ion-grid.outline ion-col.day{min-width:calc(110px + var(--button-width))}ion-grid.outline ion-col.hour{--min-width: calc(65px + var(--button-width));--max-width: calc(75px + var(--button-width))}mat-form-field.mat-form-field-disabled ion-col.day{min-width:150px}.hour mat-form-field.mat-mdc-form-field-should-float .mat-mdc-form-field-placeholder{max-width:inherit}\n"] }]
11202
+ args: [{ selector: 'mat-date-time-field', providers: [DEFAULT_VALUE_ACCESSOR$2], changeDetection: ChangeDetectionStrategy.OnPush, template: "<!-- readonly -->\r\n@if (readonly) {\r\n <mat-form-field\r\n [floatLabel]=\"floatLabel | asFloatLabelType\"\r\n [appearance]=\"appearance\"\r\n [subscriptSizing]=\"subscriptSizing\"\r\n class=\"mat-form-field-disabled\"\r\n >\r\n <div matPrefix>\r\n <ng-container *ngTemplateOutlet=\"matPrefixTemplate\"></ng-container>\r\n </div>\r\n\r\n @if (floatLabel !== 'never' && !!placeholder) {\r\n <mat-label>{{ placeholder }}</mat-label>\r\n }\r\n\r\n <input matInput hidden type=\"text\" readonly [formControl]=\"_formControl\" />\r\n <ion-text>{{ _formControl.value | dateFormat: { pattern: displayPattern } }}</ion-text>\r\n\r\n <div matSuffix>\r\n <ng-container *ngTemplateOutlet=\"matSuffixTemplate\"></ng-container>\r\n </div>\r\n\r\n <!-- hints -->\r\n <mat-hint [class.cdk-visually-hidden]=\"_formControl.invalid\">\r\n <ng-container *ngTemplateOutlet=\"matHintTemplate\"></ng-container>\r\n </mat-hint>\r\n </mat-form-field>\r\n} @else {\r\n <!-- writable + time -->\r\n <ion-grid class=\"ion-no-padding {{ appearance }}\">\r\n <ion-row class=\"ion-no-padding no-wrap\">\r\n <!-- Day -->\r\n <ion-col class=\"day ion-no-padding\" [style.--button-count]=\"clearable ? 2 : 1\">\r\n <mat-form-field\r\n [floatLabel]=\"floatLabel | asFloatLabelType\"\r\n [appearance]=\"appearance\"\r\n [subscriptSizing]=\"'dynamic'\"\r\n [class.mdc-text-field--invalid]=\"_formControl.touched && (dateControl.invalid || _formControl.invalid)\"\r\n (click)=\"_openDatePickerIfMobile($event, datePicker)\"\r\n (focus)=\"_openDatePickerIfMobile($event, datePicker)\"\r\n >\r\n <div matPrefix>\r\n <ng-container *ngTemplateOutlet=\"matPrefixTemplate\"></ng-container>\r\n </div>\r\n\r\n @if (floatLabel !== 'never' && !!placeholder) {\r\n <mat-label>{{ placeholder }}</mat-label>\r\n }\r\n\r\n <!-- Day input (mobile) -->\r\n @if (mobile) {\r\n <input\r\n #matInput\r\n autocomplete=\"off\"\r\n type=\"text\"\r\n class=\"mat-mdc-form-field-input-control mdc-text-field__input\"\r\n [formControl]=\"dateControl\"\r\n [required]=\"required\"\r\n [tabindex]=\"tabindex\"\r\n readonly\r\n />\r\n <input\r\n matInput\r\n hidden\r\n type=\"text\"\r\n readonly\r\n [formControl]=\"_formControl\"\r\n [matDatepicker]=\"datePicker\"\r\n [matDatepickerFilter]=\"datePickerFilter\"\r\n (dateChange)=\"_onDatePickerChange($event)\"\r\n />\r\n } @else {\r\n <!-- Day input (desktop) -->\r\n <input\r\n matInput\r\n #matInput\r\n autocomplete=\"off\"\r\n type=\"text\"\r\n class=\"mat-input-element\"\r\n [maskito]=\"maskitoDateOptions\"\r\n [formControl]=\"dateControl\"\r\n [placeholder]=\"datePlaceholder | translate\"\r\n (focus)=\"filterInputTextFocusEvent($event)\"\r\n (blur)=\"filterInputTextBlurEvent($event)\"\r\n (keyup.enter)=\"keyupEnter.emit($event)\"\r\n (keyup.arrowDown)=\"openDatePicker($event, datePicker)\"\r\n (keyup.escape)=\"_preventEvent($event)\"\r\n [required]=\"required\"\r\n [tabindex]=\"tabindex\"\r\n [appAutofocus]=\"autofocus\"\r\n />\r\n <input\r\n type=\"text\"\r\n [formControl]=\"_formControl\"\r\n hidden\r\n [matDatepicker]=\"datePicker\"\r\n [matDatepickerFilter]=\"datePickerFilter\"\r\n (dateChange)=\"_onDatePickerChange($event)\"\r\n readonly\r\n />\r\n }\r\n\r\n <button\r\n type=\"button\"\r\n mat-icon-button\r\n tabindex=\"-1\"\r\n matSuffix\r\n (click)=\"openDatePicker($event, datePicker)\"\r\n [disabled]=\"_formControl.disabled\"\r\n >\r\n <mat-icon>{{ mobile ? 'date_range' : 'keyboard_arrow_down' }}</mat-icon>\r\n </button>\r\n @if (clearable) {\r\n <button\r\n matSuffix\r\n mat-icon-button\r\n tabindex=\"-1\"\r\n type=\"button\"\r\n (click)=\"clear($event)\"\r\n [hidden]=\"_formControl.disabled || !_formControl.value\"\r\n >\r\n <mat-icon>close</mat-icon>\r\n </button>\r\n }\r\n </mat-form-field>\r\n\r\n <!-- The date picker -->\r\n <mat-datepicker #datePicker\r\n [touchUi]=\"mobile\" [disabled]=\"disabled\"\r\n [startAt]=\"startDate\"\r\n [xPosition]=\"!mobile ? 'end' : undefined\">\r\n <!-- Date picker buttons -->\r\n @if (mobile) {\r\n <mat-datepicker-actions>\r\n <!-- Cancel button -->\r\n <ion-button fill=\"clear\" color=\"dark\" matDatepickerCancel>\r\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\r\n </ion-button>\r\n <!-- Apply button -->\r\n <ion-button fill=\"solid\" color=\"tertiary\" matDatepickerApply>\r\n <ion-label>{{ timeControl.value || ('COMMON.TIME' | translate) }}</ion-label>\r\n <ion-icon slot=\"end\" name=\"chevron-forward\"></ion-icon>\r\n </ion-button>\r\n </mat-datepicker-actions>\r\n }\r\n </mat-datepicker>\r\n </ion-col>\r\n\r\n <!-- Hour -->\r\n <ion-col class=\"hour ion-no-padding\" [style.--button-count]=\"compact ? 0 : 1\">\r\n <mat-form-field\r\n [floatLabel]=\"floatLabel | asFloatLabelType\"\r\n [appearance]=\"appearance\"\r\n [subscriptSizing]=\"'dynamic'\"\r\n [class.mdc-text-field--invalid]=\"_formControl.touched && (timeControl.invalid || _formControl.invalid)\"\r\n >\r\n @if (floatLabel !== 'never' && !!placeholder) {\r\n <mat-label translate>COMMON.TIME</mat-label>\r\n }\r\n\r\n <!-- Hour input (mobile) -->\r\n @if (mobile) {\r\n <input\r\n #matInput\r\n type=\"text\"\r\n class=\"mat-mdc-form-field-input-control mdc-text-field__input\"\r\n [formControl]=\"timeControl\"\r\n [required]=\"requiredTime\"\r\n (click)=\"openTimePicker($event)\"\r\n readonly\r\n />\r\n\r\n <!-- Hide the final (hidden) input -->\r\n <input\r\n matInput\r\n hidden\r\n type=\"text\"\r\n readonly\r\n [formControl]=\"timeControl\"\r\n [required]=\"required\"\r\n [ngxMatTimepicker]=\"timePicker\"\r\n [format]=\"24\"\r\n />\r\n } @else {\r\n <!-- Hour input (desktop) -->\r\n <input\r\n matInput\r\n #matInput\r\n type=\"text\"\r\n [formControl]=\"timeControl\"\r\n [maskito]=\"maskitoTimeOptions\"\r\n class=\"mat-input-element\"\r\n autocomplete=\"off\"\r\n [placeholder]=\"timePlaceholder | translate\"\r\n [required]=\"requiredTime\"\r\n (keyup.enter)=\"keyupEnter.emit($event)\"\r\n (keyup.arrowDown)=\"openTimePicker($event)\"\r\n (keyup.escape)=\"_preventEvent($event)\"\r\n (focus)=\"filterInputTextFocusEvent($event)\"\r\n (blur)=\"filterInputTextBlurEvent($event)\"\r\n [tabindex]=\"tabindex !== undefined ? tabindex + 1 : undefined\"\r\n />\r\n <!-- Hide the final (hidden) input -->\r\n <input\r\n hidden\r\n type=\"text\"\r\n readonly\r\n [formControl]=\"timeControl\"\r\n [required]=\"requiredTime\"\r\n [ngxMatTimepicker]=\"timePicker\"\r\n [format]=\"24\"\r\n />\r\n }\r\n\r\n @if (!compact) {\r\n <button\r\n matSuffix\r\n type=\"button\"\r\n mat-icon-button\r\n tabindex=\"-1\"\r\n [disabled]=\"_formControl.disabled\"\r\n (click)=\"openTimePicker($event)\"\r\n >\r\n <mat-icon>{{ !compact && mobile ? 'access_time' : 'keyboard_arrow_down' }}</mat-icon>\r\n </button>\r\n }\r\n <ngx-mat-timepicker\r\n #timePicker\r\n [isEsc]=\"!mobile\"\r\n [defaultTime]=\"'00:00'\"\r\n [cancelBtnTmpl]=\"timePickerCancelButton\"\r\n [confirmBtnTmpl]=\"timePickerOkButton\"\r\n [preventOverlayClick]=\"mobile\"\r\n [enableKeyboardInput]=\"!mobile\"\r\n [dottedMinutesInGap]=\"dottedMinutesInGap\"\r\n [hoursOnly]=\"timeHoursOnly\"\r\n [appendToInput]=\"!mobile\"\r\n (timeSet)=\"_onTimePickerChanged($event)\"\r\n color=\"accent\"\r\n ></ngx-mat-timepicker>\r\n </mat-form-field>\r\n </ion-col>\r\n </ion-row>\r\n </ion-grid>\r\n\r\n <!-- Do the same as MatFormField since angular 15 (see component source)-->\r\n <div\r\n class=\"mat-mdc-form-field-subscript-wrapper\"\r\n [class.mat-mdc-form-field-bottom-align]=\"subscriptSizing === 'fixed'\"\r\n [class.mat-mdc-form-field-subscript-dynamic-size]=\"subscriptSizing === 'dynamic'\"\r\n >\r\n @if (_formControl.touched && _formControl.errors; as errors) {\r\n <!-- errors -->\r\n <div class=\"mat-mdc-form-field-error-wrapper\">\r\n @if (errors | mapKeys | arrayFirst; as errorKey) {\r\n @switch (errorKey) {\r\n @case ('required') {\r\n <mat-error translate>ERROR.FIELD_REQUIRED</mat-error>\r\n }\r\n @case ('validDate') {\r\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_TIME</mat-error>\r\n }\r\n @case ('dateIsAfter') {\r\n <mat-error>\r\n {{ 'ERROR.FIELD_NOT_VALID_DATE_AFTER' | translate: _formControl.errors.dateIsAfter }}\r\n </mat-error>\r\n }\r\n @case ('dateIsBefore') {\r\n <mat-error>\r\n {{ 'ERROR.FIELD_NOT_VALID_DATE_BEFORE' | translate: _formControl.errors.dateIsBefore }}\r\n </mat-error>\r\n }\r\n @case ('dateRange') {\r\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_RANGE</mat-error>\r\n }\r\n @case ('dateMaxDuration') {\r\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_MAX_DURATION</mat-error>\r\n }\r\n @case ('dateMinDuration') {\r\n <mat-error translate>ERROR.FIELD_NOT_VALID_DATE_MIN_DURATION</mat-error>\r\n }\r\n @case ('msg') {\r\n <mat-error>\r\n {{\r\n _formControl.errors.msg?.key || _formControl.errors.msg | translate: _formControl.errors.msg?.params\r\n }}\r\n </mat-error>\r\n }\r\n @default {\r\n <ng-container *ngTemplateOutlet=\"matErrorTemplate\"></ng-container>\r\n }\r\n }\r\n } @else {\r\n <ng-container *ngTemplateOutlet=\"matErrorTemplate\"></ng-container>\r\n }\r\n </div>\r\n } @else {\r\n <!-- hints -->\r\n <ng-container *ngTemplateOutlet=\"matHintTemplate\"></ng-container>\r\n }\r\n </div>\r\n}\r\n\r\n<!-- cancel button -->\r\n<ng-template #timePickerCancelButton>\r\n <ion-button fill=\"clear\" color=\"dark\">\r\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\r\n </ion-button>\r\n</ng-template>\r\n\r\n<!-- confirm button -->\r\n<ng-template #timePickerOkButton>\r\n <ion-button fill=\"solid\" color=\"tertiary\">\r\n <ion-label translate>COMMON.BTN_VALIDATE</ion-label>\r\n </ion-button>\r\n</ng-template>\r\n\r\n<ng-template #matPrefixTemplate>\r\n <ng-content select=\"[matPrefix]\"></ng-content>\r\n</ng-template>\r\n\r\n<ng-template #matSuffixTemplate>\r\n <ng-content select=\"[matSuffix]\"></ng-content>\r\n</ng-template>\r\n\r\n<ng-template #matErrorTemplate>\r\n <ng-content select=\"mat-error,[matError]\"></ng-content>\r\n</ng-template>\r\n\r\n<ng-template #matHintTemplate>\r\n <div class=\"mat-mdc-form-field-hint-wrapper\">\r\n <ng-content select=\"mat-hint:not([align='end']),[matHint]\"></ng-content>\r\n <div class=\"mat-mdc-form-field-hint-spacer\"></div>\r\n <ng-content select=\"mat-hint[align='end']\"></ng-content>\r\n </div>\r\n</ng-template>\r\n", styles: [":host{display:inline-block;width:100%;position:relative;--ion-grid-column-padding: 0}input[type=number]::-webkit-inner-spin-button,input[type=number]::-webkit-outer-spin-button{-webkit-appearance:none;margin:0}mat-form-field input[readonly]{-webkit-user-select:none!important;user-select:none!important}mat-form-field .datetime-md{padding:0!important}mat-form-field button[hidden]{display:none}ion-row.no-wrap{flex-wrap:nowrap}ion-grid ion-col{--button-width: calc(var(--button-count, 0px) * 24px)}ion-grid.fill ion-col.day{--min-width: calc(100px + var(--button-width, 0px));min-width:var(--min-width)}ion-grid.fill ion-col.hour{--min-width: calc(55px + var(--button-width, 0px));--max-width: calc(65px + var(--button-width, 0px));min-width:var(--min-width);max-width:var(--max-width)}ion-grid.fill ion-col.hour mat-form-field{width:100%}ion-grid.fill ion-col.hour mat-form-field mat-label,ion-grid.fill ion-col.hour mat-form-field input[type=text]{text-align:left;min-width:52px}ion-grid.outline ion-col.day{min-width:calc(110px + var(--button-width))}ion-grid.outline ion-col.hour{--min-width: calc(65px + var(--button-width));--max-width: calc(75px + var(--button-width))}mat-form-field.mat-form-field-disabled ion-col.day{min-width:150px}.hour mat-form-field.mat-mdc-form-field-should-float .mat-mdc-form-field-placeholder{max-width:inherit}\n"] }]
11203
11203
  }], ctorParameters: () => [{ type: i1.MomentDateAdapter }, { type: i1$1.TranslateService }, { type: i1$3.UntypedFormBuilder }, { type: i0.Renderer2 }, { type: i0.ChangeDetectorRef }, { type: i1$3.FormGroupDirective, decorators: [{
11204
11204
  type: Optional
11205
11205
  }] }, { type: undefined, decorators: [{
@@ -13508,7 +13508,7 @@ class LocalSettingsService extends StartableService {
13508
13508
  locale$ = merge(this.onChange, this.startSubject).pipe(startWith(this.settings), distinctUntilChanged(), map((data) => data?.locale || this.environment?.defaultLocale));
13509
13509
  _optionDefs;
13510
13510
  _serializeAsString;
13511
- _$persist;
13511
+ _$persist = new EventEmitter();
13512
13512
  get settings() {
13513
13513
  return this._data || this.defaultSettings;
13514
13514
  }
@@ -13558,6 +13558,13 @@ class LocalSettingsService extends StartableService {
13558
13558
  // Default value
13559
13559
  this._data.mobile = this.mobile;
13560
13560
  this._data.usageMode = this.usageMode;
13561
+ // Listen persist event
13562
+ this.registerSubscription(this._$persist
13563
+ .pipe(debounceTime(2000), // add a delay of 2 seconds
13564
+ filter(() => this.started))
13565
+ .subscribe(() => {
13566
+ this.save();
13567
+ }));
13561
13568
  // Restoring local settings
13562
13569
  return this.restoreLocally();
13563
13570
  }
@@ -13612,7 +13619,7 @@ class LocalSettingsService extends StartableService {
13612
13619
  this._data.properties[keyOrDef] = isNil(value) ? undefined : value.toString();
13613
13620
  // Update local settings
13614
13621
  if (!opts || opts.emitEvent !== false) {
13615
- this.persistLocally(opts?.immediate);
13622
+ this.save(opts?.immediate);
13616
13623
  }
13617
13624
  }
13618
13625
  getProperty(keyOrDef, defaultValue) {
@@ -13669,10 +13676,10 @@ class LocalSettingsService extends StartableService {
13669
13676
  this._data = data;
13670
13677
  // Save locally
13671
13678
  if (opts && opts.persistImmediate) {
13672
- await this.persistLocally(true);
13679
+ await this.save(true);
13673
13680
  }
13674
13681
  else {
13675
- this.persistLocally(); // No AWAIT
13682
+ this.save(); // No AWAIT
13676
13683
  }
13677
13684
  // Emit event
13678
13685
  if (!opts || opts.emitEvent !== false) {
@@ -13705,7 +13712,7 @@ class LocalSettingsService extends StartableService {
13705
13712
  this._data.pages[key] = value;
13706
13713
  }
13707
13714
  // Update local settings
13708
- this.persistLocally();
13715
+ this.save();
13709
13716
  }
13710
13717
  getOfflineFeature(featureName) {
13711
13718
  if (!this._data || !this._data.offlineFeatures || isEmptyArray(this._data.offlineFeatures))
@@ -13761,7 +13768,7 @@ class LocalSettingsService extends StartableService {
13761
13768
  this._data.offlineFeatures.push(feature);
13762
13769
  }
13763
13770
  // Update local settings
13764
- this.persistLocally();
13771
+ this.save();
13765
13772
  }
13766
13773
  markOfflineFeatureAsSync(featureName) {
13767
13774
  let feature = this.getOfflineFeature(featureName);
@@ -13780,7 +13787,7 @@ class LocalSettingsService extends StartableService {
13780
13787
  if (this._data && this._data.offlineFeatures) {
13781
13788
  this._data.offlineFeatures = [];
13782
13789
  // Update local settings
13783
- this.persistLocally();
13790
+ this.save();
13784
13791
  }
13785
13792
  }
13786
13793
  getFieldDisplayAttributes(fieldName, defaultAttributes) {
@@ -13919,37 +13926,30 @@ class LocalSettingsService extends StartableService {
13919
13926
  if (this.started)
13920
13927
  this.onChange.next(this._data);
13921
13928
  }
13922
- persistLocally(immediate) {
13923
- // Execute immediate
13929
+ async save(immediate) {
13924
13930
  if (immediate) {
13925
- if (!this._data) {
13926
- // INFO
13927
- console.info('[settings] Removing local settings from storage');
13928
- return this.storage.remove(SETTINGS_STORAGE_KEY);
13929
- }
13930
- else {
13931
- // INFO
13932
- console.info('[settings] Store local settings', this._data);
13933
- if (this._serializeAsString) {
13934
- // Fix serialization error, in Sumaris-App
13935
- return this.storage.set(SETTINGS_STORAGE_KEY, JSON.stringify(this._data));
13936
- }
13937
- return this.storage.set(SETTINGS_STORAGE_KEY, this._data);
13938
- }
13931
+ return await this.persistLocally();
13939
13932
  }
13940
- // Execute with delay
13941
13933
  else {
13942
- // Create the event emitter
13943
- if (!this._$persist) {
13944
- this._$persist = new EventEmitter(true);
13945
- this._$persist
13946
- .pipe(debounceTime(2000), // add a delay of 2s
13947
- filter(() => this.started))
13948
- .subscribe(() => this.persistLocally(true));
13949
- }
13950
13934
  this._$persist.emit();
13951
13935
  }
13952
13936
  }
13937
+ persistLocally() {
13938
+ if (!this._data) {
13939
+ // INFO
13940
+ console.info('[settings] Removing local settings from storage');
13941
+ return this.storage.remove(SETTINGS_STORAGE_KEY);
13942
+ }
13943
+ else {
13944
+ // INFO
13945
+ console.info('[settings] Store local settings', this._data);
13946
+ if (this._serializeAsString) {
13947
+ // Fix serialization error, in Sumaris-App
13948
+ return this.storage.set(SETTINGS_STORAGE_KEY, JSON.stringify(this._data));
13949
+ }
13950
+ return this.storage.set(SETTINGS_STORAGE_KEY, this._data);
13951
+ }
13952
+ }
13953
13953
  fillPageHistoryDefaults(page, opts) {
13954
13954
  if (!page || !page.title || !page.path)
13955
13955
  throw Error("Missing required argument 'page', 'page.path' or 'page.title'");
@@ -16753,22 +16753,22 @@ class AppLoadingSpinner {
16753
16753
  color = 'secondary';
16754
16754
  name;
16755
16755
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: AppLoadingSpinner, deps: [], target: i0.ɵɵFactoryTarget.Component });
16756
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.13", type: AppLoadingSpinner, selector: "app-loading-spinner", inputs: { loading: "loading", color: "color", name: "name" }, ngImport: i0, template: `
16757
- <ion-spinner *ngIf="loading; else content" [color]="color" [name]="name"></ion-spinner>
16758
- <ng-template #content>
16759
- <ng-content></ng-content>
16760
- </ng-template>
16756
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.13", type: AppLoadingSpinner, selector: "app-loading-spinner", inputs: { loading: "loading", color: "color", name: "name" }, ngImport: i0, template: `
16757
+ <ion-spinner *ngIf="loading; else content" [color]="color" [name]="name"></ion-spinner>
16758
+ <ng-template #content>
16759
+ <ng-content></ng-content>
16760
+ </ng-template>
16761
16761
  `, isInline: true, dependencies: [{ kind: "directive", type: i3$1.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: i2$1.IonSpinner, selector: "ion-spinner", inputs: ["color", "duration", "name", "paused"] }] });
16762
16762
  }
16763
16763
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: AppLoadingSpinner, decorators: [{
16764
16764
  type: Component,
16765
16765
  args: [{
16766
16766
  selector: 'app-loading-spinner',
16767
- template: `
16768
- <ion-spinner *ngIf="loading; else content" [color]="color" [name]="name"></ion-spinner>
16769
- <ng-template #content>
16770
- <ng-content></ng-content>
16771
- </ng-template>
16767
+ template: `
16768
+ <ion-spinner *ngIf="loading; else content" [color]="color" [name]="name"></ion-spinner>
16769
+ <ng-template #content>
16770
+ <ng-content></ng-content>
16771
+ </ng-template>
16772
16772
  `,
16773
16773
  }]
16774
16774
  }], propDecorators: { loading: [{
@@ -27347,11 +27347,11 @@ class AppImageGalleryComponent {
27347
27347
  this.cd.markForCheck();
27348
27348
  }
27349
27349
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: AppImageGalleryComponent, deps: [{ token: ImageService }, { token: i2$1.Platform }, { token: i2$1.AlertController }, { token: i1$1.TranslateService }, { token: i0.ChangeDetectorRef }, { token: ENVIRONMENT, optional: true }], target: i0.ɵɵFactoryTarget.Component });
27350
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.13", type: AppImageGalleryComponent, selector: "app-image-gallery", inputs: { cardColor: "cardColor", debug: ["debug", "debug", booleanAttribute], disabled: ["disabled", "disabled", booleanAttribute], readOnly: ["readOnly", "readOnly", booleanAttribute], mobile: ["mobile", "mobile", booleanAttribute], mode: "mode", confirmBeforeDelete: "confirmBeforeDelete", showToolbar: ["showToolbar", "showToolbar", booleanAttribute], showFabButton: ["showFabButton", "showFabButton", booleanAttribute], showTitle: ["showTitle", "showTitle", booleanAttribute], showAddToolbarButton: ["showAddToolbarButton", "showAddToolbarButton", booleanAttribute], showAddTextButton: ["showAddTextButton", "showAddTextButton", booleanAttribute], showAddCardButton: ["showAddCardButton", "showAddCardButton", booleanAttribute], showCardToolbar: ["showCardToolbar", "showCardToolbar", booleanAttribute], addButtonColor: "addButtonColor", addButtonText: "addButtonText", cardTemplate: "cardTemplate", imageSizes: "imageSizes", imageSizeQueryParam: "imageSizeQueryParam", dataSource: "dataSource" }, outputs: { onBeforeDeleteRows: "onBeforeDeleteRows", onAfterAddRows: "onAfterAddRows", onAfterEditRow: "onAfterEditRow", click: "click" }, viewQueries: [{ propertyName: "zoomModal", first: true, predicate: ["zoomModal"], descendants: true }, { propertyName: "titlePopover", first: true, predicate: ["titlePopover"], descendants: true }, { propertyName: "swiperRef", first: true, predicate: ["modalSwiper"], descendants: true }], ngImport: i0, template: "<ion-toolbar color=\"light\" *ngIf=\"showToolbar\">\n <ng-content select=\"ion-buttons[slot=start]\"></ng-content>\n\n <!-- Add -->\n @if (!readOnly && showAddToolbarButton && enabled) {\n <button mat-icon-button [title]=\"'COMMON.BTN_ADD' | translate\" (click)=\"add()\">\n <mat-icon>add</mat-icon>\n </button>\n }\n\n <ng-content select=\"ion-buttons[slot=end]\"></ng-content>\n\n <ion-buttons slot=\"end\">\n <!-- Toggle view mode -->\n <ion-segment (ionChange)=\"toggleViewMode($event)\" color=\"accent\" [value]=\"_colSize\">\n <ion-segment-button [value]=\"4\">\n <mat-icon>view_module</mat-icon>\n </ion-segment-button>\n <ion-segment-button [value]=\"12\">\n <mat-icon>view_list</mat-icon>\n </ion-segment-button>\n </ion-segment>\n </ion-buttons>\n</ion-toolbar>\n\n<div class=\"gallery-container ion-padding-bottom {{ this.mode }}\">\n <div *ngIf=\"mobile && zoomActive\" class=\"backdrop\" [style.opacity]=\"zoomScale\"></div>\n\n <ion-grid class=\"ion-no-padding\">\n <ion-row>\n <ion-col *rxFor=\"let row of _data$; index as index; trackBy: trackByFn\" [size]=\"_colSize\">\n @let image = row | propertyGet: 'currentData';\n @if (cardTemplate) {\n <ng-container\n *ngTemplateOutlet=\"cardTemplate; context: { $implicit: row, mode: mode, image: image }\"\n ></ng-container>\n } @else {\n <ion-card\n #card\n class=\"image-card\"\n [class.zoom-hover]=\"!mobile\"\n [color]=\"cardColor\"\n (click)=\"clickRow(row, index)\"\n tappable\n @fadeInAnimation\n >\n <figure class=\"card-thumbnail\">\n @if (image.url) {\n <ion-img [src]=\"image.url | appendQueryParams: getImageSizeQueryParams()\" />\n } @else {\n <ion-img [src]=\"image.dataUrl\" />\n }\n </figure>\n\n <!-- toolbar for title (when not hover) -->\n @if (showTitle && image.title) {\n <ion-toolbar color=\"transparent\" class=\"title\">\n <ion-label class=\"card-title\">{{ image.title }}</ion-label>\n </ion-toolbar>\n }\n\n <!-- action toolbar shown when hover image -->\n @if (!readOnly && !mobile && showCardToolbar) {\n <ion-toolbar #cardToolbar color=\"light\" class=\"buttons\">\n <!-- edit title button -->\n @if (showTitle) {\n <button\n mat-button\n slot=\"start\"\n [disabled]=\"disabled\"\n (click)=\"editTitle($event, row, cardToolbar)\"\n (focusin)=\"focusCardToolbar(cardToolbar)\"\n >\n <mat-icon>edit</mat-icon>\n <mat-label>\n <span *ngIf=\"row.currentData.title | isNotNilOrBlank; else editLabel\" translate>\n IMAGE.GALLERY.BTN_EDIT_TITLE\n </span>\n <ng-template #editLabel>\n <span translate>IMAGE.GALLERY.BTN_ADD_TITLE</span>\n </ng-template>\n </mat-label>\n </button>\n }\n\n <div class=\"flex-spacer\"></div>\n\n <!-- delete button -->\n <button\n mat-icon-button\n slot=\"end\"\n class=\"ion-float-end\"\n [title]=\"'COMMON.BTN_DELETE' | translate\"\n [disabled]=\"disabled\"\n (click)=\"delete($event, row)\"\n >\n <mat-icon>delete</mat-icon>\n </button>\n </ion-toolbar>\n }\n </ion-card>\n }\n </ion-col>\n\n <!-- add button -->\n @if ((showAddTextButton || showAddCardButton) && !readOnly) {\n <ion-col [size]=\"_colSize\" @fadeInAnimation>\n @if (showAddTextButton) {\n <ion-button (click)=\"add($event)\" [disabled]=\"disabled\" [color]=\"addButtonColor\">\n <mat-label translate>{{ addButtonText }}</mat-label>\n <ion-icon slot=\"end\" name=\"camera\"></ion-icon>\n </ion-button>\n } @else if (showAddCardButton) {\n <ion-card\n class=\"image-card-button\"\n color=\"light\"\n (click)=\"add($event)\"\n [disabled]=\"disabled\"\n [title]=\"addButtonText\"\n tappable\n >\n <ion-card-content>\n <div class=\"icon-container\">\n <ion-icon name=\"camera\" [color]=\"addButtonColor\"></ion-icon>\n <ion-icon name=\"add\" [color]=\"addButtonColor\" class=\"icon-secondary\"></ion-icon>\n </div>\n </ion-card-content>\n </ion-card>\n }\n </ion-col>\n }\n </ion-row>\n </ion-grid>\n</div>\n\n<!-- FAB button: add -->\n<ion-fab\n slot=\"fixed\"\n vertical=\"bottom\"\n horizontal=\"end\"\n *ngIf=\"showFabButton && !readOnly\"\n [class.cdk-visually-hidden]=\"disabled\"\n @fadeInOutAnimation\n>\n <ion-fab-button color=\"tertiary\" (click)=\"add($event)\">\n <ion-icon name=\"camera\"></ion-icon>\n <ion-icon name=\"add\" class=\"icon-secondary\" style=\"left: 33px; top: 9px; font-size: 20px\"></ion-icon>\n </ion-fab-button>\n</ion-fab>\n\n<!-- Zoom modal -->\n<ion-modal #zoomModal class=\"stack-modal zoom-modal\" [class.modal-fullscreen]=\"mobile\" [class.modal-large]=\"!mobile\">\n <ng-template>\n <ion-content class=\"ion-no-padding ion-no-margin\">\n @let count = rows?.length || 0;\n <!-- Counter -->\n <div class=\"top-left\">\n <ion-label color=\"light\">{{ activeSlideIndex + 1 }} / {{ count }}</ion-label>\n </div>\n\n <!-- zoom button -->\n <div class=\"top-right\">\n @if (!mobile) {\n <ion-fab-button size=\"small\" (click)=\"zoom(modalSwiper, true)\" color=\"light\">\n <ion-icon name=\"search\"></ion-icon>\n <ion-icon class=\"icon-secondary\" name=\"add\"></ion-icon>\n </ion-fab-button>\n <ion-fab-button size=\"small\" (click)=\"zoom(modalSwiper, false)\" color=\"light\">\n <ion-icon name=\"search\"></ion-icon>\n <ion-icon class=\"icon-secondary\" name=\"remove\"></ion-icon>\n </ion-fab-button>\n }\n </div>\n\n <!-- navigation side buttons next/back -->\n <ng-container *ngIf=\"!mobile && (rows | isArrayLength: { greaterThan: 1 })\">\n <div class=\"side-buttons prev\" (click)=\"slidePrev(modalSwiper)\">\n <ion-icon name=\"chevron-back\"></ion-icon>\n </div>\n <div class=\"side-buttons next\" (click)=\"slideNext(modalSwiper)\">\n <ion-icon name=\"chevron-forward\"></ion-icon>\n </div>\n </ng-container>\n\n <!-- image slides -->\n <swiper-container\n #modalSwiper\n [modules]=\"swiperModules\"\n [zoom]=\"true\"\n (swiperslidechange)=\"onSlideChange(modalSwiper)\"\n (swiperinit)=\"initModalSlides(modalSwiper)\"\n >\n @for (row of rows; track row.id; let last = $last) {\n <swiper-slide>\n @let image = row | propertyGet: 'currentData';\n <div class=\"swiper-zoom-container\">\n @if (image.url) {\n <ion-img [src]=\"image.url | appendQueryParams: getImageSizeQueryParams('modal')\" />\n } @else {\n <img [src]=\"image.dataUrl\" [alt]=\"image.title\" />\n }\n </div>\n </swiper-slide>\n }\n </swiper-container>\n </ion-content>\n\n <ion-footer>\n <ion-toolbar color=\"light\">\n <ion-row>\n <ion-col size=\"4\" class=\"ion-text-start\">\n <ion-button\n *ngIf=\"!readOnly\"\n (click)=\"deleteFromModal($event, modalSwiper)\"\n [disabled]=\"disabled\"\n fill=\"clear\"\n color=\"danger\"\n >\n <mat-icon slot=\"start\">delete</mat-icon>\n {{ 'COMMON.BTN_DELETE' | translate }}\n </ion-button>\n </ion-col>\n <ion-col size=\"4\"></ion-col>\n <ion-col size=\"4\" class=\"ion-text-end\">\n <ion-button (click)=\"zoomModal.dismiss()\" color=\"tertiary\" fill=\"clear\" *ngIf=\"mobile; else desktop\">\n <ion-icon slot=\"start\" name=\"close\"></ion-icon>\n {{ 'COMMON.BTN_CLOSE' | translate }}\n </ion-button>\n <ng-template #desktop>\n <ion-button (click)=\"zoomModal.dismiss()\" color=\"tertiary\">\n {{ 'COMMON.BTN_CLOSE' | translate }}\n </ion-button>\n </ng-template>\n </ion-col>\n </ion-row>\n </ion-toolbar>\n </ion-footer>\n </ng-template>\n</ion-modal>\n\n<ion-popover #titlePopover>\n <ng-template>\n <ion-content class=\"ion-padding\" cdkTrapFocus [cdkTrapFocusAutoCapture]=\"true\">\n <form [formGroup]=\"_titleForm\">\n <mat-form-field floatLabel=\"auto\">\n <mat-label translate>IMAGE.GALLERY.TITLE</mat-label>\n <input\n matInput\n formControlName=\"title\"\n [readonly]=\"disabled\"\n [appAutofocus]=\"_titleAutofocus\"\n (keydown.control.enter)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\n />\n </mat-form-field>\n </form>\n </ion-content>\n\n <ion-footer>\n <ion-toolbar>\n <ion-row class=\"ion-no-padding\" nowrap>\n <ion-col></ion-col>\n\n <ion-col size=\"auto\">\n <ion-button fill=\"clear\" color=\"dark\" (click)=\"titlePopover.dismiss(null, 'CANCEL')\">\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\n </ion-button>\n <ion-button\n [fill]=\"disabled ? 'clear' : 'solid'\"\n (click)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\n (keyup.enter)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\n color=\"tertiary\"\n [disabled]=\"disabled\"\n [title]=\"'COMMON.BTN_VALIDATE_WITH_SHORTCUT_HELP' | translate\"\n >\n <ion-label translate>COMMON.BTN_VALIDATE</ion-label>\n </ion-button>\n </ion-col>\n </ion-row>\n </ion-toolbar>\n </ion-footer>\n </ng-template>\n</ion-popover>\n", styles: [":host{--image-margin-inline: 10px;--image-margin-safe-area: var(--image-margin-inline, 0px) * 2 - 3px;--segment-max-width: 150px}ion-toolbar ion-segment{max-width:var(--segment-max-width)}mat-toolbar,.mat-toolbar-single-row{padding:0;height:42px}ion-card{margin-left:unset;margin-right:unset;margin-inline:var(--image-margin-inline, 10px)}.image-slide{overflow:visible}.image-card{background-color:var(--ion-color-base);z-index:9;--img-scale: 1}.image-card .card-thumbnail{position:relative;overflow:hidden;display:flex;justify-content:center;align-items:center;margin:0;padding:0;width:100%;height:100%;max-height:var(--img-max-height, calc(100% - var(--image-margin-safe-area, 0px)))}.image-card .card-thumbnail>ion-img{min-height:100%;height:100%;object-fit:cover;object-position:center;transition:scale .2s ease-in-out;scale:var(--img-scale)}.image-card .card-thumbnail>ion-img img{max-height:var(--img-max-height)}.image-card.zoom-hover:hover{--img-scale: 1.2}.image-card ion-toolbar{--top-offset: calc(-1 * var(--ion-toolbar-height));position:absolute}.image-card ion-toolbar.title{--padding-start: 16px;--padding-end: 16px;--ion-color-base: rgba(0, 0, 0, .45) !important;position:absolute;top:calc(100% + var(--top-offset));transition:opacity .2s ease-in-out}.image-card ion-toolbar.title ion-label{color:#fff}.image-card ion-toolbar.buttons{--padding-start: 4px;--padding-end: 4px;--ion-color-base: var(--ion-color-light) !important;position:absolute;top:100%;transition:transform .2s ease-in-out}.image-card:hover ion-toolbar.buttons,.image-card ion-toolbar.buttons.focused{transform:translateY(var(--top-offset))}.image-card-button{height:calc(100% - var(--image-margin-safe-area, 0px));max-height:max(min(30vh,200px),var(--img-max-height, 0px));transition:.2s ease-in-out;max-width:250px}.image-card-button ion-card-content{height:100%}.image-card-button .icon-container{height:auto;position:relative;top:calc(50% - 75px);display:flex;align-items:center;justify-content:center}.image-card-button ion-icon:first-of-type{font-size:150px;height:150px;position:relative;top:0}.image-card-button ion-icon.icon-secondary{font-size:50px;position:absolute;top:0;left:max(min(50% + 25px,100% - 50px),0px)}.image-card-button ion-button{float:right}.image-card-button:hover{--ion-color-base: var(--ion-color-shade) !important}.image-card-button:hover ion-icon{--ion-color-base: var(--ion-color-shade) !important}.backdrop{height:100vh;width:100vw;background:#000;position:absolute;z-index:10}.zoom-modal{-webkit-user-select:none;user-select:none}.zoom-modal .top-left{z-index:14;position:absolute;display:inline-grid;left:var(--ion-padding-start, 8px);top:var(--ion-padding-start, 8px)}.zoom-modal .top-right{z-index:14;position:absolute;display:inline-grid;right:var(--ion-padding-start, 8px);top:var(--ion-padding-start, 8px)}.zoom-modal .side-buttons{--side-buttons-width: 120px;--side-buttons-margin: calc(var(--side-buttons-width) / 3);z-index:13;position:absolute;top:0;bottom:0;width:var(--side-buttons-width)}.zoom-modal .side-buttons ion-icon{top:50%;color:#fff;font-size:2.5rem;position:absolute;opacity:0;transition-duration:.15s;transition-timing-function:ease-in}.zoom-modal .side-buttons:hover{cursor:pointer}.zoom-modal .side-buttons:hover ion-icon{opacity:1}.zoom-modal .side-buttons.prev{left:0}.zoom-modal .side-buttons.prev ion-icon{left:var(--side-buttons-margin)}.zoom-modal .side-buttons.next{right:0}.zoom-modal .side-buttons.next ion-icon{right:var(--side-buttons-margin)}.zoom-modal swiper-container{height:100%;background:#000}.zoom-modal ion-fab-button .icon-secondary{top:11px;left:6px;height:14px}\n"], dependencies: [{ kind: "directive", type: i3$1.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: i3$1.NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "component", type: i2$1.IonButton, selector: "ion-button", inputs: ["buttonType", "color", "disabled", "download", "expand", "fill", "form", "href", "mode", "rel", "routerAnimation", "routerDirection", "shape", "size", "strong", "target", "type"] }, { kind: "component", type: i2$1.IonButtons, selector: "ion-buttons", inputs: ["collapse"] }, { kind: "component", type: i2$1.IonCard, selector: "ion-card", inputs: ["button", "color", "disabled", "download", "href", "mode", "rel", "routerAnimation", "routerDirection", "target", "type"] }, { kind: "component", type: i2$1.IonCardContent, selector: "ion-card-content", inputs: ["mode"] }, { kind: "component", type: i2$1.IonCol, selector: "ion-col", inputs: ["offset", "offsetLg", "offsetMd", "offsetSm", "offsetXl", "offsetXs", "pull", "pullLg", "pullMd", "pullSm", "pullXl", "pullXs", "push", "pushLg", "pushMd", "pushSm", "pushXl", "pushXs", "size", "sizeLg", "sizeMd", "sizeSm", "sizeXl", "sizeXs"] }, { kind: "component", type: i2$1.IonContent, selector: "ion-content", inputs: ["color", "forceOverscroll", "fullscreen", "scrollEvents", "scrollX", "scrollY"] }, { kind: "component", type: i2$1.IonFab, selector: "ion-fab", inputs: ["activated", "edge", "horizontal", "vertical"] }, { kind: "component", type: i2$1.IonFabButton, selector: "ion-fab-button", inputs: ["activated", "closeIcon", "color", "disabled", "download", "href", "mode", "rel", "routerAnimation", "routerDirection", "show", "size", "target", "translucent", "type"] }, { kind: "component", type: i2$1.IonFooter, selector: "ion-footer", inputs: ["collapse", "mode", "translucent"] }, { kind: "component", type: i2$1.IonGrid, selector: "ion-grid", inputs: ["fixed"] }, { kind: "component", type: i2$1.IonIcon, selector: "ion-icon", inputs: ["color", "flipRtl", "icon", "ios", "lazy", "md", "mode", "name", "sanitize", "size", "src"] }, { kind: "component", type: i2$1.IonImg, selector: "ion-img", inputs: ["alt", "src"] }, { kind: "component", type: i2$1.IonLabel, selector: "ion-label", inputs: ["color", "mode", "position"] }, { kind: "component", type: i2$1.IonRow, selector: "ion-row" }, { kind: "component", type: i2$1.IonSegment, selector: "ion-segment", inputs: ["color", "disabled", "mode", "scrollable", "selectOnFocus", "swipeGesture", "value"] }, { kind: "component", type: i2$1.IonSegmentButton, selector: "ion-segment-button", inputs: ["disabled", "layout", "mode", "type", "value"] }, { kind: "component", type: i2$1.IonToolbar, selector: "ion-toolbar", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonModal, selector: "ion-modal" }, { kind: "component", type: i2$1.IonPopover, selector: "ion-popover" }, { kind: "directive", type: i2$1.SelectValueAccessor, selector: "ion-select, ion-radio-group, ion-segment, ion-datetime" }, { kind: "directive", type: i1$3.ɵNgNoValidate, selector: "form:not([ngNoForm]):not([ngNativeValidate])" }, { kind: "directive", type: i1$3.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$3.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i1$3.FormGroupDirective, selector: "[formGroup]", inputs: ["formGroup"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: i1$3.FormControlName, selector: "[formControlName]", inputs: ["formControlName", "disabled", "ngModel"], outputs: ["ngModelChange"] }, { kind: "component", type: i3.MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: i3.MatLabel, selector: "mat-label" }, { kind: "directive", type: i4.MatInput, selector: "input[matInput], textarea[matInput], select[matNativeControl], input[matNativeControl], textarea[matNativeControl]", inputs: ["disabled", "id", "placeholder", "name", "required", "type", "errorStateMatcher", "aria-describedby", "value", "readonly"], exportAs: ["matInput"] }, { kind: "component", type: i6$1.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i9.MatButton, selector: " button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button] ", exportAs: ["matButton"] }, { kind: "component", type: i9.MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "directive", type: i1$5.CdkTrapFocus, selector: "[cdkTrapFocus]", inputs: ["cdkTrapFocus", "cdkTrapFocusAutoCapture"], exportAs: ["cdkTrapFocus"] }, { kind: "directive", type: i1$1.TranslateDirective, selector: "[translate],[ngx-translate]", inputs: ["translate", "translateParams"] }, { kind: "directive", type: AutofocusDirective, selector: "[autofocus], input[appAutofocus]", inputs: ["appAutofocus", "autofocusDelay"] }, { kind: "directive", type: i12.RxFor, selector: "[rxFor][rxForOf]", inputs: ["rxForOf", "rxForTemplate", "rxForStrategy", "rxForParent", "rxForPatchZone", "rxForTrackBy", "rxForRenderCallback"] }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }, { kind: "pipe", type: PropertyGetPipe, name: "propertyGet" }, { kind: "pipe", type: ArrayLengthPipe, name: "isArrayLength" }, { kind: "pipe", type: IsNotNilOrBlankPipe, name: "isNotNilOrBlank" }, { kind: "pipe", type: AppendQueryParamsPipePipe, name: "appendQueryParams" }], animations: [fadeInAnimation, fadeInOutAnimation], changeDetection: i0.ChangeDetectionStrategy.OnPush });
27350
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.13", type: AppImageGalleryComponent, selector: "app-image-gallery", inputs: { cardColor: "cardColor", debug: ["debug", "debug", booleanAttribute], disabled: ["disabled", "disabled", booleanAttribute], readOnly: ["readOnly", "readOnly", booleanAttribute], mobile: ["mobile", "mobile", booleanAttribute], mode: "mode", confirmBeforeDelete: "confirmBeforeDelete", showToolbar: ["showToolbar", "showToolbar", booleanAttribute], showFabButton: ["showFabButton", "showFabButton", booleanAttribute], showTitle: ["showTitle", "showTitle", booleanAttribute], showAddToolbarButton: ["showAddToolbarButton", "showAddToolbarButton", booleanAttribute], showAddTextButton: ["showAddTextButton", "showAddTextButton", booleanAttribute], showAddCardButton: ["showAddCardButton", "showAddCardButton", booleanAttribute], showCardToolbar: ["showCardToolbar", "showCardToolbar", booleanAttribute], addButtonColor: "addButtonColor", addButtonText: "addButtonText", cardTemplate: "cardTemplate", imageSizes: "imageSizes", imageSizeQueryParam: "imageSizeQueryParam", dataSource: "dataSource" }, outputs: { onBeforeDeleteRows: "onBeforeDeleteRows", onAfterAddRows: "onAfterAddRows", onAfterEditRow: "onAfterEditRow", click: "click" }, viewQueries: [{ propertyName: "zoomModal", first: true, predicate: ["zoomModal"], descendants: true }, { propertyName: "titlePopover", first: true, predicate: ["titlePopover"], descendants: true }, { propertyName: "swiperRef", first: true, predicate: ["modalSwiper"], descendants: true }], ngImport: i0, template: "<ion-toolbar color=\"light\" *ngIf=\"showToolbar\">\r\n <ng-content select=\"ion-buttons[slot=start]\"></ng-content>\r\n\r\n <!-- Add -->\r\n @if (!readOnly && showAddToolbarButton && enabled) {\r\n <button mat-icon-button [title]=\"'COMMON.BTN_ADD' | translate\" (click)=\"add()\">\r\n <mat-icon>add</mat-icon>\r\n </button>\r\n }\r\n\r\n <ng-content select=\"ion-buttons[slot=end]\"></ng-content>\r\n\r\n <ion-buttons slot=\"end\">\r\n <!-- Toggle view mode -->\r\n <ion-segment (ionChange)=\"toggleViewMode($event)\" color=\"accent\" [value]=\"_colSize\">\r\n <ion-segment-button [value]=\"4\">\r\n <mat-icon>view_module</mat-icon>\r\n </ion-segment-button>\r\n <ion-segment-button [value]=\"12\">\r\n <mat-icon>view_list</mat-icon>\r\n </ion-segment-button>\r\n </ion-segment>\r\n </ion-buttons>\r\n</ion-toolbar>\r\n\r\n<div class=\"gallery-container ion-padding-bottom {{ this.mode }}\">\r\n <div *ngIf=\"mobile && zoomActive\" class=\"backdrop\" [style.opacity]=\"zoomScale\"></div>\r\n\r\n <ion-grid class=\"ion-no-padding\">\r\n <ion-row>\r\n <ion-col *rxFor=\"let row of _data$; index as index; trackBy: trackByFn\" [size]=\"_colSize\">\r\n @let image = row | propertyGet: 'currentData';\r\n @if (cardTemplate) {\r\n <ng-container\r\n *ngTemplateOutlet=\"cardTemplate; context: { $implicit: row, mode: mode, image: image }\"\r\n ></ng-container>\r\n } @else {\r\n <ion-card\r\n #card\r\n class=\"image-card\"\r\n [class.zoom-hover]=\"!mobile\"\r\n [color]=\"cardColor\"\r\n (click)=\"clickRow(row, index)\"\r\n tappable\r\n @fadeInAnimation\r\n >\r\n <figure class=\"card-thumbnail\">\r\n @if (image.url) {\r\n <ion-img [src]=\"image.url | appendQueryParams: getImageSizeQueryParams()\" />\r\n } @else {\r\n <ion-img [src]=\"image.dataUrl\" />\r\n }\r\n </figure>\r\n\r\n <!-- toolbar for title (when not hover) -->\r\n @if (showTitle && image.title) {\r\n <ion-toolbar color=\"transparent\" class=\"title\">\r\n <ion-label class=\"card-title\">{{ image.title }}</ion-label>\r\n </ion-toolbar>\r\n }\r\n\r\n <!-- action toolbar shown when hover image -->\r\n @if (!readOnly && !mobile && showCardToolbar) {\r\n <ion-toolbar #cardToolbar color=\"light\" class=\"buttons\">\r\n <!-- edit title button -->\r\n @if (showTitle) {\r\n <button\r\n mat-button\r\n slot=\"start\"\r\n [disabled]=\"disabled\"\r\n (click)=\"editTitle($event, row, cardToolbar)\"\r\n (focusin)=\"focusCardToolbar(cardToolbar)\"\r\n >\r\n <mat-icon>edit</mat-icon>\r\n <mat-label>\r\n <span *ngIf=\"row.currentData.title | isNotNilOrBlank; else editLabel\" translate>\r\n IMAGE.GALLERY.BTN_EDIT_TITLE\r\n </span>\r\n <ng-template #editLabel>\r\n <span translate>IMAGE.GALLERY.BTN_ADD_TITLE</span>\r\n </ng-template>\r\n </mat-label>\r\n </button>\r\n }\r\n\r\n <div class=\"flex-spacer\"></div>\r\n\r\n <!-- delete button -->\r\n <button\r\n mat-icon-button\r\n slot=\"end\"\r\n class=\"ion-float-end\"\r\n [title]=\"'COMMON.BTN_DELETE' | translate\"\r\n [disabled]=\"disabled\"\r\n (click)=\"delete($event, row)\"\r\n >\r\n <mat-icon>delete</mat-icon>\r\n </button>\r\n </ion-toolbar>\r\n }\r\n </ion-card>\r\n }\r\n </ion-col>\r\n\r\n <!-- add button -->\r\n @if ((showAddTextButton || showAddCardButton) && !readOnly) {\r\n <ion-col [size]=\"_colSize\" @fadeInAnimation>\r\n @if (showAddTextButton) {\r\n <ion-button (click)=\"add($event)\" [disabled]=\"disabled\" [color]=\"addButtonColor\">\r\n <mat-label translate>{{ addButtonText }}</mat-label>\r\n <ion-icon slot=\"end\" name=\"camera\"></ion-icon>\r\n </ion-button>\r\n } @else if (showAddCardButton) {\r\n <ion-card\r\n class=\"image-card-button\"\r\n color=\"light\"\r\n (click)=\"add($event)\"\r\n [disabled]=\"disabled\"\r\n [title]=\"addButtonText\"\r\n tappable\r\n >\r\n <ion-card-content>\r\n <div class=\"icon-container\">\r\n <ion-icon name=\"camera\" [color]=\"addButtonColor\"></ion-icon>\r\n <ion-icon name=\"add\" [color]=\"addButtonColor\" class=\"icon-secondary\"></ion-icon>\r\n </div>\r\n </ion-card-content>\r\n </ion-card>\r\n }\r\n </ion-col>\r\n }\r\n </ion-row>\r\n </ion-grid>\r\n</div>\r\n\r\n<!-- FAB button: add -->\r\n<ion-fab\r\n slot=\"fixed\"\r\n vertical=\"bottom\"\r\n horizontal=\"end\"\r\n *ngIf=\"showFabButton && !readOnly\"\r\n [class.cdk-visually-hidden]=\"disabled\"\r\n @fadeInOutAnimation\r\n>\r\n <ion-fab-button color=\"tertiary\" (click)=\"add($event)\">\r\n <ion-icon name=\"camera\"></ion-icon>\r\n <ion-icon name=\"add\" class=\"icon-secondary\" style=\"left: 33px; top: 9px; font-size: 20px\"></ion-icon>\r\n </ion-fab-button>\r\n</ion-fab>\r\n\r\n<!-- Zoom modal -->\r\n<ion-modal #zoomModal class=\"stack-modal zoom-modal\" [class.modal-fullscreen]=\"mobile\" [class.modal-large]=\"!mobile\">\r\n <ng-template>\r\n <ion-content class=\"ion-no-padding ion-no-margin\">\r\n @let count = rows?.length || 0;\r\n <!-- Counter -->\r\n <div class=\"top-left\">\r\n <ion-label color=\"light\">{{ activeSlideIndex + 1 }} / {{ count }}</ion-label>\r\n </div>\r\n\r\n <!-- zoom button -->\r\n <div class=\"top-right\">\r\n @if (!mobile) {\r\n <ion-fab-button size=\"small\" (click)=\"zoom(modalSwiper, true)\" color=\"light\">\r\n <ion-icon name=\"search\"></ion-icon>\r\n <ion-icon class=\"icon-secondary\" name=\"add\"></ion-icon>\r\n </ion-fab-button>\r\n <ion-fab-button size=\"small\" (click)=\"zoom(modalSwiper, false)\" color=\"light\">\r\n <ion-icon name=\"search\"></ion-icon>\r\n <ion-icon class=\"icon-secondary\" name=\"remove\"></ion-icon>\r\n </ion-fab-button>\r\n }\r\n </div>\r\n\r\n <!-- navigation side buttons next/back -->\r\n <ng-container *ngIf=\"!mobile && (rows | isArrayLength: { greaterThan: 1 })\">\r\n <div class=\"side-buttons prev\" (click)=\"slidePrev(modalSwiper)\">\r\n <ion-icon name=\"chevron-back\"></ion-icon>\r\n </div>\r\n <div class=\"side-buttons next\" (click)=\"slideNext(modalSwiper)\">\r\n <ion-icon name=\"chevron-forward\"></ion-icon>\r\n </div>\r\n </ng-container>\r\n\r\n <!-- image slides -->\r\n <swiper-container\r\n #modalSwiper\r\n [modules]=\"swiperModules\"\r\n [zoom]=\"true\"\r\n (swiperslidechange)=\"onSlideChange(modalSwiper)\"\r\n (swiperinit)=\"initModalSlides(modalSwiper)\"\r\n >\r\n @for (row of rows; track row.id; let last = $last) {\r\n <swiper-slide>\r\n @let image = row | propertyGet: 'currentData';\r\n <div class=\"swiper-zoom-container\">\r\n @if (image.url) {\r\n <ion-img [src]=\"image.url | appendQueryParams: getImageSizeQueryParams('modal')\" />\r\n } @else {\r\n <img [src]=\"image.dataUrl\" [alt]=\"image.title\" />\r\n }\r\n </div>\r\n </swiper-slide>\r\n }\r\n </swiper-container>\r\n </ion-content>\r\n\r\n <ion-footer>\r\n <ion-toolbar color=\"light\">\r\n <ion-row>\r\n <ion-col size=\"4\" class=\"ion-text-start\">\r\n <ion-button\r\n *ngIf=\"!readOnly\"\r\n (click)=\"deleteFromModal($event, modalSwiper)\"\r\n [disabled]=\"disabled\"\r\n fill=\"clear\"\r\n color=\"danger\"\r\n >\r\n <mat-icon slot=\"start\">delete</mat-icon>\r\n {{ 'COMMON.BTN_DELETE' | translate }}\r\n </ion-button>\r\n </ion-col>\r\n <ion-col size=\"4\"></ion-col>\r\n <ion-col size=\"4\" class=\"ion-text-end\">\r\n <ion-button (click)=\"zoomModal.dismiss()\" color=\"tertiary\" fill=\"clear\" *ngIf=\"mobile; else desktop\">\r\n <ion-icon slot=\"start\" name=\"close\"></ion-icon>\r\n {{ 'COMMON.BTN_CLOSE' | translate }}\r\n </ion-button>\r\n <ng-template #desktop>\r\n <ion-button (click)=\"zoomModal.dismiss()\" color=\"tertiary\">\r\n {{ 'COMMON.BTN_CLOSE' | translate }}\r\n </ion-button>\r\n </ng-template>\r\n </ion-col>\r\n </ion-row>\r\n </ion-toolbar>\r\n </ion-footer>\r\n </ng-template>\r\n</ion-modal>\r\n\r\n<ion-popover #titlePopover>\r\n <ng-template>\r\n <ion-content class=\"ion-padding\" cdkTrapFocus [cdkTrapFocusAutoCapture]=\"true\">\r\n <form [formGroup]=\"_titleForm\">\r\n <mat-form-field floatLabel=\"auto\">\r\n <mat-label translate>IMAGE.GALLERY.TITLE</mat-label>\r\n <input\r\n matInput\r\n formControlName=\"title\"\r\n [readonly]=\"disabled\"\r\n [appAutofocus]=\"_titleAutofocus\"\r\n (keydown.control.enter)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\r\n />\r\n </mat-form-field>\r\n </form>\r\n </ion-content>\r\n\r\n <ion-footer>\r\n <ion-toolbar>\r\n <ion-row class=\"ion-no-padding\" nowrap>\r\n <ion-col></ion-col>\r\n\r\n <ion-col size=\"auto\">\r\n <ion-button fill=\"clear\" color=\"dark\" (click)=\"titlePopover.dismiss(null, 'CANCEL')\">\r\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\r\n </ion-button>\r\n <ion-button\r\n [fill]=\"disabled ? 'clear' : 'solid'\"\r\n (click)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\r\n (keyup.enter)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\r\n color=\"tertiary\"\r\n [disabled]=\"disabled\"\r\n [title]=\"'COMMON.BTN_VALIDATE_WITH_SHORTCUT_HELP' | translate\"\r\n >\r\n <ion-label translate>COMMON.BTN_VALIDATE</ion-label>\r\n </ion-button>\r\n </ion-col>\r\n </ion-row>\r\n </ion-toolbar>\r\n </ion-footer>\r\n </ng-template>\r\n</ion-popover>\r\n", styles: [":host{--image-margin-inline: 10px;--image-margin-safe-area: var(--image-margin-inline, 0px) * 2 - 3px;--segment-max-width: 150px}ion-toolbar ion-segment{max-width:var(--segment-max-width)}mat-toolbar,.mat-toolbar-single-row{padding:0;height:42px}ion-card{margin-left:unset;margin-right:unset;margin-inline:var(--image-margin-inline, 10px)}.image-slide{overflow:visible}.image-card{background-color:var(--ion-color-base);z-index:9;--img-scale: 1}.image-card .card-thumbnail{position:relative;overflow:hidden;display:flex;justify-content:center;align-items:center;margin:0;padding:0;width:100%;height:100%;max-height:var(--img-max-height, calc(100% - var(--image-margin-safe-area, 0px)))}.image-card .card-thumbnail>ion-img{min-height:100%;height:100%;object-fit:cover;object-position:center;transition:scale .2s ease-in-out;scale:var(--img-scale)}.image-card .card-thumbnail>ion-img img{max-height:var(--img-max-height)}.image-card.zoom-hover:hover{--img-scale: 1.2}.image-card ion-toolbar{--top-offset: calc(-1 * var(--ion-toolbar-height));position:absolute}.image-card ion-toolbar.title{--padding-start: 16px;--padding-end: 16px;--ion-color-base: rgba(0, 0, 0, .45) !important;position:absolute;top:calc(100% + var(--top-offset));transition:opacity .2s ease-in-out}.image-card ion-toolbar.title ion-label{color:#fff}.image-card ion-toolbar.buttons{--padding-start: 4px;--padding-end: 4px;--ion-color-base: var(--ion-color-light) !important;position:absolute;top:100%;transition:transform .2s ease-in-out}.image-card:hover ion-toolbar.buttons,.image-card ion-toolbar.buttons.focused{transform:translateY(var(--top-offset))}.image-card-button{height:calc(100% - var(--image-margin-safe-area, 0px));max-height:max(min(30vh,200px),var(--img-max-height, 0px));transition:.2s ease-in-out;max-width:250px}.image-card-button ion-card-content{height:100%}.image-card-button .icon-container{height:auto;position:relative;top:calc(50% - 75px);display:flex;align-items:center;justify-content:center}.image-card-button ion-icon:first-of-type{font-size:150px;height:150px;position:relative;top:0}.image-card-button ion-icon.icon-secondary{font-size:50px;position:absolute;top:0;left:max(min(50% + 25px,100% - 50px),0px)}.image-card-button ion-button{float:right}.image-card-button:hover{--ion-color-base: var(--ion-color-shade) !important}.image-card-button:hover ion-icon{--ion-color-base: var(--ion-color-shade) !important}.backdrop{height:100vh;width:100vw;background:#000;position:absolute;z-index:10}.zoom-modal{-webkit-user-select:none;user-select:none}.zoom-modal .top-left{z-index:14;position:absolute;display:inline-grid;left:var(--ion-padding-start, 8px);top:var(--ion-padding-start, 8px)}.zoom-modal .top-right{z-index:14;position:absolute;display:inline-grid;right:var(--ion-padding-start, 8px);top:var(--ion-padding-start, 8px)}.zoom-modal .side-buttons{--side-buttons-width: 120px;--side-buttons-margin: calc(var(--side-buttons-width) / 3);z-index:13;position:absolute;top:0;bottom:0;width:var(--side-buttons-width)}.zoom-modal .side-buttons ion-icon{top:50%;color:#fff;font-size:2.5rem;position:absolute;opacity:0;transition-duration:.15s;transition-timing-function:ease-in}.zoom-modal .side-buttons:hover{cursor:pointer}.zoom-modal .side-buttons:hover ion-icon{opacity:1}.zoom-modal .side-buttons.prev{left:0}.zoom-modal .side-buttons.prev ion-icon{left:var(--side-buttons-margin)}.zoom-modal .side-buttons.next{right:0}.zoom-modal .side-buttons.next ion-icon{right:var(--side-buttons-margin)}.zoom-modal swiper-container{height:100%;background:#000}.zoom-modal ion-fab-button .icon-secondary{top:11px;left:6px;height:14px}\n"], dependencies: [{ kind: "directive", type: i3$1.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: i3$1.NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "component", type: i2$1.IonButton, selector: "ion-button", inputs: ["buttonType", "color", "disabled", "download", "expand", "fill", "form", "href", "mode", "rel", "routerAnimation", "routerDirection", "shape", "size", "strong", "target", "type"] }, { kind: "component", type: i2$1.IonButtons, selector: "ion-buttons", inputs: ["collapse"] }, { kind: "component", type: i2$1.IonCard, selector: "ion-card", inputs: ["button", "color", "disabled", "download", "href", "mode", "rel", "routerAnimation", "routerDirection", "target", "type"] }, { kind: "component", type: i2$1.IonCardContent, selector: "ion-card-content", inputs: ["mode"] }, { kind: "component", type: i2$1.IonCol, selector: "ion-col", inputs: ["offset", "offsetLg", "offsetMd", "offsetSm", "offsetXl", "offsetXs", "pull", "pullLg", "pullMd", "pullSm", "pullXl", "pullXs", "push", "pushLg", "pushMd", "pushSm", "pushXl", "pushXs", "size", "sizeLg", "sizeMd", "sizeSm", "sizeXl", "sizeXs"] }, { kind: "component", type: i2$1.IonContent, selector: "ion-content", inputs: ["color", "forceOverscroll", "fullscreen", "scrollEvents", "scrollX", "scrollY"] }, { kind: "component", type: i2$1.IonFab, selector: "ion-fab", inputs: ["activated", "edge", "horizontal", "vertical"] }, { kind: "component", type: i2$1.IonFabButton, selector: "ion-fab-button", inputs: ["activated", "closeIcon", "color", "disabled", "download", "href", "mode", "rel", "routerAnimation", "routerDirection", "show", "size", "target", "translucent", "type"] }, { kind: "component", type: i2$1.IonFooter, selector: "ion-footer", inputs: ["collapse", "mode", "translucent"] }, { kind: "component", type: i2$1.IonGrid, selector: "ion-grid", inputs: ["fixed"] }, { kind: "component", type: i2$1.IonIcon, selector: "ion-icon", inputs: ["color", "flipRtl", "icon", "ios", "lazy", "md", "mode", "name", "sanitize", "size", "src"] }, { kind: "component", type: i2$1.IonImg, selector: "ion-img", inputs: ["alt", "src"] }, { kind: "component", type: i2$1.IonLabel, selector: "ion-label", inputs: ["color", "mode", "position"] }, { kind: "component", type: i2$1.IonRow, selector: "ion-row" }, { kind: "component", type: i2$1.IonSegment, selector: "ion-segment", inputs: ["color", "disabled", "mode", "scrollable", "selectOnFocus", "swipeGesture", "value"] }, { kind: "component", type: i2$1.IonSegmentButton, selector: "ion-segment-button", inputs: ["disabled", "layout", "mode", "type", "value"] }, { kind: "component", type: i2$1.IonToolbar, selector: "ion-toolbar", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonModal, selector: "ion-modal" }, { kind: "component", type: i2$1.IonPopover, selector: "ion-popover" }, { kind: "directive", type: i2$1.SelectValueAccessor, selector: "ion-select, ion-radio-group, ion-segment, ion-datetime" }, { kind: "directive", type: i1$3.ɵNgNoValidate, selector: "form:not([ngNoForm]):not([ngNativeValidate])" }, { kind: "directive", type: i1$3.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$3.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i1$3.FormGroupDirective, selector: "[formGroup]", inputs: ["formGroup"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: i1$3.FormControlName, selector: "[formControlName]", inputs: ["formControlName", "disabled", "ngModel"], outputs: ["ngModelChange"] }, { kind: "component", type: i3.MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: i3.MatLabel, selector: "mat-label" }, { kind: "directive", type: i4.MatInput, selector: "input[matInput], textarea[matInput], select[matNativeControl], input[matNativeControl], textarea[matNativeControl]", inputs: ["disabled", "id", "placeholder", "name", "required", "type", "errorStateMatcher", "aria-describedby", "value", "readonly"], exportAs: ["matInput"] }, { kind: "component", type: i6$1.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i9.MatButton, selector: " button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button] ", exportAs: ["matButton"] }, { kind: "component", type: i9.MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "directive", type: i1$5.CdkTrapFocus, selector: "[cdkTrapFocus]", inputs: ["cdkTrapFocus", "cdkTrapFocusAutoCapture"], exportAs: ["cdkTrapFocus"] }, { kind: "directive", type: i1$1.TranslateDirective, selector: "[translate],[ngx-translate]", inputs: ["translate", "translateParams"] }, { kind: "directive", type: AutofocusDirective, selector: "[autofocus], input[appAutofocus]", inputs: ["appAutofocus", "autofocusDelay"] }, { kind: "directive", type: i12.RxFor, selector: "[rxFor][rxForOf]", inputs: ["rxForOf", "rxForTemplate", "rxForStrategy", "rxForParent", "rxForPatchZone", "rxForTrackBy", "rxForRenderCallback"] }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }, { kind: "pipe", type: PropertyGetPipe, name: "propertyGet" }, { kind: "pipe", type: ArrayLengthPipe, name: "isArrayLength" }, { kind: "pipe", type: IsNotNilOrBlankPipe, name: "isNotNilOrBlank" }, { kind: "pipe", type: AppendQueryParamsPipePipe, name: "appendQueryParams" }], animations: [fadeInAnimation, fadeInOutAnimation], changeDetection: i0.ChangeDetectionStrategy.OnPush });
27351
27351
  }
27352
27352
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: AppImageGalleryComponent, decorators: [{
27353
27353
  type: Component,
27354
- args: [{ selector: 'app-image-gallery', animations: [fadeInAnimation, fadeInOutAnimation], changeDetection: ChangeDetectionStrategy.OnPush, template: "<ion-toolbar color=\"light\" *ngIf=\"showToolbar\">\n <ng-content select=\"ion-buttons[slot=start]\"></ng-content>\n\n <!-- Add -->\n @if (!readOnly && showAddToolbarButton && enabled) {\n <button mat-icon-button [title]=\"'COMMON.BTN_ADD' | translate\" (click)=\"add()\">\n <mat-icon>add</mat-icon>\n </button>\n }\n\n <ng-content select=\"ion-buttons[slot=end]\"></ng-content>\n\n <ion-buttons slot=\"end\">\n <!-- Toggle view mode -->\n <ion-segment (ionChange)=\"toggleViewMode($event)\" color=\"accent\" [value]=\"_colSize\">\n <ion-segment-button [value]=\"4\">\n <mat-icon>view_module</mat-icon>\n </ion-segment-button>\n <ion-segment-button [value]=\"12\">\n <mat-icon>view_list</mat-icon>\n </ion-segment-button>\n </ion-segment>\n </ion-buttons>\n</ion-toolbar>\n\n<div class=\"gallery-container ion-padding-bottom {{ this.mode }}\">\n <div *ngIf=\"mobile && zoomActive\" class=\"backdrop\" [style.opacity]=\"zoomScale\"></div>\n\n <ion-grid class=\"ion-no-padding\">\n <ion-row>\n <ion-col *rxFor=\"let row of _data$; index as index; trackBy: trackByFn\" [size]=\"_colSize\">\n @let image = row | propertyGet: 'currentData';\n @if (cardTemplate) {\n <ng-container\n *ngTemplateOutlet=\"cardTemplate; context: { $implicit: row, mode: mode, image: image }\"\n ></ng-container>\n } @else {\n <ion-card\n #card\n class=\"image-card\"\n [class.zoom-hover]=\"!mobile\"\n [color]=\"cardColor\"\n (click)=\"clickRow(row, index)\"\n tappable\n @fadeInAnimation\n >\n <figure class=\"card-thumbnail\">\n @if (image.url) {\n <ion-img [src]=\"image.url | appendQueryParams: getImageSizeQueryParams()\" />\n } @else {\n <ion-img [src]=\"image.dataUrl\" />\n }\n </figure>\n\n <!-- toolbar for title (when not hover) -->\n @if (showTitle && image.title) {\n <ion-toolbar color=\"transparent\" class=\"title\">\n <ion-label class=\"card-title\">{{ image.title }}</ion-label>\n </ion-toolbar>\n }\n\n <!-- action toolbar shown when hover image -->\n @if (!readOnly && !mobile && showCardToolbar) {\n <ion-toolbar #cardToolbar color=\"light\" class=\"buttons\">\n <!-- edit title button -->\n @if (showTitle) {\n <button\n mat-button\n slot=\"start\"\n [disabled]=\"disabled\"\n (click)=\"editTitle($event, row, cardToolbar)\"\n (focusin)=\"focusCardToolbar(cardToolbar)\"\n >\n <mat-icon>edit</mat-icon>\n <mat-label>\n <span *ngIf=\"row.currentData.title | isNotNilOrBlank; else editLabel\" translate>\n IMAGE.GALLERY.BTN_EDIT_TITLE\n </span>\n <ng-template #editLabel>\n <span translate>IMAGE.GALLERY.BTN_ADD_TITLE</span>\n </ng-template>\n </mat-label>\n </button>\n }\n\n <div class=\"flex-spacer\"></div>\n\n <!-- delete button -->\n <button\n mat-icon-button\n slot=\"end\"\n class=\"ion-float-end\"\n [title]=\"'COMMON.BTN_DELETE' | translate\"\n [disabled]=\"disabled\"\n (click)=\"delete($event, row)\"\n >\n <mat-icon>delete</mat-icon>\n </button>\n </ion-toolbar>\n }\n </ion-card>\n }\n </ion-col>\n\n <!-- add button -->\n @if ((showAddTextButton || showAddCardButton) && !readOnly) {\n <ion-col [size]=\"_colSize\" @fadeInAnimation>\n @if (showAddTextButton) {\n <ion-button (click)=\"add($event)\" [disabled]=\"disabled\" [color]=\"addButtonColor\">\n <mat-label translate>{{ addButtonText }}</mat-label>\n <ion-icon slot=\"end\" name=\"camera\"></ion-icon>\n </ion-button>\n } @else if (showAddCardButton) {\n <ion-card\n class=\"image-card-button\"\n color=\"light\"\n (click)=\"add($event)\"\n [disabled]=\"disabled\"\n [title]=\"addButtonText\"\n tappable\n >\n <ion-card-content>\n <div class=\"icon-container\">\n <ion-icon name=\"camera\" [color]=\"addButtonColor\"></ion-icon>\n <ion-icon name=\"add\" [color]=\"addButtonColor\" class=\"icon-secondary\"></ion-icon>\n </div>\n </ion-card-content>\n </ion-card>\n }\n </ion-col>\n }\n </ion-row>\n </ion-grid>\n</div>\n\n<!-- FAB button: add -->\n<ion-fab\n slot=\"fixed\"\n vertical=\"bottom\"\n horizontal=\"end\"\n *ngIf=\"showFabButton && !readOnly\"\n [class.cdk-visually-hidden]=\"disabled\"\n @fadeInOutAnimation\n>\n <ion-fab-button color=\"tertiary\" (click)=\"add($event)\">\n <ion-icon name=\"camera\"></ion-icon>\n <ion-icon name=\"add\" class=\"icon-secondary\" style=\"left: 33px; top: 9px; font-size: 20px\"></ion-icon>\n </ion-fab-button>\n</ion-fab>\n\n<!-- Zoom modal -->\n<ion-modal #zoomModal class=\"stack-modal zoom-modal\" [class.modal-fullscreen]=\"mobile\" [class.modal-large]=\"!mobile\">\n <ng-template>\n <ion-content class=\"ion-no-padding ion-no-margin\">\n @let count = rows?.length || 0;\n <!-- Counter -->\n <div class=\"top-left\">\n <ion-label color=\"light\">{{ activeSlideIndex + 1 }} / {{ count }}</ion-label>\n </div>\n\n <!-- zoom button -->\n <div class=\"top-right\">\n @if (!mobile) {\n <ion-fab-button size=\"small\" (click)=\"zoom(modalSwiper, true)\" color=\"light\">\n <ion-icon name=\"search\"></ion-icon>\n <ion-icon class=\"icon-secondary\" name=\"add\"></ion-icon>\n </ion-fab-button>\n <ion-fab-button size=\"small\" (click)=\"zoom(modalSwiper, false)\" color=\"light\">\n <ion-icon name=\"search\"></ion-icon>\n <ion-icon class=\"icon-secondary\" name=\"remove\"></ion-icon>\n </ion-fab-button>\n }\n </div>\n\n <!-- navigation side buttons next/back -->\n <ng-container *ngIf=\"!mobile && (rows | isArrayLength: { greaterThan: 1 })\">\n <div class=\"side-buttons prev\" (click)=\"slidePrev(modalSwiper)\">\n <ion-icon name=\"chevron-back\"></ion-icon>\n </div>\n <div class=\"side-buttons next\" (click)=\"slideNext(modalSwiper)\">\n <ion-icon name=\"chevron-forward\"></ion-icon>\n </div>\n </ng-container>\n\n <!-- image slides -->\n <swiper-container\n #modalSwiper\n [modules]=\"swiperModules\"\n [zoom]=\"true\"\n (swiperslidechange)=\"onSlideChange(modalSwiper)\"\n (swiperinit)=\"initModalSlides(modalSwiper)\"\n >\n @for (row of rows; track row.id; let last = $last) {\n <swiper-slide>\n @let image = row | propertyGet: 'currentData';\n <div class=\"swiper-zoom-container\">\n @if (image.url) {\n <ion-img [src]=\"image.url | appendQueryParams: getImageSizeQueryParams('modal')\" />\n } @else {\n <img [src]=\"image.dataUrl\" [alt]=\"image.title\" />\n }\n </div>\n </swiper-slide>\n }\n </swiper-container>\n </ion-content>\n\n <ion-footer>\n <ion-toolbar color=\"light\">\n <ion-row>\n <ion-col size=\"4\" class=\"ion-text-start\">\n <ion-button\n *ngIf=\"!readOnly\"\n (click)=\"deleteFromModal($event, modalSwiper)\"\n [disabled]=\"disabled\"\n fill=\"clear\"\n color=\"danger\"\n >\n <mat-icon slot=\"start\">delete</mat-icon>\n {{ 'COMMON.BTN_DELETE' | translate }}\n </ion-button>\n </ion-col>\n <ion-col size=\"4\"></ion-col>\n <ion-col size=\"4\" class=\"ion-text-end\">\n <ion-button (click)=\"zoomModal.dismiss()\" color=\"tertiary\" fill=\"clear\" *ngIf=\"mobile; else desktop\">\n <ion-icon slot=\"start\" name=\"close\"></ion-icon>\n {{ 'COMMON.BTN_CLOSE' | translate }}\n </ion-button>\n <ng-template #desktop>\n <ion-button (click)=\"zoomModal.dismiss()\" color=\"tertiary\">\n {{ 'COMMON.BTN_CLOSE' | translate }}\n </ion-button>\n </ng-template>\n </ion-col>\n </ion-row>\n </ion-toolbar>\n </ion-footer>\n </ng-template>\n</ion-modal>\n\n<ion-popover #titlePopover>\n <ng-template>\n <ion-content class=\"ion-padding\" cdkTrapFocus [cdkTrapFocusAutoCapture]=\"true\">\n <form [formGroup]=\"_titleForm\">\n <mat-form-field floatLabel=\"auto\">\n <mat-label translate>IMAGE.GALLERY.TITLE</mat-label>\n <input\n matInput\n formControlName=\"title\"\n [readonly]=\"disabled\"\n [appAutofocus]=\"_titleAutofocus\"\n (keydown.control.enter)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\n />\n </mat-form-field>\n </form>\n </ion-content>\n\n <ion-footer>\n <ion-toolbar>\n <ion-row class=\"ion-no-padding\" nowrap>\n <ion-col></ion-col>\n\n <ion-col size=\"auto\">\n <ion-button fill=\"clear\" color=\"dark\" (click)=\"titlePopover.dismiss(null, 'CANCEL')\">\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\n </ion-button>\n <ion-button\n [fill]=\"disabled ? 'clear' : 'solid'\"\n (click)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\n (keyup.enter)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\n color=\"tertiary\"\n [disabled]=\"disabled\"\n [title]=\"'COMMON.BTN_VALIDATE_WITH_SHORTCUT_HELP' | translate\"\n >\n <ion-label translate>COMMON.BTN_VALIDATE</ion-label>\n </ion-button>\n </ion-col>\n </ion-row>\n </ion-toolbar>\n </ion-footer>\n </ng-template>\n</ion-popover>\n", styles: [":host{--image-margin-inline: 10px;--image-margin-safe-area: var(--image-margin-inline, 0px) * 2 - 3px;--segment-max-width: 150px}ion-toolbar ion-segment{max-width:var(--segment-max-width)}mat-toolbar,.mat-toolbar-single-row{padding:0;height:42px}ion-card{margin-left:unset;margin-right:unset;margin-inline:var(--image-margin-inline, 10px)}.image-slide{overflow:visible}.image-card{background-color:var(--ion-color-base);z-index:9;--img-scale: 1}.image-card .card-thumbnail{position:relative;overflow:hidden;display:flex;justify-content:center;align-items:center;margin:0;padding:0;width:100%;height:100%;max-height:var(--img-max-height, calc(100% - var(--image-margin-safe-area, 0px)))}.image-card .card-thumbnail>ion-img{min-height:100%;height:100%;object-fit:cover;object-position:center;transition:scale .2s ease-in-out;scale:var(--img-scale)}.image-card .card-thumbnail>ion-img img{max-height:var(--img-max-height)}.image-card.zoom-hover:hover{--img-scale: 1.2}.image-card ion-toolbar{--top-offset: calc(-1 * var(--ion-toolbar-height));position:absolute}.image-card ion-toolbar.title{--padding-start: 16px;--padding-end: 16px;--ion-color-base: rgba(0, 0, 0, .45) !important;position:absolute;top:calc(100% + var(--top-offset));transition:opacity .2s ease-in-out}.image-card ion-toolbar.title ion-label{color:#fff}.image-card ion-toolbar.buttons{--padding-start: 4px;--padding-end: 4px;--ion-color-base: var(--ion-color-light) !important;position:absolute;top:100%;transition:transform .2s ease-in-out}.image-card:hover ion-toolbar.buttons,.image-card ion-toolbar.buttons.focused{transform:translateY(var(--top-offset))}.image-card-button{height:calc(100% - var(--image-margin-safe-area, 0px));max-height:max(min(30vh,200px),var(--img-max-height, 0px));transition:.2s ease-in-out;max-width:250px}.image-card-button ion-card-content{height:100%}.image-card-button .icon-container{height:auto;position:relative;top:calc(50% - 75px);display:flex;align-items:center;justify-content:center}.image-card-button ion-icon:first-of-type{font-size:150px;height:150px;position:relative;top:0}.image-card-button ion-icon.icon-secondary{font-size:50px;position:absolute;top:0;left:max(min(50% + 25px,100% - 50px),0px)}.image-card-button ion-button{float:right}.image-card-button:hover{--ion-color-base: var(--ion-color-shade) !important}.image-card-button:hover ion-icon{--ion-color-base: var(--ion-color-shade) !important}.backdrop{height:100vh;width:100vw;background:#000;position:absolute;z-index:10}.zoom-modal{-webkit-user-select:none;user-select:none}.zoom-modal .top-left{z-index:14;position:absolute;display:inline-grid;left:var(--ion-padding-start, 8px);top:var(--ion-padding-start, 8px)}.zoom-modal .top-right{z-index:14;position:absolute;display:inline-grid;right:var(--ion-padding-start, 8px);top:var(--ion-padding-start, 8px)}.zoom-modal .side-buttons{--side-buttons-width: 120px;--side-buttons-margin: calc(var(--side-buttons-width) / 3);z-index:13;position:absolute;top:0;bottom:0;width:var(--side-buttons-width)}.zoom-modal .side-buttons ion-icon{top:50%;color:#fff;font-size:2.5rem;position:absolute;opacity:0;transition-duration:.15s;transition-timing-function:ease-in}.zoom-modal .side-buttons:hover{cursor:pointer}.zoom-modal .side-buttons:hover ion-icon{opacity:1}.zoom-modal .side-buttons.prev{left:0}.zoom-modal .side-buttons.prev ion-icon{left:var(--side-buttons-margin)}.zoom-modal .side-buttons.next{right:0}.zoom-modal .side-buttons.next ion-icon{right:var(--side-buttons-margin)}.zoom-modal swiper-container{height:100%;background:#000}.zoom-modal ion-fab-button .icon-secondary{top:11px;left:6px;height:14px}\n"] }]
27354
+ args: [{ selector: 'app-image-gallery', animations: [fadeInAnimation, fadeInOutAnimation], changeDetection: ChangeDetectionStrategy.OnPush, template: "<ion-toolbar color=\"light\" *ngIf=\"showToolbar\">\r\n <ng-content select=\"ion-buttons[slot=start]\"></ng-content>\r\n\r\n <!-- Add -->\r\n @if (!readOnly && showAddToolbarButton && enabled) {\r\n <button mat-icon-button [title]=\"'COMMON.BTN_ADD' | translate\" (click)=\"add()\">\r\n <mat-icon>add</mat-icon>\r\n </button>\r\n }\r\n\r\n <ng-content select=\"ion-buttons[slot=end]\"></ng-content>\r\n\r\n <ion-buttons slot=\"end\">\r\n <!-- Toggle view mode -->\r\n <ion-segment (ionChange)=\"toggleViewMode($event)\" color=\"accent\" [value]=\"_colSize\">\r\n <ion-segment-button [value]=\"4\">\r\n <mat-icon>view_module</mat-icon>\r\n </ion-segment-button>\r\n <ion-segment-button [value]=\"12\">\r\n <mat-icon>view_list</mat-icon>\r\n </ion-segment-button>\r\n </ion-segment>\r\n </ion-buttons>\r\n</ion-toolbar>\r\n\r\n<div class=\"gallery-container ion-padding-bottom {{ this.mode }}\">\r\n <div *ngIf=\"mobile && zoomActive\" class=\"backdrop\" [style.opacity]=\"zoomScale\"></div>\r\n\r\n <ion-grid class=\"ion-no-padding\">\r\n <ion-row>\r\n <ion-col *rxFor=\"let row of _data$; index as index; trackBy: trackByFn\" [size]=\"_colSize\">\r\n @let image = row | propertyGet: 'currentData';\r\n @if (cardTemplate) {\r\n <ng-container\r\n *ngTemplateOutlet=\"cardTemplate; context: { $implicit: row, mode: mode, image: image }\"\r\n ></ng-container>\r\n } @else {\r\n <ion-card\r\n #card\r\n class=\"image-card\"\r\n [class.zoom-hover]=\"!mobile\"\r\n [color]=\"cardColor\"\r\n (click)=\"clickRow(row, index)\"\r\n tappable\r\n @fadeInAnimation\r\n >\r\n <figure class=\"card-thumbnail\">\r\n @if (image.url) {\r\n <ion-img [src]=\"image.url | appendQueryParams: getImageSizeQueryParams()\" />\r\n } @else {\r\n <ion-img [src]=\"image.dataUrl\" />\r\n }\r\n </figure>\r\n\r\n <!-- toolbar for title (when not hover) -->\r\n @if (showTitle && image.title) {\r\n <ion-toolbar color=\"transparent\" class=\"title\">\r\n <ion-label class=\"card-title\">{{ image.title }}</ion-label>\r\n </ion-toolbar>\r\n }\r\n\r\n <!-- action toolbar shown when hover image -->\r\n @if (!readOnly && !mobile && showCardToolbar) {\r\n <ion-toolbar #cardToolbar color=\"light\" class=\"buttons\">\r\n <!-- edit title button -->\r\n @if (showTitle) {\r\n <button\r\n mat-button\r\n slot=\"start\"\r\n [disabled]=\"disabled\"\r\n (click)=\"editTitle($event, row, cardToolbar)\"\r\n (focusin)=\"focusCardToolbar(cardToolbar)\"\r\n >\r\n <mat-icon>edit</mat-icon>\r\n <mat-label>\r\n <span *ngIf=\"row.currentData.title | isNotNilOrBlank; else editLabel\" translate>\r\n IMAGE.GALLERY.BTN_EDIT_TITLE\r\n </span>\r\n <ng-template #editLabel>\r\n <span translate>IMAGE.GALLERY.BTN_ADD_TITLE</span>\r\n </ng-template>\r\n </mat-label>\r\n </button>\r\n }\r\n\r\n <div class=\"flex-spacer\"></div>\r\n\r\n <!-- delete button -->\r\n <button\r\n mat-icon-button\r\n slot=\"end\"\r\n class=\"ion-float-end\"\r\n [title]=\"'COMMON.BTN_DELETE' | translate\"\r\n [disabled]=\"disabled\"\r\n (click)=\"delete($event, row)\"\r\n >\r\n <mat-icon>delete</mat-icon>\r\n </button>\r\n </ion-toolbar>\r\n }\r\n </ion-card>\r\n }\r\n </ion-col>\r\n\r\n <!-- add button -->\r\n @if ((showAddTextButton || showAddCardButton) && !readOnly) {\r\n <ion-col [size]=\"_colSize\" @fadeInAnimation>\r\n @if (showAddTextButton) {\r\n <ion-button (click)=\"add($event)\" [disabled]=\"disabled\" [color]=\"addButtonColor\">\r\n <mat-label translate>{{ addButtonText }}</mat-label>\r\n <ion-icon slot=\"end\" name=\"camera\"></ion-icon>\r\n </ion-button>\r\n } @else if (showAddCardButton) {\r\n <ion-card\r\n class=\"image-card-button\"\r\n color=\"light\"\r\n (click)=\"add($event)\"\r\n [disabled]=\"disabled\"\r\n [title]=\"addButtonText\"\r\n tappable\r\n >\r\n <ion-card-content>\r\n <div class=\"icon-container\">\r\n <ion-icon name=\"camera\" [color]=\"addButtonColor\"></ion-icon>\r\n <ion-icon name=\"add\" [color]=\"addButtonColor\" class=\"icon-secondary\"></ion-icon>\r\n </div>\r\n </ion-card-content>\r\n </ion-card>\r\n }\r\n </ion-col>\r\n }\r\n </ion-row>\r\n </ion-grid>\r\n</div>\r\n\r\n<!-- FAB button: add -->\r\n<ion-fab\r\n slot=\"fixed\"\r\n vertical=\"bottom\"\r\n horizontal=\"end\"\r\n *ngIf=\"showFabButton && !readOnly\"\r\n [class.cdk-visually-hidden]=\"disabled\"\r\n @fadeInOutAnimation\r\n>\r\n <ion-fab-button color=\"tertiary\" (click)=\"add($event)\">\r\n <ion-icon name=\"camera\"></ion-icon>\r\n <ion-icon name=\"add\" class=\"icon-secondary\" style=\"left: 33px; top: 9px; font-size: 20px\"></ion-icon>\r\n </ion-fab-button>\r\n</ion-fab>\r\n\r\n<!-- Zoom modal -->\r\n<ion-modal #zoomModal class=\"stack-modal zoom-modal\" [class.modal-fullscreen]=\"mobile\" [class.modal-large]=\"!mobile\">\r\n <ng-template>\r\n <ion-content class=\"ion-no-padding ion-no-margin\">\r\n @let count = rows?.length || 0;\r\n <!-- Counter -->\r\n <div class=\"top-left\">\r\n <ion-label color=\"light\">{{ activeSlideIndex + 1 }} / {{ count }}</ion-label>\r\n </div>\r\n\r\n <!-- zoom button -->\r\n <div class=\"top-right\">\r\n @if (!mobile) {\r\n <ion-fab-button size=\"small\" (click)=\"zoom(modalSwiper, true)\" color=\"light\">\r\n <ion-icon name=\"search\"></ion-icon>\r\n <ion-icon class=\"icon-secondary\" name=\"add\"></ion-icon>\r\n </ion-fab-button>\r\n <ion-fab-button size=\"small\" (click)=\"zoom(modalSwiper, false)\" color=\"light\">\r\n <ion-icon name=\"search\"></ion-icon>\r\n <ion-icon class=\"icon-secondary\" name=\"remove\"></ion-icon>\r\n </ion-fab-button>\r\n }\r\n </div>\r\n\r\n <!-- navigation side buttons next/back -->\r\n <ng-container *ngIf=\"!mobile && (rows | isArrayLength: { greaterThan: 1 })\">\r\n <div class=\"side-buttons prev\" (click)=\"slidePrev(modalSwiper)\">\r\n <ion-icon name=\"chevron-back\"></ion-icon>\r\n </div>\r\n <div class=\"side-buttons next\" (click)=\"slideNext(modalSwiper)\">\r\n <ion-icon name=\"chevron-forward\"></ion-icon>\r\n </div>\r\n </ng-container>\r\n\r\n <!-- image slides -->\r\n <swiper-container\r\n #modalSwiper\r\n [modules]=\"swiperModules\"\r\n [zoom]=\"true\"\r\n (swiperslidechange)=\"onSlideChange(modalSwiper)\"\r\n (swiperinit)=\"initModalSlides(modalSwiper)\"\r\n >\r\n @for (row of rows; track row.id; let last = $last) {\r\n <swiper-slide>\r\n @let image = row | propertyGet: 'currentData';\r\n <div class=\"swiper-zoom-container\">\r\n @if (image.url) {\r\n <ion-img [src]=\"image.url | appendQueryParams: getImageSizeQueryParams('modal')\" />\r\n } @else {\r\n <img [src]=\"image.dataUrl\" [alt]=\"image.title\" />\r\n }\r\n </div>\r\n </swiper-slide>\r\n }\r\n </swiper-container>\r\n </ion-content>\r\n\r\n <ion-footer>\r\n <ion-toolbar color=\"light\">\r\n <ion-row>\r\n <ion-col size=\"4\" class=\"ion-text-start\">\r\n <ion-button\r\n *ngIf=\"!readOnly\"\r\n (click)=\"deleteFromModal($event, modalSwiper)\"\r\n [disabled]=\"disabled\"\r\n fill=\"clear\"\r\n color=\"danger\"\r\n >\r\n <mat-icon slot=\"start\">delete</mat-icon>\r\n {{ 'COMMON.BTN_DELETE' | translate }}\r\n </ion-button>\r\n </ion-col>\r\n <ion-col size=\"4\"></ion-col>\r\n <ion-col size=\"4\" class=\"ion-text-end\">\r\n <ion-button (click)=\"zoomModal.dismiss()\" color=\"tertiary\" fill=\"clear\" *ngIf=\"mobile; else desktop\">\r\n <ion-icon slot=\"start\" name=\"close\"></ion-icon>\r\n {{ 'COMMON.BTN_CLOSE' | translate }}\r\n </ion-button>\r\n <ng-template #desktop>\r\n <ion-button (click)=\"zoomModal.dismiss()\" color=\"tertiary\">\r\n {{ 'COMMON.BTN_CLOSE' | translate }}\r\n </ion-button>\r\n </ng-template>\r\n </ion-col>\r\n </ion-row>\r\n </ion-toolbar>\r\n </ion-footer>\r\n </ng-template>\r\n</ion-modal>\r\n\r\n<ion-popover #titlePopover>\r\n <ng-template>\r\n <ion-content class=\"ion-padding\" cdkTrapFocus [cdkTrapFocusAutoCapture]=\"true\">\r\n <form [formGroup]=\"_titleForm\">\r\n <mat-form-field floatLabel=\"auto\">\r\n <mat-label translate>IMAGE.GALLERY.TITLE</mat-label>\r\n <input\r\n matInput\r\n formControlName=\"title\"\r\n [readonly]=\"disabled\"\r\n [appAutofocus]=\"_titleAutofocus\"\r\n (keydown.control.enter)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\r\n />\r\n </mat-form-field>\r\n </form>\r\n </ion-content>\r\n\r\n <ion-footer>\r\n <ion-toolbar>\r\n <ion-row class=\"ion-no-padding\" nowrap>\r\n <ion-col></ion-col>\r\n\r\n <ion-col size=\"auto\">\r\n <ion-button fill=\"clear\" color=\"dark\" (click)=\"titlePopover.dismiss(null, 'CANCEL')\">\r\n <ion-label translate>COMMON.BTN_CANCEL</ion-label>\r\n </ion-button>\r\n <ion-button\r\n [fill]=\"disabled ? 'clear' : 'solid'\"\r\n (click)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\r\n (keyup.enter)=\"titlePopover.dismiss(_titleForm.controls.title.value)\"\r\n color=\"tertiary\"\r\n [disabled]=\"disabled\"\r\n [title]=\"'COMMON.BTN_VALIDATE_WITH_SHORTCUT_HELP' | translate\"\r\n >\r\n <ion-label translate>COMMON.BTN_VALIDATE</ion-label>\r\n </ion-button>\r\n </ion-col>\r\n </ion-row>\r\n </ion-toolbar>\r\n </ion-footer>\r\n </ng-template>\r\n</ion-popover>\r\n", styles: [":host{--image-margin-inline: 10px;--image-margin-safe-area: var(--image-margin-inline, 0px) * 2 - 3px;--segment-max-width: 150px}ion-toolbar ion-segment{max-width:var(--segment-max-width)}mat-toolbar,.mat-toolbar-single-row{padding:0;height:42px}ion-card{margin-left:unset;margin-right:unset;margin-inline:var(--image-margin-inline, 10px)}.image-slide{overflow:visible}.image-card{background-color:var(--ion-color-base);z-index:9;--img-scale: 1}.image-card .card-thumbnail{position:relative;overflow:hidden;display:flex;justify-content:center;align-items:center;margin:0;padding:0;width:100%;height:100%;max-height:var(--img-max-height, calc(100% - var(--image-margin-safe-area, 0px)))}.image-card .card-thumbnail>ion-img{min-height:100%;height:100%;object-fit:cover;object-position:center;transition:scale .2s ease-in-out;scale:var(--img-scale)}.image-card .card-thumbnail>ion-img img{max-height:var(--img-max-height)}.image-card.zoom-hover:hover{--img-scale: 1.2}.image-card ion-toolbar{--top-offset: calc(-1 * var(--ion-toolbar-height));position:absolute}.image-card ion-toolbar.title{--padding-start: 16px;--padding-end: 16px;--ion-color-base: rgba(0, 0, 0, .45) !important;position:absolute;top:calc(100% + var(--top-offset));transition:opacity .2s ease-in-out}.image-card ion-toolbar.title ion-label{color:#fff}.image-card ion-toolbar.buttons{--padding-start: 4px;--padding-end: 4px;--ion-color-base: var(--ion-color-light) !important;position:absolute;top:100%;transition:transform .2s ease-in-out}.image-card:hover ion-toolbar.buttons,.image-card ion-toolbar.buttons.focused{transform:translateY(var(--top-offset))}.image-card-button{height:calc(100% - var(--image-margin-safe-area, 0px));max-height:max(min(30vh,200px),var(--img-max-height, 0px));transition:.2s ease-in-out;max-width:250px}.image-card-button ion-card-content{height:100%}.image-card-button .icon-container{height:auto;position:relative;top:calc(50% - 75px);display:flex;align-items:center;justify-content:center}.image-card-button ion-icon:first-of-type{font-size:150px;height:150px;position:relative;top:0}.image-card-button ion-icon.icon-secondary{font-size:50px;position:absolute;top:0;left:max(min(50% + 25px,100% - 50px),0px)}.image-card-button ion-button{float:right}.image-card-button:hover{--ion-color-base: var(--ion-color-shade) !important}.image-card-button:hover ion-icon{--ion-color-base: var(--ion-color-shade) !important}.backdrop{height:100vh;width:100vw;background:#000;position:absolute;z-index:10}.zoom-modal{-webkit-user-select:none;user-select:none}.zoom-modal .top-left{z-index:14;position:absolute;display:inline-grid;left:var(--ion-padding-start, 8px);top:var(--ion-padding-start, 8px)}.zoom-modal .top-right{z-index:14;position:absolute;display:inline-grid;right:var(--ion-padding-start, 8px);top:var(--ion-padding-start, 8px)}.zoom-modal .side-buttons{--side-buttons-width: 120px;--side-buttons-margin: calc(var(--side-buttons-width) / 3);z-index:13;position:absolute;top:0;bottom:0;width:var(--side-buttons-width)}.zoom-modal .side-buttons ion-icon{top:50%;color:#fff;font-size:2.5rem;position:absolute;opacity:0;transition-duration:.15s;transition-timing-function:ease-in}.zoom-modal .side-buttons:hover{cursor:pointer}.zoom-modal .side-buttons:hover ion-icon{opacity:1}.zoom-modal .side-buttons.prev{left:0}.zoom-modal .side-buttons.prev ion-icon{left:var(--side-buttons-margin)}.zoom-modal .side-buttons.next{right:0}.zoom-modal .side-buttons.next ion-icon{right:var(--side-buttons-margin)}.zoom-modal swiper-container{height:100%;background:#000}.zoom-modal ion-fab-button .icon-secondary{top:11px;left:6px;height:14px}\n"] }]
27355
27355
  }], ctorParameters: () => [{ type: ImageService }, { type: i2$1.Platform }, { type: i2$1.AlertController }, { type: i1$1.TranslateService }, { type: i0.ChangeDetectorRef }, { type: Environment, decorators: [{
27356
27356
  type: Optional
27357
27357
  }, {
@@ -29606,22 +29606,22 @@ class AppMarkdownContent {
29606
29606
  await this.printService.printElement(this.element.nativeElement, {
29607
29607
  id: this._printId,
29608
29608
  // Print as portrait, by default
29609
- style: `@media print {
29610
- @page {
29611
- size: portrait;
29612
- margin: 1.1cm;
29613
- }
29614
- markdown hr {
29615
- page-break-before: always;
29616
- border: none;
29617
- margin: 0;
29618
- padding: 0;
29619
- }
29620
- markdown img {
29621
- max-width: 100%;
29622
- height: auto;
29623
- page-break-inside: avoid;
29624
- }
29609
+ style: `@media print {
29610
+ @page {
29611
+ size: portrait;
29612
+ margin: 1.1cm;
29613
+ }
29614
+ markdown hr {
29615
+ page-break-before: always;
29616
+ border: none;
29617
+ margin: 0;
29618
+ padding: 0;
29619
+ }
29620
+ markdown img {
29621
+ max-width: 100%;
29622
+ height: auto;
29623
+ page-break-inside: avoid;
29624
+ }
29625
29625
  }`,
29626
29626
  });
29627
29627
  }
@@ -35216,11 +35216,11 @@ class FeedsComponent {
35216
35216
  }
35217
35217
  }
35218
35218
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: FeedsComponent, deps: [{ token: LocalSettingsService }, { token: ENVIRONMENT }, { token: APP_FEED_SERVICE, optional: true }, { token: AccountService }, { token: i2$1.AlertController }], target: i0.ɵɵFactoryTarget.Component });
35219
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.13", type: FeedsComponent, selector: "app-feed", inputs: { debug: "debug", mobile: "mobile", showHeader: "showHeader", showReadMoreButton: "showReadMoreButton", headerColor: "headerColor", cardColor: "cardColor", shape: "shape", class: "class", itemId: "itemId", filterItem: "filterItem", feeds: "feeds", urls: "urls", maxAgeInMonths: "maxAgeInMonths", maxContentLength: "maxContentLength" }, outputs: { editItem: "editItem", deleteItem: "deleteItem" }, host: { properties: { "class": "this.hostClass" } }, providers: [RxState], viewQueries: [{ propertyName: "modal", first: true, predicate: ["modal"], descendants: true }], ngImport: i0, template: "<!-- debug -->\n@if (debug) {\n <app-debug [title]=\"'Feed'\">\n <p>\n hasFeeds?: {{ hasFeeds$ | async }}\n <br />\n urls: {{ urls$ | async | json }}\n <br />\n shape: {{ shape }}\n </p>\n </app-debug>\n}\n\n@let feeds = feeds$ | async;\n@let userId = userId$ | async;\n\n@if (feeds | isNotEmptyArray) {\n <!-- top header -->\n @if (showHeader && (feeds | arrayFirst); as feed) {\n <ion-item lines=\"none\" [color]=\"headerColor\" class=\"feed-header shape-{{ shape }}\">\n <ion-icon slot=\"start\" name=\"megaphone\"></ion-icon>\n <ion-label>\n <b>{{ feed.title || ('SOCIAL.FEED.NEWS' | translate) }}</b>\n </ion-label>\n <ion-button slot=\"end\" fill=\"clear\" (click)=\"openFeedHome()\" shape=\"\">\n <ion-label translate>SOCIAL.FEED.SHOW_ALL_FEED</ion-label>\n <ion-icon slot=\"end\" name=\"chevron-forward-outline\"></ion-icon>\n </ion-button>\n </ion-item>\n }\n\n <div class=\"feed-content shape-{{ shape }} ion-no-padding\" [class.has-header]=\"showHeader\">\n <!-- feeds -->\n @for (feed of feeds; track feed.feed_url; let firstFeed = $first; let lastFeed = $last) {\n <!-- items -->\n @for (item of feed.items | arrayFilter: filterItem; track item.id; let firstItem = $first; let lastItem = $last) {\n <ion-card\n [class.first]=\"firstFeed && firstItem\"\n [class.last]=\"lastFeed && lastItem\"\n [color]=\"cardColor !== 'light-transparent' ? cardColor : undefined\"\n class=\"feed-item-card\"\n >\n <ion-card-header>\n <ion-card-subtitle style=\"vertical-align: middle\">\n <!-- Authors -->\n @for (author of item.authors || feed.authors; track author) {\n @if (author.name || author.avatar) {\n <ion-chip (click)=\"openUrl(author.url)\" tappable>\n @if (author.avatar) {\n <ion-avatar>\n <ion-img [src]=\"author.avatar\" [alt]=\"author.name\"></ion-img>\n </ion-avatar>\n }\n @if (author.name) {\n <ion-label class=\"author\">{{ author.name }}</ion-label>\n }\n </ion-chip>\n }\n }\n <ion-note class=\"ion-float-end\">\n <small>{{ item.date_published | dateFromNow }}</small>\n </ion-note>\n </ion-card-subtitle>\n\n <!-- title -->\n <ion-card-title (click)=\"openFeedItem(item, feed)\" tappable>{{ item?.title }}</ion-card-title>\n\n <!-- tags -->\n @let tags = item | map: getTags;\n @if (tags | isNotEmptyArray) {\n <ion-text class=\"tags\">\n @for (tag of tags; track tag; let last = $last) {\n <a (click)=\"openTag(feed, tag)\" tappable>\n <ion-text>#{{ tag }}</ion-text>\n </a>\n @if (!last) {\n &nbsp;\n }\n }\n </ion-text>\n }\n </ion-card-header>\n\n <!-- Feed content -->\n <ion-card-content>\n <ion-text [feed]=\"item.url || feed.feed_url\">\n @if (item.content_html) {\n <p [innerHTML]=\"item.content_html\"></p>\n } @else if (item.content_text) {\n <p>\n <markdown [data]=\"item.content_text\" emoji></markdown>\n </p>\n }\n </ion-text>\n </ion-card-content>\n\n @let editable = canEditItem(item, userId, feed);\n @if (editable || showReadMoreButton) {\n @if (editable) {\n\n <!-- Delete button (visible hover)-->\n <button\n mat-icon-button\n (click)=\"onDeleteItem($event, item)\"\n class=\"visible-hover ion-float-start\"\n [title]=\"'COMMON.BTN_DELETE' | translate\"\n >\n <mat-icon>delete</mat-icon>\n </button>\n <!-- Edit button (visible hover) -->\n <ion-button\n (click)=\"onEditItem($event, item)\"\n class=\"visible-hover ion-float-start\" fill=\"clear\"\n >\n <mat-icon slot=\"start\">edit</mat-icon>\n<!-- <ion-icon name=\"pencil\" slot=\"start\"></ion-icon>-->\n <ion-label translate>COMMON.BTN_EDIT</ion-label>\n </ion-button>\n }\n @if (showReadMoreButton) {\n <ion-button (click)=\"openFeedItem(item, feed)\" class=\"ion-float-end\" fill=\"clear\">\n <ion-label>{{ (item.truncated ? 'SOCIAL.FEED.READ_MORE' : 'COMMON.BTN_SHOW') | translate }}</ion-label>\n <ion-icon slot=\"end\" name=\"chevron-forward-outline\"></ion-icon>\n </ion-button>\n }\n }\n </ion-card>\n }\n }\n </div>\n}\n\n<!-- Details modal -->\n<ion-modal #modal [showBackdrop]=\"false\"\n class=\"stack-modal\" [class.modal-large]=\"!mobile\">\n <ng-template>\n <ion-header>\n <ion-toolbar color=\"secondary\">\n <ion-title>{{ 'SOCIAL.FEED.NEWS' | translate }}</ion-title>\n <ion-buttons slot=\"end\">\n <ion-button (click)=\"modal.dismiss()\">\n <ion-icon slot=\"icon-only\" name=\"close\"></ion-icon>\n </ion-button>\n </ion-buttons>\n </ion-toolbar>\n </ion-header>\n <ion-content>\n <div class=\"ion-padding\">\n <app-feed\n [urls]=\"urls\"\n [showHeader]=\"false\"\n [showReadMoreButton]=\"false\"\n [maxContentLength]=\"-1\"\n [maxAgeInMonths]=\"-1\"\n [itemId]=\"modalItemId\"\n cardColor=\"light\"\n [debug]=\"debug\"\n ></app-feed>\n </div>\n </ion-content>\n </ng-template>\n</ion-modal>\n", styles: [":host{display:block;height:calc(100% - 10px);max-height:fit-content;overflow:hidden;--feed-header-height: 48px;-webkit-box-shadow:0 3px 1px -2px rgba(0,0,0,.2),0 2px 2px 0 rgba(0,0,0,.14),0 1px 5px 0 rgba(0,0,0,.12);box-shadow:0 3px 1px -2px rgba(0,0,0,.2),0 2px 2px rgba(0,0,0,.14),0 1px 5px rgba(0,0,0,.12);-webkit-margin-start:10px;margin-inline-start:10px;-webkit-margin-end:10px;margin-inline-end:10px;margin-top:0;margin-bottom:10px;--feed-border-radius: 4px;border-radius:var(--feed-border-radius);--ion-card-background: rgba(var(--ion-background-color-rgb), .6)}:host.shape-round{--feed-border-radius: 12px}ion-button{text-transform:unset;--color: rgba(var(--ion-color-contrast-rgb), .7)}ion-item.feed-header{height:var(--feed-header-height);margin:0;backdrop-filter:blur(4px);-webkit-backdrop-filter:blur(4px);border-radius:var(--feed-border-radius) var(--feed-border-radius) 0 0}ion-item.feed-header ion-icon[slot=start]{-webkit-margin-end:8px;margin-inline-end:8px}.feed-content{height:auto;overflow-y:auto;--margin-bottom: 8px}.feed-content.has-header{height:calc(100% - var(--feed-header-height, 0))}.feed-content ion-card.feed-item-card{--top-radius: 4px;--bottom-radius: 4px;backdrop-filter:blur(4px);-webkit-backdrop-filter:blur(4px);margin:0 0 var(--margin-bottom) 0;border-radius:var(--top-radius) var(--top-radius) var(--bottom-radius) var(--bottom-radius);--ion-card-color-contrast-rgb: var(--ion-color-contrast-rgb, var(--ion-color-dark-rgb, 0, 0, 0));--color: rgba(var(--ion-card-color-contrast-rgb), .87)}.feed-content ion-card.feed-item-card.first{--top-radius: 0}.feed-content ion-card.feed-item-card.last{--margin-bottom: 0;--bottom-radius: 0}.feed-content ion-card.feed-item-card ion-card-header ion-card-title{--color: rgba(var(--ion-card-color-contrast-rgb), .87)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip{--background: transparent;--border-color: transparent;--border-width: 0}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip ion-avatar{--color: rgba(var(--ion-card-color-contrast-rgb), .6);border:1px solid var(--color)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip ion-label{--color: rgba(var(--ion-card-color-contrast-rgb), .8);color:var(--color)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-note{--color: rgba(var(--ion-card-color-contrast-rgb), .6);color:var(--color)}.feed-content ion-card.feed-item-card ion-card-header .tags{display:inline}.feed-content ion-card.feed-item-card ion-card-header .tags a{color:rgba(var(--ion-card-color-contrast-rgb),.6)!important}.feed-content ion-card.feed-item-card ion-card-content ion-text ::ng-deep img{max-width:100%;height:auto!important}.feed-content ion-card.feed-item-card .visible-hover{opacity:0;transition:opacity .2s ease-in-out}.feed-content ion-card.feed-item-card:hover .visible-hover{opacity:1}\n"], dependencies: [{ kind: "component", type: i2$1.IonAvatar, selector: "ion-avatar" }, { kind: "component", type: i2$1.IonButton, selector: "ion-button", inputs: ["buttonType", "color", "disabled", "download", "expand", "fill", "form", "href", "mode", "rel", "routerAnimation", "routerDirection", "shape", "size", "strong", "target", "type"] }, { kind: "component", type: i2$1.IonButtons, selector: "ion-buttons", inputs: ["collapse"] }, { kind: "component", type: i2$1.IonCard, selector: "ion-card", inputs: ["button", "color", "disabled", "download", "href", "mode", "rel", "routerAnimation", "routerDirection", "target", "type"] }, { kind: "component", type: i2$1.IonCardContent, selector: "ion-card-content", inputs: ["mode"] }, { kind: "component", type: i2$1.IonCardHeader, selector: "ion-card-header", inputs: ["color", "mode", "translucent"] }, { kind: "component", type: i2$1.IonCardSubtitle, selector: "ion-card-subtitle", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonCardTitle, selector: "ion-card-title", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonChip, selector: "ion-chip", inputs: ["color", "disabled", "mode", "outline"] }, { kind: "component", type: i2$1.IonContent, selector: "ion-content", inputs: ["color", "forceOverscroll", "fullscreen", "scrollEvents", "scrollX", "scrollY"] }, { kind: "component", type: i2$1.IonHeader, selector: "ion-header", inputs: ["collapse", "mode", "translucent"] }, { kind: "component", type: i2$1.IonIcon, selector: "ion-icon", inputs: ["color", "flipRtl", "icon", "ios", "lazy", "md", "mode", "name", "sanitize", "size", "src"] }, { kind: "component", type: i2$1.IonImg, selector: "ion-img", inputs: ["alt", "src"] }, { kind: "component", type: i2$1.IonItem, selector: "ion-item", inputs: ["button", "color", "counter", "counterFormatter", "detail", "detailIcon", "disabled", "download", "fill", "href", "lines", "mode", "rel", "routerAnimation", "routerDirection", "shape", "target", "type"] }, { kind: "component", type: i2$1.IonLabel, selector: "ion-label", inputs: ["color", "mode", "position"] }, { kind: "component", type: i2$1.IonNote, selector: "ion-note", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonText, selector: "ion-text", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonTitle, selector: "ion-title", inputs: ["color", "size"] }, { kind: "component", type: i2$1.IonToolbar, selector: "ion-toolbar", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonModal, selector: "ion-modal" }, { kind: "directive", type: i1$1.TranslateDirective, selector: "[translate],[ngx-translate]", inputs: ["translate", "translateParams"] }, { kind: "component", type: i4$2.MarkdownComponent, selector: "markdown, [markdown]", inputs: ["data", "src", "disableSanitizer", "inline", "clipboard", "clipboardButtonComponent", "clipboardButtonTemplate", "emoji", "katex", "katexOptions", "mermaid", "mermaidOptions", "lineHighlight", "line", "lineOffset", "lineNumbers", "start", "commandLine", "filterOutput", "host", "prompt", "output", "user"], outputs: ["error", "load", "ready"] }, { kind: "component", type: i6$1.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i9.MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "component", type: DebugComponent, selector: "app-debug", inputs: ["titlePrefix", "title", "enable", "expanded"] }, { kind: "directive", type: MarkdownDirective, selector: "markdown,[markdown]" }, { kind: "component", type: FeedsComponent, selector: "app-feed", inputs: ["debug", "mobile", "showHeader", "showReadMoreButton", "headerColor", "cardColor", "shape", "class", "itemId", "filterItem", "feeds", "urls", "maxAgeInMonths", "maxContentLength"], outputs: ["editItem", "deleteItem"] }, { kind: "directive", type: FeedDirective, selector: "feed,[feed]", inputs: ["feed"] }, { kind: "pipe", type: i3$1.AsyncPipe, name: "async" }, { kind: "pipe", type: i3$1.JsonPipe, name: "json" }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }, { kind: "pipe", type: DateFromNowPipe, name: "dateFromNow" }, { kind: "pipe", type: NotEmptyArrayPipe, name: "isNotEmptyArray" }, { kind: "pipe", type: ArrayFirstPipe, name: "arrayFirst" }, { kind: "pipe", type: ArrayFilterPipe, name: "arrayFilter" }, { kind: "pipe", type: MapPipe, name: "map" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
35219
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.13", type: FeedsComponent, selector: "app-feed", inputs: { debug: "debug", mobile: "mobile", showHeader: "showHeader", showReadMoreButton: "showReadMoreButton", headerColor: "headerColor", cardColor: "cardColor", shape: "shape", class: "class", itemId: "itemId", filterItem: "filterItem", feeds: "feeds", urls: "urls", maxAgeInMonths: "maxAgeInMonths", maxContentLength: "maxContentLength" }, outputs: { editItem: "editItem", deleteItem: "deleteItem" }, host: { properties: { "class": "this.hostClass" } }, providers: [RxState], viewQueries: [{ propertyName: "modal", first: true, predicate: ["modal"], descendants: true }], ngImport: i0, template: "<!-- debug -->\n@if (debug) {\n <app-debug [title]=\"'Feed'\">\n <p>\n hasFeeds?: {{ hasFeeds$ | async }}\n <br />\n urls: {{ urls$ | async | json }}\n <br />\n shape: {{ shape }}\n </p>\n </app-debug>\n}\n\n@let feeds = feeds$ | async;\n@let userId = userId$ | async;\n\n@if (feeds | isNotEmptyArray) {\n <!-- top header -->\n @if (showHeader && (feeds | arrayFirst); as feed) {\n <ion-item lines=\"none\" [color]=\"headerColor\" class=\"feed-header shape-{{ shape }}\">\n <ion-icon slot=\"start\" name=\"megaphone\"></ion-icon>\n <ion-label>\n <b>{{ feed.title || ('SOCIAL.FEED.NEWS' | translate) }}</b>\n </ion-label>\n <ion-button slot=\"end\" fill=\"clear\" (click)=\"openFeedHome()\" shape=\"\">\n <ion-label translate>SOCIAL.FEED.SHOW_ALL_FEED</ion-label>\n <ion-icon slot=\"end\" name=\"chevron-forward-outline\"></ion-icon>\n </ion-button>\n </ion-item>\n }\n\n <div class=\"feed-content shape-{{ shape }} ion-no-padding\" [class.has-header]=\"showHeader\">\n <!-- feeds -->\n @for (feed of feeds; track feed.feed_url; let firstFeed = $first; let lastFeed = $last) {\n <!-- items -->\n @for (item of feed.items | arrayFilter: filterItem; track item.id; let firstItem = $first; let lastItem = $last) {\n <ion-card\n [class.first]=\"firstFeed && firstItem\"\n [class.last]=\"lastFeed && lastItem\"\n [color]=\"cardColor !== 'light-transparent' ? cardColor : undefined\"\n class=\"feed-item-card\"\n >\n <ion-card-header>\n <ion-card-subtitle style=\"vertical-align: middle\">\n <!-- Authors -->\n @for (author of item.authors || feed.authors; track author) {\n @if (author.name || author.avatar) {\n <ion-chip (click)=\"openUrl(author.url)\" tappable>\n @if (author.avatar) {\n <ion-avatar>\n <ion-img [src]=\"author.avatar\" [alt]=\"author.name\"></ion-img>\n </ion-avatar>\n }\n @if (author.name) {\n <ion-label class=\"author\">{{ author.name }}</ion-label>\n }\n </ion-chip>\n }\n }\n <ion-note class=\"ion-float-end\">\n <small>{{ item.date_published | dateFromNow }}</small>\n </ion-note>\n </ion-card-subtitle>\n\n <!-- title -->\n <ion-card-title (click)=\"openFeedItem(item, feed)\" tappable>{{ item?.title }}</ion-card-title>\n\n <!-- tags -->\n @let tags = item | map: getTags;\n @if (tags | isNotEmptyArray) {\n <ion-text class=\"tags\">\n @for (tag of tags; track tag; let last = $last) {\n <a (click)=\"openTag(feed, tag)\" tappable>\n <ion-text>#{{ tag }}</ion-text>\n </a>\n @if (!last) {\n &nbsp;\n }\n }\n </ion-text>\n }\n </ion-card-header>\n\n <!-- Feed content -->\n <ion-card-content>\n <ion-text [feed]=\"item.url || feed.feed_url\">\n @if (item.content_html) {\n <p [innerHTML]=\"item.content_html\"></p>\n } @else if (item.content_text) {\n <p>\n <markdown [data]=\"item.content_text\" emoji></markdown>\n </p>\n }\n </ion-text>\n </ion-card-content>\n\n @let editable = canEditItem(item, userId, feed);\n @if (editable || showReadMoreButton) {\n @if (editable) {\n\n <!-- Delete button (visible hover)-->\n <button\n mat-icon-button\n (click)=\"onDeleteItem($event, item)\"\n class=\"visible-hover ion-float-start\"\n [title]=\"'COMMON.BTN_DELETE' | translate\"\n >\n <mat-icon>delete</mat-icon>\n </button>\n <!-- Edit button (visible hover) -->\n <ion-button\n (click)=\"onEditItem($event, item)\"\n class=\"visible-hover ion-float-start\" fill=\"clear\"\n >\n <mat-icon slot=\"start\">edit</mat-icon>\n<!-- <ion-icon name=\"pencil\" slot=\"start\"></ion-icon>-->\n <ion-label translate>COMMON.BTN_EDIT</ion-label>\n </ion-button>\n }\n @if (showReadMoreButton) {\n <ion-button (click)=\"openFeedItem(item, feed)\" class=\"ion-float-end\" fill=\"clear\">\n <ion-label>{{ (item.truncated ? 'SOCIAL.FEED.READ_MORE' : 'COMMON.BTN_SHOW') | translate }}</ion-label>\n <ion-icon slot=\"end\" name=\"chevron-forward-outline\"></ion-icon>\n </ion-button>\n }\n }\n </ion-card>\n }\n }\n </div>\n}\n\n<!-- Details modal -->\n<ion-modal #modal [showBackdrop]=\"false\"\n class=\"stack-modal\" [class.modal-large]=\"!mobile\">\n <ng-template>\n <ion-header>\n <ion-toolbar color=\"secondary\">\n <ion-title>{{ 'SOCIAL.FEED.NEWS' | translate }}</ion-title>\n <ion-buttons slot=\"end\">\n <ion-button (click)=\"modal.dismiss()\">\n <ion-icon slot=\"icon-only\" name=\"close\"></ion-icon>\n </ion-button>\n </ion-buttons>\n </ion-toolbar>\n </ion-header>\n <ion-content>\n <div class=\"ion-padding\">\n <app-feed\n [urls]=\"urls\"\n [showHeader]=\"false\"\n [showReadMoreButton]=\"false\"\n [maxContentLength]=\"-1\"\n [maxAgeInMonths]=\"-1\"\n [itemId]=\"modalItemId\"\n cardColor=\"light\"\n [debug]=\"debug\"\n ></app-feed>\n </div>\n </ion-content>\n </ng-template>\n</ion-modal>\n", styles: [":host{display:block;height:calc(100% - 10px);max-height:fit-content;overflow:hidden;--feed-header-height: 48px;-webkit-box-shadow:0 3px 1px -2px rgba(0,0,0,.2),0 2px 2px 0 rgba(0,0,0,.14),0 1px 5px 0 rgba(0,0,0,.12);box-shadow:0 3px 1px -2px #0003,0 2px 2px #00000024,0 1px 5px #0000001f;-webkit-margin-start:10px;margin-inline-start:10px;-webkit-margin-end:10px;margin-inline-end:10px;margin-top:0;margin-bottom:10px;--feed-border-radius: 4px;border-radius:var(--feed-border-radius);--ion-card-background: rgba(var(--ion-background-color-rgb), .6)}:host.shape-round{--feed-border-radius: 12px}ion-button{text-transform:unset;--color: rgba(var(--ion-color-contrast-rgb), .7)}ion-item.feed-header{height:var(--feed-header-height);margin:0;backdrop-filter:blur(4px);-webkit-backdrop-filter:blur(4px);border-radius:var(--feed-border-radius) var(--feed-border-radius) 0 0}ion-item.feed-header ion-icon[slot=start]{-webkit-margin-end:8px;margin-inline-end:8px}.feed-content{height:auto;overflow-y:auto;--margin-bottom: 8px}.feed-content.has-header{height:calc(100% - var(--feed-header-height, 0))}.feed-content ion-card.feed-item-card{--top-radius: 4px;--bottom-radius: 4px;backdrop-filter:blur(4px);-webkit-backdrop-filter:blur(4px);margin:0 0 var(--margin-bottom) 0;border-radius:var(--top-radius) var(--top-radius) var(--bottom-radius) var(--bottom-radius);--ion-card-color-contrast-rgb: var(--ion-color-contrast-rgb, var(--ion-color-dark-rgb, 0, 0, 0));--color: rgba(var(--ion-card-color-contrast-rgb), .87)}.feed-content ion-card.feed-item-card.first{--top-radius: 0}.feed-content ion-card.feed-item-card.last{--margin-bottom: 0;--bottom-radius: 0}.feed-content ion-card.feed-item-card ion-card-header ion-card-title{--color: rgba(var(--ion-card-color-contrast-rgb), .87)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip{--background: transparent;--border-color: transparent;--border-width: 0}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip ion-avatar{--color: rgba(var(--ion-card-color-contrast-rgb), .6);border:1px solid var(--color)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip ion-label{--color: rgba(var(--ion-card-color-contrast-rgb), .8);color:var(--color)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-note{--color: rgba(var(--ion-card-color-contrast-rgb), .6);color:var(--color)}.feed-content ion-card.feed-item-card ion-card-header .tags{display:inline}.feed-content ion-card.feed-item-card ion-card-header .tags a{color:rgba(var(--ion-card-color-contrast-rgb),.6)!important}.feed-content ion-card.feed-item-card ion-card-content ion-text ::ng-deep img{max-width:100%;height:auto!important}.feed-content ion-card.feed-item-card .visible-hover{opacity:0;transition:opacity .2s ease-in-out}.feed-content ion-card.feed-item-card:hover .visible-hover{opacity:1}\n"], dependencies: [{ kind: "component", type: i2$1.IonAvatar, selector: "ion-avatar" }, { kind: "component", type: i2$1.IonButton, selector: "ion-button", inputs: ["buttonType", "color", "disabled", "download", "expand", "fill", "form", "href", "mode", "rel", "routerAnimation", "routerDirection", "shape", "size", "strong", "target", "type"] }, { kind: "component", type: i2$1.IonButtons, selector: "ion-buttons", inputs: ["collapse"] }, { kind: "component", type: i2$1.IonCard, selector: "ion-card", inputs: ["button", "color", "disabled", "download", "href", "mode", "rel", "routerAnimation", "routerDirection", "target", "type"] }, { kind: "component", type: i2$1.IonCardContent, selector: "ion-card-content", inputs: ["mode"] }, { kind: "component", type: i2$1.IonCardHeader, selector: "ion-card-header", inputs: ["color", "mode", "translucent"] }, { kind: "component", type: i2$1.IonCardSubtitle, selector: "ion-card-subtitle", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonCardTitle, selector: "ion-card-title", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonChip, selector: "ion-chip", inputs: ["color", "disabled", "mode", "outline"] }, { kind: "component", type: i2$1.IonContent, selector: "ion-content", inputs: ["color", "forceOverscroll", "fullscreen", "scrollEvents", "scrollX", "scrollY"] }, { kind: "component", type: i2$1.IonHeader, selector: "ion-header", inputs: ["collapse", "mode", "translucent"] }, { kind: "component", type: i2$1.IonIcon, selector: "ion-icon", inputs: ["color", "flipRtl", "icon", "ios", "lazy", "md", "mode", "name", "sanitize", "size", "src"] }, { kind: "component", type: i2$1.IonImg, selector: "ion-img", inputs: ["alt", "src"] }, { kind: "component", type: i2$1.IonItem, selector: "ion-item", inputs: ["button", "color", "counter", "counterFormatter", "detail", "detailIcon", "disabled", "download", "fill", "href", "lines", "mode", "rel", "routerAnimation", "routerDirection", "shape", "target", "type"] }, { kind: "component", type: i2$1.IonLabel, selector: "ion-label", inputs: ["color", "mode", "position"] }, { kind: "component", type: i2$1.IonNote, selector: "ion-note", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonText, selector: "ion-text", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonTitle, selector: "ion-title", inputs: ["color", "size"] }, { kind: "component", type: i2$1.IonToolbar, selector: "ion-toolbar", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonModal, selector: "ion-modal" }, { kind: "directive", type: i1$1.TranslateDirective, selector: "[translate],[ngx-translate]", inputs: ["translate", "translateParams"] }, { kind: "component", type: i4$2.MarkdownComponent, selector: "markdown, [markdown]", inputs: ["data", "src", "disableSanitizer", "inline", "clipboard", "clipboardButtonComponent", "clipboardButtonTemplate", "emoji", "katex", "katexOptions", "mermaid", "mermaidOptions", "lineHighlight", "line", "lineOffset", "lineNumbers", "start", "commandLine", "filterOutput", "host", "prompt", "output", "user"], outputs: ["error", "load", "ready"] }, { kind: "component", type: i6$1.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i9.MatIconButton, selector: "button[mat-icon-button]", exportAs: ["matButton"] }, { kind: "component", type: DebugComponent, selector: "app-debug", inputs: ["titlePrefix", "title", "enable", "expanded"] }, { kind: "directive", type: MarkdownDirective, selector: "markdown,[markdown]" }, { kind: "component", type: FeedsComponent, selector: "app-feed", inputs: ["debug", "mobile", "showHeader", "showReadMoreButton", "headerColor", "cardColor", "shape", "class", "itemId", "filterItem", "feeds", "urls", "maxAgeInMonths", "maxContentLength"], outputs: ["editItem", "deleteItem"] }, { kind: "directive", type: FeedDirective, selector: "feed,[feed]", inputs: ["feed"] }, { kind: "pipe", type: i3$1.AsyncPipe, name: "async" }, { kind: "pipe", type: i3$1.JsonPipe, name: "json" }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }, { kind: "pipe", type: DateFromNowPipe, name: "dateFromNow" }, { kind: "pipe", type: NotEmptyArrayPipe, name: "isNotEmptyArray" }, { kind: "pipe", type: ArrayFirstPipe, name: "arrayFirst" }, { kind: "pipe", type: ArrayFilterPipe, name: "arrayFilter" }, { kind: "pipe", type: MapPipe, name: "map" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
35220
35220
  }
35221
35221
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: FeedsComponent, decorators: [{
35222
35222
  type: Component,
35223
- args: [{ selector: 'app-feed', providers: [RxState], changeDetection: ChangeDetectionStrategy.OnPush, template: "<!-- debug -->\n@if (debug) {\n <app-debug [title]=\"'Feed'\">\n <p>\n hasFeeds?: {{ hasFeeds$ | async }}\n <br />\n urls: {{ urls$ | async | json }}\n <br />\n shape: {{ shape }}\n </p>\n </app-debug>\n}\n\n@let feeds = feeds$ | async;\n@let userId = userId$ | async;\n\n@if (feeds | isNotEmptyArray) {\n <!-- top header -->\n @if (showHeader && (feeds | arrayFirst); as feed) {\n <ion-item lines=\"none\" [color]=\"headerColor\" class=\"feed-header shape-{{ shape }}\">\n <ion-icon slot=\"start\" name=\"megaphone\"></ion-icon>\n <ion-label>\n <b>{{ feed.title || ('SOCIAL.FEED.NEWS' | translate) }}</b>\n </ion-label>\n <ion-button slot=\"end\" fill=\"clear\" (click)=\"openFeedHome()\" shape=\"\">\n <ion-label translate>SOCIAL.FEED.SHOW_ALL_FEED</ion-label>\n <ion-icon slot=\"end\" name=\"chevron-forward-outline\"></ion-icon>\n </ion-button>\n </ion-item>\n }\n\n <div class=\"feed-content shape-{{ shape }} ion-no-padding\" [class.has-header]=\"showHeader\">\n <!-- feeds -->\n @for (feed of feeds; track feed.feed_url; let firstFeed = $first; let lastFeed = $last) {\n <!-- items -->\n @for (item of feed.items | arrayFilter: filterItem; track item.id; let firstItem = $first; let lastItem = $last) {\n <ion-card\n [class.first]=\"firstFeed && firstItem\"\n [class.last]=\"lastFeed && lastItem\"\n [color]=\"cardColor !== 'light-transparent' ? cardColor : undefined\"\n class=\"feed-item-card\"\n >\n <ion-card-header>\n <ion-card-subtitle style=\"vertical-align: middle\">\n <!-- Authors -->\n @for (author of item.authors || feed.authors; track author) {\n @if (author.name || author.avatar) {\n <ion-chip (click)=\"openUrl(author.url)\" tappable>\n @if (author.avatar) {\n <ion-avatar>\n <ion-img [src]=\"author.avatar\" [alt]=\"author.name\"></ion-img>\n </ion-avatar>\n }\n @if (author.name) {\n <ion-label class=\"author\">{{ author.name }}</ion-label>\n }\n </ion-chip>\n }\n }\n <ion-note class=\"ion-float-end\">\n <small>{{ item.date_published | dateFromNow }}</small>\n </ion-note>\n </ion-card-subtitle>\n\n <!-- title -->\n <ion-card-title (click)=\"openFeedItem(item, feed)\" tappable>{{ item?.title }}</ion-card-title>\n\n <!-- tags -->\n @let tags = item | map: getTags;\n @if (tags | isNotEmptyArray) {\n <ion-text class=\"tags\">\n @for (tag of tags; track tag; let last = $last) {\n <a (click)=\"openTag(feed, tag)\" tappable>\n <ion-text>#{{ tag }}</ion-text>\n </a>\n @if (!last) {\n &nbsp;\n }\n }\n </ion-text>\n }\n </ion-card-header>\n\n <!-- Feed content -->\n <ion-card-content>\n <ion-text [feed]=\"item.url || feed.feed_url\">\n @if (item.content_html) {\n <p [innerHTML]=\"item.content_html\"></p>\n } @else if (item.content_text) {\n <p>\n <markdown [data]=\"item.content_text\" emoji></markdown>\n </p>\n }\n </ion-text>\n </ion-card-content>\n\n @let editable = canEditItem(item, userId, feed);\n @if (editable || showReadMoreButton) {\n @if (editable) {\n\n <!-- Delete button (visible hover)-->\n <button\n mat-icon-button\n (click)=\"onDeleteItem($event, item)\"\n class=\"visible-hover ion-float-start\"\n [title]=\"'COMMON.BTN_DELETE' | translate\"\n >\n <mat-icon>delete</mat-icon>\n </button>\n <!-- Edit button (visible hover) -->\n <ion-button\n (click)=\"onEditItem($event, item)\"\n class=\"visible-hover ion-float-start\" fill=\"clear\"\n >\n <mat-icon slot=\"start\">edit</mat-icon>\n<!-- <ion-icon name=\"pencil\" slot=\"start\"></ion-icon>-->\n <ion-label translate>COMMON.BTN_EDIT</ion-label>\n </ion-button>\n }\n @if (showReadMoreButton) {\n <ion-button (click)=\"openFeedItem(item, feed)\" class=\"ion-float-end\" fill=\"clear\">\n <ion-label>{{ (item.truncated ? 'SOCIAL.FEED.READ_MORE' : 'COMMON.BTN_SHOW') | translate }}</ion-label>\n <ion-icon slot=\"end\" name=\"chevron-forward-outline\"></ion-icon>\n </ion-button>\n }\n }\n </ion-card>\n }\n }\n </div>\n}\n\n<!-- Details modal -->\n<ion-modal #modal [showBackdrop]=\"false\"\n class=\"stack-modal\" [class.modal-large]=\"!mobile\">\n <ng-template>\n <ion-header>\n <ion-toolbar color=\"secondary\">\n <ion-title>{{ 'SOCIAL.FEED.NEWS' | translate }}</ion-title>\n <ion-buttons slot=\"end\">\n <ion-button (click)=\"modal.dismiss()\">\n <ion-icon slot=\"icon-only\" name=\"close\"></ion-icon>\n </ion-button>\n </ion-buttons>\n </ion-toolbar>\n </ion-header>\n <ion-content>\n <div class=\"ion-padding\">\n <app-feed\n [urls]=\"urls\"\n [showHeader]=\"false\"\n [showReadMoreButton]=\"false\"\n [maxContentLength]=\"-1\"\n [maxAgeInMonths]=\"-1\"\n [itemId]=\"modalItemId\"\n cardColor=\"light\"\n [debug]=\"debug\"\n ></app-feed>\n </div>\n </ion-content>\n </ng-template>\n</ion-modal>\n", styles: [":host{display:block;height:calc(100% - 10px);max-height:fit-content;overflow:hidden;--feed-header-height: 48px;-webkit-box-shadow:0 3px 1px -2px rgba(0,0,0,.2),0 2px 2px 0 rgba(0,0,0,.14),0 1px 5px 0 rgba(0,0,0,.12);box-shadow:0 3px 1px -2px rgba(0,0,0,.2),0 2px 2px rgba(0,0,0,.14),0 1px 5px rgba(0,0,0,.12);-webkit-margin-start:10px;margin-inline-start:10px;-webkit-margin-end:10px;margin-inline-end:10px;margin-top:0;margin-bottom:10px;--feed-border-radius: 4px;border-radius:var(--feed-border-radius);--ion-card-background: rgba(var(--ion-background-color-rgb), .6)}:host.shape-round{--feed-border-radius: 12px}ion-button{text-transform:unset;--color: rgba(var(--ion-color-contrast-rgb), .7)}ion-item.feed-header{height:var(--feed-header-height);margin:0;backdrop-filter:blur(4px);-webkit-backdrop-filter:blur(4px);border-radius:var(--feed-border-radius) var(--feed-border-radius) 0 0}ion-item.feed-header ion-icon[slot=start]{-webkit-margin-end:8px;margin-inline-end:8px}.feed-content{height:auto;overflow-y:auto;--margin-bottom: 8px}.feed-content.has-header{height:calc(100% - var(--feed-header-height, 0))}.feed-content ion-card.feed-item-card{--top-radius: 4px;--bottom-radius: 4px;backdrop-filter:blur(4px);-webkit-backdrop-filter:blur(4px);margin:0 0 var(--margin-bottom) 0;border-radius:var(--top-radius) var(--top-radius) var(--bottom-radius) var(--bottom-radius);--ion-card-color-contrast-rgb: var(--ion-color-contrast-rgb, var(--ion-color-dark-rgb, 0, 0, 0));--color: rgba(var(--ion-card-color-contrast-rgb), .87)}.feed-content ion-card.feed-item-card.first{--top-radius: 0}.feed-content ion-card.feed-item-card.last{--margin-bottom: 0;--bottom-radius: 0}.feed-content ion-card.feed-item-card ion-card-header ion-card-title{--color: rgba(var(--ion-card-color-contrast-rgb), .87)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip{--background: transparent;--border-color: transparent;--border-width: 0}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip ion-avatar{--color: rgba(var(--ion-card-color-contrast-rgb), .6);border:1px solid var(--color)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip ion-label{--color: rgba(var(--ion-card-color-contrast-rgb), .8);color:var(--color)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-note{--color: rgba(var(--ion-card-color-contrast-rgb), .6);color:var(--color)}.feed-content ion-card.feed-item-card ion-card-header .tags{display:inline}.feed-content ion-card.feed-item-card ion-card-header .tags a{color:rgba(var(--ion-card-color-contrast-rgb),.6)!important}.feed-content ion-card.feed-item-card ion-card-content ion-text ::ng-deep img{max-width:100%;height:auto!important}.feed-content ion-card.feed-item-card .visible-hover{opacity:0;transition:opacity .2s ease-in-out}.feed-content ion-card.feed-item-card:hover .visible-hover{opacity:1}\n"] }]
35223
+ args: [{ selector: 'app-feed', providers: [RxState], changeDetection: ChangeDetectionStrategy.OnPush, template: "<!-- debug -->\n@if (debug) {\n <app-debug [title]=\"'Feed'\">\n <p>\n hasFeeds?: {{ hasFeeds$ | async }}\n <br />\n urls: {{ urls$ | async | json }}\n <br />\n shape: {{ shape }}\n </p>\n </app-debug>\n}\n\n@let feeds = feeds$ | async;\n@let userId = userId$ | async;\n\n@if (feeds | isNotEmptyArray) {\n <!-- top header -->\n @if (showHeader && (feeds | arrayFirst); as feed) {\n <ion-item lines=\"none\" [color]=\"headerColor\" class=\"feed-header shape-{{ shape }}\">\n <ion-icon slot=\"start\" name=\"megaphone\"></ion-icon>\n <ion-label>\n <b>{{ feed.title || ('SOCIAL.FEED.NEWS' | translate) }}</b>\n </ion-label>\n <ion-button slot=\"end\" fill=\"clear\" (click)=\"openFeedHome()\" shape=\"\">\n <ion-label translate>SOCIAL.FEED.SHOW_ALL_FEED</ion-label>\n <ion-icon slot=\"end\" name=\"chevron-forward-outline\"></ion-icon>\n </ion-button>\n </ion-item>\n }\n\n <div class=\"feed-content shape-{{ shape }} ion-no-padding\" [class.has-header]=\"showHeader\">\n <!-- feeds -->\n @for (feed of feeds; track feed.feed_url; let firstFeed = $first; let lastFeed = $last) {\n <!-- items -->\n @for (item of feed.items | arrayFilter: filterItem; track item.id; let firstItem = $first; let lastItem = $last) {\n <ion-card\n [class.first]=\"firstFeed && firstItem\"\n [class.last]=\"lastFeed && lastItem\"\n [color]=\"cardColor !== 'light-transparent' ? cardColor : undefined\"\n class=\"feed-item-card\"\n >\n <ion-card-header>\n <ion-card-subtitle style=\"vertical-align: middle\">\n <!-- Authors -->\n @for (author of item.authors || feed.authors; track author) {\n @if (author.name || author.avatar) {\n <ion-chip (click)=\"openUrl(author.url)\" tappable>\n @if (author.avatar) {\n <ion-avatar>\n <ion-img [src]=\"author.avatar\" [alt]=\"author.name\"></ion-img>\n </ion-avatar>\n }\n @if (author.name) {\n <ion-label class=\"author\">{{ author.name }}</ion-label>\n }\n </ion-chip>\n }\n }\n <ion-note class=\"ion-float-end\">\n <small>{{ item.date_published | dateFromNow }}</small>\n </ion-note>\n </ion-card-subtitle>\n\n <!-- title -->\n <ion-card-title (click)=\"openFeedItem(item, feed)\" tappable>{{ item?.title }}</ion-card-title>\n\n <!-- tags -->\n @let tags = item | map: getTags;\n @if (tags | isNotEmptyArray) {\n <ion-text class=\"tags\">\n @for (tag of tags; track tag; let last = $last) {\n <a (click)=\"openTag(feed, tag)\" tappable>\n <ion-text>#{{ tag }}</ion-text>\n </a>\n @if (!last) {\n &nbsp;\n }\n }\n </ion-text>\n }\n </ion-card-header>\n\n <!-- Feed content -->\n <ion-card-content>\n <ion-text [feed]=\"item.url || feed.feed_url\">\n @if (item.content_html) {\n <p [innerHTML]=\"item.content_html\"></p>\n } @else if (item.content_text) {\n <p>\n <markdown [data]=\"item.content_text\" emoji></markdown>\n </p>\n }\n </ion-text>\n </ion-card-content>\n\n @let editable = canEditItem(item, userId, feed);\n @if (editable || showReadMoreButton) {\n @if (editable) {\n\n <!-- Delete button (visible hover)-->\n <button\n mat-icon-button\n (click)=\"onDeleteItem($event, item)\"\n class=\"visible-hover ion-float-start\"\n [title]=\"'COMMON.BTN_DELETE' | translate\"\n >\n <mat-icon>delete</mat-icon>\n </button>\n <!-- Edit button (visible hover) -->\n <ion-button\n (click)=\"onEditItem($event, item)\"\n class=\"visible-hover ion-float-start\" fill=\"clear\"\n >\n <mat-icon slot=\"start\">edit</mat-icon>\n<!-- <ion-icon name=\"pencil\" slot=\"start\"></ion-icon>-->\n <ion-label translate>COMMON.BTN_EDIT</ion-label>\n </ion-button>\n }\n @if (showReadMoreButton) {\n <ion-button (click)=\"openFeedItem(item, feed)\" class=\"ion-float-end\" fill=\"clear\">\n <ion-label>{{ (item.truncated ? 'SOCIAL.FEED.READ_MORE' : 'COMMON.BTN_SHOW') | translate }}</ion-label>\n <ion-icon slot=\"end\" name=\"chevron-forward-outline\"></ion-icon>\n </ion-button>\n }\n }\n </ion-card>\n }\n }\n </div>\n}\n\n<!-- Details modal -->\n<ion-modal #modal [showBackdrop]=\"false\"\n class=\"stack-modal\" [class.modal-large]=\"!mobile\">\n <ng-template>\n <ion-header>\n <ion-toolbar color=\"secondary\">\n <ion-title>{{ 'SOCIAL.FEED.NEWS' | translate }}</ion-title>\n <ion-buttons slot=\"end\">\n <ion-button (click)=\"modal.dismiss()\">\n <ion-icon slot=\"icon-only\" name=\"close\"></ion-icon>\n </ion-button>\n </ion-buttons>\n </ion-toolbar>\n </ion-header>\n <ion-content>\n <div class=\"ion-padding\">\n <app-feed\n [urls]=\"urls\"\n [showHeader]=\"false\"\n [showReadMoreButton]=\"false\"\n [maxContentLength]=\"-1\"\n [maxAgeInMonths]=\"-1\"\n [itemId]=\"modalItemId\"\n cardColor=\"light\"\n [debug]=\"debug\"\n ></app-feed>\n </div>\n </ion-content>\n </ng-template>\n</ion-modal>\n", styles: [":host{display:block;height:calc(100% - 10px);max-height:fit-content;overflow:hidden;--feed-header-height: 48px;-webkit-box-shadow:0 3px 1px -2px rgba(0,0,0,.2),0 2px 2px 0 rgba(0,0,0,.14),0 1px 5px 0 rgba(0,0,0,.12);box-shadow:0 3px 1px -2px #0003,0 2px 2px #00000024,0 1px 5px #0000001f;-webkit-margin-start:10px;margin-inline-start:10px;-webkit-margin-end:10px;margin-inline-end:10px;margin-top:0;margin-bottom:10px;--feed-border-radius: 4px;border-radius:var(--feed-border-radius);--ion-card-background: rgba(var(--ion-background-color-rgb), .6)}:host.shape-round{--feed-border-radius: 12px}ion-button{text-transform:unset;--color: rgba(var(--ion-color-contrast-rgb), .7)}ion-item.feed-header{height:var(--feed-header-height);margin:0;backdrop-filter:blur(4px);-webkit-backdrop-filter:blur(4px);border-radius:var(--feed-border-radius) var(--feed-border-radius) 0 0}ion-item.feed-header ion-icon[slot=start]{-webkit-margin-end:8px;margin-inline-end:8px}.feed-content{height:auto;overflow-y:auto;--margin-bottom: 8px}.feed-content.has-header{height:calc(100% - var(--feed-header-height, 0))}.feed-content ion-card.feed-item-card{--top-radius: 4px;--bottom-radius: 4px;backdrop-filter:blur(4px);-webkit-backdrop-filter:blur(4px);margin:0 0 var(--margin-bottom) 0;border-radius:var(--top-radius) var(--top-radius) var(--bottom-radius) var(--bottom-radius);--ion-card-color-contrast-rgb: var(--ion-color-contrast-rgb, var(--ion-color-dark-rgb, 0, 0, 0));--color: rgba(var(--ion-card-color-contrast-rgb), .87)}.feed-content ion-card.feed-item-card.first{--top-radius: 0}.feed-content ion-card.feed-item-card.last{--margin-bottom: 0;--bottom-radius: 0}.feed-content ion-card.feed-item-card ion-card-header ion-card-title{--color: rgba(var(--ion-card-color-contrast-rgb), .87)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip{--background: transparent;--border-color: transparent;--border-width: 0}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip ion-avatar{--color: rgba(var(--ion-card-color-contrast-rgb), .6);border:1px solid var(--color)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-chip ion-label{--color: rgba(var(--ion-card-color-contrast-rgb), .8);color:var(--color)}.feed-content ion-card.feed-item-card ion-card-header ion-card-subtitle ion-note{--color: rgba(var(--ion-card-color-contrast-rgb), .6);color:var(--color)}.feed-content ion-card.feed-item-card ion-card-header .tags{display:inline}.feed-content ion-card.feed-item-card ion-card-header .tags a{color:rgba(var(--ion-card-color-contrast-rgb),.6)!important}.feed-content ion-card.feed-item-card ion-card-content ion-text ::ng-deep img{max-width:100%;height:auto!important}.feed-content ion-card.feed-item-card .visible-hover{opacity:0;transition:opacity .2s ease-in-out}.feed-content ion-card.feed-item-card:hover .visible-hover{opacity:1}\n"] }]
35224
35224
  }], ctorParameters: () => [{ type: LocalSettingsService }, { type: Environment, decorators: [{
35225
35225
  type: Inject,
35226
35226
  args: [ENVIRONMENT]
@@ -47618,11 +47618,11 @@ class MatBadgeTestPage {
47618
47618
  this.cd.markForCheck();
47619
47619
  }
47620
47620
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: MatBadgeTestPage, deps: [{ token: i0.ChangeDetectorRef }], target: i0.ɵɵFactoryTarget.Component });
47621
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.13", type: MatBadgeTestPage, selector: "mat-badge-test", ngImport: i0, template: "<ion-header>\n <ion-toolbar color=\"primary\">\n <ion-buttons slot=\"start\">\n <ion-back-button></ion-back-button>\n </ion-buttons>\n\n <ion-title>matBadgeIcon directive</ion-title>\n </ion-toolbar>\n</ion-header>\n\n<ion-content class=\"ion-padding\">\n <!-- small badge -->\n <p>\n <ion-text color=\"tertiary\">\n <span appBadge appBadgeMatIcon=\"check\" appBadgeSize=\"small\" appBadgeColor=\"accent\" appBadgeOverlap=\"false\">\n Small badge\n </span>\n </ion-text>\n </p>\n\n <!-- small badge with text -->\n <p>\n <ion-text color=\"tertiary\">\n <span [appBadge]=\"0\" appBadgeSize=\"small\" appBadgeColor=\"accent\" appBadgeOverlap=\"false\">\n Small badge with text 0\n </span>\n </ion-text>\n </p>\n\n <!-- medium badge -->\n <p>\n <ion-text\n appBadge\n appBadgeMatIcon=\"check\"\n appBadgeSize=\"medium\"\n [appBadgeColor]=\"'tertiary' | matColor\"\n appBadgeOverlap=\"false\"\n >\n Medium badge\n </ion-text>\n </p>\n\n <!-- small badge -->\n <p>\n <ion-label appBadge appBadgeMatIcon=\"close\" appBadgeSize=\"large\" appBadgeOverlap=\"false\">Large badge</ion-label>\n </p>\n\n <!-- default size badge -->\n <p>\n <ion-label appBadge appBadgeMatIcon=\"check\" [appBadgeColor]=\"'success' | matColor\" appBadgeOverlap=\"false\">\n Badge (no size, no color)\n </ion-label>\n </p>\n\n <!-- ion icon -->\n <p>\n <ion-label appBadge appBadgeIcon=\"checkmark\" [appBadgeColor]=\"'success' | matColor\" appBadgeOverlap=\"false\">\n Badge with ion-icon\n </ion-label>\n </p>\n\n <!-- ion icon clear -->\n <p>\n <ion-label\n appBadge\n appBadgeIcon=\"checkmark-circle\"\n [appBadgeColor]=\"'tertiary' | matColor\"\n appBadgeFill=\"clear\"\n appBadgeOverlap=\"false\"\n >\n Badge with clear icon\n </ion-label>\n </p>\n\n <!-- changing text-->\n <ion-row>\n <ion-col>\n <ion-label\n appBadge\n appBadgeIcon=\"checkmark-circle\"\n [appBadgeColor]=\"'tertiary' | matColor\"\n appBadgeFill=\"clear\"\n appBadgeOverlap=\"false\"\n >\n {{ userText }}\n </ion-label>\n </ion-col>\n <ion-col>\n <input type=\"text\" [value]=\"userText\" (input)=\"onInputChanged($event)\" />\n </ion-col>\n </ion-row>\n\n <ion-row>\n <ion-col>Configurable example :</ion-col>\n </ion-row>\n <ion-row class=\"ion-no-padding\">\n <ion-col size=\"auto\">\n <mat-icon\n [style.color]=\"'var(--ion-color-secondary)'\"\n appBadge\n [appBadgeIcon]=\"$icon | async\"\n [appBadgeColor]=\"$color | async | matColor\"\n [appBadgeHidden]=\"$hidden | async\"\n [appBadgeFill]=\"$fill | async\"\n [appBadgeSize]=\"$size | async\"\n appBadgeOverlap=\"true\"\n appBadgePosition=\"above before\"\n >\n <ion-icon slot=\"icon-only\" [color]=\"'secondary'\" name=\"navigate\"></ion-icon>\n </mat-icon>\n </ion-col>\n\n <ion-col>\n <mat-form-field>\n <mat-label>appBadgeColor</mat-label>\n <mat-select [value]=\"$color.value\" (selectionChange)=\"this.$color.next($event.value)\">\n <mat-option [value]=\"'primary'\">primary</mat-option>\n <mat-option [value]=\"'secondary'\">secondary</mat-option>\n <mat-option [value]=\"'tertiary'\">tertiary</mat-option>\n <mat-option [value]=\"'danger'\">danger</mat-option>\n </mat-select>\n </mat-form-field>\n </ion-col>\n\n <ion-col>\n <mat-form-field>\n <mat-label>appBadgeIcon</mat-label>\n <mat-select [value]=\"$icon.value\" (selectionChange)=\"this.$icon.next($event.value)\">\n <mat-option [value]=\"'checkmark-circle'\">checkmark-circle</mat-option>\n <mat-option [value]=\"'alert-circle'\">alert-circle</mat-option>\n <mat-option [value]=\"'alert'\">alert</mat-option>\n <mat-option [value]=\"'flag'\">flag</mat-option>\n </mat-select>\n </mat-form-field>\n </ion-col>\n\n <ion-col>\n <mat-form-field>\n <mat-label>appBadgeSize</mat-label>\n <mat-select [value]=\"$size.value\" (selectionChange)=\"this.$size.next($event.value)\">\n <mat-option [value]=\"'large'\">large</mat-option>\n <mat-option [value]=\"'medium'\">medium</mat-option>\n <mat-option [value]=\"'small'\">small</mat-option>\n </mat-select>\n </mat-form-field>\n </ion-col>\n\n <ion-col>\n <mat-form-field>\n <mat-label>appBadgeFill</mat-label>\n <mat-select [value]=\"$fill.value\" (selectionChange)=\"this.$fill.next($event.value)\">\n <mat-option [value]=\"'clear'\">clear</mat-option>\n <mat-option [value]=\"'solid'\">solid</mat-option>\n </mat-select>\n </mat-form-field>\n </ion-col>\n\n <ion-col>\n <mat-form-field>\n <mat-label>appBadgeHidden</mat-label>\n <mat-select [value]=\"$hidden.value\" (selectionChange)=\"this.$hidden.next($event.value)\">\n <mat-option [value]=\"true\">true</mat-option>\n <mat-option [value]=\"false\">false</mat-option>\n </mat-select>\n </mat-form-field>\n </ion-col>\n </ion-row>\n\n <ion-row>\n <ion-col size=\"auto\">\n <p>mat-raised-button:</p>\n </ion-col>\n <ion-col>\n <button\n mat-raised-button\n color=\"primary\"\n [appBadgeIcon]=\"$icon | async\"\n [appBadgeColor]=\"$color | async | matColor\"\n [appBadgeHidden]=\"$hidden | async\"\n [appBadgeFill]=\"$fill | async\"\n [appBadgeSize]=\"$size | async\"\n appBadgeOverlap=\"true\"\n appBadgePosition=\"below after\"\n >\n {{ userText }}\n </button>\n </ion-col>\n </ion-row>\n\n <ion-row>\n <ion-col size=\"auto\">\n <p>mat-button with mat-label:</p>\n </ion-col>\n <ion-col>\n <button\n mat-button\n color=\"primary\"\n class=\"ion-no-padding\"\n [appBadgeIcon]=\"$icon | async\"\n [appBadgeColor]=\"$color | async | matColor\"\n [appBadgeHidden]=\"$hidden | async\"\n [appBadgeFill]=\"$fill | async\"\n [appBadgeSize]=\"$size | async\"\n matBadgeOverlap=\"true\"\n matBadgePosition=\"above after\"\n >\n {{ userText }}\n </button>\n </ion-col>\n </ion-row>\n\n <h4>Angular Material Badge (standard way)</h4>\n\n <ion-row>\n <ion-col size=\"auto\">\n <p>mat-icon:</p>\n </ion-col>\n <ion-col>\n <mat-icon\n [style.color]=\"'var(--ion-color-secondary)'\"\n [matBadge]=\"'!'\"\n [matBadgeColor]=\"$color | async | matColor\"\n [matBadgeHidden]=\"$hidden | async\"\n [matBadgeSize]=\"$size | async\"\n matBadgeOverlap=\"true\"\n >\n <ion-icon slot=\"icon-only\" [color]=\"'secondary'\" name=\"navigate\"></ion-icon>\n </mat-icon>\n </ion-col>\n </ion-row>\n\n <ion-row>\n <ion-col size=\"auto\">\n <p>mat-button:</p>\n </ion-col>\n <ion-col>\n <button\n mat-raised-button\n color=\"primary\"\n [matBadge]=\"matBadgeContent\"\n [matBadgeColor]=\"$color | async | matColor\"\n [matBadgeHidden]=\"$hidden | async\"\n [matBadgeSize]=\"$size | async\"\n matBadgeOverlap=\"true\"\n matBadgePosition=\"above after\"\n >\n {{ userText }}\n </button>\n </ion-col>\n\n <ion-col>\n <input type=\"text\" [value]=\"matBadgeContent\" (input)=\"onMatBadgeContentChanged($event)\" />\n </ion-col>\n </ion-row>\n\n <ion-row>\n <ion-col size=\"auto\">\n <p>mat-button</p>\n </ion-col>\n <ion-col>\n <button\n mat-button\n color=\"primary\"\n [matBadge]=\"matBadgeContent\"\n [matBadgeColor]=\"$color | async | matColor\"\n [matBadgeHidden]=\"$hidden | async\"\n [matBadgeSize]=\"$size | async\"\n matBadgeOverlap=\"true\"\n matBadgePosition=\"after\"\n >\n {{ userText }}\n </button>\n </ion-col>\n </ion-row>\n</ion-content>\n", dependencies: [{ kind: "component", type: i2$1.IonButtons, selector: "ion-buttons", inputs: ["collapse"] }, { kind: "component", type: i2$1.IonCol, selector: "ion-col", inputs: ["offset", "offsetLg", "offsetMd", "offsetSm", "offsetXl", "offsetXs", "pull", "pullLg", "pullMd", "pullSm", "pullXl", "pullXs", "push", "pushLg", "pushMd", "pushSm", "pushXl", "pushXs", "size", "sizeLg", "sizeMd", "sizeSm", "sizeXl", "sizeXs"] }, { kind: "component", type: i2$1.IonContent, selector: "ion-content", inputs: ["color", "forceOverscroll", "fullscreen", "scrollEvents", "scrollX", "scrollY"] }, { kind: "component", type: i2$1.IonHeader, selector: "ion-header", inputs: ["collapse", "mode", "translucent"] }, { kind: "component", type: i2$1.IonIcon, selector: "ion-icon", inputs: ["color", "flipRtl", "icon", "ios", "lazy", "md", "mode", "name", "sanitize", "size", "src"] }, { kind: "component", type: i2$1.IonLabel, selector: "ion-label", inputs: ["color", "mode", "position"] }, { kind: "component", type: i2$1.IonRow, selector: "ion-row" }, { kind: "component", type: i2$1.IonText, selector: "ion-text", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonTitle, selector: "ion-title", inputs: ["color", "size"] }, { kind: "component", type: i2$1.IonToolbar, selector: "ion-toolbar", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonBackButton, selector: "ion-back-button" }, { kind: "component", type: i3.MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: i3.MatLabel, selector: "mat-label" }, { kind: "component", type: i6$1.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i9.MatButton, selector: " button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button] ", exportAs: ["matButton"] }, { kind: "component", type: i6$3.MatSelect, selector: "mat-select", inputs: ["aria-describedby", "panelClass", "disabled", "disableRipple", "tabIndex", "hideSingleSelectionIndicator", "placeholder", "required", "multiple", "disableOptionCentering", "compareWith", "value", "aria-label", "aria-labelledby", "errorStateMatcher", "typeaheadDebounceInterval", "sortComparator", "id", "panelWidth"], outputs: ["openedChange", "opened", "closed", "selectionChange", "valueChange"], exportAs: ["matSelect"] }, { kind: "component", type: i2.MatOption, selector: "mat-option", inputs: ["value", "id", "disabled"], outputs: ["onSelectionChange"], exportAs: ["matOption"] }, { kind: "directive", type: i8.MatBadge, selector: "[matBadge]", inputs: ["matBadgeColor", "matBadgeOverlap", "matBadgeDisabled", "matBadgePosition", "matBadge", "matBadgeDescription", "matBadgeSize", "matBadgeHidden"] }, { kind: "directive", type: BadgeDirective, selector: "[appBadge], [appBadgeIcon], [appBadgeMatIcon]", inputs: ["appBadge", "appBadgeDisabled", "appBadgeSize", "appBadgeColor", "appBadgeFill", "appBadgeMatIcon", "appBadgeIcon", "appBadgeHidden", "appBadgeOverlap", "appBadgePosition"] }, { kind: "pipe", type: i3$1.AsyncPipe, name: "async" }, { kind: "pipe", type: MatColorPipe, name: "matColor" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
47621
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.13", type: MatBadgeTestPage, selector: "mat-badge-test", ngImport: i0, template: "<ion-header>\r\n <ion-toolbar color=\"primary\">\r\n <ion-buttons slot=\"start\">\r\n <ion-back-button></ion-back-button>\r\n </ion-buttons>\r\n\r\n <ion-title>matBadgeIcon directive</ion-title>\r\n </ion-toolbar>\r\n</ion-header>\r\n\r\n<ion-content class=\"ion-padding\">\r\n <!-- small badge -->\r\n <p>\r\n <ion-text color=\"tertiary\">\r\n <span appBadge appBadgeMatIcon=\"check\" appBadgeSize=\"small\" appBadgeColor=\"accent\" appBadgeOverlap=\"false\">\r\n Small badge\r\n </span>\r\n </ion-text>\r\n </p>\r\n\r\n <!-- small badge with text -->\r\n <p>\r\n <ion-text color=\"tertiary\">\r\n <span [appBadge]=\"0\" appBadgeSize=\"small\" appBadgeColor=\"accent\" appBadgeOverlap=\"false\">\r\n Small badge with text 0\r\n </span>\r\n </ion-text>\r\n </p>\r\n\r\n <!-- medium badge -->\r\n <p>\r\n <ion-text\r\n appBadge\r\n appBadgeMatIcon=\"check\"\r\n appBadgeSize=\"medium\"\r\n [appBadgeColor]=\"'tertiary' | matColor\"\r\n appBadgeOverlap=\"false\"\r\n >\r\n Medium badge\r\n </ion-text>\r\n </p>\r\n\r\n <!-- small badge -->\r\n <p>\r\n <ion-label appBadge appBadgeMatIcon=\"close\" appBadgeSize=\"large\" appBadgeOverlap=\"false\">Large badge</ion-label>\r\n </p>\r\n\r\n <!-- default size badge -->\r\n <p>\r\n <ion-label appBadge appBadgeMatIcon=\"check\" [appBadgeColor]=\"'success' | matColor\" appBadgeOverlap=\"false\">\r\n Badge (no size, no color)\r\n </ion-label>\r\n </p>\r\n\r\n <!-- ion icon -->\r\n <p>\r\n <ion-label appBadge appBadgeIcon=\"checkmark\" [appBadgeColor]=\"'success' | matColor\" appBadgeOverlap=\"false\">\r\n Badge with ion-icon\r\n </ion-label>\r\n </p>\r\n\r\n <!-- ion icon clear -->\r\n <p>\r\n <ion-label\r\n appBadge\r\n appBadgeIcon=\"checkmark-circle\"\r\n [appBadgeColor]=\"'tertiary' | matColor\"\r\n appBadgeFill=\"clear\"\r\n appBadgeOverlap=\"false\"\r\n >\r\n Badge with clear icon\r\n </ion-label>\r\n </p>\r\n\r\n <!-- changing text-->\r\n <ion-row>\r\n <ion-col>\r\n <ion-label\r\n appBadge\r\n appBadgeIcon=\"checkmark-circle\"\r\n [appBadgeColor]=\"'tertiary' | matColor\"\r\n appBadgeFill=\"clear\"\r\n appBadgeOverlap=\"false\"\r\n >\r\n {{ userText }}\r\n </ion-label>\r\n </ion-col>\r\n <ion-col>\r\n <input type=\"text\" [value]=\"userText\" (input)=\"onInputChanged($event)\" />\r\n </ion-col>\r\n </ion-row>\r\n\r\n <ion-row>\r\n <ion-col>Configurable example :</ion-col>\r\n </ion-row>\r\n <ion-row class=\"ion-no-padding\">\r\n <ion-col size=\"auto\">\r\n <mat-icon\r\n [style.color]=\"'var(--ion-color-secondary)'\"\r\n appBadge\r\n [appBadgeIcon]=\"$icon | async\"\r\n [appBadgeColor]=\"$color | async | matColor\"\r\n [appBadgeHidden]=\"$hidden | async\"\r\n [appBadgeFill]=\"$fill | async\"\r\n [appBadgeSize]=\"$size | async\"\r\n appBadgeOverlap=\"true\"\r\n appBadgePosition=\"above before\"\r\n >\r\n <ion-icon slot=\"icon-only\" [color]=\"'secondary'\" name=\"navigate\"></ion-icon>\r\n </mat-icon>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <mat-form-field>\r\n <mat-label>appBadgeColor</mat-label>\r\n <mat-select [value]=\"$color.value\" (selectionChange)=\"this.$color.next($event.value)\">\r\n <mat-option [value]=\"'primary'\">primary</mat-option>\r\n <mat-option [value]=\"'secondary'\">secondary</mat-option>\r\n <mat-option [value]=\"'tertiary'\">tertiary</mat-option>\r\n <mat-option [value]=\"'danger'\">danger</mat-option>\r\n </mat-select>\r\n </mat-form-field>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <mat-form-field>\r\n <mat-label>appBadgeIcon</mat-label>\r\n <mat-select [value]=\"$icon.value\" (selectionChange)=\"this.$icon.next($event.value)\">\r\n <mat-option [value]=\"'checkmark-circle'\">checkmark-circle</mat-option>\r\n <mat-option [value]=\"'alert-circle'\">alert-circle</mat-option>\r\n <mat-option [value]=\"'alert'\">alert</mat-option>\r\n <mat-option [value]=\"'flag'\">flag</mat-option>\r\n </mat-select>\r\n </mat-form-field>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <mat-form-field>\r\n <mat-label>appBadgeSize</mat-label>\r\n <mat-select [value]=\"$size.value\" (selectionChange)=\"this.$size.next($event.value)\">\r\n <mat-option [value]=\"'large'\">large</mat-option>\r\n <mat-option [value]=\"'medium'\">medium</mat-option>\r\n <mat-option [value]=\"'small'\">small</mat-option>\r\n </mat-select>\r\n </mat-form-field>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <mat-form-field>\r\n <mat-label>appBadgeFill</mat-label>\r\n <mat-select [value]=\"$fill.value\" (selectionChange)=\"this.$fill.next($event.value)\">\r\n <mat-option [value]=\"'clear'\">clear</mat-option>\r\n <mat-option [value]=\"'solid'\">solid</mat-option>\r\n </mat-select>\r\n </mat-form-field>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <mat-form-field>\r\n <mat-label>appBadgeHidden</mat-label>\r\n <mat-select [value]=\"$hidden.value\" (selectionChange)=\"this.$hidden.next($event.value)\">\r\n <mat-option [value]=\"true\">true</mat-option>\r\n <mat-option [value]=\"false\">false</mat-option>\r\n </mat-select>\r\n </mat-form-field>\r\n </ion-col>\r\n </ion-row>\r\n\r\n <ion-row>\r\n <ion-col size=\"auto\">\r\n <p>mat-raised-button:</p>\r\n </ion-col>\r\n <ion-col>\r\n <button\r\n mat-raised-button\r\n color=\"primary\"\r\n [appBadgeIcon]=\"$icon | async\"\r\n [appBadgeColor]=\"$color | async | matColor\"\r\n [appBadgeHidden]=\"$hidden | async\"\r\n [appBadgeFill]=\"$fill | async\"\r\n [appBadgeSize]=\"$size | async\"\r\n appBadgeOverlap=\"true\"\r\n appBadgePosition=\"below after\"\r\n >\r\n {{ userText }}\r\n </button>\r\n </ion-col>\r\n </ion-row>\r\n\r\n <ion-row>\r\n <ion-col size=\"auto\">\r\n <p>mat-button with mat-label:</p>\r\n </ion-col>\r\n <ion-col>\r\n <button\r\n mat-button\r\n color=\"primary\"\r\n class=\"ion-no-padding\"\r\n [appBadgeIcon]=\"$icon | async\"\r\n [appBadgeColor]=\"$color | async | matColor\"\r\n [appBadgeHidden]=\"$hidden | async\"\r\n [appBadgeFill]=\"$fill | async\"\r\n [appBadgeSize]=\"$size | async\"\r\n matBadgeOverlap=\"true\"\r\n matBadgePosition=\"above after\"\r\n >\r\n {{ userText }}\r\n </button>\r\n </ion-col>\r\n </ion-row>\r\n\r\n <h4>Angular Material Badge (standard way)</h4>\r\n\r\n <ion-row>\r\n <ion-col size=\"auto\">\r\n <p>mat-icon:</p>\r\n </ion-col>\r\n <ion-col>\r\n <mat-icon\r\n [style.color]=\"'var(--ion-color-secondary)'\"\r\n [matBadge]=\"'!'\"\r\n [matBadgeColor]=\"$color | async | matColor\"\r\n [matBadgeHidden]=\"$hidden | async\"\r\n [matBadgeSize]=\"$size | async\"\r\n matBadgeOverlap=\"true\"\r\n >\r\n <ion-icon slot=\"icon-only\" [color]=\"'secondary'\" name=\"navigate\"></ion-icon>\r\n </mat-icon>\r\n </ion-col>\r\n </ion-row>\r\n\r\n <ion-row>\r\n <ion-col size=\"auto\">\r\n <p>mat-button:</p>\r\n </ion-col>\r\n <ion-col>\r\n <button\r\n mat-raised-button\r\n color=\"primary\"\r\n [matBadge]=\"matBadgeContent\"\r\n [matBadgeColor]=\"$color | async | matColor\"\r\n [matBadgeHidden]=\"$hidden | async\"\r\n [matBadgeSize]=\"$size | async\"\r\n matBadgeOverlap=\"true\"\r\n matBadgePosition=\"above after\"\r\n >\r\n {{ userText }}\r\n </button>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <input type=\"text\" [value]=\"matBadgeContent\" (input)=\"onMatBadgeContentChanged($event)\" />\r\n </ion-col>\r\n </ion-row>\r\n\r\n <ion-row>\r\n <ion-col size=\"auto\">\r\n <p>mat-button</p>\r\n </ion-col>\r\n <ion-col>\r\n <button\r\n mat-button\r\n color=\"primary\"\r\n [matBadge]=\"matBadgeContent\"\r\n [matBadgeColor]=\"$color | async | matColor\"\r\n [matBadgeHidden]=\"$hidden | async\"\r\n [matBadgeSize]=\"$size | async\"\r\n matBadgeOverlap=\"true\"\r\n matBadgePosition=\"after\"\r\n >\r\n {{ userText }}\r\n </button>\r\n </ion-col>\r\n </ion-row>\r\n</ion-content>\r\n", dependencies: [{ kind: "component", type: i2$1.IonButtons, selector: "ion-buttons", inputs: ["collapse"] }, { kind: "component", type: i2$1.IonCol, selector: "ion-col", inputs: ["offset", "offsetLg", "offsetMd", "offsetSm", "offsetXl", "offsetXs", "pull", "pullLg", "pullMd", "pullSm", "pullXl", "pullXs", "push", "pushLg", "pushMd", "pushSm", "pushXl", "pushXs", "size", "sizeLg", "sizeMd", "sizeSm", "sizeXl", "sizeXs"] }, { kind: "component", type: i2$1.IonContent, selector: "ion-content", inputs: ["color", "forceOverscroll", "fullscreen", "scrollEvents", "scrollX", "scrollY"] }, { kind: "component", type: i2$1.IonHeader, selector: "ion-header", inputs: ["collapse", "mode", "translucent"] }, { kind: "component", type: i2$1.IonIcon, selector: "ion-icon", inputs: ["color", "flipRtl", "icon", "ios", "lazy", "md", "mode", "name", "sanitize", "size", "src"] }, { kind: "component", type: i2$1.IonLabel, selector: "ion-label", inputs: ["color", "mode", "position"] }, { kind: "component", type: i2$1.IonRow, selector: "ion-row" }, { kind: "component", type: i2$1.IonText, selector: "ion-text", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonTitle, selector: "ion-title", inputs: ["color", "size"] }, { kind: "component", type: i2$1.IonToolbar, selector: "ion-toolbar", inputs: ["color", "mode"] }, { kind: "component", type: i2$1.IonBackButton, selector: "ion-back-button" }, { kind: "component", type: i3.MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: i3.MatLabel, selector: "mat-label" }, { kind: "component", type: i6$1.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i9.MatButton, selector: " button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button] ", exportAs: ["matButton"] }, { kind: "component", type: i6$3.MatSelect, selector: "mat-select", inputs: ["aria-describedby", "panelClass", "disabled", "disableRipple", "tabIndex", "hideSingleSelectionIndicator", "placeholder", "required", "multiple", "disableOptionCentering", "compareWith", "value", "aria-label", "aria-labelledby", "errorStateMatcher", "typeaheadDebounceInterval", "sortComparator", "id", "panelWidth"], outputs: ["openedChange", "opened", "closed", "selectionChange", "valueChange"], exportAs: ["matSelect"] }, { kind: "component", type: i2.MatOption, selector: "mat-option", inputs: ["value", "id", "disabled"], outputs: ["onSelectionChange"], exportAs: ["matOption"] }, { kind: "directive", type: i8.MatBadge, selector: "[matBadge]", inputs: ["matBadgeColor", "matBadgeOverlap", "matBadgeDisabled", "matBadgePosition", "matBadge", "matBadgeDescription", "matBadgeSize", "matBadgeHidden"] }, { kind: "directive", type: BadgeDirective, selector: "[appBadge], [appBadgeIcon], [appBadgeMatIcon]", inputs: ["appBadge", "appBadgeDisabled", "appBadgeSize", "appBadgeColor", "appBadgeFill", "appBadgeMatIcon", "appBadgeIcon", "appBadgeHidden", "appBadgeOverlap", "appBadgePosition"] }, { kind: "pipe", type: i3$1.AsyncPipe, name: "async" }, { kind: "pipe", type: MatColorPipe, name: "matColor" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
47622
47622
  }
47623
47623
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: MatBadgeTestPage, decorators: [{
47624
47624
  type: Component,
47625
- args: [{ selector: 'mat-badge-test', changeDetection: ChangeDetectionStrategy.OnPush, template: "<ion-header>\n <ion-toolbar color=\"primary\">\n <ion-buttons slot=\"start\">\n <ion-back-button></ion-back-button>\n </ion-buttons>\n\n <ion-title>matBadgeIcon directive</ion-title>\n </ion-toolbar>\n</ion-header>\n\n<ion-content class=\"ion-padding\">\n <!-- small badge -->\n <p>\n <ion-text color=\"tertiary\">\n <span appBadge appBadgeMatIcon=\"check\" appBadgeSize=\"small\" appBadgeColor=\"accent\" appBadgeOverlap=\"false\">\n Small badge\n </span>\n </ion-text>\n </p>\n\n <!-- small badge with text -->\n <p>\n <ion-text color=\"tertiary\">\n <span [appBadge]=\"0\" appBadgeSize=\"small\" appBadgeColor=\"accent\" appBadgeOverlap=\"false\">\n Small badge with text 0\n </span>\n </ion-text>\n </p>\n\n <!-- medium badge -->\n <p>\n <ion-text\n appBadge\n appBadgeMatIcon=\"check\"\n appBadgeSize=\"medium\"\n [appBadgeColor]=\"'tertiary' | matColor\"\n appBadgeOverlap=\"false\"\n >\n Medium badge\n </ion-text>\n </p>\n\n <!-- small badge -->\n <p>\n <ion-label appBadge appBadgeMatIcon=\"close\" appBadgeSize=\"large\" appBadgeOverlap=\"false\">Large badge</ion-label>\n </p>\n\n <!-- default size badge -->\n <p>\n <ion-label appBadge appBadgeMatIcon=\"check\" [appBadgeColor]=\"'success' | matColor\" appBadgeOverlap=\"false\">\n Badge (no size, no color)\n </ion-label>\n </p>\n\n <!-- ion icon -->\n <p>\n <ion-label appBadge appBadgeIcon=\"checkmark\" [appBadgeColor]=\"'success' | matColor\" appBadgeOverlap=\"false\">\n Badge with ion-icon\n </ion-label>\n </p>\n\n <!-- ion icon clear -->\n <p>\n <ion-label\n appBadge\n appBadgeIcon=\"checkmark-circle\"\n [appBadgeColor]=\"'tertiary' | matColor\"\n appBadgeFill=\"clear\"\n appBadgeOverlap=\"false\"\n >\n Badge with clear icon\n </ion-label>\n </p>\n\n <!-- changing text-->\n <ion-row>\n <ion-col>\n <ion-label\n appBadge\n appBadgeIcon=\"checkmark-circle\"\n [appBadgeColor]=\"'tertiary' | matColor\"\n appBadgeFill=\"clear\"\n appBadgeOverlap=\"false\"\n >\n {{ userText }}\n </ion-label>\n </ion-col>\n <ion-col>\n <input type=\"text\" [value]=\"userText\" (input)=\"onInputChanged($event)\" />\n </ion-col>\n </ion-row>\n\n <ion-row>\n <ion-col>Configurable example :</ion-col>\n </ion-row>\n <ion-row class=\"ion-no-padding\">\n <ion-col size=\"auto\">\n <mat-icon\n [style.color]=\"'var(--ion-color-secondary)'\"\n appBadge\n [appBadgeIcon]=\"$icon | async\"\n [appBadgeColor]=\"$color | async | matColor\"\n [appBadgeHidden]=\"$hidden | async\"\n [appBadgeFill]=\"$fill | async\"\n [appBadgeSize]=\"$size | async\"\n appBadgeOverlap=\"true\"\n appBadgePosition=\"above before\"\n >\n <ion-icon slot=\"icon-only\" [color]=\"'secondary'\" name=\"navigate\"></ion-icon>\n </mat-icon>\n </ion-col>\n\n <ion-col>\n <mat-form-field>\n <mat-label>appBadgeColor</mat-label>\n <mat-select [value]=\"$color.value\" (selectionChange)=\"this.$color.next($event.value)\">\n <mat-option [value]=\"'primary'\">primary</mat-option>\n <mat-option [value]=\"'secondary'\">secondary</mat-option>\n <mat-option [value]=\"'tertiary'\">tertiary</mat-option>\n <mat-option [value]=\"'danger'\">danger</mat-option>\n </mat-select>\n </mat-form-field>\n </ion-col>\n\n <ion-col>\n <mat-form-field>\n <mat-label>appBadgeIcon</mat-label>\n <mat-select [value]=\"$icon.value\" (selectionChange)=\"this.$icon.next($event.value)\">\n <mat-option [value]=\"'checkmark-circle'\">checkmark-circle</mat-option>\n <mat-option [value]=\"'alert-circle'\">alert-circle</mat-option>\n <mat-option [value]=\"'alert'\">alert</mat-option>\n <mat-option [value]=\"'flag'\">flag</mat-option>\n </mat-select>\n </mat-form-field>\n </ion-col>\n\n <ion-col>\n <mat-form-field>\n <mat-label>appBadgeSize</mat-label>\n <mat-select [value]=\"$size.value\" (selectionChange)=\"this.$size.next($event.value)\">\n <mat-option [value]=\"'large'\">large</mat-option>\n <mat-option [value]=\"'medium'\">medium</mat-option>\n <mat-option [value]=\"'small'\">small</mat-option>\n </mat-select>\n </mat-form-field>\n </ion-col>\n\n <ion-col>\n <mat-form-field>\n <mat-label>appBadgeFill</mat-label>\n <mat-select [value]=\"$fill.value\" (selectionChange)=\"this.$fill.next($event.value)\">\n <mat-option [value]=\"'clear'\">clear</mat-option>\n <mat-option [value]=\"'solid'\">solid</mat-option>\n </mat-select>\n </mat-form-field>\n </ion-col>\n\n <ion-col>\n <mat-form-field>\n <mat-label>appBadgeHidden</mat-label>\n <mat-select [value]=\"$hidden.value\" (selectionChange)=\"this.$hidden.next($event.value)\">\n <mat-option [value]=\"true\">true</mat-option>\n <mat-option [value]=\"false\">false</mat-option>\n </mat-select>\n </mat-form-field>\n </ion-col>\n </ion-row>\n\n <ion-row>\n <ion-col size=\"auto\">\n <p>mat-raised-button:</p>\n </ion-col>\n <ion-col>\n <button\n mat-raised-button\n color=\"primary\"\n [appBadgeIcon]=\"$icon | async\"\n [appBadgeColor]=\"$color | async | matColor\"\n [appBadgeHidden]=\"$hidden | async\"\n [appBadgeFill]=\"$fill | async\"\n [appBadgeSize]=\"$size | async\"\n appBadgeOverlap=\"true\"\n appBadgePosition=\"below after\"\n >\n {{ userText }}\n </button>\n </ion-col>\n </ion-row>\n\n <ion-row>\n <ion-col size=\"auto\">\n <p>mat-button with mat-label:</p>\n </ion-col>\n <ion-col>\n <button\n mat-button\n color=\"primary\"\n class=\"ion-no-padding\"\n [appBadgeIcon]=\"$icon | async\"\n [appBadgeColor]=\"$color | async | matColor\"\n [appBadgeHidden]=\"$hidden | async\"\n [appBadgeFill]=\"$fill | async\"\n [appBadgeSize]=\"$size | async\"\n matBadgeOverlap=\"true\"\n matBadgePosition=\"above after\"\n >\n {{ userText }}\n </button>\n </ion-col>\n </ion-row>\n\n <h4>Angular Material Badge (standard way)</h4>\n\n <ion-row>\n <ion-col size=\"auto\">\n <p>mat-icon:</p>\n </ion-col>\n <ion-col>\n <mat-icon\n [style.color]=\"'var(--ion-color-secondary)'\"\n [matBadge]=\"'!'\"\n [matBadgeColor]=\"$color | async | matColor\"\n [matBadgeHidden]=\"$hidden | async\"\n [matBadgeSize]=\"$size | async\"\n matBadgeOverlap=\"true\"\n >\n <ion-icon slot=\"icon-only\" [color]=\"'secondary'\" name=\"navigate\"></ion-icon>\n </mat-icon>\n </ion-col>\n </ion-row>\n\n <ion-row>\n <ion-col size=\"auto\">\n <p>mat-button:</p>\n </ion-col>\n <ion-col>\n <button\n mat-raised-button\n color=\"primary\"\n [matBadge]=\"matBadgeContent\"\n [matBadgeColor]=\"$color | async | matColor\"\n [matBadgeHidden]=\"$hidden | async\"\n [matBadgeSize]=\"$size | async\"\n matBadgeOverlap=\"true\"\n matBadgePosition=\"above after\"\n >\n {{ userText }}\n </button>\n </ion-col>\n\n <ion-col>\n <input type=\"text\" [value]=\"matBadgeContent\" (input)=\"onMatBadgeContentChanged($event)\" />\n </ion-col>\n </ion-row>\n\n <ion-row>\n <ion-col size=\"auto\">\n <p>mat-button</p>\n </ion-col>\n <ion-col>\n <button\n mat-button\n color=\"primary\"\n [matBadge]=\"matBadgeContent\"\n [matBadgeColor]=\"$color | async | matColor\"\n [matBadgeHidden]=\"$hidden | async\"\n [matBadgeSize]=\"$size | async\"\n matBadgeOverlap=\"true\"\n matBadgePosition=\"after\"\n >\n {{ userText }}\n </button>\n </ion-col>\n </ion-row>\n</ion-content>\n" }]
47625
+ args: [{ selector: 'mat-badge-test', changeDetection: ChangeDetectionStrategy.OnPush, template: "<ion-header>\r\n <ion-toolbar color=\"primary\">\r\n <ion-buttons slot=\"start\">\r\n <ion-back-button></ion-back-button>\r\n </ion-buttons>\r\n\r\n <ion-title>matBadgeIcon directive</ion-title>\r\n </ion-toolbar>\r\n</ion-header>\r\n\r\n<ion-content class=\"ion-padding\">\r\n <!-- small badge -->\r\n <p>\r\n <ion-text color=\"tertiary\">\r\n <span appBadge appBadgeMatIcon=\"check\" appBadgeSize=\"small\" appBadgeColor=\"accent\" appBadgeOverlap=\"false\">\r\n Small badge\r\n </span>\r\n </ion-text>\r\n </p>\r\n\r\n <!-- small badge with text -->\r\n <p>\r\n <ion-text color=\"tertiary\">\r\n <span [appBadge]=\"0\" appBadgeSize=\"small\" appBadgeColor=\"accent\" appBadgeOverlap=\"false\">\r\n Small badge with text 0\r\n </span>\r\n </ion-text>\r\n </p>\r\n\r\n <!-- medium badge -->\r\n <p>\r\n <ion-text\r\n appBadge\r\n appBadgeMatIcon=\"check\"\r\n appBadgeSize=\"medium\"\r\n [appBadgeColor]=\"'tertiary' | matColor\"\r\n appBadgeOverlap=\"false\"\r\n >\r\n Medium badge\r\n </ion-text>\r\n </p>\r\n\r\n <!-- small badge -->\r\n <p>\r\n <ion-label appBadge appBadgeMatIcon=\"close\" appBadgeSize=\"large\" appBadgeOverlap=\"false\">Large badge</ion-label>\r\n </p>\r\n\r\n <!-- default size badge -->\r\n <p>\r\n <ion-label appBadge appBadgeMatIcon=\"check\" [appBadgeColor]=\"'success' | matColor\" appBadgeOverlap=\"false\">\r\n Badge (no size, no color)\r\n </ion-label>\r\n </p>\r\n\r\n <!-- ion icon -->\r\n <p>\r\n <ion-label appBadge appBadgeIcon=\"checkmark\" [appBadgeColor]=\"'success' | matColor\" appBadgeOverlap=\"false\">\r\n Badge with ion-icon\r\n </ion-label>\r\n </p>\r\n\r\n <!-- ion icon clear -->\r\n <p>\r\n <ion-label\r\n appBadge\r\n appBadgeIcon=\"checkmark-circle\"\r\n [appBadgeColor]=\"'tertiary' | matColor\"\r\n appBadgeFill=\"clear\"\r\n appBadgeOverlap=\"false\"\r\n >\r\n Badge with clear icon\r\n </ion-label>\r\n </p>\r\n\r\n <!-- changing text-->\r\n <ion-row>\r\n <ion-col>\r\n <ion-label\r\n appBadge\r\n appBadgeIcon=\"checkmark-circle\"\r\n [appBadgeColor]=\"'tertiary' | matColor\"\r\n appBadgeFill=\"clear\"\r\n appBadgeOverlap=\"false\"\r\n >\r\n {{ userText }}\r\n </ion-label>\r\n </ion-col>\r\n <ion-col>\r\n <input type=\"text\" [value]=\"userText\" (input)=\"onInputChanged($event)\" />\r\n </ion-col>\r\n </ion-row>\r\n\r\n <ion-row>\r\n <ion-col>Configurable example :</ion-col>\r\n </ion-row>\r\n <ion-row class=\"ion-no-padding\">\r\n <ion-col size=\"auto\">\r\n <mat-icon\r\n [style.color]=\"'var(--ion-color-secondary)'\"\r\n appBadge\r\n [appBadgeIcon]=\"$icon | async\"\r\n [appBadgeColor]=\"$color | async | matColor\"\r\n [appBadgeHidden]=\"$hidden | async\"\r\n [appBadgeFill]=\"$fill | async\"\r\n [appBadgeSize]=\"$size | async\"\r\n appBadgeOverlap=\"true\"\r\n appBadgePosition=\"above before\"\r\n >\r\n <ion-icon slot=\"icon-only\" [color]=\"'secondary'\" name=\"navigate\"></ion-icon>\r\n </mat-icon>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <mat-form-field>\r\n <mat-label>appBadgeColor</mat-label>\r\n <mat-select [value]=\"$color.value\" (selectionChange)=\"this.$color.next($event.value)\">\r\n <mat-option [value]=\"'primary'\">primary</mat-option>\r\n <mat-option [value]=\"'secondary'\">secondary</mat-option>\r\n <mat-option [value]=\"'tertiary'\">tertiary</mat-option>\r\n <mat-option [value]=\"'danger'\">danger</mat-option>\r\n </mat-select>\r\n </mat-form-field>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <mat-form-field>\r\n <mat-label>appBadgeIcon</mat-label>\r\n <mat-select [value]=\"$icon.value\" (selectionChange)=\"this.$icon.next($event.value)\">\r\n <mat-option [value]=\"'checkmark-circle'\">checkmark-circle</mat-option>\r\n <mat-option [value]=\"'alert-circle'\">alert-circle</mat-option>\r\n <mat-option [value]=\"'alert'\">alert</mat-option>\r\n <mat-option [value]=\"'flag'\">flag</mat-option>\r\n </mat-select>\r\n </mat-form-field>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <mat-form-field>\r\n <mat-label>appBadgeSize</mat-label>\r\n <mat-select [value]=\"$size.value\" (selectionChange)=\"this.$size.next($event.value)\">\r\n <mat-option [value]=\"'large'\">large</mat-option>\r\n <mat-option [value]=\"'medium'\">medium</mat-option>\r\n <mat-option [value]=\"'small'\">small</mat-option>\r\n </mat-select>\r\n </mat-form-field>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <mat-form-field>\r\n <mat-label>appBadgeFill</mat-label>\r\n <mat-select [value]=\"$fill.value\" (selectionChange)=\"this.$fill.next($event.value)\">\r\n <mat-option [value]=\"'clear'\">clear</mat-option>\r\n <mat-option [value]=\"'solid'\">solid</mat-option>\r\n </mat-select>\r\n </mat-form-field>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <mat-form-field>\r\n <mat-label>appBadgeHidden</mat-label>\r\n <mat-select [value]=\"$hidden.value\" (selectionChange)=\"this.$hidden.next($event.value)\">\r\n <mat-option [value]=\"true\">true</mat-option>\r\n <mat-option [value]=\"false\">false</mat-option>\r\n </mat-select>\r\n </mat-form-field>\r\n </ion-col>\r\n </ion-row>\r\n\r\n <ion-row>\r\n <ion-col size=\"auto\">\r\n <p>mat-raised-button:</p>\r\n </ion-col>\r\n <ion-col>\r\n <button\r\n mat-raised-button\r\n color=\"primary\"\r\n [appBadgeIcon]=\"$icon | async\"\r\n [appBadgeColor]=\"$color | async | matColor\"\r\n [appBadgeHidden]=\"$hidden | async\"\r\n [appBadgeFill]=\"$fill | async\"\r\n [appBadgeSize]=\"$size | async\"\r\n appBadgeOverlap=\"true\"\r\n appBadgePosition=\"below after\"\r\n >\r\n {{ userText }}\r\n </button>\r\n </ion-col>\r\n </ion-row>\r\n\r\n <ion-row>\r\n <ion-col size=\"auto\">\r\n <p>mat-button with mat-label:</p>\r\n </ion-col>\r\n <ion-col>\r\n <button\r\n mat-button\r\n color=\"primary\"\r\n class=\"ion-no-padding\"\r\n [appBadgeIcon]=\"$icon | async\"\r\n [appBadgeColor]=\"$color | async | matColor\"\r\n [appBadgeHidden]=\"$hidden | async\"\r\n [appBadgeFill]=\"$fill | async\"\r\n [appBadgeSize]=\"$size | async\"\r\n matBadgeOverlap=\"true\"\r\n matBadgePosition=\"above after\"\r\n >\r\n {{ userText }}\r\n </button>\r\n </ion-col>\r\n </ion-row>\r\n\r\n <h4>Angular Material Badge (standard way)</h4>\r\n\r\n <ion-row>\r\n <ion-col size=\"auto\">\r\n <p>mat-icon:</p>\r\n </ion-col>\r\n <ion-col>\r\n <mat-icon\r\n [style.color]=\"'var(--ion-color-secondary)'\"\r\n [matBadge]=\"'!'\"\r\n [matBadgeColor]=\"$color | async | matColor\"\r\n [matBadgeHidden]=\"$hidden | async\"\r\n [matBadgeSize]=\"$size | async\"\r\n matBadgeOverlap=\"true\"\r\n >\r\n <ion-icon slot=\"icon-only\" [color]=\"'secondary'\" name=\"navigate\"></ion-icon>\r\n </mat-icon>\r\n </ion-col>\r\n </ion-row>\r\n\r\n <ion-row>\r\n <ion-col size=\"auto\">\r\n <p>mat-button:</p>\r\n </ion-col>\r\n <ion-col>\r\n <button\r\n mat-raised-button\r\n color=\"primary\"\r\n [matBadge]=\"matBadgeContent\"\r\n [matBadgeColor]=\"$color | async | matColor\"\r\n [matBadgeHidden]=\"$hidden | async\"\r\n [matBadgeSize]=\"$size | async\"\r\n matBadgeOverlap=\"true\"\r\n matBadgePosition=\"above after\"\r\n >\r\n {{ userText }}\r\n </button>\r\n </ion-col>\r\n\r\n <ion-col>\r\n <input type=\"text\" [value]=\"matBadgeContent\" (input)=\"onMatBadgeContentChanged($event)\" />\r\n </ion-col>\r\n </ion-row>\r\n\r\n <ion-row>\r\n <ion-col size=\"auto\">\r\n <p>mat-button</p>\r\n </ion-col>\r\n <ion-col>\r\n <button\r\n mat-button\r\n color=\"primary\"\r\n [matBadge]=\"matBadgeContent\"\r\n [matBadgeColor]=\"$color | async | matColor\"\r\n [matBadgeHidden]=\"$hidden | async\"\r\n [matBadgeSize]=\"$size | async\"\r\n matBadgeOverlap=\"true\"\r\n matBadgePosition=\"after\"\r\n >\r\n {{ userText }}\r\n </button>\r\n </ion-col>\r\n </ion-row>\r\n</ion-content>\r\n" }]
47626
47626
  }], ctorParameters: () => [{ type: i0.ChangeDetectorRef }] });
47627
47627
 
47628
47628
  class DurationTestPage {
@@ -47916,54 +47916,54 @@ class FormFieldCustomControlExample {
47916
47916
  tel: new FormControl(null),
47917
47917
  });
47918
47918
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: FormFieldCustomControlExample, deps: [], target: i0.ɵɵFactoryTarget.Component });
47919
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.13", type: FormFieldCustomControlExample, isStandalone: true, selector: "form-field-custom-control-example", ngImport: i0, template: `
47920
- <ion-header>
47921
- <ion-toolbar color="primary">
47922
- <ion-buttons slot="start">
47923
- <ion-back-button></ion-back-button>
47924
- </ion-buttons>
47925
-
47926
- <ion-title>Custom field test page</ion-title>
47927
- </ion-toolbar>
47928
- </ion-header>
47929
- <ion-content class="ion-padding">
47930
- <div [formGroup]="form">
47931
- <mat-form-field>
47932
- <mat-label>Phone number</mat-label>
47933
- <example-tel-input formControlName="tel" required></example-tel-input>
47934
- <mat-icon matSuffix>phone</mat-icon>
47935
- <mat-hint>Include area code</mat-hint>
47936
- </mat-form-field>
47937
- <p>Entered value: {{ form.valueChanges | async | json }}</p>
47938
- </div>
47939
- </ion-content>
47919
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.13", type: FormFieldCustomControlExample, isStandalone: true, selector: "form-field-custom-control-example", ngImport: i0, template: `
47920
+ <ion-header>
47921
+ <ion-toolbar color="primary">
47922
+ <ion-buttons slot="start">
47923
+ <ion-back-button></ion-back-button>
47924
+ </ion-buttons>
47925
+
47926
+ <ion-title>Custom field test page</ion-title>
47927
+ </ion-toolbar>
47928
+ </ion-header>
47929
+ <ion-content class="ion-padding">
47930
+ <div [formGroup]="form">
47931
+ <mat-form-field>
47932
+ <mat-label>Phone number</mat-label>
47933
+ <example-tel-input formControlName="tel" required></example-tel-input>
47934
+ <mat-icon matSuffix>phone</mat-icon>
47935
+ <mat-hint>Include area code</mat-hint>
47936
+ </mat-form-field>
47937
+ <p>Entered value: {{ form.valueChanges | async | json }}</p>
47938
+ </div>
47939
+ </ion-content>
47940
47940
  `, isInline: true, dependencies: [{ kind: "ngmodule", type: i0.forwardRef(() => FormsModule) }, { kind: "directive", type: i0.forwardRef(() => i1$3.NgControlStatus), selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i0.forwardRef(() => i1$3.NgControlStatusGroup), selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i0.forwardRef(() => i1$3.RequiredValidator), selector: ":not([type=checkbox])[required][formControlName],:not([type=checkbox])[required][formControl],:not([type=checkbox])[required][ngModel]", inputs: ["required"] }, { kind: "ngmodule", type: i0.forwardRef(() => ReactiveFormsModule) }, { kind: "directive", type: i0.forwardRef(() => i1$3.FormGroupDirective), selector: "[formGroup]", inputs: ["formGroup"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: i0.forwardRef(() => i1$3.FormControlName), selector: "[formControlName]", inputs: ["formControlName", "disabled", "ngModel"], outputs: ["ngModelChange"] }, { kind: "ngmodule", type: i0.forwardRef(() => MatFormFieldModule) }, { kind: "component", type: i0.forwardRef(() => i3.MatFormField), selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: i0.forwardRef(() => i3.MatLabel), selector: "mat-label" }, { kind: "directive", type: i0.forwardRef(() => i3.MatHint), selector: "mat-hint", inputs: ["align", "id"] }, { kind: "directive", type: i0.forwardRef(() => i3.MatSuffix), selector: "[matSuffix], [matIconSuffix], [matTextSuffix]", inputs: ["matTextSuffix"] }, { kind: "component", type: i0.forwardRef(() => MyTelInput), selector: "example-tel-input", inputs: ["aria-describedby", "placeholder", "required", "disabled", "value"], outputs: ["valueChange"] }, { kind: "ngmodule", type: i0.forwardRef(() => MatIconModule) }, { kind: "component", type: i0.forwardRef(() => i6$1.MatIcon), selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "pipe", type: i0.forwardRef(() => AsyncPipe), name: "async" }, { kind: "pipe", type: i0.forwardRef(() => JsonPipe), name: "json" }, { kind: "ngmodule", type: i0.forwardRef(() => IonicModule) }, { kind: "component", type: i0.forwardRef(() => i2$1.IonButtons), selector: "ion-buttons", inputs: ["collapse"] }, { kind: "component", type: i0.forwardRef(() => i2$1.IonContent), selector: "ion-content", inputs: ["color", "forceOverscroll", "fullscreen", "scrollEvents", "scrollX", "scrollY"] }, { kind: "component", type: i0.forwardRef(() => i2$1.IonHeader), selector: "ion-header", inputs: ["collapse", "mode", "translucent"] }, { kind: "component", type: i0.forwardRef(() => i2$1.IonTitle), selector: "ion-title", inputs: ["color", "size"] }, { kind: "component", type: i0.forwardRef(() => i2$1.IonToolbar), selector: "ion-toolbar", inputs: ["color", "mode"] }, { kind: "component", type: i0.forwardRef(() => i2$1.IonBackButton), selector: "ion-back-button" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
47941
47941
  }
47942
47942
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: FormFieldCustomControlExample, decorators: [{
47943
47943
  type: Component,
47944
47944
  args: [{
47945
47945
  selector: 'form-field-custom-control-example',
47946
- template: `
47947
- <ion-header>
47948
- <ion-toolbar color="primary">
47949
- <ion-buttons slot="start">
47950
- <ion-back-button></ion-back-button>
47951
- </ion-buttons>
47952
-
47953
- <ion-title>Custom field test page</ion-title>
47954
- </ion-toolbar>
47955
- </ion-header>
47956
- <ion-content class="ion-padding">
47957
- <div [formGroup]="form">
47958
- <mat-form-field>
47959
- <mat-label>Phone number</mat-label>
47960
- <example-tel-input formControlName="tel" required></example-tel-input>
47961
- <mat-icon matSuffix>phone</mat-icon>
47962
- <mat-hint>Include area code</mat-hint>
47963
- </mat-form-field>
47964
- <p>Entered value: {{ form.valueChanges | async | json }}</p>
47965
- </div>
47966
- </ion-content>
47946
+ template: `
47947
+ <ion-header>
47948
+ <ion-toolbar color="primary">
47949
+ <ion-buttons slot="start">
47950
+ <ion-back-button></ion-back-button>
47951
+ </ion-buttons>
47952
+
47953
+ <ion-title>Custom field test page</ion-title>
47954
+ </ion-toolbar>
47955
+ </ion-header>
47956
+ <ion-content class="ion-padding">
47957
+ <div [formGroup]="form">
47958
+ <mat-form-field>
47959
+ <mat-label>Phone number</mat-label>
47960
+ <example-tel-input formControlName="tel" required></example-tel-input>
47961
+ <mat-icon matSuffix>phone</mat-icon>
47962
+ <mat-hint>Include area code</mat-hint>
47963
+ </mat-form-field>
47964
+ <p>Entered value: {{ form.valueChanges | async | json }}</p>
47965
+ </div>
47966
+ </ion-content>
47967
47967
  `,
47968
47968
  standalone: true,
47969
47969
  imports: [FormsModule, ReactiveFormsModule, MatFormFieldModule, forwardRef(() => MyTelInput), MatIconModule, AsyncPipe, JsonPipe, IonicModule],