UNPKG

clr-angular-static-fix

Version:

1. Install Clarity Icons package through npm:

396 lines (345 loc) 15 kB
/* * Copyright (c) 2016-2018 VMware, Inc. All Rights Reserved. * This software is released under MIT license. * The full license information can be found in LICENSE in the root directory of this project. */ import { Component } from '@angular/core'; import { fakeAsync, TestBed, tick } from '@angular/core/testing'; import { itIgnore } from '../../../../tests/tests.helpers'; import { Expand } from '../../utils/expand/providers/expand'; import { LoadingListener } from '../../utils/loading/loading-listener'; import { DatagridWillyWonka } from './chocolate/datagrid-willy-wonka'; import { DatagridHideableColumnModel } from './datagrid-hideable-column.model'; import { ClrDatagridRow } from './datagrid-row'; import { TestContext } from './helpers.spec'; import { FiltersProvider } from './providers/filters'; import { ExpandableRowsCount } from './providers/global-expandable-rows'; import { HideableColumnService } from './providers/hideable-column.service'; import { Items } from './providers/items'; import { Page } from './providers/page'; import { RowActionService } from './providers/row-action-service'; import { Selection, SelectionType } from './providers/selection'; import { Sort } from './providers/sort'; import { StateDebouncer } from './providers/state-debouncer.provider'; import { DomAdapter } from './render/dom-adapter'; import { DatagridRenderOrganizer } from './render/render-organizer'; const PROVIDERS = [ Selection, Items, FiltersProvider, Sort, Page, RowActionService, ExpandableRowsCount, DatagridRenderOrganizer, DomAdapter, HideableColumnService, DatagridWillyWonka, StateDebouncer, ]; export default function(): void { describe('ClrDatagridRow component', function() { describe('View', function() { // Until we can properly type "this" let context: TestContext<ClrDatagridRow, FullTest>; beforeEach(function() { context = this.create(ClrDatagridRow, FullTest, PROVIDERS); }); it('projects content', function() { expect(context.clarityElement.textContent.trim()).toMatch('Hello world'); }); it('adds the .datagrid-row class to the host', function() { expect(context.clarityElement.classList.contains('datagrid-row')).toBeTruthy(); }); it("receives an input for the row's modal", function() { context.testComponent.item = { id: 1 }; context.detectChanges(); expect(context.clarityDirective.item).toBe(context.testComponent.item); }); it('displays an empty cell when one of the rows is expandable', function() { expect(context.clarityElement.querySelector('.datagrid-fixed-column')).toBeNull(); context.getClarityProvider(ExpandableRowsCount).register(); context.detectChanges(); expect(context.clarityElement.querySelector('.datagrid-fixed-column')).not.toBeNull(); }); }); describe('Selection', function() { // Until we can properly type "this" let context: TestContext<ClrDatagridRow, FullTest>; let selectionProvider: Selection; beforeEach(function() { context = this.create(ClrDatagridRow, FullTest, PROVIDERS); selectionProvider = TestBed.get(Selection); TestBed.get(Items).all = [{ id: 1 }, { id: 2 }]; }); it("doesn't display a checkbox unless selection type is multi", function() { selectionProvider.selectionType = SelectionType.None; context.detectChanges(); expect(context.clarityElement.querySelector("input[type='checkbox']")).toBeNull(); selectionProvider.selectionType = SelectionType.Single; context.detectChanges(); expect(context.clarityElement.querySelector("input[type='checkbox']")).toBeNull(); }); it("doesn't display a radio button unless selection type is single", function() { selectionProvider.selectionType = SelectionType.None; context.detectChanges(); expect(context.clarityElement.querySelector("input[type='radio']")).toBeNull(); selectionProvider.selectionType = SelectionType.Multi; context.detectChanges(); expect(context.clarityElement.querySelector("input[type='radio']")).toBeNull(); }); it('selects the model when the checkbox is clicked', function() { selectionProvider.selectionType = SelectionType.Multi; context.testComponent.item = { id: 1 }; context.detectChanges(); const checkbox = context.clarityElement.querySelector("input[type='checkbox']"); expect(selectionProvider.current).toEqual([]); checkbox.click(); context.detectChanges(); expect(selectionProvider.current).toEqual([context.testComponent.item]); checkbox.click(); context.detectChanges(); expect(selectionProvider.current).toEqual([]); }); it('selects the model when the radio button is clicked', function() { selectionProvider.selectionType = SelectionType.Single; context.testComponent.item = { id: 1 }; context.detectChanges(); const radio = context.clarityElement.querySelector("input[type='radio']"); expect(selectionProvider.currentSingle).toBeUndefined(); radio.click(); context.detectChanges(); expect(selectionProvider.currentSingle).toEqual(context.testComponent.item); }); it('adds the .datagrid-selected class to the host when the row is selected', function() { selectionProvider.selectionType = SelectionType.Multi; context.testComponent.item = { id: 1 }; context.detectChanges(); context.clarityDirective.selected = true; context.detectChanges(); expect(context.clarityElement.classList.contains('datagrid-selected')).toBeTruthy(); }); it( 'offers two-way binding on the selected state of the row', fakeAsync(function() { selectionProvider.selectionType = SelectionType.Multi; context.testComponent.item = { id: 1 }; flushAndAssertSelected(false); // Input context.testComponent.selected = true; flushAndAssertSelected(true); // Output context.clarityElement.querySelector("input[type='checkbox']").click(); flushAndAssertSelected(false); }) ); it( "supports selected rows even if the datagrid isn't selectable", fakeAsync(function() { selectionProvider.selectionType = SelectionType.None; expect(context.testComponent.item).toBeUndefined(); expect(context.clarityDirective.selected).toBe(false); context.testComponent.selected = true; context.detectChanges(); expect(context.clarityDirective.selected).toBe(true); context.testComponent.selected = false; context.detectChanges(); expect(context.clarityDirective.selected).toBe(false); }) ); it('selects the model on click only when `rowSelectionMode` is enabled (Single selection)', function() { selectionProvider.selectionType = SelectionType.Single; context.testComponent.item = { id: 1 }; context.detectChanges(); const row = context.clarityElement; row.click(); context.detectChanges(); expect(selectionProvider.currentSingle).toBeUndefined(); // Enabling the rowSelectionMode selectionProvider.rowSelectionMode = true; context.detectChanges(); row.click(); context.detectChanges(); expect(selectionProvider.currentSingle).toEqual(context.testComponent.item); }); it('selects the model on click only when `rowSelectionMode` is enabled (Multi selection)', function() { selectionProvider.selectionType = SelectionType.Multi; context.testComponent.item = { id: 1 }; context.detectChanges(); const row = context.clarityElement; expect(selectionProvider.current).toEqual([]); row.click(); context.detectChanges(); expect(selectionProvider.current).toEqual([]); // Enabling the rowSelectionMode selectionProvider.rowSelectionMode = true; context.detectChanges(); row.click(); context.detectChanges(); expect(selectionProvider.current).toEqual([context.testComponent.item]); row.click(); context.detectChanges(); expect(selectionProvider.current).toEqual([]); }); // IE doesn't support Event constructor // @TODO Consider if we care to fix this test for IE support itIgnore(['ie'], 'select the model on space or enter when `rowSelectionMode` is enabled', function() { selectionProvider.selectionType = SelectionType.Multi; selectionProvider.rowSelectionMode = true; context.testComponent.item = { id: 1 }; const row = context.clarityElement; context.detectChanges(); const event: any = new Event('keypress'); event.keyCode = 13; // Enter row.dispatchEvent(event); context.detectChanges(); expect(selectionProvider.current).toEqual([context.testComponent.item]); event.keyCode = 32; // Space row.dispatchEvent(event); context.detectChanges(); expect(selectionProvider.current).toEqual([]); }); function flushAndAssertSelected(selected: boolean) { context.detectChanges(); // ngModel is asynchronous, we need an extra change detection tick(); context.detectChanges(); expect(context.testComponent.selected).toBe(selected); expect(context.clarityDirective.selected).toBe(selected); } }); describe('Expand/Collapse', function() { // Until we can properly type "this" let context: TestContext<ClrDatagridRow, ExpandTest>; let expand: Expand; beforeEach(function() { context = this.create(ClrDatagridRow, ExpandTest, PROVIDERS); context.detectChanges(); expand = context.getClarityProvider(Expand); }); it('registers a LoadingListener', function() { expect(context.getClarityProvider(LoadingListener)).toBeTruthy(); }); it('displays a clickable caret when the row is expandable', function() { expect(context.clarityElement.querySelector('button clr-icon[shape^=caret]')).not.toBeNull(); }); it('displays a spinner instead of the caret when the details are loading', function() { expect(context.clarityElement.querySelector('.spinner')).toBeNull(); expand.loading = true; context.detectChanges(); expect(context.clarityElement.querySelector('.spinner')).not.toBeNull(); }); it("doesn't display the details when collapsed", function() { expect(context.clarityElement.textContent).toMatch('Hello world'); expect(context.clarityElement.textContent).not.toMatch('Detail'); expand.replace = true; context.detectChanges(); expect(context.clarityElement.textContent).toMatch('Hello world'); expect(context.clarityElement.textContent).not.toMatch('Detail'); }); it( 'displays both the row and the details when expanded and not replacing', fakeAsync(function() { expand.expanded = true; tick(); context.detectChanges(); expect(context.clarityElement.textContent).toMatch('Hello world'); expect(context.clarityElement.textContent).toMatch('Detail'); }) ); it( 'displays only the details when expanded and replacing', fakeAsync(function() { expand.replace = true; expand.expanded = true; tick(); context.detectChanges(); expect(context.clarityElement.textContent).not.toMatch('Hello world'); expect(context.clarityElement.textContent).toMatch('Detail'); }) ); it( "doesn't display the details while loading", fakeAsync(function() { expand.expanded = true; expand.loading = true; tick(); context.detectChanges(); expect(context.clarityElement.textContent).not.toMatch('Detail'); }) ); it( 'expands and collapses when the caret is clicked', fakeAsync(function() { const caret = context.clarityElement.querySelector('.datagrid-expandable-caret button'); caret.click(); flushAnimations(); expect(expand.expanded).toBe(true); caret.click(); flushAnimations(); expect(expand.expanded).toBe(false); }) ); it( 'offers 2-way binding on the expanded state of the row', fakeAsync(function() { context.testComponent.expanded = true; flushAnimations(); expect(context.clarityDirective.expanded).toBe(true); context.clarityElement.querySelector('.datagrid-expandable-caret button').click(); flushAnimations(); expect(context.testComponent.expanded).toBe(false); }) ); function flushAnimations() { context.detectChanges(); tick(); context.detectChanges(); } }); describe('Hide/Show', function() { let context: TestContext<ClrDatagridRow, ExpandTest>; let hideableColumnService: HideableColumnService; beforeEach(function() { context = this.create(ClrDatagridRow, HideShowTest, PROVIDERS); hideableColumnService = context.getClarityProvider(HideableColumnService); }); it('should update cells for columns', function() { // TODO: figure out how to test for cell changes and make sure updateCellsForColumns is called spyOn(context.clarityDirective, 'updateCellsForColumns'); hideableColumnService = context.getClarityProvider(HideableColumnService); const hiddenColumns: DatagridHideableColumnModel[] = [ new DatagridHideableColumnModel(null, 'dg-col-0', false), new DatagridHideableColumnModel(null, 'dg-col-1', true), ]; hideableColumnService.updateColumnList(hiddenColumns); expect(context.clarityDirective.updateCellsForColumns).toHaveBeenCalled(); }); }); }); } @Component({ template: `<clr-dg-row [clrDgItem]="item" [(clrDgSelected)]="selected">Hello world</clr-dg-row>` }) class FullTest { item: any; selected = false; } @Component({ template: ` <clr-dg-row [(clrDgExpanded)]="expanded"> Hello world <clr-dg-row-detail *clrIfExpanded> Detail </clr-dg-row-detail> </clr-dg-row>`, }) class ExpandTest { expanded = false; } @Component({ template: ` <clr-dg-row> <clr-dg-cell>ID</clr-dg-cell> <clr-dg-cell>Name</clr-dg-cell> </clr-dg-row>`, }) class HideShowTest {}