@snabcentr/client-ui 4.9.2 → 4.11.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 (23) hide show
  1. package/esm2022/pages/frequently-asked-questions/sc-faq-query-params.mjs +5 -0
  2. package/esm2022/pages/frequently-asked-questions/sc-get-faq-group-query-params.mjs +14 -0
  3. package/esm2022/pages/frequently-asked-questions-group-selector/sc-frequently-asked-questions-group-selector.component.mjs +46 -17
  4. package/esm2022/pages/frequently-asked-questions-with-groups/sc-frequently-asked-questions-with-groups.component.mjs +29 -33
  5. package/esm2022/pages/index.mjs +4 -1
  6. package/esm2022/pages/news-list/sc-news-list.component.mjs +90 -0
  7. package/esm2022/pagination/index.mjs +2 -0
  8. package/esm2022/pagination/sc-pagination-links/sc-pagination-links.component.mjs +99 -0
  9. package/esm2022/public-api.mjs +2 -1
  10. package/fesm2022/snabcentr-client-ui.mjs +253 -46
  11. package/fesm2022/snabcentr-client-ui.mjs.map +1 -1
  12. package/package.json +2 -2
  13. package/pages/frequently-asked-questions/sc-faq-query-params.d.ts +4 -0
  14. package/pages/frequently-asked-questions/sc-get-faq-group-query-params.d.ts +10 -0
  15. package/pages/frequently-asked-questions-group-selector/sc-frequently-asked-questions-group-selector.component.d.ts +23 -4
  16. package/pages/frequently-asked-questions-with-groups/sc-frequently-asked-questions-with-groups.component.d.ts +14 -16
  17. package/pages/index.d.ts +3 -0
  18. package/pages/news-list/sc-news-list.component.d.ts +57 -0
  19. package/pagination/index.d.ts +1 -0
  20. package/pagination/sc-pagination-links/sc-pagination-links.component.d.ts +60 -0
  21. package/public-api.d.ts +1 -0
  22. package/release_notes.tmp +8 -3
  23. package/styles/tailwind/tailwind.scss +4 -4
@@ -1,20 +1,20 @@
1
1
  import * as i0 from '@angular/core';
2
2
  import { InjectionToken, inject, Injectable, NgZone, signal, EventEmitter, ChangeDetectorRef, Directive, Input, Output, Pipe, ElementRef, HostListener, Renderer2, ContentChildren, NgModule, input, computed, Component, ChangeDetectionStrategy, Inject, HostBinding, model, output, SkipSelf, DestroyRef, effect, ContentChild, ViewChild, viewChild, Optional, contentChild, TemplateRef, forwardRef } from '@angular/core';
3
3
  import * as i1 from '@snabcentr/client-core';
4
- import { ScContactsService, ScUserService, ScLocationsService, ScAuthService, SEARCH_TERM, ScUnitsHelper, ScImageHelper, SC_PATH_IMAGE_NOT_FOUND, ScImage, ScPhoneService, ScUserMetrikaService, ScUserMetrikaGoalsEnum, IS_RUNNING_ON_TERMINAL, ScVCardService, ScVerificationService, ScISuggestionType, SC_MIN_LENGTH_SEARCH_TERM, ScConvertersService, ScOpfList, ScReferencesService, ScContragentService, ScBannerService, ScMediaImageTransformerPipe, ScCartService, ScUploadedFile, loadingPlaceholder, SC_ORDER_LOADER, ScMimeTypes, ScCatalogService, SC_URLS, IS_SERVER, ScWarehouseService, SEARCH_TERM_PROVIDERS, ScPaginationService, SC_NEXT_PAGE_PAGINATION_CLICK, SC_PRODUCT_PAGINATION_OPTIONS, ScCatalogFilterService, ScIdOrSlugPipe, SC_CATEGORY_INFO, ScConfiguratorService, RESPONSE, ScIconTypesEnum, ScDocumentInfoTypesEnum, ScDeliveryAddressService, ScOrdersService, ScUIService, SC_USER_INFO as SC_USER_INFO$1, ScPaymentType, ScDeliveryType, TERMINAL_PROVIDERS, ScOrderDraftsService, ScRouteKeys, ScSeoService, scOrderIsLoaded, ScFrequentlyAskedQuestionsService, SchemaOrgFactory, SC_COMPANY_INFO, ScFeedbackService } from '@snabcentr/client-core';
4
+ import { ScContactsService, ScUserService, ScLocationsService, ScAuthService, SEARCH_TERM, ScUnitsHelper, ScImageHelper, SC_PATH_IMAGE_NOT_FOUND, ScImage, ScPhoneService, ScUserMetrikaService, ScUserMetrikaGoalsEnum, IS_RUNNING_ON_TERMINAL, ScVCardService, ScVerificationService, ScISuggestionType, SC_MIN_LENGTH_SEARCH_TERM, ScConvertersService, ScOpfList, ScReferencesService, ScContragentService, ScBannerService, ScMediaImageTransformerPipe, ScCartService, ScUploadedFile, loadingPlaceholder, SC_ORDER_LOADER, ScMimeTypes, ScCatalogService, SC_URLS, IS_SERVER, ScWarehouseService, SEARCH_TERM_PROVIDERS, ScPaginationService, SC_NEXT_PAGE_PAGINATION_CLICK, SC_PRODUCT_PAGINATION_OPTIONS, ScCatalogFilterService, ScIdOrSlugPipe, SC_CATEGORY_INFO, ScConfiguratorService, RESPONSE, ScIconTypesEnum, ScDocumentInfoTypesEnum, ScDeliveryAddressService, ScOrdersService, ScUIService, SC_USER_INFO as SC_USER_INFO$1, ScPaymentType, ScDeliveryType, TERMINAL_PROVIDERS, ScOrderDraftsService, ScRouteKeys, ScSeoService, scOrderIsLoaded, SC_PAGE_QUERY_PARAM, ScFrequentlyAskedQuestionsService, SchemaOrgFactory, scGetPageQueryParamChanges, ScNewsService, SC_COMPANY_INFO, ScFeedbackService } from '@snabcentr/client-core';
5
5
  import * as i5$1 from 'rxjs';
6
6
  import { EMPTY, BehaviorSubject, switchMap, of, shareReplay, map, Subject, filter, tap, catchError, finalize, startWith, share, timer, scan, takeWhile, endWith, distinctUntilChanged, debounceTime, throwError, combineLatest, Observable, pairwise, Subscription, merge, skip, from, concatMap, noop, first, retry } from 'rxjs';
7
7
  import { WA_WINDOW } from '@ng-web-apis/common';
8
8
  import { takeUntilDestroyed, toSignal, outputFromObservable, toObservable } from '@angular/core/rxjs-interop';
9
9
  import * as i4$1 from '@taiga-ui/cdk';
10
- import { TuiDay, TuiTime, TuiValueTransformer, TUI_IS_MOBILE, tuiControlValue, tuiIsPresent, tuiMarkControlAsTouchedAndValidate, tuiIsFalsy, TuiAutoFocus, TuiRepeatTimes, TuiHovered, TuiDayRange, TuiMonth, tuiPure, tuiProvide, TuiValidationError, TUI_WINDOW_SIZE, TUI_TRUE_HANDLER } from '@taiga-ui/cdk';
10
+ import { TuiDay, TuiTime, TuiValueTransformer, TUI_IS_MOBILE, tuiControlValue, tuiIsPresent, tuiMarkControlAsTouchedAndValidate, tuiIsFalsy, TuiAutoFocus, TuiRepeatTimes, TuiHovered, TuiDayRange, TuiMonth, tuiPure, tuiProvide, TuiValidationError, tuiClamp, TUI_WINDOW_SIZE, TUI_TRUE_HANDLER } from '@taiga-ui/cdk';
11
11
  import * as i2$1 from '@taiga-ui/kit';
12
- import { TUI_DATE_VALUE_TRANSFORMER, TuiPreview, TuiAvatar, TuiAccordionItem, TuiElasticContainer, TuiAccordion, TuiFieldErrorPipe, TuiFilterByInputPipe, TuiStringifyContentPipe, TuiDataListWrapper, TuiButtonLoading, TuiSortCountriesPipe, TuiStepper, TuiCarousel, TuiPush, TuiCheckbox, TuiFiles, TuiChip, TuiInputNumber, TuiBadge, TuiTooltip, TuiHighlight, TuiLineClamp, TuiFade, TuiRange, tuiInputNumberOptionsProvider, TuiDataListWrapperComponent, TuiChevron, TuiSelect, TuiInputSlider, TuiTreeService, TuiTreeItemContent, TUI_TREE_START, TUI_TREE_CONTENT, TUI_TREE_LOADING, TUI_TREE_LOADER, TuiTree, TuiPreviewDialogService, tuiFilesAccepted, TuiInputFiles, TuiInputFilesDirective, TuiFilesComponent, TuiFile, TuiFileRejectedPipe, TUI_CONFIRM, tuiItemsHandlersProvider as tuiItemsHandlersProvider$1, TuiPagination, TuiAccordionDirective, TuiAccordionItemContent } from '@taiga-ui/kit';
12
+ import { TUI_DATE_VALUE_TRANSFORMER, TuiPreview, TuiAvatar, TuiAccordionItem, TuiElasticContainer, TuiAccordion, TuiFieldErrorPipe, TuiFilterByInputPipe, TuiStringifyContentPipe, TuiDataListWrapper, TuiButtonLoading, TuiSortCountriesPipe, TuiStepper, TuiCarousel, TuiPush, TuiCheckbox, TuiFiles, TuiChip, TuiInputNumber, TuiBadge, TuiTooltip, TuiHighlight, TuiLineClamp, TuiFade, TuiRange, tuiInputNumberOptionsProvider, TuiDataListWrapperComponent, TuiChevron, TuiSelect, TuiInputSlider, TuiTreeService, TuiTreeItemContent, TUI_TREE_START, TUI_TREE_CONTENT, TUI_TREE_LOADING, TUI_TREE_LOADER, TuiTree, TuiPreviewDialogService, tuiFilesAccepted, TuiInputFiles, TuiInputFilesDirective, TuiFilesComponent, TuiFile, TuiFileRejectedPipe, TUI_CONFIRM, tuiItemsHandlersProvider as tuiItemsHandlersProvider$1, TUI_PAGINATION_TEXTS, TuiAccordionDirective, TuiAccordionItemContent } from '@taiga-ui/kit';
13
13
  import { HttpClient, HttpErrorResponse } from '@angular/common/http';
