import { isDataSource } from './_data-source-chunk.mjs'; export { DataSource } from './_data-source-chunk.mjs'; import * as i0 from '@angular/core'; import { InjectionToken, inject, TemplateRef, Directive, booleanAttribute, Input, ContentChild, ElementRef, IterableDiffers, ViewContainerRef, Component, ChangeDetectionStrategy, ViewEncapsulation, afterNextRender, ChangeDetectorRef, Injector, DOCUMENT, EventEmitter, HostAttributeToken, Output, ContentChildren, ViewChild, NgModule } from '@angular/core'; import { Subject, BehaviorSubject, isObservable, of, combineLatest, animationFrameScheduler, asapScheduler } from 'rxjs'; import { takeUntil, auditTime } from 'rxjs/operators'; import { ViewportRuler, CDK_VIRTUAL_SCROLL_VIEWPORT, ScrollingModule } from './scrolling.mjs'; import { _DisposeViewRepeaterStrategy } from './_dispose-view-repeater-strategy-chunk.mjs'; import { _RecycleViewRepeaterStrategy, _ViewRepeaterOperation } from './_recycle-view-repeater-strategy-chunk.mjs'; import { Directionality } from './_directionality-chunk.mjs'; import { Platform } from './_platform-chunk.mjs'; import './_element-chunk.mjs'; import './_scrolling-chunk.mjs'; import './bidi.mjs'; import '@angular/common'; const CDK_TABLE = new InjectionToken('CDK_TABLE'); const TEXT_COLUMN_OPTIONS = new InjectionToken('text-column-options'); class CdkCellDef { template = inject(TemplateRef); constructor() {} static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkCellDef, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: CdkCellDef, isStandalone: true, selector: "[cdkCellDef]", ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkCellDef, decorators: [{ type: Directive, args: [{ selector: '[cdkCellDef]' }] }], ctorParameters: () => [] }); class CdkHeaderCellDef { template = inject(TemplateRef); constructor() {} static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkHeaderCellDef, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: CdkHeaderCellDef, isStandalone: true, selector: "[cdkHeaderCellDef]", ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkHeaderCellDef, decorators: [{ type: Directive, args: [{ selector: '[cdkHeaderCellDef]' }] }], ctorParameters: () => [] }); class CdkFooterCellDef { template = inject(TemplateRef); constructor() {} static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkFooterCellDef, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: CdkFooterCellDef, isStandalone: true, selector: "[cdkFooterCellDef]", ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkFooterCellDef, decorators: [{ type: Directive, args: [{ selector: '[cdkFooterCellDef]' }] }], ctorParameters: () => [] }); class CdkColumnDef { _table = inject(CDK_TABLE, { optional: true }); _hasStickyChanged = false; get name() { return this._name; } set name(name) { this._setNameInput(name); } _name; get sticky() { return this._sticky; } set sticky(value) { if (value !== this._sticky) { this._sticky = value; this._hasStickyChanged = true; } } _sticky = false; get stickyEnd() { return this._stickyEnd; } set stickyEnd(value) { if (value !== this._stickyEnd) { this._stickyEnd = value; this._hasStickyChanged = true; } } _stickyEnd = false; cell; headerCell; footerCell; cssClassFriendlyName; _columnCssClassName; constructor() {} hasStickyChanged() { const hasStickyChanged = this._hasStickyChanged; this.resetStickyChanged(); return hasStickyChanged; } resetStickyChanged() { this._hasStickyChanged = false; } _updateColumnCssClassName() { this._columnCssClassName = [`cdk-column-${this.cssClassFriendlyName}`]; } _setNameInput(value) { if (value) { this._name = value; this.cssClassFriendlyName = value.replace(/[^a-z0-9_-]/gi, '-'); this._updateColumnCssClassName(); } } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkColumnDef, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "16.1.0", version: "21.0.3", type: CdkColumnDef, isStandalone: true, selector: "[cdkColumnDef]", inputs: { name: ["cdkColumnDef", "name"], sticky: ["sticky", "sticky", booleanAttribute], stickyEnd: ["stickyEnd", "stickyEnd", booleanAttribute] }, providers: [{ provide: 'MAT_SORT_HEADER_COLUMN_DEF', useExisting: CdkColumnDef }], queries: [{ propertyName: "cell", first: true, predicate: CdkCellDef, descendants: true }, { propertyName: "headerCell", first: true, predicate: CdkHeaderCellDef, descendants: true }, { propertyName: "footerCell", first: true, predicate: CdkFooterCellDef, descendants: true }], ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkColumnDef, decorators: [{ type: Directive, args: [{ selector: '[cdkColumnDef]', providers: [{ provide: 'MAT_SORT_HEADER_COLUMN_DEF', useExisting: CdkColumnDef }] }] }], ctorParameters: () => [], propDecorators: { name: [{ type: Input, args: ['cdkColumnDef'] }], sticky: [{ type: Input, args: [{ transform: booleanAttribute }] }], stickyEnd: [{ type: Input, args: [{ transform: booleanAttribute }] }], cell: [{ type: ContentChild, args: [CdkCellDef] }], headerCell: [{ type: ContentChild, args: [CdkHeaderCellDef] }], footerCell: [{ type: ContentChild, args: [CdkFooterCellDef] }] } }); class BaseCdkCell { constructor(columnDef, elementRef) { elementRef.nativeElement.classList.add(...columnDef._columnCssClassName); } } class CdkHeaderCell extends BaseCdkCell { constructor() { super(inject(CdkColumnDef), inject(ElementRef)); } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkHeaderCell, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: CdkHeaderCell, isStandalone: true, selector: "cdk-header-cell, th[cdk-header-cell]", host: { attributes: { "role": "columnheader" }, classAttribute: "cdk-header-cell" }, usesInheritance: true, ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkHeaderCell, decorators: [{ type: Directive, args: [{ selector: 'cdk-header-cell, th[cdk-header-cell]', host: { 'class': 'cdk-header-cell', 'role': 'columnheader' } }] }], ctorParameters: () => [] }); class CdkFooterCell extends BaseCdkCell { constructor() { const columnDef = inject(CdkColumnDef); const elementRef = inject(ElementRef); super(columnDef, elementRef); const role = columnDef._table?._getCellRole(); if (role) { elementRef.nativeElement.setAttribute('role', role); } } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkFooterCell, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: CdkFooterCell, isStandalone: true, selector: "cdk-footer-cell, td[cdk-footer-cell]", host: { classAttribute: "cdk-footer-cell" }, usesInheritance: true, ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkFooterCell, decorators: [{ type: Directive, args: [{ selector: 'cdk-footer-cell, td[cdk-footer-cell]', host: { 'class': 'cdk-footer-cell' } }] }], ctorParameters: () => [] }); class CdkCell extends BaseCdkCell { constructor() { const columnDef = inject(CdkColumnDef); const elementRef = inject(ElementRef); super(columnDef, elementRef); const role = columnDef._table?._getCellRole(); if (role) { elementRef.nativeElement.setAttribute('role', role); } } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkCell, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: CdkCell, isStandalone: true, selector: "cdk-cell, td[cdk-cell]", host: { classAttribute: "cdk-cell" }, usesInheritance: true, ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkCell, decorators: [{ type: Directive, args: [{ selector: 'cdk-cell, td[cdk-cell]', host: { 'class': 'cdk-cell' } }] }], ctorParameters: () => [] }); const CDK_ROW_TEMPLATE = ``; class BaseRowDef { template = inject(TemplateRef); _differs = inject(IterableDiffers); columns; _columnsDiffer; constructor() {} ngOnChanges(changes) { if (!this._columnsDiffer) { const columns = changes['columns'] && changes['columns'].currentValue || []; this._columnsDiffer = this._differs.find(columns).create(); this._columnsDiffer.diff(columns); } } getColumnsDiff() { return this._columnsDiffer.diff(this.columns); } extractCellTemplate(column) { if (this instanceof CdkHeaderRowDef) { return column.headerCell.template; } if (this instanceof CdkFooterRowDef) { return column.footerCell.template; } else { return column.cell.template; } } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: BaseRowDef, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: BaseRowDef, isStandalone: true, usesOnChanges: true, ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: BaseRowDef, decorators: [{ type: Directive }], ctorParameters: () => [] }); class CdkHeaderRowDef extends BaseRowDef { _table = inject(CDK_TABLE, { optional: true }); _hasStickyChanged = false; get sticky() { return this._sticky; } set sticky(value) { if (value !== this._sticky) { this._sticky = value; this._hasStickyChanged = true; } } _sticky = false; constructor() { super(inject(TemplateRef), inject(IterableDiffers)); } ngOnChanges(changes) { super.ngOnChanges(changes); } hasStickyChanged() { const hasStickyChanged = this._hasStickyChanged; this.resetStickyChanged(); return hasStickyChanged; } resetStickyChanged() { this._hasStickyChanged = false; } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkHeaderRowDef, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "16.1.0", version: "21.0.3", type: CdkHeaderRowDef, isStandalone: true, selector: "[cdkHeaderRowDef]", inputs: { columns: ["cdkHeaderRowDef", "columns"], sticky: ["cdkHeaderRowDefSticky", "sticky", booleanAttribute] }, usesInheritance: true, usesOnChanges: true, ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkHeaderRowDef, decorators: [{ type: Directive, args: [{ selector: '[cdkHeaderRowDef]', inputs: [{ name: 'columns', alias: 'cdkHeaderRowDef' }] }] }], ctorParameters: () => [], propDecorators: { sticky: [{ type: Input, args: [{ alias: 'cdkHeaderRowDefSticky', transform: booleanAttribute }] }] } }); class CdkFooterRowDef extends BaseRowDef { _table = inject(CDK_TABLE, { optional: true }); _hasStickyChanged = false; get sticky() { return this._sticky; } set sticky(value) { if (value !== this._sticky) { this._sticky = value; this._hasStickyChanged = true; } } _sticky = false; constructor() { super(inject(TemplateRef), inject(IterableDiffers)); } ngOnChanges(changes) { super.ngOnChanges(changes); } hasStickyChanged() { const hasStickyChanged = this._hasStickyChanged; this.resetStickyChanged(); return hasStickyChanged; } resetStickyChanged() { this._hasStickyChanged = false; } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkFooterRowDef, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "16.1.0", version: "21.0.3", type: CdkFooterRowDef, isStandalone: true, selector: "[cdkFooterRowDef]", inputs: { columns: ["cdkFooterRowDef", "columns"], sticky: ["cdkFooterRowDefSticky", "sticky", booleanAttribute] }, usesInheritance: true, usesOnChanges: true, ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkFooterRowDef, decorators: [{ type: Directive, args: [{ selector: '[cdkFooterRowDef]', inputs: [{ name: 'columns', alias: 'cdkFooterRowDef' }] }] }], ctorParameters: () => [], propDecorators: { sticky: [{ type: Input, args: [{ alias: 'cdkFooterRowDefSticky', transform: booleanAttribute }] }] } }); class CdkRowDef extends BaseRowDef { _table = inject(CDK_TABLE, { optional: true }); when; constructor() { super(inject(TemplateRef), inject(IterableDiffers)); } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkRowDef, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: CdkRowDef, isStandalone: true, selector: "[cdkRowDef]", inputs: { columns: ["cdkRowDefColumns", "columns"], when: ["cdkRowDefWhen", "when"] }, usesInheritance: true, ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkRowDef, decorators: [{ type: Directive, args: [{ selector: '[cdkRowDef]', inputs: [{ name: 'columns', alias: 'cdkRowDefColumns' }, { name: 'when', alias: 'cdkRowDefWhen' }] }] }], ctorParameters: () => [] }); class CdkCellOutlet { _viewContainer = inject(ViewContainerRef); cells; context; static mostRecentCellOutlet = null; constructor() { CdkCellOutlet.mostRecentCellOutlet = this; } ngOnDestroy() { if (CdkCellOutlet.mostRecentCellOutlet === this) { CdkCellOutlet.mostRecentCellOutlet = null; } } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkCellOutlet, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: CdkCellOutlet, isStandalone: true, selector: "[cdkCellOutlet]", ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkCellOutlet, decorators: [{ type: Directive, args: [{ selector: '[cdkCellOutlet]' }] }], ctorParameters: () => [] }); class CdkHeaderRow { static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkHeaderRow, deps: [], target: i0.ɵɵFactoryTarget.Component }); static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "21.0.3", type: CdkHeaderRow, isStandalone: true, selector: "cdk-header-row, tr[cdk-header-row]", host: { attributes: { "role": "row" }, classAttribute: "cdk-header-row" }, ngImport: i0, template: "", isInline: true, dependencies: [{ kind: "directive", type: CdkCellOutlet, selector: "[cdkCellOutlet]" }], changeDetection: i0.ChangeDetectionStrategy.Default, encapsulation: i0.ViewEncapsulation.None }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkHeaderRow, decorators: [{ type: Component, args: [{ selector: 'cdk-header-row, tr[cdk-header-row]', template: CDK_ROW_TEMPLATE, host: { 'class': 'cdk-header-row', 'role': 'row' }, changeDetection: ChangeDetectionStrategy.Default, encapsulation: ViewEncapsulation.None, imports: [CdkCellOutlet] }] }] }); class CdkFooterRow { static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkFooterRow, deps: [], target: i0.ɵɵFactoryTarget.Component }); static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "21.0.3", type: CdkFooterRow, isStandalone: true, selector: "cdk-footer-row, tr[cdk-footer-row]", host: { attributes: { "role": "row" }, classAttribute: "cdk-footer-row" }, ngImport: i0, template: "", isInline: true, dependencies: [{ kind: "directive", type: CdkCellOutlet, selector: "[cdkCellOutlet]" }], changeDetection: i0.ChangeDetectionStrategy.Default, encapsulation: i0.ViewEncapsulation.None }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkFooterRow, decorators: [{ type: Component, args: [{ selector: 'cdk-footer-row, tr[cdk-footer-row]', template: CDK_ROW_TEMPLATE, host: { 'class': 'cdk-footer-row', 'role': 'row' }, changeDetection: ChangeDetectionStrategy.Default, encapsulation: ViewEncapsulation.None, imports: [CdkCellOutlet] }] }] }); class CdkRow { static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkRow, deps: [], target: i0.ɵɵFactoryTarget.Component }); static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "21.0.3", type: CdkRow, isStandalone: true, selector: "cdk-row, tr[cdk-row]", host: { attributes: { "role": "row" }, classAttribute: "cdk-row" }, ngImport: i0, template: "", isInline: true, dependencies: [{ kind: "directive", type: CdkCellOutlet, selector: "[cdkCellOutlet]" }], changeDetection: i0.ChangeDetectionStrategy.Default, encapsulation: i0.ViewEncapsulation.None }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkRow, decorators: [{ type: Component, args: [{ selector: 'cdk-row, tr[cdk-row]', template: CDK_ROW_TEMPLATE, host: { 'class': 'cdk-row', 'role': 'row' }, changeDetection: ChangeDetectionStrategy.Default, encapsulation: ViewEncapsulation.None, imports: [CdkCellOutlet] }] }] }); class CdkNoDataRow { templateRef = inject(TemplateRef); _contentClassNames = ['cdk-no-data-row', 'cdk-row']; _cellClassNames = ['cdk-cell', 'cdk-no-data-cell']; _cellSelector = 'td, cdk-cell, [cdk-cell], .cdk-cell'; constructor() {} static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkNoDataRow, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: CdkNoDataRow, isStandalone: true, selector: "ng-template[cdkNoDataRow]", ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkNoDataRow, decorators: [{ type: Directive, args: [{ selector: 'ng-template[cdkNoDataRow]' }] }], ctorParameters: () => [] }); const STICKY_DIRECTIONS = ['top', 'bottom', 'left', 'right']; class StickyStyler { _isNativeHtmlTable; _stickCellCss; _isBrowser; _needsPositionStickyOnElement; direction; _positionListener; _tableInjector; _elemSizeCache = new WeakMap(); _resizeObserver = globalThis?.ResizeObserver ? new globalThis.ResizeObserver(entries => this._updateCachedSizes(entries)) : null; _updatedStickyColumnsParamsToReplay = []; _stickyColumnsReplayTimeout = null; _cachedCellWidths = []; _borderCellCss; _destroyed = false; constructor(_isNativeHtmlTable, _stickCellCss, _isBrowser = true, _needsPositionStickyOnElement = true, direction, _positionListener, _tableInjector) { this._isNativeHtmlTable = _isNativeHtmlTable; this._stickCellCss = _stickCellCss; this._isBrowser = _isBrowser; this._needsPositionStickyOnElement = _needsPositionStickyOnElement; this.direction = direction; this._positionListener = _positionListener; this._tableInjector = _tableInjector; this._borderCellCss = { 'top': `${_stickCellCss}-border-elem-top`, 'bottom': `${_stickCellCss}-border-elem-bottom`, 'left': `${_stickCellCss}-border-elem-left`, 'right': `${_stickCellCss}-border-elem-right` }; } clearStickyPositioning(rows, stickyDirections) { if (stickyDirections.includes('left') || stickyDirections.includes('right')) { this._removeFromStickyColumnReplayQueue(rows); } const elementsToClear = []; for (const row of rows) { if (row.nodeType !== row.ELEMENT_NODE) { continue; } elementsToClear.push(row, ...Array.from(row.children)); } afterNextRender({ write: () => { for (const element of elementsToClear) { this._removeStickyStyle(element, stickyDirections); } } }, { injector: this._tableInjector }); } updateStickyColumns(rows, stickyStartStates, stickyEndStates, recalculateCellWidths = true, replay = true) { if (!rows.length || !this._isBrowser || !(stickyStartStates.some(state => state) || stickyEndStates.some(state => state))) { this._positionListener?.stickyColumnsUpdated({ sizes: [] }); this._positionListener?.stickyEndColumnsUpdated({ sizes: [] }); return; } const firstRow = rows[0]; const numCells = firstRow.children.length; const isRtl = this.direction === 'rtl'; const start = isRtl ? 'right' : 'left'; const end = isRtl ? 'left' : 'right'; const lastStickyStart = stickyStartStates.lastIndexOf(true); const firstStickyEnd = stickyEndStates.indexOf(true); let cellWidths; let startPositions; let endPositions; if (replay) { this._updateStickyColumnReplayQueue({ rows: [...rows], stickyStartStates: [...stickyStartStates], stickyEndStates: [...stickyEndStates] }); } afterNextRender({ earlyRead: () => { cellWidths = this._getCellWidths(firstRow, recalculateCellWidths); startPositions = this._getStickyStartColumnPositions(cellWidths, stickyStartStates); endPositions = this._getStickyEndColumnPositions(cellWidths, stickyEndStates); }, write: () => { for (const row of rows) { for (let i = 0; i < numCells; i++) { const cell = row.children[i]; if (stickyStartStates[i]) { this._addStickyStyle(cell, start, startPositions[i], i === lastStickyStart); } if (stickyEndStates[i]) { this._addStickyStyle(cell, end, endPositions[i], i === firstStickyEnd); } } } if (this._positionListener && cellWidths.some(w => !!w)) { this._positionListener.stickyColumnsUpdated({ sizes: lastStickyStart === -1 ? [] : cellWidths.slice(0, lastStickyStart + 1).map((width, index) => stickyStartStates[index] ? width : null) }); this._positionListener.stickyEndColumnsUpdated({ sizes: firstStickyEnd === -1 ? [] : cellWidths.slice(firstStickyEnd).map((width, index) => stickyEndStates[index + firstStickyEnd] ? width : null).reverse() }); } } }, { injector: this._tableInjector }); } stickRows(rowsToStick, stickyStates, position) { if (!this._isBrowser) { return; } const rows = position === 'bottom' ? rowsToStick.slice().reverse() : rowsToStick; const states = position === 'bottom' ? stickyStates.slice().reverse() : stickyStates; const stickyOffsets = []; const stickyCellHeights = []; const elementsToStick = []; afterNextRender({ earlyRead: () => { for (let rowIndex = 0, stickyOffset = 0; rowIndex < rows.length; rowIndex++) { if (!states[rowIndex]) { continue; } stickyOffsets[rowIndex] = stickyOffset; const row = rows[rowIndex]; elementsToStick[rowIndex] = this._isNativeHtmlTable ? Array.from(row.children) : [row]; const height = this._retrieveElementSize(row).height; stickyOffset += height; stickyCellHeights[rowIndex] = height; } }, write: () => { const borderedRowIndex = states.lastIndexOf(true); for (let rowIndex = 0; rowIndex < rows.length; rowIndex++) { if (!states[rowIndex]) { continue; } const offset = stickyOffsets[rowIndex]; const isBorderedRowIndex = rowIndex === borderedRowIndex; for (const element of elementsToStick[rowIndex]) { this._addStickyStyle(element, position, offset, isBorderedRowIndex); } } if (position === 'top') { this._positionListener?.stickyHeaderRowsUpdated({ sizes: stickyCellHeights, offsets: stickyOffsets, elements: elementsToStick }); } else { this._positionListener?.stickyFooterRowsUpdated({ sizes: stickyCellHeights, offsets: stickyOffsets, elements: elementsToStick }); } } }, { injector: this._tableInjector }); } updateStickyFooterContainer(tableElement, stickyStates) { if (!this._isNativeHtmlTable) { return; } afterNextRender({ write: () => { const tfoot = tableElement.querySelector('tfoot'); if (tfoot) { if (stickyStates.some(state => !state)) { this._removeStickyStyle(tfoot, ['bottom']); } else { this._addStickyStyle(tfoot, 'bottom', 0, false); } } } }, { injector: this._tableInjector }); } destroy() { if (this._stickyColumnsReplayTimeout) { clearTimeout(this._stickyColumnsReplayTimeout); } this._resizeObserver?.disconnect(); this._destroyed = true; } _removeStickyStyle(element, stickyDirections) { if (!element.classList.contains(this._stickCellCss)) { return; } for (const dir of stickyDirections) { element.style[dir] = ''; element.classList.remove(this._borderCellCss[dir]); } const hasDirection = STICKY_DIRECTIONS.some(dir => stickyDirections.indexOf(dir) === -1 && element.style[dir]); if (hasDirection) { element.style.zIndex = this._getCalculatedZIndex(element); } else { element.style.zIndex = ''; if (this._needsPositionStickyOnElement) { element.style.position = ''; } element.classList.remove(this._stickCellCss); } } _addStickyStyle(element, dir, dirValue, isBorderElement) { element.classList.add(this._stickCellCss); if (isBorderElement) { element.classList.add(this._borderCellCss[dir]); } element.style[dir] = `${dirValue}px`; element.style.zIndex = this._getCalculatedZIndex(element); if (this._needsPositionStickyOnElement) { element.style.cssText += 'position: -webkit-sticky; position: sticky; '; } } _getCalculatedZIndex(element) { const zIndexIncrements = { top: 100, bottom: 10, left: 1, right: 1 }; let zIndex = 0; for (const dir of STICKY_DIRECTIONS) { if (element.style[dir]) { zIndex += zIndexIncrements[dir]; } } return zIndex ? `${zIndex}` : ''; } _getCellWidths(row, recalculateCellWidths = true) { if (!recalculateCellWidths && this._cachedCellWidths.length) { return this._cachedCellWidths; } const cellWidths = []; const firstRowCells = row.children; for (let i = 0; i < firstRowCells.length; i++) { const cell = firstRowCells[i]; cellWidths.push(this._retrieveElementSize(cell).width); } this._cachedCellWidths = cellWidths; return cellWidths; } _getStickyStartColumnPositions(widths, stickyStates) { const positions = []; let nextPosition = 0; for (let i = 0; i < widths.length; i++) { if (stickyStates[i]) { positions[i] = nextPosition; nextPosition += widths[i]; } } return positions; } _getStickyEndColumnPositions(widths, stickyStates) { const positions = []; let nextPosition = 0; for (let i = widths.length; i > 0; i--) { if (stickyStates[i]) { positions[i] = nextPosition; nextPosition += widths[i]; } } return positions; } _retrieveElementSize(element) { const cachedSize = this._elemSizeCache.get(element); if (cachedSize) { return cachedSize; } const clientRect = element.getBoundingClientRect(); const size = { width: clientRect.width, height: clientRect.height }; if (!this._resizeObserver) { return size; } this._elemSizeCache.set(element, size); this._resizeObserver.observe(element, { box: 'border-box' }); return size; } _updateStickyColumnReplayQueue(params) { this._removeFromStickyColumnReplayQueue(params.rows); if (!this._stickyColumnsReplayTimeout) { this._updatedStickyColumnsParamsToReplay.push(params); } } _removeFromStickyColumnReplayQueue(rows) { const rowsSet = new Set(rows); for (const update of this._updatedStickyColumnsParamsToReplay) { update.rows = update.rows.filter(row => !rowsSet.has(row)); } this._updatedStickyColumnsParamsToReplay = this._updatedStickyColumnsParamsToReplay.filter(update => !!update.rows.length); } _updateCachedSizes(entries) { let needsColumnUpdate = false; for (const entry of entries) { const newEntry = entry.borderBoxSize?.length ? { width: entry.borderBoxSize[0].inlineSize, height: entry.borderBoxSize[0].blockSize } : { width: entry.contentRect.width, height: entry.contentRect.height }; if (newEntry.width !== this._elemSizeCache.get(entry.target)?.width && isCell(entry.target)) { needsColumnUpdate = true; } this._elemSizeCache.set(entry.target, newEntry); } if (needsColumnUpdate && this._updatedStickyColumnsParamsToReplay.length) { if (this._stickyColumnsReplayTimeout) { clearTimeout(this._stickyColumnsReplayTimeout); } this._stickyColumnsReplayTimeout = setTimeout(() => { if (this._destroyed) { return; } for (const update of this._updatedStickyColumnsParamsToReplay) { this.updateStickyColumns(update.rows, update.stickyStartStates, update.stickyEndStates, true, false); } this._updatedStickyColumnsParamsToReplay = []; this._stickyColumnsReplayTimeout = null; }, 0); } } } function isCell(element) { return ['cdk-cell', 'cdk-header-cell', 'cdk-footer-cell'].some(klass => element.classList.contains(klass)); } function getTableUnknownColumnError(id) { return Error(`Could not find column with id "${id}".`); } function getTableDuplicateColumnNameError(name) { return Error(`Duplicate column definition name provided: "${name}".`); } function getTableMultipleDefaultRowDefsError() { return Error(`There can only be one default row without a when predicate function. ` + 'Or set `multiTemplateDataRows`.'); } function getTableMissingMatchingRowDefError(data) { return Error(`Could not find a matching row definition for the ` + `provided row data: ${JSON.stringify(data)}`); } function getTableMissingRowDefsError() { return Error('Missing definitions for header, footer, and row; ' + 'cannot determine which columns should be rendered.'); } function getTableUnknownDataSourceError() { return Error(`Provided data source did not match an array, Observable, or DataSource`); } function getTableTextColumnMissingParentTableError() { return Error(`Text column could not find a parent table for registration.`); } function getTableTextColumnMissingNameError() { return Error(`Table text column must have a name.`); } const STICKY_POSITIONING_LISTENER = new InjectionToken('STICKY_POSITIONING_LISTENER'); class CdkRecycleRows { static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkRecycleRows, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: CdkRecycleRows, isStandalone: true, selector: "cdk-table[recycleRows], table[cdk-table][recycleRows]", ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkRecycleRows, decorators: [{ type: Directive, args: [{ selector: 'cdk-table[recycleRows], table[cdk-table][recycleRows]' }] }] }); class DataRowOutlet { viewContainer = inject(ViewContainerRef); elementRef = inject(ElementRef); constructor() { const table = inject(CDK_TABLE); table._rowOutlet = this; table._outletAssigned(); } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: DataRowOutlet, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: DataRowOutlet, isStandalone: true, selector: "[rowOutlet]", ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: DataRowOutlet, decorators: [{ type: Directive, args: [{ selector: '[rowOutlet]' }] }], ctorParameters: () => [] }); class HeaderRowOutlet { viewContainer = inject(ViewContainerRef); elementRef = inject(ElementRef); constructor() { const table = inject(CDK_TABLE); table._headerRowOutlet = this; table._outletAssigned(); } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: HeaderRowOutlet, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: HeaderRowOutlet, isStandalone: true, selector: "[headerRowOutlet]", ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: HeaderRowOutlet, decorators: [{ type: Directive, args: [{ selector: '[headerRowOutlet]' }] }], ctorParameters: () => [] }); class FooterRowOutlet { viewContainer = inject(ViewContainerRef); elementRef = inject(ElementRef); constructor() { const table = inject(CDK_TABLE); table._footerRowOutlet = this; table._outletAssigned(); } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: FooterRowOutlet, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: FooterRowOutlet, isStandalone: true, selector: "[footerRowOutlet]", ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: FooterRowOutlet, decorators: [{ type: Directive, args: [{ selector: '[footerRowOutlet]' }] }], ctorParameters: () => [] }); class NoDataRowOutlet { viewContainer = inject(ViewContainerRef); elementRef = inject(ElementRef); constructor() { const table = inject(CDK_TABLE); table._noDataRowOutlet = this; table._outletAssigned(); } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: NoDataRowOutlet, deps: [], target: i0.ɵɵFactoryTarget.Directive }); static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "21.0.3", type: NoDataRowOutlet, isStandalone: true, selector: "[noDataRowOutlet]", ngImport: i0 }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: NoDataRowOutlet, decorators: [{ type: Directive, args: [{ selector: '[noDataRowOutlet]' }] }], ctorParameters: () => [] }); class CdkTable { _differs = inject(IterableDiffers); _changeDetectorRef = inject(ChangeDetectorRef); _elementRef = inject(ElementRef); _dir = inject(Directionality, { optional: true }); _platform = inject(Platform); _viewRepeater; _viewportRuler = inject(ViewportRuler); _injector = inject(Injector); _virtualScrollViewport = inject(CDK_VIRTUAL_SCROLL_VIEWPORT, { optional: true, host: true }); _positionListener = inject(STICKY_POSITIONING_LISTENER, { optional: true }) || inject(STICKY_POSITIONING_LISTENER, { optional: true, skipSelf: true }); _document = inject(DOCUMENT); _data; _renderedRange; _onDestroy = new Subject(); _renderRows; _renderChangeSubscription = null; _columnDefsByName = new Map(); _rowDefs; _headerRowDefs; _footerRowDefs; _dataDiffer; _defaultRowDef = null; _customColumnDefs = new Set(); _customRowDefs = new Set(); _customHeaderRowDefs = new Set(); _customFooterRowDefs = new Set(); _customNoDataRow = null; _headerRowDefChanged = true; _footerRowDefChanged = true; _stickyColumnStylesNeedReset = true; _forceRecalculateCellWidths = true; _cachedRenderRowsMap = new Map(); _isNativeHtmlTable; _stickyStyler; stickyCssClass = 'cdk-table-sticky'; needsPositionStickyOnElement = true; _isServer; _isShowingNoDataRow = false; _hasAllOutlets = false; _hasInitialized = false; _headerRowStickyUpdates = new Subject(); _footerRowStickyUpdates = new Subject(); _disableVirtualScrolling = false; _getCellRole() { if (this._cellRoleInternal === undefined) { const tableRole = this._elementRef.nativeElement.getAttribute('role'); return tableRole === 'grid' || tableRole === 'treegrid' ? 'gridcell' : 'cell'; } return this._cellRoleInternal; } _cellRoleInternal = undefined; get trackBy() { return this._trackByFn; } set trackBy(fn) { if ((typeof ngDevMode === 'undefined' || ngDevMode) && fn != null && typeof fn !== 'function') { console.warn(`trackBy must be a function, but received ${JSON.stringify(fn)}.`); } this._trackByFn = fn; } _trackByFn; get dataSource() { return this._dataSource; } set dataSource(dataSource) { if (this._dataSource !== dataSource) { this._switchDataSource(dataSource); this._changeDetectorRef.markForCheck(); } } _dataSource; _dataSourceChanges = new Subject(); _dataStream = new Subject(); get multiTemplateDataRows() { return this._multiTemplateDataRows; } set multiTemplateDataRows(value) { this._multiTemplateDataRows = value; if (this._rowOutlet && this._rowOutlet.viewContainer.length) { this._forceRenderDataRows(); this.updateStickyColumnStyles(); } } _multiTemplateDataRows = false; get fixedLayout() { return this._virtualScrollEnabled() ? true : this._fixedLayout; } set fixedLayout(value) { this._fixedLayout = value; this._forceRecalculateCellWidths = true; this._stickyColumnStylesNeedReset = true; } _fixedLayout = false; recycleRows = false; contentChanged = new EventEmitter(); viewChange = new BehaviorSubject({ start: 0, end: Number.MAX_VALUE }); _rowOutlet; _headerRowOutlet; _footerRowOutlet; _noDataRowOutlet; _contentColumnDefs; _contentRowDefs; _contentHeaderRowDefs; _contentFooterRowDefs; _noDataRow; constructor() { const role = inject(new HostAttributeToken('role'), { optional: true }); if (!role) { this._elementRef.nativeElement.setAttribute('role', 'table'); } this._isServer = !this._platform.isBrowser; this._isNativeHtmlTable = this._elementRef.nativeElement.nodeName === 'TABLE'; this._dataDiffer = this._differs.find([]).create((_i, dataRow) => { return this.trackBy ? this.trackBy(dataRow.dataIndex, dataRow.data) : dataRow; }); } ngOnInit() { this._setupStickyStyler(); this._viewportRuler.change().pipe(takeUntil(this._onDestroy)).subscribe(() => { this._forceRecalculateCellWidths = true; }); } ngAfterContentInit() { this._viewRepeater = this.recycleRows || this._virtualScrollEnabled() ? new _RecycleViewRepeaterStrategy() : new _DisposeViewRepeaterStrategy(); if (this._virtualScrollEnabled()) { this._setupVirtualScrolling(this._virtualScrollViewport); } this._hasInitialized = true; } ngAfterContentChecked() { if (this._canRender()) { this._render(); } } ngOnDestroy() { this._stickyStyler?.destroy(); [this._rowOutlet?.viewContainer, this._headerRowOutlet?.viewContainer, this._footerRowOutlet?.viewContainer, this._cachedRenderRowsMap, this._customColumnDefs, this._customRowDefs, this._customHeaderRowDefs, this._customFooterRowDefs, this._columnDefsByName].forEach(def => { def?.clear(); }); this._headerRowDefs = []; this._footerRowDefs = []; this._defaultRowDef = null; this._headerRowStickyUpdates.complete(); this._footerRowStickyUpdates.complete(); this._onDestroy.next(); this._onDestroy.complete(); if (isDataSource(this.dataSource)) { this.dataSource.disconnect(this); } } renderRows() { this._renderRows = this._getAllRenderRows(); const changes = this._dataDiffer.diff(this._renderRows); if (!changes) { this._updateNoDataRow(); this.contentChanged.next(); return; } const viewContainer = this._rowOutlet.viewContainer; this._viewRepeater.applyChanges(changes, viewContainer, (record, _adjustedPreviousIndex, currentIndex) => this._getEmbeddedViewArgs(record.item, currentIndex), record => record.item.data, change => { if (change.operation === _ViewRepeaterOperation.INSERTED && change.context) { this._renderCellTemplateForItem(change.record.item.rowDef, change.context); } }); this._updateRowIndexContext(); changes.forEachIdentityChange(record => { const rowView = viewContainer.get(record.currentIndex); rowView.context.$implicit = record.item.data; }); this._updateNoDataRow(); this.contentChanged.next(); this.updateStickyColumnStyles(); } addColumnDef(columnDef) { this._customColumnDefs.add(columnDef); } removeColumnDef(columnDef) { this._customColumnDefs.delete(columnDef); } addRowDef(rowDef) { this._customRowDefs.add(rowDef); } removeRowDef(rowDef) { this._customRowDefs.delete(rowDef); } addHeaderRowDef(headerRowDef) { this._customHeaderRowDefs.add(headerRowDef); this._headerRowDefChanged = true; } removeHeaderRowDef(headerRowDef) { this._customHeaderRowDefs.delete(headerRowDef); this._headerRowDefChanged = true; } addFooterRowDef(footerRowDef) { this._customFooterRowDefs.add(footerRowDef); this._footerRowDefChanged = true; } removeFooterRowDef(footerRowDef) { this._customFooterRowDefs.delete(footerRowDef); this._footerRowDefChanged = true; } setNoDataRow(noDataRow) { this._customNoDataRow = noDataRow; } updateStickyHeaderRowStyles() { const headerRows = this._getRenderedRows(this._headerRowOutlet); if (this._isNativeHtmlTable) { const thead = closestTableSection(this._headerRowOutlet, 'thead'); if (thead) { thead.style.display = headerRows.length ? '' : 'none'; } } const stickyStates = this._headerRowDefs.map(def => def.sticky); this._stickyStyler.clearStickyPositioning(headerRows, ['top']); this._stickyStyler.stickRows(headerRows, stickyStates, 'top'); this._headerRowDefs.forEach(def => def.resetStickyChanged()); } updateStickyFooterRowStyles() { const footerRows = this._getRenderedRows(this._footerRowOutlet); if (this._isNativeHtmlTable) { const tfoot = closestTableSection(this._footerRowOutlet, 'tfoot'); if (tfoot) { tfoot.style.display = footerRows.length ? '' : 'none'; } } const stickyStates = this._footerRowDefs.map(def => def.sticky); this._stickyStyler.clearStickyPositioning(footerRows, ['bottom']); this._stickyStyler.stickRows(footerRows, stickyStates, 'bottom'); this._stickyStyler.updateStickyFooterContainer(this._elementRef.nativeElement, stickyStates); this._footerRowDefs.forEach(def => def.resetStickyChanged()); } updateStickyColumnStyles() { const headerRows = this._getRenderedRows(this._headerRowOutlet); const dataRows = this._getRenderedRows(this._rowOutlet); const footerRows = this._getRenderedRows(this._footerRowOutlet); if (this._isNativeHtmlTable && !this.fixedLayout || this._stickyColumnStylesNeedReset) { this._stickyStyler.clearStickyPositioning([...headerRows, ...dataRows, ...footerRows], ['left', 'right']); this._stickyColumnStylesNeedReset = false; } headerRows.forEach((headerRow, i) => { this._addStickyColumnStyles([headerRow], this._headerRowDefs[i]); }); this._rowDefs.forEach(rowDef => { const rows = []; for (let i = 0; i < dataRows.length; i++) { if (this._renderRows[i].rowDef === rowDef) { rows.push(dataRows[i]); } } this._addStickyColumnStyles(rows, rowDef); }); footerRows.forEach((footerRow, i) => { this._addStickyColumnStyles([footerRow], this._footerRowDefs[i]); }); Array.from(this._columnDefsByName.values()).forEach(def => def.resetStickyChanged()); } stickyColumnsUpdated(update) { this._positionListener?.stickyColumnsUpdated(update); } stickyEndColumnsUpdated(update) { this._positionListener?.stickyEndColumnsUpdated(update); } stickyHeaderRowsUpdated(update) { this._headerRowStickyUpdates.next(update); this._positionListener?.stickyHeaderRowsUpdated(update); } stickyFooterRowsUpdated(update) { this._footerRowStickyUpdates.next(update); this._positionListener?.stickyFooterRowsUpdated(update); } _outletAssigned() { if (!this._hasAllOutlets && this._rowOutlet && this._headerRowOutlet && this._footerRowOutlet && this._noDataRowOutlet) { this._hasAllOutlets = true; if (this._canRender()) { this._render(); } } } _canRender() { return this._hasAllOutlets && this._hasInitialized; } _render() { this._cacheRowDefs(); this._cacheColumnDefs(); if (!this._headerRowDefs.length && !this._footerRowDefs.length && !this._rowDefs.length && (typeof ngDevMode === 'undefined' || ngDevMode)) { throw getTableMissingRowDefsError(); } const columnsChanged = this._renderUpdatedColumns(); const rowDefsChanged = columnsChanged || this._headerRowDefChanged || this._footerRowDefChanged; this._stickyColumnStylesNeedReset = this._stickyColumnStylesNeedReset || rowDefsChanged; this._forceRecalculateCellWidths = rowDefsChanged; if (this._headerRowDefChanged) { this._forceRenderHeaderRows(); this._headerRowDefChanged = false; } if (this._footerRowDefChanged) { this._forceRenderFooterRows(); this._footerRowDefChanged = false; } if (this.dataSource && this._rowDefs.length > 0 && !this._renderChangeSubscription) { this._observeRenderChanges(); } else if (this._stickyColumnStylesNeedReset) { this.updateStickyColumnStyles(); } this._checkStickyStates(); } _getAllRenderRows() { if (!Array.isArray(this._data) || !this._renderedRange) { return []; } const renderRows = []; const end = Math.min(this._data.length, this._renderedRange.end); const prevCachedRenderRows = this._cachedRenderRowsMap; this._cachedRenderRowsMap = new Map(); for (let i = this._renderedRange.start; i < end; i++) { const data = this._data[i]; const renderRowsForData = this._getRenderRowsForData(data, i, prevCachedRenderRows.get(data)); if (!this._cachedRenderRowsMap.has(data)) { this._cachedRenderRowsMap.set(data, new WeakMap()); } for (let j = 0; j < renderRowsForData.length; j++) { let renderRow = renderRowsForData[j]; const cache = this._cachedRenderRowsMap.get(renderRow.data); if (cache.has(renderRow.rowDef)) { cache.get(renderRow.rowDef).push(renderRow); } else { cache.set(renderRow.rowDef, [renderRow]); } renderRows.push(renderRow); } } return renderRows; } _getRenderRowsForData(data, dataIndex, cache) { const rowDefs = this._getRowDefs(data, dataIndex); return rowDefs.map(rowDef => { const cachedRenderRows = cache && cache.has(rowDef) ? cache.get(rowDef) : []; if (cachedRenderRows.length) { const dataRow = cachedRenderRows.shift(); dataRow.dataIndex = dataIndex; return dataRow; } else { return { data, rowDef, dataIndex }; } }); } _cacheColumnDefs() { this._columnDefsByName.clear(); const columnDefs = mergeArrayAndSet(this._getOwnDefs(this._contentColumnDefs), this._customColumnDefs); columnDefs.forEach(columnDef => { if (this._columnDefsByName.has(columnDef.name) && (typeof ngDevMode === 'undefined' || ngDevMode)) { throw getTableDuplicateColumnNameError(columnDef.name); } this._columnDefsByName.set(columnDef.name, columnDef); }); } _cacheRowDefs() { this._headerRowDefs = mergeArrayAndSet(this._getOwnDefs(this._contentHeaderRowDefs), this._customHeaderRowDefs); this._footerRowDefs = mergeArrayAndSet(this._getOwnDefs(this._contentFooterRowDefs), this._customFooterRowDefs); this._rowDefs = mergeArrayAndSet(this._getOwnDefs(this._contentRowDefs), this._customRowDefs); const defaultRowDefs = this._rowDefs.filter(def => !def.when); if (!this.multiTemplateDataRows && defaultRowDefs.length > 1 && (typeof ngDevMode === 'undefined' || ngDevMode)) { throw getTableMultipleDefaultRowDefsError(); } this._defaultRowDef = defaultRowDefs[0]; } _renderUpdatedColumns() { const columnsDiffReducer = (acc, def) => { const diff = !!def.getColumnsDiff(); return acc || diff; }; const dataColumnsChanged = this._rowDefs.reduce(columnsDiffReducer, false); if (dataColumnsChanged) { this._forceRenderDataRows(); } const headerColumnsChanged = this._headerRowDefs.reduce(columnsDiffReducer, false); if (headerColumnsChanged) { this._forceRenderHeaderRows(); } const footerColumnsChanged = this._footerRowDefs.reduce(columnsDiffReducer, false); if (footerColumnsChanged) { this._forceRenderFooterRows(); } return dataColumnsChanged || headerColumnsChanged || footerColumnsChanged; } _switchDataSource(dataSource) { this._data = []; if (isDataSource(this.dataSource)) { this.dataSource.disconnect(this); } if (this._renderChangeSubscription) { this._renderChangeSubscription.unsubscribe(); this._renderChangeSubscription = null; } if (!dataSource) { if (this._dataDiffer) { this._dataDiffer.diff([]); } if (this._rowOutlet) { this._rowOutlet.viewContainer.clear(); } } this._dataSource = dataSource; } _observeRenderChanges() { if (!this.dataSource) { return; } let dataStream; if (isDataSource(this.dataSource)) { dataStream = this.dataSource.connect(this); } else if (isObservable(this.dataSource)) { dataStream = this.dataSource; } else if (Array.isArray(this.dataSource)) { dataStream = of(this.dataSource); } if (dataStream === undefined && (typeof ngDevMode === 'undefined' || ngDevMode)) { throw getTableUnknownDataSourceError(); } this._renderChangeSubscription = combineLatest([dataStream, this.viewChange]).pipe(takeUntil(this._onDestroy)).subscribe(([data, range]) => { this._data = data || []; this._renderedRange = range; this._dataStream.next(data); this.renderRows(); }); } _forceRenderHeaderRows() { if (this._headerRowOutlet.viewContainer.length > 0) { this._headerRowOutlet.viewContainer.clear(); } this._headerRowDefs.forEach((def, i) => this._renderRow(this._headerRowOutlet, def, i)); this.updateStickyHeaderRowStyles(); } _forceRenderFooterRows() { if (this._footerRowOutlet.viewContainer.length > 0) { this._footerRowOutlet.viewContainer.clear(); } this._footerRowDefs.forEach((def, i) => this._renderRow(this._footerRowOutlet, def, i)); this.updateStickyFooterRowStyles(); } _addStickyColumnStyles(rows, rowDef) { const columnDefs = Array.from(rowDef?.columns || []).map(columnName => { const columnDef = this._columnDefsByName.get(columnName); if (!columnDef && (typeof ngDevMode === 'undefined' || ngDevMode)) { throw getTableUnknownColumnError(columnName); } return columnDef; }); const stickyStartStates = columnDefs.map(columnDef => columnDef.sticky); const stickyEndStates = columnDefs.map(columnDef => columnDef.stickyEnd); this._stickyStyler.updateStickyColumns(rows, stickyStartStates, stickyEndStates, !this.fixedLayout || this._forceRecalculateCellWidths); } _getRenderedRows(rowOutlet) { const renderedRows = []; for (let i = 0; i < rowOutlet.viewContainer.length; i++) { const viewRef = rowOutlet.viewContainer.get(i); renderedRows.push(viewRef.rootNodes[0]); } return renderedRows; } _getRowDefs(data, dataIndex) { if (this._rowDefs.length == 1) { return [this._rowDefs[0]]; } let rowDefs = []; if (this.multiTemplateDataRows) { rowDefs = this._rowDefs.filter(def => !def.when || def.when(dataIndex, data)); } else { let rowDef = this._rowDefs.find(def => def.when && def.when(dataIndex, data)) || this._defaultRowDef; if (rowDef) { rowDefs.push(rowDef); } } if (!rowDefs.length && (typeof ngDevMode === 'undefined' || ngDevMode)) { throw getTableMissingMatchingRowDefError(data); } return rowDefs; } _getEmbeddedViewArgs(renderRow, index) { const rowDef = renderRow.rowDef; const context = { $implicit: renderRow.data }; return { templateRef: rowDef.template, context, index }; } _renderRow(outlet, rowDef, index, context = {}) { const view = outlet.viewContainer.createEmbeddedView(rowDef.template, context, index); this._renderCellTemplateForItem(rowDef, context); return view; } _renderCellTemplateForItem(rowDef, context) { for (let cellTemplate of this._getCellTemplates(rowDef)) { if (CdkCellOutlet.mostRecentCellOutlet) { CdkCellOutlet.mostRecentCellOutlet._viewContainer.createEmbeddedView(cellTemplate, context); } } this._changeDetectorRef.markForCheck(); } _updateRowIndexContext() { const viewContainer = this._rowOutlet.viewContainer; for (let renderIndex = 0, count = viewContainer.length; renderIndex < count; renderIndex++) { const viewRef = viewContainer.get(renderIndex); const context = viewRef.context; context.count = count; context.first = renderIndex === 0; context.last = renderIndex === count - 1; context.even = renderIndex % 2 === 0; context.odd = !context.even; if (this.multiTemplateDataRows) { context.dataIndex = this._renderRows[renderIndex].dataIndex; context.renderIndex = renderIndex; } else { context.index = this._renderRows[renderIndex].dataIndex; } } } _getCellTemplates(rowDef) { if (!rowDef || !rowDef.columns) { return []; } return Array.from(rowDef.columns, columnId => { const column = this._columnDefsByName.get(columnId); if (!column && (typeof ngDevMode === 'undefined' || ngDevMode)) { throw getTableUnknownColumnError(columnId); } return rowDef.extractCellTemplate(column); }); } _forceRenderDataRows() { this._dataDiffer.diff([]); this._rowOutlet.viewContainer.clear(); this.renderRows(); } _checkStickyStates() { const stickyCheckReducer = (acc, d) => { return acc || d.hasStickyChanged(); }; if (this._headerRowDefs.reduce(stickyCheckReducer, false)) { this.updateStickyHeaderRowStyles(); } if (this._footerRowDefs.reduce(stickyCheckReducer, false)) { this.updateStickyFooterRowStyles(); } if (Array.from(this._columnDefsByName.values()).reduce(stickyCheckReducer, false)) { this._stickyColumnStylesNeedReset = true; this.updateStickyColumnStyles(); } } _setupStickyStyler() { const direction = this._dir ? this._dir.value : 'ltr'; const injector = this._injector; this._stickyStyler = new StickyStyler(this._isNativeHtmlTable, this.stickyCssClass, this._platform.isBrowser, this.needsPositionStickyOnElement, direction, this, injector); (this._dir ? this._dir.change : of()).pipe(takeUntil(this._onDestroy)).subscribe(value => { this._stickyStyler.direction = value; this.updateStickyColumnStyles(); }); } _setupVirtualScrolling(viewport) { const virtualScrollScheduler = typeof requestAnimationFrame !== 'undefined' ? animationFrameScheduler : asapScheduler; this.viewChange.next({ start: 0, end: 0 }); viewport.renderedRangeStream.pipe(auditTime(0, virtualScrollScheduler), takeUntil(this._onDestroy)).subscribe(this.viewChange); viewport.attach({ dataStream: this._dataStream, measureRangeSize: (range, orientation) => this._measureRangeSize(range, orientation) }); combineLatest([viewport.renderedContentOffset, this._headerRowStickyUpdates]).pipe(takeUntil(this._onDestroy)).subscribe(([offsetFromTop, update]) => { if (!update.sizes || !update.offsets || !update.elements) { return; } for (let i = 0; i < update.elements.length; i++) { const cells = update.elements[i]; if (cells) { const current = update.offsets[i]; const offset = offsetFromTop !== 0 ? Math.max(offsetFromTop - current, current) : -current; for (const cell of cells) { cell.style.top = `${-offset}px`; } } } }); combineLatest([viewport.renderedContentOffset, this._footerRowStickyUpdates]).pipe(takeUntil(this._onDestroy)).subscribe(([offsetFromTop, update]) => { if (!update.sizes || !update.offsets || !update.elements) { return; } for (let i = 0; i < update.elements.length; i++) { const cells = update.elements[i]; if (cells) { for (const cell of cells) { cell.style.bottom = `${offsetFromTop + update.offsets[i]}px`; } } } }); } _getOwnDefs(items) { return items.filter(item => !item._table || item._table === this); } _updateNoDataRow() { const noDataRow = this._customNoDataRow || this._noDataRow; if (!noDataRow) { return; } const shouldShow = this._rowOutlet.viewContainer.length === 0; if (shouldShow === this._isShowingNoDataRow) { return; } const container = this._noDataRowOutlet.viewContainer; if (shouldShow) { const view = container.createEmbeddedView(noDataRow.templateRef); const rootNode = view.rootNodes[0]; if (view.rootNodes.length === 1 && rootNode?.nodeType === this._document.ELEMENT_NODE) { rootNode.setAttribute('role', 'row'); rootNode.classList.add(...noDataRow._contentClassNames); const cells = rootNode.querySelectorAll(noDataRow._cellSelector); for (let i = 0; i < cells.length; i++) { cells[i].classList.add(...noDataRow._cellClassNames); } } } else { container.clear(); } this._isShowingNoDataRow = shouldShow; this._changeDetectorRef.markForCheck(); } _measureRangeSize(range, orientation) { if (range.start >= range.end || orientation !== 'vertical') { return 0; } const renderedRange = this.viewChange.value; const viewContainerRef = this._rowOutlet.viewContainer; if ((range.start < renderedRange.start || range.end > renderedRange.end) && (typeof ngDevMode === 'undefined' || ngDevMode)) { throw Error(`Error: attempted to measure an item that isn't rendered.`); } const renderedStartIndex = range.start - renderedRange.start; const rangeLen = range.end - range.start; let firstNode; let lastNode; for (let i = 0; i < rangeLen; i++) { const view = viewContainerRef.get(i + renderedStartIndex); if (view && view.rootNodes.length) { firstNode = lastNode = view.rootNodes[0]; break; } } for (let i = rangeLen - 1; i > -1; i--) { const view = viewContainerRef.get(i + renderedStartIndex); if (view && view.rootNodes.length) { lastNode = view.rootNodes[view.rootNodes.length - 1]; break; } } const startRect = firstNode?.getBoundingClientRect?.(); const endRect = lastNode?.getBoundingClientRect?.(); return startRect && endRect ? endRect.bottom - startRect.top : 0; } _virtualScrollEnabled() { return !this._disableVirtualScrolling && this._virtualScrollViewport != null; } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkTable, deps: [], target: i0.ɵɵFactoryTarget.Component }); static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.0.3", type: CdkTable, isStandalone: true, selector: "cdk-table, table[cdk-table]", inputs: { trackBy: "trackBy", dataSource: "dataSource", multiTemplateDataRows: ["multiTemplateDataRows", "multiTemplateDataRows", booleanAttribute], fixedLayout: ["fixedLayout", "fixedLayout", booleanAttribute], recycleRows: ["recycleRows", "recycleRows", booleanAttribute] }, outputs: { contentChanged: "contentChanged" }, host: { properties: { "class.cdk-table-fixed-layout": "fixedLayout" }, classAttribute: "cdk-table" }, providers: [{ provide: CDK_TABLE, useExisting: CdkTable }, { provide: STICKY_POSITIONING_LISTENER, useValue: null }], queries: [{ propertyName: "_noDataRow", first: true, predicate: CdkNoDataRow, descendants: true }, { propertyName: "_contentColumnDefs", predicate: CdkColumnDef, descendants: true }, { propertyName: "_contentRowDefs", predicate: CdkRowDef, descendants: true }, { propertyName: "_contentHeaderRowDefs", predicate: CdkHeaderRowDef, descendants: true }, { propertyName: "_contentFooterRowDefs", predicate: CdkFooterRowDef, descendants: true }], exportAs: ["cdkTable"], ngImport: i0, template: ` @if (_isServer) { } @if (_isNativeHtmlTable) { } @else { } `, isInline: true, styles: [".cdk-table-fixed-layout{table-layout:fixed}\n"], dependencies: [{ kind: "directive", type: HeaderRowOutlet, selector: "[headerRowOutlet]" }, { kind: "directive", type: DataRowOutlet, selector: "[rowOutlet]" }, { kind: "directive", type: NoDataRowOutlet, selector: "[noDataRowOutlet]" }, { kind: "directive", type: FooterRowOutlet, selector: "[footerRowOutlet]" }], changeDetection: i0.ChangeDetectionStrategy.Default, encapsulation: i0.ViewEncapsulation.None }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkTable, decorators: [{ type: Component, args: [{ selector: 'cdk-table, table[cdk-table]', exportAs: 'cdkTable', template: ` @if (_isServer) { } @if (_isNativeHtmlTable) { } @else { } `, host: { 'class': 'cdk-table', '[class.cdk-table-fixed-layout]': 'fixedLayout' }, encapsulation: ViewEncapsulation.None, changeDetection: ChangeDetectionStrategy.Default, providers: [{ provide: CDK_TABLE, useExisting: CdkTable }, { provide: STICKY_POSITIONING_LISTENER, useValue: null }], imports: [HeaderRowOutlet, DataRowOutlet, NoDataRowOutlet, FooterRowOutlet], styles: [".cdk-table-fixed-layout{table-layout:fixed}\n"] }] }], ctorParameters: () => [], propDecorators: { trackBy: [{ type: Input }], dataSource: [{ type: Input }], multiTemplateDataRows: [{ type: Input, args: [{ transform: booleanAttribute }] }], fixedLayout: [{ type: Input, args: [{ transform: booleanAttribute }] }], recycleRows: [{ type: Input, args: [{ transform: booleanAttribute }] }], contentChanged: [{ type: Output }], _contentColumnDefs: [{ type: ContentChildren, args: [CdkColumnDef, { descendants: true }] }], _contentRowDefs: [{ type: ContentChildren, args: [CdkRowDef, { descendants: true }] }], _contentHeaderRowDefs: [{ type: ContentChildren, args: [CdkHeaderRowDef, { descendants: true }] }], _contentFooterRowDefs: [{ type: ContentChildren, args: [CdkFooterRowDef, { descendants: true }] }], _noDataRow: [{ type: ContentChild, args: [CdkNoDataRow] }] } }); function mergeArrayAndSet(array, set) { return array.concat(Array.from(set)); } function closestTableSection(outlet, section) { const uppercaseSection = section.toUpperCase(); let current = outlet.viewContainer.element.nativeElement; while (current) { const nodeName = current.nodeType === 1 ? current.nodeName : null; if (nodeName === uppercaseSection) { return current; } else if (nodeName === 'TABLE') { break; } current = current.parentNode; } return null; } class CdkTextColumn { _table = inject(CdkTable, { optional: true }); _options = inject(TEXT_COLUMN_OPTIONS, { optional: true }); get name() { return this._name; } set name(name) { this._name = name; this._syncColumnDefName(); } _name; headerText; dataAccessor; justify = 'start'; columnDef; cell; headerCell; constructor() { this._options = this._options || {}; } ngOnInit() { this._syncColumnDefName(); if (this.headerText === undefined) { this.headerText = this._createDefaultHeaderText(); } if (!this.dataAccessor) { this.dataAccessor = this._options.defaultDataAccessor || ((data, name) => data[name]); } if (this._table) { this.columnDef.cell = this.cell; this.columnDef.headerCell = this.headerCell; this._table.addColumnDef(this.columnDef); } else if (typeof ngDevMode === 'undefined' || ngDevMode) { throw getTableTextColumnMissingParentTableError(); } } ngOnDestroy() { if (this._table) { this._table.removeColumnDef(this.columnDef); } } _createDefaultHeaderText() { const name = this.name; if (!name && (typeof ngDevMode === 'undefined' || ngDevMode)) { throw getTableTextColumnMissingNameError(); } if (this._options && this._options.defaultHeaderTextTransform) { return this._options.defaultHeaderTextTransform(name); } return name[0].toUpperCase() + name.slice(1); } _syncColumnDefName() { if (this.columnDef) { this.columnDef.name = this.name; } } static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkTextColumn, deps: [], target: i0.ɵɵFactoryTarget.Component }); static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "21.0.3", type: CdkTextColumn, isStandalone: true, selector: "cdk-text-column", inputs: { name: "name", headerText: "headerText", dataAccessor: "dataAccessor", justify: "justify" }, viewQueries: [{ propertyName: "columnDef", first: true, predicate: CdkColumnDef, descendants: true, static: true }, { propertyName: "cell", first: true, predicate: CdkCellDef, descendants: true, static: true }, { propertyName: "headerCell", first: true, predicate: CdkHeaderCellDef, descendants: true, static: true }], ngImport: i0, template: ` {{headerText}} {{dataAccessor(data, name)}} `, isInline: true, dependencies: [{ kind: "directive", type: CdkColumnDef, selector: "[cdkColumnDef]", inputs: ["cdkColumnDef", "sticky", "stickyEnd"] }, { kind: "directive", type: CdkHeaderCellDef, selector: "[cdkHeaderCellDef]" }, { kind: "directive", type: CdkHeaderCell, selector: "cdk-header-cell, th[cdk-header-cell]" }, { kind: "directive", type: CdkCellDef, selector: "[cdkCellDef]" }, { kind: "directive", type: CdkCell, selector: "cdk-cell, td[cdk-cell]" }], changeDetection: i0.ChangeDetectionStrategy.Default, encapsulation: i0.ViewEncapsulation.None }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkTextColumn, decorators: [{ type: Component, args: [{ selector: 'cdk-text-column', template: ` {{headerText}} {{dataAccessor(data, name)}} `, encapsulation: ViewEncapsulation.None, changeDetection: ChangeDetectionStrategy.Default, imports: [CdkColumnDef, CdkHeaderCellDef, CdkHeaderCell, CdkCellDef, CdkCell] }] }], ctorParameters: () => [], propDecorators: { name: [{ type: Input }], headerText: [{ type: Input }], dataAccessor: [{ type: Input }], justify: [{ type: Input }], columnDef: [{ type: ViewChild, args: [CdkColumnDef, { static: true }] }], cell: [{ type: ViewChild, args: [CdkCellDef, { static: true }] }], headerCell: [{ type: ViewChild, args: [CdkHeaderCellDef, { static: true }] }] } }); const EXPORTED_DECLARATIONS = [CdkTable, CdkRowDef, CdkCellDef, CdkCellOutlet, CdkHeaderCellDef, CdkFooterCellDef, CdkColumnDef, CdkCell, CdkRow, CdkHeaderCell, CdkFooterCell, CdkHeaderRow, CdkHeaderRowDef, CdkFooterRow, CdkFooterRowDef, DataRowOutlet, HeaderRowOutlet, FooterRowOutlet, CdkTextColumn, CdkNoDataRow, CdkRecycleRows, NoDataRowOutlet]; class CdkTableModule { static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkTableModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule }); static ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "21.0.3", ngImport: i0, type: CdkTableModule, imports: [ScrollingModule, CdkTable, CdkRowDef, CdkCellDef, CdkCellOutlet, CdkHeaderCellDef, CdkFooterCellDef, CdkColumnDef, CdkCell, CdkRow, CdkHeaderCell, CdkFooterCell, CdkHeaderRow, CdkHeaderRowDef, CdkFooterRow, CdkFooterRowDef, DataRowOutlet, HeaderRowOutlet, FooterRowOutlet, CdkTextColumn, CdkNoDataRow, CdkRecycleRows, NoDataRowOutlet], exports: [CdkTable, CdkRowDef, CdkCellDef, CdkCellOutlet, CdkHeaderCellDef, CdkFooterCellDef, CdkColumnDef, CdkCell, CdkRow, CdkHeaderCell, CdkFooterCell, CdkHeaderRow, CdkHeaderRowDef, CdkFooterRow, CdkFooterRowDef, DataRowOutlet, HeaderRowOutlet, FooterRowOutlet, CdkTextColumn, CdkNoDataRow, CdkRecycleRows, NoDataRowOutlet] }); static ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkTableModule, imports: [ScrollingModule] }); } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.3", ngImport: i0, type: CdkTableModule, decorators: [{ type: NgModule, args: [{ exports: EXPORTED_DECLARATIONS, imports: [ScrollingModule, ...EXPORTED_DECLARATIONS] }] }] }); export { BaseCdkCell, BaseRowDef, CDK_ROW_TEMPLATE, CDK_TABLE, CdkCell, CdkCellDef, CdkCellOutlet, CdkColumnDef, CdkFooterCell, CdkFooterCellDef, CdkFooterRow, CdkFooterRowDef, CdkHeaderCell, CdkHeaderCellDef, CdkHeaderRow, CdkHeaderRowDef, CdkNoDataRow, CdkRecycleRows, CdkRow, CdkRowDef, CdkTable, CdkTableModule, CdkTextColumn, DataRowOutlet, FooterRowOutlet, HeaderRowOutlet, NoDataRowOutlet, STICKY_POSITIONING_LISTENER, TEXT_COLUMN_OPTIONS }; //# sourceMappingURL=table.mjs.map