diff --git a/src/lib/dom-api-mutation-content.html b/src/lib/dom-api-mutation-content.html
index 5683c4b52e..220e1ff2b7 100644
--- a/src/lib/dom-api-mutation-content.html
+++ b/src/lib/dom-api-mutation-content.html
@@ -23,54 +23,18 @@
Polymer.Base.extend(DomApi.MutationContent.prototype, {
- addListener: function(callback, options) {
- var h = DomApi.Mutation.prototype.addListener.call(this, callback,
- options);
- this._scheduleNotify();
- return h;
- },
+ // NOTE: ShadyDOM distribute provokes notification of these observers
+ // so no setup is required.
+ _setup: function() {},
- _ensureSetup: function(options) {},
+ _cleanup: function() {},
- notify: function() {
- if (this._hasListeners()) {
- this._scheduleNotify();
- }
- },
-
- _notify: function() {
- var info = this._suspendChangeInfo ? {} : this._calcChanges();
- if (info) {
- info.target = this.node;
- this._callListeners(info);
- }
- },
+ // no need to update sub-elements since does not nest
+ // (but note that will)
+ _beforeCallListeners: function() {},
- _calcChanges: function() {
- var changes = {
- addedNodes: [],
- removedNodes: []
- };
- var o$ = this.node.__distributedNodes = this.node.__distributedNodes ||
- [];
- var n$ = this.domApi.getDistributedNodes();
- this.node.__distributedNodes = n$;
- var splices = Polymer.ArraySplice.calculateSplices(n$, o$);
- // process removals
- for (var i=0, s; (i= 0) {
+ this._listeners.splice(i, 1);
+ handle._nodes = [];
+ }
if (!this._hasListeners()) {
- this._ensureCleanup();
+ this._cleanup();
+ this._isSetup = false;
}
},
- _ensureSetup: function(options) {
- if (!this._isSetup) {
- this._isSetup = true;
- this._observeContentElements(this.domApi.childNodes);
- }
+ _setup: function() {
+ this._observeContentElements(this.domApi.childNodes);
},
- _ensureCleanup: function() {}, // abstract
+ _cleanup: function() {
+ this._unobserveContentElements(this.domApi.childNodes);
+ },
_hasListeners: function() {
return Boolean(this._listeners.length);
},
- addNode: function(node) {
- if (this._hasListeners()) {
- this._addedNodes.push(node);
- this._scheduleNotify();
+ _scheduleNotify: function() {
+ if (this._debouncer) {
+ this._debouncer.stop();
}
+ this._debouncer = Polymer.Debounce(this._debouncer,
+ this._notify);
+ this._debouncer.context = this;
+ Polymer.dom.addDebouncer(this._debouncer);
},
- removeNode: function(node) {
+ notify: function() {
if (this._hasListeners()) {
- this._removedNodes.push(node);
this._scheduleNotify();
}
},
- addAllNodes: function(force) {
- if (this._hasListeners() || force) {
- var c$ = this.domApi.childNodes;
- if (c$.length) {
- for (var i=0, c; (i < c$.length) && (c=c$[i]); i++) {
- this._addedNodes.push(c);
- }
- this._scheduleNotify();
- }
- }
- },
-
- _scheduleNotify: function() {
- this._debouncer = Polymer.Debounce(this._debouncer,
- this._notify);
- this._debouncer.context = this;
- Polymer.dom.addDebouncer(this._debouncer);
- },
-
_notify: function(mxns) {
- var info = mxns || {
- target: this.node,
- addedNodes: this._addedNodes,
- removedNodes: this._removedNodes
- }
- this._updateContentElements(info);
- this._callListeners(info);
- this._addedNodes = [];
- this._removedNodes = [];
+ this._beforeCallListeners();
+ this._callListeners();
},
- _notifyInitial: function(listener) {
- var info = {
- target: this.node,
- addedNodes: this.domApi.childNodes,
- removedNodes: []
- };
- this._callListener(listener, info);
+ _beforeCallListeners: function() {
+ this._updateContentElements();
},
- _updateContentElements: function(info) {
- this._observeContentElements(info.addedNodes);
- this._unobserveContentElements(info.removedNodes);
+ _updateContentElements: function() {
+ this._observeContentElements(this.domApi.childNodes);
},
_observeContentElements: function(elements) {
- for (var i=0, h, n; (i < elements.length) && (n=elements[i]); i++) {
+ for (var i=0, n; (i < elements.length) && (n=elements[i]); i++) {
if (this._isContent(n)) {
n.__observeNodesMap = n.__observeNodesMap || new WeakMap();
- if (n.__observeNodesMap.get(this) == null) {
- h = this._observeContent(n);
- n.__observeNodesMap.set(this, h);
+ if (!n.__observeNodesMap.has(this)) {
+ n.__observeNodesMap.set(this, this._observeContent(n));
}
}
}
},
_observeContent: function(content) {
- return Polymer.dom(content).observeNodes(this._notify.bind(this));
+ return Polymer.dom(content).observeNodes(this._scheduleNotify.bind(this));
},
_unobserveContentElements: function(elements) {
@@ -134,8 +108,8 @@
if (this._isContent(n)) {
h = n.__observeNodesMap.get(this);
if (h) {
- n.__observeNodesMap.set(this, null);
Polymer.dom(n).unobserveNodes(h);
+ n.__observeNodesMap.delete(this);
}
}
}
@@ -145,15 +119,44 @@
return (node.localName === 'content');
},
- _callListeners: function(info, filter) {
+ _callListeners: function() {
var o$ = this._listeners;
+ var nodes = this.domApi.getEffectiveChildNodes();
for (var i=0, o; (i < o$.length) && (o=o$[i]); i++) {
- if (!filter || filter(o.options)) {
+ var info = this._generateListenerInfo(o, nodes);
+ if (info || o._alwaysCallListener) {
this._callListener(o, info);
}
}
},
+ _generateListenerInfo: function(listener, newNodes) {
+ var oldNodes = listener._nodes;
+ var info = {
+ target: this.node,
+ addedNodes: [],
+ removedNodes: []
+ };
+ var splices = Polymer.ArraySplice.calculateSplices(newNodes, oldNodes);
+ // process removals
+ for (var i=0, s; (i 1x is a no-op
- this._observer.observe(this.node, {childList: true});
+ // NOTE: subtree true is way too aggressive, but it easily catches
+ // attribute changes on children. These changes otherwise require
+ // attribute observers on every child. Testing has shown this
+ // approach to be more efficient.
+ // TODO(sorvell): do we still need to include an option to defeat
+ // attribute tracking?
+ this._observer.observe(this.node, {
+ childList: true,
+ attributes: true,
+ subtree: true
+ });
}
- ensureSetup.call(this, options);
+ baseSetup.call(this);
},
- _ensureCleanup: function() {
+ _cleanup: function() {
this._observer.disconnect();
+ this._observer = null;
+ this._mutationHandler = null;
Polymer.dom.removePreflush(this._preflush);
- },
-
- _notify: function(mxns) {
- var info = {
- target: this.node,
- addedNodes: [],
- removedNodes: []
- };
- // collapse multiple mutations into one view
- if (Array.isArray(mxns)) {
- Array.prototype.forEach.call(mxns, function(m) {
- if (m.addedNodes) {
- for (var i=0; i < m.addedNodes.length; i++) {
- info.addedNodes.push(m.addedNodes[i]);
- }
- }
- if (m.removedNodes) {
- for (var i=0; i < m.removedNodes.length; i++) {
- info.removedNodes.push(m.removedNodes[i]);
- }
- }
- });
- } else if (mxns) {
- info = mxns;
- }
- if (info.addedNodes.length || info.removedNodes.length) {
- this._updateContentElements(info);
- // attribute tracking helps us notice distributed nodes changes
- // needed only with shadow dom.
- if (this._trackAttributes) {
- this._updateAttributeObservers(info);
- }
- this._callListeners(info);
- }
+ baseCleanup.call(this);
},
_flush: function() {
if (this._observer) {
- this._notify(this._observer.takeRecords());
- }
- },
-
- _observeContent: function(content) {
- return Polymer.dom(content).observeNodes(this._notify.bind(this), {
- attributes: this._trackAttributes
- });
- },
-
- _updateAttributeObservers: function(info) {
- this._observeAttributes(info.addedNodes);
- this._unobserveAttributes(info.removedNodes);
- },
-
- _observeAttributes: function(elements) {
- for (var i=0, h, n; (i < elements.length) && (n=elements[i]); i++) {
- if (n.nodeType === Node.ELEMENT_NODE) {
- this._ensureElementAttrObserver(n);
- }
- }
- },
-
- _ensureElementAttrObserver: function(element) {
- this._attrObservers = this._attrObservers || new WeakMap();
- if (!this._attrObservers.get(element)) {
- var self = this;
- this._attrObservers.set(element, new MutationObserver(
- function(mxns) {
- self._callListeners(mxns, function(options) {
- return Boolean(options.attributes);
- });
- }
- ));
- this._attrObservers.get(element)
- .observe(element, {attributes: true});
- }
- },
-
- _unobserveAttributes: function(elements) {
- for (var i=0, h, n; (i < elements.length) && (n=elements[i]); i++) {
- if (n.nodeType === Node.ELEMENT_NODE) {
- h = this._attrObservers.get(n);
- if (h) {
- h.disconnect(n);
- }
- this._attrObservers.set(n, null);
- }
+ this._mutationHandler(this._observer.takeRecords());
}
}
diff --git a/src/lib/dom-api.html b/src/lib/dom-api.html
index faa8d4ffa7..9d4067eb4f 100644
--- a/src/lib/dom-api.html
+++ b/src/lib/dom-api.html
@@ -111,7 +111,7 @@
this._updateInsertionPoints(root.host);
}
if (this.observer) {
- this.observer.addNode(node);
+ this.observer.notify();
}
return node;
},
@@ -137,7 +137,7 @@
}
}
if (this.observer) {
- this.observer.removeNode(node);
+ this.observer.notify();
}
return node;
},
@@ -526,23 +526,20 @@
return n;
},
- observeNodes: function(callback, options) {
+ observeNodes: function(callback) {
if (!this.observer) {
this.observer = this.node.localName === CONTENT ?
new DomApi.MutationContent(this) :
new DomApi.Mutation(this);
}
- return this.observer.addListener.apply(this.observer, arguments);
+ return this.observer.addListener(callback);
},
unobserveNodes: function(handle) {
if (this.observer) {
this.observer.removeListener(handle);
}
- },
-
- // abstract, intended as public 'kick' mehanism
- notifyObservers: function() {}
+ }
};
@@ -752,25 +749,6 @@
DomApi.prototype._distributeParent = function() {};
- DomApi.prototype.notifyObservers = function() {
- if (this.node.shadowRoot) {
- var ip$ = this.node.shadowRoot.querySelectorAll('content');
- for (var i=0, c; (i
- []
+ []
+
+
+
+
+
+
+
[]
@@ -192,7 +205,7 @@
var d1 = document.createElement('div');
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 2);
assert.equal(recorded.removedNodes.length, 0);
assert.equal(recorded.addedNodes[0], d);
@@ -200,7 +213,7 @@
// remove
Polymer.dom(el).removeChild(d);
Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 0);
assert.equal(recorded.removedNodes.length, 2);
assert.equal(recorded.removedNodes[0], d);
@@ -208,7 +221,7 @@
// add
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 2);
assert.equal(recorded.addedNodes[0], d);
assert.equal(recorded.addedNodes[1], d1);
@@ -217,11 +230,54 @@
Polymer.dom(el).unobserveNodes(handle);
Polymer.dom(el).removeChild(d);
Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded, null);
document.body.removeChild(el);
});
+ test('observe children changes to distributing element (async)', function(done) {
+ var el = document.createElement('test-content');
+ document.body.appendChild(el);
+
+ var nodes = [];
+ var handle = Polymer.dom(el).observeNodes(function(info) {
+ for (var i=0, at; i < info.removedNodes.length; i++) {
+ at = nodes.indexOf(info.removedNodes[i]);
+ assert.isAbove(at, -1);
+ nodes.splice(at, 1);
+ }
+ nodes = nodes.concat(info.addedNodes);
+ });
+ // add
+ var d = document.createElement('div');
+ var d1 = document.createElement('div');
+ Polymer.dom(el).appendChild(d);
+ Polymer.dom(el).appendChild(d1);
+ setTimeout(function() {
+ assert.sameMembers(el.getEffectiveChildNodes(), nodes);
+ // remove
+ Polymer.dom(el).removeChild(d);
+ Polymer.dom(el).removeChild(d1);
+ setTimeout(function() {
+ assert.sameMembers(el.getEffectiveChildNodes(), nodes);
+ // add
+ Polymer.dom(el).appendChild(d);
+ Polymer.dom(el).appendChild(d1);
+ setTimeout(function() {
+ assert.sameMembers(el.getEffectiveChildNodes(), nodes);
+ Polymer.dom(el).unobserveNodes(handle);
+ Polymer.dom(el).removeChild(d);
+ Polymer.dom(el).removeChild(d1);
+ setTimeout(function() {
+ assert.notEqual(nodes.length, el.getEffectiveChildNodes().length)
+ document.body.removeChild(el);
+ done();
+ });
+ });
+ });
+ });
+ });
+
test('observe children changes to non-distributing element', function() {
var el = document.createElement('test-static');
document.body.appendChild(el);
@@ -235,7 +291,7 @@
var d1 = document.createElement('div');
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 2);
assert.equal(recorded.removedNodes.length, 0);
assert.equal(recorded.addedNodes[0], d);
@@ -243,7 +299,7 @@
// remove
Polymer.dom(el).removeChild(d);
Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 0);
assert.equal(recorded.removedNodes.length, 2);
assert.equal(recorded.removedNodes[0], d);
@@ -251,7 +307,7 @@
// add
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 2);
assert.equal(recorded.addedNodes[0], d);
assert.equal(recorded.addedNodes[1], d1);
@@ -260,106 +316,63 @@
Polymer.dom(el).unobserveNodes(handle);
Polymer.dom(el).removeChild(d);
Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded, null);
document.body.removeChild(el);
});
- test('observe changes to distributed nodes without changes', function() {
+ test('observe changes to inner node with ', function() {
var el = document.createElement('test-content');
document.body.appendChild(el);
-
- var distributed;
- var handle = Polymer.dom(el.$.content).observeNodes(function(info) {
- distributed = Polymer.dom(info.target).getDistributedNodes();
- });
- // add
- var d = document.createElement('div');
- var d1 = document.createElement('div');
- Polymer.dom(el).appendChild(d);
- Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
- assert.equal(distributed.length, 2);
- assert.equal(distributed[0], d);
- // remove
- Polymer.dom(el).removeChild(d);
- Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
- assert.equal(distributed.length, 0);
- // add
- Polymer.dom(el).appendChild(d);
- Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
- assert.equal(distributed.length, 2);
- assert.equal(distributed[0], d);
- assert.equal(distributed[1], d1);
- // reset, unobserve and remove
- distributed = null;
- Polymer.dom(el.$.content).unobserveNodes(handle);
- Polymer.dom(el).removeChild(d);
- Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
- assert.equal(distributed, null);
- document.body.removeChild(el);
- });
-
- test('observe changes to distributed nodes with changes', function() {
- var el = document.createElement('test-content');
- document.body.appendChild(el);
-
- var recorded;
- var handle = Polymer.dom(el.$.content).observeNodes(function(info) {
- recorded = info;
+ var observedInfo;
+ var handle = Polymer.dom(el.$.contentContainer).observeNodes(function(info) {
+ observedInfo = info;
});
+ Polymer.dom.flush();
// add
var d = document.createElement('div');
var d1 = document.createElement('div');
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
- assert.equal(recorded.addedNodes.length, 2);
- assert.equal(recorded.removedNodes.length, 0);
- assert.equal(recorded.addedNodes[0], d);
- assert.equal(recorded.addedNodes[1], d1);
+ Polymer.dom.flush();
+ assert.equal(observedInfo.addedNodes.length, 2);
+ assert.equal(observedInfo.removedNodes.length, 0);
// remove
Polymer.dom(el).removeChild(d);
Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
- assert.equal(recorded.addedNodes.length, 0);
- assert.equal(recorded.removedNodes.length, 2);
- assert.equal(recorded.removedNodes[0], d);
- assert.equal(recorded.removedNodes[1], d1);
+ Polymer.dom.flush();
+ assert.equal(observedInfo.addedNodes.length, 0);
+ assert.equal(observedInfo.removedNodes.length, 2);
// add
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
- assert.equal(recorded.addedNodes.length, 2);
- assert.equal(recorded.addedNodes[0], d);
- assert.equal(recorded.addedNodes[1], d1);
+ Polymer.dom.flush();
+ assert.equal(observedInfo.addedNodes.length, 2);
+ assert.equal(observedInfo.removedNodes.length, 0);
// reset, unobserve and remove
- recorded = null;
- Polymer.dom(el.$.content).unobserveNodes(handle);
+ observedInfo = null;
+ Polymer.dom(el.$.contentContainer).unobserveNodes(handle);
Polymer.dom(el).removeChild(d);
Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
- assert.equal(recorded, null);
+ Polymer.dom.flush();
+ assert.equal(observedInfo, null);
document.body.removeChild(el);
});
test('observe effective children inside distributing element', function() {
var el = document.createElement('test-content1');
document.body.appendChild(el);
-
var recorded;
var handle = Polymer.dom(el.$.content).observeNodes(function(info) {
recorded = info;
});
+ Polymer.dom.flush();
// add
var d = document.createElement('div');
var d1 = document.createElement('div');
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 2);
assert.equal(recorded.removedNodes.length, 0);
assert.equal(recorded.addedNodes[0], d);
@@ -367,7 +380,7 @@
// remove
Polymer.dom(el).removeChild(d);
Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 0);
assert.equal(recorded.removedNodes.length, 2);
assert.equal(recorded.removedNodes[0], d);
@@ -375,7 +388,7 @@
// add
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 2);
assert.equal(recorded.addedNodes[0], d);
assert.equal(recorded.addedNodes[1], d1);
@@ -384,7 +397,7 @@
Polymer.dom(el.$.content).unobserveNodes(handle);
Polymer.dom(el).removeChild(d);
Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded, null);
document.body.removeChild(el);
});
@@ -403,7 +416,7 @@
var d1 = document.createElement('div');
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 2);
assert.equal(recorded.removedNodes.length, 0);
assert.equal(recorded.addedNodes[0], d);
@@ -411,7 +424,7 @@
// remove
Polymer.dom(el).removeChild(d);
Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 0);
assert.equal(recorded.removedNodes.length, 2);
assert.equal(recorded.removedNodes[0], d);
@@ -419,7 +432,7 @@
// add
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded.addedNodes.length, 2);
assert.equal(recorded.addedNodes[0], d);
assert.equal(recorded.addedNodes[1], d1);
@@ -428,11 +441,12 @@
Polymer.dom(content).unobserveNodes(handle);
Polymer.dom(el).removeChild(d);
Polymer.dom(el).removeChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded, null);
document.body.removeChild(el);
});
+
test('observe effective children attr changes inside deep distributing element', function(done) {
var el = document.createElement('test-content-attr3');
document.body.appendChild(el);
@@ -442,14 +456,14 @@
var handle = Polymer.dom(content).observeNodes(function(info) {
recorded = info;
}, {attributes: true});
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
recorded = null;
// add
var d = document.createElement('div');
var d1 = document.createElement('div');
Polymer.dom(el).appendChild(d);
Polymer.dom(el).appendChild(d1);
- Polymer.dom(el).flush();
+ Polymer.dom.flush();
assert.equal(recorded, null);
Polymer.dom(d).setAttribute('a', '');
Polymer.dom(d).setAttribute('b', '');
@@ -477,6 +491,86 @@
});
});
});
+
+ test('add/remove multiple observers', function() {
+ var el = document.createElement('test-content1');
+ document.body.appendChild(el);
+ var r1 = 0;
+ var h1 = Polymer.dom(el.$.content).observeNodes(function(info) {
+ r1++;
+ });
+ var r2 = 0;
+ var h2 = Polymer.dom(el.$.content).observeNodes(function(info) {
+ r2++;
+ });
+ var r3 = 0;
+ var h3 = Polymer.dom(el.$.content).observeNodes(function(info) {
+ r3++;
+ });
+ // add
+ var d = document.createElement('div');
+ Polymer.dom(el).appendChild(d);
+ Polymer.dom.flush();
+ assert.equal(r1, 1);
+ assert.equal(r2, 1);
+ assert.equal(r3, 1);
+ Polymer.dom(el.$.content).unobserveNodes(h1);
+ var d = document.createElement('div');
+ Polymer.dom(el).appendChild(d);
+ Polymer.dom.flush();
+ assert.equal(r1, 1);
+ assert.equal(r2, 2);
+ assert.equal(r3, 2);
+ Polymer.dom(el.$.content).unobserveNodes(h2);
+ var d = document.createElement('div');
+ Polymer.dom(el).appendChild(d);
+ Polymer.dom.flush();
+ assert.equal(r1, 1);
+ assert.equal(r2, 2);
+ assert.equal(r3, 3);
+ Polymer.dom(el.$.content).unobserveNodes(h3);
+ var d = document.createElement('div');
+ Polymer.dom(el).appendChild(d);
+ Polymer.dom.flush();
+ assert.equal(r1, 1);
+ assert.equal(r2, 2);
+ assert.equal(r3, 3);
+ h1 = Polymer.dom(el.$.content).observeNodes(h1.fn);
+ h2 = Polymer.dom(el.$.content).observeNodes(h2.fn);
+ h3 = Polymer.dom(el.$.content).observeNodes(h3.fn);
+ Polymer.dom.flush();
+ assert.equal(r1, 2);
+ assert.equal(r2, 3);
+ assert.equal(r3, 4);
+ var d = document.createElement('div');
+ Polymer.dom(el).appendChild(d);
+ Polymer.dom.flush();
+ assert.equal(r1, 3);
+ assert.equal(r2, 4);
+ assert.equal(r3, 5);
+ Polymer.dom(el.$.content).unobserveNodes(h3);
+ var d = document.createElement('div');
+ Polymer.dom(el).appendChild(d);
+ Polymer.dom.flush();
+ assert.equal(r1, 4);
+ assert.equal(r2, 5);
+ assert.equal(r3, 5);
+ Polymer.dom(el.$.content).unobserveNodes(h2);
+ var d = document.createElement('div');
+ Polymer.dom(el).appendChild(d);
+ Polymer.dom.flush();
+ assert.equal(r1, 5);
+ assert.equal(r2, 5);
+ assert.equal(r3, 5);
+ Polymer.dom(el.$.content).unobserveNodes(h1);
+ var d = document.createElement('div');
+ Polymer.dom(el).appendChild(d);
+ Polymer.dom.flush();
+ assert.equal(r1, 5);
+ assert.equal(r2, 5);
+ assert.equal(r3, 5);
+ });
+
});