Skip to content
This repository was archived by the owner on Jan 6, 2025. It is now read-only.

Commit 5db01e7

Browse files
ThomasBurlesontinayuangao
authored andcommitted
fix(ngClass,ngStyle): support proper API usages and ChangeDetectionStrategy.OnPush strategies (#228)
* fix(ngClass): properly differentiate between `ngClass` and `class` api usages * `class.<xxx>` are destructive overrides (as seen in `NgClass::klass`) * `ngClass.<xxx>` use iterables to merge/enable/disable 0...n classes * fix(ngClass,ngStyle): support ChangeDetectionStrategy.OnPush * Add support for both **OnPush** change detection strategies and for @input changes. * fix class lt-<xx> selectors > @see https://plnkr.co/edit/jCICQ1GXFnzFqFTFlXwh?p=preview fixes #206, fixes #215.
1 parent 3743282 commit 5db01e7

File tree

6 files changed

+666
-131
lines changed

6 files changed

+666
-131
lines changed

src/lib/flexbox/api/base-adapter.spec.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ export class MockElementRef extends ElementRef {
2020
describe('BaseFxDirectiveAdapter class', () => {
2121
let component;
2222
beforeEach(() => {
23-
component = new BaseFxDirectiveAdapter(null, new MockElementRef(), null);
23+
component = new BaseFxDirectiveAdapter(null, null, new MockElementRef(), null);
2424
});
2525
describe('cacheInput', () => {
2626
it('should call _cacheInputArray when source is an array', () => {

src/lib/flexbox/api/base-adapter.ts

+36-1
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,36 @@
1+
/**
2+
* @license
3+
* Copyright Google Inc. All Rights Reserved.
4+
*
5+
* Use of this source code is governed by an MIT-style license that can be
6+
* found in the LICENSE file at https://angular.io/license
7+
*/
8+
import {ElementRef, Renderer} from '@angular/core';
9+
110
import {BaseFxDirective} from './base';
211
import {ResponsiveActivation} from './../responsive/responsive-activation';
312
import {MediaQuerySubscriber} from '../../media-query/media-change';
13+
import {MediaMonitor} from '../../media-query/media-monitor';
14+
415

516
/**
617
* Adapter to the BaseFxDirective abstract class so it can be used via composition.
718
* @see BaseFxDirective
819
*/
920
export class BaseFxDirectiveAdapter extends BaseFxDirective {
21+
22+
/**
23+
* Accessor to determine which @Input property is "active"
24+
* e.g. which property value will be used.
25+
*/
26+
get activeKey() {
27+
let mqa = this._mqActivation;
28+
let key = mqa ? mqa.activatedInputKey : this._baseKey;
29+
// Note: ClassDirective::SimpleChanges uses 'klazz' instead of 'class' as a key
30+
return (key === 'class') ? 'klazz' : key;
31+
}
32+
33+
/** Hash map of all @Input keys/values defined/used */
1034
get inputMap() {
1135
return this._inputMap;
1236
}
@@ -18,11 +42,22 @@ export class BaseFxDirectiveAdapter extends BaseFxDirective {
1842
return this._mqActivation;
1943
}
2044

45+
/**
46+
* BaseFxDirectiveAdapter constructor
47+
*/
48+
constructor(protected _baseKey: string, // non-responsive @Input property name
49+
protected _mediaMonitor: MediaMonitor,
50+
protected _elementRef: ElementRef,
51+
protected _renderer: Renderer ) {
52+
super(_mediaMonitor, _elementRef, _renderer);
53+
}
54+
55+
2156
/**
2257
* @see BaseFxDirective._queryInput
2358
*/
2459
queryInput(key) {
25-
return this._queryInput(key);
60+
return key ? this._queryInput(key) : undefined;
2661
}
2762

2863
/**

src/lib/flexbox/api/base.ts

+25-19
Original file line numberDiff line numberDiff line change
@@ -22,20 +22,10 @@ export type StyleDefinition = string|{[property: string]: string|number};
2222

2323
/** Abstract base class for the Layout API styling directives. */
2424
export abstract class BaseFxDirective implements OnDestroy {
25-
/**
26-
* Original dom Elements CSS display style
27-
*/
28-
protected _display;
2925

30-
/**
31-
* MediaQuery Activation Tracker
32-
*/
33-
protected _mqActivation: ResponsiveActivation;
34-
35-
/**
36-
* Dictionary of input keys with associated values
37-
*/
38-
protected _inputMap = {};
26+
get hasMediaQueryListener() {
27+
return !!this._mqActivation;
28+
}
3929

4030
/**
4131
*
@@ -46,6 +36,7 @@ export abstract class BaseFxDirective implements OnDestroy {
4636
this._display = this._getDisplayStyle();
4737
}
4838

39+
4940
// *********************************************
5041
// Accessor Methods
5142
// *********************************************
@@ -172,12 +163,15 @@ export abstract class BaseFxDirective implements OnDestroy {
172163
protected _listenForMediaQueryChanges(key: string,
173164
defaultValue: any,
174165
onMediaQueryChange: MediaQuerySubscriber): ResponsiveActivation { // tslint:disable-line:max-line-length
175-
let keyOptions = new KeyOptions(key, defaultValue, this._inputMap);
176-
return this._mqActivation = new ResponsiveActivation(
177-
keyOptions,
178-
this._mediaMonitor,
179-
(change) => onMediaQueryChange.call(this, change)
180-
);
166+
if ( !this._mqActivation ) {
167+
let keyOptions = new KeyOptions(key, defaultValue, this._inputMap);
168+
this._mqActivation = new ResponsiveActivation(
169+
keyOptions,
170+
this._mediaMonitor,
171+
(change) => onMediaQueryChange(change)
172+
);
173+
}
174+
return this._mqActivation;
181175
}
182176

183177
/**
@@ -201,4 +195,16 @@ export abstract class BaseFxDirective implements OnDestroy {
201195
return this._mqActivation.hasKeyValue(key);
202196
}
203197

198+
/** Original dom Elements CSS display style */
199+
protected _display;
200+
201+
/**
202+
* MediaQuery Activation Tracker
203+
*/
204+
protected _mqActivation: ResponsiveActivation;
205+
206+
/**
207+
* Dictionary of input keys with associated values
208+
*/
209+
protected _inputMap = {};
204210
}

0 commit comments

Comments
 (0)