Skip to content
This repository was archived by the owner on Oct 7, 2020. It is now read-only.

Commit 3c6ccc1

Browse files
authored
feat(card): Add [mdc-card-button] + refactoring (#90)
* refactor(card): External directives merged into card.component file * feat(card): Add [mdc-card-button] to card component * refactor(card): Remove [darkTheme] property. BREAKING CHANGE: Property [cardAction] of mdc-button was removed, you'll need to use mdc-card-button. Please update your code accordingly. BREAKING CHANGE: [darkTheme] property was removed from Card. Use [mdc-theme-dark] instead.
1 parent 9b96e1d commit 3c6ccc1

11 files changed

+146
-173
lines changed

src/lib/button/button.component.ts

Lines changed: 11 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -4,9 +4,7 @@ import {
44
HostBinding,
55
HostListener,
66
Input,
7-
OnChanges,
87
Renderer2,
9-
SimpleChange,
108
ViewEncapsulation
119
} from '@angular/core';
1210
import { Ripple } from '.././ripple/ripple.directive';
@@ -20,30 +18,29 @@ import { isSpaceKey } from '../common/events';
2018
encapsulation: ViewEncapsulation.None,
2119
providers: [Ripple]
2220
})
23-
export class ButtonComponent implements OnChanges {
24-
private _disabled: boolean = false;
21+
export class ButtonComponent {
22+
private disabled_: boolean = false;
2523

2624
@Input() type: string;
2725
@Input() raised: boolean;
2826
@Input() primary: boolean;
2927
@Input() dense: boolean;
3028
@Input() compact: boolean;
3129
@Input() accent: boolean;
32-
@Input() cardAction: boolean;
3330
@Input()
34-
get disabled() { return this._disabled; }
31+
get disabled() { return this.disabled_; }
3532
set disabled(value) {
36-
this._disabled = toBoolean(value);
37-
if (this._disabled) {
33+
this.disabled_ = toBoolean(value);
34+
if (this.disabled_) {
3835
this.renderer.setAttribute(this.elementRef.nativeElement, "disabled", 'true');
3936
} else {
4037
this.renderer.removeAttribute(this.elementRef.nativeElement, "disabled");
4138
}
4239
}
4340
@Input()
44-
get disableRipple() { return this._ripple.disabled; }
41+
get disableRipple() { return this.ripple.disabled; }
4542
set disableRipple(value) {
46-
this._ripple.disabled = toBoolean(value);
43+
this.ripple.disabled = toBoolean(value);
4744
}
4845
@HostBinding('tabindex') get tabindex(): number {
4946
return this.disabled ? -1 : 0;
@@ -67,9 +64,6 @@ export class ButtonComponent implements OnChanges {
6764
@HostBinding('class.mdc-button--compact') get classCompact(): string {
6865
return this.compact ? 'mdc-button--compact' : '';
6966
}
70-
@HostBinding('class.mdc-card__action') get classCardAction(): string {
71-
return this.cardAction ? 'mdc-card__action' : '';
72-
}
7367
@HostListener('keypress', ['$event']) onkeypress(evt) {
7468
this.handleKeyPress_(evt);
7569
}
@@ -80,33 +74,21 @@ export class ButtonComponent implements OnChanges {
8074
constructor(
8175
public renderer: Renderer2,
8276
public elementRef: ElementRef,
83-
private _ripple: Ripple) {
84-
this._ripple.init();
85-
}
86-
87-
ngOnChanges(changes: { [key: string]: SimpleChange }) {
88-
let change = changes['cardAction'];
89-
90-
if (change) {
91-
if (!toBoolean(change.currentValue)) {
92-
this.compact = false;
93-
} else {
94-
this.compact = true;
95-
}
96-
}
77+
public ripple: Ripple) {
78+
this.ripple.init();
9779
}
9880

9981
private handleKeyPress_(keyboardEvent: KeyboardEvent) {
10082
let keyCode = keyboardEvent.keyCode;
10183
if (keyCode == KeyCodes.ENTER || isSpaceKey(keyboardEvent)) {
102-
this._ripple.active = true;
84+
this.ripple.active = true;
10385
if (keyCode != KeyCodes.ENTER) {
10486
keyboardEvent.preventDefault();
10587
}
10688
}
10789
}
10890

10991
private handleBlur_(focusEvent: FocusEvent) {
110-
this._ripple.active = false;
92+
this.ripple.active = false;
11193
}
11294
}

src/lib/card/card-actions.directive.ts

Lines changed: 0 additions & 16 deletions
This file was deleted.

src/lib/card/card-horizontal.component.ts

Lines changed: 0 additions & 14 deletions
This file was deleted.

src/lib/card/card-media-item.directive.ts

Lines changed: 0 additions & 25 deletions
This file was deleted.

src/lib/card/card-media.component.ts

Lines changed: 0 additions & 14 deletions
This file was deleted.

src/lib/card/card-primary.directive.ts

Lines changed: 0 additions & 11 deletions
This file was deleted.

src/lib/card/card-subtitle.directive.ts

Lines changed: 0 additions & 11 deletions
This file was deleted.

src/lib/card/card-supporting-text.directive.ts

Lines changed: 0 additions & 11 deletions
This file was deleted.

src/lib/card/card-title.directive.ts

Lines changed: 0 additions & 16 deletions
This file was deleted.

src/lib/card/card.component.ts

Lines changed: 117 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,132 @@
11
import {
2+
AfterContentInit,
23
Component,
4+
ContentChildren,
5+
Directive,
6+
ElementRef,
37
HostBinding,
8+
Inject,
49
Input,
10+
QueryList,
11+
Renderer2,
512
ViewEncapsulation,
613
} from '@angular/core';
14+
import { toBoolean } from '../common/boolean-property';
15+
16+
import { Ripple } from '../ripple/ripple.directive';
17+
import { ButtonComponent } from '../button/button.component';
18+
19+
@Directive({
20+
selector: 'mdc-card-primary'
21+
})
22+
export class CardPrimaryDirective {
23+
@HostBinding('class.mdc-card__primary') isHostClass = true;
24+
}
25+
26+
@Component({
27+
selector: 'mdc-card-horizontal',
28+
template: '<ng-content select="mdc-card-primary, mdc-card-title, mdc-card-subtitle, [mdc-card-media-item], mdc-card-actions"></ng-content>',
29+
encapsulation: ViewEncapsulation.None
30+
})
31+
export class CardHorizontalComponent {
32+
@HostBinding('class.mdc-card__horizontal-block') isHostClass = true;
33+
}
34+
35+
@Directive({
36+
selector: '[mdc-card-title], mdc-card-title'
37+
})
38+
export class CardTitleDirective {
39+
@Input() large: boolean = true;
40+
@HostBinding('class.mdc-card__title') isHostClass = true;
41+
@HostBinding('class.mdc-card__title--large') get classTitleLarge(): string {
42+
return this.large ? 'mdc-card__title--large' : '';
43+
}
44+
}
45+
46+
@Directive({
47+
selector: '[mdc-card-subtitle], mdc-card-subtitle'
48+
})
49+
export class CardSubtitleComponent {
50+
@HostBinding('class.mdc-card__subtitle') isHostClass = true;
51+
}
52+
53+
@Directive({
54+
selector: '[mdc-card-supporting-text], mdc-card-supporting-text'
55+
})
56+
export class CardSupportingTextDirective {
57+
@HostBinding('class.mdc-card__supporting-text') isHostClass = true;
58+
}
59+
60+
@Directive({
61+
selector: '[mdc-card-media-item]'
62+
})
63+
export class CardMediaItemDirective {
64+
@Input() size: number;
65+
@HostBinding('class.mdc-card__media-item') isHostClass = true;
66+
@HostBinding('class.mdc-card__media-item--1dot5x') get classMediaItemOne(): string {
67+
return this.size === 1 ? 'mdc-card__media-item--1x' : '';
68+
}
69+
@HostBinding('class.mdc-card__media-item--1dot5x') get classMediaItemOneDotFive(): string {
70+
return this.size === 1.5 ? 'mdc-card__media-item--1dot5x' : '';
71+
}
72+
@HostBinding('class.mdc-card__media-item--2x') get classMediaItemTwo(): string {
73+
return this.size === 2 ? 'mdc-card__media-item--2x' : '';
74+
}
75+
@HostBinding('class.mdc-card__media-item--3x') get classMediaItemThree(): string {
76+
return this.size === 3 ? 'mdc-card__media-item--3x' : '';
77+
}
78+
}
79+
80+
@Component({
81+
selector: 'mdc-card-media',
82+
template: '<ng-content></ng-content>',
83+
encapsulation: ViewEncapsulation.None
84+
})
85+
export class CardMediaComponent {
86+
@HostBinding('class.mdc-card__media') isHostClass = true;
87+
}
88+
89+
@Directive({
90+
selector: 'mdc-card-actions'
91+
})
92+
export class CardActionsDirective {
93+
@Input() vertical: boolean;
94+
@HostBinding('class.mdc-card__actions') isHostClass = true;
95+
@HostBinding('class.mdc-card__actions--vertical') get classCardActionVertical(): string {
96+
return this.vertical ? 'mdc-card__actions--vertical' : '';
97+
}
98+
}
99+
100+
@Directive({
101+
selector: 'button[mdc-card-button], a[mdc-card-button]',
102+
providers: [Ripple]
103+
})
104+
export class CardActionButtonDirective extends ButtonComponent {
105+
constructor(
106+
@Inject(Renderer2) renderer: Renderer2,
107+
@Inject(ElementRef) elementRef: ElementRef,
108+
@Inject(Ripple) ripple: Ripple) {
109+
super(renderer, elementRef, ripple);
110+
}
111+
}
7112

8113
@Component({
9114
selector: 'mdc-card',
10115
template: '<ng-content></ng-content>',
11116
encapsulation: ViewEncapsulation.None
12117
})
13-
export class CardComponent {
14-
@Input() darkTheme: boolean;
118+
export class CardComponent implements AfterContentInit {
15119
@HostBinding('class.mdc-card') isHostClass = true;
16-
@HostBinding('class.mdc-card--theme-dark') get classDarkTheme(): string {
17-
return this.darkTheme ? 'mdc-card--theme-dark' : '';
120+
@ContentChildren(CardActionButtonDirective, { descendants: true }) cardButtons: QueryList<CardActionButtonDirective>;
121+
122+
constructor(
123+
private _renderer: Renderer2,
124+
public elementRef: ElementRef) { }
125+
126+
ngAfterContentInit() {
127+
this.cardButtons.forEach((_) => {
128+
this._renderer.addClass(_.elementRef.nativeElement, 'mdc-card__action');
129+
_.compact = true;
130+
});
18131
}
19132
}

0 commit comments

Comments
 (0)