Skip to content

Commit 0099884

Browse files
jelbournDerek Louie
authored and
Derek Louie
committed
build: add most components to kitchen-sink (angular#4836)
* build: add most components to kitchen-sink * debug Terrible code just exporting for the sake of asking an question to Andrew
1 parent 549d622 commit 0099884

21 files changed

+475
-140
lines changed

src/demo-app/data-table/data-table-demo.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@
3838
<cdk-cell *cdkCellDef="let row" [style.color]="row.color"> {{row.color}} </cdk-cell>
3939
</ng-container>
4040

41-
<cdk-header-row *cdkHeaderRowDef="propertiesToDisplay"></cdk-header-row>
41+
<cdk-header-row *cdkHeaderRowDef="propertiesToDisplay" cdkStickyRow></cdk-header-row>
4242
<cdk-row *cdkRowDef="let row; columns: propertiesToDisplay"></cdk-row>
4343
</cdk-table>
4444
</div>

src/demo-app/data-table/data-table-demo.scss

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
// Table fills in the remaining area with a scroll
99
.cdk-table {
1010
flex: 1 1 auto;
11-
overflow: auto;
11+
/*overflow: auto;*/
1212
}
1313
}
1414

src/lib/chips/chip-list.spec.ts

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -47,14 +47,14 @@ describe('MdChipList', () => {
4747
manager = chipListInstance._keyManager;
4848
});
4949

