From 706e4c35cd64f84accadf20ba6b38ed7822ed27d Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Tue, 6 Nov 2018 18:40:41 +0200 Subject: [PATCH 01/24] feat(filtering): header group component POC #542 # Conflicts: # projects/igniteui-angular/src/lib/grids/column.component.ts # projects/igniteui-angular/src/lib/grids/grid-header.component.ts # projects/igniteui-angular/src/lib/grids/grid/grid.component.html # projects/igniteui-angular/src/lib/grids/grid/grid.component.ts # projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid.component.html --- .../styles/components/grid/_grid-theme.scss | 13 +- .../igniteui-angular/src/lib/core/utils.ts | 16 + .../src/lib/grids/column.component.ts | 58 ++- .../grid-filtering-cell.component.ts | 28 -- .../src/lib/grids/grid-base.component.ts | 57 ++- .../lib/grids/grid-column-resizing.service.ts | 123 +++++ .../src/lib/grids/grid-common.module.ts | 8 +- .../grids/grid-header-group.component.html | 37 ++ .../lib/grids/grid-header-group.component.ts | 130 +++++ .../src/lib/grids/grid-header.component.html | 52 +- .../src/lib/grids/grid-header.component.ts | 197 +------- .../src/lib/grids/grid.common.ts | 39 +- .../src/lib/grids/grid/grid.component.html | 16 +- .../src/lib/grids/grid/grid.component.ts | 3 +- .../grids/tree-grid/tree-grid.component.html | 26 +- src/app/app.component.ts | 5 + src/app/app.module.ts | 4 +- src/app/app.routing.ts | 5 + .../grid-column-groups.sample.html | 1 - .../grid-column-moving.sample.html | 3 +- .../grid-percantge-widths.sample.html | 51 ++ .../grid-percantge-widths.sample.ts | 453 ++++++++++++++++++ src/app/routing.ts | 5 + 23 files changed, 955 insertions(+), 375 deletions(-) create mode 100644 projects/igniteui-angular/src/lib/grids/grid-column-resizing.service.ts create mode 100644 projects/igniteui-angular/src/lib/grids/grid-header-group.component.html create mode 100644 projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts create mode 100644 src/app/grid-percentage-columns/grid-percantge-widths.sample.html create mode 100644 src/app/grid-percentage-columns/grid-percantge-widths.sample.ts diff --git a/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss b/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss index 645aadea6e7..e811bace2e5 100644 --- a/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss +++ b/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss @@ -1172,12 +1172,12 @@ %grid__drag-ghost-image { position: absolute; - display: flex; + // display: flex; align-items: center; background-color: --var($theme, 'ghost-header-background'); color: --var($theme, 'ghost-header-text-color'); - height: map-get($grid-header-height, 'comfortable'); - min-height: map-get($grid-header-height, 'comfortable'); + // height: map-get($grid-header-height, 'comfortable'); + // min-height: map-get($grid-header-height, 'comfortable'); top: -99999px; left: -99999px; border: none; @@ -1211,18 +1211,23 @@ %grid__drag-ghost-image-icon { color: --var($theme, 'ghost-header-icon-color'); margin-right: rem(12px); + margin-bottom: rem(12px); } %grid__drag-ghost-image-icon-group { color: --var($theme, 'ghost-header-icon-color'); padding: --var($grid-header-padding, 'comfortable'); padding-right: 0; - margin-right: rem(8); + // margin-right: rem(8); } %igx-grid__drag-col-header { background-color: --var($theme, 'header-background'); + %grid-thead-title { + opacity: .4; + } + %grid-cell-header-title, %grid-cell-header-icons { opacity: .4; diff --git a/projects/igniteui-angular/src/lib/core/utils.ts b/projects/igniteui-angular/src/lib/core/utils.ts index 96301bbfc2f..71288c2b977 100644 --- a/projects/igniteui-angular/src/lib/core/utils.ts +++ b/projects/igniteui-angular/src/lib/core/utils.ts @@ -230,6 +230,22 @@ export function isNavigationKey(key: string): boolean { 'home', 'end', 'space', 'spacebar', ' '].indexOf(key) !== -1; } +/** + *@hidden + */ +export function flatten(arr: any[]) { + let result = []; + + arr.forEach(el => { + result.push(el); + if (el.children) { + const children = Array.isArray(el.children) ? el.children : el.children.toArray(); + result = result.concat(flatten(children)); + } + }); + return result; +} + export interface CancelableEventArgs { /** * Provides the ability to cancel the event. diff --git a/projects/igniteui-angular/src/lib/grids/column.component.ts b/projects/igniteui-angular/src/lib/grids/column.component.ts index 392a2d04947..3500bc87204 100644 --- a/projects/igniteui-angular/src/lib/grids/column.component.ts +++ b/projects/igniteui-angular/src/lib/grids/column.component.ts @@ -21,15 +21,17 @@ import { IgxCellHeaderTemplateDirective, IgxCellTemplateDirective } from './grid.common'; -import { - IgxBooleanFilteringOperand, IgxNumberFilteringOperand, IgxDateFilteringOperand, - IgxStringFilteringOperand, - IgxGridBaseComponent, - FilteringExpressionsTree -} from '../../public_api'; import { IgxGridHeaderComponent } from './grid-header.component'; -import { valToPxlsUsingRange } from '../core/utils'; import { DefaultSortingStrategy, ISortingStrategy } from '../data-operations/sorting-strategy'; +import { valToPxlsUsingRange, flatten } from '../core/utils'; +import { + IgxBooleanFilteringOperand, + IgxNumberFilteringOperand, + IgxDateFilteringOperand, + IgxStringFilteringOperand } from '../data-operations/filtering-condition'; +import { IgxGridBaseComponent } from './grid-base.component'; +import { FilteringExpressionsTree } from '../data-operations/filtering-expressions-tree'; +import { IgxGridFilteringCellComponent } from './filtering/grid-filtering-cell.component'; /** * **Ignite UI for Angular Column** - @@ -1064,9 +1066,19 @@ export class IgxColumnComponent implements AfterContentInit { * @memberof IgxColumnComponent */ get headerCell(): IgxGridHeaderComponent { - if (this.grid.headerList.length > 0) { - return flatten(this.grid.headerList.toArray()).find((h) => h.column === this); - } + return this.grid.headerCellList.find((header) => header.column === this); + } + + /** + * Returns a reference to the filter cell of the column. + * ```typescript + * let column = this.grid.columnList.filter(c => c.field === 'ID')[0]; + * let filterell = column.filterell; + * ``` + * @memberof IgxColumnComponent + */ + get filterell(): IgxGridFilteringCellComponent { + return this.grid.filterCellList.find((filterCell) => filterCell.column === this); } /** @@ -1122,16 +1134,15 @@ export class IgxColumnComponent implements AfterContentInit { if (this.headerCell) { let headerCell; - const titleIndex = this.grid.hasMovableColumns ? 1 : 0; - if (this.headerTemplate && this.headerCell.elementRef.nativeElement.children[titleIndex].children.length > 0) { - headerCell = Math.max(...Array.from(this.headerCell.elementRef.nativeElement.children[titleIndex].children) + if (this.headerTemplate && this.headerCell.elementRef.nativeElement.children[0].children.length > 0) { + headerCell = Math.max(...Array.from(this.headerCell.elementRef.nativeElement.children[0].children) .map((child) => valToPxlsUsingRange(range, child))); } else { - headerCell = valToPxlsUsingRange(range, this.headerCell.elementRef.nativeElement.children[titleIndex]); + headerCell = valToPxlsUsingRange(range, this.headerCell.elementRef.nativeElement.children[0]); } - if (this.sortable || (this.grid.allowFiltering && this.filterable)) { - headerCell += this.headerCell.elementRef.nativeElement.children[titleIndex + 1].getBoundingClientRect().width; + if (this.sortable) { + headerCell += this.headerCell.elementRef.nativeElement.children[1].getBoundingClientRect().width; } const headerStyle = this.grid.document.defaultView.getComputedStyle(this.headerCell.elementRef.nativeElement); @@ -1350,7 +1361,6 @@ export class IgxColumnGroupComponent extends IgxColumnComponent implements After if (val.width && val.width.indexOf('%') !== -1) { isChildrenWidthInPercent = true; } - return acc + parseInt(val.width, 10); }, 0)}`; return isChildrenWidthInPercent ? width + '%' : width; @@ -1358,17 +1368,3 @@ export class IgxColumnGroupComponent extends IgxColumnComponent implements After set width(val) { } } - - - -function flatten(arr: any[]) { - let result = []; - - arr.forEach(el => { - result.push(el); - if (el.children) { - result = result.concat(flatten(el.children.toArray())); - } - }); - return result; -} diff --git a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts index 2276e0aedff..2034d223a4b 100644 --- a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts +++ b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts @@ -61,37 +61,9 @@ export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit { @ViewChild('complexChip', { read: IgxChipComponent }) protected complexChip: IgxChipComponent; - @HostBinding('style.min-width') - @HostBinding('style.max-width') - @HostBinding('style.flex-basis') - get width() { - // HACK - think of a better solution - const colWidth = this.column.width; - const isPercentageWidth = colWidth && typeof colWidth === 'string' && colWidth.indexOf('%') !== -1; - - if (isPercentageWidth) { - const firstContentCell = this.column.cells[0]; - if (firstContentCell) { - return firstContentCell.nativeElement.getBoundingClientRect().width + 'px'; - } - } else { - return this.column.width; - } - } - @HostBinding('class.igx-grid__filtering-cell') public cssClass = 'igx-grid__filtering-cell'; - @HostBinding('class.igx-grid__th--pinned-last') - get isLastPinned() { - const pinnedCols = this.filteringService.grid.pinnedColumns; - if (pinnedCols.length === 0) { - return false; - } else { - return pinnedCols.indexOf(this.column) === pinnedCols.length - 1; - } - } - constructor(public cdr: ChangeDetectorRef, public filteringService: IgxFilteringService, public navService: IgxGridNavigationService) { this.filteringService.subscribeToEvents(); } diff --git a/projects/igniteui-angular/src/lib/grids/grid-base.component.ts b/projects/igniteui-angular/src/lib/grids/grid-base.component.ts index 3d3c98d7e56..ff31a402efb 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-base.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-base.component.ts @@ -28,7 +28,7 @@ import { import { Subject } from 'rxjs'; import { takeUntil } from 'rxjs/operators'; import { IgxSelectionAPIService } from '../core/selection'; -import { cloneArray, isNavigationKey, mergeObjects, CancelableEventArgs } from '../core/utils'; +import { cloneArray, isNavigationKey, mergeObjects, CancelableEventArgs, flatten } from '../core/utils'; import { DataType, DataUtil } from '../data-operations/data-util'; import { FilteringLogic, IFilteringExpression } from '../data-operations/filtering-expression.interface'; import { IGroupByRecord } from '../data-operations/groupby-record.interface'; @@ -61,6 +61,7 @@ import { IDisplayDensityOptions, DisplayDensityToken, DisplayDensityBase } from import { IgxGridRowComponent } from './grid'; import { IgxFilteringService } from './filtering/grid-filtering.service'; import { IgxGridFilteringCellComponent } from './filtering/grid-filtering-cell.component'; +import { IgxGridHeaderGroupComponent } from './grid-header-group.component'; const MINIMUM_COLUMN_WIDTH = 136; @@ -1153,14 +1154,41 @@ export abstract class IgxGridBaseComponent extends DisplayDensityBase implements /** * @hidden */ - @ViewChildren(IgxGridHeaderComponent, { read: IgxGridHeaderComponent }) - public headerList: QueryList; + @ViewChildren(IgxGridHeaderGroupComponent, { read: IgxGridHeaderGroupComponent }) + public headerGroups: QueryList; /** - * @hidden + * A list of all `IgxGridHeaderGroupComponent`. + * ```typescript + * const headerGroupsList = this.grid.headerGroupsList; + * ``` + * @memberof IgxGridBaseComponent + */ + get headerGroupsList(): IgxGridHeaderGroupComponent[] { + return flatten(this.headerGroups.toArray()); + } + + /** + * A list of all `IgxGridHeaderComponent`. + * ```typescript + * const headers = this.grid.headerCellList; + * ``` + * @memberof IgxGridBaseComponent */ - @ViewChildren(IgxGridFilteringCellComponent, { read: IgxGridFilteringCellComponent }) - public filterCellList: QueryList; + get headerCellList(): IgxGridHeaderComponent[] { + return this.headerGroupsList.map((headerGroup) => headerGroup.headerCell).filter((headerCell) => headerCell); + } + + /** + * A list of all `IgxGridFilteringCellComponent`. + * ```typescript + * const filterCells = this.grid.filterCellList; + * ``` + * @memberof IgxGridBaseComponent + */ + get filterCellList(): IgxGridFilteringCellComponent[] { + return this.headerGroupsList.map((headerGroup) => headerGroup.filterCell).filter((filterCell) => filterCell); + } @ViewChildren('row') private _rowList: QueryList; @@ -1881,14 +1909,6 @@ export abstract class IgxGridBaseComponent extends DisplayDensityBase implements * @hidden */ public draggedColumn: IgxColumnComponent; - /** - * @hidden - */ - public isColumnResizing: boolean; - /** - * @hidden - */ - public isColumnMoving: boolean; /** * @hidden @@ -2264,6 +2284,15 @@ export abstract class IgxGridBaseComponent extends DisplayDensityBase implements return this.theadRow.nativeElement.clientHeight + this.tbody.nativeElement.clientHeight; } + /** + * @hidden + */ + get headerCheckboxWidth() { + if (this.headerCheckboxContainer) { + return this.headerCheckboxContainer.nativeElement.clientWidth; + } + } + /** * Returns the `IgxGridComponent`'s rows height. * ```typescript diff --git a/projects/igniteui-angular/src/lib/grids/grid-column-resizing.service.ts b/projects/igniteui-angular/src/lib/grids/grid-column-resizing.service.ts new file mode 100644 index 00000000000..3d86a1f76e7 --- /dev/null +++ b/projects/igniteui-angular/src/lib/grids/grid-column-resizing.service.ts @@ -0,0 +1,123 @@ +import { Injectable } from '@angular/core'; +import { isFirefox } from '../core/utils'; +import { IgxColumnComponent } from './column.component'; + +/** @hidden */ +@Injectable() +export class IgxColumnResizingService { + + public startResizePos: number; + public isColumnResizing: boolean; + public resizeCursor: any = null; + public showResizer = false; + public resizerHeight: number; + public resizeEndTimeout = isFirefox() ? 200 : 0; + public column: IgxColumnComponent; + + private pinnedMaxWidth; + + get restrictResizeMin(): number { + const actualMinWidth = parseFloat(this.column.minWidth); + const defaultMinWidth = parseFloat(this.column.defaultMinWidth); + + let minWidth = Number.isNaN(actualMinWidth) || actualMinWidth < defaultMinWidth ? defaultMinWidth : actualMinWidth; + minWidth = minWidth < parseFloat(this.column.width) ? minWidth : parseFloat(this.column.width); + + return minWidth - this.column.headerCell.elementRef.nativeElement.getBoundingClientRect().width; + } + + get restrictResizeMax(): number { + const actualWidth = this.column.headerCell.elementRef.nativeElement.getBoundingClientRect().width; + + if (this.column.pinned) { + const pinnedMaxWidth = this.pinnedMaxWidth = + this.column.grid.calcPinnedContainerMaxWidth - this.column.grid.getPinnedWidth(true) + actualWidth; + + if (this.column.maxWidth && parseFloat(this.column.maxWidth) < pinnedMaxWidth) { + this.pinnedMaxWidth = this.column.maxWidth; + + return parseFloat(this.column.maxWidth) - actualWidth; + } else { + return pinnedMaxWidth - actualWidth; + } + } else { + if (this.column.maxWidth) { + return parseFloat(this.column.maxWidth) - actualWidth; + } else { + return Number.MAX_SAFE_INTEGER; + } + } + } + + public autosizeColumnOnDblClick() { + if (this.column.resizable) { + const currentColWidth = this.column.headerCell.elementRef.nativeElement.getBoundingClientRect().width; + + const size = this.column.getLargestCellWidth(); + + if (this.column.pinned) { + const newPinnedWidth = this.column.grid.getPinnedWidth(true) - currentColWidth + parseFloat(size); + + if (newPinnedWidth <= this.column.grid.calcPinnedContainerMaxWidth) { + this.column.width = size; + } + } else if (this.column.maxWidth && (parseFloat(size) > parseFloat(this.column.maxWidth))) { + this.column.width = parseFloat(this.column.maxWidth) + 'px'; + } else if (parseFloat(size) < parseFloat(this.column.defaultMinWidth)) { + this.column.width = this.column.defaultMinWidth + 'px'; + } else { + this.column.width = size; + } + + this.column.grid.markForCheck(); + this.column.grid.reflow(); + this.column.grid.onColumnResized.emit({ + column: this.column, + prevWidth: currentColWidth.toString(), + newWidth: this.column.width + }); + } + } + + public resizeColumn(event) { + + this.isColumnResizing = false; + + this.showResizer = false; + const diff = event.clientX - this.startResizePos; + + if (this.column.resizable) { + let currentColWidth = parseFloat(this.column.width); + + const actualMinWidth = parseFloat(this.column.minWidth); + const defaultMinWidth = parseFloat(this.column.defaultMinWidth); + + let colMinWidth = Number.isNaN(actualMinWidth) || actualMinWidth < defaultMinWidth ? defaultMinWidth : actualMinWidth; + const colMaxWidth = this.column.pinned ? parseFloat(this.pinnedMaxWidth) : parseFloat(this.column.maxWidth); + + const actualWidth = this.column.headerCell.elementRef.nativeElement.getBoundingClientRect().width; + + currentColWidth = Number.isNaN(currentColWidth) || (currentColWidth < actualWidth) ? actualWidth : currentColWidth; + colMinWidth = colMinWidth < currentColWidth ? colMinWidth : currentColWidth; + + if (currentColWidth + diff < colMinWidth) { + this.column.width = colMinWidth + 'px'; + } else if (colMaxWidth && (currentColWidth + diff > colMaxWidth)) { + this.column.width = colMaxWidth + 'px'; + } else { + this.column.width = (currentColWidth + diff) + 'px'; + } + + this.column.grid.markForCheck(); + this.column.grid.reflow(); + + if (currentColWidth !== parseFloat(this.column.width)) { + this.column.grid.onColumnResized.emit({ + column: this.column, + prevWidth: currentColWidth.toString(), + newWidth: this.column.width + }); + } + } + } +} diff --git a/projects/igniteui-angular/src/lib/grids/grid-common.module.ts b/projects/igniteui-angular/src/lib/grids/grid-common.module.ts index c453f53ab72..af3d1392672 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-common.module.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-common.module.ts @@ -55,6 +55,8 @@ import { IgxRowEditTabStopDirective } from './grid.rowEdit.directive'; import { IgxGridNavigationService } from './grid-navigation.service'; +import { IgxGridHeaderGroupComponent } from './grid-header-group.component'; +import { IgxColumnResizingService } from './grid-column-resizing.service'; @NgModule({ declarations: [ @@ -81,8 +83,8 @@ import { IgxGridNavigationService } from './grid-navigation.service'; IgxGridFilteringRowComponent, IgxDatePipeComponent, IgxDecimalPipeComponent, - IgxRowComponent - + IgxRowComponent, + IgxGridHeaderGroupComponent ], entryComponents: [ IgxColumnComponent, @@ -132,6 +134,7 @@ import { IgxGridNavigationService } from './grid-navigation.service'; IgxColumnPinningModule, IgxGridFilteringCellComponent, IgxGridFilteringRowComponent, + IgxGridHeaderGroupComponent ], imports: [ CommonModule, @@ -160,6 +163,7 @@ import { IgxGridNavigationService } from './grid-navigation.service'; IgxSelectionAPIService, IgxColumnMovingService, IgxGridNavigationService, + IgxColumnResizingService, { provide: IgxGridTransaction, useClass: IgxBaseTransactionService } ] }) diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html new file mode 100644 index 00000000000..4be9386561e --- /dev/null +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html @@ -0,0 +1,37 @@ + + +
{{ column.header }}
+
+ + + +
+ +
+ + + + + + + + + + + + +
+
+
+ +
+ + diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts new file mode 100644 index 00000000000..9867865b2e8 --- /dev/null +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts @@ -0,0 +1,130 @@ +import { + ChangeDetectorRef, + Component, + HostBinding, + Input, + ViewChild, + QueryList, + ViewChildren, + forwardRef +} from '@angular/core'; +import { IgxColumnComponent } from './column.component'; +import { IgxFilteringService } from './filtering/grid-filtering.service'; +import { GridBaseAPIService } from './api.service'; +import { IgxGridBaseComponent } from './grid-base.component'; +import { IgxColumnResizingService } from './grid-column-resizing.service'; +import { IgxGridHeaderComponent } from './grid-header.component'; +import { IgxGridFilteringCellComponent } from './filtering/grid-filtering-cell.component'; +import { isIE } from '../core/utils'; + + +/** + * @hidden + */ +@Component({ + preserveWhitespaces: false, + selector: 'igx-grid-header-group', + templateUrl: './grid-header-group.component.html' +}) +export class IgxGridHeaderGroupComponent { + + @Input() + public column: IgxColumnComponent; + + @Input() + public gridID: string; + + @ViewChild(IgxGridHeaderComponent) + public headerCell: IgxGridHeaderComponent; + + @ViewChild(IgxGridFilteringCellComponent) + public filterCell: IgxGridFilteringCellComponent; + + @ViewChildren(forwardRef(() => IgxGridHeaderGroupComponent), { read: IgxGridHeaderGroupComponent }) + public children: QueryList; + + @HostBinding('style.min-width') + @HostBinding('style.flex-basis') + get width() { + const colWidth = this.column.width; + const isNotPxInIE = isIE() && colWidth && typeof colWidth === 'string' && colWidth.indexOf('px') === -1; + + // a hack for fixing issue #2917, to be revised if ussue #1951 is ever fixed + if (isNotPxInIE && this.grid.pinnedColumns.length > 0) { + const firstContentCell = this.column.cells[0]; + if (firstContentCell) { + return firstContentCell.nativeElement.getBoundingClientRect().width + 'px'; + } + } + + return colWidth; + } + + @HostBinding('class') + get styleClasses(): string { + const defaultClasses = [ + 'igx-grid__thead-item' + ]; + + const classList = { + 'igx-grid__th--pinned-last': this.isLastPinned, + 'igx-grid__drag-col-header': this.isHeaderDragged + }; + + Object.entries(classList).forEach(([klass, value]) => { + if (value) { + defaultClasses.push(klass); + } + }); + return defaultClasses.join(' '); + } + + @HostBinding('style.z-index') + get zIndex() { + if (!this.column.pinned) { + return null; + } + return 9999 - this.grid.pinnedColumns.indexOf(this.column); + } + + get grid(): any { + return this.gridAPI.get(this.gridID); + } + + get isLastPinned() { + const pinnedCols = this.grid.pinnedColumns; + if (pinnedCols.length === 0) { + return false; + } else { + return pinnedCols.indexOf(this.column) === pinnedCols.length - 1; + } + } + + get isHeaderDragged() { + return this.grid.draggedColumn === this.column; + } + + constructor( + public cdr: ChangeDetectorRef, + public gridAPI: GridBaseAPIService, + public colReszingService: IgxColumnResizingService, + public filteringService: IgxFilteringService) { } + + public onResizeAreaMouseOver() { + if (this.column.resizable) { + this.colReszingService.column = this.column; + this.colReszingService.resizeCursor = 'col-resize'; + } + } + + public onResizeAreaMouseDown(event) { + if (event.button === 0 && this.column.resizable) { + this.colReszingService.showResizer = true; + this.colReszingService.isColumnResizing = true; + this.colReszingService.resizerHeight = this.column.grid.calcResizerHeight; + this.colReszingService.startResizePos = event.clientX; + } else { + this.colReszingService.resizeCursor = null; + } + } +} diff --git a/projects/igniteui-angular/src/lib/grids/grid-header.component.html b/projects/igniteui-angular/src/lib/grids/grid-header.component.html index b1d1d032c98..67d857a69a9 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid-header.component.html @@ -2,49 +2,11 @@ {{ column.header || column.field }} - - -
{{ column.header }}
-
- -
- - -
-
-
- -
- - - - - - - - -
- {{sortingIcon}} - -
- - - -
-
- -
- - - -
+ + + + +
+ {{sortingIcon}} +
diff --git a/projects/igniteui-angular/src/lib/grids/grid-header.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header.component.ts index 216225c4d59..f76de1704cd 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header.component.ts @@ -1,5 +1,4 @@ import { - AfterViewInit, ChangeDetectionStrategy, ChangeDetectorRef, Component, @@ -9,22 +8,15 @@ import { HostListener, Input, NgZone, - OnInit, - ViewChild, - QueryList, - ViewChildren, - OnDestroy + OnInit } from '@angular/core'; import { DataType } from '../data-operations/data-util'; import { SortingDirection } from '../data-operations/sorting-expression.interface'; -import { RestrictDrag } from '../directives/dragdrop/dragdrop.directive'; import { GridBaseAPIService } from './api.service'; import { IgxColumnComponent } from './column.component'; -import { IgxColumnMovingService } from './grid.common'; -import { isFirefox } from '../core/utils'; import { IgxGridBaseComponent } from './grid-base.component'; import { IgxFilteringService } from './filtering/grid-filtering.service'; -import { IgxGridComponent } from './grid'; +import { IgxColumnResizingService } from './grid-column-resizing.service'; /** * @hidden @@ -35,7 +27,7 @@ import { IgxGridComponent } from './grid'; selector: 'igx-grid-header', templateUrl: './grid-header.component.html' }) -export class IgxGridHeaderComponent implements OnInit, DoCheck, AfterViewInit, OnDestroy { +export class IgxGridHeaderComponent implements OnInit, DoCheck { @Input() public column: IgxColumnComponent; @@ -56,8 +48,6 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck, AfterViewInit, O 'desc': this.descending, 'igx-grid__th--number': this.column.dataType === DataType.Number, 'igx-grid__th--sorted': this.sorted, - 'igx-grid__drag-col-header': this.dragged, - 'igx-grid__th--pinned-last': this.isLastPinned, 'igx-grid__th--filtering': this.filteringService.filteredColumn === this.column }; @@ -69,25 +59,6 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck, AfterViewInit, O return defaultClasses.join(' '); } - - @HostBinding('style.min-width') - @HostBinding('style.max-width') - @HostBinding('style.flex-basis') - get width() { - // HACK - think of a better solution - const colWidth = this.column.width; - const isPercentageWidth = colWidth && typeof colWidth === 'string' && colWidth.indexOf('%') !== -1; - - if (isPercentageWidth) { - const firstContentCell = this.column.cells[0]; - if (firstContentCell) { - return firstContentCell.nativeElement.getBoundingClientRect().width + 'px'; - } - } else { - return this.column.width; - } - } - @HostBinding('style.height.px') get height() { if (this.grid.hasColumnGroups) { @@ -121,14 +92,6 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck, AfterViewInit, O return this.column === this.column.grid.draggedColumn; } - @HostBinding('style.z-index') - get zIndex() { - if (!this.column.pinned) { - return null; - } - return 9999 - this.grid.pinnedColumns.indexOf(this.column); - } - @HostBinding('attr.role') public hostRole = 'columnheader'; @@ -140,29 +103,14 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck, AfterViewInit, O return `${this.gridID}_${this.column.field}`; } - @ViewChild('resizeArea') - public resizeArea: ElementRef; - - @ViewChildren(IgxGridHeaderComponent, { read: IgxGridHeaderComponent }) - public children: QueryList; - - public resizeCursor = null; - public showResizer = false; - public resizerHeight; - public dragDirection: RestrictDrag = RestrictDrag.HORIZONTALLY; - public resizeEndTimeout = isFirefox() ? 200 : 0; - protected sortDirection = SortingDirection.None; - private _startResizePos; - private _pinnedMaxWidth; - constructor( public gridAPI: GridBaseAPIService, + public colReszingService: IgxColumnResizingService, public cdr: ChangeDetectorRef, public elementRef: ElementRef, public zone: NgZone, - private cms: IgxColumnMovingService, public filteringService: IgxFilteringService ) { } @@ -176,29 +124,9 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck, AfterViewInit, O this.cdr.markForCheck(); } - ngAfterViewInit() { - if (!this.column.columnGroup) { - this.zone.runOutsideAngular(() => { - this.resizeArea.nativeElement.addEventListener('mouseover', this.onResizeAreaMouseOver.bind(this)); - this.resizeArea.nativeElement.addEventListener('mousedown', this.onResizeAreaMouseDown.bind(this)); - this.resizeArea.nativeElement.addEventListener('dblclick', this.onResizeAreaDblClick.bind(this)); - }); - } - } - - ngOnDestroy() { - if (!this.column.columnGroup) { - this.zone.runOutsideAngular(() => { - this.resizeArea.nativeElement.removeEventListener('mouseover', this.onResizeAreaMouseOver); - this.resizeArea.nativeElement.removeEventListener('mousedown', this.onResizeAreaMouseDown); - this.resizeArea.nativeElement.removeEventListener('dblclick', this.onResizeAreaDblClick); - }); - } - } - @HostListener('click', ['$event']) public onClick(event) { - if (!this.column.grid.isColumnResizing) { + if (!this.colReszingService.isColumnResizing) { event.stopPropagation(); if (this.grid.filteringService.isFilterRowVisible) { if (this.column.filterable && !this.column.columnGroup && @@ -224,39 +152,6 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck, AfterViewInit, O } } - get restrictResizeMin(): number { - const actualMinWidth = parseFloat(this.column.minWidth); - const defaultMinWidth = parseFloat(this.column.defaultMinWidth); - - let minWidth = Number.isNaN(actualMinWidth) || actualMinWidth < defaultMinWidth ? defaultMinWidth : actualMinWidth; - minWidth = minWidth < parseFloat(this.column.width) ? minWidth : parseFloat(this.column.width); - - return minWidth - this.elementRef.nativeElement.getBoundingClientRect().width; - } - - get restrictResizeMax(): number { - const actualWidth = this.elementRef.nativeElement.getBoundingClientRect().width; - - if (this.column.pinned) { - const pinnedMaxWidth = this._pinnedMaxWidth = - this.grid.calcPinnedContainerMaxWidth - this.grid.getPinnedWidth(true) + actualWidth; - - if (this.column.maxWidth && parseFloat(this.column.maxWidth) < pinnedMaxWidth) { - this._pinnedMaxWidth = this.column.maxWidth; - - return parseFloat(this.column.maxWidth) - actualWidth; - } else { - return pinnedMaxWidth - actualWidth; - } - } else { - if (this.column.maxWidth) { - return parseFloat(this.column.maxWidth) - actualWidth; - } else { - return Number.MAX_SAFE_INTEGER; - } - } - } - get grid(): any { return this.gridAPI.get(this.gridID); } @@ -278,86 +173,4 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck, AfterViewInit, O const expr = this.gridAPI.get(this.gridID).sortingExpressions.find((x) => x.fieldName === this.column.field); this.sortDirection = expr ? expr.dir : SortingDirection.None; } - - private onResizeAreaMouseOver() { - if (this.column.resizable) { - this.resizeCursor = 'col-resize'; - this.cdr.detectChanges(); - } - } - - private onResizeAreaMouseDown(event) { - if (event.button === 0 && this.column.resizable) { - this.showResizer = true; - this.column.grid.isColumnResizing = true; - this.resizerHeight = this.grid.calcResizerHeight; - this._startResizePos = event.clientX; - } else { - this.resizeCursor = null; - } - this.cdr.detectChanges(); - } - - private onResizeAreaDblClick() { - if (this.column.resizable) { - const currentColWidth = this.elementRef.nativeElement.getBoundingClientRect().width; - - const size = this.column.getLargestCellWidth(); - - if (this.column.pinned) { - const newPinnedWidth = this.grid.getPinnedWidth(true) - currentColWidth + parseFloat(size); - - if (newPinnedWidth <= this.grid.calcPinnedContainerMaxWidth) { - this.column.width = size; - } - } else if (this.column.maxWidth && (parseFloat(size) > parseFloat(this.column.maxWidth))) { - this.column.width = parseFloat(this.column.maxWidth) + 'px'; - } else if (parseFloat(size) < parseFloat(this.column.defaultMinWidth)) { - this.column.width = this.column.defaultMinWidth + 'px'; - } else { - this.column.width = size; - } - - this.grid.markForCheck(); - this.grid.reflow(); - this.grid.onColumnResized.emit({ column: this.column, prevWidth: currentColWidth.toString(), newWidth: this.column.width }); - } - } - - public onResize(event) { - this.column.grid.isColumnResizing = false; - - this.showResizer = false; - const diff = event.clientX - this._startResizePos; - - if (this.column.resizable) { - let currentColWidth = parseFloat(this.column.width); - - const actualMinWidth = parseFloat(this.column.minWidth); - const defaultMinWidth = parseFloat(this.column.defaultMinWidth); - - let colMinWidth = Number.isNaN(actualMinWidth) || actualMinWidth < defaultMinWidth ? defaultMinWidth : actualMinWidth; - const colMaxWidth = this.column.pinned ? parseFloat(this._pinnedMaxWidth) : parseFloat(this.column.maxWidth); - - const actualWidth = this.elementRef.nativeElement.getBoundingClientRect().width; - - currentColWidth = Number.isNaN(currentColWidth) || (currentColWidth < actualWidth) ? actualWidth : currentColWidth; - colMinWidth = colMinWidth < currentColWidth ? colMinWidth : currentColWidth; - - if (currentColWidth + diff < colMinWidth) { - this.column.width = colMinWidth + 'px'; - } else if (colMaxWidth && (currentColWidth + diff > colMaxWidth)) { - this.column.width = colMaxWidth + 'px'; - } else { - this.column.width = (currentColWidth + diff) + 'px'; - } - - this.grid.markForCheck(); - this.grid.reflow(); - - if (currentColWidth !== parseFloat(this.column.width)) { - this.grid.onColumnResized.emit({ column: this.column, prevWidth: currentColWidth.toString(), newWidth: this.column.width }); - } - } - } } diff --git a/projects/igniteui-angular/src/lib/grids/grid.common.ts b/projects/igniteui-angular/src/lib/grids/grid.common.ts index a210f9876cc..f4c658f0a95 100644 --- a/projects/igniteui-angular/src/lib/grids/grid.common.ts +++ b/projects/igniteui-angular/src/lib/grids/grid.common.ts @@ -123,6 +123,7 @@ export class IgxColumnResizerDirective implements OnInit, OnDestroy { event.preventDefault(); } } + /** * @hidden */ @@ -176,6 +177,8 @@ export class IgxColumnMovingService { private _column: IgxColumnComponent; public cancelDrop: boolean; + public isColumnMoving: boolean; + public selection: { column: IgxColumnComponent, rowID: any @@ -256,7 +259,6 @@ export class IgxColumnMovingDragDirective extends IgxDragDirective { } public onPointerDown(event) { - if (!this.draggable || event.target.getAttribute('draggable') === 'false') { return; } @@ -270,7 +272,7 @@ export class IgxColumnMovingDragDirective extends IgxDragDirective { super.onPointerDown(event); - this.column.grid.isColumnMoving = true; + this.cms.isColumnMoving = true; this.column.grid.cdr.detectChanges(); const currSelection = this.column.grid.selection.first_item(this.column.gridID + '-cell'); @@ -296,7 +298,7 @@ export class IgxColumnMovingDragDirective extends IgxDragDirective { this.column.grid.cdr.detectChanges(); } - if (this.column.grid.isColumnMoving) { + if (this.cms.isColumnMoving) { const args = { source: this.column, cancel: false @@ -314,7 +316,7 @@ export class IgxColumnMovingDragDirective extends IgxDragDirective { this.zone.run(() => { super.onPointerUp(event); - this.column.grid.isColumnMoving = false; + this.cms.isColumnMoving = false; this.column.grid.draggedColumn = null; this.column.grid.cdr.detectChanges(); }); @@ -332,10 +334,8 @@ export class IgxColumnMovingDragDirective extends IgxDragDirective { pageY = event.touches[0].pageY; } - this._dragGhost.style.height = null; this._dragGhost.style.minWidth = null; this._dragGhost.style.flexBasis = null; - this._dragGhost.style.position = null; const icon = document.createElement('i'); const text = document.createTextNode('block'); @@ -344,22 +344,21 @@ export class IgxColumnMovingDragDirective extends IgxDragDirective { icon.classList.add('material-icons'); this.cms.icon = icon; + const removeChildIndex = this.column.grid.hasMovableColumns ? 2 : 1; if (!this.column.columnGroup) { this.renderer.addClass(icon, this._dragGhostImgIconClass); - this._dragGhost.removeChild(this._dragGhost.children[2]); - this._dragGhost.insertBefore(icon, this._dragGhost.children[1]); + this._dragGhost.children[removeChildIndex].remove(); + this._dragGhost.children[removeChildIndex - 1].insertBefore(icon, this._dragGhost.children[removeChildIndex - 1].children[0]); this.left = this._dragStartX = pageX - ((this._dragGhost.getBoundingClientRect().width / 3) * 2); this.top = this._dragStartY = pageY - ((this._dragGhost.getBoundingClientRect().height / 3) * 2); } else { - this._dragGhost.removeChild(this._dragGhost.children[2]); - this._dragGhost.removeChild(this._dragGhost.firstElementChild); - this._dragGhost.removeChild(this._dragGhost.lastElementChild); - this._dragGhost.insertBefore(icon, this._dragGhost.firstElementChild); + this._dragGhost.children[removeChildIndex].remove(); + this._dragGhost.insertBefore(icon, this._dragGhost.children[removeChildIndex - 1]); + this._dragGhost.style.display = 'flex'; this.renderer.addClass(icon, this._dragGhostImgIconGroupClass); - this._dragGhost.children[1].style.paddingLeft = '0px'; this.left = this._dragStartX = pageX - ((this._dragGhost.getBoundingClientRect().width / 3) * 2); this.top = this._dragStartY = pageY - ((this._dragGhost.getBoundingClientRect().height / 3) * 2); @@ -389,7 +388,7 @@ export class IgxColumnMovingDropDirective extends IgxDropDirective implements On } get isDropTarget(): boolean { - return this._column && this._column.grid.hasMovableColumns; + return this._column && this._column.grid.hasMovableColumns && this.cms.column.movable; } get horizontalScroll(): any { @@ -425,7 +424,8 @@ export class IgxColumnMovingDropDirective extends IgxDropDirective implements On this.renderer.removeClass(this._dropIndicator, this._dropIndicatorClass); } - const pos = this.elementRef.nativeElement.getBoundingClientRect().left + parseFloat(this.column.width) / 2; + const clientRect = this.elementRef.nativeElement.getBoundingClientRect(); + const pos = clientRect.left + clientRect.width / 2; if (event.detail.pageX < pos) { this._dropPos = DropPosition.BeforeDropTarget; @@ -530,17 +530,10 @@ export class IgxColumnMovingDropDirective extends IgxDropDirective implements On this.column.grid.moveColumn(this.cms.column, this.column, this._dropPos); if (this.cms.selection && this.cms.selection.column) { - const colID = this.column.grid.columnList.toArray().indexOf(this.cms.selection.column); - - this.column.grid.selection.set(this.column.gridID + '-cell', new Set([{ - rowID: this.cms.selection.rowID, - columnID: colID - }])); - const cell = this.column.grid.getCellByKey(this.cms.selection.rowID, this.cms.selection.column.field); if (cell) { - cell.nativeElement.focus(); + cell._updateCellSelectionStatus(true, event); } this.cms.selection = null; diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid.component.html b/projects/igniteui-angular/src/lib/grids/grid/grid.component.html index d06fb0ebdde..cc00db56177 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid/grid.component.html @@ -40,7 +40,7 @@
- +
@@ -54,22 +54,12 @@ -
- - -
+
-
- - -
+
diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid.component.ts b/projects/igniteui-angular/src/lib/grids/grid/grid.component.ts index 04bd26c3396..70dfaa27863 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid.component.ts @@ -24,6 +24,7 @@ import { IgxColumnComponent } from '../column.component'; import { takeUntil } from 'rxjs/operators'; import { IgxFilteringService } from '../filtering/grid-filtering.service'; import { IGroupingExpression } from '../../data-operations/grouping-expression.interface'; +import { IgxColumnResizingService } from '../grid-column-resizing.service'; let NEXT_ID = 0; @@ -58,7 +59,7 @@ export interface IGroupingDoneEventArgs { providers: [IgxGridNavigationService, { provide: GridBaseAPIService, useClass: IgxGridAPIService }, { provide: IgxGridBaseComponent, useExisting: forwardRef(() => IgxGridComponent) }, - IgxFilteringService + IgxFilteringService, IgxColumnResizingService ], selector: 'igx-grid', templateUrl: './grid.component.html' diff --git a/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid.component.html b/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid.component.html index 34569aa7232..47e17761a81 100644 --- a/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid.component.html +++ b/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid.component.html @@ -22,7 +22,7 @@
- +
@@ -31,22 +31,12 @@ -
- - -
+
-
- - -
+
@@ -56,10 +46,10 @@
- - + @@ -119,7 +109,7 @@
-
+
diff --git a/src/app/app.component.ts b/src/app/app.component.ts index ceabe9129be..6187ef164c1 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -148,6 +148,11 @@ export class AppComponent implements OnInit { icon: 'view_column', name: 'Grid Performance' }, + { + link: '/gridPercentage', + icon: 'view_column', + name: 'Grid Percentage' + }, { link: '/gridRemoteVirtualization', icon: 'view_column', diff --git a/src/app/app.module.ts b/src/app/app.module.ts index 83ad99ef0bf..03e8c838052 100644 --- a/src/app/app.module.ts +++ b/src/app/app.module.ts @@ -74,6 +74,7 @@ import { GridRowEditSampleComponent } from './grid-row-edit/grid-row-edit-sample import { GridWithTransactionsComponent } from './grid-row-edit/grid-with-transactions.component'; import { TreeGridSampleComponent } from './tree-grid/tree-grid.sample'; import { TreeGridFlatDataSampleComponent } from './tree-grid-flat-data/tree-grid-flat-data.sample'; +import { GridColumnPercentageWidthsSampleComponent } from './grid-percentage-columns/grid-percantge-widths.sample'; const components = [ AppComponent, @@ -136,7 +137,8 @@ const components = [ ShadowsSampleComponent, TypographySampleComponent, RadioSampleComponent, - TooltipSampleComponent + TooltipSampleComponent, + GridColumnPercentageWidthsSampleComponent ]; @NgModule({ diff --git a/src/app/app.routing.ts b/src/app/app.routing.ts index df53f775f7d..289d4d62d0c 100644 --- a/src/app/app.routing.ts +++ b/src/app/app.routing.ts @@ -44,6 +44,7 @@ import { GridCellStylingSampleComponent } from './gird-cell-styling/grid-cell-st import { GridRowEditSampleComponent } from './grid-row-edit/grid-row-edit-sample.component'; import { TreeGridSampleComponent } from './tree-grid/tree-grid.sample'; import { TreeGridFlatDataSampleComponent } from './tree-grid-flat-data/tree-grid-flat-data.sample'; +import { GridColumnPercentageWidthsSampleComponent } from './grid-percentage-columns/grid-percantge-widths.sample'; const appRoutes = [ { @@ -231,6 +232,10 @@ const appRoutes = [ { path: 'tooltip', component: TooltipSampleComponent + }, + { + path: 'gridPercentage', + component: GridColumnPercentageWidthsSampleComponent } ]; diff --git a/src/app/grid-column-groups/grid-column-groups.sample.html b/src/app/grid-column-groups/grid-column-groups.sample.html index 02ef5c55a71..06dc63c6630 100644 --- a/src/app/grid-column-groups/grid-column-groups.sample.html +++ b/src/app/grid-column-groups/grid-column-groups.sample.html @@ -61,7 +61,6 @@ - Pin first group Hide first group diff --git a/src/app/grid-column-moving/grid-column-moving.sample.html b/src/app/grid-column-moving/grid-column-moving.sample.html index 2bba6311a56..2b1ce8971cc 100644 --- a/src/app/grid-column-moving/grid-column-moving.sample.html +++ b/src/app/grid-column-moving/grid-column-moving.sample.html @@ -15,8 +15,7 @@ [rowSelectable]="true" [paging]="false" [width]="'900px'" - [height]="'500px'" - > + [height]="'500px'"> + + Grid with column widths in % + +
+
+ + + + + + + + {{val | date:'dd/MM/yyyy'}} + + + + + + + + + + +
+
+ + + +
+ + + + + + + + {{+val | currency}} + + + + + + + Continued + Discontinued + + + +
+
diff --git a/src/app/grid-percentage-columns/grid-percantge-widths.sample.ts b/src/app/grid-percentage-columns/grid-percantge-widths.sample.ts new file mode 100644 index 00000000000..25f407c603f --- /dev/null +++ b/src/app/grid-percentage-columns/grid-percantge-widths.sample.ts @@ -0,0 +1,453 @@ +import { Component, OnInit, ViewChild } from '@angular/core'; +import { IgxGridComponent, IgxStringFilteringOperand } from 'igniteui-angular'; + @Component({ + providers: [], + selector: 'ap-grid-percantge-widths.sample', + templateUrl: 'grid-percantge-widths.sample.html' +}) + export class GridColumnPercentageWidthsSampleComponent implements OnInit { + public data: Array; + public data1: Array; + + @ViewChild("grid1", { read: IgxGridComponent }) + public grid1: IgxGridComponent; + + public ngOnInit(): void { + this.data1 = [{ + ProductID: 1, + ProductName: "Chai", + SupplierID: 1, + CategoryID: 1, + QuantityPerUnit: "10 boxes x 20 bags", + UnitPrice: 18.0000, + UnitsInStock: 39, + UnitsOnOrder: 0, + ReorderLevel: 10, + Discontinued: false, + OrderDate: new Date("2012-02-12") + }, { + ProductID: 2, + ProductName: "Chang", + SupplierID: 1, + CategoryID: 1, + QuantityPerUnit: "24 - 12 oz bottles", + UnitPrice: 19.0000, + UnitsInStock: 17, + UnitsOnOrder: 40, + ReorderLevel: 25, + Discontinued: false, + OrderDate: new Date("2003-03-17") + }, { + ProductID: 3, + ProductName: "Aniseed Syrup", + SupplierID: 1, + CategoryID: 2, + QuantityPerUnit: "12 - 550 ml bottles", + UnitPrice: 10.0000, + UnitsInStock: 13, + UnitsOnOrder: 70, + ReorderLevel: 25, + Discontinued: false, + OrderDate: new Date("2006-03-17") + }, { + ProductID: 4, + ProductName: "Chef Antons Cajun Seasoning", + SupplierID: 2, + CategoryID: 2, + QuantityPerUnit: "48 - 6 oz jars", + UnitPrice: 22.0000, + UnitsInStock: 53, + UnitsOnOrder: 0, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2016-03-17") + }, { + ProductID: 5, + ProductName: "Chef Antons Gumbo Mix", + SupplierID: 2, + CategoryID: 2, + QuantityPerUnit: "36 boxes", + UnitPrice: 21.3500, + UnitsInStock: 0, + UnitsOnOrder: 0, + ReorderLevel: 0, + Discontinued: true, + OrderDate: new Date("2011-11-11") + }, { + ProductID: 6, + ProductName: "Grandmas Boysenberry Spread", + SupplierID: 3, + CategoryID: 2, + QuantityPerUnit: "12 - 8 oz jars", + UnitPrice: 25.0000, + UnitsInStock: 0, + UnitsOnOrder: 0, + ReorderLevel: 25, + Discontinued: false, + OrderDate: new Date("2017-12-17") + }, { + ProductID: 7, + ProductName: "Uncle Bobs Organic Dried Pears", + SupplierID: 3, + CategoryID: 7, + QuantityPerUnit: "12 - 1 lb pkgs.", + UnitPrice: 30.0000, + UnitsInStock: 150, + UnitsOnOrder: 0, + ReorderLevel: 10, + Discontinued: false, + OrderDate: new Date("2016-07-17") + }, { + ProductID: 8, + ProductName: "Northwoods Cranberry Sauce", + SupplierID: 3, + CategoryID: 2, + QuantityPerUnit: "12 - 12 oz jars", + UnitPrice: 40.0000, + UnitsInStock: 6, + UnitsOnOrder: 0, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2018-01-17") + }, { + ProductID: 9, + ProductName: "Mishi Kobe Niku", + SupplierID: 4, + CategoryID: 6, + QuantityPerUnit: "18 - 500 g pkgs.", + UnitPrice: 97.0000, + UnitsInStock: 29, + UnitsOnOrder: 0, + ReorderLevel: 0, + Discontinued: true, + OrderDate: new Date("2010-02-17") + }, { + ProductID: 10, + ProductName: "Ikura", + SupplierID: 4, + CategoryID: 8, + QuantityPerUnit: "12 - 200 ml jars", + UnitPrice: 31.0000, + UnitsInStock: 31, + UnitsOnOrder: 0, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2008-05-17") + }, { + ProductID: 11, + ProductName: "Queso Cabrales", + SupplierID: 5, + CategoryID: 4, + QuantityPerUnit: "1 kg pkg.", + UnitPrice: 21.0000, + UnitsInStock: 22, + UnitsOnOrder: 30, + ReorderLevel: 30, + Discontinued: false, + OrderDate: new Date("2009-01-17") + }, { + ProductID: 12, + ProductName: "Queso Manchego La Pastora", + SupplierID: 5, + CategoryID: 4, + QuantityPerUnit: "10 - 500 g pkgs.", + UnitPrice: 38.0000, + UnitsInStock: 86, + UnitsOnOrder: 0, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2015-11-17") + }, { + ProductID: 13, + ProductName: "Konbu", + SupplierID: 6, + CategoryID: 8, + QuantityPerUnit: "2 kg box", + UnitPrice: 6.0000, + UnitsInStock: 24, + UnitsOnOrder: 0, + ReorderLevel: 5, + Discontinued: false, + OrderDate: new Date("2015-03-17") + }, { + ProductID: 14, + ProductName: "Tofu", + SupplierID: 6, + CategoryID: 7, + QuantityPerUnit: "40 - 100 g pkgs.", + UnitPrice: 23.2500, + UnitsInStock: 35, + UnitsOnOrder: 0, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2017-06-17") + }, { + ProductID: 15, + ProductName: "Genen Shouyu", + SupplierID: 6, + CategoryID: 2, + QuantityPerUnit: "24 - 250 ml bottles", + UnitPrice: 15.5000, + UnitsInStock: 39, + UnitsOnOrder: 0, + ReorderLevel: 5, + Discontinued: false, + OrderDate: new Date("2014-03-17") + }, { + ProductID: 16, + ProductName: "Pavlova", + SupplierID: 7, + CategoryID: 3, + QuantityPerUnit: "32 - 500 g boxes", + UnitPrice: 17.4500, + UnitsInStock: 29, + UnitsOnOrder: 0, + ReorderLevel: 10, + Discontinued: false, + OrderDate: new Date("2018-03-28") + }, { + ProductID: 17, + ProductName: "Alice Mutton", + SupplierID: 7, + CategoryID: 6, + QuantityPerUnit: "20 - 1 kg tins", + UnitPrice: 39.0000, + UnitsInStock: 0, + UnitsOnOrder: 0, + ReorderLevel: 0, + Discontinued: true, + OrderDate: new Date("2015-08-17") + }, { + ProductID: 18, + ProductName: "Carnarvon Tigers", + SupplierID: 7, + CategoryID: 8, + QuantityPerUnit: "16 kg pkg.", + UnitPrice: 62.5000, + UnitsInStock: 42, + UnitsOnOrder: 0, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2005-09-27") + }, { + ProductID: 19, + ProductName: "Teatime Chocolate Biscuits", + SupplierID: 8, + CategoryID: 3, + QuantityPerUnit: "", + UnitPrice: 9.2000, + UnitsInStock: 25, + UnitsOnOrder: 0, + ReorderLevel: 5, + Discontinued: false, + OrderDate: new Date("2001-03-17") + }, { + ProductID: 20, + ProductName: "Sir Rodneys Marmalade", + SupplierID: 8, + CategoryID: 3, + QuantityPerUnit: undefined, + UnitPrice: undefined, + UnitsInStock: 40, + UnitsOnOrder: 0, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2005-03-17") + }]; + + this.data = [{ + ProductID: 1, + ProductName: "Chai", + QuantityPerUnit: "10 boxes x 20 bags", + UnitPrice: 18.0000, + UnitsInStock: 39, + ReorderLevel: 10, + Discontinued: false, + OrderDate: new Date("2012-02-12") + }, { + ProductID: 2, + ProductName: "Chang", + QuantityPerUnit: "24 - 12 oz bottles", + UnitPrice: 19.0000, + UnitsInStock: 17, + ReorderLevel: 25, + Discontinued: false, + OrderDate: new Date("2003-03-17") + }, { + ProductID: 3, + ProductName: "Aniseed Syrup", + QuantityPerUnit: "12 - 550 ml bottles", + UnitPrice: 10.0000, + UnitsInStock: 13, + ReorderLevel: 25, + Discontinued: false, + OrderDate: new Date("2006-03-17") + }, { + ProductID: 4, + ProductName: "Chef Antons Cajun Seasoning", + QuantityPerUnit: "48 - 6 oz jars", + UnitPrice: 22.0000, + UnitsInStock: 53, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2016-03-17") + }, { + ProductID: 5, + ProductName: "Chef Antons Gumbo Mix", + QuantityPerUnit: "36 boxes", + UnitPrice: 21.3500, + UnitsInStock: 0, + ReorderLevel: 0, + Discontinued: true, + OrderDate: new Date("2011-11-11") + }, { + ProductID: 6, + ProductName: "Grandmas Boysenberry Spread", + QuantityPerUnit: "12 - 8 oz jars", + UnitPrice: 25.0000, + UnitsInStock: 0, + ReorderLevel: 25, + Discontinued: false, + OrderDate: new Date("2017-12-17") + }, { + ProductID: 7, + ProductName: "Uncle Bobs Organic Dried Pears", + QuantityPerUnit: "12 - 1 lb pkgs.", + UnitPrice: 30.0000, + UnitsInStock: 150, + ReorderLevel: 10, + Discontinued: false, + OrderDate: new Date("2016-07-17") + }, { + ProductID: 8, + ProductName: "Northwoods Cranberry Sauce", + QuantityPerUnit: "12 - 12 oz jars", + UnitPrice: 40.0000, + UnitsInStock: 6, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2018-01-17") + }, { + ProductID: 9, + ProductName: "Mishi Kobe Niku", + QuantityPerUnit: "18 - 500 g pkgs.", + UnitPrice: 97.0000, + UnitsInStock: 29, + ReorderLevel: 0, + Discontinued: true, + OrderDate: new Date("2010-02-17") + }, { + ProductID: 10, + ProductName: "Ikura", + QuantityPerUnit: "12 - 200 ml jars", + UnitPrice: 31.0000, + UnitsInStock: 31, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2008-05-17") + }, { + ProductID: 11, + ProductName: "Queso Cabrales", + QuantityPerUnit: "1 kg pkg.", + UnitPrice: 21.0000, + UnitsInStock: 22, + ReorderLevel: 30, + Discontinued: false, + OrderDate: new Date("2009-01-17") + }, { + ProductID: 12, + ProductName: "Queso Manchego La Pastora", + QuantityPerUnit: "10 - 500 g pkgs.", + UnitPrice: 38.0000, + UnitsInStock: 86, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2015-11-17") + }, { + ProductID: 13, + ProductName: "Konbu", + QuantityPerUnit: "2 kg box", + UnitPrice: 6.0000, + UnitsInStock: 24, + ReorderLevel: 5, + Discontinued: false, + OrderDate: new Date("2015-03-17") + }, { + ProductID: 14, + ProductName: "Tofu", + QuantityPerUnit: "40 - 100 g pkgs.", + UnitPrice: 23.2500, + UnitsInStock: 35, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2017-06-17") + }, { + ProductID: 15, + ProductName: "Genen Shouyu", + QuantityPerUnit: "24 - 250 ml bottles", + UnitPrice: 15.5000, + UnitsInStock: 39, + ReorderLevel: 5, + Discontinued: false, + OrderDate: new Date("2014-03-17") + }, { + ProductID: 16, + ProductName: "Pavlova", + QuantityPerUnit: "32 - 500 g boxes", + UnitPrice: 17.4500, + UnitsInStock: 29, + ReorderLevel: 10, + Discontinued: false, + OrderDate: new Date("2018-03-28") + }, { + ProductID: 17, + ProductName: "Alice Mutton", + QuantityPerUnit: "20 - 1 kg tins", + UnitPrice: 39.0000, + UnitsInStock: 0, + ReorderLevel: 0, + Discontinued: true, + OrderDate: new Date("2015-08-17") + }, { + ProductID: 18, + ProductName: "Carnarvon Tigers", + QuantityPerUnit: "16 kg pkg.", + UnitPrice: 62.5000, + UnitsInStock: 42, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2005-09-27") + }, { + ProductID: 19, + ProductName: "Teatime Chocolate Biscuits", + QuantityPerUnit: "", + UnitPrice: 9.2000, + UnitsInStock: 25, + ReorderLevel: 5, + Discontinued: false, + OrderDate: new Date("2001-03-17") + }, { + ProductID: 20, + ProductName: "Sir Rodneys Marmalade", + QuantityPerUnit: undefined, + UnitPrice: undefined, + UnitsInStock: 40, + ReorderLevel: 0, + Discontinued: false, + OrderDate: new Date("2005-03-17") + }]; + } + + + public formatDate(val: Date) { + return new Intl.DateTimeFormat("en-US").format(val); + } + + public formatCurrency(val: string) { + return parseInt(val, 10).toFixed(2); + } + + public filter(term) { + this.grid1.filter("ProductName", term, IgxStringFilteringOperand.instance().condition("contains")); + } +} diff --git a/src/app/routing.ts b/src/app/routing.ts index f3f556b5a9b..877acb27715 100644 --- a/src/app/routing.ts +++ b/src/app/routing.ts @@ -55,6 +55,7 @@ import { GridCellStylingSampleComponent } from './gird-cell-styling/grid-cell-st import { GridRowEditSampleComponent } from './grid-row-edit/grid-row-edit-sample.component'; import { TreeGridSampleComponent } from './tree-grid/tree-grid.sample'; import { TreeGridFlatDataSampleComponent } from './tree-grid-flat-data/tree-grid-flat-data.sample'; +import { GridColumnPercentageWidthsSampleComponent } from './grid-percentage-columns/grid-percantge-widths.sample'; const appRoutes = [ { @@ -286,6 +287,10 @@ const appRoutes = [ { path: 'tooltip', component: TooltipSampleComponent + }, + { + path: 'gridPercentage', + component: GridColumnPercentageWidthsSampleComponent } ]; From 7c2c66a95a327cdc3fc56523ba9478bb3ea87981 Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Tue, 6 Nov 2018 18:40:41 +0200 Subject: [PATCH 02/24] feat(filtering): header group component POC #542 # Conflicts: # projects/igniteui-angular/src/lib/grids/column.component.ts # projects/igniteui-angular/src/lib/grids/grid-base.component.ts # projects/igniteui-angular/src/lib/grids/grid-header-group.component.html # projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts # projects/igniteui-angular/src/lib/grids/grid/grid.component.html # projects/igniteui-angular/src/lib/grids/grid/grid.component.ts # projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid.component.html --- .../src/lib/grids/grid-header-group.component.html | 12 ++---------- .../src/lib/grids/grid-header-group.component.ts | 5 +++++ .../src/lib/grids/grid-header.component.ts | 13 ------------- .../src/lib/grids/grid/grid.component.html | 2 +- .../lib/grids/tree-grid/tree-grid.component.html | 2 +- 5 files changed, 9 insertions(+), 25 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html index 4be9386561e..b6f292a101a 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html @@ -11,14 +11,8 @@ - - - - - - - - + + @@ -33,5 +27,3 @@ - - diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts index 9867865b2e8..9cc6ba3dbff 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts @@ -67,6 +67,7 @@ export class IgxGridHeaderGroupComponent { ]; const classList = { + 'igx-grid__th--pinned': this.isPinned, 'igx-grid__th--pinned-last': this.isLastPinned, 'igx-grid__drag-col-header': this.isHeaderDragged }; @@ -100,6 +101,10 @@ export class IgxGridHeaderGroupComponent { } } + get isPinned() { + return this.column.pinned; + } + get isHeaderDragged() { return this.grid.draggedColumn === this.column; } diff --git a/projects/igniteui-angular/src/lib/grids/grid-header.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header.component.ts index f76de1704cd..99843322f66 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header.component.ts @@ -156,19 +156,6 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck { return this.gridAPI.get(this.gridID); } - get isPinned() { - return this.column.pinned; - } - - get isLastPinned() { - const pinnedCols = this.grid.pinnedColumns; - if (pinnedCols.length === 0) { - return false; - } else { - return pinnedCols.indexOf(this.column) === pinnedCols.length - 1; - } - } - protected getSortDirection() { const expr = this.gridAPI.get(this.gridID).sortingExpressions.find((x) => x.fieldName === this.column.field); this.sortDirection = expr ? expr.dir : SortingDirection.None; diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid.component.html b/projects/igniteui-angular/src/lib/grids/grid/grid.component.html index cc00db56177..da8c65258cf 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid/grid.component.html @@ -54,7 +54,7 @@ - + - + Date: Mon, 12 Nov 2018 22:49:25 +0200 Subject: [PATCH 03/24] feat(filtering): some MCH related improvements #542 --- .../src/lib/grids/column.component.ts | 2 +- .../lib/grids/grid-header-group.component.html | 4 ++-- .../lib/grids/grid-header-group.component.ts | 18 +++++++++++++----- 3 files changed, 16 insertions(+), 8 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/column.component.ts b/projects/igniteui-angular/src/lib/grids/column.component.ts index 3500bc87204..5640e6a1527 100644 --- a/projects/igniteui-angular/src/lib/grids/column.component.ts +++ b/projects/igniteui-angular/src/lib/grids/column.component.ts @@ -1077,7 +1077,7 @@ export class IgxColumnComponent implements AfterContentInit { * ``` * @memberof IgxColumnComponent */ - get filterell(): IgxGridFilteringCellComponent { + get filterCell(): IgxGridFilteringCellComponent { return this.grid.filterCellList.find((filterCell) => filterCell.column === this); } diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html index b6f292a101a..ccfd3a9d00c 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html @@ -1,6 +1,6 @@ -
{{ column.header }}
+
{{ column.header }}
@@ -12,7 +12,7 @@ - + diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts index 9cc6ba3dbff..a9b767d979a 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts @@ -109,11 +109,19 @@ export class IgxGridHeaderGroupComponent { return this.grid.draggedColumn === this.column; } - constructor( - public cdr: ChangeDetectorRef, - public gridAPI: GridBaseAPIService, - public colReszingService: IgxColumnResizingService, - public filteringService: IgxFilteringService) { } + get hasLastPinnedChildColumn(): boolean { + const pinnedCols = this.grid.pinnedColumns; + if (this.column.allChildren) { + return this.column.allChildren.some((child) => { + return pinnedCols.length > 0 && pinnedCols.indexOf(child) === pinnedCols.length - 1; + }); + } + + } + + constructor(public gridAPI: GridBaseAPIService, + public colReszingService: IgxColumnResizingService, + public filteringService: IgxFilteringService) { } public onResizeAreaMouseOver() { if (this.column.resizable) { From c1298b0811799c1f0d48b2b41ebd960251c20244 Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Tue, 13 Nov 2018 11:32:16 +0200 Subject: [PATCH 04/24] feat(filtering): fix some minor issues #542 --- .../src/lib/grids/grid-header-group.component.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html index ccfd3a9d00c..56f49bcd2c4 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html @@ -12,7 +12,7 @@ - + From 419561a309650642d7455b3d240b587d70dc0977 Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Wed, 14 Nov 2018 10:34:28 +0200 Subject: [PATCH 05/24] test(*): start fixing failing tests for MCH #542 --- .../src/lib/grids/grid/column-group.spec.ts | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid/column-group.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/column-group.spec.ts index d131d7a4cac..c43efa1eb02 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/column-group.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/column-group.spec.ts @@ -67,7 +67,8 @@ describe('IgxGrid - multi-column headers', () => { addressGroup.hidden = true; tick(); - expect(document.querySelectorAll('igx-grid-header').length).toEqual(6); + expect(document.querySelectorAll('igx-grid-header').length).toEqual(4); + expect(document.querySelectorAll('igx-grid-header-group').length).toEqual(6); })); it('column hiding - child level', fakeAsync(() => { @@ -80,7 +81,7 @@ describe('IgxGrid - multi-column headers', () => { addressGroup.children.first.hidden = true; tick(); - expect(document.querySelectorAll('igx-grid-header').length).toEqual(5); + expect(document.querySelectorAll('igx-grid-header-group').length).toEqual(5); expect(addressGroup.children.first.hidden).toBe(true); expect(addressGroup.children.first.children.toArray().every(c => c.hidden === true)).toEqual(true); })); @@ -101,7 +102,7 @@ describe('IgxGrid - multi-column headers', () => { // Hide column in goup grid.getColumnByName('CompanyName').hidden = true; tick(); - expect(document.querySelectorAll('igx-grid-header').length).toEqual(16); + expect(document.querySelectorAll('igx-grid-header-group').length).toEqual(16); expect(fixture.debugElement.queryAll(By.css(GRID_COL_THEAD_CLASS)).length).toEqual(9); grid.getColumnByName('Address').hidden = true; @@ -2069,7 +2070,7 @@ function testColumnsVisibleIndexes(columns: IgxColumnComponent[]) { } function testGroupsAndColumns(groups: number, columns: number) { - expect(document.querySelectorAll('igx-grid-header').length).toEqual(groups); + expect(document.querySelectorAll('igx-grid-header-group').length).toEqual(groups); expect(document.querySelectorAll(GRID_COL_THEAD_CLASS).length).toEqual(columns); } From 1b1acf87595bc55d84e672a2a90920c942d20271 Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Wed, 14 Nov 2018 12:21:09 +0200 Subject: [PATCH 06/24] feat(filtering): fix build error #542 --- .../igniteui-angular/src/lib/grids/grid-navigation.service.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts b/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts index 07641cbcd14..67ce96fd2f4 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts @@ -419,7 +419,7 @@ export class IgxGridNavigationService { this.grid.rowList.find(row => row instanceof IgxGridRowComponent).cells.first._clearCellSelection(); const visColLength = this.grid.unpinnedColumns.length; if (this.isColumnFullyVisible(visColLength - 1)) { - this.grid.filteringService.focusFilterCellChip(this.grid.filterCellList.last.column.field, false); + this.grid.filteringService.focusFilterCellChip(this.grid.filterCellList[this.grid.filterCellList.length-1].column.field, false); } else { this.grid.filteringService.columnToFocus = this.grid.unpinnedColumns[visColLength - 1]; this.grid.filteringService.shouldFocusNext = false; From 3e47a1aa457fb9b3d488a54127e14e4fb5cb69f6 Mon Sep 17 00:00:00 2001 From: Borislav Kulov Date: Fri, 9 Nov 2018 19:00:31 +0200 Subject: [PATCH 07/24] chore(filtering): Small refactoring (#2938) --- .../grid-filtering-cell.component.html | 5 ++- .../grid-filtering-cell.component.ts | 41 ++++++++++--------- .../filtering/grid-filtering-row.component.ts | 9 ++-- .../grids/filtering/grid-filtering.service.ts | 23 ++++++----- .../src/lib/grids/grid-base.component.ts | 2 +- .../src/lib/grids/grid-navigation.service.ts | 3 +- 6 files changed, 43 insertions(+), 40 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.html b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.html index c7bfec3f9d9..aade63cb526 100644 --- a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.html +++ b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.html @@ -9,8 +9,9 @@ - + - {{filteringService.getOperatorAsString(item.afterOperator)}} + {{filteringService.getOperatorAsString(item.afterOperator)}}
filter_list diff --git a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts index 2034d223a4b..506073ba23b 100644 --- a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts +++ b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts @@ -12,10 +12,9 @@ import { } from '@angular/core'; import { IgxColumnComponent } from '../column.component'; import { IFilteringExpression } from '../../data-operations/filtering-expression.interface'; -import { FilteringExpressionsTree } from '../../data-operations/filtering-expressions-tree'; import { IBaseChipEventArgs, IgxChipsAreaComponent, IgxChipComponent } from '../../chips'; import { IgxFilteringService, ExpressionUI } from './grid-filtering.service'; -import { KEYS, cloneArray } from '../../core/utils'; +import { KEYS } from '../../core/utils'; import { IgxGridNavigationService } from '../grid-navigation.service'; import { IgxGridGroupByRowComponent } from '../grid'; @@ -29,12 +28,10 @@ import { IgxGridGroupByRowComponent } from '../grid'; }) export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit { - private rootExpressionsTree: FilteringExpressionsTree; - private expressionsList: ExpressionUI[]; private baseClass = 'igx-grid__filtering-cell-indicator'; private currentTemplate = null; - public visibleExpressionsList: ExpressionUI[]; + public expressionsList: ExpressionUI[]; public moreFiltersCount = 0; @Input() @@ -89,6 +86,7 @@ export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit { eventArgs.stopPropagation(); return; } + if (this.column.visibleIndex === this.filteringService.grid.columnList.length - 1) { if (!this.filteringService.grid.filteredData || this.filteringService.grid.filteredData.length > 0) { if (this.filteringService.grid.rowList.filter(row => row instanceof IgxGridGroupByRowComponent).length > 0) { @@ -109,10 +107,9 @@ export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit { @HostListener('keydown.shift.tab', ['$event']) public onShiftTabKeyDown(eventArgs) { if (this.isFirstElementFocused()) { - const prevIndex = this.column.visibleIndex - 1 - this.filteringService.grid.pinnedColumns.length; - if (this.column.visibleIndex > 0 && !this.navService.isColumnLeftFullyVisible(this.column.visibleIndex - 1)) { eventArgs.preventDefault(); + const prevIndex = this.column.visibleIndex - 1 - this.filteringService.grid.pinnedColumns.length; this.ScrollToChip(prevIndex, false); } else if (this.column.visibleIndex === 0) { eventArgs.preventDefault(); @@ -121,6 +118,14 @@ export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit { eventArgs.stopPropagation(); } + /** + * Returns whether a chip with a given index is visible or not. + */ + public isChipVisible(index: number) { + const expression = this.expressionsList[index]; + return !!(expression && expression.isVisible); + } + /** * Updates the filtering cell area. */ @@ -233,13 +238,7 @@ export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit { this.filteringService.removeExpression(this.column.field, indexToRemove); this.updateVisibleFilters(); - this.filter(); - } - - private filter(): void { - this.rootExpressionsTree = this.filteringService.createSimpleFilteringTree(this.column.field); - - this.filteringService.filter(this.column.field, this.rootExpressionsTree); + this.filteringService.filter(this.column.field); } private isMoreIconHidden(): boolean { @@ -247,21 +246,20 @@ export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit { } private updateVisibleFilters() { - this.visibleExpressionsList = cloneArray(this.expressionsList); - - // TODO: revise the usage of this.cdr.detectChanges() here - this.cdr.detectChanges(); + this.expressionsList.forEach((ex) => ex.isVisible = true); if (this.moreIcon) { this.filteringService.columnToMoreIconHidden.set(this.column.field, true); } + this.cdr.detectChanges(); + if (this.chipsArea && this.expressionsList.length > 1) { const areaWidth = this.chipsArea.element.nativeElement.offsetWidth; let viewWidth = 0; const chipsAreaElements = this.chipsArea.element.nativeElement.children; let visibleChipsCount = 0; const moreIconWidth = this.moreIcon.nativeElement.offsetWidth - - parseInt(document.defaultView.getComputedStyle(this.moreIcon.nativeElement)['margin-left'], 10); + parseInt(document.defaultView.getComputedStyle(this.moreIcon.nativeElement)['margin-left'], 10); for (let index = 0; index < chipsAreaElements.length - 1; index++) { if (viewWidth + chipsAreaElements[index].offsetWidth < areaWidth) { @@ -280,10 +278,13 @@ export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit { } this.moreFiltersCount = this.expressionsList.length - visibleChipsCount; this.filteringService.columnToMoreIconHidden.set(this.column.field, false); - this.visibleExpressionsList.splice(visibleChipsCount); break; } } + + for (let i = visibleChipsCount; i < this.expressionsList.length; i++) { + this.expressionsList[i].isVisible = false; + } this.cdr.detectChanges(); } } diff --git a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-row.component.ts b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-row.component.ts index 612abfd9e26..508ad04c055 100644 --- a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-row.component.ts +++ b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-row.component.ts @@ -57,7 +57,6 @@ export class IgxGridFilteringRowComponent implements AfterViewInit, OnDestroy { positionStrategy: new ConnectedPositioningStrategy(this._positionSettings) }; - private rootExpressionsTree: FilteringExpressionsTree; private chipsAreaWidth: number; private chipAreaScrollOffset = 0; private conditionChanged = new Subject(); @@ -352,8 +351,8 @@ export class IgxGridFilteringRowComponent implements AfterViewInit, OnDestroy { }); } - this.filteringService.updateFilteringCell(this.column.field); - this.filteringService.focusFilterCellChip(this.column.field, true); + this.filteringService.updateFilteringCell(this.column); + this.filteringService.focusFilterCellChip(this.column, true); this.filteringService.isFilterRowVisible = false; this.filteringService.filteredColumn = null; @@ -641,8 +640,6 @@ export class IgxGridFilteringRowComponent implements AfterViewInit, OnDestroy { } private filter() { - this.rootExpressionsTree = this.filteringService.createSimpleFilteringTree(this.column.field); - - this.filteringService.filter(this.column.field, this.rootExpressionsTree); + this.filteringService.filter(this.column.field); } } diff --git a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering.service.ts b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering.service.ts index 31c5327ef04..26b93422719 100644 --- a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering.service.ts +++ b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering.service.ts @@ -10,6 +10,7 @@ import { takeUntil } from 'rxjs/operators'; import { IForOfState } from '../../directives/for-of/for_of.directive'; import { IgxGridFilterConditionPipe } from '../grid-common.pipes'; import { TitleCasePipe, DatePipe } from '@angular/common'; +import { IgxColumnComponent } from '../grid'; const FILTERING_ICONS_FONT_SET = 'filtering-icons'; @@ -21,6 +22,7 @@ export class ExpressionUI { public beforeOperator: FilteringLogic; public afterOperator: FilteringLogic; public isSelected = false; + public isVisible = true; } /** @@ -41,9 +43,9 @@ export class IgxFilteringService implements OnDestroy { public gridId: string; public isFilterRowVisible = false; - public filteredColumn = null; + public filteredColumn: IgxColumnComponent = null; public selectedExpression: IFilteringExpression = null; - public columnToFocus = null; + public columnToFocus: IgxColumnComponent = null; public shouldFocusNext = false; public columnToMoreIconHidden = new Map(); @@ -66,7 +68,7 @@ export class IgxFilteringService implements OnDestroy { this.areEventsSubscribed = true; this.grid.onColumnResized.pipe(takeUntil(this.destroy$)).subscribe((eventArgs: IColumnResizeEventArgs) => { - this.updateFilteringCell(eventArgs.column.field); + this.updateFilteringCell(eventArgs.column); }); this.grid.parentVirtDir.onChunkLoad.pipe(takeUntil(this.destroy$)).subscribe((eventArgs: IForOfState) => { @@ -77,7 +79,7 @@ export class IgxFilteringService implements OnDestroy { }); } if (this.columnToFocus) { - this.focusFilterCellChip(this.columnToFocus.field, false); + this.focusFilterCellChip(this.columnToFocus, false); this.columnToFocus = null; } }); @@ -93,9 +95,10 @@ export class IgxFilteringService implements OnDestroy { /** * Execute filtering on the grid. */ - public filter(field: string, expressionsTree: FilteringExpressionsTree): void { + public filter(field: string): void { this.isFiltering = true; + const expressionsTree = this.createSimpleFilteringTree(field); this.grid.filter(field, null, expressionsTree); // Wait for the change detection to update filtered data through the pipes and then emit the event. @@ -169,7 +172,7 @@ export class IgxFilteringService implements OnDestroy { this.columnsWithComplexFilter.add(key); } - this.updateFilteringCell(key); + this.updateFilteringCell(column); }); } } @@ -272,8 +275,8 @@ export class IgxFilteringService implements OnDestroy { /** * Updates the content of a filterCell. */ - public updateFilteringCell(columnId: string) { - const filterCell = this.grid.filterCellList.find(cell => cell.column.field === columnId); + public updateFilteringCell(column: IgxColumnComponent) { + const filterCell = column.filterCell; if (filterCell) { filterCell.updateFilterCellArea(); } @@ -282,8 +285,8 @@ export class IgxFilteringService implements OnDestroy { /** * Focus a chip in a filterCell. */ - public focusFilterCellChip(columnId: string, focusFirst: boolean) { - const filterCell = this.grid.filterCellList.find(cell => cell.column.field === columnId); + public focusFilterCellChip(column: IgxColumnComponent, focusFirst: boolean) { + const filterCell = column.filterCell; if (filterCell) { filterCell.focusChip(focusFirst); } diff --git a/projects/igniteui-angular/src/lib/grids/grid-base.component.ts b/projects/igniteui-angular/src/lib/grids/grid-base.component.ts index ff31a402efb..c10102ccb82 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-base.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-base.component.ts @@ -243,7 +243,7 @@ export abstract class IgxGridBaseComponent extends DisplayDensityBase implements this.filteringService.refreshExpressions(); this.clearSummaryCache(); - this.cdr.markForCheck(); + this.markForCheck(); } } diff --git a/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts b/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts index 67ce96fd2f4..c678b8a7fea 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts @@ -419,7 +419,8 @@ export class IgxGridNavigationService { this.grid.rowList.find(row => row instanceof IgxGridRowComponent).cells.first._clearCellSelection(); const visColLength = this.grid.unpinnedColumns.length; if (this.isColumnFullyVisible(visColLength - 1)) { - this.grid.filteringService.focusFilterCellChip(this.grid.filterCellList[this.grid.filterCellList.length-1].column.field, false); + const lastFilterCell = this.grid.filterCellList[this.grid.filterCellList.length-1]; + lastFilterCell.focusChip(false); } else { this.grid.filteringService.columnToFocus = this.grid.unpinnedColumns[visColLength - 1]; this.grid.filteringService.shouldFocusNext = false; From 67751beddaf34ffe2a579b059fb11e825444ba19 Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Sat, 17 Nov 2018 20:10:45 +0200 Subject: [PATCH 08/24] test(*): refactor failing tests #542 --- .../src/lib/grids/column.component.ts | 5 + .../grids/grid-header-group.component.html | 4 +- .../lib/grids/grid-header-group.component.ts | 16 ++- .../src/lib/grids/grid-header.component.ts | 3 +- .../src/lib/grids/grid.common.ts | 9 +- .../src/lib/grids/grid/column-group.spec.ts | 33 ++--- .../src/lib/grids/grid/column-moving.spec.ts | 109 +++++---------- .../lib/grids/grid/column-resizing.spec.ts | 125 +++++++++--------- .../src/lib/grids/grid/column.spec.ts | 4 +- .../lib/grids/grid/grid-filtering-ui.spec.ts | 19 +-- .../src/lib/grids/grid/grid.component.spec.ts | 7 +- .../src/lib/grids/grid/grid.groupby.spec.ts | 7 +- .../src/lib/grids/grid/grid.pinning.spec.ts | 5 +- .../tree-grid/tree-grid-indentation.spec.ts | 4 +- .../tree-grid/tree-grid-integration.spec.ts | 4 +- .../test-utils/tree-grid-functions.spec.ts | 3 +- 16 files changed, 164 insertions(+), 193 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/column.component.ts b/projects/igniteui-angular/src/lib/grids/column.component.ts index 5640e6a1527..8ab80ea650e 100644 --- a/projects/igniteui-angular/src/lib/grids/column.component.ts +++ b/projects/igniteui-angular/src/lib/grids/column.component.ts @@ -306,6 +306,11 @@ export class IgxColumnComponent implements AfterContentInit { */ @Input() public headerClasses = ''; + /** + *@hidden + */ + @Input() + public headerGroupClasses = ''; /** * Sets a conditional class selector of the column cells. * Accepts an object literal, containing key-value pairs, diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html index 56f49bcd2c4..f59a18f2df0 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html @@ -14,9 +14,9 @@ -
{ @@ -125,13 +126,13 @@ export class IgxGridHeaderGroupComponent { public onResizeAreaMouseOver() { if (this.column.resizable) { - this.colReszingService.column = this.column; this.colReszingService.resizeCursor = 'col-resize'; } } public onResizeAreaMouseDown(event) { if (event.button === 0 && this.column.resizable) { + this.colReszingService.column = this.column; this.colReszingService.showResizer = true; this.colReszingService.isColumnResizing = true; this.colReszingService.resizerHeight = this.column.grid.calcResizerHeight; @@ -140,4 +141,11 @@ export class IgxGridHeaderGroupComponent { this.colReszingService.resizeCursor = null; } } + + public autosizeColumnOnDblClick(event) { + if (event.button === 0 && this.column.resizable) { + this.colReszingService.column = this.column; + this.colReszingService.autosizeColumnOnDblClick(); + } + } } diff --git a/projects/igniteui-angular/src/lib/grids/grid-header.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header.component.ts index 99843322f66..3ed8319ace9 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header.component.ts @@ -47,8 +47,7 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck { 'asc': this.ascending, 'desc': this.descending, 'igx-grid__th--number': this.column.dataType === DataType.Number, - 'igx-grid__th--sorted': this.sorted, - 'igx-grid__th--filtering': this.filteringService.filteredColumn === this.column + 'igx-grid__th--sorted': this.sorted }; Object.entries(classList).forEach(([klass, value]) => { diff --git a/projects/igniteui-angular/src/lib/grids/grid.common.ts b/projects/igniteui-angular/src/lib/grids/grid.common.ts index fc4b9c49a84..7fada2ccfc8 100644 --- a/projects/igniteui-angular/src/lib/grids/grid.common.ts +++ b/projects/igniteui-angular/src/lib/grids/grid.common.ts @@ -530,13 +530,16 @@ export class IgxColumnMovingDropDirective extends IgxDropDirective implements On this.column.grid.moveColumn(this.cms.column, this.column, this._dropPos); if (this.cms.selection && this.cms.selection.column) { + this.column.grid.selection.set(this.column.gridID + '-cell', new Set([{ + rowID: this.cms.selection.rowID, + columnID: this.column.grid.columnList.toArray().indexOf(this.cms.selection.column) + }])); + const cell = this.column.grid.getCellByKey(this.cms.selection.rowID, this.cms.selection.column.field); if (cell) { - cell._updateCellSelectionStatus(true, event); + cell.nativeElement.focus(); } - - this.cms.selection = null; } this.column.grid.draggedColumn = null; diff --git a/projects/igniteui-angular/src/lib/grids/grid/column-group.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/column-group.spec.ts index c43efa1eb02..cf4b91acca6 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/column-group.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/column-group.spec.ts @@ -586,7 +586,7 @@ describe('IgxGrid - multi-column headers', () => { testColumnGroupHeaderRendering(secondGroup, secondGroupChildrenCount * secondSubGroupChildrenCount * columnWidthPx, gridHeadersDepth * grid.defaultRowHeight, componentInstance.secondGroupTitle, - 'secondSubGroup', secondGroupChildrenCount); + 'secondSubGroup', 0); const secondSubGroups = secondGroup.queryAll(By.css('.secondSubGroup')); testColumnGroupHeaderRendering(secondSubGroups[0], @@ -1843,21 +1843,21 @@ export class StegosaurusGridComponent implements AfterViewInit { @Component({ template: ` - + - - + + - + - + @@ -1900,7 +1900,7 @@ export class BlueWhaleGridComponent { @Component({ template: ` - + ` @@ -1918,13 +1918,13 @@ export class EmptyColGridComponent { @Component({ template: ` - + - + - + @@ -1953,13 +1953,13 @@ export class OneColPerGroupGridComponent { @Component({ template: ` - - + + - + @@ -2021,8 +2021,9 @@ function getColGroup(grid: IgxGridComponent, headerName: string): IgxColumnGroup // tests column and column group header rendering function testColumnGroupHeaderRendering(column: DebugElement, width: number, height: number, title: string, descendentColumnCssClass?: string, descendentColumnCount?: number) { - expect(column.nativeElement.parentElement.offsetHeight).toBe(height); - expect(column.nativeElement.parentElement.offsetWidth).toBe(width); + + expect(column.nativeElement.offsetHeight).toBe(height); + expect(column.nativeElement.offsetWidth).toBe(width); const colHeaderTitle = column.children .filter(c => c.nativeElement.classList.contains(GRID_COL_GROUP_THEAD_TITLE_CLASS))[0]; @@ -2143,7 +2144,7 @@ class NestedColGroupsTests { const masterColGroup = fixture.debugElement.query(By.css('.masterColGroup')); const masterColGroupWidth = firstSlaveColGroupWidth + secondSlaveColGroupWidth; const masterSlaveColGroupDepth = 3; - const masterColGroupChildrenCount = 2; + const masterColGroupChildrenCount = 0; testColumnGroupHeaderRendering(masterColGroup, masterColGroupWidth, masterSlaveColGroupDepth * grid.defaultRowHeight, ci.masterColGroupTitle, diff --git a/projects/igniteui-angular/src/lib/grids/grid/column-moving.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/column-moving.spec.ts index b2c6fb0d715..6f3be21d2cf 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/column-moving.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/column-moving.spec.ts @@ -24,7 +24,7 @@ describe('IgxGrid - Column Moving', () => { configureTestSuite(); const CELL_CSS_CLASS = '.igx-grid__td'; const COLUMN_HEADER_CLASS = '.igx-grid__th'; - const COLUMN_GROUP_HEADER_CLASS = '.igx-grid__th--fw'; + const COLUMN_GROUP_HEADER_CLASS = '.igx-grid__thead-title'; let fixture, grid: IgxGridComponent; @@ -141,8 +141,7 @@ describe('IgxGrid - Column Moving', () => { expect(columnsList[2].field).toEqual('LastName'); })); - xit('Should not break filtering, sorting and resizing when column moving is enabled.', (async() => { - pending('This scenario need to be reworked with new Filtering row'); + it('Should not break sorting and resizing when column moving is enabled.', (async() => { fixture.componentInstance.isFilterable = true; fixture.componentInstance.isResizable = true; fixture.componentInstance.isSortable = true; @@ -171,13 +170,12 @@ describe('IgxGrid - Column Moving', () => { // step 2 - verify resizing is not broken - const resizeHandle = headers[0].nativeElement.children[3]; - - UIInteractions.simulateMouseEvent('mousedown', resizeHandle, 200, 0); + const resizeHandle = headers[0].parent.nativeElement.children[2]; + UIInteractions.simulateMouseEvent('mousedown', resizeHandle, 200, 80); await wait(); fixture.detectChanges(); - const resizer = headers[0].nativeElement.children[3].children[0]; + const resizer = headers[0].parent.nativeElement.children[2].children[0]; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 300, 5); await wait(); @@ -194,18 +192,6 @@ describe('IgxGrid - Column Moving', () => { fixture.detectChanges(); expect(grid.getCellByColumn(0, 'ID').value).toEqual(6); - - - // step 4 - verify filtering is not broken - const filterUIContainer = fixture.debugElement.query(By.css('igx-grid-filter')); - const filterIcon = filterUIContainer.query(By.css('igx-icon')); - - filterIcon.nativeElement.click(); - await wait(); - fixture.detectChanges(); - - const dialog = filterUIContainer.query(By.directive(IgxToggleDirective)); - expect(dialog.nativeElement.classList).toContain('igx-toggle'); })); it('Should not break vertical or horizontal scrolling after columns are reordered.', (async() => { @@ -245,44 +231,6 @@ describe('IgxGrid - Column Moving', () => { expect(grid.columnList.toArray()[2].cells[3].value).toBeTruthy('BRown'); })); - xit('Should close filter dialog, if opened, when column moving starts.', (async() => { - pending('This scenario need to be reworked with new Filtering row'); - fixture.componentInstance.isFilterable = true; - fixture.detectChanges(); - - const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); - - headers[0].triggerEventHandler('click', new Event('click')); - fixture.detectChanges(); - - const filterUIContainer = fixture.debugElement.query(By.css('igx-grid-filter')); - const filterIcon = filterUIContainer.query(By.css('igx-icon')); - - // step 1 - open the filtering dialog - filterIcon.nativeElement.click(); - await wait(); - fixture.detectChanges(); - - let dialog = filterUIContainer.query(By.directive(IgxToggleDirective)); - expect(dialog.nativeElement.classList.contains('igx-toggle')).toBeTruthy(); - - // step 2 - move a column - const header = headers[0].nativeElement; - UIInteractions.simulatePointerEvent('pointerdown', header, 100, 65); - await wait(); - UIInteractions.simulatePointerEvent('pointermove', header, 106, 71); - await wait(); - UIInteractions.simulatePointerEvent('pointermove', header, 300, 71); - await wait(); - UIInteractions.simulatePointerEvent('pointerup', header, 300, 71); - await wait(); - fixture.detectChanges(); - - // step 3 - verify the filtering dialog is closed - dialog = filterUIContainer.query(By.directive(IgxToggleDirective)); - expect(dialog.nativeElement.classList.contains('igx-toggle--hidden')).toBeTruthy(); - })); - it('Should fire onColumnMovingStart, onColumnMoving and onColumnMovingEnd with correct values of event arguments.', (async() => { const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); @@ -509,6 +457,7 @@ describe('IgxGrid - Column Moving', () => { cell = fixture.debugElement.queryAll(By.css(CELL_CSS_CLASS))[1]; UIInteractions.triggerKeyDownEvtUponElem('arrowright', cell.nativeElement, true); await wait(50); + fixture.detectChanges(); expect(grid.getCellByColumn(0, 'LastName').selected).toBeTruthy(); })); @@ -542,6 +491,7 @@ describe('IgxGrid - Column Moving', () => { cell = fixture.debugElement.queryAll(By.css(CELL_CSS_CLASS))[0]; UIInteractions.triggerKeyDownEvtUponElem('arrowright', cell.nativeElement, true); await wait(50); + fixture.detectChanges(); expect(grid.getCellByColumn(0, 'LastName').selected).toBeTruthy(); })); @@ -1002,7 +952,7 @@ describe('IgxGrid - Column Moving', () => { it('MCH - should reorder only columns on the same level (top level simple column).', (async() => { // step 1 - try reordering simple column level 0 and simple column level 1 - const header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[0].nativeElement; + const header = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS))[0].nativeElement; UIInteractions.simulatePointerEvent('pointerdown', header, 50, 75); await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 50, 81); @@ -1051,7 +1001,7 @@ describe('IgxGrid - Column Moving', () => { it('MCH - should reorder only columns on the same level (top level group column).', (async() => { // step 1 - try reordering group column level 0 and simple column level 1 - let header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[1].nativeElement; + let header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[0].nativeElement; UIInteractions.simulatePointerEvent('pointerdown', header, 250, 25); await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 250, 31); @@ -1073,9 +1023,9 @@ describe('IgxGrid - Column Moving', () => { await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 250, 31); await wait(50); - UIInteractions.simulatePointerEvent('pointermove', header, 560, 81); - await wait(); - UIInteractions.simulatePointerEvent('pointerup', header, 560, 81); + UIInteractions.simulatePointerEvent('pointermove', header, 570, 81); + await wait(50); + UIInteractions.simulatePointerEvent('pointerup', header, 570, 81); await wait(); fixture.detectChanges(); @@ -1085,14 +1035,14 @@ describe('IgxGrid - Column Moving', () => { expect(columnsList[2].field).toEqual('CompanyName'); // step 3 - try reordering group column level 0 and group column level 0 - header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[7].nativeElement; - UIInteractions.simulatePointerEvent('pointerdown', header, 800, 25); + header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[2].nativeElement; + UIInteractions.simulatePointerEvent('pointerdown', header, 700, 25); await wait(); - UIInteractions.simulatePointerEvent('pointermove', header, 800, 31); + UIInteractions.simulatePointerEvent('pointermove', header, 700, 31); await wait(50); - UIInteractions.simulatePointerEvent('pointermove', header, 350, 31); + UIInteractions.simulatePointerEvent('pointermove', header, 200, 31); await wait(); - UIInteractions.simulatePointerEvent('pointerup', header, 350, 31); + UIInteractions.simulatePointerEvent('pointerup', header, 200, 31); await wait(); fixture.detectChanges(); @@ -1106,7 +1056,7 @@ describe('IgxGrid - Column Moving', () => { it('MCH - should reorder only columns on the same level (sub level simple column).', (async() => { // step 1 - try reordering simple column level 1 and simple column level 0 - const header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[2].nativeElement; + const header = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS))[1].nativeElement; UIInteractions.simulatePointerEvent('pointerdown', header, 150, 100); await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 150, 106); @@ -1174,7 +1124,8 @@ describe('IgxGrid - Column Moving', () => { it('MCH - should reorder only columns on the same level (sub level group column).', (async() => { // step 1 - try reordering group column level 1 and simple column level 0 - const header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[3].nativeElement; + const header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[1].nativeElement; + UIInteractions.simulatePointerEvent('pointerdown', header, 300, 75); await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 300, 81); @@ -1226,7 +1177,7 @@ describe('IgxGrid - Column Moving', () => { it('MCH - should reorder only columns on the same level, with same parent.', (async() => { // step 1 - try reordering simple column level 1 and simple column level 1 (different parent) - let header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[2].nativeElement; + let header = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS))[1].nativeElement; UIInteractions.simulatePointerEvent('pointerdown', header, 150, 75); await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 150, 81); @@ -1242,7 +1193,7 @@ describe('IgxGrid - Column Moving', () => { expect(columnsList[5].field).toEqual('Country'); // step 2 - try reordering simple column level 2 and simple column level 2 (same parent) - header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[5].nativeElement; + header = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS))[3].nativeElement; UIInteractions.simulatePointerEvent('pointerdown', header, 400, 125); await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 400, 131); @@ -1258,14 +1209,14 @@ describe('IgxGrid - Column Moving', () => { expect(columnsList[3].field).toEqual('ContactName'); // step 3 - try reordering simple column level 0 and simple column level 0 (no parent) - header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[0].nativeElement; + header = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS))[0].nativeElement; UIInteractions.simulatePointerEvent('pointerdown', header, 50, 75); await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 50, 81); await wait(50); - UIInteractions.simulatePointerEvent('pointermove', header, 560, 81); + UIInteractions.simulatePointerEvent('pointermove', header, 580, 81); await wait(); - UIInteractions.simulatePointerEvent('pointerup', header, 560, 81); + UIInteractions.simulatePointerEvent('pointerup', header, 580, 81); await wait(); fixture.detectChanges(); @@ -1284,14 +1235,14 @@ describe('IgxGrid - Column Moving', () => { fixture.detectChanges(); // step 2 - reorder the parent column and verify selection is preserved - const header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[1].nativeElement; + const header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[0].nativeElement; UIInteractions.simulatePointerEvent('pointerdown', header, 300, 25); await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 300, 31); await wait(50); - UIInteractions.simulatePointerEvent('pointermove', header, 560, 50); + UIInteractions.simulatePointerEvent('pointermove', header, 580, 50); await wait(); - UIInteractions.simulatePointerEvent('pointerup', header, 560, 50); + UIInteractions.simulatePointerEvent('pointerup', header, 580, 50); await wait(); fixture.detectChanges(); @@ -1312,7 +1263,7 @@ describe('IgxGrid - Column Moving', () => { fixture.detectChanges(); // step 2 - try pinning a sub level simple column - let header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[2].nativeElement; + let header = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS))[1].nativeElement; UIInteractions.simulatePointerEvent('pointerdown', header, 150, 75); await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 150, 81); @@ -1327,7 +1278,7 @@ describe('IgxGrid - Column Moving', () => { expect(columnsList[1].field).toEqual('CompanyName'); // step 3 - try pinning a top level group column - header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[1].nativeElement; + header = fixture.debugElement.queryAll(By.css(COLUMN_GROUP_HEADER_CLASS))[0].nativeElement; UIInteractions.simulatePointerEvent('pointerdown', header, 150, 25); await wait(); UIInteractions.simulatePointerEvent('pointermove', header, 150, 31); diff --git a/projects/igniteui-angular/src/lib/grids/grid/column-resizing.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/column-resizing.spec.ts index 21755caab31..a66e6bd813e 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/column-resizing.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/column-resizing.spec.ts @@ -1,5 +1,5 @@ import { Component, DebugElement, OnInit, ViewChild } from '@angular/core'; -import { async, fakeAsync, TestBed, tick } from '@angular/core/testing'; +import { async, fakeAsync, TestBed, tick, flush } from '@angular/core/testing'; import { FormsModule } from '@angular/forms'; import { By } from '@angular/platform-browser'; import { NoopAnimationsModule } from '@angular/platform-browser/animations'; @@ -18,6 +18,7 @@ import { configureTestSuite } from '../../test-utils/configure-suite'; describe('IgxGrid - Deferred Column Resizing', () => { configureTestSuite(); const COLUMN_HEADER_CLASS = '.igx-grid__th'; + const COLUMN_HEADER_GROUP_CLASS = '.igx-grid__thead-item'; beforeEach(async(() => { TestBed.configureTestingModule({ @@ -50,22 +51,17 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[0].resizable).toBeTruthy(); expect(grid.columns[2].resizable).toBeFalsy(); - const headerResArea = headers[0].nativeElement.children[2]; - UIInteractions.simulateMouseEvent('mouseover', headerResArea, 100, 5); - UIInteractions.simulateMouseEvent('mousedown', headerResArea, 100, 5); - UIInteractions.simulateMouseEvent('mousedup', headerResArea, 100, 5); - tick(100); - fixture.detectChanges(); - UIInteractions.simulateMouseEvent('mousedown', headerResArea, 100, 5); - tick(100); + const headerResArea = headers[0].parent.children[1].nativeElement; + UIInteractions.simulateMouseEvent('mousedown', headerResArea, 100, 15); + tick(); fixture.detectChanges(); - let resizer = headers[0].nativeElement.children[2].children[0]; + let resizer = headers[0].parent.children[1].children[0].nativeElement; expect(resizer).toBeDefined(); - UIInteractions.simulateMouseEvent('mousemove', resizer, 250, 5); - tick(100); + UIInteractions.simulateMouseEvent('mousemove', resizer, 250, 15); + tick(); - UIInteractions.simulateMouseEvent('mouseup', resizer, 250, 5); + UIInteractions.simulateMouseEvent('mouseup', resizer, 250, 15); tick(); fixture.detectChanges(); @@ -75,7 +71,7 @@ describe('IgxGrid - Deferred Column Resizing', () => { tick(); fixture.detectChanges(); - resizer = headers[0].nativeElement.children[2].children[0]; + resizer = headers[0].parent.children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 40, 5); tick(); @@ -105,12 +101,12 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[0].width).toEqual('100px'); - const headerResArea = headers[0].nativeElement.children[2]; + const headerResArea = headers[0].parent.children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 100, 0); tick(); fixture.detectChanges(); - const resizer = headers[0].nativeElement.children[2].children[0]; + const resizer = headers[0].parent.children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 700, 5); tick(); @@ -134,18 +130,18 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[1].maxWidth).toEqual('250px'); expect(grid.columns[1].resizable).toBeTruthy(); - const headerResArea = headers[1].nativeElement.children[2]; + const headerResArea = headers[1].parent.children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 200, 0); tick(); fixture.detectChanges(); - let resizer = headers[1].nativeElement.children[2].children[0]; + let resizer = headers[1].parent.children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 370, 5); tick(); UIInteractions.simulateMouseEvent('mouseup', resizer, 370, 5); - tick(100); + tick(); fixture.detectChanges(); expect(grid.columns[1].width).toEqual('250px'); @@ -154,7 +150,7 @@ describe('IgxGrid - Deferred Column Resizing', () => { tick(); fixture.detectChanges(); - resizer = headers[1].nativeElement.children[2].children[0]; + resizer = headers[1].parent.children[1].children[0].nativeElement; UIInteractions.simulateMouseEvent('mousemove', resizer, 100, 5); tick(); @@ -176,12 +172,12 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[2].sortable).toBeTruthy(); expect(grid.columns[2].cells[0].value).toEqual(254); - const headerResArea = headers[2].nativeElement.children[2]; + const headerResArea = headers[2].parent.children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 450, 0); tick(); fixture.detectChanges(); - const resizer = headers[2].nativeElement.children[1].children[0]; + const resizer = headers[2].parent.children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 550, 5); tick(); @@ -211,12 +207,12 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[0].width).toEqual('100px'); expect(grid.columns[1].width).toEqual('100px'); - const headerResArea = headers[0].nativeElement.children[2]; + const headerResArea = headers[0].parent.children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 100, 0); tick(); fixture.detectChanges(); - let resizer = headers[0].nativeElement.children[2].children[0]; + let resizer = headers[0].parent.children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 450, 5); tick(); @@ -232,7 +228,7 @@ describe('IgxGrid - Deferred Column Resizing', () => { tick(); fixture.detectChanges(); - resizer = headers[0].nativeElement.children[2].children[0]; + resizer = headers[0].parent.children[1].children[0].nativeElement; UIInteractions.simulateMouseEvent('mousemove', resizer, 100, 5); tick(); @@ -252,12 +248,12 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(parseInt(grid.columns[0].width, 10)).not.toBeNaN(); - let headerResArea = headers[0].nativeElement.children[2]; + let headerResArea = headers[0].parent.children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 126, 5); tick(); fixture.detectChanges(); - let resizer = headers[0].nativeElement.children[2].children[0]; + let resizer = headers[0].parent.children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 250, 5); tick(); @@ -272,7 +268,7 @@ describe('IgxGrid - Deferred Column Resizing', () => { tick(); fixture.detectChanges(); - resizer = headers[0].nativeElement.children[2].children[0]; + resizer = headers[0].parent.children[1].children[0].nativeElement; UIInteractions.simulateMouseEvent('mousemove', resizer, 50, 5); tick(); @@ -282,14 +278,14 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[0].width).toEqual('70px'); - headerResArea = headers[1].nativeElement.children[2]; + headerResArea = headers[1].parent.children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 197, 5); tick(); fixture.detectChanges(); expect(parseInt(grid.columns[1].width, 10)).not.toBeNaN(); - resizer = headers[1].nativeElement.children[2].children[0]; + resizer = headers[1].parent.children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 300, 5); tick(); @@ -304,7 +300,7 @@ describe('IgxGrid - Deferred Column Resizing', () => { tick(); fixture.detectChanges(); - resizer = headers[1].nativeElement.children[2].children[0]; + resizer = headers[1].parent.children[1].children[0].nativeElement; UIInteractions.simulateMouseEvent('mousemove', resizer, 50, 5); tick(); @@ -328,12 +324,12 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[1].width).toEqual('100px'); - const headerResArea = headers[1].nativeElement.children[2]; + const headerResArea = headers[1].parent.children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 200, 0); tick(); fixture.detectChanges(); - const resizer = headers[1].nativeElement.children[2].children[0]; + const resizer = headers[1].parent.children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 350, 5); tick(); @@ -350,43 +346,44 @@ describe('IgxGrid - Deferred Column Resizing', () => { fixture.detectChanges(); const grid = fixture.componentInstance.grid; - const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); + const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); expect(grid.columns[0].width).toEqual('150px'); expect(grid.columns[1].width).toEqual('150px'); expect(grid.columns[2].width).toEqual('150px'); - let resizeArea = headers[0].componentInstance.resizeArea.nativeElement; - UIInteractions.simulateMouseEvent('dblclick', resizeArea, 148, 5); + let resizeArea = headers[0].children[1].nativeElement; + UIInteractions.simulateMouseEvent('dblclick', resizeArea, 148, 15); tick(); fixture.detectChanges(); expect(grid.columns[0].width).toEqual('78px'); - resizeArea = headers[1].componentInstance.resizeArea.nativeElement; + resizeArea = headers[1].children[1].nativeElement; + UIInteractions.simulateMouseEvent('mouseover', resizeArea, 248, 5); UIInteractions.simulateMouseEvent('dblclick', resizeArea, 248, 5); tick(); fixture.detectChanges(); expect(grid.columns[1].width).toEqual('195px'); - resizeArea = headers[2].componentInstance.resizeArea.nativeElement; + resizeArea = headers[2].children[1].nativeElement; UIInteractions.simulateMouseEvent('dblclick', resizeArea, 305, 5); tick(); fixture.detectChanges(); expect(grid.columns[2].width).toEqual('78px'); - resizeArea = headers[3].componentInstance.resizeArea.nativeElement; + resizeArea = headers[3].children[1].nativeElement; UIInteractions.simulateMouseEvent('dblclick', resizeArea, 400, 5); tick(); fixture.detectChanges(); expect(grid.columns[3].width).toEqual('73px'); - resizeArea = headers[5].componentInstance.resizeArea.nativeElement; + resizeArea = headers[5].children[1].nativeElement; UIInteractions.simulateMouseEvent('dblclick', resizeArea, 486, 5); - tick(); + tick(100); fixture.detectChanges(); expect(grid.columns[5].width).toEqual('89px'); @@ -397,13 +394,13 @@ describe('IgxGrid - Deferred Column Resizing', () => { fixture.detectChanges(); const grid = fixture.componentInstance.grid; - const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); + const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); - expect(grid.columns[4].cells[0].nativeElement.getBoundingClientRect().width).toEqual(48); + expect(grid.columns[4].cells[0].nativeElement.getBoundingClientRect().width).toEqual(50); expect(grid.columns[4].maxWidth).toEqual('100px'); - const resizeArea = headers[4].componentInstance.resizeArea.nativeElement; - UIInteractions.simulateMouseEvent('dblclick', resizeArea, 498, 5); + const resizeArea = headers[4].children[1].nativeElement; + UIInteractions.simulateMouseEvent('dblclick', resizeArea, 448, 15); tick(); fixture.detectChanges(); @@ -415,11 +412,11 @@ describe('IgxGrid - Deferred Column Resizing', () => { fixture.detectChanges(); const grid = fixture.componentInstance.grid; - const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); + const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); expect(grid.columns[5].width).toEqual('150px'); - const resizeArea = headers[5].componentInstance.resizeArea.nativeElement; + const resizeArea = headers[5].children[1].nativeElement; UIInteractions.simulateMouseEvent('dblclick', resizeArea, 898, 5); tick(); fixture.detectChanges(); @@ -432,11 +429,11 @@ describe('IgxGrid - Deferred Column Resizing', () => { fixture.detectChanges(); const grid = fixture.componentInstance.grid; - const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); + const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); expect(grid.columns[2].width).toEqual('100px'); - const resizeArea = headers[2].componentInstance.resizeArea.nativeElement; + const resizeArea = headers[2].children[1].nativeElement; UIInteractions.simulateMouseEvent('dblclick', resizeArea, 298, 5); tick(); fixture.detectChanges(); @@ -449,13 +446,13 @@ describe('IgxGrid - Deferred Column Resizing', () => { fixture.detectChanges(); const grid = fixture.componentInstance.grid; - const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); + const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); expect(grid.columns[0].width).toEqual('100px'); expect(grid.columns[1].width).toEqual('100px'); expect(grid.columns[2].width).toEqual('100px'); - const resizeArea = headers[1].componentInstance.resizeArea.nativeElement; + const resizeArea = headers[1].children[1].nativeElement UIInteractions.simulateMouseEvent('dblclick', resizeArea, 198, 5); tick(); fixture.detectChanges(); @@ -464,12 +461,12 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[1].width).toEqual('100px'); expect(grid.columns[2].width).toEqual('100px'); - const headerResArea = headers[0].nativeElement.children[2]; + const headerResArea = headers[0].children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 100, 0); tick(); fixture.detectChanges(); - const resizer = headers[0].nativeElement.children[2].children[0]; + const resizer = headers[0].children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 450, 5); tick(); @@ -488,17 +485,17 @@ describe('IgxGrid - Deferred Column Resizing', () => { fixture.detectChanges(); const grid = fixture.componentInstance.grid; - const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); + const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); expect(grid.columns[0].width).toEqual('150px'); expect(fixture.componentInstance.count).toEqual(0); - const headerResArea = headers[0].nativeElement.children[2]; + const headerResArea = headers[0].children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 150, 5); tick(); fixture.detectChanges(); - const resizer = headers[0].nativeElement.children[2].children[0]; + const resizer = headers[0].children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 300, 5); tick(); @@ -515,7 +512,7 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[1].width).toEqual('150px'); - const resizeArea = headers[1].componentInstance.resizeArea.nativeElement; + const resizeArea = headers[1].children[1].nativeElement; UIInteractions.simulateMouseEvent('dblclick', resizeArea, 198, 5); tick(); fixture.detectChanges(); @@ -531,7 +528,7 @@ describe('IgxGrid - Deferred Column Resizing', () => { const fixture = TestBed.createComponent(ResizableColumnsComponent); fixture.detectChanges(); const grid = fixture.componentInstance.grid; - const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); + const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); const displayContainer: HTMLElement = fixture.componentInstance.grid.tbody.nativeElement.querySelector('igx-display-container'); let rowsRendered = displayContainer.querySelectorAll('igx-display-container'); let colsRendered = rowsRendered[0].children; @@ -540,12 +537,12 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(colsRendered.length).toEqual(4); // Resize first column - const headerResArea = headers[0].nativeElement.children[2]; + const headerResArea = headers[0].children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 100, 0); tick(); fixture.detectChanges(); - const resizer = headers[0].nativeElement.children[2].children[0]; + const resizer = headers[0].children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 700, 5); tick(); @@ -577,7 +574,7 @@ describe('IgxGrid - Deferred Column Resizing', () => { fixture.detectChanges(); const grid = fixture.componentInstance.grid; - const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); + const headers: DebugElement[] = fixture.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); const expectedHeight = fixture.debugElement.query(By.css('igx-grid')).nativeElement.getBoundingClientRect().height - grid.nativeElement.querySelector('.igx-grid__thead').getBoundingClientRect().height - grid.nativeElement.querySelector('.igx-grid__tfoot').getBoundingClientRect().height; @@ -586,12 +583,12 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[0].width).toEqual('100px'); // Resize first column - const headerResArea = headers[0].nativeElement.children[2]; + const headerResArea = headers[0].children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 100, 0); tick(); fixture.detectChanges(); - const resizer = headers[0].nativeElement.children[2].children[0]; + const resizer = headers[0].children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 250, 5); tick(); @@ -751,7 +748,7 @@ export class PinnedColumnsComponent { [formatter]="returnVal"> - +
diff --git a/projects/igniteui-angular/src/lib/grids/grid/column.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/column.spec.ts index 0af94dce994..42c22b7d921 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/column.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/column.spec.ts @@ -13,6 +13,7 @@ describe('IgxGrid - Column properties', () => { configureTestSuite(); const COLUMN_HEADER_CLASS = '.igx-grid__th'; + const COLUMN_HEADER_GROUP_CLASS = '.igx-grid__thead-item'; beforeEach(async(() => { TestBed.configureTestingModule({ @@ -170,10 +171,11 @@ describe('IgxGrid - Column properties', () => { fix.componentInstance.grid.columnWidth = '200px'; fix.detectChanges(); const cols = fix.componentInstance.grid.columnList; + cols.forEach((item) => { expect(item.width).toEqual('200px'); }); - const headers = fix.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); + const headers = fix.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); expect(headers[0].nativeElement.style['min-width']).toEqual('200px'); }); diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts index 50867d14403..765fceba024 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts @@ -21,6 +21,7 @@ import { IgxBadgeComponent } from '../../badge/badge.component'; import { IgxCheckboxComponent } from '../../checkbox/checkbox.component'; import { SortingDirection } from '../../data-operations/sorting-expression.interface'; import { DefaultSortingStrategy } from '../../data-operations/sorting-strategy'; +import { IgxGridHeaderGroupComponent } from '../grid-header-group.component'; const FILTER_UI_ROW = 'igx-grid-filtering-row'; @@ -2320,13 +2321,13 @@ describe('IgxGrid - Filtering Row UI actions', () => { expect(colIndicator.length).toEqual(0); // Make 'ProductName' column smaller - const headers: DebugElement[] = fix.debugElement.queryAll(By.directive(IgxGridHeaderComponent)); - const headerResArea = headers[1].nativeElement.children[2]; + const headers: DebugElement[] = fix.debugElement.queryAll(By.directive(IgxGridHeaderGroupComponent)); + const headerResArea = headers[1].children[2].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 200, 0); tick(); fix.detectChanges(); - const resizer = headers[1].nativeElement.children[2].children[0]; + const resizer = headers[1].children[2].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 100, 5); tick(); @@ -2365,8 +2366,8 @@ describe('IgxGrid - Filtering Row UI actions', () => { stringCellChip.click(); fix.detectChanges(); - const headers: DebugElement[] = fix.debugElement.queryAll(By.directive(IgxGridHeaderComponent)); - const headerResArea = headers[1].nativeElement.children[2]; + const headers: DebugElement[] = fix.debugElement.queryAll(By.directive(IgxGridHeaderGroupComponent)); + const headerResArea = headers[1].children[2].nativeElement; let filteringRow = fix.debugElement.query(By.directive(IgxGridFilteringRowComponent)); expect(filteringRow).toBeTruthy(); @@ -2376,7 +2377,7 @@ describe('IgxGrid - Filtering Row UI actions', () => { tick(); fix.detectChanges(); - const resizer = headers[1].nativeElement.children[2].children[0]; + const resizer = headers[1].children[2].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 100, 5); tick(); @@ -2425,13 +2426,13 @@ describe('IgxGrid - Filtering Row UI actions', () => { expect(indicatorBadge.nativeElement.innerText.trim()).toEqual('2'); // Make 'Downloads' column bigger - const headers: DebugElement[] = fix.debugElement.queryAll(By.directive(IgxGridHeaderComponent)); - const headerResArea = headers[2].nativeElement.children[2]; + const headers: DebugElement[] = fix.debugElement.queryAll(By.directive(IgxGridHeaderGroupComponent)); + const headerResArea = headers[2].children[2].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 100, 0); tick(); fix.detectChanges(); - const resizer = headers[2].nativeElement.children[2].children[0]; + const resizer = headers[2].children[2].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 300, 5); tick(); diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid.component.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/grid.component.spec.ts index fbaf3cce12e..e1c7b59a0f3 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid.component.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid.component.spec.ts @@ -32,6 +32,7 @@ const DEBOUNCETIME = 30; describe('IgxGrid Component Tests', () => { const MIN_COL_WIDTH = '136px'; const COLUMN_HEADER_CLASS = '.igx-grid__th'; + const COLUMN_HEADER_GROUP_CLASS = '.igx-grid__thead-item'; const CELL_CLASS = '.igx-grid__td'; const ROW_CLASS = '.igx-grid__tr'; const ROW_EDITING_OUTLET_CLASS = '.igx-grid__row-editing-outlet'; @@ -2328,13 +2329,13 @@ describe('IgxGrid Component Tests', () => { column.resizable = true; fix.detectChanges(); - const headers: DebugElement[] = fix.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); - const headerResArea = headers[2].nativeElement.children[2]; + const headers: DebugElement[] = fix.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); + const headerResArea = headers[2].children[1].nativeElement; UIInteractions.simulateMouseEvent('mousedown', headerResArea, 500, 0); tick(); fix.detectChanges(); - const resizer = headers[2].nativeElement.children[2].children[0]; + const resizer = headers[2].children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 550, 0); tick(); diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid.groupby.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/grid.groupby.spec.ts index aa86c221b7f..6bc89e0e18c 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid.groupby.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid.groupby.spec.ts @@ -22,6 +22,7 @@ import { MultiColumnHeadersWithGroupingComponent } from '../../test-utils/grid-s describe('IgxGrid - GroupBy', () => { configureTestSuite(); const COLUMN_HEADER_CLASS = '.igx-grid__th'; + const COLUMN_HEADER_GROUP_CLASS = '.igx-grid__thead-item'; const CELL_CSS_CLASS = '.igx-grid__td'; const SORTING_ICON_ASC_CONTENT = 'arrow_upward'; const SORTING_ICON_DESC_CONTENT = 'arrow_downward'; @@ -1480,8 +1481,8 @@ describe('IgxGrid - GroupBy', () => { expect(grRow.element.nativeElement.clientWidth).toEqual(1200); } - const headers = fix.debugElement.queryAll(By.css(COLUMN_HEADER_CLASS)); - const headerResArea = headers[0].nativeElement.children[2]; + const headers = fix.debugElement.queryAll(By.css(COLUMN_HEADER_GROUP_CLASS)); + const headerResArea = headers[0].children[1].nativeElement; UIInteractions.simulateMouseEvent('mouseover', headerResArea, 200, 5); UIInteractions.simulateMouseEvent('mousedown', headerResArea, 200, 5); UIInteractions.simulateMouseEvent('mouseup', headerResArea, 200, 5); @@ -1491,7 +1492,7 @@ describe('IgxGrid - GroupBy', () => { tick(100); fix.detectChanges(); - const resizer = headers[0].nativeElement.children[2].children[0]; + const resizer = headers[0].children[1].children[0].nativeElement; expect(resizer).toBeDefined(); UIInteractions.simulateMouseEvent('mousemove', resizer, 550, 5); tick(100); diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid.pinning.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/grid.pinning.spec.ts index 81ab5b4c49f..f3f0d5bf48f 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid.pinning.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid.pinning.spec.ts @@ -14,6 +14,7 @@ import { wait, UIInteractions } from '../../test-utils/ui-interactions.spec'; import { IgxStringFilteringOperand } from '../../data-operations/filtering-condition'; import { DefaultSortingStrategy } from '../../data-operations/sorting-strategy'; import { configureTestSuite } from '../../test-utils/configure-suite'; +import { IgxGridHeaderGroupComponent } from '../grid-header-group.component'; describe('IgxGrid - Column Pinning ', () => { configureTestSuite(); @@ -579,7 +580,7 @@ describe('IgxGrid - Column Pinning ', () => { fix.detectChanges(); const grid = fix.componentInstance.instance; - let headers = fix.debugElement.queryAll(By.directive(IgxGridHeaderComponent)); + let headers = fix.debugElement.queryAll(By.directive(IgxGridHeaderGroupComponent)); // First two headers are pinned expect(headers[0].componentInstance.zIndex).toEqual(9999); @@ -590,7 +591,7 @@ describe('IgxGrid - Column Pinning ', () => { fix.detectChanges(); // First three headers are pinned - headers = fix.debugElement.queryAll(By.directive(IgxGridHeaderComponent)); + headers = fix.debugElement.queryAll(By.directive(IgxGridHeaderGroupComponent)); expect(headers[2].componentInstance.zIndex).toEqual(9997); })); diff --git a/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid-indentation.spec.ts b/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid-indentation.spec.ts index e954d89bbe7..d72b9b32609 100644 --- a/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid-indentation.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid-indentation.spec.ts @@ -131,7 +131,7 @@ describe('IgxTreeGrid - Indentation', () => { fix.detectChanges(); const header = TreeGridFunctions.getHeaderCell(fix, 'ID'); - const resizer = header.query(By.css('.igx-grid__th-resize-handle')).nativeElement; + const resizer = header.parent.query(By.css('.igx-grid__th-resize-handle')).nativeElement; // Verify before resizing width expect((header.nativeElement).getBoundingClientRect().width).toBe(225); @@ -284,7 +284,7 @@ describe('IgxTreeGrid - Indentation', () => { fix.detectChanges(); const header = TreeGridFunctions.getHeaderCell(fix, 'ID'); - const resizer = header.query(By.css('.igx-grid__th-resize-handle')).nativeElement; + const resizer = header.parent.query(By.css('.igx-grid__th-resize-handle')).nativeElement; // Verify before resizing width expect((header.nativeElement).getBoundingClientRect().width).toBe(180); diff --git a/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid-integration.spec.ts b/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid-integration.spec.ts index b1c3cc1b26e..803d0cef869 100644 --- a/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid-integration.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/tree-grid/tree-grid-integration.spec.ts @@ -160,7 +160,7 @@ describe('IgxTreeGrid - Integration', () => { }); it('(UI) should autosize tree-column', () => { - const headerCell = TreeGridFunctions.getHeaderCell(fix, 'ID'); + const headerCell = TreeGridFunctions.getHeaderCell(fix, 'ID').parent; const column = treeGrid.columnList.filter(c => c.field === 'ID')[0]; column.resizable = true; @@ -271,7 +271,7 @@ describe('IgxTreeGrid - Integration', () => { }); it('(UI) should autosize tree-column', () => { - const headerCell = TreeGridFunctions.getHeaderCell(fix, 'ID'); + const headerCell = TreeGridFunctions.getHeaderCell(fix, 'ID').parent; const column = treeGrid.columnList.filter(c => c.field === 'ID')[0]; column.resizable = true; diff --git a/projects/igniteui-angular/src/lib/test-utils/tree-grid-functions.spec.ts b/projects/igniteui-angular/src/lib/test-utils/tree-grid-functions.spec.ts index 42aeb047a82..e9245df8c42 100644 --- a/projects/igniteui-angular/src/lib/test-utils/tree-grid-functions.spec.ts +++ b/projects/igniteui-angular/src/lib/test-utils/tree-grid-functions.spec.ts @@ -152,7 +152,8 @@ export class TreeGridFunctions { * Verifies that the specified column is the tree column, that contains the tree cells. */ public static verifyTreeColumn(fix, expectedTreeColumnKey, expectedColumnsCount) { - const headerCell = TreeGridFunctions.getHeaderCell(fix, expectedTreeColumnKey); + const headerCell = TreeGridFunctions.getHeaderCell(fix, expectedTreeColumnKey).parent; + const treeCells = TreeGridFunctions.getTreeCells(fix); const rows = TreeGridFunctions.getAllRows(fix); From ad4e781787a4bf7f4ce89502eb182f95a46042e9 Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Sun, 18 Nov 2018 11:50:38 +0200 Subject: [PATCH 09/24] feat(filtering): CD strategy for header group component #542 --- .../src/lib/grids/grid-header-group.component.ts | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts index e25faa7fa9f..50375605f60 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts @@ -5,7 +5,9 @@ import { ViewChild, QueryList, ViewChildren, - forwardRef + forwardRef, + ChangeDetectionStrategy, + ChangeDetectorRef } from '@angular/core'; import { IgxColumnComponent } from './column.component'; import { IgxFilteringService } from './filtering/grid-filtering.service'; @@ -16,11 +18,11 @@ import { IgxGridHeaderComponent } from './grid-header.component'; import { IgxGridFilteringCellComponent } from './filtering/grid-filtering-cell.component'; import { isIE } from '../core/utils'; - /** * @hidden */ @Component({ + changeDetection: ChangeDetectionStrategy.OnPush, preserveWhitespaces: false, selector: 'igx-grid-header-group', templateUrl: './grid-header-group.component.html' @@ -120,7 +122,14 @@ export class IgxGridHeaderGroupComponent { } - constructor(public gridAPI: GridBaseAPIService, + public ngDoCheck() { + if (this.column.columnGroup) { + this.cdr.markForCheck(); + } + } + + constructor(private cdr: ChangeDetectorRef, + public gridAPI: GridBaseAPIService, public colReszingService: IgxColumnResizingService, public filteringService: IgxFilteringService) { } From 1de81f5f021affce66b0b526f6793d7beba6d2ed Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Sun, 18 Nov 2018 18:39:17 +0200 Subject: [PATCH 10/24] feat(filtering): rework column moving dragGhost creation #542 --- .../core/styles/components/grid/_grid-theme.scss | 9 ++++----- .../lib/directives/dragdrop/dragdrop.directive.ts | 4 ++-- .../igniteui-angular/src/lib/grids/grid.common.ts | 15 ++++++++------- 3 files changed, 14 insertions(+), 14 deletions(-) diff --git a/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss b/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss index e811bace2e5..9da03fd9ec8 100644 --- a/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss +++ b/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss @@ -1172,12 +1172,12 @@ %grid__drag-ghost-image { position: absolute; - // display: flex; + display: flex; align-items: center; background-color: --var($theme, 'ghost-header-background'); color: --var($theme, 'ghost-header-text-color'); - // height: map-get($grid-header-height, 'comfortable'); - // min-height: map-get($grid-header-height, 'comfortable'); + height: map-get($grid-header-height, 'comfortable'); + min-height: map-get($grid-header-height, 'comfortable'); top: -99999px; left: -99999px; border: none; @@ -1211,14 +1211,13 @@ %grid__drag-ghost-image-icon { color: --var($theme, 'ghost-header-icon-color'); margin-right: rem(12px); - margin-bottom: rem(12px); } %grid__drag-ghost-image-icon-group { color: --var($theme, 'ghost-header-icon-color'); padding: --var($grid-header-padding, 'comfortable'); padding-right: 0; - // margin-right: rem(8); + margin-right: rem(8); } %igx-grid__drag-col-header { diff --git a/projects/igniteui-angular/src/lib/directives/dragdrop/dragdrop.directive.ts b/projects/igniteui-angular/src/lib/directives/dragdrop/dragdrop.directive.ts index 56a37b5eb40..62c844aac69 100644 --- a/projects/igniteui-angular/src/lib/directives/dragdrop/dragdrop.directive.ts +++ b/projects/igniteui-angular/src/lib/directives/dragdrop/dragdrop.directive.ts @@ -575,8 +575,8 @@ export class IgxDragDirective implements OnInit, OnDestroy { * Create dragGhost element - copy of the base element. Bind all needed events. * @param event Pointer event required when the dragGhost is being initialized. */ - protected createDragGhost(event) { - this._dragGhost = this.element.nativeElement.cloneNode(true); + protected createDragGhost(event, node = null) { + this._dragGhost = node ? node.cloneNode(true) : this.element.nativeElement.cloneNode(true); this._dragGhost.style.transitionDuration = '0.0s'; this._dragGhost.style.position = 'absolute'; this._dragGhost.style.top = this._dragStartY + 'px'; diff --git a/projects/igniteui-angular/src/lib/grids/grid.common.ts b/projects/igniteui-angular/src/lib/grids/grid.common.ts index 7fada2ccfc8..6e86a987365 100644 --- a/projects/igniteui-angular/src/lib/grids/grid.common.ts +++ b/projects/igniteui-angular/src/lib/grids/grid.common.ts @@ -323,7 +323,9 @@ export class IgxColumnMovingDragDirective extends IgxDragDirective { } protected createDragGhost(event) { - super.createDragGhost(event); + const index = this.column.grid.hasMovableColumns ? 1 : 0; + + super.createDragGhost(event, this.element.nativeElement.children[index]); let pageX, pageY; if (this.pointerEventsEnabled || !this.touchEventsEnabled) { @@ -334,8 +336,10 @@ export class IgxColumnMovingDragDirective extends IgxDragDirective { pageY = event.touches[0].pageY; } + this._dragGhost.style.height = null; this._dragGhost.style.minWidth = null; this._dragGhost.style.flexBasis = null; + this._dragGhost.style.position = null; const icon = document.createElement('i'); const text = document.createTextNode('block'); @@ -344,21 +348,18 @@ export class IgxColumnMovingDragDirective extends IgxDragDirective { icon.classList.add('material-icons'); this.cms.icon = icon; - const removeChildIndex = this.column.grid.hasMovableColumns ? 2 : 1; if (!this.column.columnGroup) { this.renderer.addClass(icon, this._dragGhostImgIconClass); - this._dragGhost.children[removeChildIndex].remove(); - this._dragGhost.children[removeChildIndex - 1].insertBefore(icon, this._dragGhost.children[removeChildIndex - 1].children[0]); + this._dragGhost.insertBefore(icon, this._dragGhost.firstElementChild); this.left = this._dragStartX = pageX - ((this._dragGhost.getBoundingClientRect().width / 3) * 2); this.top = this._dragStartY = pageY - ((this._dragGhost.getBoundingClientRect().height / 3) * 2); } else { - this._dragGhost.children[removeChildIndex].remove(); - this._dragGhost.insertBefore(icon, this._dragGhost.children[removeChildIndex - 1]); - this._dragGhost.style.display = 'flex'; + this._dragGhost.insertBefore(icon, this._dragGhost.childNodes[0]); this.renderer.addClass(icon, this._dragGhostImgIconGroupClass); + this._dragGhost.children[0].style.paddingLeft = '0px'; this.left = this._dragStartX = pageX - ((this._dragGhost.getBoundingClientRect().width / 3) * 2); this.top = this._dragStartY = pageY - ((this._dragGhost.getBoundingClientRect().height / 3) * 2); From 06f58f34245c97fa6e7583e26a692012dfc21d3d Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Sun, 18 Nov 2018 19:55:58 +0200 Subject: [PATCH 11/24] feat(filtering): minor fixes and improvements #542 --- .../src/lib/grids/cell.component.ts | 1 + .../lib/grids/grid-header-group.component.ts | 37 ++++++++----------- .../src/lib/grids/grid-navigation.service.ts | 4 +- .../lib/grids/grid/column-resizing.spec.ts | 2 +- 4 files changed, 19 insertions(+), 25 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/cell.component.ts b/projects/igniteui-angular/src/lib/grids/cell.component.ts index 3f3407d4eb0..ef57a983a3c 100644 --- a/projects/igniteui-angular/src/lib/grids/cell.component.ts +++ b/projects/igniteui-angular/src/lib/grids/cell.component.ts @@ -379,6 +379,7 @@ export class IgxGridCellComponent implements OnInit, AfterViewInit { * @memberof IgxGridCellComponent */ @HostBinding('style.min-width') + @HostBinding('style.max-width') @HostBinding('style.flex-basis') get width() { const hasVerticalScroll = !this.grid.verticalScrollContainer.dc.instance.notVirtual; diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts index 50375605f60..b858c1b3b71 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts @@ -7,7 +7,8 @@ import { ViewChildren, forwardRef, ChangeDetectionStrategy, - ChangeDetectorRef + ChangeDetectorRef, + DoCheck } from '@angular/core'; import { IgxColumnComponent } from './column.component'; import { IgxFilteringService } from './filtering/grid-filtering.service'; @@ -16,7 +17,6 @@ import { IgxGridBaseComponent } from './grid-base.component'; import { IgxColumnResizingService } from './grid-column-resizing.service'; import { IgxGridHeaderComponent } from './grid-header.component'; import { IgxGridFilteringCellComponent } from './filtering/grid-filtering-cell.component'; -import { isIE } from '../core/utils'; /** * @hidden @@ -27,7 +27,7 @@ import { isIE } from '../core/utils'; selector: 'igx-grid-header-group', templateUrl: './grid-header-group.component.html' }) -export class IgxGridHeaderGroupComponent { +export class IgxGridHeaderGroupComponent implements DoCheck { @Input() public column: IgxColumnComponent; @@ -47,18 +47,7 @@ export class IgxGridHeaderGroupComponent { @HostBinding('style.min-width') @HostBinding('style.flex-basis') get width() { - const colWidth = this.column.width; - const isNotPxInIE = isIE() && colWidth && typeof colWidth === 'string' && colWidth.indexOf('px') === -1; - - // a hack for fixing issue #2917, to be revised if ussue #1951 is ever fixed - if (isNotPxInIE && this.grid.pinnedColumns.length > 0) { - const firstContentCell = this.column.cells[0]; - if (firstContentCell) { - return firstContentCell.nativeElement.getBoundingClientRect().width + 'px'; - } - } - - return colWidth; + return this.column.width; } @HostBinding('class') @@ -72,7 +61,7 @@ export class IgxGridHeaderGroupComponent { 'igx-grid__th--pinned': this.isPinned, 'igx-grid__th--pinned-last': this.isLastPinned, 'igx-grid__drag-col-header': this.isHeaderDragged, - 'igx-grid__th--filtering': this.filteringService.filteredColumn === this.column + 'igx-grid__th--filtering': this.isFiltered }; Object.entries(classList).forEach(([klass, value]) => { @@ -95,20 +84,25 @@ export class IgxGridHeaderGroupComponent { return this.gridAPI.get(this.gridID); } - get isLastPinned() { + get isFiltered(): boolean { + return this.filteringService.filteredColumn === this.column; + } + + get isLastPinned(): boolean { const pinnedCols = this.grid.pinnedColumns; + if (pinnedCols.length === 0) { return false; - } else { - return pinnedCols.indexOf(this.column) === pinnedCols.length - 1; } + + return pinnedCols.indexOf(this.column) === pinnedCols.length - 1; } - get isPinned() { + get isPinned(): boolean { return this.column.pinned; } - get isHeaderDragged() { + get isHeaderDragged(): boolean { return this.grid.draggedColumn === this.column; } @@ -119,7 +113,6 @@ export class IgxGridHeaderGroupComponent { return pinnedCols.length > 0 && pinnedCols.indexOf(child) === pinnedCols.length - 1; }); } - } public ngDoCheck() { diff --git a/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts b/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts index c678b8a7fea..f41f30099ad 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts @@ -419,8 +419,8 @@ export class IgxGridNavigationService { this.grid.rowList.find(row => row instanceof IgxGridRowComponent).cells.first._clearCellSelection(); const visColLength = this.grid.unpinnedColumns.length; if (this.isColumnFullyVisible(visColLength - 1)) { - const lastFilterCell = this.grid.filterCellList[this.grid.filterCellList.length-1]; - lastFilterCell.focusChip(false); + const lastFilterCellIndex = this.grid.filterCellList.length - 1; + this.grid.filteringService.focusFilterCellChip(this.grid.filterCellList[lastFilterCellIndex].column, false); } else { this.grid.filteringService.columnToFocus = this.grid.unpinnedColumns[visColLength - 1]; this.grid.filteringService.shouldFocusNext = false; diff --git a/projects/igniteui-angular/src/lib/grids/grid/column-resizing.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/column-resizing.spec.ts index a66e6bd813e..2d4d7020863 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/column-resizing.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/column-resizing.spec.ts @@ -452,7 +452,7 @@ describe('IgxGrid - Deferred Column Resizing', () => { expect(grid.columns[1].width).toEqual('100px'); expect(grid.columns[2].width).toEqual('100px'); - const resizeArea = headers[1].children[1].nativeElement + const resizeArea = headers[1].children[1].nativeElement; UIInteractions.simulateMouseEvent('dblclick', resizeArea, 198, 5); tick(); fixture.detectChanges(); From 334c1a252dd4c70bea90015e0f4c77eeb633ea53 Mon Sep 17 00:00:00 2001 From: Borislav Kulov Date: Mon, 19 Nov 2018 17:13:49 +0200 Subject: [PATCH 12/24] chore(filtering): Change filtering components strategy to OnPush (#2938) --- .../grid-filtering-cell.component.ts | 11 +++++-- .../filtering/grid-filtering-row.component.ts | 31 ++++++++----------- .../src/lib/grids/grid-base.component.ts | 7 ++++- .../grids/grid-header-group.component.html | 14 ++++----- .../lib/grids/grid-header-group.component.ts | 20 ++++++------ .../src/lib/grids/grid-header.component.ts | 4 +-- 6 files changed, 47 insertions(+), 40 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts index 506073ba23b..ffe836665ae 100644 --- a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts +++ b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-cell.component.ts @@ -8,7 +8,9 @@ import { AfterViewInit, ElementRef, HostListener, - OnInit + OnInit, + ChangeDetectionStrategy, + DoCheck } from '@angular/core'; import { IgxColumnComponent } from '../column.component'; import { IFilteringExpression } from '../../data-operations/filtering-expression.interface'; @@ -22,11 +24,12 @@ import { IgxGridGroupByRowComponent } from '../grid'; * @hidden */ @Component({ + changeDetection: ChangeDetectionStrategy.OnPush, preserveWhitespaces: false, selector: 'igx-grid-filtering-cell', templateUrl: './grid-filtering-cell.component.html' }) -export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit { +export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit, DoCheck { private baseClass = 'igx-grid__filtering-cell-indicator'; private currentTemplate = null; @@ -73,6 +76,10 @@ export class IgxGridFilteringCellComponent implements AfterViewInit, OnInit { this.updateFilterCellArea(); } + public ngDoCheck() { + this.updateFilterCellArea(); + } + @HostListener('keydown.tab', ['$event']) public onTabKeyDown(eventArgs) { const pinnedColumns = this.filteringService.grid.pinnedColumns; diff --git a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-row.component.ts b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-row.component.ts index 508ad04c055..fd6986f25eb 100644 --- a/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-row.component.ts +++ b/projects/igniteui-angular/src/lib/grids/filtering/grid-filtering-row.component.ts @@ -5,12 +5,12 @@ import { Input, TemplateRef, ViewChild, - OnDestroy, ViewChildren, QueryList, ElementRef, HostBinding, - HostListener + HostListener, + ChangeDetectionStrategy } from '@angular/core'; import { Subject } from 'rxjs'; import { DataType } from '../../data-operations/data-util'; @@ -20,7 +20,6 @@ import { IFilteringOperation } from '../../data-operations/filtering-condition'; import { FilteringLogic, IFilteringExpression } from '../../data-operations/filtering-expression.interface'; import { HorizontalAlignment, VerticalAlignment, OverlaySettings } from '../../services/overlay/utilities'; import { ConnectedPositioningStrategy } from '../../services/overlay/position/connected-positioning-strategy'; -import { FilteringExpressionsTree } from '../../data-operations/filtering-expressions-tree'; import { IChipSelectEventArgs, IBaseChipEventArgs, IgxChipsAreaComponent, IgxChipComponent } from '../../chips'; import { ExpressionUI } from './grid-filtering.service'; import { IgxDropDownItemComponent } from '../../drop-down/drop-down-item.component'; @@ -32,11 +31,12 @@ import { AbsoluteScrollStrategy } from '../../services/overlay/scroll'; * @hidden */ @Component({ + changeDetection: ChangeDetectionStrategy.OnPush, preserveWhitespaces: false, selector: 'igx-grid-filtering-row', templateUrl: './grid-filtering-row.component.html' }) -export class IgxGridFilteringRowComponent implements AfterViewInit, OnDestroy { +export class IgxGridFilteringRowComponent implements AfterViewInit { private _positionSettings = { horizontalStartPoint: HorizontalAlignment.Left, @@ -59,8 +59,6 @@ export class IgxGridFilteringRowComponent implements AfterViewInit, OnDestroy { private chipsAreaWidth: number; private chipAreaScrollOffset = 0; - private conditionChanged = new Subject(); - private unaryConditionChanged = new Subject(); private _column = null; public showArrows: boolean; @@ -140,10 +138,7 @@ export class IgxGridFilteringRowComponent implements AfterViewInit, OnDestroy { @HostBinding('class.igx-grid__filtering-row') public cssClass = 'igx-grid__filtering-row'; - constructor(public filteringService: IgxFilteringService, public element: ElementRef, public cdr: ChangeDetectorRef) { - this.unaryConditionChanged.subscribe(() => this.unaryConditionChangedCallback()); - this.conditionChanged.subscribe(() => this.conditionChangedCallback()); - } + constructor(public filteringService: IgxFilteringService, public element: ElementRef, public cdr: ChangeDetectorRef) {} ngAfterViewInit() { this._conditionsOverlaySettings.outlet = this.column.grid.outletDirective; @@ -157,11 +152,6 @@ export class IgxGridFilteringRowComponent implements AfterViewInit, OnDestroy { this.input.nativeElement.focus(); } - ngOnDestroy() { - this.conditionChanged.unsubscribe(); - this.unaryConditionChanged.unsubscribe(); - } - @HostListener('keydown.shift.tab', ['$event']) @HostListener('keydown.tab', ['$event']) public onTabKeydown(event) { @@ -395,9 +385,11 @@ export class IgxGridFilteringRowComponent implements AfterViewInit, OnDestroy { const value = (eventArgs.newSelection as IgxDropDownItemComponent).value; this.expression.condition = this.getCondition(value); if (this.expression.condition.isUnary) { - this.unaryConditionChanged.next(value); + // update grid's filtering on the next cycle to ensure the drop-down is closed + // if the drop-down is not closed this event handler will be invoked multiple times + requestAnimationFrame(() => this.unaryConditionChangedCallback()); } else { - this.conditionChanged.next(value); + requestAnimationFrame(() => this.conditionChangedCallback()); } if (this.input) { @@ -464,7 +456,10 @@ export class IgxGridFilteringRowComponent implements AfterViewInit, OnDestroy { if (eventArgs.oldSelection) { expression.afterOperator = (eventArgs.newSelection as IgxDropDownItemComponent).value; this.expressionsList[this.expressionsList.indexOf(expression) + 1].beforeOperator = expression.afterOperator; - this.filter(); + + // update grid's filtering on the next cycle to ensure the drop-down is closed + // if the drop-down is not closed this event handler will be invoked multiple times + requestAnimationFrame(() => this.filter()); } } diff --git a/projects/igniteui-angular/src/lib/grids/grid-base.component.ts b/projects/igniteui-angular/src/lib/grids/grid-base.component.ts index c10102ccb82..ffc5eb79f5c 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-base.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-base.component.ts @@ -1165,7 +1165,7 @@ export abstract class IgxGridBaseComponent extends DisplayDensityBase implements * @memberof IgxGridBaseComponent */ get headerGroupsList(): IgxGridHeaderGroupComponent[] { - return flatten(this.headerGroups.toArray()); + return this.headerGroups ? flatten(this.headerGroups.toArray()) : []; } /** @@ -2758,6 +2758,11 @@ export abstract class IgxGridBaseComponent extends DisplayDensityBase implements if (this.rowList) { this.rowList.forEach((row) => row.cdr.markForCheck()); } + + if (this.filterCellList) { + this.filterCellList.forEach((c) => c.cdr.markForCheck()); + } + this.cdr.detectChanges(); } diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html index f59a18f2df0..ccd97e3af47 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html @@ -13,16 +13,16 @@ - -
+ [style.height.px]="colResizingService.resizerHeight" + [restrictHResizeMax]="colResizingService.restrictResizeMax" + [restrictHResizeMin]="colResizingService.restrictResizeMin" + [resizeEndTimeout]="colResizingService.resizeEndTimeout" + (resizeEnd)="colResizingService.resizeColumn($event)">
diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts index b858c1b3b71..f79a8b610a6 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts @@ -123,31 +123,31 @@ export class IgxGridHeaderGroupComponent implements DoCheck { constructor(private cdr: ChangeDetectorRef, public gridAPI: GridBaseAPIService, - public colReszingService: IgxColumnResizingService, + public colResizingService: IgxColumnResizingService, public filteringService: IgxFilteringService) { } public onResizeAreaMouseOver() { if (this.column.resizable) { - this.colReszingService.resizeCursor = 'col-resize'; + this.colResizingService.resizeCursor = 'col-resize'; } } public onResizeAreaMouseDown(event) { if (event.button === 0 && this.column.resizable) { - this.colReszingService.column = this.column; - this.colReszingService.showResizer = true; - this.colReszingService.isColumnResizing = true; - this.colReszingService.resizerHeight = this.column.grid.calcResizerHeight; - this.colReszingService.startResizePos = event.clientX; + this.colResizingService.column = this.column; + this.colResizingService.showResizer = true; + this.colResizingService.isColumnResizing = true; + this.colResizingService.resizerHeight = this.column.grid.calcResizerHeight; + this.colResizingService.startResizePos = event.clientX; } else { - this.colReszingService.resizeCursor = null; + this.colResizingService.resizeCursor = null; } } public autosizeColumnOnDblClick(event) { if (event.button === 0 && this.column.resizable) { - this.colReszingService.column = this.column; - this.colReszingService.autosizeColumnOnDblClick(); + this.colResizingService.column = this.column; + this.colResizingService.autosizeColumnOnDblClick(); } } } diff --git a/projects/igniteui-angular/src/lib/grids/grid-header.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header.component.ts index 3ed8319ace9..718532aecf8 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header.component.ts @@ -106,7 +106,7 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck { constructor( public gridAPI: GridBaseAPIService, - public colReszingService: IgxColumnResizingService, + public colResizingService: IgxColumnResizingService, public cdr: ChangeDetectorRef, public elementRef: ElementRef, public zone: NgZone, @@ -125,7 +125,7 @@ export class IgxGridHeaderComponent implements OnInit, DoCheck { @HostListener('click', ['$event']) public onClick(event) { - if (!this.colReszingService.isColumnResizing) { + if (!this.colResizingService.isColumnResizing) { event.stopPropagation(); if (this.grid.filteringService.isFilterRowVisible) { if (this.column.filterable && !this.column.columnGroup && From 0aec11c8fa0a735d00b6cc38bcb5f4aa8a67b73c Mon Sep 17 00:00:00 2001 From: Borislav Kulov Date: Mon, 19 Nov 2018 17:45:16 +0200 Subject: [PATCH 13/24] test(filtering): Fix failing tests (#2938) --- .../lib/grids/grid/grid-filtering-ui.spec.ts | 265 +++++++++++------- 1 file changed, 165 insertions(+), 100 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts index 765fceba024..158c0f23051 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts @@ -1,7 +1,7 @@ import { Component, ViewChild, DebugElement } from '@angular/core'; import { async, discardPeriodicTasks, fakeAsync, TestBed, tick } from '@angular/core/testing'; import { By } from '@angular/platform-browser'; -import { BrowserAnimationsModule } from '@angular/platform-browser/animations'; +import { BrowserAnimationsModule, NoopAnimationsModule } from '@angular/platform-browser/animations'; import { Calendar } from '../../calendar/calendar'; import { IgxInputDirective } from '../../directives/input/input.directive'; import { IgxGridComponent } from './grid.component'; @@ -25,7 +25,7 @@ import { IgxGridHeaderGroupComponent } from '../grid-header-group.component'; const FILTER_UI_ROW = 'igx-grid-filtering-row'; -describe('IgxGrid - Filtering actions', () => { +fdescribe('IgxGrid - Filtering actions', () => { configureTestSuite(); beforeEach(async(() => { TestBed.configureTestingModule({ @@ -34,6 +34,7 @@ describe('IgxGrid - Filtering actions', () => { ], imports: [ BrowserAnimationsModule, + NoopAnimationsModule, IgxGridModule.forRoot()] }) .compileComponents(); @@ -64,8 +65,8 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); const ddItems = ddList.nativeElement.children; @@ -75,9 +76,8 @@ describe('IgxGrid - Filtering actions', () => { verifyFilterUIPosition(filterUIRow, grid); ddItems[2].click(); - // select.nativeElement.dispatchEvent(new Event('change')); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -86,12 +86,12 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // ends with ddItems[3].click(); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -100,12 +100,12 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // does not contain ddItems[1].click(); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -114,12 +114,12 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // equals ddItems[0].click(); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -128,12 +128,12 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // does not equal ddItems[5].click(); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -142,12 +142,12 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // empty ddItems[6].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(4); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -158,12 +158,12 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // not empty ddItems[7].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(4); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -174,13 +174,13 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // iterate over unary conditions // null ddItems[8].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(3); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -191,12 +191,12 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // not null ddItems[9].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(5); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -205,13 +205,13 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // changing from unary to not unary condition when input is empty - filtering should keep its state // contains ddItems[0].click(); + tick(100); fix.detectChanges(); - tick(); input = filterUIRow.query(By.directive(IgxInputDirective)); expect(grid.rowList.length).toEqual(5); @@ -242,21 +242,17 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); const ddItems = ddList.nativeElement.children; - filterIcon.nativeElement.click(); - fix.detectChanges(); - tick(100); - // iterate over not unary conditions and fill the input // contains sendInput(input, 'Ignite', fix); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(2); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -265,12 +261,12 @@ describe('IgxGrid - Filtering actions', () => { // starts with ddItems[2].click(); + tick(100); fix.detectChanges(); - tick(); sendInput(input, 'Net', fix); - fix.detectChanges(); tick(); + fix.detectChanges(); verifyFilterUIPosition(filterUIRow, grid); expect(grid.rowList.length).toEqual(1); @@ -282,16 +278,16 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // ends with ddItems[3].click(); + tick(100); fix.detectChanges(); - tick(); sendInput(input, 'script', fix); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(2); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -300,12 +296,12 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // does not contain ddItems[1].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(6); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -314,8 +310,8 @@ describe('IgxGrid - Filtering actions', () => { // use reset button reset.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -324,16 +320,16 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // equals ddItems[4].click(); + tick(100); fix.detectChanges(); - tick(); sendInput(input, 'NetAdvantage', fix); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(1); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -342,16 +338,16 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // equals ddItems[4].click(); + tick(100); fix.detectChanges(); - tick(); sendInput(input, ' ', fix); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(0); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -362,16 +358,16 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // does not equal ddItems[5].click(); + tick(100); fix.detectChanges(); - tick(); sendInput(input, 'NetAdvantage', fix); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(7); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -401,8 +397,8 @@ describe('IgxGrid - Filtering actions', () => { expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeTruthy(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); const ddItems = ddList.nativeElement.children; @@ -412,8 +408,8 @@ describe('IgxGrid - Filtering actions', () => { // iterate over not unary conditions and fill the input // equals sendInput(input, 0, fix); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(1); expect(grid.getCellByColumn(0, 'Downloads').value).toEqual(0); @@ -424,24 +420,32 @@ describe('IgxGrid - Filtering actions', () => { // clear input value GridFunctions.removeFilterChipByIndex(0, filterUIRow); - fix.detectChanges(); tick(); + fix.detectChanges(); // iterate over not unary conditions when input is empty + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // does not equal ddItems[1].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeTruthy(); expect(input.nativeElement.offsetHeight).toBeGreaterThan(0); + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // greater than ddItems[2].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -449,40 +453,56 @@ describe('IgxGrid - Filtering actions', () => { expect(input.nativeElement.offsetHeight).toBeGreaterThan(0); // iterate over unary conditions - // null + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); + // empty ddItems[6].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(1); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(input.nativeElement.offsetHeight).toBeGreaterThan(0); - // not null + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); + // not empty ddItems[7].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(7); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(input.nativeElement.offsetHeight).toBeGreaterThan(0); - // empty + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); + // null ddItems[8].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(1); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(input.nativeElement.offsetHeight).toBeGreaterThan(0); - // not empty + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); + // not null ddItems[9].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(7); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -490,10 +510,14 @@ describe('IgxGrid - Filtering actions', () => { expect(input.nativeElement.offsetHeight).toBeGreaterThan(0); // changing from unary to not unary condition when input is empty - filtering should keep its state + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // equals - filter should keep its state and not be reset ddItems[0].click(); + tick(100); fix.detectChanges(); - tick(); input = filterUIRow.query(By.directive(IgxInputDirective)); expect(grid.rowList.length).toEqual(7); @@ -505,8 +529,8 @@ describe('IgxGrid - Filtering actions', () => { // iterate over not unary conditions and fill the input // equals sendInput(input, 100, fix); - fix.detectChanges(); tick(); + fix.detectChanges(); clear = filterUIRow.query(By.css('igx-suffix')); expect(grid.rowList.length).toEqual(1); @@ -516,24 +540,32 @@ describe('IgxGrid - Filtering actions', () => { expect(clear.nativeElement.offsetHeight).toBeGreaterThan(0); expect(input.nativeElement.offsetHeight).toBeGreaterThan(0); + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // does not equal ddItems[1].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(7); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(input.nativeElement.offsetHeight).toBeGreaterThan(0); + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // greater than ddItems[2].click(); + tick(100); fix.detectChanges(); - tick(); sendInput(input, 300, fix); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(2); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -542,8 +574,8 @@ describe('IgxGrid - Filtering actions', () => { // use reset button reset.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -553,16 +585,16 @@ describe('IgxGrid - Filtering actions', () => { // open dropdown filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); // less than ddItems[3].click(); + tick(100); fix.detectChanges(); - tick(); sendInput(input, 100, fix); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(3); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -572,8 +604,8 @@ describe('IgxGrid - Filtering actions', () => { GridFunctions.removeFilterChipByIndex(0, filterUIRow); clear.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -582,24 +614,32 @@ describe('IgxGrid - Filtering actions', () => { // revert to the default after expect(filterIcon.componentInstance.iconName).toMatch('equals'); + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // greater than or equal to ddItems[4].click(); + tick(100); fix.detectChanges(); - tick(); sendInput(input, 254, fix); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(3); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(input.nativeElement.offsetHeight).toBeGreaterThan(0); + // open dropdown + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // less than or equal to ddItems[5].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(6); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); @@ -625,8 +665,8 @@ describe('IgxGrid - Filtering actions', () => { expect(grid.rowList.length).toEqual(8); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); const ddItems = ddList.nativeElement.children; @@ -635,8 +675,8 @@ describe('IgxGrid - Filtering actions', () => { // false condition ddItems[2].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(2); expect(grid.getCellByColumn(0, 'Released').value).toBeFalsy(); @@ -644,10 +684,13 @@ describe('IgxGrid - Filtering actions', () => { expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // true condition ddItems[1].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(3); expect(grid.getCellByColumn(0, 'Released').value).toBe(true); @@ -656,19 +699,25 @@ describe('IgxGrid - Filtering actions', () => { expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // (all) condition ddItems[0].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(8); expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // empty condition ddItems[3].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(3); expect(grid.getCellByColumn(0, 'Released').value).toEqual(null); @@ -677,10 +726,13 @@ describe('IgxGrid - Filtering actions', () => { expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // not empty condition ddItems[4].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(5); expect(grid.getCellByColumn(0, 'Released').value).toBe(false); @@ -691,10 +743,13 @@ describe('IgxGrid - Filtering actions', () => { expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // null condition ddItems[5].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(2); expect(grid.getCellByColumn(0, 'Released').value).toEqual(null); @@ -702,10 +757,13 @@ describe('IgxGrid - Filtering actions', () => { expect(close.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); expect(reset.nativeElement.classList.contains('igx-button--disabled')).toBeFalsy(); + filterIcon.nativeElement.click(); + tick(); + fix.detectChanges(); // not null condition ddItems[6].click(); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(6); expect(grid.getCellByColumn(0, 'Released').value).toBe(false); @@ -719,61 +777,66 @@ describe('IgxGrid - Filtering actions', () => { })); // UI tests date column - it('UI - should correctly filter date column by \'today\' filtering conditions', () => { + it('UI - should correctly filter date column by \'today\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); - fix.detectChanges(); verifyFilterUIPosition(filterUIRow, grid); GridFunctions.selectFilteringCondition('Today', ddList); + tick(100); fix.detectChanges(); // only one record is populated with 'today' date, this is why rows must be 1 expect(grid.rowList.length).toEqual(1); - }); + })); - it('UI - should correctly filter date column by \'yesterday\' filtering conditions', () => { + it('UI - should correctly filter date column by \'yesterday\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); - fix.detectChanges(); verifyFilterUIPosition(filterUIRow, grid); GridFunctions.selectFilteringCondition('Yesterday', ddList); + tick(100); fix.detectChanges(); // only one record is populated with (today - 1 day) date, this is why rows must be 1 expect(grid.rowList.length).toEqual(1); - }); + })); - it('UI - should correctly filter date column by \'this month\' filtering conditions', () => { + it('UI - should correctly filter date column by \'this month\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); @@ -783,25 +846,26 @@ describe('IgxGrid - Filtering actions', () => { // Fill expected results based on the current date fillExpectedResults(grid, cal, today); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); verifyFilterUIPosition(filterIcon, grid); GridFunctions.selectFilteringCondition('This Month', ddList); + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(expectedResults[5]); - }); + })); - it('UI - should correctly filter date column by \'next month\' filtering conditions', () => { + it('UI - should correctly filter date column by \'next month\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); @@ -811,26 +875,27 @@ describe('IgxGrid - Filtering actions', () => { // Fill expected results based on the current date fillExpectedResults(grid, cal, today); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); + const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Next Month', ddList); - + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(expectedResults[1]); - }); + })); - it('UI - should correctly filter date column by \'last month\' filtering conditions', () => { + fit('UI - should correctly filter date column by \'last month\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); @@ -840,18 +905,18 @@ describe('IgxGrid - Filtering actions', () => { // Fill expected results based on the current date fillExpectedResults(grid, cal, today); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); + const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Last Month', ddList); - + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(expectedResults[0]); - }); + })); it('UI - should correctly filter date column by \'empty\' filtering conditions', () => { const fix = TestBed.createComponent(IgxGridFilteringComponent); From e1f3c4cfbd3398806eac81728a8af02e1751ef30 Mon Sep 17 00:00:00 2001 From: Borislav Kulov Date: Mon, 19 Nov 2018 18:21:09 +0200 Subject: [PATCH 14/24] test(filtering): Fix filtering UI tests (#2938) --- .../lib/grids/grid/grid-filtering-ui.spec.ts | 186 ++++++++++-------- 1 file changed, 100 insertions(+), 86 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts index 158c0f23051..fdcf565bec6 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts @@ -25,7 +25,7 @@ import { IgxGridHeaderGroupComponent } from '../grid-header-group.component'; const FILTER_UI_ROW = 'igx-grid-filtering-row'; -fdescribe('IgxGrid - Filtering actions', () => { +describe('IgxGrid - Filtering actions', () => { configureTestSuite(); beforeEach(async(() => { TestBed.configureTestingModule({ @@ -888,7 +888,7 @@ fdescribe('IgxGrid - Filtering actions', () => { expect(grid.rowList.length).toEqual(expectedResults[1]); })); - fit('UI - should correctly filter date column by \'last month\' filtering conditions', fakeAsync(() => { + it('UI - should correctly filter date column by \'last month\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); @@ -918,105 +918,113 @@ fdescribe('IgxGrid - Filtering actions', () => { expect(grid.rowList.length).toEqual(expectedResults[0]); })); - it('UI - should correctly filter date column by \'empty\' filtering conditions', () => { + it('UI - should correctly filter date column by \'empty\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); + const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Empty', ddList); + tick(100); fix.detectChanges(); - expect(grid.rowList.length).toEqual(2); - }); + })); - it('UI - should correctly filter date column by \'notEmpty\' filtering conditions', () => { + it('UI - should correctly filter date column by \'notEmpty\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); + const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Not Empty', ddList); + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(6); - }); + })); - it('UI - should correctly filter date column by \'null\' filtering conditions', () => { + it('UI - should correctly filter date column by \'null\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); + const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Null', ddList); + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(1); - }); + })); - it('UI - should correctly filter date column by \'notNull\' filtering conditions', () => { + it('UI - should correctly filter date column by \'notNull\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); + const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Not Null', ddList); + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(7); - }); + })); - it('UI - should correctly filter date column by \'thisYear\' filtering conditions', () => { + it('UI - should correctly filter date column by \'thisYear\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); @@ -1026,25 +1034,26 @@ fdescribe('IgxGrid - Filtering actions', () => { // Fill expected results based on the current date fillExpectedResults(grid, cal, today); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); + const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('This Year', ddList); + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(expectedResults[2]); - }); + })); - it('UI - should correctly filter date column by \'lastYear\' filtering conditions', () => { + it('UI - should correctly filter date column by \'lastYear\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); @@ -1054,25 +1063,27 @@ fdescribe('IgxGrid - Filtering actions', () => { // Fill expected results based on the current date fillExpectedResults(grid, cal, today); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); + const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Last Year', ddList); + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(expectedResults[4]); - }); + })); - it('UI - should correctly filter date column by \'nextYear\' filtering conditions', () => { + it('UI - should correctly filter date column by \'nextYear\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); @@ -1082,17 +1093,18 @@ fdescribe('IgxGrid - Filtering actions', () => { // Fill expected results based on the current date fillExpectedResults(grid, cal, today); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); + const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Next Year', ddList); + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(expectedResults[3]); - }); + })); it('UI - should correctly filter date column by \'equals\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); @@ -1101,33 +1113,32 @@ fdescribe('IgxGrid - Filtering actions', () => { const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); const input = filterUIRow.query(By.directive(IgxInputDirective)); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); verifyFilterUIPosition(filterIcon, grid); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Equals', ddList); input.nativeElement.click(); + tick(100); fix.detectChanges(); - tick(); const calendar = fix.debugElement.query(By.css('igx-calendar')); const currentDay = calendar.query(By.css('span.igx-calendar__date--current')); currentDay.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); input.nativeElement.dispatchEvent(new Event('change')); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(1); })); @@ -1139,33 +1150,32 @@ fdescribe('IgxGrid - Filtering actions', () => { const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); const input = filterUIRow.query(By.directive(IgxInputDirective)); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); - tick(100); + tick(); + fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); - fix.detectChanges(); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Does Not Equal', ddList); input.nativeElement.click(); + tick(100); fix.detectChanges(); - tick(); const calendar = fix.debugElement.query(By.css('igx-calendar')); const currentDay = calendar.query(By.css('span.igx-calendar__date--current')); currentDay.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); input.nativeElement.dispatchEvent(new Event('change')); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(7); })); @@ -1177,33 +1187,33 @@ fdescribe('IgxGrid - Filtering actions', () => { const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); const input = filterUIRow.query(By.directive(IgxInputDirective)); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); verifyFilterUIPosition(filterIcon, grid); + const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('After', ddList); input.nativeElement.click(); + tick(100); fix.detectChanges(); - tick(); const calendar = fix.debugElement.query(By.css('igx-calendar')); const currentDay = calendar.query(By.css('span.igx-calendar__date--current')); currentDay.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); input.nativeElement.dispatchEvent(new Event('change')); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(3); })); @@ -1215,33 +1225,32 @@ fdescribe('IgxGrid - Filtering actions', () => { const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); const input = filterUIRow.query(By.directive(IgxInputDirective)); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); verifyFilterUIPosition(filterIcon, grid); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Before', ddList); input.nativeElement.click(); + tick(100); fix.detectChanges(); - tick(); const calendar = fix.debugElement.query(By.css('igx-calendar')); const currentDay = calendar.query(By.css('span.igx-calendar__date--current')); currentDay.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); input.nativeElement.dispatchEvent(new Event('change')); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(2); })); @@ -1251,31 +1260,30 @@ fdescribe('IgxGrid - Filtering actions', () => { fix.detectChanges(); const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); const input = filterUIRow.query(By.directive(IgxInputDirective)); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); input.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); let calendar = fix.debugElement.query(By.css('igx-calendar')); const monthView = calendar.queryAll(By.css('.date__el'))[0]; monthView.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); const firstMonth = calendar.queryAll(By.css('.igx-calendar__month'))[0]; firstMonth.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); calendar = fix.debugElement.query(By.css('igx-calendar')); const month = calendar.queryAll(By.css('.date__el'))[0]; @@ -1288,31 +1296,30 @@ fdescribe('IgxGrid - Filtering actions', () => { fix.detectChanges(); const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); const input = filterUIRow.query(By.directive(IgxInputDirective)); - filterIcon.triggerEventHandler('mousedown', null); - fix.detectChanges(); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); input.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); let calendar = fix.debugElement.query(By.css('igx-calendar')); const monthView = calendar.queryAll(By.css('.date__el'))[1]; monthView.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); const firstMonth = calendar.queryAll(By.css('.igx-calendar__year'))[0]; firstMonth.nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); calendar = fix.debugElement.query(By.css('igx-calendar')); const month = calendar.queryAll(By.css('.date__el'))[1]; @@ -1331,6 +1338,7 @@ fdescribe('IgxGrid - Filtering actions', () => { const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[5].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); @@ -1342,18 +1350,18 @@ fdescribe('IgxGrid - Filtering actions', () => { expect(grid.rowList.length).toEqual(8); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); sendInput(input, 'a', fix); - fix.detectChanges(); tick(); + fix.detectChanges(); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); // false condition GridFunctions.selectFilteringCondition('False', ddList); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(1); expect(grid.getCellByColumn(0, 'AnotherField').value).toMatch('custom'); @@ -1370,6 +1378,7 @@ fdescribe('IgxGrid - Filtering actions', () => { const columnName = 'ProductName'; grid.filter(columnName, filterVal, IgxStringFilteringOperand.instance().condition('contains')); + tick(100); fix.detectChanges(); const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); @@ -1378,15 +1387,17 @@ fdescribe('IgxGrid - Filtering actions', () => { spyOn(grid.onFilteringDone, 'emit'); idCellChips[0].nativeElement.click(); + tick(); fix.detectChanges(); + const filterUiRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const reset = filterUiRow.queryAll(By.css('button'))[0]; const input = filterUiRow.query(By.directive(IgxInputDirective)); sendInput(input, filterVal, fix); reset.nativeElement.dispatchEvent(new MouseEvent('click')); - fix.detectChanges(); tick(100); + fix.detectChanges(); expect(grid.onFilteringDone.emit).toHaveBeenCalledWith(null); })); @@ -1396,12 +1407,13 @@ fdescribe('IgxGrid - Filtering actions', () => { fix.detectChanges(); const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[1].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); UIInteractions.clickElement(filterIcon); - tick(50); + tick(); fix.detectChanges(); // apply two filters for And/Or button @@ -1410,7 +1422,7 @@ fdescribe('IgxGrid - Filtering actions', () => { const andButton = fix.debugElement.queryAll(By.css('#operand')); - tick(50); + tick(100); fix.detectChanges(); expect(andButton.length).toEqual(1); @@ -1425,6 +1437,7 @@ fdescribe('IgxGrid - Filtering actions', () => { const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[1].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); @@ -1432,21 +1445,18 @@ fdescribe('IgxGrid - Filtering actions', () => { expect(grid.rowList.length).toEqual(8); filterIcon.nativeElement.click(); + tick(); fix.detectChanges(); - tick(100); verifyFilterUIPosition(filterUIRow, grid); GridFunctions.filterBy('Contains', 'I', fix); + tick(100); fix.detectChanges(); - tick(); - - fix.detectChanges(); - tick(); GridFunctions.filterBy('Contains', 'g', fix); + tick(100); fix.detectChanges(); - tick(); expect(grid.rowList.length).toEqual(2); let andButton = fix.debugElement.queryAll(By.css('#operand')); @@ -1455,8 +1465,8 @@ fdescribe('IgxGrid - Filtering actions', () => { // remove the second chip const secondChip = filterUIRow.queryAll(By.css('igx-chip'))[1]; secondChip.query(By.css('div.igx-chip__remove')).nativeElement.click(); - fix.detectChanges(); tick(); + fix.detectChanges(); expect(grid.rowList.length).toEqual(3); andButton = fix.debugElement.queryAll(By.css('#operand')); @@ -1471,10 +1481,12 @@ fdescribe('IgxGrid - Filtering actions', () => { const columnName = 'ProductName'; const filterValue = 'search'; grid.filter(columnName, filterValue, IgxStringFilteringOperand.instance().condition('contains')); + tick(100); fix.detectChanges(); const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[1].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const input = filterUIRow.query(By.directive(IgxInputDirective)); @@ -1487,8 +1499,8 @@ fdescribe('IgxGrid - Filtering actions', () => { clearSuffix.nativeElement.dispatchEvent(new MouseEvent('click')); GridFunctions.simulateKeyboardEvent(input, 'keydown', 'Enter'); - fix.detectChanges(); tick(100); + fix.detectChanges(); const columnFilteringExpressionsTree = grid.filteringExpressionsTree.find(columnName); expect(grid.onFilteringDone.emit).toHaveBeenCalledWith(columnFilteringExpressionsTree); @@ -1503,6 +1515,7 @@ fdescribe('IgxGrid - Filtering actions', () => { const headerOfTypeNumber = gridheaders.find(gh => gh.nativeElement.classList.contains('igx-grid__th--number')); const filterCellsForTypeNumber = headerOfTypeNumber.parent.query(By.css('igx-grid-filtering-cell')); filterCellsForTypeNumber.query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); const filterUiRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); @@ -1510,21 +1523,19 @@ fdescribe('IgxGrid - Filtering actions', () => { const input = filterUiRow.query(By.directive(IgxInputDirective)); filterIcon.nativeElement.click(); - fix.detectChanges(); tick(); fix.detectChanges(); sendInput(input, 0, fix); - fix.detectChanges(); tick(); fix.detectChanges(); grid.nativeElement.click(); - fix.detectChanges(); tick(); fix.detectChanges(); filterUiRow.queryAll(By.css('button'))[1].nativeElement.click(); + tick(); fix.detectChanges(); expect(filterCellsForTypeNumber.queryAll(By.css('.igx-filtering-chips')).length).toBe(1); })); @@ -1545,20 +1556,23 @@ fdescribe('IgxGrid - Filtering actions', () => { filteringExpressionsTree.filteringOperands.push(expression); grid.filteringExpressionsTree = filteringExpressionsTree; + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(2); const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[1].query(By.css('igx-chip')).nativeElement.click(); + tick(); fix.detectChanges(); + const filterUIContainer = fix.debugElement.queryAll(By.css(FILTER_UI_ROW))[0]; const filterIcon = filterUIContainer.query(By.css('igx-icon')); const input = filterUIContainer.query(By.directive(IgxInputDirective)); filterIcon.nativeElement.click(); - fix.detectChanges(); tick(100); + fix.detectChanges(); verifyFilterUIPosition(filterUIContainer, grid); From f100af804f643c7ee47d2cc99bcdb44ed19a4700 Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Tue, 20 Nov 2018 10:31:16 +0200 Subject: [PATCH 15/24] test(filtering): filtering UI tests refactoring #542 --- .../lib/grids/grid/grid-filtering-ui.spec.ts | 140 ++++++++++-------- .../src/lib/test-utils/grid-functions.spec.ts | 8 +- 2 files changed, 85 insertions(+), 63 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts index fdcf565bec6..db56ed8b85a 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts @@ -1592,40 +1592,31 @@ describe('IgxGrid - Filtering Row UI actions', () => { IgxGridFilteringMCHComponent ], imports: [ - BrowserAnimationsModule, + NoopAnimationsModule, IgxGridModule.forRoot()] - }) - .compileComponents(); + }).compileComponents(); })); afterEach(() => { UIInteractions.clearOverlay(); }); - // TODO - add new tests based on the test plan in the spec. - it('should render Filter chip for filterable columns and render empty cell for a column when filterable is set to false', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); - tick(100); + const grid = fix.componentInstance.grid; grid.width = '1500px'; fix.detectChanges(); + const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); const filteringChips = fix.debugElement.queryAll(By.css('.igx-filtering-chips')); expect(filteringCells.length).toBe(6); expect(filteringChips.length).toBe(5); - let idCellChips = filteringCells[0].queryAll(By.css('.igx-filtering-chips')); + const idCellChips = filteringCells[0].queryAll(By.css('.igx-filtering-chips')); expect(idCellChips.length).toBe(0); - - grid.getColumnByName('ID').filterable = true; - fix.detectChanges(); - tick(100); - - idCellChips = filteringCells[0].queryAll(By.css('.igx-filtering-chips')); - expect(idCellChips.length).toBe(1); })); it('should render correct input and dropdown in filter row for different column types', fakeAsync(() => { @@ -1640,7 +1631,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { // open for string stringCellChip.nativeElement.click(); fix.detectChanges(); - tick(200); checkUIForType('string', fix.debugElement); @@ -1648,40 +1638,44 @@ describe('IgxGrid - Filtering Row UI actions', () => { let filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); let close = filterUIRow.queryAll(By.css('button'))[1]; close.nativeElement.click(); + tick(100); fix.detectChanges(); - tick(200); // open for number numberCellChip.nativeElement.click(); fix.detectChanges(); - tick(200); checkUIForType('number', fix.debugElement); // close filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); close = filterUIRow.queryAll(By.css('button'))[1]; close.nativeElement.click(); + tick(100); fix.detectChanges(); - tick(200); // open for date dateCellChip.nativeElement.click(); fix.detectChanges(); - tick(200); checkUIForType('date', fix.debugElement); // close filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); close = filterUIRow.queryAll(By.css('button'))[1]; close.nativeElement.click(); + tick(100); fix.detectChanges(); - tick(200); // open for bool boolCellChip.nativeElement.click(); fix.detectChanges(); - tick(200); checkUIForType('bool', fix.debugElement); + + // close + filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); + close = filterUIRow.queryAll(By.css('button'))[1]; + close.nativeElement.click(); + tick(100); + fix.detectChanges(); })); it('should apply multiple conditions to grid immediately while the filter row is still open', fakeAsync(() => { @@ -1694,11 +1688,12 @@ describe('IgxGrid - Filtering Row UI actions', () => { const boolCellChip = filteringCells[3].query(By.css('igx-chip')); const dateCellChip = filteringCells[4].query(By.css('igx-chip')); const grid = fix.componentInstance.grid; + // open for string stringCellChip.nativeElement.click(); - tick(); fix.detectChanges(); + GridFunctions.filterBy('Starts With', 'I', fix); expect(grid.rowList.length).toEqual(2); GridFunctions.filterBy('Ends With', 'r', fix); @@ -1708,9 +1703,9 @@ describe('IgxGrid - Filtering Row UI actions', () => { GridFunctions.resetFilterRow(fix); GridFunctions.closeFilterRow(fix); + // open for number numberCellChip.nativeElement.click(); - tick(); fix.detectChanges(); GridFunctions.filterBy('Less Than', '100', fix); @@ -1721,9 +1716,10 @@ describe('IgxGrid - Filtering Row UI actions', () => { // Reset and Close GridFunctions.resetFilterRow(fix); GridFunctions.closeFilterRow(fix); + + // open for bool boolCellChip.nativeElement.click(); - tick(); fix.detectChanges(); GridFunctions.filterBy('False', '', fix); @@ -1738,6 +1734,7 @@ describe('IgxGrid - Filtering Row UI actions', () => { // open for date dateCellChip.nativeElement.click(); fix.detectChanges(); + GridFunctions.filterBy('Today', '', fix); expect(grid.rowList.length).toEqual(1); GridFunctions.filterBy('Null', '', fix); @@ -1757,7 +1754,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { for (let i = 0; i < 10; i++) { GridFunctions.filterBy('Starts With', 'I', fix); - tick(200); } const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const startArrow = filterUIRow.query(By.css('.igx-grid__filtering-row-scroll-start')); @@ -1770,13 +1766,15 @@ describe('IgxGrid - Filtering Row UI actions', () => { it('should update UI when chip is removed from header cell.', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); + let filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); let stringCellChip = filteringCells[1].query(By.css('igx-chip')); const grid = fix.componentInstance.grid; + // filter string col stringCellChip.nativeElement.click(); - tick(); fix.detectChanges(); + GridFunctions.filterBy('Starts With', 'I', fix); expect(grid.rowList.length).toEqual(2); @@ -1788,7 +1786,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { // remove chip const removeButton = stringCellChip.query(By.css('div.igx-chip__remove')); removeButton.nativeElement.click(); - tick(); fix.detectChanges(); expect(grid.rowList.length).toEqual(8); @@ -1797,20 +1794,22 @@ describe('IgxGrid - Filtering Row UI actions', () => { it('should update UI when chip is removed from filter row.', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); + const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); const stringCellChip = filteringCells[1].query(By.css('igx-chip')); const grid = fix.componentInstance.grid; + // filter string col stringCellChip.nativeElement.click(); - tick(); fix.detectChanges(); + GridFunctions.filterBy('Starts With', 'I', fix); expect(grid.rowList.length).toEqual(2); // remove from row const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); GridFunctions.removeFilterChipByIndex(0, filterUIRow); - tick(); + tick(100); fix.detectChanges(); expect(grid.rowList.length).toEqual(8); @@ -1820,22 +1819,26 @@ describe('IgxGrid - Filtering Row UI actions', () => { fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); + let filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); const stringCellChip = filteringCells[1].query(By.css('igx-chip')); const grid = fix.componentInstance.grid; + // filter string col stringCellChip.nativeElement.click(); - tick(); fix.detectChanges(); + GridFunctions.filterBy('Starts With', 'I', fix); - // remote text from input + + // remove text from input const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const input = filterUIRow.query(By.directive(IgxInputDirective)); input.nativeElement.value = null; + const exprList = filterUIRow.componentInstance.expressionsList; exprList[0].expression.searchVal = null; - tick(); fix.detectChanges(); + GridFunctions.closeFilterRow(fix); // check no condition is applied @@ -1888,28 +1891,24 @@ describe('IgxGrid - Filtering Row UI actions', () => { fix.detectChanges(); checkUIForType('string', fix.debugElement); - tick(200); // Click on number column. numberHeader.nativeElement.click(); fix.detectChanges(); checkUIForType('number', fix.debugElement); - tick(200); // Click on boolean column boolHeader.nativeElement.click(); fix.detectChanges(); checkUIForType('bool', fix.debugElement); - tick(200); // Click on date column dateHeader.nativeElement.click(); fix.detectChanges(); checkUIForType('date', fix.debugElement); - tick(200); })); it('Should correctly render read-only input when selecting read-only condition and should create a chip.', fakeAsync(() => { @@ -1996,7 +1995,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { expect(filterChip.componentInstance.selected).toBeTruthy(); GridFunctions.filterBy('Starts With', 'S', fix); - tick(200); fix.detectChanges(); expect(grid.rowList.length).toEqual(1); @@ -2055,6 +2053,7 @@ describe('IgxGrid - Filtering Row UI actions', () => { grid.width = '1600px'; grid.columnWidth = '400px'; fix.detectChanges(); + const filteringExpressionsTree = new FilteringExpressionsTree(FilteringLogic.And, 'ProductName'); const expression = { fieldName: 'ProductName', @@ -2070,7 +2069,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { filteringExpressionsTree.filteringOperands.push(expression1); grid.filter('ProductName', null, filteringExpressionsTree); grid.filter('Released', true, IgxBooleanFilteringOperand.instance().condition('false')); - tick(); fix.detectChanges(); expect(grid.rowList.length).toEqual(0); @@ -2101,14 +2099,16 @@ describe('IgxGrid - Filtering Row UI actions', () => { fix.detectChanges(); let filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); + const stringCellChip = filteringCells[1].query(By.css('igx-chip')); // filter string col stringCellChip.nativeElement.click(); - tick(); fix.detectChanges(); + GridFunctions.filterBy('Starts With', 'IgniteUI', fix); GridFunctions.filterBy('Contains', 'for', fix); GridFunctions.closeFilterRow(fix); + // check 1 chip and view more icon is displayed. const chips = filteringCells[1].queryAll(By.css('igx-chip')); expect(chips.length).toEqual(1); @@ -2134,7 +2134,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { ]; gridFilteringExpressionsTree.filteringOperands.push(columnsFilteringTree); grid.filteringExpressionsTree = gridFilteringExpressionsTree; - tick(); fix.detectChanges(); const colChips = GridFunctions.getFilterChipsForColumn('ProductName', fix); @@ -2162,9 +2161,9 @@ describe('IgxGrid - Filtering Row UI actions', () => { const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); const stringCellChip = filteringCells[1].query(By.css('igx-chip')); + // filter string col stringCellChip.nativeElement.click(); - tick(); fix.detectChanges(); const filteringRow = fix.debugElement.query(By.directive(IgxGridFilteringRowComponent)); @@ -2187,7 +2186,7 @@ describe('IgxGrid - Filtering Row UI actions', () => { expect(cellElem.offsetParent.offsetHeight + cellElem.offsetHeight).toBeCloseTo(thead.clientHeight, 10); idCellChip.nativeElement.click(); - tick(); + // tick(); fix.detectChanges(); // check if it is positioned at the bottom of the thead. @@ -2198,7 +2197,10 @@ describe('IgxGrid - Filtering Row UI actions', () => { it('should position filter row and chips correctly when grid has column groups and one is hidden.', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringMCHComponent); + fix.detectChanges(); + const grid = fix.componentInstance.grid; + const filteringExpressionsTree = new FilteringExpressionsTree(FilteringLogic.And, 'ProductName'); const expression = { fieldName: 'ProductName', @@ -2207,7 +2209,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { }; filteringExpressionsTree.filteringOperands.push(expression); grid.filteringExpressionsTree = filteringExpressionsTree; - tick(); fix.detectChanges(); let filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); expect(filteringCells.length).toEqual(6); @@ -2215,12 +2216,12 @@ describe('IgxGrid - Filtering Row UI actions', () => { const groupCol = grid.getColumnByName('General'); groupCol.hidden = true; fix.detectChanges(); + filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); expect(filteringCells.length).toEqual(1); const chip = filteringCells[0].query(By.css('igx-chip')); chip.nativeElement.click(); - tick(); fix.detectChanges(); // check if it is positioned at the bottom of the thead. @@ -2232,7 +2233,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { GridFunctions.closeFilterRow(fix); groupCol.hidden = false; - tick(); fix.detectChanges(); filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); @@ -2245,14 +2245,17 @@ describe('IgxGrid - Filtering Row UI actions', () => { // Filtering + Moving it('should move chip under the correct column when column is moved and filter row should open for correct column.', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); - const grid = fix.componentInstance.grid; fix.detectChanges(); + const grid = fix.componentInstance.grid; + let filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); let stringCellChip = filteringCells[1].query(By.css('igx-chip')); + // filter string col stringCellChip.nativeElement.click(); fix.detectChanges(); + GridFunctions.filterBy('Contains', 'Angular', fix); GridFunctions.closeFilterRow(fix); @@ -2288,22 +2291,27 @@ describe('IgxGrid - Filtering Row UI actions', () => { // Filtering + Hiding it('should not display filter cell for hidden columns and chips should show under correct column.', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); - const grid = fix.componentInstance.grid; fix.detectChanges(); + const grid = fix.componentInstance.grid; + let filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); let stringCellChip = filteringCells[1].query(By.css('igx-chip')); + // filter string col stringCellChip.nativeElement.click(); fix.detectChanges(); + GridFunctions.filterBy('Contains', 'Angular', fix); GridFunctions.closeFilterRow(fix); + filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); expect(filteringCells.length).toEqual(6); + // hide column grid.getColumnByName('ID').hidden = true; - tick(); fix.detectChanges(); + filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); expect(filteringCells.length).toEqual(5); stringCellChip = filteringCells[0].query(By.css('igx-chip')); @@ -2315,6 +2323,7 @@ describe('IgxGrid - Filtering Row UI actions', () => { grid.getColumnByName('ProductName').hidden = true; fix.detectChanges(); + filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); expect(filteringCells.length).toEqual(4); @@ -2328,14 +2337,17 @@ describe('IgxGrid - Filtering Row UI actions', () => { // Filtering + Grouping it('should display the header expand/collapse icon for groupby above the filter row.', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); - const grid = fix.componentInstance.grid; fix.detectChanges(); + + const grid = fix.componentInstance.grid; + grid.getColumnByName('ProductName').groupable = true; grid.groupBy({fieldName: 'ProductName', dir: SortingDirection.Asc, ignoreCase: false, strategy: DefaultSortingStrategy.instance()}); fix.detectChanges(); const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); const stringCellChip = filteringCells[1].query(By.css('igx-chip')); + // filter string col stringCellChip.nativeElement.click(); fix.detectChanges(); @@ -2350,15 +2362,20 @@ describe('IgxGrid - Filtering Row UI actions', () => { // Filtering + Pinning it('should position chips correctly after pinning column.', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); - const grid = fix.componentInstance.grid; fix.detectChanges(); + + const grid = fix.componentInstance.grid; + let filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); let stringCellChip = filteringCells[1].query(By.css('igx-chip')); + // filter string col stringCellChip.nativeElement.click(); fix.detectChanges(); + GridFunctions.filterBy('Contains', 'Angular', fix); GridFunctions.closeFilterRow(fix); + grid.getColumnByName('ProductName').pinned = true; fix.detectChanges(); @@ -2374,6 +2391,7 @@ describe('IgxGrid - Filtering Row UI actions', () => { const fix = TestBed.createComponent(IgxGridFilteringComponent); const grid = fix.componentInstance.grid; grid.columnWidth = '250px'; + fix.detectChanges(); // Add initial filtering conditions const gridFilteringExpressionsTree = new FilteringExpressionsTree(FilteringLogic.And); @@ -2384,11 +2402,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { ]; gridFilteringExpressionsTree.filteringOperands.push(columnsFilteringTree); grid.filteringExpressionsTree = gridFilteringExpressionsTree; - tick(); - fix.detectChanges(); - - // Enable resizing - grid.columns.forEach(col => col.resizable = true); fix.detectChanges(); let colChips = GridFunctions.getFilterChipsForColumn('ProductName', fix); @@ -2399,6 +2412,10 @@ describe('IgxGrid - Filtering Row UI actions', () => { expect(colOperands.length).toEqual(1); expect(colIndicator.length).toEqual(0); + // Enable resizing + fix.componentInstance.resizable = true; + fix.detectChanges(); + // Make 'ProductName' column smaller const headers: DebugElement[] = fix.debugElement.queryAll(By.directive(IgxGridHeaderGroupComponent)); const headerResArea = headers[1].children[2].nativeElement; @@ -2575,15 +2592,15 @@ export class CustomFilter extends IgxFilteringOperand { @Component({ template: ` - - - - + + + + + dataType="date" [resizable]="resizable"> + dataType="string" [filters]="customFilter" [resizable]="resizable"> ` }) @@ -2592,6 +2609,7 @@ export class IgxGridFilteringComponent { public timeGenerator: Calendar = new Calendar(); public today: Date = new Date(new Date().getFullYear(), new Date().getMonth(), new Date().getDate(), 0, 0, 0); public customFilter = CustomFilter; + public resizable = false; public data = [ { diff --git a/projects/igniteui-angular/src/lib/test-utils/grid-functions.spec.ts b/projects/igniteui-angular/src/lib/test-utils/grid-functions.spec.ts index 3bd838a3c61..37860563637 100644 --- a/projects/igniteui-angular/src/lib/test-utils/grid-functions.spec.ts +++ b/projects/igniteui-angular/src/lib/test-utils/grid-functions.spec.ts @@ -6,7 +6,7 @@ import { Calendar, IgxCheckboxComponent } from '../../public_api'; import { DebugElement } from '@angular/core'; import { By } from '@angular/platform-browser'; -import { ComponentFixture } from '@angular/core/testing'; +import { ComponentFixture, tick } from '@angular/core/testing'; import { IgxInputDirective } from '../input-group'; import { IgxGridHeaderComponent } from '../grids/grid-header.component'; import { IgxChipComponent } from '../chips'; @@ -408,6 +408,7 @@ export class GridFunctions { for ( i = 0; i < ddItems.length; i++) { if (ddItems[i].textContent === cond) { ddItems[i].click(); + tick(100); return; } } @@ -417,11 +418,12 @@ export class GridFunctions { const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); // open dropdown this.openFilterDD(fix.debugElement); + fix.detectChanges(); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); this.selectFilteringCondition(condition, ddList); - const input = filterUIRow.query(By.directive(IgxInputDirective)); + const input = filterUIRow.query(By.directive(IgxInputDirective)); input.nativeElement.value = value; input.nativeElement.dispatchEvent(new Event('input')); fix.detectChanges(); @@ -436,6 +438,7 @@ export class GridFunctions { const editingBtns = filterUIRow.query(By.css('.igx-grid__filtering-row-editing-buttons')); const reset = editingBtns.queryAll(By.css('button'))[0]; reset.nativeElement.click(); + tick(100); fix.detectChanges(); } @@ -444,6 +447,7 @@ export class GridFunctions { const editingBtns = filterUIRow.query(By.css('.igx-grid__filtering-row-editing-buttons')); const close = editingBtns.queryAll(By.css('button'))[1]; close.nativeElement.click(); + tick(100); fix.detectChanges(); } From 9a4bdba04aef0d731c587729d48bb3f987d86ddd Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Tue, 20 Nov 2018 11:43:41 +0200 Subject: [PATCH 16/24] test(filtering): fix timer issues in filtering UI test #542 --- .../lib/grids/grid/grid-filtering-ui.spec.ts | 30 ++++++++++--------- 1 file changed, 16 insertions(+), 14 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts index db56ed8b85a..6e2dcd5bae6 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts @@ -1,5 +1,5 @@ import { Component, ViewChild, DebugElement } from '@angular/core'; -import { async, discardPeriodicTasks, fakeAsync, TestBed, tick } from '@angular/core/testing'; +import { async, discardPeriodicTasks, fakeAsync, TestBed, tick, flush } from '@angular/core/testing'; import { By } from '@angular/platform-browser'; import { BrowserAnimationsModule, NoopAnimationsModule } from '@angular/platform-browser/animations'; import { Calendar } from '../../calendar/calendar'; @@ -33,7 +33,6 @@ describe('IgxGrid - Filtering actions', () => { IgxGridFilteringComponent ], imports: [ - BrowserAnimationsModule, NoopAnimationsModule, IgxGridModule.forRoot()] }) @@ -1113,27 +1112,27 @@ describe('IgxGrid - Filtering actions', () => { const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); - tick(); fix.detectChanges(); + const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); const input = filterUIRow.query(By.directive(IgxInputDirective)); filterIcon.nativeElement.click(); - tick(); fix.detectChanges(); verifyFilterUIPosition(filterIcon, grid); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Equals', ddList); + input.nativeElement.click(); - tick(100); + tick(); fix.detectChanges(); const calendar = fix.debugElement.query(By.css('igx-calendar')); const currentDay = calendar.query(By.css('span.igx-calendar__date--current')); currentDay.nativeElement.click(); - tick(); + flush(); fix.detectChanges(); input.nativeElement.dispatchEvent(new Event('change')); @@ -1150,8 +1149,8 @@ describe('IgxGrid - Filtering actions', () => { const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); - tick(); fix.detectChanges(); + const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); const input = filterUIRow.query(By.directive(IgxInputDirective)); @@ -1163,14 +1162,15 @@ describe('IgxGrid - Filtering actions', () => { verifyFilterUIPosition(filterIcon, grid); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Does Not Equal', ddList); + input.nativeElement.click(); - tick(100); + tick(); fix.detectChanges(); const calendar = fix.debugElement.query(By.css('igx-calendar')); const currentDay = calendar.query(By.css('span.igx-calendar__date--current')); currentDay.nativeElement.click(); - tick(); + flush(); fix.detectChanges(); input.nativeElement.dispatchEvent(new Event('change')); @@ -1187,8 +1187,8 @@ describe('IgxGrid - Filtering actions', () => { const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); - tick(); fix.detectChanges(); + const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); const input = filterUIRow.query(By.directive(IgxInputDirective)); @@ -1201,6 +1201,7 @@ describe('IgxGrid - Filtering actions', () => { const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('After', ddList); + input.nativeElement.click(); tick(100); fix.detectChanges(); @@ -1208,7 +1209,7 @@ describe('IgxGrid - Filtering actions', () => { const calendar = fix.debugElement.query(By.css('igx-calendar')); const currentDay = calendar.query(By.css('span.igx-calendar__date--current')); currentDay.nativeElement.click(); - tick(); + flush(); fix.detectChanges(); input.nativeElement.dispatchEvent(new Event('change')); @@ -1225,8 +1226,8 @@ describe('IgxGrid - Filtering actions', () => { const grid = fix.componentInstance.grid; const filteringCells = fix.debugElement.queryAll(By.css('igx-grid-filtering-cell')); filteringCells[4].query(By.css('igx-chip')).nativeElement.click(); - tick(); fix.detectChanges(); + const filterUIRow = fix.debugElement.query(By.css(FILTER_UI_ROW)); const filterIcon = filterUIRow.query(By.css('igx-icon')); const input = filterUIRow.query(By.directive(IgxInputDirective)); @@ -1238,14 +1239,15 @@ describe('IgxGrid - Filtering actions', () => { verifyFilterUIPosition(filterIcon, grid); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); GridFunctions.selectFilteringCondition('Before', ddList); + input.nativeElement.click(); - tick(100); + tick(); fix.detectChanges(); const calendar = fix.debugElement.query(By.css('igx-calendar')); const currentDay = calendar.query(By.css('span.igx-calendar__date--current')); currentDay.nativeElement.click(); - tick(); + flush(); fix.detectChanges(); input.nativeElement.dispatchEvent(new Event('change')); From 611e93b2a30c6ec565309f9e30b2d224a219cf0e Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Tue, 20 Nov 2018 12:12:44 +0200 Subject: [PATCH 17/24] fix(*): sorting icon not being updated when sort/groupBy via API #542 --- .../src/lib/grids/grid-header-group.component.ts | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts index f79a8b610a6..bb9b961052c 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts @@ -116,9 +116,7 @@ export class IgxGridHeaderGroupComponent implements DoCheck { } public ngDoCheck() { - if (this.column.columnGroup) { - this.cdr.markForCheck(); - } + this.cdr.markForCheck(); } constructor(private cdr: ChangeDetectorRef, From 3a7d4e0925392ebd8171e27732760c29672583a1 Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Tue, 20 Nov 2018 14:08:43 +0200 Subject: [PATCH 18/24] feat(filtering): fix introduced resizer bug #542 --- .../src/lib/grids/grid-header-group.component.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html index ccd97e3af47..3c91782d9dd 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html @@ -16,7 +16,7 @@ -
Date: Tue, 20 Nov 2018 18:14:57 +0200 Subject: [PATCH 19/24] chore(*): review comments changes #542 --- .../igniteui-angular/src/lib/core/utils.ts | 6 ++-- .../src/lib/grids/cell.component.ts | 4 +-- .../src/lib/grids/column.component.ts | 8 ++--- .../grids/grid-header-group.component.html | 29 ++++++++++++++----- .../grids/tree-grid/tree-cell.component.ts | 4 +-- 5 files changed, 33 insertions(+), 18 deletions(-) diff --git a/projects/igniteui-angular/src/lib/core/utils.ts b/projects/igniteui-angular/src/lib/core/utils.ts index 71288c2b977..e71f423447e 100644 --- a/projects/igniteui-angular/src/lib/core/utils.ts +++ b/projects/igniteui-angular/src/lib/core/utils.ts @@ -163,10 +163,10 @@ export const enum KEYS { * let range = document.createRange(); * let column = this.grid.columnList.filter(c => c.field === 'ID')[0]; * -* let size = valToPxlsUsingRange(range, column.cells[0].nativeElement); +* let size = getNodeSizeViaRange(range, column.cells[0].nativeElement); * ``` */ -export function valToPxlsUsingRange(range: Range, node: any): number { +export function getNodeSizeViaRange(range: Range, node: any): number { let overflow = null; if (isIE() || isEdge()) { overflow = node.style.overflow; @@ -194,7 +194,7 @@ export function valToPxlsUsingRange(range: Range, node: any): number { * let size = valToPxlsUsingCanvas(ctx, column.cells[0].nativeElement); * ``` */ -export function valToPxlsUsingCanvas(canvas2dCtx: any, node: any): number { +export function getNodeSizeViaCanvas(canvas2dCtx: any, node: any): number { const s = this.grid.document.defaultView.getComputedStyle(node); // need to set the font to get correct width diff --git a/projects/igniteui-angular/src/lib/grids/cell.component.ts b/projects/igniteui-angular/src/lib/grids/cell.component.ts index 94a19c7c263..f19b67299aa 100644 --- a/projects/igniteui-angular/src/lib/grids/cell.component.ts +++ b/projects/igniteui-angular/src/lib/grids/cell.component.ts @@ -15,7 +15,7 @@ import { IgxSelectionAPIService } from '../core/selection'; import { IgxTextHighlightDirective } from '../directives/text-highlight/text-highlight.directive'; import { GridBaseAPIService } from './api.service'; import { IgxColumnComponent } from './column.component'; -import { isNavigationKey, valToPxlsUsingRange, KEYS } from '../core/utils'; +import { isNavigationKey, getNodeSizeViaRange, KEYS } from '../core/utils'; import { State } from '../services/index'; import { IgxGridBaseComponent, IGridEditEventArgs } from './grid-base.component'; import { first } from 'rxjs/operators'; @@ -903,7 +903,7 @@ export class IgxGridCellComponent implements OnInit, AfterViewInit { */ public calculateSizeToFit(range: any): number { return Math.max(...Array.from(this.nativeElement.children) - .map((child) => valToPxlsUsingRange(range, child))); + .map((child) => getNodeSizeViaRange(range, child))); } private isToggleKey(key) { diff --git a/projects/igniteui-angular/src/lib/grids/column.component.ts b/projects/igniteui-angular/src/lib/grids/column.component.ts index 8ab80ea650e..2b78328ea21 100644 --- a/projects/igniteui-angular/src/lib/grids/column.component.ts +++ b/projects/igniteui-angular/src/lib/grids/column.component.ts @@ -23,7 +23,7 @@ import { } from './grid.common'; import { IgxGridHeaderComponent } from './grid-header.component'; import { DefaultSortingStrategy, ISortingStrategy } from '../data-operations/sorting-strategy'; -import { valToPxlsUsingRange, flatten } from '../core/utils'; +import { getNodeSizeViaRange, flatten } from '../core/utils'; import { IgxBooleanFilteringOperand, IgxNumberFilteringOperand, @@ -1126,7 +1126,7 @@ export class IgxColumnComponent implements AfterContentInit { if (this.cells[0].nativeElement.children.length > 0) { this.cells.forEach((cell) => cellsContentWidths.push(cell.calculateSizeToFit(range))); } else { - cellsContentWidths = this.cells.map((cell) => valToPxlsUsingRange(range, cell.nativeElement)); + cellsContentWidths = this.cells.map((cell) => getNodeSizeViaRange(range, cell.nativeElement)); } const index = cellsContentWidths.indexOf(Math.max(...cellsContentWidths)); @@ -1141,9 +1141,9 @@ export class IgxColumnComponent implements AfterContentInit { let headerCell; if (this.headerTemplate && this.headerCell.elementRef.nativeElement.children[0].children.length > 0) { headerCell = Math.max(...Array.from(this.headerCell.elementRef.nativeElement.children[0].children) - .map((child) => valToPxlsUsingRange(range, child))); + .map((child) => getNodeSizeViaRange(range, child))); } else { - headerCell = valToPxlsUsingRange(range, this.headerCell.elementRef.nativeElement.children[0]); + headerCell = getNodeSizeViaRange(range, this.headerCell.elementRef.nativeElement.children[0]); } if (this.sortable) { diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html index 3c91782d9dd..ad5a5701d3d 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html @@ -1,9 +1,20 @@ -
{{ column.header }}
+
+ {{ column.header }} +
- + +
@@ -12,13 +23,17 @@ - - -
+ +
valToPxlsUsingRange(range, child))); + .map((child) => getNodeSizeViaRange(range, child))); return largestWidth + indicatorWidth + indicatorMargin + leftPadding; } } From 79cafbbd22faa253af9ecdb577adb81d36de7182 Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Wed, 21 Nov 2018 08:58:12 +0200 Subject: [PATCH 20/24] feat(filtering): fix broken behaviors #542 --- .../src/lib/grids/grid-header-group.component.html | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html index ad5a5701d3d..42058a79ce7 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.html @@ -1,9 +1,7 @@
- {{ column.header }} -
+ [ngClass]="{'igx-grid__th--pinned-last': hasLastPinnedChildColumn}">{{ column.header }}
Date: Wed, 21 Nov 2018 09:47:50 +0200 Subject: [PATCH 21/24] chore(*): some clean up, etc. #542 --- .../src/lib/core/styles/components/grid/_grid-theme.scss | 4 ---- src/app/grid-column-moving/grid-column-moving.sample.ts | 2 +- 2 files changed, 1 insertion(+), 5 deletions(-) diff --git a/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss b/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss index cad7d5fe309..e90341788ce 100644 --- a/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss +++ b/projects/igniteui-angular/src/lib/core/styles/components/grid/_grid-theme.scss @@ -1150,10 +1150,6 @@ %igx-grid__drag-col-header { background-color: --var($theme, 'header-background'); - %grid-thead-title { - opacity: .4; - } - %grid-cell-header-title, %grid-cell-header-icons { opacity: .4; diff --git a/src/app/grid-column-moving/grid-column-moving.sample.ts b/src/app/grid-column-moving/grid-column-moving.sample.ts index 35fd367aaa3..b7e23ff4e07 100644 --- a/src/app/grid-column-moving/grid-column-moving.sample.ts +++ b/src/app/grid-column-moving/grid-column-moving.sample.ts @@ -18,7 +18,7 @@ export class GridColumnMovingSampleComponent implements OnInit { public ngOnInit(): void { this.columns = [ - { field: 'ID', width: 150, resizable: true, movable: true }, + { field: 'ID', width: 40, resizable: true, movable: true }, { field: 'CompanyName', width: 150, resizable: true, movable: true, type: 'string'}, { field: 'ContactName', width: 150, resizable: true, movable: true, type: 'string' }, { field: 'ContactTitle', width: 150, resizable: true, movable: true, type: 'string' }, From 8555ba910f0fd17e352f52fafa7ee7ac77af0f75 Mon Sep 17 00:00:00 2001 From: SAndreeva Date: Thu, 22 Nov 2018 11:45:52 +0200 Subject: [PATCH 22/24] feat(filtering): some API refinements #542 --- .../directives/dragdrop/dragdrop.directive.ts | 7 +- .../src/lib/grids/grid-base.component.ts | 2 + .../lib/grids/grid-column-resizing.service.ts | 45 ++++++++++-- .../lib/grids/grid-header-group.component.ts | 68 ++++++++++++++++++- 4 files changed, 113 insertions(+), 9 deletions(-) diff --git a/projects/igniteui-angular/src/lib/directives/dragdrop/dragdrop.directive.ts b/projects/igniteui-angular/src/lib/directives/dragdrop/dragdrop.directive.ts index 62c844aac69..502be6d07ad 100644 --- a/projects/igniteui-angular/src/lib/directives/dragdrop/dragdrop.directive.ts +++ b/projects/igniteui-angular/src/lib/directives/dragdrop/dragdrop.directive.ts @@ -572,10 +572,13 @@ export class IgxDragDirective implements OnInit, OnDestroy { /** * @hidden - * Create dragGhost element - copy of the base element. Bind all needed events. + * Create dragGhost element - if a Node object is provided it creates a clone of that node, + * otherwise it clones the host element. + * Bind all needed events. * @param event Pointer event required when the dragGhost is being initialized. + * @param node The Node object to be cloned. */ - protected createDragGhost(event, node = null) { + protected createDragGhost(event, node: any = null) { this._dragGhost = node ? node.cloneNode(true) : this.element.nativeElement.cloneNode(true); this._dragGhost.style.transitionDuration = '0.0s'; this._dragGhost.style.position = 'absolute'; diff --git a/projects/igniteui-angular/src/lib/grids/grid-base.component.ts b/projects/igniteui-angular/src/lib/grids/grid-base.component.ts index 23129da3f06..ac37956d5bc 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-base.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-base.component.ts @@ -2291,6 +2291,8 @@ export abstract class IgxGridBaseComponent extends DisplayDensityBase implements if (this.headerCheckboxContainer) { return this.headerCheckboxContainer.nativeElement.clientWidth; } + + return 0; } /** diff --git a/projects/igniteui-angular/src/lib/grids/grid-column-resizing.service.ts b/projects/igniteui-angular/src/lib/grids/grid-column-resizing.service.ts index 3d86a1f76e7..a5eac5e8ed2 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-column-resizing.service.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-column-resizing.service.ts @@ -6,16 +6,41 @@ import { IgxColumnComponent } from './column.component'; @Injectable() export class IgxColumnResizingService { + private pinnedMaxWidth: string; + + /** + *@hidden + */ public startResizePos: number; + /** + * Indicates that a column is currently being resized. + */ public isColumnResizing: boolean; - public resizeCursor: any = null; + /** + *@hidden + */ + public resizeCursor: string = null; + /** + *@hidden + */ public showResizer = false; + /** + *@hidden + */ public resizerHeight: number; + /** + *@hidden + */ public resizeEndTimeout = isFirefox() ? 200 : 0; + /** + * The column being resized. + */ public column: IgxColumnComponent; - private pinnedMaxWidth; + /** + * Returns the minimal possible width to which the column can be resized. + */ get restrictResizeMin(): number { const actualMinWidth = parseFloat(this.column.minWidth); const defaultMinWidth = parseFloat(this.column.defaultMinWidth); @@ -26,6 +51,9 @@ export class IgxColumnResizingService { return minWidth - this.column.headerCell.elementRef.nativeElement.getBoundingClientRect().width; } + /** + * Returns the maximal possible width to which the column can be resized. + */ get restrictResizeMax(): number { const actualWidth = this.column.headerCell.elementRef.nativeElement.getBoundingClientRect().width; @@ -49,6 +77,13 @@ export class IgxColumnResizingService { } } + /** + * Autosizes the column to the longest currently visible cell value, including the header cell. + * If the column has a predifined maxWidth and the autosized column width will become bigger than it, + * then the column is sized to its maxWidth. + * If the column is pinned and the autosized column width will cause the pinned area to become bigger + * than the maximum allowed pinned area width (80% of the total grid width), autosizing will be deismissed. + */ public autosizeColumnOnDblClick() { if (this.column.resizable) { const currentColWidth = this.column.headerCell.elementRef.nativeElement.getBoundingClientRect().width; @@ -79,8 +114,10 @@ export class IgxColumnResizingService { } } - public resizeColumn(event) { - + /** + * Resizes the column regaridng to the column minWidth and maxWidth. + */ + public resizeColumn(event: MouseEvent) { this.isColumnResizing = false; this.showResizer = false; diff --git a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts index bb9b961052c..bd9981d6058 100644 --- a/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts +++ b/projects/igniteui-angular/src/lib/grids/grid-header-group.component.ts @@ -18,6 +18,8 @@ import { IgxColumnResizingService } from './grid-column-resizing.service'; import { IgxGridHeaderComponent } from './grid-header.component'; import { IgxGridFilteringCellComponent } from './filtering/grid-filtering-cell.component'; +const Z_INDEX = 9999; + /** * @hidden */ @@ -29,27 +31,52 @@ import { IgxGridFilteringCellComponent } from './filtering/grid-filtering-cell.c }) export class IgxGridHeaderGroupComponent implements DoCheck { + /** + * Gets the column of the header group. + * @memberof IgxGridHeaderGroupComponent + */ @Input() public column: IgxColumnComponent; + /** + * Gets the `id` of the grid in which the header group is stored. + * @memberof IgxGridHeaderGroupComponent + */ @Input() public gridID: string; + /** + * @hidden + */ @ViewChild(IgxGridHeaderComponent) public headerCell: IgxGridHeaderComponent; + /** + * @hidden + */ @ViewChild(IgxGridFilteringCellComponent) public filterCell: IgxGridFilteringCellComponent; + /** + * @hidden + */ @ViewChildren(forwardRef(() => IgxGridHeaderGroupComponent), { read: IgxGridHeaderGroupComponent }) public children: QueryList; + /** + * Gets the width of the header group. + * @memberof IgxGridHeaderGroupComponent + */ @HostBinding('style.min-width') @HostBinding('style.flex-basis') get width() { return this.column.width; } + /** + * Gets the style classes of the header group. + * @memberof IgxGridHeaderGroupComponent + */ @HostBinding('class') get styleClasses(): string { const defaultClasses = [ @@ -64,30 +91,45 @@ export class IgxGridHeaderGroupComponent implements DoCheck { 'igx-grid__th--filtering': this.isFiltered }; - Object.entries(classList).forEach(([klass, value]) => { + Object.entries(classList).forEach(([className, value]) => { if (value) { - defaultClasses.push(klass); + defaultClasses.push(className); } }); return defaultClasses.join(' '); } + /** + * @hidden + */ @HostBinding('style.z-index') get zIndex() { if (!this.column.pinned) { return null; } - return 9999 - this.grid.pinnedColumns.indexOf(this.column); + return Z_INDEX - this.grid.pinnedColumns.indexOf(this.column); } + /** + * Gets the grid of the header group. + * @memberof IgxGridHeaderGroupComponent + */ get grid(): any { return this.gridAPI.get(this.gridID); } + /** + * Gets whether the header group belongs to a column that is filtered. + * @memberof IgxGridHeaderGroupComponent + */ get isFiltered(): boolean { return this.filteringService.filteredColumn === this.column; } + /** + * Gets whether the header group is stored in the last column in the pinned area. + * @memberof IgxGridHeaderGroupComponent + */ get isLastPinned(): boolean { const pinnedCols = this.grid.pinnedColumns; @@ -98,14 +140,25 @@ export class IgxGridHeaderGroupComponent implements DoCheck { return pinnedCols.indexOf(this.column) === pinnedCols.length - 1; } + /** + * Gets whether the header group is stored in a pinned column. + * @memberof IgxGridHeaderGroupComponent + */ get isPinned(): boolean { return this.column.pinned; } + /** + * Gets whether the header group belongs to a column that is moved. + * @memberof IgxGridHeaderGroupComponent + */ get isHeaderDragged(): boolean { return this.grid.draggedColumn === this.column; } + /** + * @hidden + */ get hasLastPinnedChildColumn(): boolean { const pinnedCols = this.grid.pinnedColumns; if (this.column.allChildren) { @@ -124,12 +177,18 @@ export class IgxGridHeaderGroupComponent implements DoCheck { public colResizingService: IgxColumnResizingService, public filteringService: IgxFilteringService) { } + /** + * @hidden + */ public onResizeAreaMouseOver() { if (this.column.resizable) { this.colResizingService.resizeCursor = 'col-resize'; } } + /** + * @hidden + */ public onResizeAreaMouseDown(event) { if (event.button === 0 && this.column.resizable) { this.colResizingService.column = this.column; @@ -142,6 +201,9 @@ export class IgxGridHeaderGroupComponent implements DoCheck { } } + /** + * @hidden + */ public autosizeColumnOnDblClick(event) { if (event.button === 0 && this.column.resizable) { this.colResizingService.column = this.column; From 67910c31166a32a3eac0f2c8412eed89739de2fd Mon Sep 17 00:00:00 2001 From: Borislav Kulov Date: Thu, 22 Nov 2018 17:25:43 +0200 Subject: [PATCH 23/24] fix(filtering): Fix async issue in test (#2995) --- .../lib/grids/grid/grid-filtering-ui.spec.ts | 22 +++++++++++++------ 1 file changed, 15 insertions(+), 7 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts index 6e2dcd5bae6..feec9c2289c 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts @@ -1180,7 +1180,7 @@ describe('IgxGrid - Filtering actions', () => { expect(grid.rowList.length).toEqual(7); })); - it('UI - should correctly filter date column by \'after\' filtering conditions', fakeAsync(() => { + it('UI - should correctly filter date column by \'after\' filtering conditions', async() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); fix.detectChanges(); @@ -1194,30 +1194,38 @@ describe('IgxGrid - Filtering actions', () => { const input = filterUIRow.query(By.directive(IgxInputDirective)); filterIcon.nativeElement.click(); - tick(); fix.detectChanges(); + await wait(); verifyFilterUIPosition(filterIcon, grid); const ddList = fix.debugElement.query(By.css('div.igx-drop-down__list.igx-toggle')); - GridFunctions.selectFilteringCondition('After', ddList); + const ddItems = ddList.nativeElement.children; + let i; + for (i = 0; i < ddItems.length; i++) { + if (ddItems[i].textContent === 'After') { + ddItems[i].click(); + await wait(100); + return; + } + } input.nativeElement.click(); - tick(100); fix.detectChanges(); + await wait(100); const calendar = fix.debugElement.query(By.css('igx-calendar')); const currentDay = calendar.query(By.css('span.igx-calendar__date--current')); currentDay.nativeElement.click(); - flush(); fix.detectChanges(); + await wait(); input.nativeElement.dispatchEvent(new Event('change')); - tick(); fix.detectChanges(); + await wait(); expect(grid.rowList.length).toEqual(3); - })); + }); it('UI - should correctly filter date column by \'before\' filtering conditions', fakeAsync(() => { const fix = TestBed.createComponent(IgxGridFilteringComponent); From 6f92a5517ce7158f133d95ab316612768548b87d Mon Sep 17 00:00:00 2001 From: Borislav Kulov Date: Fri, 23 Nov 2018 09:47:19 +0200 Subject: [PATCH 24/24] fix(filtering): Fix empty bool expected result (#2938) --- .../src/lib/grids/grid/grid-filtering-ui.spec.ts | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts index feec9c2289c..04f8abb58ac 100644 --- a/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts +++ b/projects/igniteui-angular/src/lib/grids/grid/grid-filtering-ui.spec.ts @@ -1703,7 +1703,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { stringCellChip.nativeElement.click(); fix.detectChanges(); - GridFunctions.filterBy('Starts With', 'I', fix); expect(grid.rowList.length).toEqual(2); GridFunctions.filterBy('Ends With', 'r', fix); @@ -1713,7 +1712,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { GridFunctions.resetFilterRow(fix); GridFunctions.closeFilterRow(fix); - // open for number numberCellChip.nativeElement.click(); fix.detectChanges(); @@ -1727,7 +1725,6 @@ describe('IgxGrid - Filtering Row UI actions', () => { GridFunctions.resetFilterRow(fix); GridFunctions.closeFilterRow(fix); - // open for bool boolCellChip.nativeElement.click(); fix.detectChanges(); @@ -1735,7 +1732,7 @@ describe('IgxGrid - Filtering Row UI actions', () => { GridFunctions.filterBy('False', '', fix); expect(grid.rowList.length).toEqual(2); GridFunctions.filterBy('Empty', '', fix); - expect(grid.rowList.length).toEqual(0); + expect(grid.rowList.length).toEqual(3); // Reset and Close GridFunctions.resetFilterRow(fix);