UNPKG

@rangertechnologies/ngnxt

Version:

This library was used for creating dymanic UI based on the input JSON/data

373 lines (372 loc) 18.8 kB
import { EventEmitter, ElementRef, Renderer2, SimpleChanges, ChangeDetectorRef } from '@angular/core'; import { MatSort } from '@angular/material/sort'; import { TranslationService } from '../../services/translation/translation.service'; import { DataService } from '../../services/data/data.service'; import { ChangeService } from '../../services/change/change.service'; import { StorageService } from '../../services/storage/storage.service'; import { CountryService } from '../../services/country/country.service'; import * as i0 from "@angular/core"; /** Configuration for a single advanced-filter control. */ export interface AdvancedFilterConfig { /** Data field path (supports dot-notation, e.g. 'employee.name'). */ field: string; /** Human-readable label shown above the control. */ label: string; /** Control type determines which reusable control is rendered. */ type: 'text' | 'date' | 'dropdown' | 'list'; /** Options list for 'dropdown' and 'searchDropdown' types. * Each option should have the shape: { id, name, value, label, ... } * Use `labelField` to pick the display property and `valueField` for the match value. */ options?: any[]; /** Placeholder text shown inside the control. */ placeholder?: string; /** Property on an option object used as display label (default: 'label'). */ labelField?: string; /** Property on an option object used as the filter/match value (default: 'value'). * For searchDropdown, the emitted object `{ id, name, value }` is read with this key. */ valueField?: string; /** CSS width for the control, e.g. '180px'. Defaults to 160px for text, 190px for dropdowns. */ width?: string; /** Evaluation priority. Lower number runs first. Default: index order. */ priority?: number; /** Pre-populate this filter with a default value on init. */ defaultValue?: any; /** If true, the control is rendered in read-only/disabled state. */ disabled?: boolean; /** If true, the filter item is not rendered in the bar. */ hidden?: boolean; } /** SKS1JUL26 Represents a date-range filter value for type:'date' fields. */ export interface AdvancedDateRange { startDate: string; endDate: string; } /** SKS1JUL26 Map of field -> current filter value (scalar or date-range). */ export type AdvancedFilterValues = Record<string, string | AdvancedDateRange | null>; export declare class NxtDatatable { private countryService; private storageService; private cdRef; private translationService; private renderer; private dataService; private changeService; data: any[]; summaryValues: { [label: string]: any; }; tableFilterData: any[]; columns: Array<any>; withCheckBox: boolean; searchBar: boolean; tableSaveButton: boolean; hideSaveButton: boolean; stickyColumn: boolean; tableWidth: string; actionColumHeader: string; actionButton: boolean; title: any; isButtons: boolean; buttonArray: any; tableId: any; isEditRow: boolean; isDeleteRow: boolean; addInlineRecord: boolean; searchConfigs: any; direction: 'rtl' | 'ltr'; pagination: boolean; actionButtonArray: any; multipleFilter: any; isPagination: any; isListViews: any; id: any; isNosIndicator: any; isEditable: any; from: any; question: any; rowTextSize: any; rowTextColor: any; apiMeta: any; summaryRows: any; summaryColumns: any; isLoading: any; tableConfig: any; tableParams: any; listViews: any[]; mode: 'view' | 'edit' | 'print'; languageCode: string; selectedColumn: string | null; allIcons: any[]; isButtonLoading: boolean; isPreview: boolean; groupFilter: boolean; groupFilterConfig: any; groupFilterColumn: any; onlyView: boolean; tableHeight: any; serialNumberColumn: boolean; /** SKS1JUL26 SKS1JUL26: Configuration array for the advanced filter bar. Each entry produces one filter control. */ advancedFilters: AdvancedFilterConfig[]; tableRowClick: EventEmitter<any>; onEditData: EventEmitter<any>; onSaveData: EventEmitter<any>; saveButtonData: EventEmitter<any>; onDeleteData: EventEmitter<any>; buttonEmit: EventEmitter<any>; hyperLinkEmit: EventEmitter<any>; sideNavEmit: EventEmitter<{ data: any; col: any; config: any; }>; actionButtonEmit: EventEmitter<any>; columnSelected: EventEmitter<{ uniqueIdentifier: string; data: any[]; }>; removeColumn: EventEmitter<{ uniqueIdentifier: string; data: any[]; }>; valueChange: EventEmitter<any>; selectedValues: EventEmitter<any[]>; fileEmit: EventEmitter<any>; NxtTableFilterEmit: EventEmitter<any>; hadleDropDownDependent: EventEmitter<any>; NxtTableParamsEmit: EventEmitter<any>; sort: MatSort; tableContainer: ElementRef<HTMLElement>; selection: any; stickyCondition: number; searchFilter: boolean; filterArray: Array<any>; selectedFilter: any; pageSizeOptions: Array<any>; dataSource: any; totalCount: number; searchBoxValue: any; prevSearch: any; activeColumn: string | null; isScrolled: boolean; isShadowHidden: boolean; currentSortColumn: string; currentSortDirection: 'asc' | 'desc' | 'none'; originalData: any; hoveredColumn: string | null; searchText: any; multipleFilterArray: any; tableFilterArray: any; filterDataArray: any; isResized: boolean; sFilterData: any; currentColumns: Array<any>; inlineElement: any; pageSize: any; pageIndex: any; totalRecords: number; deleteData: any; deleteModal: boolean; dropdownActionButton: any; currentOpenIndex: number | null; clickListener: any; deleteIndex: number; showPopover: boolean; isSummaryColumn: boolean; isSummaryStartColumn: any[]; isSummaryEndColumn: any[]; filterBoxData: any; filterTableNos: any; selectedView: any; isDropdownOpen: boolean; currentViewFilter: any; isFullTableSummaryRow: boolean; isImageHover: boolean; isImageEdit: boolean; selectedImageElement: any; private questionsCache; isResizing: boolean; private currentColumn; private startX; private startWidth; private resizeFrameId; columnWidthTrack: any; currentTableData: any; oldTableData: any; viewEdit: boolean; currencyOption: any; columnSourceId: any; summaryRowsOrginal: any; displaySummaryRows: any; Array: ArrayConstructor; tableEditTrack: boolean; alignRight: boolean; selectedIsEmpty: boolean; private destroy$; private timers; /** Current values for every advanced filter control. */ advancedFilterValues: AdvancedFilterValues; /** * SKS1JUL26: Emits a JSON-serialised snapshot of advancedFilterValues * so that debounceTime(300) + distinctUntilChanged() both work correctly. * Subject<void> makes distinctUntilChanged useless because every emission * looks the same. Subject<string> compares serialised state. */ private advancedFilter$; constructor(countryService: CountryService, storageService: StorageService, cdRef: ChangeDetectorRef, translationService: TranslationService, renderer: Renderer2, dataService: DataService, changeService: ChangeService); ngOnChanges(changes: SimpleChanges): void; ngOnInit(): void; ngAfterViewInit(): void; autoDistributeExtraTableWidth(from?: any): void; onResizeStart(event: MouseEvent): void; private onResizeMove; private applyWidthToColumn; private onResizeEnd; ngOnDestroy(): void; computeSummaryColumns(): void; computeSummaryValues(from?: any): void; sortData(column: string, sortingState?: any | undefined, currentState?: any | undefined, from?: any): void; onScroll(tableContainer: HTMLElement): void; onDocumentClick(event: any): void; filter(datas: any, event: MouseEvent): void; pageParams(event: any, from?: any): void; /** SKS29OCT25 Formats a cell value exactly the way it appears in the UI */ private formatDateForSearch; applyFilter(event: any, from?: any): void; /** SKS15FEB25 Whether the number of selected elements matches the total number of rows. */ isAllSelected(): boolean; /** SKS15FEB25 Selects all rows if they are not all selected; otherwise clear selection. */ masterToggle(): void; isSomeSelected(): boolean; separateRowSelect(data: any, element: any): void; tableClick(data: any): void; getNestedValue(obj: any, path: string): any; filterRetain(filterkeyMap: any, from?: any): void; removeDuplicates(objects: any): any[]; deleteRecord(data: any, index: number): void; deleteRecordData(): void; saveButton(element: any): void; private isSameRow; private normalizeRow; onEdit(data: any): void; onSave(data: any): void; commonButtonClick(button: any): void; getObjValue(element: any, column: string): any; onClickHyperlink(column: any, element: any, isHyperLink: any): void; addTableRecord(element: any, from?: any): void; prepareActionVisibility(rows: any[]): any[]; evaluateConditionString(row: any, condition: string): boolean; onSearch(event: any, from?: any): void; emptySearch(event: any): void; onSideNavInfoClick(data: any, col: any): void; onColumnClick(uniqueIdentifier: string): void; closefilter(from?: any): void; isSelected(event: any): boolean; checkedData(event: any, from?: any): void; private addClickOutsideListener; private removeClickListener; toggleDropdown(index: number): void; actionButtonClicked(event: any, data: any): void; removeCol(uniqueIdentifier: string): void; emitTableDataValue(updatedTableData: any): void; updateEdit(index: number, value: any, element: any, column: any, type?: any): void; updateValue(element: any, column: string, value: any): any; expenseAttachment(event: any): void; listViewEmit(event: any): void; onImageEdit(ques: any): Promise<void>; onImageDelete(ques: any): Promise<void>; fileChangeEvent(ques: any, event: any): Promise<void>; private readFileAsDataURL; getDropDown(event: any): void; trackByRow(index: number, row: any): any; trackByColumn(index: number, column: any): any; trackBySummary(index: number, summary: any): any; trackByIndex(index: number): number; editModeChange(): void; saveTable(): void; discardChanges(): void; groupFilterEmit(event: any, from?: any): void; groupFilterRetain(filterkey: any, from?: any): void; changeAnnounce(event: any): void; /** * THE SINGLE UNIFIED FILTER PIPELINE (client-side mode). * * Pipeline order matches the documented priority: * originalData * 1. List View → sFilterData (managed by listViewEmit / ngOnChanges) * 2. Advanced Filter → applyAdvancedFilters(sFilterData) * 3. Global Search → searchBoxValue contains match * 4. Column Filter → filterDataArray exact match * 5. Sort → currentSortColumn / currentSortDirection * 6. Pagination → pageIndex / pageSize → dataSource.data * * For server-side (pagination=true), we skip client filtering and just emit * the full params object (including advancedFilterData) to the parent. * * All event handlers (onAdvancedFilterChange, applyFilter, filterRetain, * checkedData, closefilter, pageParams) ultimately call this method so * there is exactly ONE place where filtering logic lives. */ refreshTableData(from?: string): void; /** * Builds the `advancedFilterValues` map from the current `advancedFilters` config. * Existing values are preserved if their field still exists in the new config. * Respects `defaultValue` from the config for initial population. */ initializeAdvancedFilters(): void; /** * Called from the template whenever any advanced filter control changes. * * @param field - The data field this filter maps to * @param value - New value: * - text/dropdown: plain string * - searchDropdown: scalar extracted via config.valueField from * the emitted object shape `{ id, name, value, label, ... }` * - date: ISO 8601 string from app-nxt-datepicker * @param subKey - For date filters only: 'startDate' | 'endDate' */ onAdvancedFilterChange(field: string, value: any, subKey?: 'startDate' | 'endDate'): void; /** * Applies current advancedFilterValues against a data array. * Returns a new filtered array — never mutates the input. * * Reuses existing helpers: * - getObjValue() for field access * - formatDateForSearch() for display-safe date formatting (NxtDatePipe) * * Date comparison uses formatDateForSearch() on both cell and filter values * so timezone handling is consistent with the rest of the table. * * Filter logic per type: * text → case-insensitive contains * dropdown → strict string equality * searchDropdown → strict string equality on extracted valueField * date → >= startDate and/or <= endDate (normalised via NxtDatePipe) */ applyAdvancedFilters(baseData: any[]): any[]; /** * Resets all advanced filter values and re-runs the unified pipeline. * pageIndex is reset to 1 so users don't get confused on high page numbers. */ clearAdvancedFilters(): void; /** * Returns true if at least one visible advanced filter field has a non-empty value. * Used in the template to decide whether to show the clear-all button. */ hasAdvancedFilter(): boolean; /** * Returns a clean snapshot of the ACTIVE advanced filter values. * Included in NxtTableParamsEmit so server-side implementations receive * the filter state under the `advancedFilterData` key: * * tableParams = { * pagination: { pageSize, pageIndex }, * tableSearch: { fields, value }, * searchFilterData: { [column]: [values] }, * advancedFilterData: { [field]: string | AdvancedDateRange }, ← NEW * sort: { column, direction, listView }, * } */ buildAdvancedFilterObject(): AdvancedFilterValues; static ɵfac: i0.ɵɵFactoryDeclaration<NxtDatatable, never>; static ɵcmp: i0.ɵɵComponentDeclaration<NxtDatatable, "nxt-datatable", never, { "data": { "alias": "data"; "required": false; }; "summaryValues": { "alias": "summaryValues"; "required": false; }; "tableFilterData": { "alias": "tableFilterData"; "required": false; }; "columns": { "alias": "columns"; "required": false; }; "withCheckBox": { "alias": "withCheckBox"; "required": false; }; "searchBar": { "alias": "searchBar"; "required": false; }; "tableSaveButton": { "alias": "tableSaveButton"; "required": false; }; "hideSaveButton": { "alias": "hideSaveButton"; "required": false; }; "stickyColumn": { "alias": "stickyColumn"; "required": false; }; "tableWidth": { "alias": "tableWidth"; "required": false; }; "actionColumHeader": { "alias": "actionColumHeader"; "required": false; }; "actionButton": { "alias": "actionButton"; "required": false; }; "title": { "alias": "title"; "required": false; }; "isButtons": { "alias": "isButtons"; "required": false; }; "buttonArray": { "alias": "buttonArray"; "required": false; }; "tableId": { "alias": "tableId"; "required": false; }; "isEditRow": { "alias": "isEditRow"; "required": false; }; "isDeleteRow": { "alias": "isDeleteRow"; "required": false; }; "addInlineRecord": { "alias": "addInlineRecord"; "required": false; }; "searchConfigs": { "alias": "searchConfigs"; "required": false; }; "direction": { "alias": "direction"; "required": false; }; "pagination": { "alias": "pagination"; "required": false; }; "actionButtonArray": { "alias": "actionButtonArray"; "required": false; }; "multipleFilter": { "alias": "multipleFilter"; "required": false; }; "isPagination": { "alias": "isPagination"; "required": false; }; "isListViews": { "alias": "isListViews"; "required": false; }; "id": { "alias": "id"; "required": false; }; "isNosIndicator": { "alias": "isNosIndicator"; "required": false; }; "isEditable": { "alias": "isEditable"; "required": false; }; "from": { "alias": "from"; "required": false; }; "question": { "alias": "question"; "required": false; }; "rowTextSize": { "alias": "rowTextSize"; "required": false; }; "rowTextColor": { "alias": "rowTextColor"; "required": false; }; "apiMeta": { "alias": "apiMeta"; "required": false; }; "summaryRows": { "alias": "summaryRows"; "required": false; }; "summaryColumns": { "alias": "summaryColumns"; "required": false; }; "isLoading": { "alias": "isLoading"; "required": false; }; "tableConfig": { "alias": "tableConfig"; "required": false; }; "tableParams": { "alias": "tableParams"; "required": false; }; "listViews": { "alias": "listViews"; "required": false; }; "mode": { "alias": "mode"; "required": false; }; "languageCode": { "alias": "languageCode"; "required": false; }; "selectedColumn": { "alias": "selectedColumn"; "required": false; }; "allIcons": { "alias": "allIcons"; "required": false; }; "isButtonLoading": { "alias": "isButtonLoading"; "required": false; }; "isPreview": { "alias": "isPreview"; "required": false; }; "groupFilter": { "alias": "groupFilter"; "required": false; }; "groupFilterConfig": { "alias": "groupFilterConfig"; "required": false; }; "groupFilterColumn": { "alias": "groupFilterColumn"; "required": false; }; "onlyView": { "alias": "onlyView"; "required": false; }; "tableHeight": { "alias": "tableHeight"; "required": false; }; "serialNumberColumn": { "alias": "serialNumberColumn"; "required": false; }; "advancedFilters": { "alias": "advancedFilters"; "required": false; }; }, { "tableRowClick": "tableRowClick"; "onEditData": "onEditData"; "onSaveData": "onSaveData"; "saveButtonData": "saveButtonData"; "onDeleteData": "onDeleteData"; "buttonEmit": "buttonEmit"; "hyperLinkEmit": "hyperLinkEmit"; "sideNavEmit": "sideNavEmit"; "actionButtonEmit": "actionButtonEmit"; "columnSelected": "columnSelected"; "removeColumn": "removeColumn"; "valueChange": "valueChange"; "selectedValues": "selectedValues"; "fileEmit": "fileEmit"; "NxtTableFilterEmit": "NxtTableFilterEmit"; "hadleDropDownDependent": "hadleDropDownDependent"; "NxtTableParamsEmit": "NxtTableParamsEmit"; }, never, never, true, never>; }