diff --git a/src/lib/button/_button-base.scss b/src/lib/button/_button-base.scss index 810919549c69..2a354f37ab3d 100644 --- a/src/lib/button/_button-base.scss +++ b/src/lib/button/_button-base.scss @@ -55,7 +55,7 @@ $mat-mini-fab-padding: 8px !default; cursor: default; } - &.mat-button-focus { + &.cdk-keyboard-focused { .mat-button-focus-overlay { opacity: 1; } diff --git a/src/lib/button/_button-theme.scss b/src/lib/button/_button-theme.scss index fdf516d3505f..c77f5dbf202d 100644 --- a/src/lib/button/_button-theme.scss +++ b/src/lib/button/_button-theme.scss @@ -54,7 +54,7 @@ $foreground: map-get($theme, foreground); .mat-button, .mat-icon-button, .mat-raised-button, .mat-fab, .mat-mini-fab { - &.mat-button-focus { + &.cdk-keyboard-focused { @include _mat-button-focus-color($theme); } } diff --git a/src/lib/button/button.spec.ts b/src/lib/button/button.spec.ts index aba70a71e02e..d010953f47db 100644 --- a/src/lib/button/button.spec.ts +++ b/src/lib/button/button.spec.ts @@ -1,4 +1,4 @@ -import {async, TestBed, ComponentFixture} from '@angular/core/testing'; +import {async, ComponentFixture, TestBed} from '@angular/core/testing'; import {Component} from '@angular/core'; import {By} from '@angular/platform-browser'; import {MdButtonModule} from './index'; diff --git a/src/lib/button/button.ts b/src/lib/button/button.ts index 8cddd0d647a3..41d7a7c43a0a 100644 --- a/src/lib/button/button.ts +++ b/src/lib/button/button.ts @@ -1,17 +1,17 @@ import { - Component, - ViewEncapsulation, - Input, - HostBinding, ChangeDetectionStrategy, + Component, + Directive, ElementRef, + HostBinding, + Input, + OnDestroy, Renderer, - Directive, + ViewEncapsulation } from '@angular/core'; -import {coerceBooleanProperty} from '../core'; +import {coerceBooleanProperty, FocusOriginMonitor} from '../core'; -// TODO(jelbourn): Make the `isMouseDown` stuff done with one global listener. // TODO(kara): Convert attribute selectors to classes when attr maps become available @@ -85,25 +85,15 @@ export class MdMiniFabCssMatStyler {} 'button[mat-fab], button[mat-mini-fab]', host: { '[disabled]': 'disabled', - '[class.mat-button-focus]': '_isKeyboardFocused', - '(mousedown)': '_setMousedown()', - '(focus)': '_setKeyboardFocus()', - '(blur)': '_removeKeyboardFocus()', }, templateUrl: 'button.html', styleUrls: ['button.css'], encapsulation: ViewEncapsulation.None, changeDetection: ChangeDetectionStrategy.OnPush, }) -export class MdButton { +export class MdButton implements OnDestroy { private _color: string; - /** Whether the button has focus from the keyboard (not the mouse). Used for class binding. */ - _isKeyboardFocused: boolean = false; - - /** Whether a mousedown has occurred on this element in the last 100ms. */ - _isMouseDown: boolean = false; - /** Whether the button is round. */ _isRoundButton: boolean = ['icon-button', 'fab', 'mini-fab'].some(suffix => { let el = this._getHostElement(); @@ -124,22 +114,20 @@ export class MdButton { get disabled() { return this._disabled; } set disabled(value: boolean) { this._disabled = coerceBooleanProperty(value) ? true : null; } - constructor(private _elementRef: ElementRef, private _renderer: Renderer) { } + constructor(private _elementRef: ElementRef, private _renderer: Renderer, + private _focusOriginMonitor: FocusOriginMonitor) { + this._focusOriginMonitor.monitor(this._elementRef.nativeElement, this._renderer, true); + } + + ngOnDestroy() { + this._focusOriginMonitor.unmonitor(this._elementRef.nativeElement); + } /** The color of the button. Can be `primary`, `accent`, or `warn`. */ @Input() get color(): string { return this._color; } set color(value: string) { this._updateColor(value); } - _setMousedown() { - // We only *show* the focus style when focus has come to the button via the keyboard. - // The Material Design spec is silent on this topic, and without doing this, the - // button continues to look :active after clicking. - // @see http://marcysutton.com/button-focus-hell/ - this._isMouseDown = true; - setTimeout(() => { this._isMouseDown = false; }, 100); - } - _updateColor(newColor: string) { this._setElementColor(this._color, false); this._setElementColor(newColor, true); @@ -152,14 +140,6 @@ export class MdButton { } } - _setKeyboardFocus() { - this._isKeyboardFocused = !this._isMouseDown; - } - - _removeKeyboardFocus() { - this._isKeyboardFocused = false; - } - /** Focuses the button. */ focus(): void { this._renderer.invokeElementMethod(this._getHostElement(), 'focus'); @@ -184,10 +164,6 @@ export class MdButton { host: { '[attr.disabled]': 'disabled', '[attr.aria-disabled]': '_isAriaDisabled', - '[class.mat-button-focus]': '_isKeyboardFocused', - '(mousedown)': '_setMousedown()', - '(focus)': '_setKeyboardFocus()', - '(blur)': '_removeKeyboardFocus()', '(click)': '_haltDisabledEvents($event)', }, templateUrl: 'button.html', @@ -195,8 +171,8 @@ export class MdButton { encapsulation: ViewEncapsulation.None }) export class MdAnchor extends MdButton { - constructor(elementRef: ElementRef, renderer: Renderer) { - super(elementRef, renderer); + constructor(elementRef: ElementRef, renderer: Renderer, focusOriginMonitor: FocusOriginMonitor) { + super(elementRef, renderer, focusOriginMonitor); } /** @docs-private */ diff --git a/src/lib/button/index.ts b/src/lib/button/index.ts index 1f96453f5290..4d7ddd16408b 100644 --- a/src/lib/button/index.ts +++ b/src/lib/button/index.ts @@ -1,19 +1,27 @@ -import {NgModule, ModuleWithProviders} from '@angular/core'; +import {ModuleWithProviders, NgModule} from '@angular/core'; import {CommonModule} from '@angular/common'; -import {MdRippleModule, CompatibilityModule} from '../core'; +import {CompatibilityModule, MdRippleModule, StyleModule} from '../core'; import { - MdButton, MdAnchor, + MdButton, MdButtonCssMatStyler, - MdRaisedButtonCssMatStyler, - MdIconButtonCssMatStyler, MdFabCssMatStyler, + MdIconButtonCssMatStyler, MdMiniFabCssMatStyler, + MdRaisedButtonCssMatStyler } from './button'; +export * from './button'; + + @NgModule({ - imports: [CommonModule, MdRippleModule, CompatibilityModule], + imports: [ + CommonModule, + MdRippleModule, + CompatibilityModule, + StyleModule, + ], exports: [ MdButton, MdAnchor, @@ -22,7 +30,7 @@ import { MdRaisedButtonCssMatStyler, MdIconButtonCssMatStyler, MdFabCssMatStyler, - MdMiniFabCssMatStyler + MdMiniFabCssMatStyler, ], declarations: [ MdButton, @@ -31,7 +39,7 @@ import { MdRaisedButtonCssMatStyler, MdIconButtonCssMatStyler, MdFabCssMatStyler, - MdMiniFabCssMatStyler + MdMiniFabCssMatStyler, ], }) export class MdButtonModule { @@ -43,6 +51,3 @@ export class MdButtonModule { }; } } - - -export * from './button';