@fundamental-ngx/core 0.65.0-rc.9 → 0.65.0

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 (28) hide show
  1. package/fesm2022/fundamental-ngx-core-avatar-group.mjs +118 -39
  2. package/fesm2022/fundamental-ngx-core-avatar-group.mjs.map +1 -1
  3. package/fesm2022/fundamental-ngx-core-combobox.mjs +165 -21
  4. package/fesm2022/fundamental-ngx-core-combobox.mjs.map +1 -1
  5. package/fesm2022/fundamental-ngx-core-date-picker.mjs +1 -4
  6. package/fesm2022/fundamental-ngx-core-date-picker.mjs.map +1 -1
  7. package/fesm2022/fundamental-ngx-core-datetime-picker.mjs +21 -0
  8. package/fesm2022/fundamental-ngx-core-datetime-picker.mjs.map +1 -1
  9. package/fesm2022/fundamental-ngx-core-icon.mjs +2 -2
  10. package/fesm2022/fundamental-ngx-core-icon.mjs.map +1 -1
  11. package/fesm2022/fundamental-ngx-core-menu.mjs +63 -2
  12. package/fesm2022/fundamental-ngx-core-menu.mjs.map +1 -1
  13. package/fesm2022/fundamental-ngx-core-multi-combobox.mjs +20 -35
  14. package/fesm2022/fundamental-ngx-core-multi-combobox.mjs.map +1 -1
  15. package/fesm2022/fundamental-ngx-core-popover.mjs +22 -40
  16. package/fesm2022/fundamental-ngx-core-popover.mjs.map +1 -1
  17. package/fesm2022/fundamental-ngx-core-table.mjs +373 -499
  18. package/fesm2022/fundamental-ngx-core-table.mjs.map +1 -1
  19. package/package.json +3 -3
  20. package/schematics/package.json +1 -1
  21. package/types/fundamental-ngx-core-avatar-group.d.ts +52 -19
  22. package/types/fundamental-ngx-core-combobox.d.ts +44 -6
  23. package/types/fundamental-ngx-core-datetime-picker.d.ts +3 -1
  24. package/types/fundamental-ngx-core-menu.d.ts +8 -1
  25. package/types/fundamental-ngx-core-mobile-mode.d.ts +2 -0
  26. package/types/fundamental-ngx-core-multi-combobox.d.ts +1 -1
  27. package/types/fundamental-ngx-core-popover.d.ts +11 -16
  28. package/types/fundamental-ngx-core-table.d.ts +133 -164
@@ -60,6 +60,11 @@ class ComboboxMobileComponent extends MobileModeBase {
60
60
  * List element, which will be rendered inside dialog.
61
61
  */
62
62
  this.childContent = null;
63
+ /** @hidden */
64
+ this._handlingDialogAction = false;
65
+ /** @hidden */
66
+ this._dismissedByAction = false;
67
+ this._component.setMobileModeConfig(this.mobileConfig);
63
68
  }
64
69
  /** @hidden */
