Skip to content
This repository has been archived by the owner on Feb 22, 2018. It is now read-only.

Commit

Permalink
feat(element binder): Make ElementBinder non-recursive and create an …
Browse files Browse the repository at this point in the history
…external tree
  • Loading branch information
jbdeboer committed Mar 11, 2014
1 parent b1a518b commit 811b460
Show file tree
Hide file tree
Showing 3 changed files with 35 additions and 20 deletions.
18 changes: 10 additions & 8 deletions lib/core_dom/compiler.dart
Original file line number Diff line number Diff line change
Expand Up @@ -7,20 +7,20 @@ class Compiler implements Function {

Compiler(this._perf, this._expando);

List<ElementBinder> _compileView(NodeCursor domCursor, NodeCursor templateCursor,
List<ElementBinderTreeRef> _compileView(NodeCursor domCursor, NodeCursor templateCursor,
ElementBinder existingElementBinder,
DirectiveMap directives) {
if (domCursor.current == null) return null;

List<ElementBinder> elementBinders = null; // don't pre-create to create sparse tree and prevent GC pressure.
List<ElementBinderTreeRef> elementBinders = null; // don't pre-create to create sparse tree and prevent GC pressure.

do {
var subtrees, binder;

ElementBinder elementBinder = existingElementBinder == null
? directives.selector(domCursor.current)
: existingElementBinder;

elementBinder.offsetIndex = templateCursor.index;

if (elementBinder.hasTemplate) {
elementBinder.templateViewFactory = compileTransclusion(
domCursor, templateCursor,
Expand All @@ -31,18 +31,20 @@ class Compiler implements Function {
if (domCursor.descend()) {
templateCursor.descend();

elementBinder.childElementBinders =
subtrees =
_compileView(domCursor, templateCursor, null, directives);

domCursor.ascend();
templateCursor.ascend();
}
}

if (elementBinder.isUseful) {
if (elementBinders == null) elementBinders = [];
elementBinders.add(elementBinder);
if (elementBinder.hasDirectives) {
binder = elementBinder;
}

if (elementBinders == null) elementBinders = [];
elementBinders.add(new ElementBinderTreeRef(templateCursor.index, new ElementBinderTree(binder, subtrees)));
} while (templateCursor.moveNext() && domCursor.moveNext());

return elementBinders;
Expand Down
23 changes: 17 additions & 6 deletions lib/core_dom/element_binder.dart
Original file line number Diff line number Diff line change
Expand Up @@ -30,8 +30,6 @@ class ElementBinder {
ViewFactory templateViewFactory;

DirectiveRef component;
var childElementBinders;
var offsetIndex;

// Can be either COMPILE_CHILDREN or IGNORE_CHILDREN
String childMode = NgAnnotation.COMPILE_CHILDREN;
Expand All @@ -46,8 +44,6 @@ class ElementBinder {

decorators = other.decorators;
component = other.component;
childElementBinders = other.childElementBinders;
offsetIndex = other.offsetIndex;
childMode = other.childMode;
}

Expand Down Expand Up @@ -92,8 +88,8 @@ class ElementBinder {
return decorators;
}

bool get isUseful {
return (_usableDirectiveRefs != null && _usableDirectiveRefs.length != 0) || childElementBinders != null;
bool get hasDirectives {
return (_usableDirectiveRefs != null && _usableDirectiveRefs.length != 0);
}

// DI visibility callback allowing node-local visibility.
Expand Down Expand Up @@ -378,3 +374,18 @@ class ElementBinder {
});
}
}


// Used for walking the DOM
class ElementBinderTreeRef {
final int offsetIndex;
final ElementBinderTree subtree;

ElementBinderTreeRef(this.offsetIndex, this.subtree);
}
class ElementBinderTree {
ElementBinder binder;
List<ElementBinderTreeRef> subtrees;

ElementBinderTree(this.binder, this.subtrees);
}
14 changes: 8 additions & 6 deletions lib/core_dom/view_factory.dart
Original file line number Diff line number Diff line change
Expand Up @@ -24,13 +24,13 @@ class BoundViewFactory {
* [Compiler] as a result of compiling a template.
*/
class ViewFactory implements Function {
final List<ElementBinder> elementBinders;
final List<ElementBinderTreeRef> elementBinders;
final List<dom.Node> templateElements;
final Profiler _perf;
final Expando _expando;

ViewFactory(this.templateElements, this.elementBinders, this._perf, this._expando) {
assert(elementBinders.forEach((ElementBinder eb) { assert(eb is ElementBinder); }) != true);
assert(elementBinders.forEach((ElementBinderTreeRef eb) { assert(eb is ElementBinderTreeRef); }) != true);
}

BoundViewFactory bind(Injector injector) =>
Expand All @@ -57,7 +57,9 @@ class ViewFactory implements Function {
var eb = elementBinders[i];
int index = eb.offsetIndex;

List childElementBinders = eb.childElementBinders;
ElementBinderTree tree = eb.subtree;

//List childElementBinders = eb.childElementBinders;
int nodeListIndex = index + preRenderedIndexOffset;
dom.Node node = nodeList[nodeListIndex];

Expand All @@ -73,10 +75,10 @@ class ViewFactory implements Function {
parentNode.append(node);
}

var childInjector = eb.bind(view, parentInjector, node);
var childInjector = tree.binder != null ? tree.binder.bind(view, parentInjector, node) : parentInjector;

if (childElementBinders != null) {
_link(view, node.nodes, childElementBinders, childInjector);
if (tree.subtrees != null) {
_link(view, node.nodes, tree.subtrees, childInjector);
}

if (fakeParent) {
Expand Down

0 comments on commit 811b460

Please sign in to comment.