|
|
|
@@ -5,7 +5,8 @@ import {ShadowDomEmulated} from 'core/compiler/shadow_dom';
|
|
|
|
|
import {DirectiveMetadataReader} from 'core/compiler/directive_metadata_reader';
|
|
|
|
|
import {Component, Decorator, Template} from 'core/annotations/annotations';
|
|
|
|
|
import {OnChange} from 'core/core';
|
|
|
|
|
import {Lexer, Parser, ProtoChangeDetector, ChangeDetector} from 'change_detection/change_detection';
|
|
|
|
|
import {Lexer, Parser, DynamicProtoChangeDetector,
|
|
|
|
|
ChangeDetector} from 'change_detection/change_detection';
|
|
|
|
|
import {TemplateConfig} from 'core/annotations/template_config';
|
|
|
|
|
import {EventEmitter} from 'core/annotations/events';
|
|
|
|
|
import {List, MapWrapper} from 'facade/collection';
|
|
|
|
@@ -52,7 +53,7 @@ export function main() {
|
|
|
|
|
describe('instantiated from protoView', () => {
|
|
|
|
|
var view;
|
|
|
|
|
beforeEach(() => {
|
|
|
|
|
var pv = new ProtoView(el('<div id="1"></div>'), new ProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(el('<div id="1"></div>'), new DynamicProtoChangeDetector());
|
|
|
|
|
view = pv.instantiate(null);
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
@@ -73,7 +74,7 @@ export function main() {
|
|
|
|
|
describe('with locals', function() {
|
|
|
|
|
var view;
|
|
|
|
|
beforeEach(() => {
|
|
|
|
|
var pv = new ProtoView(el('<div id="1"></div>'), new ProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(el('<div id="1"></div>'), new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindVariable('context-foo', 'template-foo');
|
|
|
|
|
view = createView(pv);
|
|
|
|
|
});
|
|
|
|
@@ -109,7 +110,7 @@ export function main() {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
it('should collect the root node in the ProtoView element', () => {
|
|
|
|
|
var pv = new ProtoView(templateAwareCreateElement('<div id="1"></div>'), new ProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(templateAwareCreateElement('<div id="1"></div>'), new DynamicProtoChangeDetector());
|
|
|
|
|
var view = pv.instantiate(null);
|
|
|
|
|
view.hydrate(null, null, null);
|
|
|
|
|
expect(view.nodes.length).toBe(1);
|
|
|
|
@@ -119,7 +120,7 @@ export function main() {
|
|
|
|
|
describe('collect elements with property bindings', () => {
|
|
|
|
|
|
|
|
|
|
it('should collect property bindings on the root element if it has the ng-binding class', () => {
|
|
|
|
|
var pv = new ProtoView(templateAwareCreateElement('<div [prop]="a" class="ng-binding"></div>'), new ProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(templateAwareCreateElement('<div [prop]="a" class="ng-binding"></div>'), new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(null);
|
|
|
|
|
pv.bindElementProperty(parser.parseBinding('a', null), 'prop', reflector.setter('prop'));
|
|
|
|
|
|
|
|
|
@@ -131,7 +132,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should collect property bindings on child elements with ng-binding class', () => {
|
|
|
|
|
var pv = new ProtoView(templateAwareCreateElement('<div><span></span><span class="ng-binding"></span></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(null);
|
|
|
|
|
pv.bindElementProperty(parser.parseBinding('b', null), 'a', reflector.setter('a'));
|
|
|
|
|
|
|
|
|
@@ -146,7 +147,7 @@ export function main() {
|
|
|
|
|
describe('collect text nodes with bindings', () => {
|
|
|
|
|
|
|
|
|
|
it('should collect text nodes under the root element', () => {
|
|
|
|
|
var pv = new ProtoView(templateAwareCreateElement('<div class="ng-binding">{{}}<span></span>{{}}</div>'), new ProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(templateAwareCreateElement('<div class="ng-binding">{{}}<span></span>{{}}</div>'), new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(null);
|
|
|
|
|
pv.bindTextNode(0, parser.parseBinding('a', null));
|
|
|
|
|
pv.bindTextNode(2, parser.parseBinding('b', null));
|
|
|
|
@@ -160,7 +161,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should collect text nodes with bindings on child elements with ng-binding class', () => {
|
|
|
|
|
var pv = new ProtoView(templateAwareCreateElement('<div><span> </span><span class="ng-binding">{{}}</span></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(null);
|
|
|
|
|
pv.bindTextNode(0, parser.parseBinding('b', null));
|
|
|
|
|
|
|
|
|
@@ -176,7 +177,7 @@ export function main() {
|
|
|
|
|
describe('inplace instantiation', () => {
|
|
|
|
|
it('should be supported.', () => {
|
|
|
|
|
var template = el('<div></div>');
|
|
|
|
|
var pv = new ProtoView(template, new ProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(template, new DynamicProtoChangeDetector());
|
|
|
|
|
pv.instantiateInPlace = true;
|
|
|
|
|
var view = pv.instantiate(null);
|
|
|
|
|
view.hydrate(null, null, null);
|
|
|
|
@@ -185,7 +186,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should be off by default.', () => {
|
|
|
|
|
var template = el('<div></div>')
|
|
|
|
|
var view = new ProtoView(template, new ProtoChangeDetector())
|
|
|
|
|
var view = new ProtoView(template, new DynamicProtoChangeDetector())
|
|
|
|
|
.instantiate(null);
|
|
|
|
|
view.hydrate(null, null, null);
|
|
|
|
|
expect(view.nodes[0]).not.toBe(template);
|
|
|
|
@@ -202,7 +203,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
describe('create ElementInjectors', () => {
|
|
|
|
|
it('should use the directives of the ProtoElementInjector', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"></div>'), new ProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"></div>'), new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(new ProtoElementInjector(null, 1, [SomeDirective]));
|
|
|
|
|
|
|
|
|
|
var view = pv.instantiate(null);
|
|
|
|
@@ -213,7 +214,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should use the correct parent', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"><span class="ng-binding"></span></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
var protoParent = new ProtoElementInjector(null, 0, [SomeDirective]);
|
|
|
|
|
pv.bindElement(protoParent);
|
|
|
|
|
pv.bindElement(new ProtoElementInjector(protoParent, 1, [AnotherDirective]));
|
|
|
|
@@ -227,7 +228,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should not pass the host injector when a parent injector exists', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"><span class="ng-binding"></span></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
var protoParent = new ProtoElementInjector(null, 0, [SomeDirective]);
|
|
|
|
|
pv.bindElement(protoParent);
|
|
|
|
|
var testProtoElementInjector = new TestProtoElementInjector(protoParent, 1, [AnotherDirective]);
|
|
|
|
@@ -243,7 +244,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should pass the host injector when there is no parent injector', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"><span class="ng-binding"></span></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(new ProtoElementInjector(null, 0, [SomeDirective]));
|
|
|
|
|
var testProtoElementInjector = new TestProtoElementInjector(null, 1, [AnotherDirective]);
|
|
|
|
|
pv.bindElement(testProtoElementInjector);
|
|
|
|
@@ -260,7 +261,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should collect a single root element injector', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"><span class="ng-binding"></span></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
var protoParent = new ProtoElementInjector(null, 0, [SomeDirective]);
|
|
|
|
|
pv.bindElement(protoParent);
|
|
|
|
|
pv.bindElement(new ProtoElementInjector(protoParent, 1, [AnotherDirective]));
|
|
|
|
@@ -273,7 +274,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should collect multiple root element injectors', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div><span class="ng-binding"></span><span class="ng-binding"></span></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(new ProtoElementInjector(null, 1, [SomeDirective]));
|
|
|
|
|
pv.bindElement(new ProtoElementInjector(null, 2, [AnotherDirective]));
|
|
|
|
|
|
|
|
|
@@ -290,7 +291,7 @@ export function main() {
|
|
|
|
|
var ctx;
|
|
|
|
|
|
|
|
|
|
function createComponentWithSubPV(subProtoView) {
|
|
|
|
|
var pv = new ProtoView(el('<cmp class="ng-binding"></cmp>'), new ProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(el('<cmp class="ng-binding"></cmp>'), new DynamicProtoChangeDetector());
|
|
|
|
|
var binder = pv.bindElement(new ProtoElementInjector(null, 0, [SomeComponent], true));
|
|
|
|
|
binder.componentDirective = someComponentDirective;
|
|
|
|
|
binder.nestedProtoView = subProtoView;
|
|
|
|
@@ -305,7 +306,7 @@ export function main() {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
it('should expose component services to the component', () => {
|
|
|
|
|
var subpv = new ProtoView(el('<span></span>'), new ProtoChangeDetector());
|
|
|
|
|
var subpv = new ProtoView(el('<span></span>'), new DynamicProtoChangeDetector());
|
|
|
|
|
var pv = createComponentWithSubPV(subpv);
|
|
|
|
|
|
|
|
|
|
var view = createNestedView(pv);
|
|
|
|
@@ -317,7 +318,7 @@ export function main() {
|
|
|
|
|
it('should expose component services and component instance to directives in the shadow Dom',
|
|
|
|
|
() => {
|
|
|
|
|
var subpv = new ProtoView(
|
|
|
|
|
el('<div dec class="ng-binding">hello shadow dom</div>'), new ProtoChangeDetector());
|
|
|
|
|
el('<div dec class="ng-binding">hello shadow dom</div>'), new DynamicProtoChangeDetector());
|
|
|
|
|
subpv.bindElement(
|
|
|
|
|
new ProtoElementInjector(null, 0, [ServiceDependentDecorator]));
|
|
|
|
|
var pv = createComponentWithSubPV(subpv);
|
|
|
|
@@ -340,7 +341,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('dehydration should dehydrate child component views too', () => {
|
|
|
|
|
var subpv = new ProtoView(
|
|
|
|
|
el('<div dec class="ng-binding">hello shadow dom</div>'), new ProtoChangeDetector());
|
|
|
|
|
el('<div dec class="ng-binding">hello shadow dom</div>'), new DynamicProtoChangeDetector());
|
|
|
|
|
subpv.bindElement(
|
|
|
|
|
new ProtoElementInjector(null, 0, [ServiceDependentDecorator]));
|
|
|
|
|
var pv = createComponentWithSubPV(subpv);
|
|
|
|
@@ -355,7 +356,7 @@ export function main() {
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
it('should create shadow dom', () => {
|
|
|
|
|
var subpv = new ProtoView(el('<span>hello shadow dom</span>'), new ProtoChangeDetector());
|
|
|
|
|
var subpv = new ProtoView(el('<span>hello shadow dom</span>'), new DynamicProtoChangeDetector());
|
|
|
|
|
var pv = createComponentWithSubPV(subpv);
|
|
|
|
|
|
|
|
|
|
var view = createNestedView(pv);
|
|
|
|
@@ -364,9 +365,9 @@ export function main() {
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
it('should use the provided shadow DOM strategy', () => {
|
|
|
|
|
var subpv = new ProtoView(el('<span>hello shadow dom</span>'), new ProtoChangeDetector());
|
|
|
|
|
var subpv = new ProtoView(el('<span>hello shadow dom</span>'), new DynamicProtoChangeDetector());
|
|
|
|
|
|
|
|
|
|
var pv = new ProtoView(el('<cmp class="ng-binding"></cmp>'), new ProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(el('<cmp class="ng-binding"></cmp>'), new DynamicProtoChangeDetector());
|
|
|
|
|
var binder = pv.bindElement(new ProtoElementInjector(null, 0, [SomeComponentWithEmulatedShadowDom], true));
|
|
|
|
|
binder.componentDirective = new DirectiveMetadataReader().read(SomeComponentWithEmulatedShadowDom);
|
|
|
|
|
binder.nestedProtoView = subpv;
|
|
|
|
@@ -380,8 +381,8 @@ export function main() {
|
|
|
|
|
describe('with template views', () => {
|
|
|
|
|
function createViewWithTemplate() {
|
|
|
|
|
var templateProtoView = new ProtoView(
|
|
|
|
|
el('<div id="1"></div>'), new ProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(el('<someTmpl class="ng-binding"></someTmpl>'), new ProtoChangeDetector());
|
|
|
|
|
el('<div id="1"></div>'), new DynamicProtoChangeDetector());
|
|
|
|
|
var pv = new ProtoView(el('<someTmpl class="ng-binding"></someTmpl>'), new DynamicProtoChangeDetector());
|
|
|
|
|
var binder = pv.bindElement(new ProtoElementInjector(null, 0, [SomeTemplate]));
|
|
|
|
|
binder.templateDirective = someTemplateDirective;
|
|
|
|
|
binder.nestedProtoView = templateProtoView;
|
|
|
|
@@ -425,7 +426,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
function createProtoView() {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"><div></div></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(new TestProtoElementInjector(null, 0, []));
|
|
|
|
|
pv.bindEvent('click', parser.parseBinding('callMe(\$event)', null));
|
|
|
|
|
return pv;
|
|
|
|
@@ -460,7 +461,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should support custom event emitters', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"><div></div></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(new TestProtoElementInjector(null, 0, [EventEmitterDirective]));
|
|
|
|
|
pv.bindEvent('click', parser.parseBinding('callMe(\$event)', null));
|
|
|
|
|
|
|
|
|
@@ -491,7 +492,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should consume text node changes', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding">{{}}</div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(null);
|
|
|
|
|
pv.bindTextNode(0, parser.parseBinding('foo', null));
|
|
|
|
|
createViewAndChangeDetector(pv);
|
|
|
|
@@ -503,7 +504,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should consume element binding changes', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(null);
|
|
|
|
|
pv.bindElementProperty(parser.parseBinding('foo', null), 'id', reflector.setter('id'));
|
|
|
|
|
createViewAndChangeDetector(pv);
|
|
|
|
@@ -515,7 +516,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should consume directive watch expression change', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
pv.bindElement(new ProtoElementInjector(null, 0, [SomeDirective]));
|
|
|
|
|
pv.bindDirectiveProperty(0, parser.parseBinding('foo', null), 'prop', reflector.setter('prop'), false);
|
|
|
|
|
createViewAndChangeDetector(pv);
|
|
|
|
@@ -527,7 +528,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should notify a directive about changes after all its properties have been set', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
|
|
|
|
|
pv.bindElement(new ProtoElementInjector(null, 0, [DirectiveImplementingOnChange]));
|
|
|
|
|
pv.bindDirectiveProperty( 0, parser.parseBinding('a', null), 'a', reflector.setter('a'), false);
|
|
|
|
@@ -544,7 +545,7 @@ export function main() {
|
|
|
|
|
|
|
|
|
|
it('should provide a map of updated properties', () => {
|
|
|
|
|
var pv = new ProtoView(el('<div class="ng-binding"></div>'),
|
|
|
|
|
new ProtoChangeDetector());
|
|
|
|
|
new DynamicProtoChangeDetector());
|
|
|
|
|
|
|
|
|
|
pv.bindElement(new ProtoElementInjector(null, 0, [DirectiveImplementingOnChange]));
|
|
|
|
|
pv.bindDirectiveProperty( 0, parser.parseBinding('a', null), 'a', reflector.setter('a'), false);
|
|
|
|
@@ -569,18 +570,20 @@ export function main() {
|
|
|
|
|
var element, pv;
|
|
|
|
|
beforeEach(() => {
|
|
|
|
|
element = DOM.createElement('div');
|
|
|
|
|
pv = new ProtoView(el('<div>hi</div>'), new ProtoChangeDetector());
|
|
|
|
|
pv = new ProtoView(el('<div>hi</div>'), new DynamicProtoChangeDetector());
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
it('should create the root component when instantiated', () => {
|
|
|
|
|
var rootProtoView = ProtoView.createRootProtoView(pv, element, someComponentDirective);
|
|
|
|
|
var rootProtoView = ProtoView.createRootProtoView(pv, element,
|
|
|
|
|
someComponentDirective, new DynamicProtoChangeDetector());
|
|
|
|
|
var view = rootProtoView.instantiate(null);
|
|
|
|
|
view.hydrate(new Injector([]), null, null);
|
|
|
|
|
expect(view.rootElementInjectors[0].get(SomeComponent)).not.toBe(null);
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
it('should inject the protoView into the shadowDom', () => {
|
|
|
|
|
var rootProtoView = ProtoView.createRootProtoView(pv, element, someComponentDirective);
|
|
|
|
|
var rootProtoView = ProtoView.createRootProtoView(pv, element,
|
|
|
|
|
someComponentDirective, new DynamicProtoChangeDetector());
|
|
|
|
|
var view = rootProtoView.instantiate(null);
|
|
|
|
|
view.hydrate(new Injector([]), null, null);
|
|
|
|
|
expect(element.shadowRoot.childNodes[0].childNodes[0].nodeValue).toEqual('hi');
|
|
|
|
|