14
14
  import * as i1$1 from '@angular/forms';
15
15
  import { FormControl, FormGroupDirective, NgControl, FormGroup, Validators, FormArray, FormsModule, ReactiveFormsModule } from '@angular/forms';
16
16
  import * as i1$2 from '@taiga-ui/core';
17
- import { TuiButton, TuiDialog, TuiDialogService, TuiLink, TuiFallbackSrcPipe, TuiInitialsPipe, TuiIcon, TuiAppearance, TuiWithAppearance, TuiIcons, TuiWithIcons, TUI_DATA_LIST_HOST, tuiDropdownOptionsProvider, TuiLabel, TuiError, TuiLoader, TuiDataList, TuiNotification, TuiTextfield, TuiTitle, TuiNumberFormat, TuiHint, TUI_MONTHS, TuiScrollbar, tuiNumberFormatProvider, tuiItemsHandlersProvider, tuiTextfieldOptionsProvider, tuiHintOptionsProvider, TuiFormatNumberPipe, TuiHintDriver, TuiHintHover, TuiHintPosition, TuiHintDirective, TuiDataListComponent, TuiOption, TUI_BUTTON_OPTIONS, TUI_BUTTON_DEFAULT_OPTIONS, TuiSurface, tuiFadeIn } from '@taiga-ui/core';
17
+ import { TuiButton, TuiDialog, TuiDialogService, TuiLink, TuiFallbackSrcPipe, TuiInitialsPipe, TuiIcon, TuiAppearance, TuiWithAppearance, TuiIcons, TuiWithIcons, TUI_DATA_LIST_HOST, tuiDropdownOptionsProvider, TuiLabel, TuiError, TuiLoader, TuiDataList, TuiNotification, TuiTextfield, TuiTitle, TuiNumberFormat, TuiHint, TUI_MONTHS, TuiScrollbar, tuiNumberFormatProvider, tuiItemsHandlersProvider, tuiTextfieldOptionsProvider, tuiHintOptionsProvider, TuiFormatNumberPipe, TuiHintDriver, TuiHintHover, TuiHintPosition, TuiHintDirective, TuiDataListComponent, TuiOption, TUI_BUTTON_OPTIONS, TUI_BUTTON_DEFAULT_OPTIONS, TUI_SPIN_ICONS, TuiSurface, tuiFadeIn } from '@taiga-ui/core';
18
18
  import { isValidPhoneNumber } from 'libphonenumber-js/max';
19
19
  import * as i4 from '@taiga-ui/legacy/components/primitive-textfield';
20
20
  import * as i3 from '@taiga-ui/legacy';
@@ -9454,6 +9454,11 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
9454
9454
  }]
9455
9455
  }] });
9456
9456
 
9457
+ /**
9458
+ * Наименование query-параметра идентификатора группы часто задаваемых вопросов.
9459
+ */
9460
+ const SC_FAQ_GROUP_QUERY_PARAM = 'group';
9461
+
9457
9462
  /**
9458
9463
  * Компонент часто задаваемых вопросов.
9459
9464
  */
@@ -9496,48 +9501,178 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
9496
9501
  ], host: { ngSkipHydration: 'true' }, changeDetection: ChangeDetectionStrategy.OnPush, template: "<tui-loader\n [showLoader]=\"showLoading()\"\n [overlay]=\"true\"\n>\n <tui-accordion\n class=\"accordion\"\n [closeOthers]=\"false\"\n >\n @for (item of items(); track item.id) {\n <button\n [tuiAccordion]=\"isServer\"\n class=\"!whitespace-normal !text-body-m-bold\"\n >\n {{ item.question }}\n </button>\n <tui-expand>\n <div [innerHTML]=\"item.answer\"></div>\n </tui-expand>\n }\n </tui-accordion>\n</tui-loader>\n", styles: [".accordion{border-radius:0}.accordion,.accordion[data-size=s],.accordion[data-size=m],.accordion[data-size=l],.accordion .tui-list{font:inherit}.accordion [tuiAccordion]{border-block:1px solid var(--tui-border-normal);border-block-end-color:#fff!important;font-weight:400;border-color:var(--tui-border-normal);mask:none;block-size:auto;padding-block:.5rem;min-block-size:var(--t-size)}.accordion [tuiAccordion]._open{border-block-end-color:var(--tui-border-normal)!important}.accordion tui-expand,.accordion [tuiAccordion]{box-shadow:none;white-space:normal}\n"] }]
9497
9502
  }] });
9498
9503
 
9504
+ /**
9505
+ * Возвращает query-параметры ссылки на группу часто задаваемых вопросов.
9506
+ *
9507
+ * При смене группы пагинация сбрасывается на первую страницу.
9508
+ *
9509
+ * @param group Группа вопросов.
9510
+ */
9511
+ const scGetFaqGroupQueryParams = (group) => ({
9512
+ [SC_FAQ_GROUP_QUERY_PARAM]: group.id ?? null,
9513
+ [SC_PAGE_QUERY_PARAM]: null,
9514
+ });
9515
+
9499
9516
  /**
9500
9517
  * Компонент выбора группы часто задаваемых вопросов.
9518
+ *
9519
+ * TODO: [TAIGA:5]: Заменить legacy tui-select и tuiItemsHandlersProvider на актуальные аналоги.
9501
9520
  */
