docs(query): edit and extend query and view query docs.
This commit is contained in:
parent
3525d8a394
commit
5809a02624
@ -3,73 +3,7 @@ library angular2.src.core.compiler.query_list;
|
|||||||
import 'dart:collection';
|
import 'dart:collection';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An iterable and observable live list of components in the DOM.
|
* See query_list.ts
|
||||||
*
|
|
||||||
* A QueryList contains a live list of child directives in the DOM of a directive.
|
|
||||||
* The directives are kept in depth-first pre-order traversal of the DOM.
|
|
||||||
*
|
|
||||||
* The `QueryList` is iterable, therefore it can be used in both javascript code with `for..of` loop
|
|
||||||
* as well as in template with `*ng-for="of"` directive.
|
|
||||||
*
|
|
||||||
* QueryList is updated as part of the change-detection cycle of a directive. Since change detection
|
|
||||||
* happens after construction of a directive, QueryList will always be empty when observed in the
|
|
||||||
* constructor.
|
|
||||||
*
|
|
||||||
*
|
|
||||||
* NOTE: In the future this class will implement an `Observable` interface. For now it uses a plain
|
|
||||||
* list of observable callbacks.
|
|
||||||
*
|
|
||||||
* # Example:
|
|
||||||
*
|
|
||||||
* Assume that `<tabs>` component would like to get a list its children which are `<pane>`
|
|
||||||
* components as shown in this example:
|
|
||||||
*
|
|
||||||
* ```html
|
|
||||||
* <tabs>
|
|
||||||
* <pane title="Overview">...</pane>
|
|
||||||
* <pane *ng-for="#o of objects" [title]="o.title">{{o.text}}</pane>
|
|
||||||
* </tabs>
|
|
||||||
* ```
|
|
||||||
*
|
|
||||||
* In the above example the list of `<tabs>` elements needs to get a list of `<pane>` elements so
|
|
||||||
* that it could render tabs with the correct titles and in the correct order.
|
|
||||||
*
|
|
||||||
* A possible solution would be for a `<pane>` to inject `<tabs>` component and then register itself
|
|
||||||
* with `<tabs>` component's on `hydrate` and deregister on `dehydrate` event. While a reasonable
|
|
||||||
* approach, this would only work partialy since `*ng-for` could rearrange the list of `<pane>`
|
|
||||||
* components which would not be reported to `<tabs>` component and thus the list of `<pane>`
|
|
||||||
* components would be out of sync with respect to the list of `<pane>` elements.
|
|
||||||
*
|
|
||||||
* A preferred solution is to inject a `QueryList` which is a live list of directives in the
|
|
||||||
* component`s light DOM.
|
|
||||||
*
|
|
||||||
* ```javascript
|
|
||||||
* @Component(
|
|
||||||
* selector: 'tabs'
|
|
||||||
* )
|
|
||||||
* @View(
|
|
||||||
* template: `
|
|
||||||
* <ul>
|
|
||||||
* <li *ng-for="#pane of panes">{{pane.title}}</li>
|
|
||||||
* </ul>
|
|
||||||
* <content></content>
|
|
||||||
* `
|
|
||||||
* )
|
|
||||||
* class Tabs {
|
|
||||||
* QueryList<Pane> panes;
|
|
||||||
*
|
|
||||||
* constructor(@Query(Pane) QueryList<Pane> this.panes) { }
|
|
||||||
* }
|
|
||||||
*
|
|
||||||
* @Component(
|
|
||||||
* selector: 'pane',
|
|
||||||
* properties: ['title']
|
|
||||||
* )
|
|
||||||
* @View(...)
|
|
||||||
* class Pane {
|
|
||||||
* String title;
|
|
||||||
* }
|
|
||||||
* ```
|
|
||||||
*/
|
*/
|
||||||
class QueryList<T> extends Object
|
class QueryList<T> extends Object
|
||||||
with IterableMixin<T> {
|
with IterableMixin<T> {
|
||||||
@ -79,6 +13,7 @@ class QueryList<T> extends Object
|
|||||||
|
|
||||||
Iterator<T> get iterator => _results.iterator;
|
Iterator<T> get iterator => _results.iterator;
|
||||||
|
|
||||||
|
/** @private */
|
||||||
void reset(List<T> newList) {
|
void reset(List<T> newList) {
|
||||||
_results = newList;
|
_results = newList;
|
||||||
_dirty = true;
|
_dirty = true;
|
||||||
@ -89,7 +24,6 @@ class QueryList<T> extends Object
|
|||||||
_dirty = true;
|
_dirty = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void onChange(callback) {
|
void onChange(callback) {
|
||||||
_callbacks.add(callback);
|
_callbacks.add(callback);
|
||||||
}
|
}
|
||||||
@ -114,7 +48,7 @@ class QueryList<T> extends Object
|
|||||||
return this._results.map(fn).toList();
|
return this._results.map(fn).toList();
|
||||||
}
|
}
|
||||||
|
|
||||||
// Internal to the framework.
|
/** @private */
|
||||||
void fireCallbacks() {
|
void fireCallbacks() {
|
||||||
if (_dirty) {
|
if (_dirty) {
|
||||||
_callbacks.forEach((c) => c());
|
_callbacks.forEach((c) => c());
|
||||||
|
@ -3,74 +3,27 @@ import {getSymbolIterator} from 'angular2/src/core/facade/lang';
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An iterable and observable live list of components in the DOM.
|
* An unmodifiable list of items that Angular keeps up to date when the state
|
||||||
|
* of the application changes.
|
||||||
*
|
*
|
||||||
* A QueryList contains a live list of child directives in the DOM of a directive.
|
* The type of object that {@link QueryMetadata} and {@link ViewQueryMetadata} provide.
|
||||||
* The directives are kept in depth-first pre-order traversal of the DOM.
|
|
||||||
*
|
*
|
||||||
* The `QueryList` is iterable, therefore it can be used in both javascript code with `for..of` loop
|
* Implements an iterable interface, therefore it can be used in both ES6
|
||||||
* as well as in template with `*ng-for="of"` directive.
|
* javascript `for (var i of items)` loops as well as in Angular templates with
|
||||||
|
* `*ng-for="#i of myList"`.
|
||||||
*
|
*
|
||||||
* QueryList is updated as part of the change-detection cycle of a directive. Since change detection
|
* Changes can be observed by attaching callbacks.
|
||||||
* happens after construction of a directive, QueryList will always be empty when observed in the
|
|
||||||
* constructor.
|
|
||||||
*
|
*
|
||||||
|
* NOTE: In the future this class will implement an `Observable` interface.
|
||||||
*
|
*
|
||||||
* NOTE: In the future this class will implement an `Observable` interface. For now it uses a plain
|
* ### Example ([live demo](http://plnkr.co/edit/RX8sJnQYl9FWuSCWme5z?p=preview))
|
||||||
* list of observable callbacks.
|
|
||||||
*
|
|
||||||
* # Example:
|
|
||||||
*
|
|
||||||
* Assume that `<tabs>` component would like to get a list its children which are `<pane>`
|
|
||||||
* components as shown in this example:
|
|
||||||
*
|
|
||||||
* ```html
|
|
||||||
* <tabs>
|
|
||||||
* <pane title="Overview">...</pane>
|
|
||||||
* <pane *ng-for="#o of objects" [title]="o.title">{{o.text}}</pane>
|
|
||||||
* </tabs>
|
|
||||||
* ```
|
|
||||||
*
|
|
||||||
* In the above example the list of `<tabs>` elements needs to get a list of `<pane>` elements so
|
|
||||||
* that it could render tabs with the correct titles and in the correct order.
|
|
||||||
*
|
|
||||||
* A possible solution would be for a `<pane>` to inject `<tabs>` component and then register itself
|
|
||||||
* with `<tabs>` component's on `hydrate` and deregister on `dehydrate` event. While a reasonable
|
|
||||||
* approach, this would only work partially since `*ng-for` could rearrange the list of `<pane>`
|
|
||||||
* components which would not be reported to `<tabs>` component and thus the list of `<pane>`
|
|
||||||
* components would be out of sync with respect to the list of `<pane>` elements.
|
|
||||||
*
|
|
||||||
* A preferred solution is to inject a `QueryList` which is a live list of directives in the
|
|
||||||
* component`s light DOM.
|
|
||||||
*
|
|
||||||
* ```javascript
|
* ```javascript
|
||||||
* @Component({
|
* @Component({...})
|
||||||
* selector: 'tabs'
|
* class Container {
|
||||||
* })
|
* constructor(@Query(Item) items: QueryList<Item>) {
|
||||||
* @View({
|
* items.onChange(() => console.log(items.length));
|
||||||
* template: `
|
|
||||||
* <ul>
|
|
||||||
* <li *ng-for="#pane of panes">{{pane.title}}</li>
|
|
||||||
* </ul>
|
|
||||||
* <content></content>
|
|
||||||
* `
|
|
||||||
* })
|
|
||||||
* class Tabs {
|
|
||||||
* panes: QueryList<Pane>
|
|
||||||
*
|
|
||||||
* constructor(@Query(Pane) panes:QueryList<Pane>) {
|
|
||||||
* this.panes = panes;
|
|
||||||
* }
|
* }
|
||||||
* }
|
* }
|
||||||
*
|
|
||||||
* @Component({
|
|
||||||
* selector: 'pane',
|
|
||||||
* properties: ['title']
|
|
||||||
* })
|
|
||||||
* @View(...)
|
|
||||||
* class Pane {
|
|
||||||
* title:string;
|
|
||||||
* }
|
|
||||||
* ```
|
* ```
|
||||||
*/
|
*/
|
||||||
export class QueryList<T> {
|
export class QueryList<T> {
|
||||||
@ -78,21 +31,31 @@ export class QueryList<T> {
|
|||||||
protected _callbacks: Array < () => void >= [];
|
protected _callbacks: Array < () => void >= [];
|
||||||
protected _dirty: boolean = false;
|
protected _dirty: boolean = false;
|
||||||
|
|
||||||
|
/** @private */
|
||||||
reset(newList: T[]): void {
|
reset(newList: T[]): void {
|
||||||
this._results = newList;
|
this._results = newList;
|
||||||
this._dirty = true;
|
this._dirty = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** @private */
|
||||||
add(obj: T): void {
|
add(obj: T): void {
|
||||||
this._results.push(obj);
|
this._results.push(obj);
|
||||||
this._dirty = true;
|
this._dirty = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* registers a callback that is called upon each change.
|
||||||
|
*/
|
||||||
onChange(callback: () => void): void { this._callbacks.push(callback); }
|
onChange(callback: () => void): void { this._callbacks.push(callback); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* removes a given callback.
|
||||||
|
*/
|
||||||
removeCallback(callback: () => void): void { ListWrapper.remove(this._callbacks, callback); }
|
removeCallback(callback: () => void): void { ListWrapper.remove(this._callbacks, callback); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* removes all callback that have been attached.
|
||||||
|
*/
|
||||||
removeAllCallbacks(): void { this._callbacks = []; }
|
removeAllCallbacks(): void { this._callbacks = []; }
|
||||||
|
|
||||||
toString(): string { return this._results.toString(); }
|
toString(): string { return this._results.toString(); }
|
||||||
@ -101,11 +64,14 @@ export class QueryList<T> {
|
|||||||
get first(): T { return ListWrapper.first(this._results); }
|
get first(): T { return ListWrapper.first(this._results); }
|
||||||
get last(): T { return ListWrapper.last(this._results); }
|
get last(): T { return ListWrapper.last(this._results); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* returns a new list with the passsed in function applied to each element.
|
||||||
|
*/
|
||||||
map<U>(fn: (item: T) => U): U[] { return this._results.map(fn); }
|
map<U>(fn: (item: T) => U): U[] { return this._results.map(fn); }
|
||||||
|
|
||||||
[getSymbolIterator()](): any { return this._results[getSymbolIterator()](); }
|
[getSymbolIterator()](): any { return this._results[getSymbolIterator()](); }
|
||||||
|
|
||||||
// Internal to the framework.
|
/** @private */
|
||||||
fireCallbacks(): void {
|
fireCallbacks(): void {
|
||||||
if (this._dirty) {
|
if (this._dirty) {
|
||||||
ListWrapper.forEach(this._callbacks, (c) => c());
|
ListWrapper.forEach(this._callbacks, (c) => c());
|
||||||
|
@ -335,7 +335,7 @@ export interface AttributeFactory {
|
|||||||
/**
|
/**
|
||||||
* {@link QueryMetadata} factory for creating annotations, decorators or DSL.
|
* {@link QueryMetadata} factory for creating annotations, decorators or DSL.
|
||||||
*
|
*
|
||||||
* ## Example as TypeScript Decorator
|
* ### Example as TypeScript Decorator
|
||||||
*
|
*
|
||||||
* ```
|
* ```
|
||||||
* import {Query, QueryList, Component, View} from "angular2/angular2";
|
* import {Query, QueryList, Component, View} from "angular2/angular2";
|
||||||
@ -343,13 +343,13 @@ export interface AttributeFactory {
|
|||||||
* @Component({...})
|
* @Component({...})
|
||||||
* @View({...})
|
* @View({...})
|
||||||
* class MyComponent {
|
* class MyComponent {
|
||||||
* constructor(@Query(SomeType) queryList: QueryList) {
|
* constructor(@Query(SomeType) queryList: QueryList<SomeType>) {
|
||||||
* ...
|
* ...
|
||||||
* }
|
* }
|
||||||
* }
|
* }
|
||||||
* ```
|
* ```
|
||||||
*
|
*
|
||||||
* ## Example as ES5 DSL
|
* ### Example as ES5 DSL
|
||||||
*
|
*
|
||||||
* ```
|
* ```
|
||||||
* var MyComponent = ng
|
* var MyComponent = ng
|
||||||
@ -362,7 +362,7 @@ export interface AttributeFactory {
|
|||||||
* })
|
* })
|
||||||
* ```
|
* ```
|
||||||
*
|
*
|
||||||
* ## Example as ES5 annotation
|
* ### Example as ES5 annotation
|
||||||
*
|
*
|
||||||
* ```
|
* ```
|
||||||
* var MyComponent = function(queryList) {
|
* var MyComponent = function(queryList) {
|
||||||
@ -513,7 +513,7 @@ export var Query: QueryFactory = makeParamDecorator(QueryMetadata);
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* {@link di/ViewQueryMetadata} factory function.
|
* {@link ViewQueryMetadata} factory function.
|
||||||
*/
|
*/
|
||||||
export var ViewQuery: QueryFactory = makeParamDecorator(ViewQueryMetadata);
|
export var ViewQuery: QueryFactory = makeParamDecorator(ViewQueryMetadata);
|
||||||
|
|
||||||
|
@ -50,34 +50,191 @@ export class AttributeMetadata extends DependencyMetadata {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Specifies that a {@link QueryList} should be injected.
|
* Declares an injectable parameter to be a live list of directives or variable
|
||||||
|
* bindings from the content children of a directive.
|
||||||
*
|
*
|
||||||
* See {@link QueryList} for usage and example.
|
* ### Example ([live demo](http://plnkr.co/edit/lY9m8HLy7z06vDoUaSN2?p=preview))
|
||||||
|
*
|
||||||
|
* Assume that `<tabs>` component would like to get a list its children `<pane>`
|
||||||
|
* components as shown in this example:
|
||||||
|
*
|
||||||
|
* ```html
|
||||||
|
* <tabs>
|
||||||
|
* <pane title="Overview">...</pane>
|
||||||
|
* <pane *ng-for="#o of objects" [title]="o.title">{{o.text}}</pane>
|
||||||
|
* </tabs>
|
||||||
|
* ```
|
||||||
|
*
|
||||||
|
* The preferred solution is to query for `Pane` directives using this decorator.
|
||||||
|
*
|
||||||
|
* ```javascript
|
||||||
|
* @Component({
|
||||||
|
* selector: 'pane',
|
||||||
|
* properties: ['title']
|
||||||
|
* })
|
||||||
|
* @View(...)
|
||||||
|
* class Pane {
|
||||||
|
* title:string;
|
||||||
|
* }
|
||||||
|
*
|
||||||
|
* @Component({
|
||||||
|
* selector: 'tabs'
|
||||||
|
* })
|
||||||
|
* @View({
|
||||||
|
* template: `
|
||||||
|
* <ul>
|
||||||
|
* <li *ng-for="#pane of panes">{{pane.title}}</li>
|
||||||
|
* </ul>
|
||||||
|
* <content></content>
|
||||||
|
* `
|
||||||
|
* })
|
||||||
|
* class Tabs {
|
||||||
|
* panes: QueryList<Pane>;
|
||||||
|
* constructor(@Query(Pane) panes:QueryList<Pane>) {
|
||||||
|
* this.panes = panes;
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
* ```
|
||||||
|
*
|
||||||
|
* A query can look for variable bindinds by passing in a string with desired binding symbol.
|
||||||
|
*
|
||||||
|
* ### Example ([live demo](http://plnkr.co/edit/sT2j25cH1dURAyBRCKx1?p=preview))
|
||||||
|
* ```html
|
||||||
|
* <seeker>
|
||||||
|
* <div #findme>...</div>
|
||||||
|
* </seeker>
|
||||||
|
*
|
||||||
|
* @Component({
|
||||||
|
* selector: 'foo'
|
||||||
|
* })
|
||||||
|
* @View(...)
|
||||||
|
* class seeker {
|
||||||
|
* constructor(@Query('findme') elList: QueryList<ElementRef>) {...}
|
||||||
|
* }
|
||||||
|
* ```
|
||||||
|
*
|
||||||
|
* In this case the object that is injected depend on the type of the variable
|
||||||
|
* binding. It can be an ElementRef, a directive or a component.
|
||||||
|
*
|
||||||
|
* Passing in a comma separated list of variable bindings will query for all of them.
|
||||||
|
*
|
||||||
|
* ```html
|
||||||
|
* <seeker>
|
||||||
|
* <div #find-me>...</div>
|
||||||
|
* <div #find-me-too>...</div>
|
||||||
|
* </seeker>
|
||||||
|
*
|
||||||
|
* @Component({
|
||||||
|
* selector: 'foo'
|
||||||
|
* })
|
||||||
|
* @View(...)
|
||||||
|
* class Seeker {
|
||||||
|
* constructor(@Query('findMe, findMeToo') elList: QueryList<ElementRef>) {...}
|
||||||
|
* }
|
||||||
|
* ```
|
||||||
|
*
|
||||||
|
* Configure whether query looks for direct children or all descendants
|
||||||
|
* of the querying element, by using the `descendants` parameter.
|
||||||
|
* It is set to `false` by default.
|
||||||
|
*
|
||||||
|
* ### Example ([live demo](http://plnkr.co/edit/wtGeB977bv7qvA5FTYl9?p=preview))
|
||||||
|
* ```html
|
||||||
|
* <container #first>
|
||||||
|
* <item>a</item>
|
||||||
|
* <item>b</item>
|
||||||
|
* <container #second>
|
||||||
|
* <item>c</item>
|
||||||
|
* </container>
|
||||||
|
* </container>
|
||||||
|
* ```
|
||||||
|
*
|
||||||
|
* When querying for items, the first container will see only `a` and `b` by default,
|
||||||
|
* but with `Query(TextDirective, {descendants: true})` it will see `c` too.
|
||||||
|
*
|
||||||
|
* The queried directives are kept in a depth-first pre-order with respect to their
|
||||||
|
* positions in the DOM.
|
||||||
|
*
|
||||||
|
* Query does not look deep into any subcomponent views.
|
||||||
|
*
|
||||||
|
* Query is updated as part of the change-detection cycle. Since change detection
|
||||||
|
* happens after construction of a directive, QueryList will always be empty when observed in the
|
||||||
|
* constructor.
|
||||||
|
*
|
||||||
|
* The injected object is an unmodifiable live list.
|
||||||
|
* See {@link QueryList} for more details.
|
||||||
*/
|
*/
|
||||||
@CONST()
|
@CONST()
|
||||||
export class QueryMetadata extends DependencyMetadata {
|
export class QueryMetadata extends DependencyMetadata {
|
||||||
|
/**
|
||||||
|
* whether we want to query only direct children (false) or all
|
||||||
|
* children (true).
|
||||||
|
*/
|
||||||
descendants: boolean;
|
descendants: boolean;
|
||||||
|
|
||||||
constructor(private _selector: Type | string,
|
constructor(private _selector: Type | string,
|
||||||
{descendants = false}: {descendants?: boolean} = {}) {
|
{descendants = false}: {descendants?: boolean} = {}) {
|
||||||
super();
|
super();
|
||||||
this.descendants = descendants;
|
this.descendants = descendants;
|
||||||
}
|
}
|
||||||
|
|
||||||
get isViewQuery() { return false; }
|
/**
|
||||||
|
* always `false` to differentiate it with {@link ViewQueryMetadata}.
|
||||||
|
*/
|
||||||
|
get isViewQuery(): boolean { return false; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* what this is querying for.
|
||||||
|
*/
|
||||||
get selector() { return resolveForwardRef(this._selector); }
|
get selector() { return resolveForwardRef(this._selector); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* whether this is querying for a variable binding or a directive.
|
||||||
|
*/
|
||||||
get isVarBindingQuery(): boolean { return isString(this.selector); }
|
get isVarBindingQuery(): boolean { return isString(this.selector); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* returns a list of variable bindings this is querying for.
|
||||||
|
* Only applicable if this is a variable bindings query.
|
||||||
|
*/
|
||||||
get varBindings(): string[] { return StringWrapper.split(this.selector, new RegExp(",")); }
|
get varBindings(): string[] { return StringWrapper.split(this.selector, new RegExp(",")); }
|
||||||
|
|
||||||
toString(): string { return `@Query(${stringify(this.selector)})`; }
|
toString(): string { return `@Query(${stringify(this.selector)})`; }
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Similar to {@link QueryMetadata}, but querying the component view, instead of
|
||||||
|
* the content children.
|
||||||
|
*
|
||||||
|
* ### Example ([live demo](http://plnkr.co/edit/eNsFHDf7YjyM6IzKxM1j?p=preview))
|
||||||
|
*
|
||||||
|
* ```javascript
|
||||||
|
* @Component({...})
|
||||||
|
* @View({
|
||||||
|
* template: `
|
||||||
|
* <item> a </item>
|
||||||
|
* <item> b </item>
|
||||||
|
* <item> c </item>
|
||||||
|
* `
|
||||||
|
* })
|
||||||
|
* class MyComponent {
|
||||||
|
* shown: boolean;
|
||||||
|
*
|
||||||
|
* constructor(private @Query(Item) items:QueryList<Item>) {
|
||||||
|
* items.onChange(() => console.log(items.length));
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
* ```
|
||||||
|
*
|
||||||
|
* Supports the same querying parameters as {@link QueryMetadata}, except
|
||||||
|
* `descendants`. This always queries the whole view.
|
||||||
|
*
|
||||||
|
* As `shown` is flipped between true and false, items will contain zero of one
|
||||||
|
* items.
|
||||||
|
*
|
||||||
* Specifies that a {@link QueryList} should be injected.
|
* Specifies that a {@link QueryList} should be injected.
|
||||||
*
|
*
|
||||||
* See {@link QueryList} for usage and example.
|
* The injected object is an iterable and observable live list.
|
||||||
|
* See {@link QueryList} for more details.
|
||||||
*/
|
*/
|
||||||
@CONST()
|
@CONST()
|
||||||
export class ViewQueryMetadata extends QueryMetadata {
|
export class ViewQueryMetadata extends QueryMetadata {
|
||||||
@ -85,6 +242,9 @@ export class ViewQueryMetadata extends QueryMetadata {
|
|||||||
super(_selector, {descendants: descendants});
|
super(_selector, {descendants: descendants});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* always `true` to differentiate it with {@link QueryMetadata}.
|
||||||
|
*/
|
||||||
get isViewQuery() { return true; }
|
get isViewQuery() { return true; }
|
||||||
toString(): string { return `@ViewQuery(${stringify(this.selector)})`; }
|
toString(): string { return `@ViewQuery(${stringify(this.selector)})`; }
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user