OLD | NEW |
1 <!-- | 1 <!-- |
2 @license | 2 @license |
3 Copyright (c) 2014 The Polymer Project Authors. All rights reserved. | 3 Copyright (c) 2014 The Polymer Project Authors. All rights reserved. |
4 This code may only be used under the BSD style license found at http://polymer.g
ithub.io/LICENSE.txt | 4 This code may only be used under the BSD style license found at http://polymer.g
ithub.io/LICENSE.txt |
5 The complete set of authors may be found at http://polymer.github.io/AUTHORS.txt | 5 The complete set of authors may be found at http://polymer.github.io/AUTHORS.txt |
6 The complete set of contributors may be found at http://polymer.github.io/CONTRI
BUTORS.txt | 6 The complete set of contributors may be found at http://polymer.github.io/CONTRI
BUTORS.txt |
7 Code distributed by Google as part of the polymer project is also | 7 Code distributed by Google as part of the polymer project is also |
8 subject to an additional IP rights grant found at http://polymer.github.io/PATEN
TS.txt | 8 subject to an additional IP rights grant found at http://polymer.github.io/PATEN
TS.txt |
9 --><link rel="import" href="polymer-micro.html"> | 9 --><link rel="import" href="polymer-micro.html"> |
10 | 10 |
11 <script>Polymer.Base._addFeature({ | 11 <script>Polymer.Base._addFeature({ |
12 _prepTemplate: function () { | 12 _prepTemplate: function () { |
13 this._template = this._template || Polymer.DomModule.import(this.is, 'template')
; | 13 if (this._template === undefined) { |
| 14 this._template = Polymer.DomModule.import(this.is, 'template'); |
| 15 } |
14 if (this._template && this._template.hasAttribute('is')) { | 16 if (this._template && this._template.hasAttribute('is')) { |
15 this._warn(this._logf('_prepTemplate', 'top-level Polymer template ' + 'must not
be a type-extension, found', this._template, 'Move inside simple <template>.'))
; | 17 this._warn(this._logf('_prepTemplate', 'top-level Polymer template ' + 'must not
be a type-extension, found', this._template, 'Move inside simple <template>.'))
; |
16 } | 18 } |
| 19 if (this._template && !this._template.content && window.HTMLTemplateElement && H
TMLTemplateElement.decorate) { |
| 20 HTMLTemplateElement.decorate(this._template); |
| 21 } |
17 }, | 22 }, |
18 _stampTemplate: function () { | 23 _stampTemplate: function () { |
19 if (this._template) { | 24 if (this._template) { |
20 this.root = this.instanceTemplate(this._template); | 25 this.root = this.instanceTemplate(this._template); |
21 } | 26 } |
22 }, | 27 }, |
23 instanceTemplate: function (template) { | 28 instanceTemplate: function (template) { |
24 var dom = document.importNode(template._content || template.content, true); | 29 var dom = document.importNode(template._content || template.content, true); |
25 return dom; | 30 return dom; |
26 } | 31 } |
27 }); | 32 }); |
28 (function () { | 33 (function () { |
29 var baseAttachedCallback = Polymer.Base.attachedCallback; | 34 var baseAttachedCallback = Polymer.Base.attachedCallback; |
30 Polymer.Base._addFeature({ | 35 Polymer.Base._addFeature({ |
31 _hostStack: [], | 36 _hostStack: [], |
32 ready: function () { | 37 ready: function () { |
33 }, | 38 }, |
34 _pushHost: function (host) { | 39 _registerHost: function (host) { |
35 this.dataHost = host = host || Polymer.Base._hostStack[Polymer.Base._hostStack.l
ength - 1]; | 40 this.dataHost = host = host || Polymer.Base._hostStack[Polymer.Base._hostStack.l
ength - 1]; |
36 if (host && host._clients) { | 41 if (host && host._clients) { |
37 host._clients.push(this); | 42 host._clients.push(this); |
38 } | 43 } |
39 this._beginHost(); | |
40 }, | 44 }, |
41 _beginHost: function () { | 45 _beginHosting: function () { |
42 Polymer.Base._hostStack.push(this); | 46 Polymer.Base._hostStack.push(this); |
43 if (!this._clients) { | 47 if (!this._clients) { |
44 this._clients = []; | 48 this._clients = []; |
45 } | 49 } |
46 }, | 50 }, |
47 _popHost: function () { | 51 _endHosting: function () { |
48 Polymer.Base._hostStack.pop(); | 52 Polymer.Base._hostStack.pop(); |
49 }, | 53 }, |
50 _tryReady: function () { | 54 _tryReady: function () { |
51 if (this._canReady()) { | 55 if (this._canReady()) { |
52 this._ready(); | 56 this._ready(); |
53 } | 57 } |
54 }, | 58 }, |
55 _canReady: function () { | 59 _canReady: function () { |
56 return !this.dataHost || this.dataHost._clientsReadied; | 60 return !this.dataHost || this.dataHost._clientsReadied; |
57 }, | 61 }, |
58 _ready: function () { | 62 _ready: function () { |
59 this._beforeClientsReady(); | 63 this._beforeClientsReady(); |
| 64 if (this._template) { |
60 this._setupRoot(); | 65 this._setupRoot(); |
61 this._readyClients(); | 66 this._readyClients(); |
| 67 } |
| 68 this._clientsReadied = true; |
| 69 this._clients = null; |
62 this._afterClientsReady(); | 70 this._afterClientsReady(); |
63 this._readySelf(); | 71 this._readySelf(); |
64 }, | 72 }, |
65 _readyClients: function () { | 73 _readyClients: function () { |
66 this._beginDistribute(); | 74 this._beginDistribute(); |
67 var c$ = this._clients; | 75 var c$ = this._clients; |
| 76 if (c$) { |
68 for (var i = 0, l = c$.length, c; i < l && (c = c$[i]); i++) { | 77 for (var i = 0, l = c$.length, c; i < l && (c = c$[i]); i++) { |
69 c._ready(); | 78 c._ready(); |
70 } | 79 } |
| 80 } |
71 this._finishDistribute(); | 81 this._finishDistribute(); |
72 this._clientsReadied = true; | |
73 this._clients = null; | |
74 }, | 82 }, |
75 _readySelf: function () { | 83 _readySelf: function () { |
76 this._doBehavior('ready'); | 84 this._doBehavior('ready'); |
77 this._readied = true; | 85 this._readied = true; |
78 if (this._attachedPending) { | 86 if (this._attachedPending) { |
79 this._attachedPending = false; | 87 this._attachedPending = false; |
80 this.attachedCallback(); | 88 this.attachedCallback(); |
81 } | 89 } |
82 }, | 90 }, |
83 _beforeClientsReady: function () { | 91 _beforeClientsReady: function () { |
(...skipping 175 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
259 }, | 267 }, |
260 calculateSplices: function (current, previous) { | 268 calculateSplices: function (current, previous) { |
261 return this.calcSplices(current, 0, current.length, previous, 0, previous.length
); | 269 return this.calcSplices(current, 0, current.length, previous, 0, previous.length
); |
262 }, | 270 }, |
263 equals: function (currentValue, previousValue) { | 271 equals: function (currentValue, previousValue) { |
264 return currentValue === previousValue; | 272 return currentValue === previousValue; |
265 } | 273 } |
266 }; | 274 }; |
267 return new ArraySplice(); | 275 return new ArraySplice(); |
268 }(); | 276 }(); |
269 Polymer.EventApi = function () { | |
270 var Settings = Polymer.Settings; | |
271 var EventApi = function (event) { | |
272 this.event = event; | |
273 }; | |
274 if (Settings.useShadow) { | |
275 EventApi.prototype = { | |
276 get rootTarget() { | |
277 return this.event.path[0]; | |
278 }, | |
279 get localTarget() { | |
280 return this.event.target; | |
281 }, | |
282 get path() { | |
283 return this.event.path; | |
284 } | |
285 }; | |
286 } else { | |
287 EventApi.prototype = { | |
288 get rootTarget() { | |
289 return this.event.target; | |
290 }, | |
291 get localTarget() { | |
292 var current = this.event.currentTarget; | |
293 var currentRoot = current && Polymer.dom(current).getOwnerRoot(); | |
294 var p$ = this.path; | |
295 for (var i = 0; i < p$.length; i++) { | |
296 if (Polymer.dom(p$[i]).getOwnerRoot() === currentRoot) { | |
297 return p$[i]; | |
298 } | |
299 } | |
300 }, | |
301 get path() { | |
302 if (!this.event._path) { | |
303 var path = []; | |
304 var o = this.rootTarget; | |
305 while (o) { | |
306 path.push(o); | |
307 o = Polymer.dom(o).parentNode || o.host; | |
308 } | |
309 path.push(window); | |
310 this.event._path = path; | |
311 } | |
312 return this.event._path; | |
313 } | |
314 }; | |
315 } | |
316 var factory = function (event) { | |
317 if (!event.__eventApi) { | |
318 event.__eventApi = new EventApi(event); | |
319 } | |
320 return event.__eventApi; | |
321 }; | |
322 return { factory: factory }; | |
323 }(); | |
324 Polymer.domInnerHTML = function () { | 277 Polymer.domInnerHTML = function () { |
325 var escapeAttrRegExp = /[&\u00A0"]/g; | 278 var escapeAttrRegExp = /[&\u00A0"]/g; |
326 var escapeDataRegExp = /[&\u00A0<>]/g; | 279 var escapeDataRegExp = /[&\u00A0<>]/g; |
327 function escapeReplace(c) { | 280 function escapeReplace(c) { |
328 switch (c) { | 281 switch (c) { |
329 case '&': | 282 case '&': |
330 return '&'; | 283 return '&'; |
331 case '<': | 284 case '<': |
332 return '<'; | 285 return '<'; |
333 case '>': | 286 case '>': |
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
419 } | 372 } |
420 return { getInnerHTML: getInnerHTML }; | 373 return { getInnerHTML: getInnerHTML }; |
421 }(); | 374 }(); |
422 Polymer.DomApi = function () { | 375 Polymer.DomApi = function () { |
423 'use strict'; | 376 'use strict'; |
424 var Settings = Polymer.Settings; | 377 var Settings = Polymer.Settings; |
425 var getInnerHTML = Polymer.domInnerHTML.getInnerHTML; | 378 var getInnerHTML = Polymer.domInnerHTML.getInnerHTML; |
426 var nativeInsertBefore = Element.prototype.insertBefore; | 379 var nativeInsertBefore = Element.prototype.insertBefore; |
427 var nativeRemoveChild = Element.prototype.removeChild; | 380 var nativeRemoveChild = Element.prototype.removeChild; |
428 var nativeAppendChild = Element.prototype.appendChild; | 381 var nativeAppendChild = Element.prototype.appendChild; |
429 var dirtyRoots = []; | 382 var nativeCloneNode = Element.prototype.cloneNode; |
| 383 var nativeImportNode = Document.prototype.importNode; |
| 384 var needsToWrap = Settings.hasShadow && !Settings.nativeShadow; |
| 385 var wrap = window.wrap ? window.wrap : function (node) { |
| 386 return node; |
| 387 }; |
430 var DomApi = function (node) { | 388 var DomApi = function (node) { |
431 this.node = node; | 389 this.node = needsToWrap ? wrap(node) : node; |
432 if (this.patch) { | 390 if (this.patch) { |
433 this.patch(); | 391 this.patch(); |
434 } | 392 } |
435 }; | 393 }; |
436 DomApi.prototype = { | 394 DomApi.prototype = { |
437 flush: function () { | 395 flush: function () { |
438 for (var i = 0, host; i < dirtyRoots.length; i++) { | 396 Polymer.dom.flush(); |
439 host = dirtyRoots[i]; | 397 }, |
440 host.flushDebouncer('_distribute'); | 398 deepContains: function (node) { |
| 399 if (this.node.contains(node)) { |
| 400 return true; |
441 } | 401 } |
442 dirtyRoots = []; | 402 var n = node; |
| 403 var wrappedDocument = wrap(document); |
| 404 while (n && n !== wrappedDocument && n !== this.node) { |
| 405 n = Polymer.dom(n).parentNode || n.host; |
| 406 } |
| 407 return n === this.node; |
443 }, | 408 }, |
444 _lazyDistribute: function (host) { | 409 _lazyDistribute: function (host) { |
445 if (host.shadyRoot && host.shadyRoot._distributionClean) { | 410 if (host.shadyRoot && host.shadyRoot._distributionClean) { |
446 host.shadyRoot._distributionClean = false; | 411 host.shadyRoot._distributionClean = false; |
447 host.debounce('_distribute', host._distributeContent); | 412 Polymer.dom.addDebouncer(host.debounce('_distribute', host._distributeContent)); |
448 dirtyRoots.push(host); | |
449 } | 413 } |
450 }, | 414 }, |
451 appendChild: function (node) { | 415 appendChild: function (node) { |
452 var handled; | 416 return this._addNode(node); |
453 this._removeNodeFromHost(node, true); | |
454 if (this._nodeIsInLogicalTree(this.node)) { | |
455 this._addLogicalInfo(node, this.node); | |
456 this._addNodeToHost(node); | |
457 handled = this._maybeDistribute(node, this.node); | |
458 } | |
459 if (!handled && !this._tryRemoveUndistributedNode(node)) { | |
460 var container = this.node._isShadyRoot ? this.node.host : this.node; | |
461 addToComposedParent(container, node); | |
462 nativeAppendChild.call(container, node); | |
463 } | |
464 return node; | |
465 }, | 417 }, |
466 insertBefore: function (node, ref_node) { | 418 insertBefore: function (node, ref_node) { |
467 if (!ref_node) { | 419 return this._addNode(node, ref_node); |
468 return this.appendChild(node); | 420 }, |
| 421 _addNode: function (node, ref_node) { |
| 422 this._removeNodeFromParent(node); |
| 423 var addedInsertionPoint; |
| 424 var root = this.getOwnerRoot(); |
| 425 if (root) { |
| 426 addedInsertionPoint = this._maybeAddInsertionPoint(node, this.node); |
469 } | 427 } |
470 var handled; | 428 if (this._nodeHasLogicalChildren(this.node)) { |
471 this._removeNodeFromHost(node, true); | 429 if (ref_node) { |
472 if (this._nodeIsInLogicalTree(this.node)) { | |
473 saveLightChildrenIfNeeded(this.node); | |
474 var children = this.childNodes; | 430 var children = this.childNodes; |
475 var index = children.indexOf(ref_node); | 431 var index = children.indexOf(ref_node); |
476 if (index < 0) { | 432 if (index < 0) { |
477 throw Error('The ref_node to be inserted before is not a child ' + 'of this node
'); | 433 throw Error('The ref_node to be inserted before is not a child ' + 'of this node
'); |
478 } | 434 } |
| 435 } |
479 this._addLogicalInfo(node, this.node, index); | 436 this._addLogicalInfo(node, this.node, index); |
| 437 } |
480 this._addNodeToHost(node); | 438 this._addNodeToHost(node); |
481 handled = this._maybeDistribute(node, this.node); | 439 if (!this._maybeDistribute(node, this.node) && !this._tryRemoveUndistributedNode
(node)) { |
| 440 if (ref_node) { |
| 441 ref_node = ref_node.localName === CONTENT ? this._firstComposedNode(ref_node) :
ref_node; |
482 } | 442 } |
483 if (!handled && !this._tryRemoveUndistributedNode(node)) { | |
484 ref_node = ref_node.localName === CONTENT ? this._firstComposedNode(ref_node) :
ref_node; | |
485 var container = this.node._isShadyRoot ? this.node.host : this.node; | 443 var container = this.node._isShadyRoot ? this.node.host : this.node; |
486 addToComposedParent(container, node, ref_node); | 444 addToComposedParent(container, node, ref_node); |
| 445 if (ref_node) { |
487 nativeInsertBefore.call(container, node, ref_node); | 446 nativeInsertBefore.call(container, node, ref_node); |
| 447 } else { |
| 448 nativeAppendChild.call(container, node); |
488 } | 449 } |
| 450 } |
| 451 if (addedInsertionPoint) { |
| 452 this._updateInsertionPoints(root.host); |
| 453 } |
| 454 this.notifyObserver(); |
489 return node; | 455 return node; |
490 }, | 456 }, |
491 removeChild: function (node) { | 457 removeChild: function (node) { |
492 if (factory(node).parentNode !== this.node) { | 458 if (factory(node).parentNode !== this.node) { |
493 console.warn('The node to be removed is not a child of this node', node); | 459 console.warn('The node to be removed is not a child of this node', node); |
494 } | 460 } |
495 var handled; | |
496 if (this._nodeIsInLogicalTree(this.node)) { | |
497 this._removeNodeFromHost(node); | 461 this._removeNodeFromHost(node); |
498 handled = this._maybeDistribute(node, this.node); | 462 if (!this._maybeDistribute(node, this.node)) { |
499 } | |
500 if (!handled) { | |
501 var container = this.node._isShadyRoot ? this.node.host : this.node; | 463 var container = this.node._isShadyRoot ? this.node.host : this.node; |
502 if (container === node.parentNode) { | 464 if (container === node.parentNode) { |
503 removeFromComposedParent(container, node); | 465 removeFromComposedParent(container, node); |
504 nativeRemoveChild.call(container, node); | 466 nativeRemoveChild.call(container, node); |
505 } | 467 } |
506 } | 468 } |
| 469 this.notifyObserver(); |
507 return node; | 470 return node; |
508 }, | 471 }, |
509 replaceChild: function (node, ref_node) { | 472 replaceChild: function (node, ref_node) { |
510 this.insertBefore(node, ref_node); | 473 this.insertBefore(node, ref_node); |
511 this.removeChild(ref_node); | 474 this.removeChild(ref_node); |
512 return node; | 475 return node; |
513 }, | 476 }, |
| 477 _hasCachedOwnerRoot: function (node) { |
| 478 return Boolean(node._ownerShadyRoot !== undefined); |
| 479 }, |
514 getOwnerRoot: function () { | 480 getOwnerRoot: function () { |
515 return this._ownerShadyRootForNode(this.node); | 481 return this._ownerShadyRootForNode(this.node); |
516 }, | 482 }, |
517 _ownerShadyRootForNode: function (node) { | 483 _ownerShadyRootForNode: function (node) { |
518 if (!node) { | 484 if (!node) { |
519 return; | 485 return; |
520 } | 486 } |
521 if (node._ownerShadyRoot === undefined) { | 487 if (node._ownerShadyRoot === undefined) { |
522 var root; | 488 var root; |
523 if (node._isShadyRoot) { | 489 if (node._isShadyRoot) { |
524 root = node; | 490 root = node; |
525 } else { | 491 } else { |
526 var parent = Polymer.dom(node).parentNode; | 492 var parent = Polymer.dom(node).parentNode; |
527 if (parent) { | 493 if (parent) { |
528 root = parent._isShadyRoot ? parent : this._ownerShadyRootForNode(parent); | 494 root = parent._isShadyRoot ? parent : this._ownerShadyRootForNode(parent); |
529 } else { | 495 } else { |
530 root = null; | 496 root = null; |
531 } | 497 } |
532 } | 498 } |
533 node._ownerShadyRoot = root; | 499 node._ownerShadyRoot = root; |
534 } | 500 } |
535 return node._ownerShadyRoot; | 501 return node._ownerShadyRoot; |
536 }, | 502 }, |
537 _maybeDistribute: function (node, parent) { | 503 _maybeDistribute: function (node, parent) { |
538 var fragContent = node.nodeType === Node.DOCUMENT_FRAGMENT_NODE && node.querySel
ector(CONTENT); | 504 var fragContent = node.nodeType === Node.DOCUMENT_FRAGMENT_NODE && !node.__noCon
tent && Polymer.dom(node).querySelector(CONTENT); |
539 var wrappedContent = fragContent && fragContent.parentNode.nodeType !== Node.DOC
UMENT_FRAGMENT_NODE; | 505 var wrappedContent = fragContent && Polymer.dom(fragContent).parentNode.nodeType
!== Node.DOCUMENT_FRAGMENT_NODE; |
540 var hasContent = fragContent || node.localName === CONTENT; | 506 var hasContent = fragContent || node.localName === CONTENT; |
541 if (hasContent) { | 507 if (hasContent) { |
542 var root = this._ownerShadyRootForNode(parent); | 508 var root = this._ownerShadyRootForNode(parent); |
543 if (root) { | 509 if (root) { |
544 var host = root.host; | 510 var host = root.host; |
545 this._updateInsertionPoints(host); | |
546 this._lazyDistribute(host); | 511 this._lazyDistribute(host); |
547 } | 512 } |
548 } | 513 } |
549 var parentNeedsDist = this._parentNeedsDistribution(parent); | 514 var parentNeedsDist = this._parentNeedsDistribution(parent); |
550 if (parentNeedsDist) { | 515 if (parentNeedsDist) { |
551 this._lazyDistribute(parent); | 516 this._lazyDistribute(parent); |
552 } | 517 } |
553 return parentNeedsDist || hasContent && !wrappedContent; | 518 return parentNeedsDist || hasContent && !wrappedContent; |
554 }, | 519 }, |
| 520 _maybeAddInsertionPoint: function (node, parent) { |
| 521 var added; |
| 522 if (node.nodeType === Node.DOCUMENT_FRAGMENT_NODE && !node.__noContent) { |
| 523 var c$ = factory(node).querySelectorAll(CONTENT); |
| 524 for (var i = 0, n, np, na; i < c$.length && (n = c$[i]); i++) { |
| 525 np = factory(n).parentNode; |
| 526 if (np === node) { |
| 527 np = parent; |
| 528 } |
| 529 na = this._maybeAddInsertionPoint(n, np); |
| 530 added = added || na; |
| 531 } |
| 532 } else if (node.localName === CONTENT) { |
| 533 saveLightChildrenIfNeeded(parent); |
| 534 saveLightChildrenIfNeeded(node); |
| 535 added = true; |
| 536 } |
| 537 return added; |
| 538 }, |
555 _tryRemoveUndistributedNode: function (node) { | 539 _tryRemoveUndistributedNode: function (node) { |
556 if (this.node.shadyRoot) { | 540 if (this.node.shadyRoot) { |
557 if (node.parentNode) { | 541 var parent = getComposedParent(node); |
558 nativeRemoveChild.call(node.parentNode, node); | 542 if (parent) { |
| 543 nativeRemoveChild.call(parent, node); |
559 } | 544 } |
560 return true; | 545 return true; |
561 } | 546 } |
562 }, | 547 }, |
563 _updateInsertionPoints: function (host) { | 548 _updateInsertionPoints: function (host) { |
564 host.shadyRoot._insertionPoints = factory(host.shadyRoot).querySelectorAll(CONTE
NT); | 549 var i$ = host.shadyRoot._insertionPoints = factory(host.shadyRoot).querySelector
All(CONTENT); |
| 550 for (var i = 0, c; i < i$.length; i++) { |
| 551 c = i$[i]; |
| 552 saveLightChildrenIfNeeded(c); |
| 553 saveLightChildrenIfNeeded(factory(c).parentNode); |
| 554 } |
565 }, | 555 }, |
566 _nodeIsInLogicalTree: function (node) { | 556 _nodeHasLogicalChildren: function (node) { |
567 return Boolean(node._lightParent || node._isShadyRoot || this._ownerShadyRootFor
Node(node) || node.shadyRoot); | 557 return Boolean(node._lightChildren !== undefined); |
568 }, | 558 }, |
569 _parentNeedsDistribution: function (parent) { | 559 _parentNeedsDistribution: function (parent) { |
570 return parent && parent.shadyRoot && hasInsertionPoint(parent.shadyRoot); | 560 return parent && parent.shadyRoot && hasInsertionPoint(parent.shadyRoot); |
571 }, | 561 }, |
| 562 _removeNodeFromParent: function (node) { |
| 563 var parent = node._lightParent || node.parentNode; |
| 564 if (parent && hasDomApi(parent)) { |
| 565 factory(parent).notifyObserver(); |
| 566 } |
| 567 this._removeNodeFromHost(node, true); |
| 568 }, |
572 _removeNodeFromHost: function (node, ensureComposedRemoval) { | 569 _removeNodeFromHost: function (node, ensureComposedRemoval) { |
573 var hostNeedsDist; | 570 var hostNeedsDist; |
574 var root; | 571 var root; |
575 var parent = node._lightParent; | 572 var parent = node._lightParent; |
576 if (parent) { | 573 if (parent) { |
| 574 factory(node)._distributeParent(); |
577 root = this._ownerShadyRootForNode(node); | 575 root = this._ownerShadyRootForNode(node); |
578 if (root) { | 576 if (root) { |
579 root.host._elementRemove(node); | 577 root.host._elementRemove(node); |
580 hostNeedsDist = this._removeDistributedChildren(root, node); | 578 hostNeedsDist = this._removeDistributedChildren(root, node); |
581 } | 579 } |
582 this._removeLogicalInfo(node, node._lightParent); | 580 this._removeLogicalInfo(node, parent); |
583 } | 581 } |
584 this._removeOwnerShadyRoot(node); | 582 this._removeOwnerShadyRoot(node); |
585 if (root && hostNeedsDist) { | 583 if (root && hostNeedsDist) { |
586 this._updateInsertionPoints(root.host); | 584 this._updateInsertionPoints(root.host); |
587 this._lazyDistribute(root.host); | 585 this._lazyDistribute(root.host); |
588 } else if (ensureComposedRemoval) { | 586 } else if (ensureComposedRemoval) { |
589 removeFromComposedParent(parent || node.parentNode, node); | 587 removeFromComposedParent(getComposedParent(node), node); |
590 } | 588 } |
591 }, | 589 }, |
592 _removeDistributedChildren: function (root, container) { | 590 _removeDistributedChildren: function (root, container) { |
593 var hostNeedsDist; | 591 var hostNeedsDist; |
594 var ip$ = root._insertionPoints; | 592 var ip$ = root._insertionPoints; |
595 for (var i = 0; i < ip$.length; i++) { | 593 for (var i = 0; i < ip$.length; i++) { |
596 var content = ip$[i]; | 594 var content = ip$[i]; |
597 if (this._contains(container, content)) { | 595 if (this._contains(container, content)) { |
598 var dc$ = factory(content).getDistributedNodes(); | 596 var dc$ = factory(content).getDistributedNodes(); |
599 for (var j = 0; j < dc$.length; j++) { | 597 for (var j = 0; j < dc$.length; j++) { |
600 hostNeedsDist = true; | 598 hostNeedsDist = true; |
601 var node = dc$[i]; | 599 var node = dc$[j]; |
602 var parent = node.parentNode; | 600 var parent = node.parentNode; |
603 if (parent) { | 601 if (parent) { |
604 removeFromComposedParent(parent, node); | 602 removeFromComposedParent(parent, node); |
605 nativeRemoveChild.call(parent, node); | 603 nativeRemoveChild.call(parent, node); |
606 } | 604 } |
607 } | 605 } |
608 } | 606 } |
609 } | 607 } |
610 return hostNeedsDist; | 608 return hostNeedsDist; |
611 }, | 609 }, |
612 _contains: function (container, node) { | 610 _contains: function (container, node) { |
613 while (node) { | 611 while (node) { |
614 if (node == container) { | 612 if (node == container) { |
615 return true; | 613 return true; |
616 } | 614 } |
617 node = factory(node).parentNode; | 615 node = factory(node).parentNode; |
618 } | 616 } |
619 }, | 617 }, |
620 _addNodeToHost: function (node) { | 618 _addNodeToHost: function (node) { |
621 var checkNode = node.nodeType === Node.DOCUMENT_FRAGMENT_NODE ? node.firstChild
: node; | 619 var root = this.getOwnerRoot(); |
622 var root = this._ownerShadyRootForNode(checkNode); | |
623 if (root) { | 620 if (root) { |
624 root.host._elementAdd(node); | 621 root.host._elementAdd(node); |
625 } | 622 } |
626 }, | 623 }, |
627 _addLogicalInfo: function (node, container, index) { | 624 _addLogicalInfo: function (node, container, index) { |
628 saveLightChildrenIfNeeded(container); | |
629 var children = factory(container).childNodes; | 625 var children = factory(container).childNodes; |
630 index = index === undefined ? children.length : index; | 626 index = index === undefined ? children.length : index; |
631 if (node.nodeType === Node.DOCUMENT_FRAGMENT_NODE) { | 627 if (node.nodeType === Node.DOCUMENT_FRAGMENT_NODE) { |
632 var c$ = Array.prototype.slice.call(node.childNodes); | 628 var c$ = arrayCopyChildNodes(node); |
633 for (var i = 0, n; i < c$.length && (n = c$[i]); i++) { | 629 for (var i = 0, n; i < c$.length && (n = c$[i]); i++) { |
634 children.splice(index++, 0, n); | 630 children.splice(index++, 0, n); |
635 n._lightParent = container; | 631 n._lightParent = container; |
636 } | 632 } |
637 } else { | 633 } else { |
638 children.splice(index, 0, node); | 634 children.splice(index, 0, node); |
639 node._lightParent = container; | 635 node._lightParent = container; |
640 } | 636 } |
641 }, | 637 }, |
642 _removeLogicalInfo: function (node, container) { | 638 _removeLogicalInfo: function (node, container) { |
643 var children = factory(container).childNodes; | 639 var children = factory(container).childNodes; |
644 var index = children.indexOf(node); | 640 var index = children.indexOf(node); |
645 if (index < 0 || container !== node._lightParent) { | 641 if (index < 0 || container !== node._lightParent) { |
646 throw Error('The node to be removed is not a child of this node'); | 642 throw Error('The node to be removed is not a child of this node'); |
647 } | 643 } |
648 children.splice(index, 1); | 644 children.splice(index, 1); |
649 node._lightParent = null; | 645 node._lightParent = null; |
650 }, | 646 }, |
651 _removeOwnerShadyRoot: function (node) { | 647 _removeOwnerShadyRoot: function (node) { |
652 var hasCachedRoot = factory(node).getOwnerRoot() !== undefined; | 648 if (this._hasCachedOwnerRoot(node)) { |
653 if (hasCachedRoot) { | |
654 var c$ = factory(node).childNodes; | 649 var c$ = factory(node).childNodes; |
655 for (var i = 0, l = c$.length, n; i < l && (n = c$[i]); i++) { | 650 for (var i = 0, l = c$.length, n; i < l && (n = c$[i]); i++) { |
656 this._removeOwnerShadyRoot(n); | 651 this._removeOwnerShadyRoot(n); |
657 } | 652 } |
658 } | 653 } |
659 node._ownerShadyRoot = undefined; | 654 node._ownerShadyRoot = undefined; |
660 }, | 655 }, |
661 _firstComposedNode: function (content) { | 656 _firstComposedNode: function (content) { |
662 var n$ = factory(content).getDistributedNodes(); | 657 var n$ = factory(content).getDistributedNodes(); |
663 for (var i = 0, l = n$.length, n, p$; i < l && (n = n$[i]); i++) { | 658 for (var i = 0, l = n$.length, n, p$; i < l && (n = n$[i]); i++) { |
(...skipping 30 matching lines...) Expand all Loading... |
694 } | 689 } |
695 this._queryElements(factory(node).childNodes, matcher, list); | 690 this._queryElements(factory(node).childNodes, matcher, list); |
696 }, | 691 }, |
697 getDestinationInsertionPoints: function () { | 692 getDestinationInsertionPoints: function () { |
698 return this.node._destinationInsertionPoints || []; | 693 return this.node._destinationInsertionPoints || []; |
699 }, | 694 }, |
700 getDistributedNodes: function () { | 695 getDistributedNodes: function () { |
701 return this.node._distributedNodes || []; | 696 return this.node._distributedNodes || []; |
702 }, | 697 }, |
703 queryDistributedElements: function (selector) { | 698 queryDistributedElements: function (selector) { |
704 var c$ = this.childNodes; | 699 var c$ = this.getEffectiveChildNodes(); |
705 var list = []; | 700 var list = []; |
706 this._distributedFilter(selector, c$, list); | |
707 for (var i = 0, l = c$.length, c; i < l && (c = c$[i]); i++) { | 701 for (var i = 0, l = c$.length, c; i < l && (c = c$[i]); i++) { |
708 if (c.localName === CONTENT) { | 702 if (c.nodeType === Node.ELEMENT_NODE && matchesSelector.call(c, selector)) { |
709 this._distributedFilter(selector, factory(c).getDistributedNodes(), list); | 703 list.push(c); |
710 } | 704 } |
711 } | 705 } |
712 return list; | 706 return list; |
713 }, | 707 }, |
714 _distributedFilter: function (selector, list, results) { | 708 getEffectiveChildNodes: function () { |
715 results = results || []; | 709 var list = []; |
716 for (var i = 0, l = list.length, d; i < l && (d = list[i]); i++) { | 710 var c$ = this.childNodes; |
717 if (d.nodeType === Node.ELEMENT_NODE && d.localName !== CONTENT && matchesSelect
or.call(d, selector)) { | 711 for (var i = 0, l = c$.length, c; i < l && (c = c$[i]); i++) { |
718 results.push(d); | 712 if (c.localName === CONTENT) { |
| 713 var d$ = factory(c).getDistributedNodes(); |
| 714 for (var j = 0; j < d$.length; j++) { |
| 715 list.push(d$[j]); |
| 716 } |
| 717 } else { |
| 718 list.push(c); |
719 } | 719 } |
720 } | 720 } |
721 return results; | 721 return list; |
722 }, | 722 }, |
723 _clear: function () { | 723 _clear: function () { |
724 while (this.childNodes.length) { | 724 while (this.childNodes.length) { |
725 this.removeChild(this.childNodes[0]); | 725 this.removeChild(this.childNodes[0]); |
726 } | 726 } |
727 }, | 727 }, |
728 setAttribute: function (name, value) { | 728 setAttribute: function (name, value) { |
729 this.node.setAttribute(name, value); | 729 this.node.setAttribute(name, value); |
730 this._distributeParent(); | 730 this._distributeParent(); |
731 }, | 731 }, |
732 removeAttribute: function (name) { | 732 removeAttribute: function (name) { |
733 this.node.removeAttribute(name); | 733 this.node.removeAttribute(name); |
734 this._distributeParent(); | 734 this._distributeParent(); |
735 }, | 735 }, |
736 _distributeParent: function () { | 736 _distributeParent: function () { |
737 if (this._parentNeedsDistribution(this.parentNode)) { | 737 if (this._parentNeedsDistribution(this.parentNode)) { |
738 this._lazyDistribute(this.parentNode); | 738 this._lazyDistribute(this.parentNode); |
739 } | 739 } |
| 740 }, |
| 741 cloneNode: function (deep) { |
| 742 var n = nativeCloneNode.call(this.node, false); |
| 743 if (deep) { |
| 744 var c$ = this.childNodes; |
| 745 var d = factory(n); |
| 746 for (var i = 0, nc; i < c$.length; i++) { |
| 747 nc = factory(c$[i]).cloneNode(true); |
| 748 d.appendChild(nc); |
740 } | 749 } |
741 }; | |
742 Object.defineProperty(DomApi.prototype, 'classList', { | |
743 get: function () { | |
744 if (!this._classList) { | |
745 this._classList = new DomApi.ClassList(this); | |
746 } | 750 } |
747 return this._classList; | 751 return n; |
748 }, | 752 }, |
749 configurable: true | 753 importNode: function (externalNode, deep) { |
750 }); | 754 var doc = this.node instanceof Document ? this.node : this.node.ownerDocument; |
751 DomApi.ClassList = function (host) { | 755 var n = nativeImportNode.call(doc, externalNode, false); |
752 this.domApi = host; | 756 if (deep) { |
753 this.node = host.node; | 757 var c$ = factory(externalNode).childNodes; |
754 }; | 758 var d = factory(n); |
755 DomApi.ClassList.prototype = { | 759 for (var i = 0, nc; i < c$.length; i++) { |
756 add: function () { | 760 nc = factory(doc).importNode(c$[i], true); |
757 this.node.classList.add.apply(this.node.classList, arguments); | 761 d.appendChild(nc); |
758 this.domApi._distributeParent(); | 762 } |
| 763 } |
| 764 return n; |
759 }, | 765 }, |
760 remove: function () { | 766 observeNodes: function (callback) { |
761 this.node.classList.remove.apply(this.node.classList, arguments); | 767 if (callback) { |
762 this.domApi._distributeParent(); | 768 if (!this.observer) { |
| 769 this.observer = this.node.localName === CONTENT ? new DomApi.DistributedNodesObs
erver(this) : new DomApi.EffectiveNodesObserver(this); |
| 770 } |
| 771 return this.observer.addListener(callback); |
| 772 } |
763 }, | 773 }, |
764 toggle: function () { | 774 unobserveNodes: function (handle) { |
765 this.node.classList.toggle.apply(this.node.classList, arguments); | 775 if (this.observer) { |
766 this.domApi._distributeParent(); | 776 this.observer.removeListener(handle); |
| 777 } |
| 778 }, |
| 779 notifyObserver: function () { |
| 780 if (this.observer) { |
| 781 this.observer.notify(); |
| 782 } |
767 } | 783 } |
768 }; | 784 }; |
769 if (!Settings.useShadow) { | 785 if (!Settings.useShadow) { |
770 Object.defineProperties(DomApi.prototype, { | 786 Object.defineProperties(DomApi.prototype, { |
771 childNodes: { | 787 childNodes: { |
772 get: function () { | 788 get: function () { |
773 var c$ = getLightChildren(this.node); | 789 var c$ = getLightChildren(this.node); |
774 return Array.isArray(c$) ? c$ : Array.prototype.slice.call(c$); | 790 return Array.isArray(c$) ? c$ : arrayCopyChildNodes(this.node); |
775 }, | 791 }, |
776 configurable: true | 792 configurable: true |
777 }, | 793 }, |
778 children: { | 794 children: { |
779 get: function () { | 795 get: function () { |
780 return Array.prototype.filter.call(this.childNodes, function (n) { | 796 return Array.prototype.filter.call(this.childNodes, function (n) { |
781 return n.nodeType === Node.ELEMENT_NODE; | 797 return n.nodeType === Node.ELEMENT_NODE; |
782 }); | 798 }); |
783 }, | 799 }, |
784 configurable: true | 800 configurable: true |
785 }, | 801 }, |
786 parentNode: { | 802 parentNode: { |
787 get: function () { | 803 get: function () { |
788 return this.node._lightParent || (this.node.__patched ? this.node._composedParen
t : this.node.parentNode); | 804 return this.node._lightParent || getComposedParent(this.node); |
789 }, | 805 }, |
790 configurable: true | 806 configurable: true |
791 }, | 807 }, |
792 firstChild: { | 808 firstChild: { |
793 get: function () { | 809 get: function () { |
794 return this.childNodes[0]; | 810 return this.childNodes[0]; |
795 }, | 811 }, |
796 configurable: true | 812 configurable: true |
797 }, | 813 }, |
798 lastChild: { | 814 lastChild: { |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
846 get: function () { | 862 get: function () { |
847 var c$ = this.parentNode && factory(this.parentNode).children; | 863 var c$ = this.parentNode && factory(this.parentNode).children; |
848 if (c$) { | 864 if (c$) { |
849 return c$[Array.prototype.indexOf.call(c$, this.node) - 1]; | 865 return c$[Array.prototype.indexOf.call(c$, this.node) - 1]; |
850 } | 866 } |
851 }, | 867 }, |
852 configurable: true | 868 configurable: true |
853 }, | 869 }, |
854 textContent: { | 870 textContent: { |
855 get: function () { | 871 get: function () { |
856 if (this.node.nodeType === Node.TEXT_NODE) { | 872 var nt = this.node.nodeType; |
| 873 if (nt === Node.TEXT_NODE || nt === Node.COMMENT_NODE) { |
857 return this.node.textContent; | 874 return this.node.textContent; |
858 } else { | 875 } else { |
859 return Array.prototype.map.call(this.childNodes, function (c) { | 876 var tc = []; |
860 return c.textContent; | 877 for (var i = 0, cn = this.childNodes, c; c = cn[i]; i++) { |
861 }).join(''); | 878 if (c.nodeType !== Node.COMMENT_NODE) { |
| 879 tc.push(c.textContent); |
| 880 } |
| 881 } |
| 882 return tc.join(''); |
862 } | 883 } |
863 }, | 884 }, |
864 set: function (text) { | 885 set: function (text) { |
| 886 var nt = this.node.nodeType; |
| 887 if (nt === Node.TEXT_NODE || nt === Node.COMMENT_NODE) { |
| 888 this.node.textContent = text; |
| 889 } else { |
865 this._clear(); | 890 this._clear(); |
866 if (text) { | 891 if (text) { |
867 this.appendChild(document.createTextNode(text)); | 892 this.appendChild(document.createTextNode(text)); |
868 } | 893 } |
| 894 } |
869 }, | 895 }, |
870 configurable: true | 896 configurable: true |
871 }, | 897 }, |
872 innerHTML: { | 898 innerHTML: { |
873 get: function () { | 899 get: function () { |
874 if (this.node.nodeType === Node.TEXT_NODE) { | 900 var nt = this.node.nodeType; |
| 901 if (nt === Node.TEXT_NODE || nt === Node.COMMENT_NODE) { |
875 return null; | 902 return null; |
876 } else { | 903 } else { |
877 return getInnerHTML(this.node); | 904 return getInnerHTML(this.node); |
878 } | 905 } |
879 }, | 906 }, |
880 set: function (text) { | 907 set: function (text) { |
881 if (this.node.nodeType !== Node.TEXT_NODE) { | 908 var nt = this.node.nodeType; |
| 909 if (nt !== Node.TEXT_NODE || nt !== Node.COMMENT_NODE) { |
882 this._clear(); | 910 this._clear(); |
883 var d = document.createElement('div'); | 911 var d = document.createElement('div'); |
884 d.innerHTML = text; | 912 d.innerHTML = text; |
885 for (var e = d.firstChild; e; e = e.nextSibling) { | 913 var c$ = arrayCopyChildNodes(d); |
886 this.appendChild(e); | 914 for (var i = 0; i < c$.length; i++) { |
| 915 this.appendChild(c$[i]); |
887 } | 916 } |
888 } | 917 } |
889 }, | 918 }, |
890 configurable: true | 919 configurable: true |
891 } | 920 } |
892 }); | 921 }); |
893 DomApi.prototype._getComposedInnerHTML = function () { | 922 DomApi.prototype._getComposedInnerHTML = function () { |
894 return getInnerHTML(this.node, true); | 923 return getInnerHTML(this.node, true); |
895 }; | 924 }; |
896 } else { | 925 } else { |
| 926 var forwardMethods = function (m$) { |
| 927 for (var i = 0; i < m$.length; i++) { |
| 928 forwardMethod(m$[i]); |
| 929 } |
| 930 }; |
| 931 var forwardMethod = function (method) { |
| 932 DomApi.prototype[method] = function () { |
| 933 return this.node[method].apply(this.node, arguments); |
| 934 }; |
| 935 }; |
| 936 forwardMethods([ |
| 937 'cloneNode', |
| 938 'appendChild', |
| 939 'insertBefore', |
| 940 'removeChild', |
| 941 'replaceChild' |
| 942 ]); |
897 DomApi.prototype.querySelectorAll = function (selector) { | 943 DomApi.prototype.querySelectorAll = function (selector) { |
898 return Array.prototype.slice.call(this.node.querySelectorAll(selector)); | 944 return arrayCopy(this.node.querySelectorAll(selector)); |
899 }; | 945 }; |
900 DomApi.prototype.getOwnerRoot = function () { | 946 DomApi.prototype.getOwnerRoot = function () { |
901 var n = this.node; | 947 var n = this.node; |
902 while (n) { | 948 while (n) { |
903 if (n.nodeType === Node.DOCUMENT_FRAGMENT_NODE && n.host) { | 949 if (n.nodeType === Node.DOCUMENT_FRAGMENT_NODE && n.host) { |
904 return n; | 950 return n; |
905 } | 951 } |
906 n = n.parentNode; | 952 n = n.parentNode; |
907 } | 953 } |
908 }; | 954 }; |
| 955 DomApi.prototype.importNode = function (externalNode, deep) { |
| 956 var doc = this.node instanceof Document ? this.node : this.node.ownerDocument; |
| 957 return doc.importNode(externalNode, deep); |
| 958 }; |
909 DomApi.prototype.getDestinationInsertionPoints = function () { | 959 DomApi.prototype.getDestinationInsertionPoints = function () { |
910 var n$ = this.node.getDestinationInsertionPoints(); | 960 var n$ = this.node.getDestinationInsertionPoints && this.node.getDestinationInse
rtionPoints(); |
911 return n$ ? Array.prototype.slice.call(n$) : []; | 961 return n$ ? arrayCopy(n$) : []; |
912 }; | 962 }; |
913 DomApi.prototype.getDistributedNodes = function () { | 963 DomApi.prototype.getDistributedNodes = function () { |
914 var n$ = this.node.getDistributedNodes(); | 964 var n$ = this.node.getDistributedNodes && this.node.getDistributedNodes(); |
915 return n$ ? Array.prototype.slice.call(n$) : []; | 965 return n$ ? arrayCopy(n$) : []; |
916 }; | 966 }; |
917 DomApi.prototype._distributeParent = function () { | 967 DomApi.prototype._distributeParent = function () { |
918 }; | 968 }; |
919 Object.defineProperties(DomApi.prototype, { | 969 Object.defineProperties(DomApi.prototype, { |
920 childNodes: { | 970 childNodes: { |
921 get: function () { | 971 get: function () { |
922 return Array.prototype.slice.call(this.node.childNodes); | 972 return arrayCopyChildNodes(this.node); |
923 }, | 973 }, |
924 configurable: true | 974 configurable: true |
925 }, | 975 }, |
926 children: { | 976 children: { |
927 get: function () { | 977 get: function () { |
928 return Array.prototype.slice.call(this.node.children); | 978 return arrayCopyChildren(this.node); |
929 }, | 979 }, |
930 configurable: true | 980 configurable: true |
931 }, | 981 }, |
932 textContent: { | 982 textContent: { |
933 get: function () { | 983 get: function () { |
934 return this.node.textContent; | 984 return this.node.textContent; |
935 }, | 985 }, |
936 set: function (value) { | 986 set: function (value) { |
937 return this.node.textContent = value; | 987 return this.node.textContent = value; |
938 }, | 988 }, |
939 configurable: true | 989 configurable: true |
940 }, | 990 }, |
941 innerHTML: { | 991 innerHTML: { |
942 get: function () { | 992 get: function () { |
943 return this.node.innerHTML; | 993 return this.node.innerHTML; |
944 }, | 994 }, |
945 set: function (value) { | 995 set: function (value) { |
946 return this.node.innerHTML = value; | 996 return this.node.innerHTML = value; |
947 }, | 997 }, |
948 configurable: true | 998 configurable: true |
949 } | 999 } |
950 }); | 1000 }); |
951 var forwards = [ | 1001 var forwardProperties = function (f$) { |
| 1002 for (var i = 0; i < f$.length; i++) { |
| 1003 forwardProperty(f$[i]); |
| 1004 } |
| 1005 }; |
| 1006 var forwardProperty = function (name) { |
| 1007 Object.defineProperty(DomApi.prototype, name, { |
| 1008 get: function () { |
| 1009 return this.node[name]; |
| 1010 }, |
| 1011 configurable: true |
| 1012 }); |
| 1013 }; |
| 1014 forwardProperties([ |
952 'parentNode', | 1015 'parentNode', |
953 'firstChild', | 1016 'firstChild', |
954 'lastChild', | 1017 'lastChild', |
955 'nextSibling', | 1018 'nextSibling', |
956 'previousSibling', | 1019 'previousSibling', |
957 'firstElementChild', | 1020 'firstElementChild', |
958 'lastElementChild', | 1021 'lastElementChild', |
959 'nextElementSibling', | 1022 'nextElementSibling', |
960 'previousElementSibling' | 1023 'previousElementSibling' |
961 ]; | 1024 ]); |
962 forwards.forEach(function (name) { | |
963 Object.defineProperty(DomApi.prototype, name, { | |
964 get: function () { | |
965 return this.node[name]; | |
966 }, | |
967 configurable: true | |
968 }); | |
969 }); | |
970 } | 1025 } |
971 var CONTENT = 'content'; | 1026 var CONTENT = 'content'; |
972 var factory = function (node, patch) { | 1027 function factory(node, patch) { |
973 node = node || document; | 1028 node = node || document; |
974 if (!node.__domApi) { | 1029 if (!node.__domApi) { |
975 node.__domApi = new DomApi(node, patch); | 1030 node.__domApi = new DomApi(node, patch); |
976 } | 1031 } |
977 return node.__domApi; | 1032 return node.__domApi; |
978 }; | 1033 } |
| 1034 ; |
| 1035 function hasDomApi(node) { |
| 1036 return Boolean(node.__domApi); |
| 1037 } |
| 1038 ; |
979 Polymer.dom = function (obj, patch) { | 1039 Polymer.dom = function (obj, patch) { |
980 if (obj instanceof Event) { | 1040 if (obj instanceof Event) { |
981 return Polymer.EventApi.factory(obj); | 1041 return Polymer.EventApi.factory(obj); |
982 } else { | 1042 } else { |
983 return factory(obj, patch); | 1043 return factory(obj, patch); |
984 } | 1044 } |
985 }; | 1045 }; |
986 Polymer.dom.flush = DomApi.prototype.flush; | |
987 function getLightChildren(node) { | 1046 function getLightChildren(node) { |
988 var children = node._lightChildren; | 1047 var children = node._lightChildren; |
989 return children ? children : node.childNodes; | 1048 return children ? children : node.childNodes; |
990 } | 1049 } |
991 function getComposedChildren(node) { | 1050 function getComposedChildren(node) { |
992 if (!node._composedChildren) { | 1051 if (!node._composedChildren) { |
993 node._composedChildren = Array.prototype.slice.call(node.childNodes); | 1052 node._composedChildren = arrayCopyChildNodes(node); |
994 } | 1053 } |
995 return node._composedChildren; | 1054 return node._composedChildren; |
996 } | 1055 } |
997 function addToComposedParent(parent, node, ref_node) { | 1056 function addToComposedParent(parent, node, ref_node) { |
998 var children = getComposedChildren(parent); | 1057 var children = getComposedChildren(parent); |
999 var i = ref_node ? children.indexOf(ref_node) : -1; | 1058 var i = ref_node ? children.indexOf(ref_node) : -1; |
1000 if (node.nodeType === Node.DOCUMENT_FRAGMENT_NODE) { | 1059 if (node.nodeType === Node.DOCUMENT_FRAGMENT_NODE) { |
1001 var fragChildren = getComposedChildren(node); | 1060 var fragChildren = getComposedChildren(node); |
1002 for (var j = 0; j < fragChildren.length; j++) { | 1061 for (var j = 0; j < fragChildren.length; j++) { |
1003 addNodeToComposedChildren(fragChildren[j], parent, children, i + j); | 1062 addNodeToComposedChildren(fragChildren[j], parent, children, i + j); |
1004 } | 1063 } |
1005 node._composedChildren = null; | 1064 node._composedChildren = null; |
1006 } else { | 1065 } else { |
1007 addNodeToComposedChildren(node, parent, children, i); | 1066 addNodeToComposedChildren(node, parent, children, i); |
1008 } | 1067 } |
1009 } | 1068 } |
| 1069 function getComposedParent(node) { |
| 1070 return node.__patched ? node._composedParent : node.parentNode; |
| 1071 } |
1010 function addNodeToComposedChildren(node, parent, children, i) { | 1072 function addNodeToComposedChildren(node, parent, children, i) { |
1011 node._composedParent = parent; | 1073 node._composedParent = parent; |
1012 children.splice(i >= 0 ? i : children.length, 0, node); | 1074 children.splice(i >= 0 ? i : children.length, 0, node); |
1013 } | 1075 } |
1014 function removeFromComposedParent(parent, node) { | 1076 function removeFromComposedParent(parent, node) { |
1015 node._composedParent = null; | 1077 node._composedParent = null; |
1016 if (parent) { | 1078 if (parent) { |
1017 var children = getComposedChildren(parent); | 1079 var children = getComposedChildren(parent); |
1018 var i = children.indexOf(node); | 1080 var i = children.indexOf(node); |
1019 if (i >= 0) { | 1081 if (i >= 0) { |
1020 children.splice(i, 1); | 1082 children.splice(i, 1); |
1021 } | 1083 } |
1022 } | 1084 } |
1023 } | 1085 } |
1024 function saveLightChildrenIfNeeded(node) { | 1086 function saveLightChildrenIfNeeded(node) { |
1025 if (!node._lightChildren) { | 1087 if (!node._lightChildren) { |
1026 var c$ = Array.prototype.slice.call(node.childNodes); | 1088 var c$ = arrayCopyChildNodes(node); |
1027 for (var i = 0, l = c$.length, child; i < l && (child = c$[i]); i++) { | 1089 for (var i = 0, l = c$.length, child; i < l && (child = c$[i]); i++) { |
1028 child._lightParent = child._lightParent || node; | 1090 child._lightParent = child._lightParent || node; |
1029 } | 1091 } |
1030 node._lightChildren = c$; | 1092 node._lightChildren = c$; |
1031 } | 1093 } |
1032 } | 1094 } |
| 1095 function arrayCopyChildNodes(parent) { |
| 1096 var copy = [], i = 0; |
| 1097 for (var n = parent.firstChild; n; n = n.nextSibling) { |
| 1098 copy[i++] = n; |
| 1099 } |
| 1100 return copy; |
| 1101 } |
| 1102 function arrayCopyChildren(parent) { |
| 1103 var copy = [], i = 0; |
| 1104 for (var n = parent.firstElementChild; n; n = n.nextElementSibling) { |
| 1105 copy[i++] = n; |
| 1106 } |
| 1107 return copy; |
| 1108 } |
| 1109 function arrayCopy(a$) { |
| 1110 var l = a$.length; |
| 1111 var copy = new Array(l); |
| 1112 for (var i = 0; i < l; i++) { |
| 1113 copy[i] = a$[i]; |
| 1114 } |
| 1115 return copy; |
| 1116 } |
1033 function hasInsertionPoint(root) { | 1117 function hasInsertionPoint(root) { |
1034 return Boolean(root._insertionPoints.length); | 1118 return Boolean(root && root._insertionPoints.length); |
1035 } | 1119 } |
1036 var p = Element.prototype; | 1120 var p = Element.prototype; |
1037 var matchesSelector = p.matches || p.matchesSelector || p.mozMatchesSelector ||
p.msMatchesSelector || p.oMatchesSelector || p.webkitMatchesSelector; | 1121 var matchesSelector = p.matches || p.matchesSelector || p.mozMatchesSelector ||
p.msMatchesSelector || p.oMatchesSelector || p.webkitMatchesSelector; |
1038 return { | 1122 return { |
1039 getLightChildren: getLightChildren, | 1123 getLightChildren: getLightChildren, |
| 1124 getComposedParent: getComposedParent, |
1040 getComposedChildren: getComposedChildren, | 1125 getComposedChildren: getComposedChildren, |
1041 removeFromComposedParent: removeFromComposedParent, | 1126 removeFromComposedParent: removeFromComposedParent, |
1042 saveLightChildrenIfNeeded: saveLightChildrenIfNeeded, | 1127 saveLightChildrenIfNeeded: saveLightChildrenIfNeeded, |
1043 matchesSelector: matchesSelector, | 1128 matchesSelector: matchesSelector, |
1044 hasInsertionPoint: hasInsertionPoint, | 1129 hasInsertionPoint: hasInsertionPoint, |
1045 ctor: DomApi, | 1130 ctor: DomApi, |
1046 factory: factory | 1131 factory: factory, |
1047 }; | 1132 hasDomApi: hasDomApi, |
| 1133 arrayCopy: arrayCopy, |
| 1134 arrayCopyChildNodes: arrayCopyChildNodes, |
| 1135 arrayCopyChildren: arrayCopyChildren, |
| 1136 wrap: wrap |
| 1137 }; |
| 1138 }(); |
| 1139 Polymer.Base.extend(Polymer.dom, { |
| 1140 _flushGuard: 0, |
| 1141 _FLUSH_MAX: 100, |
| 1142 _needsTakeRecords: !Polymer.Settings.useNativeCustomElements, |
| 1143 _debouncers: [], |
| 1144 _staticFlushList: [], |
| 1145 _finishDebouncer: null, |
| 1146 flush: function () { |
| 1147 this._flushGuard = 0; |
| 1148 this._prepareFlush(); |
| 1149 while (this._debouncers.length && this._flushGuard < this._FLUSH_MAX) { |
| 1150 for (var i = 0; i < this._debouncers.length; i++) { |
| 1151 this._debouncers[i].complete(); |
| 1152 } |
| 1153 if (this._finishDebouncer) { |
| 1154 this._finishDebouncer.complete(); |
| 1155 } |
| 1156 this._prepareFlush(); |
| 1157 this._flushGuard++; |
| 1158 } |
| 1159 if (this._flushGuard >= this._FLUSH_MAX) { |
| 1160 console.warn('Polymer.dom.flush aborted. Flush may not be complete.'); |
| 1161 } |
| 1162 }, |
| 1163 _prepareFlush: function () { |
| 1164 if (this._needsTakeRecords) { |
| 1165 CustomElements.takeRecords(); |
| 1166 } |
| 1167 for (var i = 0; i < this._staticFlushList.length; i++) { |
| 1168 this._staticFlushList[i](); |
| 1169 } |
| 1170 }, |
| 1171 addStaticFlush: function (fn) { |
| 1172 this._staticFlushList.push(fn); |
| 1173 }, |
| 1174 removeStaticFlush: function (fn) { |
| 1175 var i = this._staticFlushList.indexOf(fn); |
| 1176 if (i >= 0) { |
| 1177 this._staticFlushList.splice(i, 1); |
| 1178 } |
| 1179 }, |
| 1180 addDebouncer: function (debouncer) { |
| 1181 this._debouncers.push(debouncer); |
| 1182 this._finishDebouncer = Polymer.Debounce(this._finishDebouncer, this._finishFlus
h); |
| 1183 }, |
| 1184 _finishFlush: function () { |
| 1185 Polymer.dom._debouncers = []; |
| 1186 } |
| 1187 }); |
| 1188 Polymer.EventApi = function () { |
| 1189 'use strict'; |
| 1190 var DomApi = Polymer.DomApi.ctor; |
| 1191 var Settings = Polymer.Settings; |
| 1192 DomApi.Event = function (event) { |
| 1193 this.event = event; |
| 1194 }; |
| 1195 if (Settings.useShadow) { |
| 1196 DomApi.Event.prototype = { |
| 1197 get rootTarget() { |
| 1198 return this.event.path[0]; |
| 1199 }, |
| 1200 get localTarget() { |
| 1201 return this.event.target; |
| 1202 }, |
| 1203 get path() { |
| 1204 return this.event.path; |
| 1205 } |
| 1206 }; |
| 1207 } else { |
| 1208 DomApi.Event.prototype = { |
| 1209 get rootTarget() { |
| 1210 return this.event.target; |
| 1211 }, |
| 1212 get localTarget() { |
| 1213 var current = this.event.currentTarget; |
| 1214 var currentRoot = current && Polymer.dom(current).getOwnerRoot(); |
| 1215 var p$ = this.path; |
| 1216 for (var i = 0; i < p$.length; i++) { |
| 1217 if (Polymer.dom(p$[i]).getOwnerRoot() === currentRoot) { |
| 1218 return p$[i]; |
| 1219 } |
| 1220 } |
| 1221 }, |
| 1222 get path() { |
| 1223 if (!this.event._path) { |
| 1224 var path = []; |
| 1225 var o = this.rootTarget; |
| 1226 while (o) { |
| 1227 path.push(o); |
| 1228 o = Polymer.dom(o).parentNode || o.host; |
| 1229 } |
| 1230 path.push(window); |
| 1231 this.event._path = path; |
| 1232 } |
| 1233 return this.event._path; |
| 1234 } |
| 1235 }; |
| 1236 } |
| 1237 var factory = function (event) { |
| 1238 if (!event.__eventApi) { |
| 1239 event.__eventApi = new DomApi.Event(event); |
| 1240 } |
| 1241 return event.__eventApi; |
| 1242 }; |
| 1243 return { factory: factory }; |
1048 }(); | 1244 }(); |
1049 (function () { | 1245 (function () { |
| 1246 'use strict'; |
| 1247 var DomApi = Polymer.DomApi.ctor; |
| 1248 Object.defineProperty(DomApi.prototype, 'classList', { |
| 1249 get: function () { |
| 1250 if (!this._classList) { |
| 1251 this._classList = new DomApi.ClassList(this); |
| 1252 } |
| 1253 return this._classList; |
| 1254 }, |
| 1255 configurable: true |
| 1256 }); |
| 1257 DomApi.ClassList = function (host) { |
| 1258 this.domApi = host; |
| 1259 this.node = host.node; |
| 1260 }; |
| 1261 DomApi.ClassList.prototype = { |
| 1262 add: function () { |
| 1263 this.node.classList.add.apply(this.node.classList, arguments); |
| 1264 this.domApi._distributeParent(); |
| 1265 }, |
| 1266 remove: function () { |
| 1267 this.node.classList.remove.apply(this.node.classList, arguments); |
| 1268 this.domApi._distributeParent(); |
| 1269 }, |
| 1270 toggle: function () { |
| 1271 this.node.classList.toggle.apply(this.node.classList, arguments); |
| 1272 this.domApi._distributeParent(); |
| 1273 }, |
| 1274 contains: function () { |
| 1275 return this.node.classList.contains.apply(this.node.classList, arguments); |
| 1276 } |
| 1277 }; |
| 1278 }()); |
| 1279 (function () { |
| 1280 'use strict'; |
| 1281 var DomApi = Polymer.DomApi.ctor; |
| 1282 var Settings = Polymer.Settings; |
| 1283 var hasDomApi = Polymer.DomApi.hasDomApi; |
| 1284 DomApi.EffectiveNodesObserver = function (domApi) { |
| 1285 this.domApi = domApi; |
| 1286 this.node = this.domApi.node; |
| 1287 this._listeners = []; |
| 1288 }; |
| 1289 DomApi.EffectiveNodesObserver.prototype = { |
| 1290 addListener: function (callback) { |
| 1291 if (!this._isSetup) { |
| 1292 this._setup(); |
| 1293 this._isSetup = true; |
| 1294 } |
| 1295 var listener = { |
| 1296 fn: callback, |
| 1297 _nodes: [] |
| 1298 }; |
| 1299 this._listeners.push(listener); |
| 1300 this._scheduleNotify(); |
| 1301 return listener; |
| 1302 }, |
| 1303 removeListener: function (handle) { |
| 1304 var i = this._listeners.indexOf(handle); |
| 1305 if (i >= 0) { |
| 1306 this._listeners.splice(i, 1); |
| 1307 handle._nodes = []; |
| 1308 } |
| 1309 if (!this._hasListeners()) { |
| 1310 this._cleanup(); |
| 1311 this._isSetup = false; |
| 1312 } |
| 1313 }, |
| 1314 _setup: function () { |
| 1315 this._observeContentElements(this.domApi.childNodes); |
| 1316 }, |
| 1317 _cleanup: function () { |
| 1318 this._unobserveContentElements(this.domApi.childNodes); |
| 1319 }, |
| 1320 _hasListeners: function () { |
| 1321 return Boolean(this._listeners.length); |
| 1322 }, |
| 1323 _scheduleNotify: function () { |
| 1324 if (this._debouncer) { |
| 1325 this._debouncer.stop(); |
| 1326 } |
| 1327 this._debouncer = Polymer.Debounce(this._debouncer, this._notify); |
| 1328 this._debouncer.context = this; |
| 1329 Polymer.dom.addDebouncer(this._debouncer); |
| 1330 }, |
| 1331 notify: function () { |
| 1332 if (this._hasListeners()) { |
| 1333 this._scheduleNotify(); |
| 1334 } |
| 1335 }, |
| 1336 _notify: function (mxns) { |
| 1337 this._beforeCallListeners(); |
| 1338 this._callListeners(); |
| 1339 }, |
| 1340 _beforeCallListeners: function () { |
| 1341 this._updateContentElements(); |
| 1342 }, |
| 1343 _updateContentElements: function () { |
| 1344 this._observeContentElements(this.domApi.childNodes); |
| 1345 }, |
| 1346 _observeContentElements: function (elements) { |
| 1347 for (var i = 0, n; i < elements.length && (n = elements[i]); i++) { |
| 1348 if (this._isContent(n)) { |
| 1349 n.__observeNodesMap = n.__observeNodesMap || new WeakMap(); |
| 1350 if (!n.__observeNodesMap.has(this)) { |
| 1351 n.__observeNodesMap.set(this, this._observeContent(n)); |
| 1352 } |
| 1353 } |
| 1354 } |
| 1355 }, |
| 1356 _observeContent: function (content) { |
| 1357 var self = this; |
| 1358 var h = Polymer.dom(content).observeNodes(function () { |
| 1359 self._scheduleNotify(); |
| 1360 }); |
| 1361 h._avoidChangeCalculation = true; |
| 1362 return h; |
| 1363 }, |
| 1364 _unobserveContentElements: function (elements) { |
| 1365 for (var i = 0, n, h; i < elements.length && (n = elements[i]); i++) { |
| 1366 if (this._isContent(n)) { |
| 1367 h = n.__observeNodesMap.get(this); |
| 1368 if (h) { |
| 1369 Polymer.dom(n).unobserveNodes(h); |
| 1370 n.__observeNodesMap.delete(this); |
| 1371 } |
| 1372 } |
| 1373 } |
| 1374 }, |
| 1375 _isContent: function (node) { |
| 1376 return node.localName === 'content'; |
| 1377 }, |
| 1378 _callListeners: function () { |
| 1379 var o$ = this._listeners; |
| 1380 var nodes = this._getEffectiveNodes(); |
| 1381 for (var i = 0, o; i < o$.length && (o = o$[i]); i++) { |
| 1382 var info = this._generateListenerInfo(o, nodes); |
| 1383 if (info || o._alwaysNotify) { |
| 1384 this._callListener(o, info); |
| 1385 } |
| 1386 } |
| 1387 }, |
| 1388 _getEffectiveNodes: function () { |
| 1389 return this.domApi.getEffectiveChildNodes(); |
| 1390 }, |
| 1391 _generateListenerInfo: function (listener, newNodes) { |
| 1392 if (listener._avoidChangeCalculation) { |
| 1393 return true; |
| 1394 } |
| 1395 var oldNodes = listener._nodes; |
| 1396 var info = { |
| 1397 target: this.node, |
| 1398 addedNodes: [], |
| 1399 removedNodes: [] |
| 1400 }; |
| 1401 var splices = Polymer.ArraySplice.calculateSplices(newNodes, oldNodes); |
| 1402 for (var i = 0, s; i < splices.length && (s = splices[i]); i++) { |
| 1403 for (var j = 0, n; j < s.removed.length && (n = s.removed[j]); j++) { |
| 1404 info.removedNodes.push(n); |
| 1405 } |
| 1406 } |
| 1407 for (var i = 0, s; i < splices.length && (s = splices[i]); i++) { |
| 1408 for (var j = s.index; j < s.index + s.addedCount; j++) { |
| 1409 info.addedNodes.push(newNodes[j]); |
| 1410 } |
| 1411 } |
| 1412 listener._nodes = newNodes; |
| 1413 if (info.addedNodes.length || info.removedNodes.length) { |
| 1414 return info; |
| 1415 } |
| 1416 }, |
| 1417 _callListener: function (listener, info) { |
| 1418 return listener.fn.call(this.node, info); |
| 1419 }, |
| 1420 enableShadowAttributeTracking: function () { |
| 1421 } |
| 1422 }; |
| 1423 if (Settings.useShadow) { |
| 1424 var baseSetup = DomApi.EffectiveNodesObserver.prototype._setup; |
| 1425 var baseCleanup = DomApi.EffectiveNodesObserver.prototype._cleanup; |
| 1426 var beforeCallListeners = DomApi.EffectiveNodesObserver.prototype._beforeCallLis
teners; |
| 1427 Polymer.Base.extend(DomApi.EffectiveNodesObserver.prototype, { |
| 1428 _setup: function () { |
| 1429 if (!this._observer) { |
| 1430 var self = this; |
| 1431 this._mutationHandler = function (mxns) { |
| 1432 if (mxns && mxns.length) { |
| 1433 self._scheduleNotify(); |
| 1434 } |
| 1435 }; |
| 1436 this._observer = new MutationObserver(this._mutationHandler); |
| 1437 this._boundFlush = function () { |
| 1438 self._flush(); |
| 1439 }; |
| 1440 Polymer.dom.addStaticFlush(this._boundFlush); |
| 1441 this._observer.observe(this.node, { childList: true }); |
| 1442 } |
| 1443 baseSetup.call(this); |
| 1444 }, |
| 1445 _cleanup: function () { |
| 1446 this._observer.disconnect(); |
| 1447 this._observer = null; |
| 1448 this._mutationHandler = null; |
| 1449 Polymer.dom.removeStaticFlush(this._boundFlush); |
| 1450 baseCleanup.call(this); |
| 1451 }, |
| 1452 _flush: function () { |
| 1453 if (this._observer) { |
| 1454 this._mutationHandler(this._observer.takeRecords()); |
| 1455 } |
| 1456 }, |
| 1457 enableShadowAttributeTracking: function () { |
| 1458 if (this._observer) { |
| 1459 this._makeContentListenersAlwaysNotify(); |
| 1460 this._observer.disconnect(); |
| 1461 this._observer.observe(this.node, { |
| 1462 childList: true, |
| 1463 attributes: true, |
| 1464 subtree: true |
| 1465 }); |
| 1466 var root = this.domApi.getOwnerRoot(); |
| 1467 var host = root && root.host; |
| 1468 if (host && Polymer.dom(host).observer) { |
| 1469 Polymer.dom(host).observer.enableShadowAttributeTracking(); |
| 1470 } |
| 1471 } |
| 1472 }, |
| 1473 _makeContentListenersAlwaysNotify: function () { |
| 1474 for (var i = 0, h; i < this._listeners.length; i++) { |
| 1475 h = this._listeners[i]; |
| 1476 h._alwaysNotify = h._isContentListener; |
| 1477 } |
| 1478 } |
| 1479 }); |
| 1480 } |
| 1481 }()); |
| 1482 (function () { |
| 1483 'use strict'; |
| 1484 var DomApi = Polymer.DomApi.ctor; |
| 1485 var Settings = Polymer.Settings; |
| 1486 DomApi.DistributedNodesObserver = function (domApi) { |
| 1487 DomApi.EffectiveNodesObserver.call(this, domApi); |
| 1488 }; |
| 1489 DomApi.DistributedNodesObserver.prototype = Object.create(DomApi.EffectiveNodesO
bserver.prototype); |
| 1490 Polymer.Base.extend(DomApi.DistributedNodesObserver.prototype, { |
| 1491 _setup: function () { |
| 1492 }, |
| 1493 _cleanup: function () { |
| 1494 }, |
| 1495 _beforeCallListeners: function () { |
| 1496 }, |
| 1497 _getEffectiveNodes: function () { |
| 1498 return this.domApi.getDistributedNodes(); |
| 1499 } |
| 1500 }); |
| 1501 if (Settings.useShadow) { |
| 1502 Polymer.Base.extend(DomApi.DistributedNodesObserver.prototype, { |
| 1503 _setup: function () { |
| 1504 if (!this._observer) { |
| 1505 var root = this.domApi.getOwnerRoot(); |
| 1506 var host = root && root.host; |
| 1507 if (host) { |
| 1508 var self = this; |
| 1509 this._observer = Polymer.dom(host).observeNodes(function () { |
| 1510 self._scheduleNotify(); |
| 1511 }); |
| 1512 this._observer._isContentListener = true; |
| 1513 if (this._hasAttrSelect()) { |
| 1514 Polymer.dom(host).observer.enableShadowAttributeTracking(); |
| 1515 } |
| 1516 } |
| 1517 } |
| 1518 }, |
| 1519 _hasAttrSelect: function () { |
| 1520 var select = this.node.getAttribute('select'); |
| 1521 return select && select.match(/[[.]+/); |
| 1522 }, |
| 1523 _cleanup: function () { |
| 1524 var root = this.domApi.getOwnerRoot(); |
| 1525 var host = root && root.host; |
| 1526 if (host) { |
| 1527 Polymer.dom(host).unobserveNodes(this._observer); |
| 1528 } |
| 1529 this._observer = null; |
| 1530 } |
| 1531 }); |
| 1532 } |
| 1533 }()); |
| 1534 (function () { |
| 1535 var hasDomApi = Polymer.DomApi.hasDomApi; |
1050 Polymer.Base._addFeature({ | 1536 Polymer.Base._addFeature({ |
1051 _prepShady: function () { | 1537 _prepShady: function () { |
1052 this._useContent = this._useContent || Boolean(this._template); | 1538 this._useContent = this._useContent || Boolean(this._template); |
1053 if (this._useContent) { | |
1054 this._template._hasInsertionPoint = this._template.content.querySelector('conten
t'); | |
1055 } | |
1056 }, | 1539 }, |
1057 _poolContent: function () { | 1540 _poolContent: function () { |
1058 if (this._useContent) { | 1541 if (this._useContent) { |
1059 saveLightChildrenIfNeeded(this); | 1542 saveLightChildrenIfNeeded(this); |
1060 } | 1543 } |
1061 }, | 1544 }, |
1062 _setupRoot: function () { | 1545 _setupRoot: function () { |
1063 if (this._useContent) { | 1546 if (this._useContent) { |
1064 this._createLocalRoot(); | 1547 this._createLocalRoot(); |
1065 if (!this.dataHost) { | 1548 if (!this.dataHost) { |
1066 upgradeLightChildren(this._lightChildren); | 1549 upgradeLightChildren(this._lightChildren); |
1067 } | 1550 } |
1068 } | 1551 } |
1069 }, | 1552 }, |
1070 _createLocalRoot: function () { | 1553 _createLocalRoot: function () { |
1071 this.shadyRoot = this.root; | 1554 this.shadyRoot = this.root; |
1072 this.shadyRoot._distributionClean = false; | 1555 this.shadyRoot._distributionClean = false; |
| 1556 this.shadyRoot._hasDistributed = false; |
1073 this.shadyRoot._isShadyRoot = true; | 1557 this.shadyRoot._isShadyRoot = true; |
1074 this.shadyRoot._dirtyRoots = []; | 1558 this.shadyRoot._dirtyRoots = []; |
1075 this.shadyRoot._insertionPoints = this._template._hasInsertionPoint ? this.shady
Root.querySelectorAll('content') : []; | 1559 var i$ = this.shadyRoot._insertionPoints = !this._notes || this._notes._hasConte
nt ? this.shadyRoot.querySelectorAll('content') : []; |
1076 saveLightChildrenIfNeeded(this.shadyRoot); | 1560 saveLightChildrenIfNeeded(this.shadyRoot); |
| 1561 for (var i = 0, c; i < i$.length; i++) { |
| 1562 c = i$[i]; |
| 1563 saveLightChildrenIfNeeded(c); |
| 1564 saveLightChildrenIfNeeded(c.parentNode); |
| 1565 } |
1077 this.shadyRoot.host = this; | 1566 this.shadyRoot.host = this; |
1078 }, | 1567 }, |
1079 get domHost() { | 1568 get domHost() { |
1080 var root = Polymer.dom(this).getOwnerRoot(); | 1569 var root = Polymer.dom(this).getOwnerRoot(); |
1081 return root && root.host; | 1570 return root && root.host; |
1082 }, | 1571 }, |
1083 distributeContent: function (updateInsertionPoints) { | 1572 distributeContent: function (updateInsertionPoints) { |
1084 if (this.shadyRoot) { | 1573 if (this.shadyRoot) { |
1085 var dom = Polymer.dom(this); | 1574 var dom = Polymer.dom(this); |
1086 if (updateInsertionPoints) { | 1575 if (updateInsertionPoints) { |
(...skipping 18 matching lines...) Expand all Loading... |
1105 }, | 1594 }, |
1106 _distributeDirtyRoots: function () { | 1595 _distributeDirtyRoots: function () { |
1107 var c$ = this.shadyRoot._dirtyRoots; | 1596 var c$ = this.shadyRoot._dirtyRoots; |
1108 for (var i = 0, l = c$.length, c; i < l && (c = c$[i]); i++) { | 1597 for (var i = 0, l = c$.length, c; i < l && (c = c$[i]); i++) { |
1109 c._distributeContent(); | 1598 c._distributeContent(); |
1110 } | 1599 } |
1111 this.shadyRoot._dirtyRoots = []; | 1600 this.shadyRoot._dirtyRoots = []; |
1112 }, | 1601 }, |
1113 _finishDistribute: function () { | 1602 _finishDistribute: function () { |
1114 if (this._useContent) { | 1603 if (this._useContent) { |
| 1604 this.shadyRoot._distributionClean = true; |
1115 if (hasInsertionPoint(this.shadyRoot)) { | 1605 if (hasInsertionPoint(this.shadyRoot)) { |
1116 this._composeTree(); | 1606 this._composeTree(); |
| 1607 notifyContentObservers(this.shadyRoot); |
1117 } else { | 1608 } else { |
1118 if (!this.shadyRoot._hasDistributed) { | 1609 if (!this.shadyRoot._hasDistributed) { |
1119 this.textContent = ''; | 1610 this.textContent = ''; |
1120 this._composedChildren = null; | 1611 this._composedChildren = null; |
1121 this.appendChild(this.shadyRoot); | 1612 this.appendChild(this.shadyRoot); |
1122 } else { | 1613 } else { |
1123 var children = this._composeNode(this); | 1614 var children = this._composeNode(this); |
1124 this._updateChildNodes(this, children); | 1615 this._updateChildNodes(this, children); |
1125 } | 1616 } |
1126 } | 1617 } |
| 1618 if (!this.shadyRoot._hasDistributed) { |
| 1619 notifyInitialDistribution(this); |
| 1620 } |
1127 this.shadyRoot._hasDistributed = true; | 1621 this.shadyRoot._hasDistributed = true; |
1128 this.shadyRoot._distributionClean = true; | |
1129 } | 1622 } |
1130 }, | 1623 }, |
1131 elementMatches: function (selector, node) { | 1624 elementMatches: function (selector, node) { |
1132 node = node || this; | 1625 node = node || this; |
1133 return matchesSelector.call(node, selector); | 1626 return matchesSelector.call(node, selector); |
1134 }, | 1627 }, |
1135 _resetDistribution: function () { | 1628 _resetDistribution: function () { |
1136 var children = getLightChildren(this); | 1629 var children = getLightChildren(this); |
1137 for (var i = 0; i < children.length; i++) { | 1630 for (var i = 0; i < children.length; i++) { |
1138 var child = children[i]; | 1631 var child = children[i]; |
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1216 children.push(child); | 1709 children.push(child); |
1217 } | 1710 } |
1218 } | 1711 } |
1219 return children; | 1712 return children; |
1220 }, | 1713 }, |
1221 _updateChildNodes: function (container, children) { | 1714 _updateChildNodes: function (container, children) { |
1222 var composed = getComposedChildren(container); | 1715 var composed = getComposedChildren(container); |
1223 var splices = Polymer.ArraySplice.calculateSplices(children, composed); | 1716 var splices = Polymer.ArraySplice.calculateSplices(children, composed); |
1224 for (var i = 0, d = 0, s; i < splices.length && (s = splices[i]); i++) { | 1717 for (var i = 0, d = 0, s; i < splices.length && (s = splices[i]); i++) { |
1225 for (var j = 0, n; j < s.removed.length && (n = s.removed[j]); j++) { | 1718 for (var j = 0, n; j < s.removed.length && (n = s.removed[j]); j++) { |
| 1719 if (getComposedParent(n) === container) { |
1226 remove(n); | 1720 remove(n); |
| 1721 } |
1227 composed.splice(s.index + d, 1); | 1722 composed.splice(s.index + d, 1); |
1228 } | 1723 } |
1229 d -= s.addedCount; | 1724 d -= s.addedCount; |
1230 } | 1725 } |
1231 for (var i = 0, s, next; i < splices.length && (s = splices[i]); i++) { | 1726 for (var i = 0, s, next; i < splices.length && (s = splices[i]); i++) { |
1232 next = composed[s.index]; | 1727 next = composed[s.index]; |
1233 for (var j = s.index, n; j < s.index + s.addedCount; j++) { | 1728 for (var j = s.index, n; j < s.index + s.addedCount; j++) { |
1234 n = children[j]; | 1729 n = children[j]; |
1235 insertBefore(container, n, next); | 1730 insertBefore(container, n, next); |
1236 composed.splice(j, 0, n); | 1731 composed.splice(j, 0, n); |
1237 } | 1732 } |
1238 } | 1733 } |
| 1734 ensureComposedParent(container, children); |
1239 }, | 1735 }, |
1240 _matchesContentSelect: function (node, contentElement) { | 1736 _matchesContentSelect: function (node, contentElement) { |
1241 var select = contentElement.getAttribute('select'); | 1737 var select = contentElement.getAttribute('select'); |
1242 if (!select) { | 1738 if (!select) { |
1243 return true; | 1739 return true; |
1244 } | 1740 } |
1245 select = select.trim(); | 1741 select = select.trim(); |
1246 if (!select) { | 1742 if (!select) { |
1247 return true; | 1743 return true; |
1248 } | 1744 } |
1249 if (!(node instanceof Element)) { | 1745 if (!(node instanceof Element)) { |
1250 return false; | 1746 return false; |
1251 } | 1747 } |
1252 var validSelectors = /^(:not\()?[*.#[a-zA-Z_|]/; | 1748 var validSelectors = /^(:not\()?[*.#[a-zA-Z_|]/; |
1253 if (!validSelectors.test(select)) { | 1749 if (!validSelectors.test(select)) { |
1254 return false; | 1750 return false; |
1255 } | 1751 } |
1256 return this.elementMatches(select, node); | 1752 return this.elementMatches(select, node); |
1257 }, | 1753 }, |
1258 _elementAdd: function () { | 1754 _elementAdd: function () { |
1259 }, | 1755 }, |
1260 _elementRemove: function () { | 1756 _elementRemove: function () { |
1261 } | 1757 } |
1262 }); | 1758 }); |
1263 var saveLightChildrenIfNeeded = Polymer.DomApi.saveLightChildrenIfNeeded; | 1759 var saveLightChildrenIfNeeded = Polymer.DomApi.saveLightChildrenIfNeeded; |
1264 var getLightChildren = Polymer.DomApi.getLightChildren; | 1760 var getLightChildren = Polymer.DomApi.getLightChildren; |
1265 var matchesSelector = Polymer.DomApi.matchesSelector; | 1761 var matchesSelector = Polymer.DomApi.matchesSelector; |
1266 var hasInsertionPoint = Polymer.DomApi.hasInsertionPoint; | 1762 var hasInsertionPoint = Polymer.DomApi.hasInsertionPoint; |
1267 var getComposedChildren = Polymer.DomApi.getComposedChildren; | 1763 var getComposedChildren = Polymer.DomApi.getComposedChildren; |
| 1764 var getComposedParent = Polymer.DomApi.getComposedParent; |
1268 var removeFromComposedParent = Polymer.DomApi.removeFromComposedParent; | 1765 var removeFromComposedParent = Polymer.DomApi.removeFromComposedParent; |
1269 function distributeNodeInto(child, insertionPoint) { | 1766 function distributeNodeInto(child, insertionPoint) { |
1270 insertionPoint._distributedNodes.push(child); | 1767 insertionPoint._distributedNodes.push(child); |
1271 var points = child._destinationInsertionPoints; | 1768 var points = child._destinationInsertionPoints; |
1272 if (!points) { | 1769 if (!points) { |
1273 child._destinationInsertionPoints = [insertionPoint]; | 1770 child._destinationInsertionPoints = [insertionPoint]; |
1274 } else { | 1771 } else { |
1275 points.push(insertionPoint); | 1772 points.push(insertionPoint); |
1276 } | 1773 } |
1277 } | 1774 } |
(...skipping 23 matching lines...) Expand all Loading... |
1301 return node.localName == 'content'; | 1798 return node.localName == 'content'; |
1302 } | 1799 } |
1303 var nativeInsertBefore = Element.prototype.insertBefore; | 1800 var nativeInsertBefore = Element.prototype.insertBefore; |
1304 var nativeRemoveChild = Element.prototype.removeChild; | 1801 var nativeRemoveChild = Element.prototype.removeChild; |
1305 function insertBefore(parentNode, newChild, refChild) { | 1802 function insertBefore(parentNode, newChild, refChild) { |
1306 var newChildParent = getComposedParent(newChild); | 1803 var newChildParent = getComposedParent(newChild); |
1307 if (newChildParent !== parentNode) { | 1804 if (newChildParent !== parentNode) { |
1308 removeFromComposedParent(newChildParent, newChild); | 1805 removeFromComposedParent(newChildParent, newChild); |
1309 } | 1806 } |
1310 remove(newChild); | 1807 remove(newChild); |
1311 saveLightChildrenIfNeeded(parentNode); | |
1312 nativeInsertBefore.call(parentNode, newChild, refChild || null); | 1808 nativeInsertBefore.call(parentNode, newChild, refChild || null); |
1313 newChild._composedParent = parentNode; | 1809 newChild._composedParent = parentNode; |
1314 } | 1810 } |
1315 function remove(node) { | 1811 function remove(node) { |
1316 var parentNode = getComposedParent(node); | 1812 var parentNode = getComposedParent(node); |
1317 if (parentNode) { | 1813 if (parentNode) { |
1318 saveLightChildrenIfNeeded(parentNode); | |
1319 node._composedParent = null; | 1814 node._composedParent = null; |
1320 nativeRemoveChild.call(parentNode, node); | 1815 nativeRemoveChild.call(parentNode, node); |
1321 } | 1816 } |
1322 } | 1817 } |
1323 function getComposedParent(node) { | 1818 function ensureComposedParent(parent, children) { |
1324 return node.__patched ? node._composedParent : node.parentNode; | 1819 for (var i = 0, n; i < children.length; i++) { |
| 1820 children[i]._composedParent = parent; |
| 1821 } |
1325 } | 1822 } |
1326 function getTopDistributingHost(host) { | 1823 function getTopDistributingHost(host) { |
1327 while (host && hostNeedsRedistribution(host)) { | 1824 while (host && hostNeedsRedistribution(host)) { |
1328 host = host.domHost; | 1825 host = host.domHost; |
1329 } | 1826 } |
1330 return host; | 1827 return host; |
1331 } | 1828 } |
1332 function hostNeedsRedistribution(host) { | 1829 function hostNeedsRedistribution(host) { |
1333 var c$ = Polymer.dom(host).children; | 1830 var c$ = Polymer.dom(host).children; |
1334 for (var i = 0, c; i < c$.length; i++) { | 1831 for (var i = 0, c; i < c$.length; i++) { |
1335 c = c$[i]; | 1832 c = c$[i]; |
1336 if (c.localName === 'content') { | 1833 if (c.localName === 'content') { |
1337 return host.domHost; | 1834 return host.domHost; |
1338 } | 1835 } |
1339 } | 1836 } |
1340 } | 1837 } |
| 1838 function notifyContentObservers(root) { |
| 1839 for (var i = 0, c; i < root._insertionPoints.length; i++) { |
| 1840 c = root._insertionPoints[i]; |
| 1841 if (hasDomApi(c)) { |
| 1842 Polymer.dom(c).notifyObserver(); |
| 1843 } |
| 1844 } |
| 1845 } |
| 1846 function notifyInitialDistribution(host) { |
| 1847 if (hasDomApi(host)) { |
| 1848 Polymer.dom(host).notifyObserver(); |
| 1849 } |
| 1850 } |
1341 var needsUpgrade = window.CustomElements && !CustomElements.useNative; | 1851 var needsUpgrade = window.CustomElements && !CustomElements.useNative; |
1342 function upgradeLightChildren(children) { | 1852 function upgradeLightChildren(children) { |
1343 if (needsUpgrade && children) { | 1853 if (needsUpgrade && children) { |
1344 for (var i = 0; i < children.length; i++) { | 1854 for (var i = 0; i < children.length; i++) { |
1345 CustomElements.upgrade(children[i]); | 1855 CustomElements.upgrade(children[i]); |
1346 } | 1856 } |
1347 } | 1857 } |
1348 } | 1858 } |
1349 }()); | 1859 }()); |
1350 if (Polymer.Settings.useShadow) { | 1860 if (Polymer.Settings.useShadow) { |
(...skipping 12 matching lines...) Expand all Loading... |
1363 this.createShadowRoot(); | 1873 this.createShadowRoot(); |
1364 this.shadowRoot.appendChild(this.root); | 1874 this.shadowRoot.appendChild(this.root); |
1365 this.root = this.shadowRoot; | 1875 this.root = this.shadowRoot; |
1366 } | 1876 } |
1367 }); | 1877 }); |
1368 } | 1878 } |
1369 Polymer.DomModule = document.createElement('dom-module'); | 1879 Polymer.DomModule = document.createElement('dom-module'); |
1370 Polymer.Base._addFeature({ | 1880 Polymer.Base._addFeature({ |
1371 _registerFeatures: function () { | 1881 _registerFeatures: function () { |
1372 this._prepIs(); | 1882 this._prepIs(); |
1373 this._prepAttributes(); | |
1374 this._prepBehaviors(); | 1883 this._prepBehaviors(); |
1375 this._prepExtends(); | |
1376 this._prepConstructor(); | 1884 this._prepConstructor(); |
1377 this._prepTemplate(); | 1885 this._prepTemplate(); |
1378 this._prepShady(); | 1886 this._prepShady(); |
| 1887 this._prepPropertyInfo(); |
1379 }, | 1888 }, |
1380 _prepBehavior: function (b) { | 1889 _prepBehavior: function (b) { |
1381 this._addHostAttributes(b.hostAttributes); | 1890 this._addHostAttributes(b.hostAttributes); |
1382 }, | 1891 }, |
1383 _initFeatures: function () { | 1892 _initFeatures: function () { |
| 1893 this._registerHost(); |
| 1894 if (this._template) { |
1384 this._poolContent(); | 1895 this._poolContent(); |
1385 this._pushHost(); | 1896 this._beginHosting(); |
1386 this._stampTemplate(); | 1897 this._stampTemplate(); |
1387 this._popHost(); | 1898 this._endHosting(); |
| 1899 } |
1388 this._marshalHostAttributes(); | 1900 this._marshalHostAttributes(); |
1389 this._setupDebouncers(); | 1901 this._setupDebouncers(); |
1390 this._marshalBehaviors(); | 1902 this._marshalBehaviors(); |
1391 this._tryReady(); | 1903 this._tryReady(); |
1392 }, | 1904 }, |
1393 _marshalBehavior: function (b) { | 1905 _marshalBehavior: function (b) { |
1394 } | 1906 } |
1395 });</script> | 1907 });</script> |
1396 | 1908 |
OLD | NEW |