65
70
  ngOnInit() {
@@ -67,22 +72,29 @@ class ComboboxMobileComponent extends MobileModeBase {
67
72
  }
68
73
  /** @hidden */
69
74
  handleDismiss() {
70
- this.dialogRef.dismiss();
71
- this._component.dialogDismiss(this._selectedBackup);
75
+ this._handlingDialogAction = true;
76
+ this._component.dialogDismiss();
77
+ this._dismissedByAction = true;
78
+ this._dismissDialog();
79
+ this._handlingDialogAction = false;
72
80
  }
73
81
  /** @hidden */
74
82
  handleApprove() {
75
- this.dialogRef.close();
83
+ this._handlingDialogAction = true;
76
84
  this._component.dialogApprove();
85
+ this._closeDialog();
86
+ this._handlingDialogAction = false;
77
87
  }
78
88
  /** @hidden */
79
89
  _toggleDialog(open) {
80
90
  if (open) {
81
- this._selectedBackup = this._component.getValue();
82
91
  if (!this._dialogService.hasOpenDialogs()) {
83
92
  this._open();
84
93
  }
85
94
  }
95
+ else if (!this._handlingDialogAction) {
96
+ this._closeDialog();
97
+ }
86
98
  }
87
99
  /** @hidden */
88
100
  _listenOnMultiInputOpenChange() {
@@ -92,8 +104,10 @@ class ComboboxMobileComponent extends MobileModeBase {
92
104
  }
93
105
  /** @hidden */
94
106
  _open() {
107
+ this._dismissedByAction = false;
95
108
  this.dialogRef = this._dialogService.open(this.dialogTemplate, {
96
109
  mobile: true,
110
+ focusTrapped: true,
97
111
  ...this.dialogConfig,
98
112
  backdropClickCloseable: false,
99
113
  container: this._elementRef.nativeElement,
@@ -101,15 +115,31 @@ class ComboboxMobileComponent extends MobileModeBase {
101
115
  });
102
116
  this._focusInputElementOnceOpened();
103
117
  const refSub = this.dialogRef.afterClosed.subscribe({
104
- error: (type) => {
105
- if (type === 'escape') {
106
- this._component.dialogDismiss(this._selectedBackup);
107
- refSub.unsubscribe();
118
+ error: () => {
119
+ if (this.dialogRef.status() === 'dismissed' && !this._dismissedByAction) {
120
+ this._component.dialogDismiss();
108
121
  }
122
+ refSub.unsubscribe();
109
123
  }
110
124
  });
111
125
  }
112
126
  /** @hidden */
127
+ _closeDialog() {
128
+ if (this._canCloseDialog()) {
129
+ this.dialogRef.close();
130
+ }
131
+ }
132
+ /** @hidden */
133
+ _dismissDialog() {
134
+ if (this._canCloseDialog()) {
135
+ this.dialogRef.dismiss();
136
+ }
137
+ }
138
+ /** @hidden */
139
+ _canCloseDialog() {
140
+ return (this.dialogRef?.isOpen() || this.dialogRef?.status() === 'pending') && !this.dialogRef.isClosed();
141
+ }
142
+ /** @hidden */
113
143
  _focusInputElementOnceOpened() {
114
144
  this.dialogRef.afterLoaded
115
145
  .pipe(observeOn(asyncScheduler), // making the listener async
@@ -127,7 +157,7 @@ class ComboboxMobileComponent extends MobileModeBase {
127
157
  });
128
158
  }
129
159
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: ComboboxMobileComponent, deps: [{ token: COMBOBOX_COMPONENT }], target: i0.ɵɵFactoryTarget.Component }); }
130
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.5", type: ComboboxMobileComponent, isStandalone: true, selector: "fd-combobox-mobile", viewQueries: [{ propertyName: "dialogTemplate", first: true, predicate: ["dialogTemplate"], descendants: true }], usesInheritance: true, ngImport: i0, template: "<ng-template [fdDialogTemplate] let-dialog let-dialogConfig=\"dialogConfig\" #dialogTemplate>\n <fd-dialog [dialogConfig]=\"dialogConfig\" [dialogRef]=\"dialog\">\n <fd-dialog-header>\n @if (mobileConfig.title) {\n <h1 fd-title>{{ mobileConfig.title }}</h1>\n }\n @if (mobileConfig.hasCloseButton) {\n <button title=\"Close\" fd-dialog-close-button [mobile]=\"true\" (click)=\"handleDismiss()\"></button>\n }\n <ng-template fdkTemplate=\"subheader\">\n <div fd-bar-middle>\n <fd-bar-element [fullWidth]=\"true\">\n <ng-template [ngTemplateOutlet]=\"childContent?.controlTemplate || null\"></ng-template>\n </fd-bar-element>\n </div>\n </ng-template>\n </fd-dialog-header>\n <fd-dialog-body>\n <ng-template [ngTemplateOutlet]=\"childContent?.listTemplate || null\"></ng-template>\n </fd-dialog-body>\n <fd-dialog-footer>\n @if (mobileConfig.approveButtonText) {\n <fd-button-bar fdType=\"emphasized\" [label]=\"mobileConfig.approveButtonText!\" (click)=\"handleApprove()\">\n </fd-button-bar>\n }\n @if (mobileConfig.cancelButtonText) {\n <fd-button-bar fdkInitialFocus [label]=\"mobileConfig.cancelButtonText!\" (click)=\"handleDismiss()\">\n </fd-button-bar>\n }\n </fd-dialog-footer>\n </fd-dialog>\n</ng-template>\n", dependencies: [{ kind: "directive", type: TemplateDirective, selector: "[fdkTemplate]", inputs: ["fdkTemplate"] }, { kind: "directive", type: BarMiddleDirective, selector: "[fd-bar-middle]", inputs: ["stackContentsVertically"] }, { kind: "directive", type: BarElementDirective, selector: "fd-bar-element", inputs: ["fullWidth"] }, { kind: "component", type: ButtonBarComponent, selector: "fd-button-bar", inputs: ["fullWidth", "fdType", "title", "ariaLabelledby", "id"] }, { kind: "component", type: DialogHeaderComponent, selector: "fd-dialog-header", inputs: ["inShellbar"] }, { kind: "component", type: DialogCloseButtonComponent, selector: "[fd-dialog-close-button]", inputs: ["mobile", "title", "ariaLabel"] }, { kind: "component", type: DialogComponent, selector: "fd-dialog", inputs: ["class", "dialogRef", "dialogConfig"] }, { kind: "component", type: DialogBodyComponent, selector: "fd-dialog-body", inputs: ["disablePaddings"] }, { kind: "component", type: DialogFooterComponent, selector: "fd-dialog-footer" }, { kind: "component", type: TitleComponent, selector: "[fd-title], [fdTitle]", inputs: ["twoLineClamp", "headerSize", "wrap"], exportAs: ["fd-title"] }, { kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "directive", type: InitialFocusDirective, selector: "[fdkInitialFocus]", inputs: ["fdkInitialFocus", "enabled", "focusLastElement"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
160
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.5", type: ComboboxMobileComponent, isStandalone: true, selector: "fd-combobox-mobile", viewQueries: [{ propertyName: "dialogTemplate", first: true, predicate: ["dialogTemplate"], descendants: true }], usesInheritance: true, ngImport: i0, template: "<ng-template [fdDialogTemplate] let-dialog let-dialogConfig=\"dialogConfig\" #dialogTemplate>\n <fd-dialog [dialogConfig]=\"dialogConfig\" [dialogRef]=\"dialog\">\n <fd-dialog-header>\n @if (mobileConfig.title) {\n <h1 fd-title>{{ mobileConfig.title }}</h1>\n }\n @if (mobileConfig.hasCloseButton) {\n <button title=\"Close\" fd-dialog-close-button [mobile]=\"true\" (click)=\"handleDismiss()\"></button>\n }\n <ng-template fdkTemplate=\"subheader\">\n <div fd-bar-middle>\n <fd-bar-element [fullWidth]=\"true\">\n <ng-template [ngTemplateOutlet]=\"childContent?.controlTemplate || null\"></ng-template>\n </fd-bar-element>\n </div>\n </ng-template>\n </fd-dialog-header>\n <fd-dialog-body>\n @if (mobileConfig.instruction) {\n <p data-dialog-instruction>{{ mobileConfig.instruction }}</p>\n }\n <ng-template [ngTemplateOutlet]=\"childContent?.listTemplate || null\"></ng-template>\n </fd-dialog-body>\n <fd-dialog-footer>\n @if (_component.hasMobileApproveAction()) {\n <fd-button-bar fdType=\"emphasized\" [label]=\"mobileConfig.approveButtonText!\" (click)=\"handleApprove()\">\n </fd-button-bar>\n }\n @if (mobileConfig.cancelButtonText) {\n <fd-button-bar fdkInitialFocus [label]=\"mobileConfig.cancelButtonText!\" (click)=\"handleDismiss()\">\n </fd-button-bar>\n }\n </fd-dialog-footer>\n </fd-dialog>\n</ng-template>\n", dependencies: [{ kind: "directive", type: TemplateDirective, selector: "[fdkTemplate]", inputs: ["fdkTemplate"] }, { kind: "directive", type: BarMiddleDirective, selector: "[fd-bar-middle]", inputs: ["stackContentsVertically"] }, { kind: "directive", type: BarElementDirective, selector: "fd-bar-element", inputs: ["fullWidth"] }, { kind: "component", type: ButtonBarComponent, selector: "fd-button-bar", inputs: ["fullWidth", "fdType", "title", "ariaLabelledby", "id"] }, { kind: "component", type: DialogHeaderComponent, selector: "fd-dialog-header", inputs: ["inShellbar"] }, { kind: "component", type: DialogCloseButtonComponent, selector: "[fd-dialog-close-button]", inputs: ["mobile", "title", "ariaLabel"] }, { kind: "component", type: DialogComponent, selector: "fd-dialog", inputs: ["class", "dialogRef", "dialogConfig"] }, { kind: "component", type: DialogBodyComponent, selector: "fd-dialog-body", inputs: ["disablePaddings"] }, { kind: "component", type: DialogFooterComponent, selector: "fd-dialog-footer" }, { kind: "component", type: TitleComponent, selector: "[fd-title], [fdTitle]", inputs: ["twoLineClamp", "headerSize", "wrap"], exportAs: ["fd-title"] }, { kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "directive", type: InitialFocusDirective, selector: "[fdkInitialFocus]", inputs: ["fdkInitialFocus", "enabled", "focusLastElement"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
131
161
  }
132
162
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: ComboboxMobileComponent, decorators: [{
133
163
  type: Component,
@@ -146,7 +176,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
146
176
  TemplateDirective,
147
177
  NgTemplateOutlet,
148
178
  InitialFocusDirective
149
- ], template: "<ng-template [fdDialogTemplate] let-dialog let-dialogConfig=\"dialogConfig\" #dialogTemplate>\n <fd-dialog [dialogConfig]=\"dialogConfig\" [dialogRef]=\"dialog\">\n <fd-dialog-header>\n @if (mobileConfig.title) {\n <h1 fd-title>{{ mobileConfig.title }}</h1>\n }\n @if (mobileConfig.hasCloseButton) {\n <button title=\"Close\" fd-dialog-close-button [mobile]=\"true\" (click)=\"handleDismiss()\"></button>\n }\n <ng-template fdkTemplate=\"subheader\">\n <div fd-bar-middle>\n <fd-bar-element [fullWidth]=\"true\">\n <ng-template [ngTemplateOutlet]=\"childContent?.controlTemplate || null\"></ng-template>\n </fd-bar-element>\n </div>\n </ng-template>\n </fd-dialog-header>\n <fd-dialog-body>\n <ng-template [ngTemplateOutlet]=\"childContent?.listTemplate || null\"></ng-template>\n </fd-dialog-body>\n <fd-dialog-footer>\n @if (mobileConfig.approveButtonText) {\n <fd-button-bar fdType=\"emphasized\" [label]=\"mobileConfig.approveButtonText!\" (click)=\"handleApprove()\">\n </fd-button-bar>\n }\n @if (mobileConfig.cancelButtonText) {\n <fd-button-bar fdkInitialFocus [label]=\"mobileConfig.cancelButtonText!\" (click)=\"handleDismiss()\">\n </fd-button-bar>\n }\n </fd-dialog-footer>\n </fd-dialog>\n</ng-template>\n" }]
179
+ ], template: "<ng-template [fdDialogTemplate] let-dialog let-dialogConfig=\"dialogConfig\" #dialogTemplate>\n <fd-dialog [dialogConfig]=\"dialogConfig\" [dialogRef]=\"dialog\">\n <fd-dialog-header>\n @if (mobileConfig.title) {\n <h1 fd-title>{{ mobileConfig.title }}</h1>\n }\n @if (mobileConfig.hasCloseButton) {\n <button title=\"Close\" fd-dialog-close-button [mobile]=\"true\" (click)=\"handleDismiss()\"></button>\n }\n <ng-template fdkTemplate=\"subheader\">\n <div fd-bar-middle>\n <fd-bar-element [fullWidth]=\"true\">\n <ng-template [ngTemplateOutlet]=\"childContent?.controlTemplate || null\"></ng-template>\n </fd-bar-element>\n </div>\n </ng-template>\n </fd-dialog-header>\n <fd-dialog-body>\n @if (mobileConfig.instruction) {\n <p data-dialog-instruction>{{ mobileConfig.instruction }}</p>\n }\n <ng-template [ngTemplateOutlet]=\"childContent?.listTemplate || null\"></ng-template>\n </fd-dialog-body>\n <fd-dialog-footer>\n @if (_component.hasMobileApproveAction()) {\n <fd-button-bar fdType=\"emphasized\" [label]=\"mobileConfig.approveButtonText!\" (click)=\"handleApprove()\">\n </fd-button-bar>\n }\n @if (mobileConfig.cancelButtonText) {\n <fd-button-bar fdkInitialFocus [label]=\"mobileConfig.cancelButtonText!\" (click)=\"handleDismiss()\">\n </fd-button-bar>\n }\n </fd-dialog-footer>\n </fd-dialog>\n</ng-template>\n" }]
150
180
  }], ctorParameters: () => [{ type: undefined, decorators: [{
151
181
  type: Inject,
152
182
  args: [COMBOBOX_COMPONENT]
@@ -355,7 +385,7 @@ class ComboboxComponent {
355
385
  fromEvent(document, 'mousedown')
356
386
  .pipe(takeUntilDestroyed(this._destroyRef))
357
387
  .subscribe((event) => {
358
- if (!this.closeOnOutsideClick) {
388
+ if (this.mobile || !this.closeOnOutsideClick) {
359
389
  return;
360
390
  }
361
391
  const target = event.target;
@@ -469,15 +499,35 @@ class ComboboxComponent {
469
499
  this.itemClicked.emit({ item: value, index });
470
500
  }
471
501
  }
472
- /** Handle dialog dismissing, closes popover and sets backup data. */
502
+ /**
503
+ * @hidden
504
+ * Receives the resolved mobile configuration from the mobile wrapper.
505
+ */
506
+ setMobileModeConfig(config) {
507
+ this._mobileModeConfig = config;
508
+ }
509
+ /**
510
+ * @hidden
511
+ * Whether the resolved mobile configuration provides a usable Approve action.
512
+ */
513
+ hasMobileApproveAction() {
514
+ return !!this._mobileModeConfig?.approveButtonText?.trim();
515
+ }
516
+ /** Handle dialog dismissing, restoring an unconfirmed mobile selection when needed. */
473
517
  dialogDismiss(term) {
474
- this.inputText = this.displayFn(term);
475
- this.setValue(term);
476
- this._lastConfirmedValue = term;
518
+ if (this._isMobileConfirmationMode()) {
519
+ this._restoreMobileConfirmationSnapshot();
520
+ }
521
+ else if (term !== undefined) {
522
+ this.inputText = this.displayFn(term);
523
+ this.setValue(term);
524
+ this._lastConfirmedValue = term;
525
+ }
477
526
  this.isOpenChangeHandle(false);
478
527
  }
479
528
  /** Handle dialog approval, closes popover and propagates data changes. */
480
529
  dialogApprove() {
530
+ this._confirmMobileSelection();
481
531
  this._propagateChange();
482
532
  this.isOpenChangeHandle(false);
483
533
  }
@@ -534,6 +584,9 @@ class ComboboxComponent {
534
584
  this.searchInputElement.nativeElement.value = this.inputTextValue;
535
585
  }
536
586
  this._lastConfirmedValue = valueToDisplay;
587
+ if (this.open && this._isMobileConfirmationMode()) {
588
+ this._captureMobileConfirmationSnapshot();
589
+ }
537
590
  this._cdRef.markForCheck();
538
591
  }
539
592
  /** @hidden */
@@ -578,6 +631,9 @@ class ComboboxComponent {
578
631
  if (this.mobile && !this.open) {
579
632
  this._resetDisplayedValues();
580
633
  }
634
+ if (isOpen && !this.open && this._isMobileConfirmationMode()) {
635
+ this._captureMobileConfirmationSnapshot();
636
+ }
581
637
  if (this.open !== isOpen) {
582
638
  this.open = isOpen;
583
639
  this.openChange.emit(isOpen);
@@ -603,6 +659,10 @@ class ComboboxComponent {
603
659
  /** Method that handles complete event from auto complete directive, setting the new value, and closing popover */
604
660
  handleAutoComplete(event) {
605
661
  if (this.inputText !== event.term) {
662
+ const matchingValues = this._getOptionObjectByDisplayedValue(event.term);
663
+ if (matchingValues.length === 1) {
664
+ this._lastConfirmedValue = matchingValues[0];
665
+ }
606
666
  this.inputText = event.term;
607
667
  this.handleSearchTermChange();
608
668
  }
@@ -634,6 +694,30 @@ class ComboboxComponent {
634
694
  }
635
695
  /** @hidden */
636
696
  _close() {
697
+ const completedValue = this.tabOutStrategy === 'closeAndSelect' ? this._getCompletedAutocompleteValue() : undefined;
698
+ if (completedValue !== undefined) {
699
+ if (completedValue !== this._lastConfirmedValue) {
700
+ this._commitCompletedAutocompleteValue(completedValue);
701
+ }
702
+ if (this.open) {
703
+ this.isOpenChangeHandle(false);
704
+ }
705
+ this.searchInputElement.nativeElement.focus();
706
+ return;
707
+ }
708
+ if (this.tabOutStrategy === 'closeAndSelect' && !this.communicateByObject) {
709
+ this.searchInputElement.nativeElement.value = this.inputText;
710
+ this.isOpenChangeHandle(false);
711
+ this.searchInputElement.nativeElement.focus();
712
+ return;
713
+ }
714
+ // When autoComplete is disabled, the user is in free-text mode.
715
+ // Typed text is intentional and must not be reverted on close.
716
+ if (!this.autoComplete) {
717
+ this._lastConfirmedValue = this.inputText;
718
+ this.isOpenChangeHandle(false);
719
+ return;
720
+ }
637
721
  const revertText = this._lastConfirmedValue != null ? this.displayFn(this._lastConfirmedValue) : '';
638
722
  this.inputText = revertText;
639
723
  this.searchInputElement.nativeElement.value = revertText;
@@ -664,6 +748,26 @@ class ComboboxComponent {
664
748
  const expected = this._lastConfirmedValue != null ? this.displayFn(this._lastConfirmedValue) : '';
665
749
  return this.inputText !== expected;
666
750
  }
751
+ /** @hidden */
752
+ _getCompletedAutocompleteValue() {
753
+ const nativeInput = this.searchInputElement.nativeElement;
754
+ const nativeValue = nativeInput.value;
755
+ const hasSelectedSuffix = nativeValue !== this.inputText &&
756
+ nativeInput.selectionStart === this.inputText.length &&
757
+ nativeInput.selectionEnd === nativeValue.length;
758
+ if (nativeValue !== this.inputText && !hasSelectedSuffix) {
759
+ return;
760
+ }
761
+ const matchingValues = this._getOptionObjectByDisplayedValue(nativeValue);
762
+ return matchingValues.length === 1 ? matchingValues[0] : undefined;
763
+ }
764
+ /** @hidden */
765
+ _commitCompletedAutocompleteValue(value) {
766
+ this._lastConfirmedValue = value;
767
+ this.setValue(value);
768
+ this.inputText = this.displayFn(value);
769
+ this.searchInputElement.nativeElement.value = this.inputText;
770
+ }
667
771
  /** Method that picks other value moved from current one by offset, called only when combobox is closed */
668
772
  _chooseOtherItem(offset) {
669
773
  const activeValue = this._getOptionObjectByDisplayedValue(this.inputTextValue)[0];
@@ -708,19 +812,23 @@ class ComboboxComponent {
708
812
  }
709
813
  /** @hidden */
710
814
  _handleClickActions(term, shouldClosePopover = true) {
711
- if (this.closeOnSelect && shouldClosePopover) {
712
- this.isOpenChangeHandle(false);
815
+ const confirmationMode = this._isMobileConfirmationMode();
816
+ if (!confirmationMode) {
817
+ this._lastConfirmedValue = term;
713
818
  }
714
- this._lastConfirmedValue = term;
715
819
  if (this.fillOnSelect) {
716
820
  this.setValue(term);
717
- this.inputText = this.displayFn(term);
718
- this.searchInputElement.nativeElement.value = this.inputText;
821
+ const displayText = this.displayFn(term);
822
+ this.searchInputElement.nativeElement.value = displayText;
823
+ this.inputText = displayText;
719
824
  this._cdRef.detectChanges();
720
- if (this.mobile) {
825
+ if (this.mobile && !confirmationMode) {
721
826
  this._propagateChange();
722
827
  }
723
828
  }
829
+ if (!confirmationMode && this.closeOnSelect && shouldClosePopover) {
830
+ this.isOpenChangeHandle(false);
831
+ }
724
832
  if (shouldClosePopover) {
725
833
  this.handleSearchTermChange();
726
834
  }
@@ -730,6 +838,42 @@ class ComboboxComponent {
730
838
  return this.dropdownValues.filter((value) => this.displayFn(value) === displayValue);
731
839
  }
732
840
  /** @hidden */
841
+ _isMobileConfirmationMode() {
842
+ return this.mobile && this.hasMobileApproveAction();
843
+ }
844
+ /** @hidden */
845
+ _captureMobileConfirmationSnapshot() {
846
+ this._mobileConfirmationSnapshot = {
847
+ inputText: this.inputTextValue,
848
+ nativeInputValue: this.searchInputElement?.nativeElement.value ?? this.inputTextValue,
849
+ value: this._value,
850
+ lastConfirmedValue: this._lastConfirmedValue
851
+ };
852
+ }
853
+ /** @hidden */
854
+ _restoreMobileConfirmationSnapshot() {
855
+ const snapshot = this._mobileConfirmationSnapshot;
856
+ if (!snapshot) {
857
+ return;
858
+ }
859
+ this.inputText = snapshot.inputText;
860
+ this._value = snapshot.value;
861
+ this._lastConfirmedValue = snapshot.lastConfirmedValue;
862
+ if (this.searchInputElement?.nativeElement) {
863
+ this.searchInputElement.nativeElement.value = snapshot.nativeInputValue;
864
+ }
865
+ this._cdRef.markForCheck();
866
+ }
867
+ /** @hidden */
868
+ _confirmMobileSelection() {
869
+ if (!this._isMobileConfirmationMode()) {
870
+ return;
871
+ }
872
+ const selectedValues = this._getOptionObjectByDisplayedValue(this.inputText);
873
+ this._lastConfirmedValue =
874
+ this.communicateByObject && selectedValues.length === 1 ? selectedValues[0] : this.inputText;
875
+ }
876
+ /** @hidden */
733
877
  _refreshDisplayedValues() {
734
878
  if (this.inputText) {
735
879
  this.displayedValues = this.filterFn(this.dropdownValues, this.inputText);