UNPKG

@true-directive/grid

Version:

Angular Data Grid from Yopsilon.

708 lines 108 kB
import * as tslib_1 from "tslib"; /** * Copyright (c) 2018-2019 Aleksey Melnikov, True Directive Company. * @link https://truedirective.com/ * @license MIT */ import { Component, Output, ViewChild, ElementRef, ChangeDetectorRef, KeyValueDiffers, EventEmitter, Inject } from '@angular/core'; import { takeUntil } from 'rxjs/operators'; import { ColumnBand, GridPart, UIActionType, UIAction, Keys, RowLayout } from '@true-directive/base'; import { RowDragEvent, RowClickEvent, ContextMenuEvent, CellClickEvent } from '@true-directive/base'; import { GridViewComponent } from './grid-view.component'; import { GridStateService } from './grid-state.service'; import { InternationalizationService } from './internationalization/internationalization.service'; let GridComponent = class GridComponent extends GridViewComponent { constructor(state, intl, elementRef, changeDetector, keyValueDiffers) { super(state, intl, elementRef, changeDetector, keyValueDiffers); this.state = state; this.intl = intl; this.elementRef = elementRef; this.changeDetector = changeDetector; this.keyValueDiffers = keyValueDiffers; this.rowMouseDown = new EventEmitter(); this.rowMouseUp = new EventEmitter(); this.rowClick = new EventEmitter(); this.cellClick = new EventEmitter(); this.rowDblClick = new EventEmitter(); this.rowKeyDown = new EventEmitter(); this.contextMenu = new EventEmitter(); this.selectionChanged = new EventEmitter(); this.checkedChanged = new EventEmitter(); /** * Пользователь перетащил строки. Событие возникает до того, как строки будут перенесены * гридом. Это действие можно отменить и обработать вне грида. */ this.rowDrag = new EventEmitter(false); /** * Пользователь перетащил строки и грид обработал это действие. */ this.rowDragged = new EventEmitter(false); this._cellTouched = null; // Ячейка с тачем this._cellTouchedScrollPos = { X: 0, Y: 0 }; this._dragColumn = false; // Перетаскивание заголовка колонки в процессе this._drag_x0 = -1; // Предыдущая позиция перетаскиваемого заголовка this._drag_y0 = -1; this._lastSel = 0; // Время последнего изменения выделения this._paging = false; // Грид в процессе исполнения PgDn/PgUp // Строчка ушла после редактирования... this.state.events.onRowUnfiltered.pipe(takeUntil(this.destroy$)).subscribe(r => { setTimeout(() => { if (this.state.dataSource.removeResultRow(r)) { this.state.layoutsHandler.updateSelectionIndices(); this.need_recalc_page = true; this.updatePage('rowUnfiltered'); } }, 100); }); // Изменены колонки this.state.events.onColumnsChanged.pipe(takeUntil(this.destroy$)).subscribe(v => { this.RC.clear(); this.checkSize(true); }); // Перетаскивание заголовка колонки this.state.events.onDrag.pipe(takeUntil(this.destroy$)).subscribe(v => this.dragColumn(v)); // Drop заголовка колонки this.state.events.onDrop.pipe(takeUntil(this.destroy$)).subscribe(v => this.dropColumn(v)); // Изменение выделения this.state.events.onSelect.pipe(takeUntil(this.destroy$)).subscribe(cellPos => { this.refreshSelection(cellPos); this.selectionChanged.emit(this.state.selection); }); // Изменение значения this.state.events.onValueChanged.pipe(takeUntil(this.destroy$)).subscribe(v => this.detectChanges('valueChanged')); // Изменение значения чекбокса this.state.events.onCheckedChanged.pipe(takeUntil(this.destroy$)).subscribe(e => this.checkedChanged.emit(e)); // Включение редактирования this.state.events.onStartEditing.pipe(takeUntil(this.destroy$)).subscribe(v => this.detectChanges('startEditing')); // Выключение редактирования this.state.events.onStopEditing.pipe(takeUntil(this.destroy$)).subscribe(returnFocus => { this.detectChanges(); if (returnFocus && this.state.settings.autoFocusAfterEditor) { this.focus(); } }); } get isDragging() { return this._dragColumn; } /** * Начало действия пользователя (перемещение строки или выделение ячеек) * @param eX Начальная координата X * @param eY Начальная координата Y * @param place Часть грида, в которой инициировано действие * @param ctrlKey Нажата ли клавиша Ctrl * @param byTouch Инициировано ли тач-событием */ startAction(cp, eX, eY, place, ctrlKey = false, byTouch = false, button = 0) { if (cp && cp.row) { this.scroller.prepareAutoScroll(); const uiType = this.state.ui.startAction(cp, ctrlKey, byTouch, button); if (uiType) { this.uiAction = new UIAction(uiType, null, eX, eY); this.addDocumentMouseListeners(); } } } /** * Касание пальцем * @param e Параметры события */ touchStart(e) { // В течение 50мс не выделяем по тачстарту, потому что этот тач останавливает // прокрутку if (this._lastScroll.time > 0) { const ms = Date.now() - this._lastScroll.time; if (ms < 50) { // Не выделяем ничего, если мы остановили прокрутку return; } } e.stopPropagation(); const touches = e.changedTouches; if (touches.length === 1) { // Если касание одно, то запоминаем ячейку, которой касаемся this._cellTouched = this.cellByXY(touches[0].clientX, touches[0].clientY); // Запоминаем положение прокрутки this._cellTouchedScrollPos = { X: this.scroller.scrollLeft, Y: this.scroller.scrollTop }; } } // Проверим, не было ли скролла во время касания get touchScroll() { return this._cellTouchedScrollPos.X !== this.scroller.scrollLeft || this._cellTouchedScrollPos.Y !== this.scroller.scrollTop; } /** * Окончание касания * @param e Параметры события */ touchEnd(e) { const touches = e.changedTouches; if (touches.length >= 1) { let rr = this.cellByXY(touches[0].clientX, touches[0].clientY); if (rr !== null && rr.equals(this._cellTouched) && !this.touchScroll) { // Should we toggle a checkbox in this cell? if (this.state.settings.checkByCellClick && this.state.check.canToggleCheck(rr)) { // Yes, we should. this.state.ui.toggleCheck(rr.row, rr.fieldName); } else { // Something will be selected. if (!rr.equals(this.state.selection.focusedCell)) { // Если клик не на выделенной ячейке, то начинаем выделение. // Начало и окончание выделения вынесено сюда, т.к. мы не можем // сразу понять, действие пользователя - это прокрутка или // выделение строки. // Поэтому, если положение прокрутки не изменилось - выделяем this.startAction(rr, touches[0].clientX, touches[0].clientY, GridPart.CENTER, false, true); } else { // Редактирование и фокус на редакторе this.state.ui.startAction(this._cellTouched, false, true); e.stopPropagation(); return; } } // End selecting anyway this.state.ui.endSelect(rr, true); } } e.stopPropagation(); } /** * Нажатие кнопки мыши. * @param e Параметры события */ dataMouseDown(e) { if (this._cellTouched) { // Touchstart has been handled. Skip this mousedown. return; } this.rowMouseDown.emit(e); if (!e.defaultPrevented) { const cp = this.cellByXY(e.clientX, e.clientY); if (this.state.ui.mouseDown(cp, false, e.button)) { // This event has been handled. return; } this.startAction(cp, e.clientX, e.clientY, GridPart.CENTER, e.ctrlKey, false, e.button); } } doRowClick(e) { if (this.state.ui.click(this.cellByXY(e.clientX, e.clientY))) { e.stopPropagation(); e.preventDefault(); } } dataContextMenu(e) { if (this.settings.enableDataContextMenu && this.settings.dataContextMenuActions.length > 0) { this.menuStarter.start(e, this.state.settings.dataContextMenuActions, 'selection'); this.detectChanges(); e.preventDefault(); return; } this.contextMenu.emit(new ContextMenuEvent(this.cellByXY(e.clientX, e.clientY), e)); } dataRowClick(e, r) { this.rowClick.emit(new RowClickEvent(r, e)); this.cellClick.emit(new CellClickEvent(this.cellByXY(e.clientX, e.clientY), e)); if (this._cellTouched) { // Skip this click. this._cellTouched = null; return; } this.doRowClick(e); } dataRowDblClick(e, r) { this.rowDblClick.emit(new RowClickEvent(r, e)); this.state.ui.dblClick(e, r); } /** * Key event handler * @param keyEvent Key event parameters */ processKey(e) { this.rowKeyDown.emit(e); if (e.defaultPrevented) { return; } const keyCode = e.keyCode; if (keyCode === Keys.SPACE && this.state.selection.focusedRow) { let f = this.state.check.firstCheckableField(); if (f !== '') { this.toggleCheckbox({ row: this.state.selection.focusedRow, fieldName: f }); return true; } } let ri = this.state.dataSource.resultRows.indexOf(this.state.selection.focusedRow); if (!this.state.st.fixedRowHeight && (keyCode === Keys.PAGE_DOWN || keyCode === Keys.PAGE_UP)) { // При переменной высоте строк прокрутить на одну страницу вниз или вверх - большая печаль. // Потому что мы не знаем, какая высота у строк выше или ниже текущей страницы. // Поэтому принимаем тяжелое решение и... // 1. Игнорируем нажатие, если еще не обработали предыдущее: if (this._paging) { return true; } // 2. Рендерим с запасом const overWork = { fwd: 4, back: 4 }; // 3. Запас как раз равен максимальному количеству строк, умещающемуся на экране if (keyCode === Keys.PAGE_DOWN) { overWork.fwd = this.scroller.viewPortHeight / this.RC.currentRH + 1; } else { if (keyCode === Keys.PAGE_UP) { overWork.back = this.scroller.viewPortHeight / this.RC.currentRH + 1; } } // 4. Рендерим страницу с заданной переработкой this.updatePage('keydown', true, overWork); // 5. Указываем на приостановку обработки клавиш this._paging = true; setTimeout(() => { // 6. Теперь мы можем точно рассчитать емкость предыдущей страницы const newPageCapacity = this.RC.pageCapacity(ri, this.scroller.viewPortHeight, this.state.dataSource.resultRows.length); // 7. Handle key if (this.state.ui.processKey(newPageCapacity, e)) { e.stopPropagation(); } // 8. Done this._paging = false; }, 50); return true; } // Остальное намного проще let pageCapacity = this.RC.pageCapacity(ri, this.scroller.viewPortHeight, this.state.dataSource.resultRows.length); return this.state.ui.processKey(pageCapacity, e); } dataKeyDown(e) { if (this.processKey(e)) { e.preventDefault(); e.stopPropagation(); } } checkAll(fieldName) { this.state.check.setColumnCheck(this.state.columnCollection.columnByFieldName(fieldName), true); } uncheckAll(fieldName) { this.state.check.setColumnCheck(this.state.columnCollection.columnByFieldName(fieldName), false); } /** * Continue selecting * @param e Event parameters */ doSelect(e) { const rr = this.cellByXY(e.clientX, e.clientY); if (rr && rr.fieldName !== '') { this.state.ui.proceedToSelect(rr); } this.scroller.checkAutoScrollX(e.clientX); this.scroller.checkAutoScrollY(e.clientY); } /** * Selection of the grid * @return GridSelection instance with selected ranges list. */ get selection() { return this.state.selection; } /** * Returns data which contained in selected ranges * @return Array with the data */ get selectedData() { return this.state.getSelectedData(this.selection).result; } get draggedRows() { if (this.uiAction && this.uiAction.target) { if (this.uiAction.renderTarget === null) { // Первые три записи в обратном порядке this.uiAction.renderTarget = []; for (let i = 0; i < 3 && i < this.uiAction.target.length; i++) { this.uiAction.renderTarget.unshift(this.uiAction.target[i]); } } return this.uiAction.renderTarget; } return []; } getDragTransform(i) { const l = this.draggedRows.length; const scale = Math.pow(0.97, l - i - 1); const dx = -40; const dy = -i * this.state.settings.rowHeight + (l - i - 1) * 7 - 40; const res = 'matrix(' + scale + ', 0, 0, 1, ' + dx + ', ' + dy + ')'; return res; } getDragWidth() { let res = 0; this.state.layoutDrag.columns.forEach(c => res += c.width); return res + this.state.settings.widthUnit; } checkRowDrag(e) { if (!this.state.settings.rowDrag) { return false; } if (this.uiAction.action === UIActionType.ROW_DRAG) { // Уже включено return false; } const xx = e.clientX; const yy = e.clientY; if (Math.abs(xx - this.uiAction.x) > 9 || Math.abs(yy - this.uiAction.y) > 9) { this.startDragRows(); return true; } return false; } startDragRows() { this.uiAction.action = UIActionType.ROW_DRAG; this.state.dragDrop.setDragItem(this.uiAction); this.setDragPosition(this.uiAction); this.detectChanges(); this.dragInProcess(true); this.dragItem.nativeElement.style.visibility = 'visible'; } specifyDropPosition(pos, rLeft, e) { return pos; } dropInfo(e) { let r = RowLayout.rowPosByXY(this.rowLayouts(this.displayedRows), e.clientX, e.clientY, this.state.isTree); const rl = r.rl; if (!rl) { return null; } const centerRect = this.scroller.centerRect; const rd = rl.rowComponent; const rr = rd.firstCellRect(); r = this.specifyDropPosition(r, rr.left, e); const canDrop = this.state.canDrop(this.uiAction.target, rl.rowComponent.row, r.pos); let dropTarget = null; if (canDrop !== '') { dropTarget = rl.rowComponent.row; r.pos = canDrop; } let top = (r.pos !== 'before' ? rl.clientRect.bottom : rl.clientRect.top) - 1; let left = rr.left; let height = 2; let width = rl.clientRect.width - (left - centerRect.left); if (r.pos === 'last') { left -= this.state.settings.levelIndent; width += this.state.settings.levelIndent; } if (r.pos === 'in') { top -= rl.clientRect.height - 3; height = rl.clientRect.height - 6; } if (left < centerRect.left) { left = centerRect.left; } if ((left + width) > rl.clientRect.right) { width = rl.clientRect.right - left; } const rect = new DOMRect(left, top, width, height); if (rect.top < centerRect.top - 1 || rect.top >= centerRect.bottom) { return null; } return { dropTarget: dropTarget, rowPosition: r, pos: r.pos, markerRect: rect }; } dragRows(e) { if (!this.uiAction.move(e.clientX, e.clientY)) { //return null; } this.setDragPosition(this.uiAction); const di = this.dropInfo(e); if (di === null || di.dropTarget === null) { this.toggleClass(true, 'true-drag-not-allowed'); this.toggleClass(false, 'true-drag-allowed'); this.hideMarker(); } else { this.showMarker(di.markerRect.left, di.markerRect.top, di.markerRect.width, di.markerRect.height, true); this.toggleClass(false, 'true-drag-not-allowed'); this.toggleClass(true, 'true-drag-allowed'); } this.scroller.checkAutoScrollY(e.clientY); return di ? di.rowPosition : null; } endDragRows(e) { this.hideMarker(); this.scroller.stopAutoScroll(); this.toggleClass(false, 'true-drag-not-allowed'); this.toggleClass(false, 'true-drag-allowed'); this.dragItem.nativeElement.style.visibility = 'hidden'; this.dragInProcess(false); const di = this.dropInfo(e); if (di && di.dropTarget) { const ce = new RowDragEvent(this.uiAction.target, di.dropTarget, di.pos); this.rowDrag.emit(ce); if (!ce.isCanceled) { this.state.moveRows(this.uiAction.target, di.dropTarget, di.pos); this.rowDragged.emit(ce); } } } documentMouseMove(e) { super.documentMouseMove(e); if (this.uiAction) // если что-то началось.. { if (e.clientX === this.uiAction.x && e.clientY === this.uiAction.y) { return; } if (this.checkRowDrag(e)) { return; } if (this.uiAction.action === UIActionType.ROW_DRAG) { this.dragRows(e); } // Продолжаем выделение данных if (this.uiAction.action === UIActionType.SELECT) { let dt = Date.now(); let ms = dt - this._lastSel; let delay = this.state.IE ? 70 : 0; if (ms < delay) { // Не так давно обновляли.. return; } this._lastSel = Date.now(); this.doSelect(e); e.preventDefault(); e.stopPropagation(); } } } // Завершение выделения области documentMouseUp(e) { if (this.uiAction.action === UIActionType.ROW_DRAG) { // Переставляем. this.endDragRows(e); } if (this.uiAction.action === UIActionType.SELECT) { let rr = this.cellByXY(e.clientX, e.clientY); if (rr && rr.fieldName !== '') { this.state.ui.endSelect(rr, false, e.button); this.focus(); } } super.documentMouseUp(e); this.rowMouseUp.emit(e); // Останавливаем автопрокрутку this.scroller.stopAutoScroll(); this.uiAction = null; } resizeInProcess(value) { this.toggleClass(value, 'true-resize-in-process'); } dragInProcess(value) { this.toggleClass(value, 'true-drag-in-process'); } showMarker(mrX, mrY, mrW, mrH, rowDrag = false) { this.dropMarker.nativeElement.style.top = mrY + 'px'; this.dropMarker.nativeElement.style.left = mrX + 'px'; this.dropMarker.nativeElement.style.width = mrW + 'px'; this.dropMarker.nativeElement.style.height = mrH + 'px'; this.dropMarker.nativeElement.style.visibility = 'visible'; } // Hide marker of REORDERING/RESIZING hideMarker() { this.dropMarker.nativeElement.style.visibility = 'hidden'; } proceedToResizeColumn(ui) { let r0 = this.scroller.clientRect; let mrX = ui.x; if ((mrX > r0.left) && mrX < r0.right) { this.showMarker(mrX, r0.top + 1, 1, r0.height - 2); } else { this.hideMarker(); } if (ui.x < r0.left) { // листаем влево this.scroller.scrollSpeedX = -this.state.st.autoScrollStep; } else { if (ui.x > r0.right) { this.scroller.scrollSpeedX = this.state.st.autoScrollStep; } else { this.scroller.scrollSpeedX = 0; } } } resizeColumn(e) { if (e.action === 'start') { this.resizeInProcess(true); return; } if (e.action === 'end') { this.hideMarker(); this.resizeInProcess(false); return; } this.proceedToResizeColumn(e.ui); } setDragPosition(e) { const dy = this.state.iOS ? window.pageYOffset : 0; this.dragItem.nativeElement.style.left = e.x + e.targetOffsetX + 'px'; this.dragItem.nativeElement.style.top = dy + e.y + e.targetOffsetY + 'px'; } isDragColumn() { return this._dragColumn; } startDragColumn(e) { if (this.filterPopup && this.filterPopup.visible) { this.filterPopup.closePopup(); } this._dragColumn = true; this.scroller.prepareAutoScroll(); this.state.dragDrop.setDragItem(e); this.detectChanges('dragColumn'); this.setDragPosition(e); this.dragItem.nativeElement.style.visibility = 'visible'; this.dragInProcess(true); } commitDrag() { this.checkSize(); this.need_recalc_page = true; } dragColumn(e) { if (!this._dragColumn) { this.startDragColumn(e); return; } this.setDragPosition(e); if (Math.abs(e.x - this._drag_x0) < 5 && Math.abs(e.y - this._drag_y0) < 5) { return; } this._drag_x0 = e.x; this._drag_y0 = e.y; let dropInfo = null; this.headerParts.forEach(p => { if (p && !dropInfo) { dropInfo = p.canDrop(e, false); //showMarker); } }); if (dropInfo) { if (e.target instanceof ColumnBand) { this.state.reorderBand(e.target, dropInfo); } else { this.state.reorderColumn(e.target, dropInfo, false); } this.commitDrag(); } let r0 = this.scroller.checkAutoScrollX(e.x); // Передаем rectangle this.checkParts(e.x, r0, e.target); } dropColumn(e) { this._dragColumn = false; this.scroller.stopAutoScroll(); this.dragItem.nativeElement.style.visibility = 'hidden'; let dropInfo = null; this.headerParts.forEach(p => { if (!dropInfo && p) { dropInfo = p.canDrop(e, false); } }); if (dropInfo) { this.state.reorderColumn(e.target, dropInfo); } else { this.state.fixDrag(e.target); // Если тащили из панели группировки, то! } this.state.dragDrop.clearDragItem(); this.dragInProcess(false); // Почему через 100 миллисекунд? Для того,чтобы плавно затухло setTimeout(() => { this.state.layoutsHandler.setLayoutsVisibility(); this.updatePage('dropColumn', true); // Может поменяться ширина центральной части this.checkSize(); }, 100); } /** * Обработка события строки - переключение чекбокса. * @param e Параметры события */ toggleCheckbox(e) { this.state.ui.toggleCheck(e.row, e.fieldName, e.value); } toggleCheckColumn(col) { this.state.ui.toggleCheckColumn(col); } setAppearance() { super.setAppearance(); this.dragItem.nativeElement.classList.add(this.state.sta.dragItemClass); } }; tslib_1.__decorate([ Output('rowMouseDown'), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "rowMouseDown", void 0); tslib_1.__decorate([ Output('rowMouseUp'), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "rowMouseUp", void 0); tslib_1.__decorate([ Output('rowClick'), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "rowClick", void 0); tslib_1.__decorate([ Output('cellClick'), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "cellClick", void 0); tslib_1.__decorate([ Output('rowDblClick'), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "rowDblClick", void 0); tslib_1.__decorate([ Output('rowKeyDown'), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "rowKeyDown", void 0); tslib_1.__decorate([ Output('contextMenu'), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "contextMenu", void 0); tslib_1.__decorate([ Output('selectionChanged'), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "selectionChanged", void 0); tslib_1.__decorate([ Output('checkedChanged'), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "checkedChanged", void 0); tslib_1.__decorate([ Output(), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "rowDrag", void 0); tslib_1.__decorate([ Output(), tslib_1.__metadata("design:type", EventEmitter) ], GridComponent.prototype, "rowDragged", void 0); tslib_1.__decorate([ ViewChild('dropMarker', { static: true }), tslib_1.__metadata("design:type", Object) ], GridComponent.prototype, "dropMarker", void 0); GridComponent = tslib_1.__decorate([ Component({ selector: 'true-grid', template: "<div #dropMarker class=\"true-grid-drop-marker\"></div>\r\n\r\n<true-menu-starter #menuStarter (itemClick)=\"menuItemClick($event)\"></true-menu-starter>\r\n<!-- \u0432\u0441\u043F\u043B\u044B\u0432\u0430\u044E\u0449\u0435\u0435 \u043E\u043A\u043D\u043E \u0434\u043B\u044F \u0444\u0438\u043B\u044C\u0442\u0440\u043E\u0432 -->\r\n<true-filter-popup #filterPopup *ngIf=\"state.settings.allowFilter\"\r\n (setFilter)=\"setFilter($event)\"\r\n (resetFilter)=\"resetFilter($event)\"\r\n (closed)=\"filterClosed($event)\">\r\n</true-filter-popup>\r\n<!-- \u042D\u043B\u0435\u043C\u0435\u043D\u0442, \u043A\u043E\u0442\u043E\u0440\u044B\u0439 \u043F\u0435\u0440\u0435\u0442\u0430\u0441\u043A\u0438\u0432\u0430\u0435\u0442\u0441\u044F \u043C\u044B\u0448\u044C\u044E, \u043F\u0440\u0438 reordering columns -->\r\n<div #dragItem true-drag-item class=\"true-grid-drag-item\">\r\n <true-grid-header *ngIf=\"isDragColumn()\"\r\n [ngClass]=\"state.settings.appearance.headerAreaClass\"\r\n [layout]=\"state.layoutDrag\"></true-grid-header>\r\n <div *ngIf=\"!isDragColumn()\" class=\"true-drag-data\" [ngClass]=\"settings.appearance.getDataClass()\">\r\n <table *ngFor=\"let r of draggedRows; let i=index\"\r\n [style.transform]=\"getDragTransform(i)\"\r\n [style.width]=\"getDragWidth()\"\r\n class=\"true-grid-data true-grid-data_fixed-height\">\r\n <colgroup>\r\n <col *ngFor=\"let c of state.layoutDrag.columns\" [style.width]=\"c.displayedWidthU\" />\r\n </colgroup>\r\n <tbody>\r\n <tr true-row\r\n [row]=\"r\"\r\n [true-layout]=\"state.layoutDrag\"\r\n [true-state]=\"state\"\r\n [true-i]=\"i\"\r\n [style.height.px]=\"state.settings.rowHeight\">\r\n </tr>\r\n </tbody>\r\n </table>\r\n </div>\r\n</div>\r\n<!-- \u041A\u043E\u043C\u043F\u043E\u043D\u0435\u043D\u0442, \u043E\u0441\u0443\u0449\u0435\u0441\u0442\u0432\u043B\u044F\u044E\u0449\u0438\u0439 \u0441\u0438\u043D\u0445\u0440\u043E\u043D\u043D\u044B\u0439 \u0441\u043A\u0440\u043E\u043B\u043B\u0438\u043D\u0433 \u0434\u0430\u043D\u043D\u044B\u0445 \u0438 \u0432\u0441\u0435\u0445 \u0441\u043E\u043F\u0443\u0442\u0441\u0442\u0432\u0443\u044E\u0449\u0438\u0445 \u044D\u043B\u0435\u043C\u0435\u043D\u0442\u043E\u0432 -->\r\n<true-scroller #scroller\r\n tabindex=\"-1\"\r\n [maxHeight]=\"maxHeight\"\r\n (keydown)=\"dataKeyDown($event)\"\r\n (autoscrollx)=\"gridAutoScrollX($event)\"\r\n (scroll)=\"gridScroll($event)\">\r\n <!-- \u0417\u0430\u0433\u043E\u043B\u043E\u0432\u043A\u0438 -->\r\n <true-grid-header #gridHeader true-header\r\n [layout]=\"state.layout\"\r\n [scroller]=\"scroller\"\r\n (toggleCheckColumn)=\"toggleCheckColumn($event)\"\r\n (resizeColumn)=\"resizeColumn($event)\">\r\n </true-grid-header>\r\n <!-- \u041E\u0441\u043D\u043E\u0432\u043D\u0430\u044F \u0447\u0430\u0441\u0442\u044C \u0434\u0430\u043D\u043D\u044B\u0445 -->\r\n <div true-data [ngClass]=\"settings.appearance.getDataClass()\">\r\n <table #gridData class=\"true-grid-data\"\r\n [class.true-grid-data_fixed-height]=\"state.settings.fixedRowHeight\"\r\n [style.width]=\"state.layout.dataWidth\"\r\n (mousedown)=\"dataMouseDown($event)\">\r\n <colgroup>\r\n <!-- \u0433\u0440\u0443\u043F\u043F\u0438\u0440\u043E\u0432\u043A\u0430 \u0438 \u0434\u0435\u0440\u0435\u0432\u044C\u044F -->\r\n <col *ngFor=\"let c of state.layout.levelColumns\" [style.width]=\"state.st.levelWidth\" />\r\n <!-- \u0434\u0430\u043D\u043D\u044B\u0435 -->\r\n <col *ngFor=\"let c of state.layout.columns\" [style.width]=\"c.displayedWidthU\" />\r\n </colgroup>\r\n\r\n <tbody *ngIf=\"!state.st.customTemplate\">\r\n <tr *ngFor=\"let r of RC.ghostRows('start'); trackBy: RC.trackGhostRowStart\" [style.height.px]=\"r.H\" style=\"border:0\">\r\n <td [style.height.px]=\"r.H\" style=\"padding:0; border-right: 0;\">&nbsp;</td>\r\n </tr>\r\n <tr *ngFor=\"let r of visibleRows; let i=index; trackBy: trackRow;\"\r\n true-row\r\n [view-port-left]=\"viewPortLeft\"\r\n [view-port-width]=\"viewPortWidth\"\r\n [row]=\"r\"\r\n [true-locale]=\"locale\"\r\n [true-layout]=\"state.layout\"\r\n [true-state]=\"state\"\r\n [true-i]=\"i\"\r\n [style.height.px]=\"state.settings.rowHeight\"\r\n (toggleCheckbox)=\"toggleCheckbox($event)\"\r\n (click)=\"dataRowClick($event, r)\"\r\n (contextmenu)=\"dataContextMenu($event)\"\r\n (dblclick)=\"dataRowDblClick($event, r)\"\r\n #displayedRows>\r\n </tr>\r\n <tr *ngFor=\"let r of RC.ghostRows('end')\" [style.height.px]=\"r.H\">\r\n <td [style.height.px]=\"r.H\" style=\"padding:0; border-right: 0;\">&nbsp;</td>\r\n </tr>\r\n <!--<tr *ngIf=\"visibleRows.length === 0\"><td style=\"border: 0;\"></td></tr>--> <!-- \u0412\u044B\u043D\u0435\u0441\u0442\u0438 \u0432 \u0441\u0442\u0438\u043B\u0438 -->\r\n </tbody>\r\n <!-- User's template -->\r\n <ng-content *ngIf=\"state.st.customTemplate\" select=\"[true-body]\"></ng-content>\r\n </table>\r\n </div>\r\n <!-- Footer -->\r\n <true-grid-footer #gridFooter true-footer [layout]=\"state.layout\"></true-grid-footer>\r\n</true-scroller>\r\n", providers: [{ provide: 'gridState', useClass: GridStateService }], styles: [":host{display:block;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.true-grid{box-sizing:border-box;height:100%;width:100%}.true-grid-data{box-sizing:border-box;table-layout:fixed;border-spacing:0;border-collapse:collapse;outline:0}.true-grid-data td{overflow-x:hidden;overflow-y:hidden}.true-grid-drop-marker{box-sizing:border-box;visibility:hidden;position:fixed;width:3px;border:1px solid #757779;background-color:rgba(255,255,255,.05);pointer-events:none;z-index:7}.true-grid-data_fixed-height td:not(.true-cell-indent){white-space:nowrap}.true-grid-data_fixed-height td:not(.true-cell-indent):not(.true-cell-checkbox){text-overflow:ellipsis}.true-cell-checkbox.true-check-by-click{cursor:pointer}.true-grid-drag-item{visibility:hidden;position:fixed;overflow-x:hidden;text-overflow:ellipsis;pointer-events:none;z-index:8}::ng-deep .true-grid-btn{cursor:pointer;align-self:stretch;visibility:hidden;display:-webkit-box;display:flex;-webkit-box-orient:vertical;-webkit-box-direction:normal;flex-direction:column;-webkit-box-pack:center;justify-content:center;flex-shrink:0}::ng-deep .true-grid-btn span{display:inline-block}::ng-deep .true-align-right{text-align:right}::ng-deep .true-align-center{text-align:center}::ng-deep .true-align-left{text-align:left!important}"] }), tslib_1.__param(0, Inject('gridState')), tslib_1.__metadata("design:paramtypes", [GridStateService, InternationalizationService, ElementRef, ChangeDetectorRef, KeyValueDiffers]) ], GridComponent); export { GridComponent }; //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZ3JpZC5jb21wb25lbnQuanMiLCJzb3VyY2VSb290Ijoibmc6Ly9AdHJ1ZS1kaXJlY3RpdmUvZ3JpZC8iLCJzb3VyY2VzIjpbInNyYy9ncmlkLmNvbXBvbmVudC50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiO0FBQUE7Ozs7RUFJRTtBQUNGLE9BQU8sRUFBRSxTQUFTLEVBQUUsTUFBTSxFQUFFLFNBQVMsRUFBRSxVQUFVLEVBQUUsaUJBQWlCLEVBQzNELGVBQWUsRUFBRSxZQUFZLEVBQUUsTUFBTSxFQUN0QyxNQUFNLGVBQWUsQ0FBQztBQUU5QixPQUFPLEVBQUUsU0FBUyxFQUFFLE1BQU0sZ0JBQWdCLENBQUM7QUFFM0MsT0FBTyxFQUFVLFVBQVUsRUFBZ0IsUUFBUSxFQUMxQyxZQUFZLEVBQUUsUUFBUSxFQUFFLElBQUksRUFDNUIsU0FBUyxFQUFFLE1BQU0sc0JBQXNCLENBQUM7QUFFakQsT0FBTyxFQUFFLFlBQVksRUFBRSxhQUFhLEVBQUUsZ0JBQWdCLEVBQzdDLGNBQWMsRUFBRSxNQUFNLHNCQUFzQixDQUFDO0FBRXRELE9BQU8sRUFBRSxpQkFBaUIsRUFBRSxNQUFNLHVCQUF1QixDQUFDO0FBRTFELE9BQU8sRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLHNCQUFzQixDQUFDO0FBQ3hELE9BQU8sRUFBRSwyQkFBMkIsRUFBRSxNQUFNLHFEQUFxRCxDQUFDO0FBWWxHLElBQWEsYUFBYSxHQUExQixNQUFhLGFBQWMsU0FBUSxpQkFBaUI7SUFrdUJsRCxZQUM4QixLQUF1QixFQUN6QyxJQUFpQyxFQUNqQyxVQUFzQixFQUN0QixjQUFpQyxFQUNqQyxlQUFnQztRQUV4QyxLQUFLLENBQUMsS0FBSyxFQUFFLElBQUksRUFBRSxVQUFVLEVBQUUsY0FBYyxFQUFFLGVBQWUsQ0FBQyxDQUFDO1FBTnRDLFVBQUssR0FBTCxLQUFLLENBQWtCO1FBQ3pDLFNBQUksR0FBSixJQUFJLENBQTZCO1FBQ2pDLGVBQVUsR0FBVixVQUFVLENBQVk7UUFDdEIsbUJBQWMsR0FBZCxj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