9502
9521
  class ScFrequentlyAskedQuestionsGroupSelectorComponent {
9522
+ /**
9523
+ * Инициализирует экземпляр класса {@link ScFrequentlyAskedQuestionsGroupSelectorComponent}.
9524
+ */
9503
9525
  constructor() {
9526
+ /**
9527
+ * Сервис маршрутизации.
9528
+ */
9529
+ this.router = inject(Router);
9530
+ /**
9531
+ * Активный маршрут.
9532
+ */
9533
+ this.route = inject(ActivatedRoute);
9504
9534
  /**
9505
9535
  * {@link Observable} списка группы часто задаваемых вопросов.
9506
9536
  */
9507
- this.groups$ = inject(ScFrequentlyAskedQuestionsService).groups$.pipe(first(), tap((groups) => {
9508
- if (groups.length > 0) {
9509
- this.groupControl.setValue(groups[0]);
9510
- }
9511
- }));
9537
+ this.groups$ = inject(ScFrequentlyAskedQuestionsService).groups$;
9512
9538
  /**
9513
9539
  * {@link FormControl} выбранной группы.
9514
9540
  */
9515
9541
  this.groupControl = new FormControl(null);
9516
9542
  /**
9517
- * {@link OutputRef} сигнал изменения идентификатора группы.
9543
+ * {@link InputSignal} идентификатора выбранной группы.
9518
9544
  */
9519
- this.groupIdChange = outputFromObservable(this.groupControl.valueChanges.pipe(filter(tuiIsPresent),
9520
- // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
9521
- map((group) => group.id)));
9545
+ this.selectedGroupId = input(null);
9522
9546
  /**
9523
9547
  * Формат отображения. 'list' - в виде списка, 'select' в виде выпадающего списка.
9524
9548
  */
9525
9549
  this.viewMode = input('list');
9550
+ /**
9551
+ * Возвращает query-параметры ссылки на группу вопросов.
9552
+ */
9553
+ this.getGroupQueryParams = scGetFaqGroupQueryParams;
9554
+ // Синхронизирует значение выпадающего списка с выбранной группой.
9555
+ combineLatest([this.groups$, toObservable(this.selectedGroupId)])
9556
+ .pipe(takeUntilDestroyed())
9557
+ .subscribe(([groups, selectedGroupId]) => {
9558
+ this.groupControl.setValue(groups.find((group) => (group.id ?? null) === selectedGroupId) ?? null, { emitEvent: false });
9559
+ });
9560
+ // Выбор группы в выпадающем списке переводит на адрес этой группы.
9561
+ this.groupControl.valueChanges.pipe(filter(tuiIsPresent), takeUntilDestroyed()).subscribe((group) => {
9562
+ this.router
9563
+ .navigate([], {
9564
+ relativeTo: this.route,
9565
+ queryParams: this.getGroupQueryParams(group),
9566
+ queryParamsHandling: 'merge',
9567
+ })
9568
+ .catch(noop);
9569
+ });
9526
9570
  }
9527
9571
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ScFrequentlyAskedQuestionsGroupSelectorComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
9528
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: ScFrequentlyAskedQuestionsGroupSelectorComponent, isStandalone: true, selector: "sc-frequently-asked-questions-group-selector", inputs: { viewMode: { classPropertyName: "viewMode", publicName: "viewMode", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { groupIdChange: "groupIdChange" }, providers: [
9572
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: ScFrequentlyAskedQuestionsGroupSelectorComponent, isStandalone: true, selector: "sc-frequently-asked-questions-group-selector", inputs: { selectedGroupId: { classPropertyName: "selectedGroupId", publicName: "selectedGroupId", isSignal: true, isRequired: false, transformFunction: null }, viewMode: { classPropertyName: "viewMode", publicName: "viewMode", isSignal: true, isRequired: false, transformFunction: null } }, providers: [
9529
9573
  tuiItemsHandlersProvider$1({
9530
9574
  stringify: (item) => item.name,
9531
9575
  }),
9532
- ], ngImport: i0, template: "@let groups = groups$ | async;\n\n@if (groups && groups.length) {\n @switch (viewMode()) {\n @case ('list') {\n <div class=\"flex flex-col items-center gap-3 rounded-xl p-4 shadow-sc\">\n <div class=\"flex w-full flex-col gap-2\">\n @for (item of groups; track $index) {\n <button\n tuiButton\n size=\"xs\"\n [tuiAppearanceState]=\"groupControl.value === item ? 'hover' : null\"\n [disabled]=\"groupControl.value === item\"\n (click)=\"groupControl.patchValue(item)\"\n appearance=\"flat-grayscale\"\n class=\"!justify-start !text-body-s-bold\"\n >\n {{ item.name }}\n </button>\n }\n </div>\n </div>\n }\n\n @case ('select') {\n <form>\n <tui-select\n [formControl]=\"groupControl\"\n [tuiTextfieldLabelOutside]=\"true\"\n >\n <tui-data-list-wrapper\n *tuiDataList\n [items]=\"groups\"\n />\n </tui-select>\n </form>\n }\n }\n}\n", dependencies: [{ kind: "pipe", type: AsyncPipe, name: "async" }, { kind: "ngmodule", type: TuiSelectModule }, { kind: "component", type: i3.TuiSelectComponent, selector: "tui-select", inputs: ["stringify", "identityMatcher", "valueContent"] }, { kind: "directive", type: i3.TuiSelectDirective, selector: "tui-select" }, { kind: "directive", type: i3$1.TuiDataListDirective, selector: "ng-template[tuiDataList]" }, { kind: "component", type: i3$3.TuiDataListWrapperComponent, selector: "tui-data-list-wrapper:not([labels]), tui-data-list-wrapper:not([labels])[new]", inputs: ["items", "disabledItemHandler", "emptyContent", "size", "itemContent"], outputs: ["itemClick"] }, { kind: "ngmodule", type: TuiTextfieldControllerModule }, { kind: "directive", type: i3.TuiTextfieldLabelOutsideDirective, selector: "[tuiTextfieldLabelOutside]", inputs: ["tuiTextfieldLabelOutside"] }, { kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1$1.ɵNgNoValidate, selector: "form:not([ngNoForm]):not([ngNativeValidate])" }, { kind: "directive", type: i1$1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$1.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i1$1.FormControlDirective, selector: "[formControl]", inputs: ["formControl", "disabled", "ngModel"], outputs: ["ngModelChange"], exportAs: ["ngForm"] }, { kind: "directive", type: TuiButton, selector: "a[tuiButton],button[tuiButton],a[tuiIconButton],button[tuiIconButton]", inputs: ["size"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$1.NgForm, selector: "form:not([ngNoForm]):not([formGroup]),ng-form,[ngForm]", inputs: ["ngFormOptions"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
9576
+ ], ngImport: i0, template: "@let groups = groups$ | async;\n\n@if (groups && groups.length) {\n @switch (viewMode()) {\n @case ('list') {\n <div class=\"flex flex-col items-center gap-3 rounded-xl p-4 shadow-sc\">\n <div class=\"flex w-full flex-col gap-2\">\n @for (item of groups; track $index) {\n @let isSelected = item.id === selectedGroupId();\n\n <a\n tuiButton\n size=\"xs\"\n [tuiAppearanceState]=\"isSelected ? 'hover' : null\"\n [attr.aria-current]=\"isSelected ? 'page' : null\"\n [class.pointer-events-none]=\"isSelected\"\n [routerLink]=\"[]\"\n [queryParams]=\"getGroupQueryParams(item)\"\n queryParamsHandling=\"merge\"\n appearance=\"flat-grayscale\"\n class=\"!justify-start !text-body-s-bold\"\n >\n {{ item.name }}\n </a>\n }\n </div>\n </div>\n }\n\n @case ('select') {\n <form>\n <tui-select\n [formControl]=\"groupControl\"\n [tuiTextfieldLabelOutside]=\"true\"\n >\n <tui-data-list-wrapper\n *tuiDataList\n [items]=\"groups\"\n />\n </tui-select>\n </form>\n }\n }\n}\n", dependencies: [{ kind: "pipe", type: AsyncPipe, name: "async" }, { kind: "ngmodule", type: TuiSelectModule }, { kind: "component", type: i3.TuiSelectComponent, selector: "tui-select", inputs: ["stringify", "identityMatcher", "valueContent"] }, { kind: "directive", type: i3.TuiSelectDirective, selector: "tui-select" }, { kind: "directive", type: i3$1.TuiDataListDirective, selector: "ng-template[tuiDataList]" }, { kind: "component", type: i3$3.TuiDataListWrapperComponent, selector: "tui-data-list-wrapper:not([labels]), tui-data-list-wrapper:not([labels])[new]", inputs: ["items", "disabledItemHandler", "emptyContent", "size", "itemContent"], outputs: ["itemClick"] }, { kind: "ngmodule", type: TuiTextfieldControllerModule }, { kind: "directive", type: i3.TuiTextfieldLabelOutsideDirective, selector: "[tuiTextfieldLabelOutside]", inputs: ["tuiTextfieldLabelOutside"] }, { kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1$1.ɵNgNoValidate, selector: "form:not([ngNoForm]):not([ngNativeValidate])" }, { kind: "directive", type: i1$1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$1.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i1$1.FormControlDirective, selector: "[formControl]", inputs: ["formControl", "disabled", "ngModel"], outputs: ["ngModelChange"], exportAs: ["ngForm"] }, { kind: "directive", type: TuiButton, selector: "a[tuiButton],button[tuiButton],a[tuiIconButton],button[tuiIconButton]", inputs: ["size"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$1.NgForm, selector: "form:not([ngNoForm]):not([formGroup]),ng-form,[ngForm]", inputs: ["ngFormOptions"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "info", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
9533
9577
  }
9534
9578
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ScFrequentlyAskedQuestionsGroupSelectorComponent, decorators: [{
9535
9579
  type: Component,
9536
- args: [{ standalone: true, selector: 'sc-frequently-asked-questions-group-selector', imports: [AsyncPipe, TuiSelectModule, TuiTextfieldControllerModule, ReactiveFormsModule, TuiDataList, TuiDataListWrapper, NgIf, TuiButton, FormsModule], providers: [
9580
+ args: [{ standalone: true, selector: 'sc-frequently-asked-questions-group-selector', imports: [AsyncPipe, TuiSelectModule, TuiTextfieldControllerModule, ReactiveFormsModule, TuiDataList, TuiDataListWrapper, NgIf, TuiButton, FormsModule, RouterLink], providers: [
9537
9581
  tuiItemsHandlersProvider$1({
9538
9582
  stringify: (item) => item.name,
9539
9583
  }),
9540
- ], changeDetection: ChangeDetectionStrategy.OnPush, template: "@let groups = groups$ | async;\n\n@if (groups && groups.length) {\n @switch (viewMode()) {\n @case ('list') {\n <div class=\"flex flex-col items-center gap-3 rounded-xl p-4 shadow-sc\">\n <div class=\"flex w-full flex-col gap-2\">\n @for (item of groups; track $index) {\n <button\n tuiButton\n size=\"xs\"\n [tuiAppearanceState]=\"groupControl.value === item ? 'hover' : null\"\n [disabled]=\"groupControl.value === item\"\n (click)=\"groupControl.patchValue(item)\"\n appearance=\"flat-grayscale\"\n class=\"!justify-start !text-body-s-bold\"\n >\n {{ item.name }}\n </button>\n }\n </div>\n </div>\n }\n\n @case ('select') {\n <form>\n <tui-select\n [formControl]=\"groupControl\"\n [tuiTextfieldLabelOutside]=\"true\"\n >\n <tui-data-list-wrapper\n *tuiDataList\n [items]=\"groups\"\n />\n </tui-select>\n </form>\n }\n }\n}\n" }]
9584
+ ], changeDetection: ChangeDetectionStrategy.OnPush, template: "@let groups = groups$ | async;\n\n@if (groups && groups.length) {\n @switch (viewMode()) {\n @case ('list') {\n <div class=\"flex flex-col items-center gap-3 rounded-xl p-4 shadow-sc\">\n <div class=\"flex w-full flex-col gap-2\">\n @for (item of groups; track $index) {\n @let isSelected = item.id === selectedGroupId();\n\n <a\n tuiButton\n size=\"xs\"\n [tuiAppearanceState]=\"isSelected ? 'hover' : null\"\n [attr.aria-current]=\"isSelected ? 'page' : null\"\n [class.pointer-events-none]=\"isSelected\"\n [routerLink]=\"[]\"\n [queryParams]=\"getGroupQueryParams(item)\"\n queryParamsHandling=\"merge\"\n appearance=\"flat-grayscale\"\n class=\"!justify-start !text-body-s-bold\"\n >\n {{ item.name }}\n </a>\n }\n </div>\n </div>\n }\n\n @case ('select') {\n <form>\n <tui-select\n [formControl]=\"groupControl\"\n [tuiTextfieldLabelOutside]=\"true\"\n >\n <tui-data-list-wrapper\n *tuiDataList\n [items]=\"groups\"\n />\n </tui-select>\n </form>\n }\n }\n}\n" }]
9585
+ }], ctorParameters: () => [] });
9586
+
9587
+ /**
9588
+ * Компонент пагинации, в котором страницы являются ссылками с номером страницы в query-параметрах.
9589
+ *
9590
+ * Ссылки позволяют переходить между страницами при отключенном JavaScript и корректно работают при SSR.
9591
+ * Внешний вид повторяет tui-pagination из @taiga-ui/kit.
9592
+ *
9593
+ * TODO: [TAIGA:5]: Проверить, появилась ли в tui-pagination поддержка ссылок, и заменить компонент на неё.
9594
+ */
9595
+ class ScPaginationLinksComponent {
9596
+ constructor() {
9597
+ /**
9598
+ * Иконки стрелок переключения страниц.
9599
+ */
9600
+ this.icons = inject(TUI_SPIN_ICONS);
9601
+ /**
9602
+ * {@link Observable} подписей стрелок переключения страниц.
9603
+ */
9604
+ this.texts$ = inject(TUI_PAGINATION_TEXTS);
9605
+ /**
9606
+ * {@link InputSignal} общего количества страниц.
9607
+ */
9608
+ this.length = input.required();
9609
+ /**
9610
+ * {@link InputSignal} номера текущей страницы, начиная с единицы.
9611
+ */
9612
+ this.index = input.required();
9613
+ /**
9614
+ * {@link InputSignal} наименования query-параметра, в котором хранится номер страницы.
9615
+ */
9616
+ this.queryParam = input(SC_PAGE_QUERY_PARAM);
9617
+ /**
9618
+ * {@link InputSignal} количества страниц, отображаемых по обе стороны от текущей.
9619
+ */
9620
+ this.activePadding = input(1);
9621
+ /**
9622
+ * {@link InputSignal} количества страниц, отображаемых по краям.
9623
+ */
9624
+ this.sidePadding = input(1);
9625
+ /**
9626
+ * {@link Signal} номеров отображаемых страниц, где `null` - разделитель пропущенных страниц.
9627
+ *
9628
+ * Состав страниц рассчитывается так же, как в tui-pagination: количество отображаемых элементов постоянно,
9629
+ * а окно вокруг текущей страницы расширяется у краёв списка.
9630
+ */
9631
+ this.pages = computed(() => {
9632
+ const length = this.length();
9633
+ const sidePadding = this.sidePadding();
9634
+ // Половина элементов: страницы у края, разделитель и страницы вокруг текущей.
9635
+ const maxHalfLength = sidePadding + 1 + this.activePadding();
9636
+ const maxElementsLength = maxHalfLength * 2 + 1;
9637
+ const elementsLength = Math.min(length, maxElementsLength);
9638
+ const lastIndex = length - 1;
9639
+ const index = this.index() - 1;
9640
+ const reverseIndex = lastIndex - index;
9641
+ const hasCollapsedItems = (value) => length > maxElementsLength && value > maxHalfLength;
9642
+ return Array.from({ length: elementsLength }, (_, elementIndex) => {
9643
+ const reverseElementIndex = elementsLength - 1 - elementIndex;
9644
+ if (elementIndex < sidePadding) {
9645
+ return elementIndex + 1;
9646
+ }
9647
+ if (elementIndex === sidePadding && hasCollapsedItems(index)) {
9648
+ return null;
9649
+ }
9650
+ if (reverseElementIndex < sidePadding) {
9651
+ return lastIndex - reverseElementIndex + 1;
9652
+ }
9653
+ if (reverseElementIndex === sidePadding && hasCollapsedItems(reverseIndex)) {
9654
+ return null;
9655
+ }
9656
+ return tuiClamp(index - maxHalfLength + elementIndex, elementIndex, lastIndex - reverseElementIndex) + 1;
9657
+ });
9658
+ });
9659
+ }
9660
+ /**
9661
+ * Возвращает query-параметры ссылки на страницу.
9662
+ *
9663
+ * Для первой страницы параметр удаляется, чтобы её адрес совпадал с адресом страницы без пагинации.
9664
+ *
9665
+ * @param page Номер страницы.
9666
+ */
9667
+ getPageQueryParams(page) {
9668
+ return { [this.queryParam()]: page > 1 ? page : null };
9669
+ }
9670
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ScPaginationLinksComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
9671
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: ScPaginationLinksComponent, isStandalone: true, selector: "sc-pagination-links", inputs: { length: { classPropertyName: "length", publicName: "length", isSignal: true, isRequired: true, transformFunction: null }, index: { classPropertyName: "index", publicName: "index", isSignal: true, isRequired: true, transformFunction: null }, queryParam: { classPropertyName: "queryParam", publicName: "queryParam", isSignal: true, isRequired: false, transformFunction: null }, activePadding: { classPropertyName: "activePadding", publicName: "activePadding", isSignal: true, isRequired: false, transformFunction: null }, sidePadding: { classPropertyName: "sidePadding", publicName: "sidePadding", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: "@let texts = texts$ | async;\n\n@if (texts) {\n <div class=\"t-content\">\n @if (index() > 1) {\n <a\n tuiIconButton\n size=\"s\"\n appearance=\"flat\"\n tabIndex=\"-1\"\n class=\"t-button\"\n [iconStart]=\"icons.decrement\"\n [routerLink]=\"[]\"\n [queryParams]=\"getPageQueryParams(index() - 1)\"\n queryParamsHandling=\"merge\"\n >\n {{ texts[0] }}\n </a>\n } @else {\n <button\n tuiIconButton\n size=\"s\"\n appearance=\"flat\"\n type=\"button\"\n tabIndex=\"-1\"\n class=\"t-button\"\n [iconStart]=\"icons.decrement\"\n [disabled]=\"true\"\n >\n {{ texts[0] }}\n </button>\n }\n\n @for (page of pages(); track $index) {\n @if (page) {\n <a\n automation-id=\"sc-pagination-links__element\"\n tuiButton\n size=\"s\"\n class=\"t-button\"\n [appearance]=\"page === index() ? 'primary' : 'flat'\"\n [attr.aria-current]=\"page === index() ? 'page' : null\"\n [routerLink]=\"[]\"\n [queryParams]=\"getPageQueryParams(page)\"\n queryParamsHandling=\"merge\"\n >\n {{ page }}\n </a>\n } @else {\n <div class=\"t-dots\"></div>\n }\n }\n\n @if (index() < length()) {\n <a\n tuiIconButton\n size=\"s\"\n appearance=\"flat\"\n tabIndex=\"-1\"\n class=\"t-button\"\n [iconStart]=\"icons.increment\"\n [routerLink]=\"[]\"\n [queryParams]=\"getPageQueryParams(index() + 1)\"\n queryParamsHandling=\"merge\"\n >\n {{ texts[1] }}\n </a>\n } @else {\n <button\n tuiIconButton\n size=\"s\"\n appearance=\"flat\"\n type=\"button\"\n tabIndex=\"-1\"\n class=\"t-button\"\n [iconStart]=\"icons.increment\"\n [disabled]=\"true\"\n >\n {{ texts[1] }}\n </button>\n }\n </div>\n}\n", styles: ["@charset \"UTF-8\";:host{display:block;font:var(--tui-font-text-s);color:var(--tui-text-primary);text-align:center}.t-content{display:flex;justify-content:center}.t-button{flex-shrink:0;margin:0 .125rem}.t-button[tuiButton]{min-inline-size:var(--tui-height-s);padding:0 .5rem}.t-button:first-child{margin-inline-start:0}.t-button:last-child{margin-inline-end:0}.t-dots{flex-shrink:0;inline-size:var(--tui-height-s);block-size:var(--tui-height-s);line-height:var(--tui-height-s);margin:0 .125rem;color:var(--tui-text-action);text-align:center;cursor:default}.t-dots:before{content:\"\\2026\"}\n"], dependencies: [{ kind: "pipe", type: AsyncPipe, name: "async" }, { kind: "directive", type: RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "info", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "directive", type: TuiButton, selector: "a[tuiButton],button[tuiButton],a[tuiIconButton],button[tuiIconButton]", inputs: ["size"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
9672
+ }
9673
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ScPaginationLinksComponent, decorators: [{
9674
+ type: Component,
9675
+ args: [{ standalone: true, selector: 'sc-pagination-links', imports: [AsyncPipe, RouterLink, TuiButton], changeDetection: ChangeDetectionStrategy.OnPush, template: "@let texts = texts$ | async;\n\n@if (texts) {\n <div class=\"t-content\">\n @if (index() > 1) {\n <a\n tuiIconButton\n size=\"s\"\n appearance=\"flat\"\n tabIndex=\"-1\"\n class=\"t-button\"\n [iconStart]=\"icons.decrement\"\n [routerLink]=\"[]\"\n [queryParams]=\"getPageQueryParams(index() - 1)\"\n queryParamsHandling=\"merge\"\n >\n {{ texts[0] }}\n </a>\n } @else {\n <button\n tuiIconButton\n size=\"s\"\n appearance=\"flat\"\n type=\"button\"\n tabIndex=\"-1\"\n class=\"t-button\"\n [iconStart]=\"icons.decrement\"\n [disabled]=\"true\"\n >\n {{ texts[0] }}\n </button>\n }\n\n @for (page of pages(); track $index) {\n @if (page) {\n <a\n automation-id=\"sc-pagination-links__element\"\n tuiButton\n size=\"s\"\n class=\"t-button\"\n [appearance]=\"page === index() ? 'primary' : 'flat'\"\n [attr.aria-current]=\"page === index() ? 'page' : null\"\n [routerLink]=\"[]\"\n [queryParams]=\"getPageQueryParams(page)\"\n queryParamsHandling=\"merge\"\n >\n {{ page }}\n </a>\n } @else {\n <div class=\"t-dots\"></div>\n }\n }\n\n @if (index() < length()) {\n <a\n tuiIconButton\n size=\"s\"\n appearance=\"flat\"\n tabIndex=\"-1\"\n class=\"t-button\"\n [iconStart]=\"icons.increment\"\n [routerLink]=\"[]\"\n [queryParams]=\"getPageQueryParams(index() + 1)\"\n queryParamsHandling=\"merge\"\n >\n {{ texts[1] }}\n </a>\n } @else {\n <button\n tuiIconButton\n size=\"s\"\n appearance=\"flat\"\n type=\"button\"\n tabIndex=\"-1\"\n class=\"t-button\"\n [iconStart]=\"icons.increment\"\n [disabled]=\"true\"\n >\n {{ texts[1] }}\n </button>\n }\n </div>\n}\n", styles: ["@charset \"UTF-8\";:host{display:block;font:var(--tui-font-text-s);color:var(--tui-text-primary);text-align:center}.t-content{display:flex;justify-content:center}.t-button{flex-shrink:0;margin:0 .125rem}.t-button[tuiButton]{min-inline-size:var(--tui-height-s);padding:0 .5rem}.t-button:first-child{margin-inline-start:0}.t-button:last-child{margin-inline-end:0}.t-dots{flex-shrink:0;inline-size:var(--tui-height-s);block-size:var(--tui-height-s);line-height:var(--tui-height-s);margin:0 .125rem;color:var(--tui-text-action);text-align:center;cursor:default}.t-dots:before{content:\"\\2026\"}\n"] }]
9541
9676
  }] });
9542
9677
 
9543
9678
  /**
@@ -9573,9 +9708,13 @@ class ScFrequentlyAskedQuestionsWithGroupsComponent {
9573
9708
  */
9574
9709
  this.router = inject(Router);
9575
9710
  /**
9576
- * Индекс первой страницы.
9711
+ * Активный маршрут.
9712
+ */
9713
+ this.route = inject(ActivatedRoute);
9714
+ /**
9715
+ * Признак, что приложение запущено на сервере.
9577
9716
  */
9578
- this.firstPageIndex = 1;
9717
+ this.isServer = inject(IS_SERVER);
9579
9718
  /**
9580
9719
  * Количество записей на странице пагинации.
9581
9720
  */
@@ -9585,13 +9724,15 @@ class ScFrequentlyAskedQuestionsWithGroupsComponent {
9585
9724
  */
9586
9725
  this.perPage$ = new BehaviorSubject(this.pageSizeOptions[0]);
9587
9726
  /**
9588
- * {@link BehaviorSubject} изменения номера страницы.
9727
+ * {@link Observable} изменения номера страницы пагинации из query-параметров.
9589
9728
  */
9590
- this.page$ = new BehaviorSubject(this.firstPageIndex);
9729
+ this.page$ = scGetPageQueryParamChanges();
9591
9730
  /**
9592
- * {@link BehaviorSubject} изменения идентификатора группы.
9731
+ * {@link Observable} изменения идентификатора выбранной группы.
9732
+ *
9733
+ * Идентификатор берётся из query-параметров, а если параметр не задан - используется первая группа списка.
9593
9734
  */
9594
- this.groupId$ = new Subject();
9735
+ this.groupId$ = combineLatest([this.route.queryParamMap, this.frequentlyAskedQuestionsService.groups$]).pipe(map(([params, groups]) => Number(params.get(SC_FAQ_GROUP_QUERY_PARAM)) || (groups[0]?.id ?? null)), distinctUntilChanged(), shareReplay({ refCount: true, bufferSize: 1 }));
9595
9736
  /**
9596
9737
  * Сигнал нажатия на кнопку "Задать вопрос".
9597
9738
  */
@@ -9602,7 +9743,7 @@ class ScFrequentlyAskedQuestionsWithGroupsComponent {
9602
9743
  this.request$ = combineLatest({
9603
9744
  page: this.page$,
9604
9745
  perPage: this.perPage$,
9605
- group: this.groupId$,
9746
+ group: this.groupId$.pipe(filter(tuiIsPresent)),
9606
9747
  paginate: of(true),
9607
9748
  }).pipe(
9608
9749
  // Нулевой debounceTime для случая, когда меняются направление и поле сортировки одновременно.
@@ -9621,7 +9762,7 @@ class ScFrequentlyAskedQuestionsWithGroupsComponent {
9621
9762
  /**
9622
9763
  * {@link Observable} изменения номера страницы пагинации из данных пагинации запроса.
9623
9764
  */
9624
- this.currentPage$ = this.request$.pipe(filter(tuiIsPresent), map(({ meta }) => meta.currentPage - 1));
9765
+ this.currentPage$ = this.request$.pipe(filter(tuiIsPresent), map(({ meta }) => meta.currentPage));
9625
9766
  /**
9626
9767
  * {@link Observable} изменения состояния загрузки данных.
9627
9768
  */
@@ -9633,33 +9774,99 @@ class ScFrequentlyAskedQuestionsWithGroupsComponent {
9633
9774
  /**
9634
9775
  * {@link Observable} изменения формата отображения фильтра групп.
9635
9776
  */
9636
- this.viewMode$ = inject(TUI_WINDOW_SIZE).pipe(map((rect) => (rect.width > 768 ? 'list' : 'select')));
9637
- }
9638
- /**
9639
- * Устанавливает данные пагинации.
9640
- *
9641
- * @param pageIndex Индекс страницы.
9642
- */
9643
- paginationChange(pageIndex) {
9644
- this.page$.next(pageIndex + 1);
9645
- }
9646
- /**
9647
- * Устанавливает идентификатор группы.
9648
- *
9649
- * @param id Идентификатор группы.
9650
- */
9651
- groupIdChange(id) {
9652
- this.groupId$.next(id);
9653
- this.paginationChange(0);
9777
+ this.viewMode$ = this.isServer
9778
+ ? of('list')
9779
+ : inject(TUI_WINDOW_SIZE).pipe(map((rect) => (rect.width > 768 ? 'list' : 'select')));
9780
+ /**
9781
+ * Наименование query-параметра номера страницы пагинации.
9782
+ */
9783
+ this.pageQueryParam = SC_PAGE_QUERY_PARAM;
9654
9784
  }
9655
9785
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ScFrequentlyAskedQuestionsWithGroupsComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
9656
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: ScFrequentlyAskedQuestionsWithGroupsComponent, isStandalone: true, selector: "sc-frequently-asked-questions-with-groups", outputs: { clickSendQuestion: "clickSendQuestion" }, ngImport: i0, template: "@let items = data$ | async;\n@let pageCount = pageCount$ | async;\n@let viewMode = viewMode$ | async;\n\n<div\n *ngIf=\"viewMode\"\n class=\"flex gap-6\"\n [class.flex-col]=\"viewMode === 'select'\"\n>\n <div class=\"flex flex-col gap-7\">\n <sc-frequently-asked-questions-group-selector\n (groupIdChange)=\"groupIdChange($event)\"\n [viewMode]=\"viewMode\"\n class=\"shrink-0\"\n [class.w-64]=\"viewMode !== 'select'\"\n />\n\n <button\n *ngIf=\"viewMode === 'list'\"\n tuiButton\n size=\"m\"\n type=\"button\"\n iconStart=\"@tui.circle-help\"\n appearance=\"secondary\"\n (click)=\"clickSendQuestion.emit()\"\n class=\"self-center\"\n >\n \u0417\u0430\u0434\u0430\u0442\u044C \u0432\u043E\u043F\u0440\u043E\u0441\n </button>\n </div>\n\n <div class=\"grow\">\n @if (items && items.length) {\n <sc-frequently-asked-questions\n [items]=\"items\"\n [showLoading]=\"isLoading()\"\n />\n\n <tui-pagination\n *ngIf=\"pageCount && pageCount > 1\"\n [length]=\"pageCount\"\n [index]=\"(currentPage$ | async) ?? 0\"\n (indexChange)=\"paginationChange($event)\"\n class=\"mt-4 !justify-items-center\"\n />\n } @else {\n <p class=\"text-body-s-bold\">\u0421\u043F\u0438\u0441\u043E\u043A \u0432\u043E\u043F\u0440\u043E\u0441\u043E\u0432 \u043F\u0443\u0441\u0442</p>\n }\n </div>\n</div>\n", dependencies: [{ kind: "pipe", type: AsyncPipe, name: "async" }, { kind: "directive", type: NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: ScFrequentlyAskedQuestionsGroupSelectorComponent, selector: "sc-frequently-asked-questions-group-selector", inputs: ["viewMode"], outputs: ["groupIdChange"] }, { kind: "directive", type: TuiButton, selector: "a[tuiButton],button[tuiButton],a[tuiIconButton],button[tuiIconButton]", inputs: ["size"] }, { kind: "component", type: ScFrequentlyAskedQuestionsComponent, selector: "sc-frequently-asked-questions", inputs: ["items", "showLoading"] }, { kind: "component", type: TuiPagination, selector: "tui-pagination", inputs: ["length", "focusable", "size", "disabled", "activePadding", "sidePadding", "content", "index"], outputs: ["indexChange"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
9786
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: ScFrequentlyAskedQuestionsWithGroupsComponent, isStandalone: true, selector: "sc-frequently-asked-questions-with-groups", outputs: { clickSendQuestion: "clickSendQuestion" }, host: { attributes: { "ngSkipHydration": "true" } }, ngImport: i0, template: "@let items = data$ | async;\n@let pageCount = pageCount$ | async;\n@let viewMode = viewMode$ | async;\n\n<div\n *ngIf=\"viewMode\"\n class=\"flex gap-6\"\n [class.flex-col]=\"viewMode === 'select'\"\n>\n <div class=\"flex flex-col gap-7\">\n <sc-frequently-asked-questions-group-selector\n [selectedGroupId]=\"groupId$ | async\"\n [viewMode]=\"viewMode\"\n class=\"shrink-0\"\n [class.w-64]=\"viewMode !== 'select'\"\n />\n\n <button\n *ngIf=\"viewMode === 'list'\"\n tuiButton\n size=\"m\"\n type=\"button\"\n iconStart=\"@tui.circle-help\"\n appearance=\"secondary\"\n (click)=\"clickSendQuestion.emit()\"\n class=\"self-center\"\n >\n \u0417\u0430\u0434\u0430\u0442\u044C \u0432\u043E\u043F\u0440\u043E\u0441\n </button>\n </div>\n\n <div class=\"grow\">\n @if (items && items.length) {\n <sc-frequently-asked-questions\n [items]=\"items\"\n [showLoading]=\"isLoading()\"\n />\n\n <sc-pagination-links\n *ngIf=\"pageCount && pageCount > 1\"\n [length]=\"pageCount\"\n [index]=\"(currentPage$ | async) ?? 1\"\n [queryParam]=\"pageQueryParam\"\n class=\"mt-4\"\n />\n } @else {\n <p class=\"text-body-s-bold\">\u0421\u043F\u0438\u0441\u043E\u043A \u0432\u043E\u043F\u0440\u043E\u0441\u043E\u0432 \u043F\u0443\u0441\u0442</p>\n }\n </div>\n</div>\n", dependencies: [{ kind: "pipe", type: AsyncPipe, name: "async" }, { kind: "directive", type: NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: ScFrequentlyAskedQuestionsGroupSelectorComponent, selector: "sc-frequently-asked-questions-group-selector", inputs: ["selectedGroupId", "viewMode"] }, { kind: "directive", type: TuiButton, selector: "a[tuiButton],button[tuiButton],a[tuiIconButton],button[tuiIconButton]", inputs: ["size"] }, { kind: "component", type: ScFrequentlyAskedQuestionsComponent, selector: "sc-frequently-asked-questions", inputs: ["items", "showLoading"] }, { kind: "component", type: ScPaginationLinksComponent, selector: "sc-pagination-links", inputs: ["length", "index", "queryParam", "activePadding", "sidePadding"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
9657
9787
  }
9658
9788
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ScFrequentlyAskedQuestionsWithGroupsComponent, decorators: [{
9659
9789
  type: Component,
9660
- args: [{ standalone: true, selector: 'sc-frequently-asked-questions-with-groups', imports: [AsyncPipe, NgIf, ScFrequentlyAskedQuestionsGroupSelectorComponent, TuiButton, ScFrequentlyAskedQuestionsComponent, TuiPagination], changeDetection: ChangeDetectionStrategy.OnPush, template: "@let items = data$ | async;\n@let pageCount = pageCount$ | async;\n@let viewMode = viewMode$ | async;\n\n<div\n *ngIf=\"viewMode\"\n class=\"flex gap-6\"\n [class.flex-col]=\"viewMode === 'select'\"\n>\n <div class=\"flex flex-col gap-7\">\n <sc-frequently-asked-questions-group-selector\n (groupIdChange)=\"groupIdChange($event)\"\n [viewMode]=\"viewMode\"\n class=\"shrink-0\"\n [class.w-64]=\"viewMode !== 'select'\"\n />\n\n <button\n *ngIf=\"viewMode === 'list'\"\n tuiButton\n size=\"m\"\n type=\"button\"\n iconStart=\"@tui.circle-help\"\n appearance=\"secondary\"\n (click)=\"clickSendQuestion.emit()\"\n class=\"self-center\"\n >\n \u0417\u0430\u0434\u0430\u0442\u044C \u0432\u043E\u043F\u0440\u043E\u0441\n </button>\n </div>\n\n <div class=\"grow\">\n @if (items && items.length) {\n <sc-frequently-asked-questions\n [items]=\"items\"\n [showLoading]=\"isLoading()\"\n />\n\n <tui-pagination\n *ngIf=\"pageCount && pageCount > 1\"\n [length]=\"pageCount\"\n [index]=\"(currentPage$ | async) ?? 0\"\n (indexChange)=\"paginationChange($event)\"\n class=\"mt-4 !justify-items-center\"\n />\n } @else {\n <p class=\"text-body-s-bold\">\u0421\u043F\u0438\u0441\u043E\u043A \u0432\u043E\u043F\u0440\u043E\u0441\u043E\u0432 \u043F\u0443\u0441\u0442</p>\n }\n </div>\n</div>\n" }]
9790
+ args: [{ standalone: true, selector: 'sc-frequently-asked-questions-with-groups', imports: [AsyncPipe, NgIf, ScFrequentlyAskedQuestionsGroupSelectorComponent, TuiButton, ScFrequentlyAskedQuestionsComponent, ScPaginationLinksComponent], host: { ngSkipHydration: 'true' }, changeDetection: ChangeDetectionStrategy.OnPush, template: "@let items = data$ | async;\n@let pageCount = pageCount$ | async;\n@let viewMode = viewMode$ | async;\n\n<div\n *ngIf=\"viewMode\"\n class=\"flex gap-6\"\n [class.flex-col]=\"viewMode === 'select'\"\n>\n <div class=\"flex flex-col gap-7\">\n <sc-frequently-asked-questions-group-selector\n [selectedGroupId]=\"groupId$ | async\"\n [viewMode]=\"viewMode\"\n class=\"shrink-0\"\n [class.w-64]=\"viewMode !== 'select'\"\n />\n\n <button\n *ngIf=\"viewMode === 'list'\"\n tuiButton\n size=\"m\"\n type=\"button\"\n iconStart=\"@tui.circle-help\"\n appearance=\"secondary\"\n (click)=\"clickSendQuestion.emit()\"\n class=\"self-center\"\n >\n \u0417\u0430\u0434\u0430\u0442\u044C \u0432\u043E\u043F\u0440\u043E\u0441\n </button>\n </div>\n\n <div class=\"grow\">\n @if (items && items.length) {\n <sc-frequently-asked-questions\n [items]=\"items\"\n [showLoading]=\"isLoading()\"\n />\n\n <sc-pagination-links\n *ngIf=\"pageCount && pageCount > 1\"\n [length]=\"pageCount\"\n [index]=\"(currentPage$ | async) ?? 1\"\n [queryParam]=\"pageQueryParam\"\n class=\"mt-4\"\n />\n } @else {\n <p class=\"text-body-s-bold\">\u0421\u043F\u0438\u0441\u043E\u043A \u0432\u043E\u043F\u0440\u043E\u0441\u043E\u0432 \u043F\u0443\u0441\u0442</p>\n }\n </div>\n</div>\n" }]
9661
9791
  }] });
9662
9792
 
9793
+ /**
9794
+ * Компонент списка новостей с пагинацией через query-параметр страницы.
9795
+ *
9796
+ * Ссылки пагинации корректно работают при SSR и позволяют поисковым роботам обходить страницы списка.
9797
+ */
9798
+ class ScNewsListComponent {
9799
+ /**
9800
+ * Инициализирует экземпляр класса {@link ScNewsListComponent}.
9801
+ */
9802
+ constructor() {
9803
+ /**
9804
+ * Сервис для получения списка новостей.
9805
+ */
9806
+ this.newsService = inject(ScNewsService);
9807
+ /**
9808
+ * Сервис маршрутизации.
9809
+ */
9810
+ this.router = inject(Router);
9811
+ /**
9812
+ * {@link InputSignal} количества записей на странице пагинации.
9813
+ */
9814
+ this.perPage = input(16);
9815
+ /**
9816
+ * {@link Observable} изменения номера страницы пагинации из query-параметров.
9817
+ */
9818
+ this.page$ = scGetPageQueryParamChanges();
9819
+ /**
9820
+ * {@link Observable} запроса данных списка новостей.
9821
+ */
9822
+ this.request$ = combineLatest([
9823
+ combineLatest({
9824
+ page: this.page$,
9825
+ perPage: toObservable(this.perPage),
9826
+ paginate: of(true),
9827
+ }),
9828
+ inject(SC_USER_INFO$1),
9829
+ ]).pipe(
9830
+ // Нулевой debounceTime для случая, когда номер страницы и количество записей меняются одновременно.
9831
+ debounceTime(0), switchMap(([value]) => this.newsService.getListOfNews$(value).pipe(startWith(null))), share());
9832
+ /**
9833
+ * {@link Observable} изменения количества страниц пагинации.
9834
+ */
9835
+ this.pagesLength$ = this.request$.pipe(filter(tuiIsPresent), map(({ meta }) => meta.lastPage), startWith(20));
9836
+ /**
9837
+ * {@link Observable} изменения номера страницы пагинации из данных пагинации запроса.
9838
+ */
9839
+ this.currentPage$ = this.request$.pipe(filter(tuiIsPresent), map(({ meta }) => meta.currentPage));
9840
+ /**
9841
+ * {@link Observable} изменения состояния загрузки данных.
9842
+ */
9843
+ this.loading$ = this.request$.pipe(map(tuiIsFalsy));
9844
+ /**
9845
+ * {@link Observable} изменения списка новостей страницы пагинации.
9846
+ */
9847
+ this.data$ = this.request$.pipe(filter(tuiIsPresent), map((data) => data.data),
9848
+ // eslint-disable-next-line unicorn/no-array-callback-reference
9849
+ map((newsList) => newsList.filter(tuiIsPresent)), startWith(null));
9850
+ /**
9851
+ * Событие изменения списка новостей страницы пагинации.
9852
+ */
9853
+ this.dataChangeEvent = outputFromObservable(this.data$.pipe(filter(tuiIsPresent)));
9854
+ inject(SC_USER_INFO$1)
9855
+ .pipe(skip(1), takeUntilDestroyed())
9856
+ .subscribe(() => {
9857
+ // Смена данных пользователя сбрасывает пагинацию на первую страницу.
9858
+ // eslint-disable-next-line no-void
9859
+ void this.router.navigate([], { queryParams: { [SC_PAGE_QUERY_PARAM]: null }, queryParamsHandling: 'merge' });
9860
+ });
9861
+ }
9862
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ScNewsListComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
9863
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "18.2.14", type: ScNewsListComponent, isStandalone: true, selector: "sc-news-list", inputs: { perPage: { classPropertyName: "perPage", publicName: "perPage", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { dataChangeEvent: "dataChangeEvent" }, ngImport: i0, template: "@let newsList = data$ | async;\n<tui-loader\n class=\"mb-4\"\n [showLoader]=\"!!(loading$ | async) && !!newsList\"\n>\n <div class=\"grid grid-cols-[repeat(auto-fill,minmax(17rem,1fr))] gap-8\">\n <ng-container *ngIf=\"newsList; else newsListSkeleton\">\n <sc-news-card\n *ngFor=\"let news of newsList\"\n [news]=\"news\"\n [href]=\"'/news/' + news.id\"\n />\n </ng-container>\n <ng-template #newsListSkeleton>\n <sc-news-card-skeleton *ngFor=\"let _ of [].constructor(perPage())\" />\n </ng-template>\n </div>\n</tui-loader>\n<tui-loader [showLoader]=\"!!(loading$ | async)\">\n <sc-pagination-links\n [index]=\"(currentPage$ | async) ?? 1\"\n [length]=\"(pagesLength$ | async)!\"\n />\n</tui-loader>\n", dependencies: [{ kind: "component", type: TuiLoader, selector: "tui-loader", inputs: ["size", "inheritColor", "overlay", "textContent", "showLoader"] }, { kind: "directive", type: NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: NgFor, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "ngmodule", type: ScNewsModule }, { kind: "component", type: ScNewsCardComponent, selector: "sc-news-card", inputs: ["news", "href"] }, { kind: "component", type: ScNewsCardSkeletonComponent, selector: "sc-news-card-skeleton", inputs: ["hasImg"] }, { kind: "component", type: ScPaginationLinksComponent, selector: "sc-pagination-links", inputs: ["length", "index", "queryParam", "activePadding", "sidePadding"] }, { kind: "pipe", type: AsyncPipe, name: "async" }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
9864
+ }
9865
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ScNewsListComponent, decorators: [{
9866
+ type: Component,
9867
+ args: [{ standalone: true, selector: 'sc-news-list', imports: [TuiLoader, NgIf, NgFor, ScNewsModule, ScPaginationLinksComponent, AsyncPipe], changeDetection: ChangeDetectionStrategy.OnPush, template: "@let newsList = data$ | async;\n<tui-loader\n class=\"mb-4\"\n [showLoader]=\"!!(loading$ | async) && !!newsList\"\n>\n <div class=\"grid grid-cols-[repeat(auto-fill,minmax(17rem,1fr))] gap-8\">\n <ng-container *ngIf=\"newsList; else newsListSkeleton\">\n <sc-news-card\n *ngFor=\"let news of newsList\"\n [news]=\"news\"\n [href]=\"'/news/' + news.id\"\n />\n </ng-container>\n <ng-template #newsListSkeleton>\n <sc-news-card-skeleton *ngFor=\"let _ of [].constructor(perPage())\" />\n </ng-template>\n </div>\n</tui-loader>\n<tui-loader [showLoader]=\"!!(loading$ | async)\">\n <sc-pagination-links\n [index]=\"(currentPage$ | async) ?? 1\"\n [length]=\"(pagesLength$ | async)!\"\n />\n</tui-loader>\n" }]
9868
+ }], ctorParameters: () => [] });
9869
+
9663
9870
  /**
9664
9871
  * Компонент политики обработки персональных данных пользователей сайта.
9665
9872
  */
@@ -10819,5 +11026,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
10819
11026
  * Generated bundle index. Do not edit.
10820
11027
  */
10821
11028
 
10822
- export { AbstractScPriceCard, AuthMethod, CURRENT_COUNTRY_ID, CostWithDiscountComponent, FilesAndDocumentsComponent, FilesAndDocumentsModule, FinishDateTimeTransformerDirective, IDLE_ITEM_STATE, IS_DEFAULT_COUNTRY, MAX_FILES_IN_FORM_INPUT, SC_ALLOW_SELECT_TERMINATED, SC_BANNER_DURATION, SC_CATALOG_PRODUCTS_FILTERS, SC_CATALOG_SHOW_PRODUCTS_RECURSIVELY, SC_DATE_FORMATTER, SC_DEBOUNCE_TIME_DEFAULT, SC_DIALOG_SERVICE_TOKEN, SC_ERROR_CHANGE_HANDLER, SC_HELP_NOTIFICATION_CLOSE, SC_HELP_NOTIFICATION_LIMIT, SC_HIDDEN_PRINT_ELEMENTS, SC_MANAGER_QR_HANDLER, SC_NOTIFY_WHEN_IN_STOCK_REQUIRED_FIELDS, SC_ORDER_FORM_CONFIG, SC_ORDER_OPTIONS, SC_PAGE_SIZE_OPTIONS$1 as SC_PAGE_SIZE_OPTIONS, SC_SHOW_HELP_NOTIFICATION_IN_PHONE_INPUT, SC_USER_CITY_INFO, SC_USER_INFO, SC_USER_PROVIDERS, SC_VERIFICATION_CODE_TIMEOUT, ScAccordionComponent, ScAccordionContentDirective, ScAccordionModule, ScAddContactDialogComponent, ScAddContragentBankAccountsDialogComponent, ScAddContragentDialogComponent, ScAddDeliveryAddressDialogComponent, ScAddOrEditingCartItemDialogComponent, ScAddOrEditingCartItemFormComponent, ScAddressesSelectionFieldComponent, ScAuthModule, ScBannerComponent, ScBannerModule, ScBrandsListComponent, ScBrandsListModule, ScCartAddProductsFromCsvDialogComponent, ScCatalogFilterCollapsibleComponent, ScCatalogFiltersComponent, ScCatalogModule, ScCategoryCardComponent, ScContactsAccordionComponent, ScContactsModule, ScContragentsAccordionComponent, ScContragentsAccordionItemComponent, ScContragentsModule, ScDeliveryAddressAccordionComponent, ScDeliveryAddressAccordionItemComponent, ScDeliveryAddressModule, ScDownloadPriceListComponent, ScDraftComponent, ScEmailLinkDirective, ScErrorBlockStatusComponent, ScErrorHandlerComponent, ScFavoriteButtonComponent, ScFeedbackFormComponent, ScFocusFirstInvalidFieldDirective, ScFormFieldsModule, ScFormatDatePipe, ScFrequentlyAskedQuestionsComponent, ScFrequentlyAskedQuestionsGroupSelectorComponent, ScFrequentlyAskedQuestionsWithGroupsComponent, ScGratitudeComponent, ScHelpNotificationService, ScHoverImageCarouselComponent, ScInputQuantityComponent, ScLinks, ScManagerCardComponent, ScManagerCardPushComponent, ScNewContactFormComponent, ScNewContragentBankAccountsFormComponent, ScNewContragentFormComponent, ScNewsCardComponent, ScNewsCardSkeletonComponent, ScNewsModule, ScNextInputFocusDirective, ScNextInputFocusModule, ScNoindexDirective, ScNoindexWrapperComponent, ScNotifyWhenInStockDialogComponent, ScOrderAccessorDirective, ScOrderDirectionItemsComponent, ScOrderFormComponent, ScOrderItemComponent, ScOrderItemsByDirection, ScOrderItemsListByDirectionsComponent, ScOrderItemsListByStockComponent, ScOrderItemsListComponent, ScOrderModule, ScPaymentStatusComponent, ScPersonalDataProcessingPolicyComponent, ScPhoneFormatPipe, ScPreviewSampleComponent, ScPreviewSampleModule, ScPreviewSamplesMosquitoComponent, ScPriceCardComponent, ScPriceCardInlineComponent, ScPriceHistoryComponent, ScPriceListPaginationComponent, ScPriceWarehouseStockComponent, ScPrintDirective, ScPrintService, ScPrivacyPolicyComponent, ScProductInAllWarehousesPipe, ScProfileAccordionsContentComponent, ScProfileModule, ScPublicOfferComponent, ScQRCodeDialogComponent, ScQRCodeModule, ScResetUserPasswordComponent, ScResourcePreviewComponent, ScSandwichComponent, ScSandwichM2Component, ScSandwichM2SkeletonComponent, ScSandwichSkeletonComponent, ScSelectOnFocusinDirective, ScSeoTagsComponent, ScShareButtonComponent, ScShareButtonModule, ScSignInFormByEmailComponent, ScSignInFormByPhoneComponent, ScSignInFormComponent, ScSignUpFormComponent, ScSimpleSignUpFormComponent, ScSuggestionFieldComponent, ScTelLinkDirective, ScTerminalLinkDirective, ScUpdateUserInfoDialogComponent, ScUserManagersComponent, ScUserModule, ScUserPhoneApproveDialogComponent, ScVerificationModule, ScVerificationPhoneCheckFormComponent, TreeDirective, TreeIconService, TreeLoaderService, TreeTopDirective, cleanupRecaptchaArtifacts, phoneValidator, scAtLeastOneRequiredValidator, scBicValidator, scClientUiIconsName, scCorrespondentAccountValidator, scGetCurrentRoute, scPasswordConfirmMatchingValidator, stepValidator, tuiDateValueTransformerDefaultProvider };
11029
+ export { AbstractScPriceCard, AuthMethod, CURRENT_COUNTRY_ID, CostWithDiscountComponent, FilesAndDocumentsComponent, FilesAndDocumentsModule, FinishDateTimeTransformerDirective, IDLE_ITEM_STATE, IS_DEFAULT_COUNTRY, MAX_FILES_IN_FORM_INPUT, SC_ALLOW_SELECT_TERMINATED, SC_BANNER_DURATION, SC_CATALOG_PRODUCTS_FILTERS, SC_CATALOG_SHOW_PRODUCTS_RECURSIVELY, SC_DATE_FORMATTER, SC_DEBOUNCE_TIME_DEFAULT, SC_DIALOG_SERVICE_TOKEN, SC_ERROR_CHANGE_HANDLER, SC_FAQ_GROUP_QUERY_PARAM, SC_HELP_NOTIFICATION_CLOSE, SC_HELP_NOTIFICATION_LIMIT, SC_HIDDEN_PRINT_ELEMENTS, SC_MANAGER_QR_HANDLER, SC_NOTIFY_WHEN_IN_STOCK_REQUIRED_FIELDS, SC_ORDER_FORM_CONFIG, SC_ORDER_OPTIONS, SC_PAGE_SIZE_OPTIONS$1 as SC_PAGE_SIZE_OPTIONS, SC_SHOW_HELP_NOTIFICATION_IN_PHONE_INPUT, SC_USER_CITY_INFO, SC_USER_INFO, SC_USER_PROVIDERS, SC_VERIFICATION_CODE_TIMEOUT, ScAccordionComponent, ScAccordionContentDirective, ScAccordionModule, ScAddContactDialogComponent, ScAddContragentBankAccountsDialogComponent, ScAddContragentDialogComponent, ScAddDeliveryAddressDialogComponent, ScAddOrEditingCartItemDialogComponent, ScAddOrEditingCartItemFormComponent, ScAddressesSelectionFieldComponent, ScAuthModule, ScBannerComponent, ScBannerModule, ScBrandsListComponent, ScBrandsListModule, ScCartAddProductsFromCsvDialogComponent, ScCatalogFilterCollapsibleComponent, ScCatalogFiltersComponent, ScCatalogModule, ScCategoryCardComponent, ScContactsAccordionComponent, ScContactsModule, ScContragentsAccordionComponent, ScContragentsAccordionItemComponent, ScContragentsModule, ScDeliveryAddressAccordionComponent, ScDeliveryAddressAccordionItemComponent, ScDeliveryAddressModule, ScDownloadPriceListComponent, ScDraftComponent, ScEmailLinkDirective, ScErrorBlockStatusComponent, ScErrorHandlerComponent, ScFavoriteButtonComponent, ScFeedbackFormComponent, ScFocusFirstInvalidFieldDirective, ScFormFieldsModule, ScFormatDatePipe, ScFrequentlyAskedQuestionsComponent, ScFrequentlyAskedQuestionsGroupSelectorComponent, ScFrequentlyAskedQuestionsWithGroupsComponent, ScGratitudeComponent, ScHelpNotificationService, ScHoverImageCarouselComponent, ScInputQuantityComponent, ScLinks, ScManagerCardComponent, ScManagerCardPushComponent, ScNewContactFormComponent, ScNewContragentBankAccountsFormComponent, ScNewContragentFormComponent, ScNewsCardComponent, ScNewsCardSkeletonComponent, ScNewsListComponent, ScNewsModule, ScNextInputFocusDirective, ScNextInputFocusModule, ScNoindexDirective, ScNoindexWrapperComponent, ScNotifyWhenInStockDialogComponent, ScOrderAccessorDirective, ScOrderDirectionItemsComponent, ScOrderFormComponent, ScOrderItemComponent, ScOrderItemsByDirection, ScOrderItemsListByDirectionsComponent, ScOrderItemsListByStockComponent, ScOrderItemsListComponent, ScOrderModule, ScPaginationLinksComponent, ScPaymentStatusComponent, ScPersonalDataProcessingPolicyComponent, ScPhoneFormatPipe, ScPreviewSampleComponent, ScPreviewSampleModule, ScPreviewSamplesMosquitoComponent, ScPriceCardComponent, ScPriceCardInlineComponent, ScPriceHistoryComponent, ScPriceListPaginationComponent, ScPriceWarehouseStockComponent, ScPrintDirective, ScPrintService, ScPrivacyPolicyComponent, ScProductInAllWarehousesPipe, ScProfileAccordionsContentComponent, ScProfileModule, ScPublicOfferComponent, ScQRCodeDialogComponent, ScQRCodeModule, ScResetUserPasswordComponent, ScResourcePreviewComponent, ScSandwichComponent, ScSandwichM2Component, ScSandwichM2SkeletonComponent, ScSandwichSkeletonComponent, ScSelectOnFocusinDirective, ScSeoTagsComponent, ScShareButtonComponent, ScShareButtonModule, ScSignInFormByEmailComponent, ScSignInFormByPhoneComponent, ScSignInFormComponent, ScSignUpFormComponent, ScSimpleSignUpFormComponent, ScSuggestionFieldComponent, ScTelLinkDirective, ScTerminalLinkDirective, ScUpdateUserInfoDialogComponent, ScUserManagersComponent, ScUserModule, ScUserPhoneApproveDialogComponent, ScVerificationModule, ScVerificationPhoneCheckFormComponent, TreeDirective, TreeIconService, TreeLoaderService, TreeTopDirective, cleanupRecaptchaArtifacts, phoneValidator, scAtLeastOneRequiredValidator, scBicValidator, scClientUiIconsName, scCorrespondentAccountValidator, scGetCurrentRoute, scGetFaqGroupQueryParams, scPasswordConfirmMatchingValidator, stepValidator, tuiDateValueTransformerDefaultProvider };
10823
11030
  //# sourceMappingURL=snabcentr-client-ui.mjs.map