50-
it('focuses the first chip on focus', () => {
50+
it('should focus the first chip on focus', () => {
5151
chipListInstance.focus();
5252
fixture.detectChanges();
5353

5454
expect(manager.activeItemIndex).toBe(0);
5555
});
5656

57-
it('watches for chip focus', () => {
57+
it('should watch for chip focus', () => {
5858
let array = chips.toArray();
5959
let lastIndex = array.length - 1;
6060
let lastItem = array[lastIndex];
@@ -81,13 +81,13 @@ describe('MdChipList', () => {
8181
expect(manager.activeItemIndex).toEqual(2);
8282
});
8383

84-
it('focuses the previous item', () => {
84+
it('should focus the previous item', () => {
8585
let array = chips.toArray();
8686
let lastIndex = array.length - 1;
8787
let lastItem = array[lastIndex];
8888

89-
// Focus the last item
90-
lastItem.focus();
89+
// Focus the last item by fake updating the _hasFocus state for unit tests.
90+
lastItem._hasFocus = true;
9191

9292
// Destroy the last item
9393
testComponent.remove = lastIndex;

src/lib/chips/chip-list.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -195,7 +195,7 @@ export class MdChipList implements AfterContentInit, OnDestroy {
195195
chip.destroy.subscribe(() => {
196196
let chipIndex: number = this.chips.toArray().indexOf(chip);
197197

198-
if (this._isValidIndex(chipIndex)) {
198+
if (this._isValidIndex(chipIndex) && chip._hasFocus) {
199199
// Check whether the chip is the last item
200200
if (chipIndex < this.chips.length - 1) {
201201
this._keyManager.setActiveItem(chipIndex);

src/lib/chips/chip.spec.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ describe('Chips', () => {
2929

3030
chipDebugElement = fixture.debugElement.query(By.directive(MdChip));
3131
chipNativeElement = chipDebugElement.nativeElement;
32-
chipInstance = chipDebugElement.componentInstance;
32+
chipInstance = chipDebugElement.injector.get(MdChip);
3333

3434
document.body.appendChild(chipNativeElement);
3535
});
@@ -56,7 +56,7 @@ describe('Chips', () => {
5656
chipDebugElement = fixture.debugElement.query(By.directive(MdChip));
5757
chipListNativeElement = fixture.debugElement.query(By.directive(MdChipList)).nativeElement;
5858
chipNativeElement = chipDebugElement.nativeElement;
59-
chipInstance = chipDebugElement.componentInstance;
59+
chipInstance = chipDebugElement.injector.get(MdChip);
6060
testComponent = fixture.debugElement.componentInstance;
6161

6262
document.body.appendChild(chipNativeElement);

src/lib/chips/chip.ts

Lines changed: 36 additions & 62 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,9 @@
11
import {
2-
Component,
2+
Directive,
33
ElementRef,
44
EventEmitter,
55
Input,
66
OnDestroy,
7-
OnInit,
87
Output,
98
Renderer2,
109
} from '@angular/core';
@@ -24,34 +23,52 @@ export class MdChipBase {
2423
export const _MdChipMixinBase = mixinColor(MdChipBase, 'primary');
2524

2625

26+
/**
27+
* Dummy directive to add CSS class to basic chips.
28+
* @docs-private
29+
*/
30+
@Directive({
31+
selector: `md-basic-chip, [md-basic-chip], mat-basic-chip, [mat-basic-chip]`,
32+
host: {'class': 'mat-basic-chip'}
33+
})
34+
export class MdBasicChip { }
35+
2736
/**
2837
* Material design styled Chip component. Used inside the MdChipList component.
2938
*/
30-
@Component({
39+
@Directive({
3140
selector: `md-basic-chip, [md-basic-chip], md-chip, [md-chip],
3241
mat-basic-chip, [mat-basic-chip], mat-chip, [mat-chip]`,
33-
template: `<ng-content></ng-content>`,
3442
inputs: ['color'],
3543
host: {
36-
'[class.mat-chip]': 'true',
44+
'class': 'mat-chip',
3745
'tabindex': '-1',
3846
'role': 'option',
39-
4047
'[class.mat-chip-selected]': 'selected',
41-
'[attr.disabled]': 'disabled',
42-
'[attr.aria-disabled]': '_isAriaDisabled',
43-
44-
'(click)': '_handleClick($event)'
48+
'[attr.disabled]': 'disabled || null',
49+
'[attr.aria-disabled]': '_isAriaDisabled()',
50+
'(click)': '_handleClick($event)',
51+
'(focus)': '_hasFocus = true',
52+
'(blur)': '_hasFocus = false',
4553
}
4654
})
47-
export class MdChip extends _MdChipMixinBase implements Focusable, OnInit, OnDestroy, CanColor {
48-
49-
/** Whether or not the chip is disabled. Disabled chips cannot be focused. */
55+
export class MdChip extends _MdChipMixinBase implements Focusable, OnDestroy, CanColor {
56+
/** Whether or not the chip is disabled. */
57+
@Input() get disabled(): boolean { return this._disabled; }
58+
set disabled(value: boolean) { this._disabled = coerceBooleanProperty(value); }
5059
protected _disabled: boolean = null;
5160

52-
/** Whether or not the chip is selected. */
61+
/** Whether the chip is selected. */
62+
@Input() get selected(): boolean { return this._selected; }
63+
set selected(value: boolean) {
64+
this._selected = coerceBooleanProperty(value);
65+
(this.selected ? this.select : this.deselect).emit({chip: this});
66+
}
5367
protected _selected: boolean = false;
5468

69+
/** Whether the chip has focus. */
70+
_hasFocus: boolean = false;
71+
5572
/** Emitted when the chip is focused. */
5673
onFocus = new EventEmitter<MdChipEvent>();
5774

@@ -68,44 +85,10 @@ export class MdChip extends _MdChipMixinBase implements Focusable, OnInit, OnDes
6885
super(renderer, elementRef);
6986
}
7087

71-
ngOnInit(): void {
72-
this._addDefaultCSSClass();
73-
}
74-
7588
ngOnDestroy(): void {
7689
this.destroy.emit({chip: this});
7790
}
7891

79-
/** Whether or not the chip is disabled. */
80-
@Input() get disabled(): boolean {
81-
return this._disabled;
82-
}
83-
84-
/** Sets the disabled state of the chip. */
85-
set disabled(value: boolean) {
86-
this._disabled = coerceBooleanProperty(value) ? true : null;
87-
}
88-
89-
/** A String representation of the current disabled state. */
90-
get _isAriaDisabled(): string {
91-
return String(coerceBooleanProperty(this.disabled));
92-
}
93-
94-
/** Whether or not this chip is selected. */
95-
@Input() get selected(): boolean {
96-
return this._selected;
97-
}
98-
99-
set selected(value: boolean) {
100-
this._selected = coerceBooleanProperty(value);
101-
102-
if (this._selected) {
103-
this.select.emit({chip: this});
104-
} else {
105-
this.deselect.emit({chip: this});
106-
}
107-
}
108-
10992
/**
11093
* Toggles the current selected state of this chip.
11194
* @return Whether the chip is selected.
@@ -121,6 +104,11 @@ export class MdChip extends _MdChipMixinBase implements Focusable, OnInit, OnDes
121104
this.onFocus.emit({chip: this});
122105
}
123106

107+
/** The aria-disabled state for the chip */
108+
_isAriaDisabled(): string {
109+
return String(this.disabled);
110+
}
111+
124112
/** Ensures events fire properly upon click. */
125113
_handleClick(event: Event) {
126114
// Check disabled
@@ -131,18 +119,4 @@ export class MdChip extends _MdChipMixinBase implements Focusable, OnInit, OnDes
131119
this.focus();
132120
}
133121
}
134-
135-
/** Initializes the appropriate CSS classes based on the chip type (basic or standard). */
136-
private _addDefaultCSSClass() {
137-
let el: HTMLElement = this._elementRef.nativeElement;
138-
139-
// Always add the `mat-chip` class
140-
this._renderer.addClass(el, 'mat-chip');
141-
142-
// If we are a basic chip, also add the `mat-basic-chip` class for :not() targeting
143-
if (el.nodeName.toLowerCase() == 'mat-basic-chip' || el.hasAttribute('mat-basic-chip') ||
144-
el.nodeName.toLowerCase() == 'md-basic-chip' || el.hasAttribute('md-basic-chip')) {
145-
this._renderer.addClass(el, 'mat-basic-chip');
146-
}
147-
}
148122
}

src/lib/chips/index.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,12 @@
11
import {NgModule} from '@angular/core';
22
import {MdChipList} from './chip-list';
3-
import {MdChip} from './chip';
3+
import {MdChip, MdBasicChip} from './chip';
44

55

66
@NgModule({
77
imports: [],
8-
exports: [MdChipList, MdChip],
9-
declarations: [MdChipList, MdChip]
8+
exports: [MdChipList, MdChip, MdBasicChip],
9+
declarations: [MdChipList, MdChip, MdBasicChip]
1010
})
1111
export class MdChipsModule {}
1212

src/lib/core/_core.scss

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
@import 'option/optgroup-theme';
1010
@import 'selection/pseudo-checkbox/pseudo-checkbox-theme';
1111
@import 'typography/all-typography';
12+
@import 'data-table/data-table';
1213

1314
// Mixin that renders all of the core styles that are not theme-dependent.
1415
@mixin mat-core() {
@@ -27,6 +28,7 @@
2728
@include mat-optgroup();
2829
@include cdk-a11y();
2930
@include cdk-overlay();
31+
@include cdk-data-table();
3032
}
3133

3234
// Mixin that renders all of the core styles that depend on the theme.

src/lib/core/a11y/focus-trap.ts

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,12 @@ import {
88
Injectable,
99
} from '@angular/core';
1010
import {InteractivityChecker} from './interactivity-checker';
11+
import {Platform} from '../platform/platform';
1112
import {coerceBooleanProperty} from '../coercion/boolean-property';
1213

1314
import 'rxjs/add/operator/first';
1415

16+
1517
/**
1618
* Class that allows for trapping focus within a DOM element.
1719
*
@@ -37,6 +39,7 @@ export class FocusTrap {
3739

3840
constructor(
3941
private _element: HTMLElement,
42+
private _platform: Platform,
4043
private _checker: InteractivityChecker,
4144
private _ngZone: NgZone,
4245
deferAnchors = false) {
@@ -64,6 +67,11 @@ export class FocusTrap {
6467
* in the constructor, but can be deferred for cases like directives with `*ngIf`.
6568
*/
6669
attachAnchors(): void {
70+
// If we're not on the browser, there can be no focus to trap.
71+
if (!this._platform.isBrowser) {
72+
return;
73+
}
74+
6775
if (!this._startAnchor) {
6876
this._startAnchor = this._createAnchor();
6977
}
@@ -223,10 +231,13 @@ export class FocusTrap {
223231
/** Factory that allows easy instantiation of focus traps. */
224232
@Injectable()
225233
export class FocusTrapFactory {
226-
constructor(private _checker: InteractivityChecker, private _ngZone: NgZone) { }
234+
constructor(
235+
private _checker: InteractivityChecker,
236+
private _platform: Platform,
237+
private _ngZone: NgZone) { }
227238

228239
create(element: HTMLElement, deferAnchors = false): FocusTrap {
229-
return new FocusTrap(element, this._checker, this._ngZone, deferAnchors);
240+
return new FocusTrap(element, this._platform, this._checker, this._ngZone, deferAnchors);
230241
}
231242
}
232243

src/lib/core/a11y/interactivity-checker.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,10 @@ export class InteractivityChecker {
4848
* @returns Whether the element is tabbable.
4949
*/
5050
isTabbable(element: HTMLElement): boolean {
51+
// Nothing is tabbable on the the server 😎
52+
if (!this._platform.isBrowser) {
53+
return false;
54+
}
5155

5256
let frameElement = getWindow(element).frameElement as HTMLElement;
5357

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
/*CSS FOR THE DATA TABLE*/
2+
@mixin cdk-data-table() {
3+
.cdk-table {
4+
position: relative;
5+
}
6+
7+
.cdk-table-body {
8+
overflow-y: auto;
9+
pointer-events: auto;
10+
// MOVE TO JS
11+
padding-top: 48px;
12+
height: 390px;
13+
}
14+
15+
.cdk-header-row {
16+
overflow: hidden;
17+
width: 100%;
18+
}
19+
20+
.cdk-sticky-row {
21+
background-color: white;
22+
z-index: 1;
23+
left: 0;
24+
// ORDER MATTERS WITH THESE OVERFLOW RULES
25+
overflow: scroll;
26+
overflow-x: hidden;
27+
overflow-y: hidden;
28+
position: absolute;
29+
top: 0;
30+
box-sizing: border-box;
31+
}
32+
}

0 commit comments

Comments
 (0)