1/**
2 * @license
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.github.io/LICENSE.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/CONTRIBUTORS.txt
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/PATENTS.txt
9 */
10// @version 0.5.5
11if (typeof WeakMap === "undefined") {
12  (function() {
13    var defineProperty = Object.defineProperty;
14    var counter = Date.now() % 1e9;
15    var WeakMap = function() {
16      this.name = "__st" + (Math.random() * 1e9 >>> 0) + (counter++ + "__");
17    };
18    WeakMap.prototype = {
19      set: function(key, value) {
20        var entry = key[this.name];
21        if (entry && entry[0] === key) entry[1] = value; else defineProperty(key, this.name, {
22          value: [ key, value ],
23          writable: true
24        });
25        return this;
26      },
27      get: function(key) {
28        var entry;
29        return (entry = key[this.name]) && entry[0] === key ? entry[1] : undefined;
30      },
31      "delete": function(key) {
32        var entry = key[this.name];
33        if (!entry || entry[0] !== key) return false;
34        entry[0] = entry[1] = undefined;
35        return true;
36      },
37      has: function(key) {
38        var entry = key[this.name];
39        if (!entry) return false;
40        return entry[0] === key;
41      }
42    };
43    window.WeakMap = WeakMap;
44  })();
45}
46
47window.ShadowDOMPolyfill = {};
48
49(function(scope) {
50  "use strict";
51  var constructorTable = new WeakMap();
52  var nativePrototypeTable = new WeakMap();
53  var wrappers = Object.create(null);
54  function detectEval() {
55    if (typeof chrome !== "undefined" && chrome.app && chrome.app.runtime) {
56      return false;
57    }
58    if (navigator.getDeviceStorage) {
59      return false;
60    }
61    try {
62      var f = new Function("return true;");
63      return f();
64    } catch (ex) {
65      return false;
66    }
67  }
68  var hasEval = detectEval();
69  function assert(b) {
70    if (!b) throw new Error("Assertion failed");
71  }
72  var defineProperty = Object.defineProperty;
73  var getOwnPropertyNames = Object.getOwnPropertyNames;
74  var getOwnPropertyDescriptor = Object.getOwnPropertyDescriptor;
75  function mixin(to, from) {
76    var names = getOwnPropertyNames(from);
77    for (var i = 0; i < names.length; i++) {
78      var name = names[i];
79      defineProperty(to, name, getOwnPropertyDescriptor(from, name));
80    }
81    return to;
82  }
83  function mixinStatics(to, from) {
84    var names = getOwnPropertyNames(from);
85    for (var i = 0; i < names.length; i++) {
86      var name = names[i];
87      switch (name) {
88       case "arguments":
89       case "caller":
90       case "length":
91       case "name":
92       case "prototype":
93       case "toString":
94        continue;
95      }
96      defineProperty(to, name, getOwnPropertyDescriptor(from, name));
97    }
98    return to;
99  }
100  function oneOf(object, propertyNames) {
101    for (var i = 0; i < propertyNames.length; i++) {
102      if (propertyNames[i] in object) return propertyNames[i];
103    }
104  }
105  var nonEnumerableDataDescriptor = {
106    value: undefined,
107    configurable: true,
108    enumerable: false,
109    writable: true
110  };
111  function defineNonEnumerableDataProperty(object, name, value) {
112    nonEnumerableDataDescriptor.value = value;
113    defineProperty(object, name, nonEnumerableDataDescriptor);
114  }
115  getOwnPropertyNames(window);
116  function getWrapperConstructor(node) {
117    var nativePrototype = node.__proto__ || Object.getPrototypeOf(node);
118    if (isFirefox) {
119      try {
120        getOwnPropertyNames(nativePrototype);
121      } catch (error) {
122        nativePrototype = nativePrototype.__proto__;
123      }
124    }
125    var wrapperConstructor = constructorTable.get(nativePrototype);
126    if (wrapperConstructor) return wrapperConstructor;
127    var parentWrapperConstructor = getWrapperConstructor(nativePrototype);
128    var GeneratedWrapper = createWrapperConstructor(parentWrapperConstructor);
129    registerInternal(nativePrototype, GeneratedWrapper, node);
130    return GeneratedWrapper;
131  }
132  function addForwardingProperties(nativePrototype, wrapperPrototype) {
133    installProperty(nativePrototype, wrapperPrototype, true);
134  }
135  function registerInstanceProperties(wrapperPrototype, instanceObject) {
136    installProperty(instanceObject, wrapperPrototype, false);
137  }
138  var isFirefox = /Firefox/.test(navigator.userAgent);
139  var dummyDescriptor = {
140    get: function() {},
141    set: function(v) {},
142    configurable: true,
143    enumerable: true
144  };
145  function isEventHandlerName(name) {
146    return /^on[a-z]+$/.test(name);
147  }
148  function isIdentifierName(name) {
149    return /^\w[a-zA-Z_0-9]*$/.test(name);
150  }
151  function getGetter(name) {
152    return hasEval && isIdentifierName(name) ? new Function("return this.__impl4cf1e782hg__." + name) : function() {
153      return this.__impl4cf1e782hg__[name];
154    };
155  }
156  function getSetter(name) {
157    return hasEval && isIdentifierName(name) ? new Function("v", "this.__impl4cf1e782hg__." + name + " = v") : function(v) {
158      this.__impl4cf1e782hg__[name] = v;
159    };
160  }
161  function getMethod(name) {
162    return hasEval && isIdentifierName(name) ? new Function("return this.__impl4cf1e782hg__." + name + ".apply(this.__impl4cf1e782hg__, arguments)") : function() {
163      return this.__impl4cf1e782hg__[name].apply(this.__impl4cf1e782hg__, arguments);
164    };
165  }
166  function getDescriptor(source, name) {
167    try {
168      return Object.getOwnPropertyDescriptor(source, name);
169    } catch (ex) {
170      return dummyDescriptor;
171    }
172  }
173  var isBrokenSafari = function() {
174    var descr = Object.getOwnPropertyDescriptor(Node.prototype, "nodeType");
175    return descr && !descr.get && !descr.set;
176  }();
177  function installProperty(source, target, allowMethod, opt_blacklist) {
178    var names = getOwnPropertyNames(source);
179    for (var i = 0; i < names.length; i++) {
180      var name = names[i];
181      if (name === "polymerBlackList_") continue;
182      if (name in target) continue;
183      if (source.polymerBlackList_ && source.polymerBlackList_[name]) continue;
184      if (isFirefox) {
185        source.__lookupGetter__(name);
186      }
187      var descriptor = getDescriptor(source, name);
188      var getter, setter;
189      if (allowMethod && typeof descriptor.value === "function") {
190        target[name] = getMethod(name);
191        continue;
192      }
193      var isEvent = isEventHandlerName(name);
194      if (isEvent) getter = scope.getEventHandlerGetter(name); else getter = getGetter(name);
195      if (descriptor.writable || descriptor.set || isBrokenSafari) {
196        if (isEvent) setter = scope.getEventHandlerSetter(name); else setter = getSetter(name);
197      }
198      var configurable = isBrokenSafari || descriptor.configurable;
199      defineProperty(target, name, {
200        get: getter,
201        set: setter,
202        configurable: configurable,
203        enumerable: descriptor.enumerable
204      });
205    }
206  }
207  function register(nativeConstructor, wrapperConstructor, opt_instance) {
208    var nativePrototype = nativeConstructor.prototype;
209    registerInternal(nativePrototype, wrapperConstructor, opt_instance);
210    mixinStatics(wrapperConstructor, nativeConstructor);
211  }
212  function registerInternal(nativePrototype, wrapperConstructor, opt_instance) {
213    var wrapperPrototype = wrapperConstructor.prototype;
214    assert(constructorTable.get(nativePrototype) === undefined);
215    constructorTable.set(nativePrototype, wrapperConstructor);
216    nativePrototypeTable.set(wrapperPrototype, nativePrototype);
217    addForwardingProperties(nativePrototype, wrapperPrototype);
218    if (opt_instance) registerInstanceProperties(wrapperPrototype, opt_instance);
219    defineNonEnumerableDataProperty(wrapperPrototype, "constructor", wrapperConstructor);
220    wrapperConstructor.prototype = wrapperPrototype;
221  }
222  function isWrapperFor(wrapperConstructor, nativeConstructor) {
223    return constructorTable.get(nativeConstructor.prototype) === wrapperConstructor;
224  }
225  function registerObject(object) {
226    var nativePrototype = Object.getPrototypeOf(object);
227    var superWrapperConstructor = getWrapperConstructor(nativePrototype);
228    var GeneratedWrapper = createWrapperConstructor(superWrapperConstructor);
229    registerInternal(nativePrototype, GeneratedWrapper, object);
230    return GeneratedWrapper;
231  }
232  function createWrapperConstructor(superWrapperConstructor) {
233    function GeneratedWrapper(node) {
234      superWrapperConstructor.call(this, node);
235    }
236    var p = Object.create(superWrapperConstructor.prototype);
237    p.constructor = GeneratedWrapper;
238    GeneratedWrapper.prototype = p;
239    return GeneratedWrapper;
240  }
241  function isWrapper(object) {
242    return object && object.__impl4cf1e782hg__;
243  }
244  function isNative(object) {
245    return !isWrapper(object);
246  }
247  function wrap(impl) {
248    if (impl === null) return null;
249    assert(isNative(impl));
250    return impl.__wrapper8e3dd93a60__ || (impl.__wrapper8e3dd93a60__ = new (getWrapperConstructor(impl))(impl));
251  }
252  function unwrap(wrapper) {
253    if (wrapper === null) return null;
254    assert(isWrapper(wrapper));
255    return wrapper.__impl4cf1e782hg__;
256  }
257  function unsafeUnwrap(wrapper) {
258    return wrapper.__impl4cf1e782hg__;
259  }
260  function setWrapper(impl, wrapper) {
261    wrapper.__impl4cf1e782hg__ = impl;
262    impl.__wrapper8e3dd93a60__ = wrapper;
263  }
264  function unwrapIfNeeded(object) {
265    return object && isWrapper(object) ? unwrap(object) : object;
266  }
267  function wrapIfNeeded(object) {
268    return object && !isWrapper(object) ? wrap(object) : object;
269  }
270  function rewrap(node, wrapper) {
271    if (wrapper === null) return;
272    assert(isNative(node));
273    assert(wrapper === undefined || isWrapper(wrapper));
274    node.__wrapper8e3dd93a60__ = wrapper;
275  }
276  var getterDescriptor = {
277    get: undefined,
278    configurable: true,
279    enumerable: true
280  };
281  function defineGetter(constructor, name, getter) {
282    getterDescriptor.get = getter;
283    defineProperty(constructor.prototype, name, getterDescriptor);
284  }
285  function defineWrapGetter(constructor, name) {
286    defineGetter(constructor, name, function() {
287      return wrap(this.__impl4cf1e782hg__[name]);
288    });
289  }
290  function forwardMethodsToWrapper(constructors, names) {
291    constructors.forEach(function(constructor) {
292      names.forEach(function(name) {
293        constructor.prototype[name] = function() {
294          var w = wrapIfNeeded(this);
295          return w[name].apply(w, arguments);
296        };
297      });
298    });
299  }
300  scope.assert = assert;
301  scope.constructorTable = constructorTable;
302  scope.defineGetter = defineGetter;
303  scope.defineWrapGetter = defineWrapGetter;
304  scope.forwardMethodsToWrapper = forwardMethodsToWrapper;
305  scope.isWrapper = isWrapper;
306  scope.isWrapperFor = isWrapperFor;
307  scope.mixin = mixin;
308  scope.nativePrototypeTable = nativePrototypeTable;
309  scope.oneOf = oneOf;
310  scope.registerObject = registerObject;
311  scope.registerWrapper = register;
312  scope.rewrap = rewrap;
313  scope.setWrapper = setWrapper;
314  scope.unsafeUnwrap = unsafeUnwrap;
315  scope.unwrap = unwrap;
316  scope.unwrapIfNeeded = unwrapIfNeeded;
317  scope.wrap = wrap;
318  scope.wrapIfNeeded = wrapIfNeeded;
319  scope.wrappers = wrappers;
320})(window.ShadowDOMPolyfill);
321
322(function(scope) {
323  "use strict";
324  function newSplice(index, removed, addedCount) {
325    return {
326      index: index,
327      removed: removed,
328      addedCount: addedCount
329    };
330  }
331  var EDIT_LEAVE = 0;
332  var EDIT_UPDATE = 1;
333  var EDIT_ADD = 2;
334  var EDIT_DELETE = 3;
335  function ArraySplice() {}
336  ArraySplice.prototype = {
337    calcEditDistances: function(current, currentStart, currentEnd, old, oldStart, oldEnd) {
338      var rowCount = oldEnd - oldStart + 1;
339      var columnCount = currentEnd - currentStart + 1;
340      var distances = new Array(rowCount);
341      for (var i = 0; i < rowCount; i++) {
342        distances[i] = new Array(columnCount);
343        distances[i][0] = i;
344      }
345      for (var j = 0; j < columnCount; j++) distances[0][j] = j;
346      for (var i = 1; i < rowCount; i++) {
347        for (var j = 1; j < columnCount; j++) {
348          if (this.equals(current[currentStart + j - 1], old[oldStart + i - 1])) distances[i][j] = distances[i - 1][j - 1]; else {
349            var north = distances[i - 1][j] + 1;
350            var west = distances[i][j - 1] + 1;
351            distances[i][j] = north < west ? north : west;
352          }
353        }
354      }
355      return distances;
356    },
357    spliceOperationsFromEditDistances: function(distances) {
358      var i = distances.length - 1;
359      var j = distances[0].length - 1;
360      var current = distances[i][j];
361      var edits = [];
362      while (i > 0 || j > 0) {
363        if (i == 0) {
364          edits.push(EDIT_ADD);
365          j--;
366          continue;
367        }
368        if (j == 0) {
369          edits.push(EDIT_DELETE);
370          i--;
371          continue;
372        }
373        var northWest = distances[i - 1][j - 1];
374        var west = distances[i - 1][j];
375        var north = distances[i][j - 1];
376        var min;
377        if (west < north) min = west < northWest ? west : northWest; else min = north < northWest ? north : northWest;
378        if (min == northWest) {
379          if (northWest == current) {
380            edits.push(EDIT_LEAVE);
381          } else {
382            edits.push(EDIT_UPDATE);
383            current = northWest;
384          }
385          i--;
386          j--;
387        } else if (min == west) {
388          edits.push(EDIT_DELETE);
389          i--;
390          current = west;
391        } else {
392          edits.push(EDIT_ADD);
393          j--;
394          current = north;
395        }
396      }
397      edits.reverse();
398      return edits;
399    },
400    calcSplices: function(current, currentStart, currentEnd, old, oldStart, oldEnd) {
401      var prefixCount = 0;
402      var suffixCount = 0;
403      var minLength = Math.min(currentEnd - currentStart, oldEnd - oldStart);
404      if (currentStart == 0 && oldStart == 0) prefixCount = this.sharedPrefix(current, old, minLength);
405      if (currentEnd == current.length && oldEnd == old.length) suffixCount = this.sharedSuffix(current, old, minLength - prefixCount);
406      currentStart += prefixCount;
407      oldStart += prefixCount;
408      currentEnd -= suffixCount;
409      oldEnd -= suffixCount;
410      if (currentEnd - currentStart == 0 && oldEnd - oldStart == 0) return [];
411      if (currentStart == currentEnd) {
412        var splice = newSplice(currentStart, [], 0);
413        while (oldStart < oldEnd) splice.removed.push(old[oldStart++]);
414        return [ splice ];
415      } else if (oldStart == oldEnd) return [ newSplice(currentStart, [], currentEnd - currentStart) ];
416      var ops = this.spliceOperationsFromEditDistances(this.calcEditDistances(current, currentStart, currentEnd, old, oldStart, oldEnd));
417      var splice = undefined;
418      var splices = [];
419      var index = currentStart;
420      var oldIndex = oldStart;
421      for (var i = 0; i < ops.length; i++) {
422        switch (ops[i]) {
423         case EDIT_LEAVE:
424          if (splice) {
425            splices.push(splice);
426            splice = undefined;
427          }
428          index++;
429          oldIndex++;
430          break;
431
432         case EDIT_UPDATE:
433          if (!splice) splice = newSplice(index, [], 0);
434          splice.addedCount++;
435          index++;
436          splice.removed.push(old[oldIndex]);
437          oldIndex++;
438          break;
439
440         case EDIT_ADD:
441          if (!splice) splice = newSplice(index, [], 0);
442          splice.addedCount++;
443          index++;
444          break;
445
446         case EDIT_DELETE:
447          if (!splice) splice = newSplice(index, [], 0);
448          splice.removed.push(old[oldIndex]);
449          oldIndex++;
450          break;
451        }
452      }
453      if (splice) {
454        splices.push(splice);
455      }
456      return splices;
457    },
458    sharedPrefix: function(current, old, searchLength) {
459      for (var i = 0; i < searchLength; i++) if (!this.equals(current[i], old[i])) return i;
460      return searchLength;
461    },
462    sharedSuffix: function(current, old, searchLength) {
463      var index1 = current.length;
464      var index2 = old.length;
465      var count = 0;
466      while (count < searchLength && this.equals(current[--index1], old[--index2])) count++;
467      return count;
468    },
469    calculateSplices: function(current, previous) {
470      return this.calcSplices(current, 0, current.length, previous, 0, previous.length);
471    },
472    equals: function(currentValue, previousValue) {
473      return currentValue === previousValue;
474    }
475  };
476  scope.ArraySplice = ArraySplice;
477})(window.ShadowDOMPolyfill);
478
479(function(context) {
480  "use strict";
481  var OriginalMutationObserver = window.MutationObserver;
482  var callbacks = [];
483  var pending = false;
484  var timerFunc;
485  function handle() {
486    pending = false;
487    var copies = callbacks.slice(0);
488    callbacks = [];
489    for (var i = 0; i < copies.length; i++) {
490      (0, copies[i])();
491    }
492  }
493  if (OriginalMutationObserver) {
494    var counter = 1;
495    var observer = new OriginalMutationObserver(handle);
496    var textNode = document.createTextNode(counter);
497    observer.observe(textNode, {
498      characterData: true
499    });
500    timerFunc = function() {
501      counter = (counter + 1) % 2;
502      textNode.data = counter;
503    };
504  } else {
505    timerFunc = window.setTimeout;
506  }
507  function setEndOfMicrotask(func) {
508    callbacks.push(func);
509    if (pending) return;
510    pending = true;
511    timerFunc(handle, 0);
512  }
513  context.setEndOfMicrotask = setEndOfMicrotask;
514})(window.ShadowDOMPolyfill);
515
516(function(scope) {
517  "use strict";
518  var setEndOfMicrotask = scope.setEndOfMicrotask;
519  var wrapIfNeeded = scope.wrapIfNeeded;
520  var wrappers = scope.wrappers;
521  var registrationsTable = new WeakMap();
522  var globalMutationObservers = [];
523  var isScheduled = false;
524  function scheduleCallback(observer) {
525    if (observer.scheduled_) return;
526    observer.scheduled_ = true;
527    globalMutationObservers.push(observer);
528    if (isScheduled) return;
529    setEndOfMicrotask(notifyObservers);
530    isScheduled = true;
531  }
532  function notifyObservers() {
533    isScheduled = false;
534    while (globalMutationObservers.length) {
535      var notifyList = globalMutationObservers;
536      globalMutationObservers = [];
537      notifyList.sort(function(x, y) {
538        return x.uid_ - y.uid_;
539      });
540      for (var i = 0; i < notifyList.length; i++) {
541        var mo = notifyList[i];
542        mo.scheduled_ = false;
543        var queue = mo.takeRecords();
544        removeTransientObserversFor(mo);
545        if (queue.length) {
546          mo.callback_(queue, mo);
547        }
548      }
549    }
550  }
551  function MutationRecord(type, target) {
552    this.type = type;
553    this.target = target;
554    this.addedNodes = new wrappers.NodeList();
555    this.removedNodes = new wrappers.NodeList();
556    this.previousSibling = null;
557    this.nextSibling = null;
558    this.attributeName = null;
559    this.attributeNamespace = null;
560    this.oldValue = null;
561  }
562  function registerTransientObservers(ancestor, node) {
563    for (;ancestor; ancestor = ancestor.parentNode) {
564      var registrations = registrationsTable.get(ancestor);
565      if (!registrations) continue;
566      for (var i = 0; i < registrations.length; i++) {
567        var registration = registrations[i];
568        if (registration.options.subtree) registration.addTransientObserver(node);
569      }
570    }
571  }
572  function removeTransientObserversFor(observer) {
573    for (var i = 0; i < observer.nodes_.length; i++) {
574      var node = observer.nodes_[i];
575      var registrations = registrationsTable.get(node);
576      if (!registrations) return;
577      for (var j = 0; j < registrations.length; j++) {
578        var registration = registrations[j];
579        if (registration.observer === observer) registration.removeTransientObservers();
580      }
581    }
582  }
583  function enqueueMutation(target, type, data) {
584    var interestedObservers = Object.create(null);
585    var associatedStrings = Object.create(null);
586    for (var node = target; node; node = node.parentNode) {
587      var registrations = registrationsTable.get(node);
588      if (!registrations) continue;
589      for (var j = 0; j < registrations.length; j++) {
590        var registration = registrations[j];
591        var options = registration.options;
592        if (node !== target && !options.subtree) continue;
593        if (type === "attributes" && !options.attributes) continue;
594        if (type === "attributes" && options.attributeFilter && (data.namespace !== null || options.attributeFilter.indexOf(data.name) === -1)) {
595          continue;
596        }
597        if (type === "characterData" && !options.characterData) continue;
598        if (type === "childList" && !options.childList) continue;
599        var observer = registration.observer;
600        interestedObservers[observer.uid_] = observer;
601        if (type === "attributes" && options.attributeOldValue || type === "characterData" && options.characterDataOldValue) {
602          associatedStrings[observer.uid_] = data.oldValue;
603        }
604      }
605    }
606    for (var uid in interestedObservers) {
607      var observer = interestedObservers[uid];
608      var record = new MutationRecord(type, target);
609      if ("name" in data && "namespace" in data) {
610        record.attributeName = data.name;
611        record.attributeNamespace = data.namespace;
612      }
613      if (data.addedNodes) record.addedNodes = data.addedNodes;
614      if (data.removedNodes) record.removedNodes = data.removedNodes;
615      if (data.previousSibling) record.previousSibling = data.previousSibling;
616      if (data.nextSibling) record.nextSibling = data.nextSibling;
617      if (associatedStrings[uid] !== undefined) record.oldValue = associatedStrings[uid];
618      scheduleCallback(observer);
619      observer.records_.push(record);
620    }
621  }
622  var slice = Array.prototype.slice;
623  function MutationObserverOptions(options) {
624    this.childList = !!options.childList;
625    this.subtree = !!options.subtree;
626    if (!("attributes" in options) && ("attributeOldValue" in options || "attributeFilter" in options)) {
627      this.attributes = true;
628    } else {
629      this.attributes = !!options.attributes;
630    }
631    if ("characterDataOldValue" in options && !("characterData" in options)) this.characterData = true; else this.characterData = !!options.characterData;
632    if (!this.attributes && (options.attributeOldValue || "attributeFilter" in options) || !this.characterData && options.characterDataOldValue) {
633      throw new TypeError();
634    }
635    this.characterData = !!options.characterData;
636    this.attributeOldValue = !!options.attributeOldValue;
637    this.characterDataOldValue = !!options.characterDataOldValue;
638    if ("attributeFilter" in options) {
639      if (options.attributeFilter == null || typeof options.attributeFilter !== "object") {
640        throw new TypeError();
641      }
642      this.attributeFilter = slice.call(options.attributeFilter);
643    } else {
644      this.attributeFilter = null;
645    }
646  }
647  var uidCounter = 0;
648  function MutationObserver(callback) {
649    this.callback_ = callback;
650    this.nodes_ = [];
651    this.records_ = [];
652    this.uid_ = ++uidCounter;
653    this.scheduled_ = false;
654  }
655  MutationObserver.prototype = {
656    constructor: MutationObserver,
657    observe: function(target, options) {
658      target = wrapIfNeeded(target);
659      var newOptions = new MutationObserverOptions(options);
660      var registration;
661      var registrations = registrationsTable.get(target);
662      if (!registrations) registrationsTable.set(target, registrations = []);
663      for (var i = 0; i < registrations.length; i++) {
664        if (registrations[i].observer === this) {
665          registration = registrations[i];
666          registration.removeTransientObservers();
667          registration.options = newOptions;
668        }
669      }
670      if (!registration) {
671        registration = new Registration(this, target, newOptions);
672        registrations.push(registration);
673        this.nodes_.push(target);
674      }
675    },
676    disconnect: function() {
677      this.nodes_.forEach(function(node) {
678        var registrations = registrationsTable.get(node);
679        for (var i = 0; i < registrations.length; i++) {
680          var registration = registrations[i];
681          if (registration.observer === this) {
682            registrations.splice(i, 1);
683            break;
684          }
685        }
686      }, this);
687      this.records_ = [];
688    },
689    takeRecords: function() {
690      var copyOfRecords = this.records_;
691      this.records_ = [];
692      return copyOfRecords;
693    }
694  };
695  function Registration(observer, target, options) {
696    this.observer = observer;
697    this.target = target;
698    this.options = options;
699    this.transientObservedNodes = [];
700  }
701  Registration.prototype = {
702    addTransientObserver: function(node) {
703      if (node === this.target) return;
704      scheduleCallback(this.observer);
705      this.transientObservedNodes.push(node);
706      var registrations = registrationsTable.get(node);
707      if (!registrations) registrationsTable.set(node, registrations = []);
708      registrations.push(this);
709    },
710    removeTransientObservers: function() {
711      var transientObservedNodes = this.transientObservedNodes;
712      this.transientObservedNodes = [];
713      for (var i = 0; i < transientObservedNodes.length; i++) {
714        var node = transientObservedNodes[i];
715        var registrations = registrationsTable.get(node);
716        for (var j = 0; j < registrations.length; j++) {
717          if (registrations[j] === this) {
718            registrations.splice(j, 1);
719            break;
720          }
721        }
722      }
723    }
724  };
725  scope.enqueueMutation = enqueueMutation;
726  scope.registerTransientObservers = registerTransientObservers;
727  scope.wrappers.MutationObserver = MutationObserver;
728  scope.wrappers.MutationRecord = MutationRecord;
729})(window.ShadowDOMPolyfill);
730
731(function(scope) {
732  "use strict";
733  function TreeScope(root, parent) {
734    this.root = root;
735    this.parent = parent;
736  }
737  TreeScope.prototype = {
738    get renderer() {
739      if (this.root instanceof scope.wrappers.ShadowRoot) {
740        return scope.getRendererForHost(this.root.host);
741      }
742      return null;
743    },
744    contains: function(treeScope) {
745      for (;treeScope; treeScope = treeScope.parent) {
746        if (treeScope === this) return true;
747      }
748      return false;
749    }
750  };
751  function setTreeScope(node, treeScope) {
752    if (node.treeScope_ !== treeScope) {
753      node.treeScope_ = treeScope;
754      for (var sr = node.shadowRoot; sr; sr = sr.olderShadowRoot) {
755        sr.treeScope_.parent = treeScope;
756      }
757      for (var child = node.firstChild; child; child = child.nextSibling) {
758        setTreeScope(child, treeScope);
759      }
760    }
761  }
762  function getTreeScope(node) {
763    if (node instanceof scope.wrappers.Window) {
764      debugger;
765    }
766    if (node.treeScope_) return node.treeScope_;
767    var parent = node.parentNode;
768    var treeScope;
769    if (parent) treeScope = getTreeScope(parent); else treeScope = new TreeScope(node, null);
770    return node.treeScope_ = treeScope;
771  }
772  scope.TreeScope = TreeScope;
773  scope.getTreeScope = getTreeScope;
774  scope.setTreeScope = setTreeScope;
775})(window.ShadowDOMPolyfill);
776
777(function(scope) {
778  "use strict";
779  var forwardMethodsToWrapper = scope.forwardMethodsToWrapper;
780  var getTreeScope = scope.getTreeScope;
781  var mixin = scope.mixin;
782  var registerWrapper = scope.registerWrapper;
783  var setWrapper = scope.setWrapper;
784  var unsafeUnwrap = scope.unsafeUnwrap;
785  var unwrap = scope.unwrap;
786  var wrap = scope.wrap;
787  var wrappers = scope.wrappers;
788  var wrappedFuns = new WeakMap();
789  var listenersTable = new WeakMap();
790  var handledEventsTable = new WeakMap();
791  var currentlyDispatchingEvents = new WeakMap();
792  var targetTable = new WeakMap();
793  var currentTargetTable = new WeakMap();
794  var relatedTargetTable = new WeakMap();
795  var eventPhaseTable = new WeakMap();
796  var stopPropagationTable = new WeakMap();
797  var stopImmediatePropagationTable = new WeakMap();
798  var eventHandlersTable = new WeakMap();
799  var eventPathTable = new WeakMap();
800  function isShadowRoot(node) {
801    return node instanceof wrappers.ShadowRoot;
802  }
803  function rootOfNode(node) {
804    return getTreeScope(node).root;
805  }
806  function getEventPath(node, event) {
807    var path = [];
808    var current = node;
809    path.push(current);
810    while (current) {
811      var destinationInsertionPoints = getDestinationInsertionPoints(current);
812      if (destinationInsertionPoints && destinationInsertionPoints.length > 0) {
813        for (var i = 0; i < destinationInsertionPoints.length; i++) {
814          var insertionPoint = destinationInsertionPoints[i];
815          if (isShadowInsertionPoint(insertionPoint)) {
816            var shadowRoot = rootOfNode(insertionPoint);
817            var olderShadowRoot = shadowRoot.olderShadowRoot;
818            if (olderShadowRoot) path.push(olderShadowRoot);
819          }
820          path.push(insertionPoint);
821        }
822        current = destinationInsertionPoints[destinationInsertionPoints.length - 1];
823      } else {
824        if (isShadowRoot(current)) {
825          if (inSameTree(node, current) && eventMustBeStopped(event)) {
826            break;
827          }
828          current = current.host;
829          path.push(current);
830        } else {
831          current = current.parentNode;
832          if (current) path.push(current);
833        }
834      }
835    }
836    return path;
837  }
838  function eventMustBeStopped(event) {
839    if (!event) return false;
840    switch (event.type) {
841     case "abort":
842     case "error":
843     case "select":
844     case "change":
845     case "load":
846     case "reset":
847     case "resize":
848     case "scroll":
849     case "selectstart":
850      return true;
851    }
852    return false;
853  }
854  function isShadowInsertionPoint(node) {
855    return node instanceof HTMLShadowElement;
856  }
857  function getDestinationInsertionPoints(node) {
858    return scope.getDestinationInsertionPoints(node);
859  }
860  function eventRetargetting(path, currentTarget) {
861    if (path.length === 0) return currentTarget;
862    if (currentTarget instanceof wrappers.Window) currentTarget = currentTarget.document;
863    var currentTargetTree = getTreeScope(currentTarget);
864    var originalTarget = path[0];
865    var originalTargetTree = getTreeScope(originalTarget);
866    var relativeTargetTree = lowestCommonInclusiveAncestor(currentTargetTree, originalTargetTree);
867    for (var i = 0; i < path.length; i++) {
868      var node = path[i];
869      if (getTreeScope(node) === relativeTargetTree) return node;
870    }
871    return path[path.length - 1];
872  }
873  function getTreeScopeAncestors(treeScope) {
874    var ancestors = [];
875    for (;treeScope; treeScope = treeScope.parent) {
876      ancestors.push(treeScope);
877    }
878    return ancestors;
879  }
880  function lowestCommonInclusiveAncestor(tsA, tsB) {
881    var ancestorsA = getTreeScopeAncestors(tsA);
882    var ancestorsB = getTreeScopeAncestors(tsB);
883    var result = null;
884    while (ancestorsA.length > 0 && ancestorsB.length > 0) {
885      var a = ancestorsA.pop();
886      var b = ancestorsB.pop();
887      if (a === b) result = a; else break;
888    }
889    return result;
890  }
891  function getTreeScopeRoot(ts) {
892    if (!ts.parent) return ts;
893    return getTreeScopeRoot(ts.parent);
894  }
895  function relatedTargetResolution(event, currentTarget, relatedTarget) {
896    if (currentTarget instanceof wrappers.Window) currentTarget = currentTarget.document;
897    var currentTargetTree = getTreeScope(currentTarget);
898    var relatedTargetTree = getTreeScope(relatedTarget);
899    var relatedTargetEventPath = getEventPath(relatedTarget, event);
900    var lowestCommonAncestorTree;
901    var lowestCommonAncestorTree = lowestCommonInclusiveAncestor(currentTargetTree, relatedTargetTree);
902    if (!lowestCommonAncestorTree) lowestCommonAncestorTree = relatedTargetTree.root;
903    for (var commonAncestorTree = lowestCommonAncestorTree; commonAncestorTree; commonAncestorTree = commonAncestorTree.parent) {
904      var adjustedRelatedTarget;
905      for (var i = 0; i < relatedTargetEventPath.length; i++) {
906        var node = relatedTargetEventPath[i];
907        if (getTreeScope(node) === commonAncestorTree) return node;
908      }
909    }
910    return null;
911  }
912  function inSameTree(a, b) {
913    return getTreeScope(a) === getTreeScope(b);
914  }
915  var NONE = 0;
916  var CAPTURING_PHASE = 1;
917  var AT_TARGET = 2;
918  var BUBBLING_PHASE = 3;
919  var pendingError;
920  function dispatchOriginalEvent(originalEvent) {
921    if (handledEventsTable.get(originalEvent)) return;
922    handledEventsTable.set(originalEvent, true);
923    dispatchEvent(wrap(originalEvent), wrap(originalEvent.target));
924    if (pendingError) {
925      var err = pendingError;
926      pendingError = null;
927      throw err;
928    }
929  }
930  function isLoadLikeEvent(event) {
931    switch (event.type) {
932     case "load":
933     case "beforeunload":
934     case "unload":
935      return true;
936    }
937    return false;
938  }
939  function dispatchEvent(event, originalWrapperTarget) {
940    if (currentlyDispatchingEvents.get(event)) throw new Error("InvalidStateError");
941    currentlyDispatchingEvents.set(event, true);
942    scope.renderAllPending();
943    var eventPath;
944    var overrideTarget;
945    var win;
946    if (isLoadLikeEvent(event) && !event.bubbles) {
947      var doc = originalWrapperTarget;
948      if (doc instanceof wrappers.Document && (win = doc.defaultView)) {
949        overrideTarget = doc;
950        eventPath = [];
951      }
952    }
953    if (!eventPath) {
954      if (originalWrapperTarget instanceof wrappers.Window) {
955        win = originalWrapperTarget;
956        eventPath = [];
957      } else {
958        eventPath = getEventPath(originalWrapperTarget, event);
959        if (!isLoadLikeEvent(event)) {
960          var doc = eventPath[eventPath.length - 1];
961          if (doc instanceof wrappers.Document) win = doc.defaultView;
962        }
963      }
964    }
965    eventPathTable.set(event, eventPath);
966    if (dispatchCapturing(event, eventPath, win, overrideTarget)) {
967      if (dispatchAtTarget(event, eventPath, win, overrideTarget)) {
968        dispatchBubbling(event, eventPath, win, overrideTarget);
969      }
970    }
971    eventPhaseTable.set(event, NONE);
972    currentTargetTable.delete(event, null);
973    currentlyDispatchingEvents.delete(event);
974    return event.defaultPrevented;
975  }
976  function dispatchCapturing(event, eventPath, win, overrideTarget) {
977    var phase = CAPTURING_PHASE;
978    if (win) {
979      if (!invoke(win, event, phase, eventPath, overrideTarget)) return false;
980    }
981    for (var i = eventPath.length - 1; i > 0; i--) {
982      if (!invoke(eventPath[i], event, phase, eventPath, overrideTarget)) return false;
983    }
984    return true;
985  }
986  function dispatchAtTarget(event, eventPath, win, overrideTarget) {
987    var phase = AT_TARGET;
988    var currentTarget = eventPath[0] || win;
989    return invoke(currentTarget, event, phase, eventPath, overrideTarget);
990  }
991  function dispatchBubbling(event, eventPath, win, overrideTarget) {
992    var phase = BUBBLING_PHASE;
993    for (var i = 1; i < eventPath.length; i++) {
994      if (!invoke(eventPath[i], event, phase, eventPath, overrideTarget)) return;
995    }
996    if (win && eventPath.length > 0) {
997      invoke(win, event, phase, eventPath, overrideTarget);
998    }
999  }
1000  function invoke(currentTarget, event, phase, eventPath, overrideTarget) {
1001    var listeners = listenersTable.get(currentTarget);
1002    if (!listeners) return true;
1003    var target = overrideTarget || eventRetargetting(eventPath, currentTarget);
1004    if (target === currentTarget) {
1005      if (phase === CAPTURING_PHASE) return true;
1006      if (phase === BUBBLING_PHASE) phase = AT_TARGET;
1007    } else if (phase === BUBBLING_PHASE && !event.bubbles) {
1008      return true;
1009    }
1010    if ("relatedTarget" in event) {
1011      var originalEvent = unwrap(event);
1012      var unwrappedRelatedTarget = originalEvent.relatedTarget;
1013      if (unwrappedRelatedTarget) {
1014        if (unwrappedRelatedTarget instanceof Object && unwrappedRelatedTarget.addEventListener) {
1015          var relatedTarget = wrap(unwrappedRelatedTarget);
1016          var adjusted = relatedTargetResolution(event, currentTarget, relatedTarget);
1017          if (adjusted === target) return true;
1018        } else {
1019          adjusted = null;
1020        }
1021        relatedTargetTable.set(event, adjusted);
1022      }
1023    }
1024    eventPhaseTable.set(event, phase);
1025    var type = event.type;
1026    var anyRemoved = false;
1027    targetTable.set(event, target);
1028    currentTargetTable.set(event, currentTarget);
1029    listeners.depth++;
1030    for (var i = 0, len = listeners.length; i < len; i++) {
1031      var listener = listeners[i];
1032      if (listener.removed) {
1033        anyRemoved = true;
1034        continue;
1035      }
1036      if (listener.type !== type || !listener.capture && phase === CAPTURING_PHASE || listener.capture && phase === BUBBLING_PHASE) {
1037        continue;
1038      }
1039      try {
1040        if (typeof listener.handler === "function") listener.handler.call(currentTarget, event); else listener.handler.handleEvent(event);
1041        if (stopImmediatePropagationTable.get(event)) return false;
1042      } catch (ex) {
1043        if (!pendingError) pendingError = ex;
1044      }
1045    }
1046    listeners.depth--;
1047    if (anyRemoved && listeners.depth === 0) {
1048      var copy = listeners.slice();
1049      listeners.length = 0;
1050      for (var i = 0; i < copy.length; i++) {
1051        if (!copy[i].removed) listeners.push(copy[i]);
1052      }
1053    }
1054    return !stopPropagationTable.get(event);
1055  }
1056  function Listener(type, handler, capture) {
1057    this.type = type;
1058    this.handler = handler;
1059    this.capture = Boolean(capture);
1060  }
1061  Listener.prototype = {
1062    equals: function(that) {
1063      return this.handler === that.handler && this.type === that.type && this.capture === that.capture;
1064    },
1065    get removed() {
1066      return this.handler === null;
1067    },
1068    remove: function() {
1069      this.handler = null;
1070    }
1071  };
1072  var OriginalEvent = window.Event;
1073  OriginalEvent.prototype.polymerBlackList_ = {
1074    returnValue: true,
1075    keyLocation: true
1076  };
1077  function Event(type, options) {
1078    if (type instanceof OriginalEvent) {
1079      var impl = type;
1080      if (!OriginalBeforeUnloadEvent && impl.type === "beforeunload" && !(this instanceof BeforeUnloadEvent)) {
1081        return new BeforeUnloadEvent(impl);
1082      }
1083      setWrapper(impl, this);
1084    } else {
1085      return wrap(constructEvent(OriginalEvent, "Event", type, options));
1086    }
1087  }
1088  Event.prototype = {
1089    get target() {
1090      return targetTable.get(this);
1091    },
1092    get currentTarget() {
1093      return currentTargetTable.get(this);
1094    },
1095    get eventPhase() {
1096      return eventPhaseTable.get(this);
1097    },
1098    get path() {
1099      var eventPath = eventPathTable.get(this);
1100      if (!eventPath) return [];
1101      return eventPath.slice();
1102    },
1103    stopPropagation: function() {
1104      stopPropagationTable.set(this, true);
1105    },
1106    stopImmediatePropagation: function() {
1107      stopPropagationTable.set(this, true);
1108      stopImmediatePropagationTable.set(this, true);
1109    }
1110  };
1111  registerWrapper(OriginalEvent, Event, document.createEvent("Event"));
1112  function unwrapOptions(options) {
1113    if (!options || !options.relatedTarget) return options;
1114    return Object.create(options, {
1115      relatedTarget: {
1116        value: unwrap(options.relatedTarget)
1117      }
1118    });
1119  }
1120  function registerGenericEvent(name, SuperEvent, prototype) {
1121    var OriginalEvent = window[name];
1122    var GenericEvent = function(type, options) {
1123      if (type instanceof OriginalEvent) setWrapper(type, this); else return wrap(constructEvent(OriginalEvent, name, type, options));
1124    };
1125    GenericEvent.prototype = Object.create(SuperEvent.prototype);
1126    if (prototype) mixin(GenericEvent.prototype, prototype);
1127    if (OriginalEvent) {
1128      try {
1129        registerWrapper(OriginalEvent, GenericEvent, new OriginalEvent("temp"));
1130      } catch (ex) {
1131        registerWrapper(OriginalEvent, GenericEvent, document.createEvent(name));
1132      }
1133    }
1134    return GenericEvent;
1135  }
1136  var UIEvent = registerGenericEvent("UIEvent", Event);
1137  var CustomEvent = registerGenericEvent("CustomEvent", Event);
1138  var relatedTargetProto = {
1139    get relatedTarget() {
1140      var relatedTarget = relatedTargetTable.get(this);
1141      if (relatedTarget !== undefined) return relatedTarget;
1142      return wrap(unwrap(this).relatedTarget);
1143    }
1144  };
1145  function getInitFunction(name, relatedTargetIndex) {
1146    return function() {
1147      arguments[relatedTargetIndex] = unwrap(arguments[relatedTargetIndex]);
1148      var impl = unwrap(this);
1149      impl[name].apply(impl, arguments);
1150    };
1151  }
1152  var mouseEventProto = mixin({
1153    initMouseEvent: getInitFunction("initMouseEvent", 14)
1154  }, relatedTargetProto);
1155  var focusEventProto = mixin({
1156    initFocusEvent: getInitFunction("initFocusEvent", 5)
1157  }, relatedTargetProto);
1158  var MouseEvent = registerGenericEvent("MouseEvent", UIEvent, mouseEventProto);
1159  var FocusEvent = registerGenericEvent("FocusEvent", UIEvent, focusEventProto);
1160  var defaultInitDicts = Object.create(null);
1161  var supportsEventConstructors = function() {
1162    try {
1163      new window.FocusEvent("focus");
1164    } catch (ex) {
1165      return false;
1166    }
1167    return true;
1168  }();
1169  function constructEvent(OriginalEvent, name, type, options) {
1170    if (supportsEventConstructors) return new OriginalEvent(type, unwrapOptions(options));
1171    var event = unwrap(document.createEvent(name));
1172    var defaultDict = defaultInitDicts[name];
1173    var args = [ type ];
1174    Object.keys(defaultDict).forEach(function(key) {
1175      var v = options != null && key in options ? options[key] : defaultDict[key];
1176      if (key === "relatedTarget") v = unwrap(v);
1177      args.push(v);
1178    });
1179    event["init" + name].apply(event, args);
1180    return event;
1181  }
1182  if (!supportsEventConstructors) {
1183    var configureEventConstructor = function(name, initDict, superName) {
1184      if (superName) {
1185        var superDict = defaultInitDicts[superName];
1186        initDict = mixin(mixin({}, superDict), initDict);
1187      }
1188      defaultInitDicts[name] = initDict;
1189    };
1190    configureEventConstructor("Event", {
1191      bubbles: false,
1192      cancelable: false
1193    });
1194    configureEventConstructor("CustomEvent", {
1195      detail: null
1196    }, "Event");
1197    configureEventConstructor("UIEvent", {
1198      view: null,
1199      detail: 0
1200    }, "Event");
1201    configureEventConstructor("MouseEvent", {
1202      screenX: 0,
1203      screenY: 0,
1204      clientX: 0,
1205      clientY: 0,
1206      ctrlKey: false,
1207      altKey: false,
1208      shiftKey: false,
1209      metaKey: false,
1210      button: 0,
1211      relatedTarget: null
1212    }, "UIEvent");
1213    configureEventConstructor("FocusEvent", {
1214      relatedTarget: null
1215    }, "UIEvent");
1216  }
1217  var OriginalBeforeUnloadEvent = window.BeforeUnloadEvent;
1218  function BeforeUnloadEvent(impl) {
1219    Event.call(this, impl);
1220  }
1221  BeforeUnloadEvent.prototype = Object.create(Event.prototype);
1222  mixin(BeforeUnloadEvent.prototype, {
1223    get returnValue() {
1224      return unsafeUnwrap(this).returnValue;
1225    },
1226    set returnValue(v) {
1227      unsafeUnwrap(this).returnValue = v;
1228    }
1229  });
1230  if (OriginalBeforeUnloadEvent) registerWrapper(OriginalBeforeUnloadEvent, BeforeUnloadEvent);
1231  function isValidListener(fun) {
1232    if (typeof fun === "function") return true;
1233    return fun && fun.handleEvent;
1234  }
1235  function isMutationEvent(type) {
1236    switch (type) {
1237     case "DOMAttrModified":
1238     case "DOMAttributeNameChanged":
1239     case "DOMCharacterDataModified":
1240     case "DOMElementNameChanged":
1241     case "DOMNodeInserted":
1242     case "DOMNodeInsertedIntoDocument":
1243     case "DOMNodeRemoved":
1244     case "DOMNodeRemovedFromDocument":
1245     case "DOMSubtreeModified":
1246      return true;
1247    }
1248    return false;
1249  }
1250  var OriginalEventTarget = window.EventTarget;
1251  function EventTarget(impl) {
1252    setWrapper(impl, this);
1253  }
1254  var methodNames = [ "addEventListener", "removeEventListener", "dispatchEvent" ];
1255  [ Node, Window ].forEach(function(constructor) {
1256    var p = constructor.prototype;
1257    methodNames.forEach(function(name) {
1258      Object.defineProperty(p, name + "_", {
1259        value: p[name]
1260      });
1261    });
1262  });
1263  function getTargetToListenAt(wrapper) {
1264    if (wrapper instanceof wrappers.ShadowRoot) wrapper = wrapper.host;
1265    return unwrap(wrapper);
1266  }
1267  EventTarget.prototype = {
1268    addEventListener: function(type, fun, capture) {
1269      if (!isValidListener(fun) || isMutationEvent(type)) return;
1270      var listener = new Listener(type, fun, capture);
1271      var listeners = listenersTable.get(this);
1272      if (!listeners) {
1273        listeners = [];
1274        listeners.depth = 0;
1275        listenersTable.set(this, listeners);
1276      } else {
1277        for (var i = 0; i < listeners.length; i++) {
1278          if (listener.equals(listeners[i])) return;
1279        }
1280      }
1281      listeners.push(listener);
1282      var target = getTargetToListenAt(this);
1283      target.addEventListener_(type, dispatchOriginalEvent, true);
1284    },
1285    removeEventListener: function(type, fun, capture) {
1286      capture = Boolean(capture);
1287      var listeners = listenersTable.get(this);
1288      if (!listeners) return;
1289      var count = 0, found = false;
1290      for (var i = 0; i < listeners.length; i++) {
1291        if (listeners[i].type === type && listeners[i].capture === capture) {
1292          count++;
1293          if (listeners[i].handler === fun) {
1294            found = true;
1295            listeners[i].remove();
1296          }
1297        }
1298      }
1299      if (found && count === 1) {
1300        var target = getTargetToListenAt(this);
1301        target.removeEventListener_(type, dispatchOriginalEvent, true);
1302      }
1303    },
1304    dispatchEvent: function(event) {
1305      var nativeEvent = unwrap(event);
1306      var eventType = nativeEvent.type;
1307      handledEventsTable.set(nativeEvent, false);
1308      scope.renderAllPending();
1309      var tempListener;
1310      if (!hasListenerInAncestors(this, eventType)) {
1311        tempListener = function() {};
1312        this.addEventListener(eventType, tempListener, true);
1313      }
1314      try {
1315        return unwrap(this).dispatchEvent_(nativeEvent);
1316      } finally {
1317        if (tempListener) this.removeEventListener(eventType, tempListener, true);
1318      }
1319    }
1320  };
1321  function hasListener(node, type) {
1322    var listeners = listenersTable.get(node);
1323    if (listeners) {
1324      for (var i = 0; i < listeners.length; i++) {
1325        if (!listeners[i].removed && listeners[i].type === type) return true;
1326      }
1327    }
1328    return false;
1329  }
1330  function hasListenerInAncestors(target, type) {
1331    for (var node = unwrap(target); node; node = node.parentNode) {
1332      if (hasListener(wrap(node), type)) return true;
1333    }
1334    return false;
1335  }
1336  if (OriginalEventTarget) registerWrapper(OriginalEventTarget, EventTarget);
1337  function wrapEventTargetMethods(constructors) {
1338    forwardMethodsToWrapper(constructors, methodNames);
1339  }
1340  var originalElementFromPoint = document.elementFromPoint;
1341  function elementFromPoint(self, document, x, y) {
1342    scope.renderAllPending();
1343    var element = wrap(originalElementFromPoint.call(unsafeUnwrap(document), x, y));
1344    if (!element) return null;
1345    var path = getEventPath(element, null);
1346    var idx = path.lastIndexOf(self);
1347    if (idx == -1) return null; else path = path.slice(0, idx);
1348    return eventRetargetting(path, self);
1349  }
1350  function getEventHandlerGetter(name) {
1351    return function() {
1352      var inlineEventHandlers = eventHandlersTable.get(this);
1353      return inlineEventHandlers && inlineEventHandlers[name] && inlineEventHandlers[name].value || null;
1354    };
1355  }
1356  function getEventHandlerSetter(name) {
1357    var eventType = name.slice(2);
1358    return function(value) {
1359      var inlineEventHandlers = eventHandlersTable.get(this);
1360      if (!inlineEventHandlers) {
1361        inlineEventHandlers = Object.create(null);
1362        eventHandlersTable.set(this, inlineEventHandlers);
1363      }
1364      var old = inlineEventHandlers[name];
1365      if (old) this.removeEventListener(eventType, old.wrapped, false);
1366      if (typeof value === "function") {
1367        var wrapped = function(e) {
1368          var rv = value.call(this, e);
1369          if (rv === false) e.preventDefault(); else if (name === "onbeforeunload" && typeof rv === "string") e.returnValue = rv;
1370        };
1371        this.addEventListener(eventType, wrapped, false);
1372        inlineEventHandlers[name] = {
1373          value: value,
1374          wrapped: wrapped
1375        };
1376      }
1377    };
1378  }
1379  scope.elementFromPoint = elementFromPoint;
1380  scope.getEventHandlerGetter = getEventHandlerGetter;
1381  scope.getEventHandlerSetter = getEventHandlerSetter;
1382  scope.wrapEventTargetMethods = wrapEventTargetMethods;
1383  scope.wrappers.BeforeUnloadEvent = BeforeUnloadEvent;
1384  scope.wrappers.CustomEvent = CustomEvent;
1385  scope.wrappers.Event = Event;
1386  scope.wrappers.EventTarget = EventTarget;
1387  scope.wrappers.FocusEvent = FocusEvent;
1388  scope.wrappers.MouseEvent = MouseEvent;
1389  scope.wrappers.UIEvent = UIEvent;
1390})(window.ShadowDOMPolyfill);
1391
1392(function(scope) {
1393  "use strict";
1394  var UIEvent = scope.wrappers.UIEvent;
1395  var mixin = scope.mixin;
1396  var registerWrapper = scope.registerWrapper;
1397  var setWrapper = scope.setWrapper;
1398  var unsafeUnwrap = scope.unsafeUnwrap;
1399  var wrap = scope.wrap;
1400  var OriginalTouchEvent = window.TouchEvent;
1401  if (!OriginalTouchEvent) return;
1402  var nativeEvent;
1403  try {
1404    nativeEvent = document.createEvent("TouchEvent");
1405  } catch (ex) {
1406    return;
1407  }
1408  var nonEnumDescriptor = {
1409    enumerable: false
1410  };
1411  function nonEnum(obj, prop) {
1412    Object.defineProperty(obj, prop, nonEnumDescriptor);
1413  }
1414  function Touch(impl) {
1415    setWrapper(impl, this);
1416  }
1417  Touch.prototype = {
1418    get target() {
1419      return wrap(unsafeUnwrap(this).target);
1420    }
1421  };
1422  var descr = {
1423    configurable: true,
1424    enumerable: true,
1425    get: null
1426  };
1427  [ "clientX", "clientY", "screenX", "screenY", "pageX", "pageY", "identifier", "webkitRadiusX", "webkitRadiusY", "webkitRotationAngle", "webkitForce" ].forEach(function(name) {
1428    descr.get = function() {
1429      return unsafeUnwrap(this)[name];
1430    };
1431    Object.defineProperty(Touch.prototype, name, descr);
1432  });
1433  function TouchList() {
1434    this.length = 0;
1435    nonEnum(this, "length");
1436  }
1437  TouchList.prototype = {
1438    item: function(index) {
1439      return this[index];
1440    }
1441  };
1442  function wrapTouchList(nativeTouchList) {
1443    var list = new TouchList();
1444    for (var i = 0; i < nativeTouchList.length; i++) {
1445      list[i] = new Touch(nativeTouchList[i]);
1446    }
1447    list.length = i;
1448    return list;
1449  }
1450  function TouchEvent(impl) {
1451    UIEvent.call(this, impl);
1452  }
1453  TouchEvent.prototype = Object.create(UIEvent.prototype);
1454  mixin(TouchEvent.prototype, {
1455    get touches() {
1456      return wrapTouchList(unsafeUnwrap(this).touches);
1457    },
1458    get targetTouches() {
1459      return wrapTouchList(unsafeUnwrap(this).targetTouches);
1460    },
1461    get changedTouches() {
1462      return wrapTouchList(unsafeUnwrap(this).changedTouches);
1463    },
1464    initTouchEvent: function() {
1465      throw new Error("Not implemented");
1466    }
1467  });
1468  registerWrapper(OriginalTouchEvent, TouchEvent, nativeEvent);
1469  scope.wrappers.Touch = Touch;
1470  scope.wrappers.TouchEvent = TouchEvent;
1471  scope.wrappers.TouchList = TouchList;
1472})(window.ShadowDOMPolyfill);
1473
1474(function(scope) {
1475  "use strict";
1476  var unsafeUnwrap = scope.unsafeUnwrap;
1477  var wrap = scope.wrap;
1478  var nonEnumDescriptor = {
1479    enumerable: false
1480  };
1481  function nonEnum(obj, prop) {
1482    Object.defineProperty(obj, prop, nonEnumDescriptor);
1483  }
1484  function NodeList() {
1485    this.length = 0;
1486    nonEnum(this, "length");
1487  }
1488  NodeList.prototype = {
1489    item: function(index) {
1490      return this[index];
1491    }
1492  };
1493  nonEnum(NodeList.prototype, "item");
1494  function wrapNodeList(list) {
1495    if (list == null) return list;
1496    var wrapperList = new NodeList();
1497    for (var i = 0, length = list.length; i < length; i++) {
1498      wrapperList[i] = wrap(list[i]);
1499    }
1500    wrapperList.length = length;
1501    return wrapperList;
1502  }
1503  function addWrapNodeListMethod(wrapperConstructor, name) {
1504    wrapperConstructor.prototype[name] = function() {
1505      return wrapNodeList(unsafeUnwrap(this)[name].apply(unsafeUnwrap(this), arguments));
1506    };
1507  }
1508  scope.wrappers.NodeList = NodeList;
1509  scope.addWrapNodeListMethod = addWrapNodeListMethod;
1510  scope.wrapNodeList = wrapNodeList;
1511})(window.ShadowDOMPolyfill);
1512
1513(function(scope) {
1514  "use strict";
1515  scope.wrapHTMLCollection = scope.wrapNodeList;
1516  scope.wrappers.HTMLCollection = scope.wrappers.NodeList;
1517})(window.ShadowDOMPolyfill);
1518
1519(function(scope) {
1520  "use strict";
1521  var EventTarget = scope.wrappers.EventTarget;
1522  var NodeList = scope.wrappers.NodeList;
1523  var TreeScope = scope.TreeScope;
1524  var assert = scope.assert;
1525  var defineWrapGetter = scope.defineWrapGetter;
1526  var enqueueMutation = scope.enqueueMutation;
1527  var getTreeScope = scope.getTreeScope;
1528  var isWrapper = scope.isWrapper;
1529  var mixin = scope.mixin;
1530  var registerTransientObservers = scope.registerTransientObservers;
1531  var registerWrapper = scope.registerWrapper;
1532  var setTreeScope = scope.setTreeScope;
1533  var unsafeUnwrap = scope.unsafeUnwrap;
1534  var unwrap = scope.unwrap;
1535  var unwrapIfNeeded = scope.unwrapIfNeeded;
1536  var wrap = scope.wrap;
1537  var wrapIfNeeded = scope.wrapIfNeeded;
1538  var wrappers = scope.wrappers;
1539  function assertIsNodeWrapper(node) {
1540    assert(node instanceof Node);
1541  }
1542  function createOneElementNodeList(node) {
1543    var nodes = new NodeList();
1544    nodes[0] = node;
1545    nodes.length = 1;
1546    return nodes;
1547  }
1548  var surpressMutations = false;
1549  function enqueueRemovalForInsertedNodes(node, parent, nodes) {
1550    enqueueMutation(parent, "childList", {
1551      removedNodes: nodes,
1552      previousSibling: node.previousSibling,
1553      nextSibling: node.nextSibling
1554    });
1555  }
1556  function enqueueRemovalForInsertedDocumentFragment(df, nodes) {
1557    enqueueMutation(df, "childList", {
1558      removedNodes: nodes
1559    });
1560  }
1561  function collectNodes(node, parentNode, previousNode, nextNode) {
1562    if (node instanceof DocumentFragment) {
1563      var nodes = collectNodesForDocumentFragment(node);
1564      surpressMutations = true;
1565      for (var i = nodes.length - 1; i >= 0; i--) {
1566        node.removeChild(nodes[i]);
1567        nodes[i].parentNode_ = parentNode;
1568      }
1569      surpressMutations = false;
1570      for (var i = 0; i < nodes.length; i++) {
1571        nodes[i].previousSibling_ = nodes[i - 1] || previousNode;
1572        nodes[i].nextSibling_ = nodes[i + 1] || nextNode;
1573      }
1574      if (previousNode) previousNode.nextSibling_ = nodes[0];
1575      if (nextNode) nextNode.previousSibling_ = nodes[nodes.length - 1];
1576      return nodes;
1577    }
1578    var nodes = createOneElementNodeList(node);
1579    var oldParent = node.parentNode;
1580    if (oldParent) {
1581      oldParent.removeChild(node);
1582    }
1583    node.parentNode_ = parentNode;
1584    node.previousSibling_ = previousNode;
1585    node.nextSibling_ = nextNode;
1586    if (previousNode) previousNode.nextSibling_ = node;
1587    if (nextNode) nextNode.previousSibling_ = node;
1588    return nodes;
1589  }
1590  function collectNodesNative(node) {
1591    if (node instanceof DocumentFragment) return collectNodesForDocumentFragment(node);
1592    var nodes = createOneElementNodeList(node);
1593    var oldParent = node.parentNode;
1594    if (oldParent) enqueueRemovalForInsertedNodes(node, oldParent, nodes);
1595    return nodes;
1596  }
1597  function collectNodesForDocumentFragment(node) {
1598    var nodes = new NodeList();
1599    var i = 0;
1600    for (var child = node.firstChild; child; child = child.nextSibling) {
1601      nodes[i++] = child;
1602    }
1603    nodes.length = i;
1604    enqueueRemovalForInsertedDocumentFragment(node, nodes);
1605    return nodes;
1606  }
1607  function snapshotNodeList(nodeList) {
1608    return nodeList;
1609  }
1610  function nodeWasAdded(node, treeScope) {
1611    setTreeScope(node, treeScope);
1612    node.nodeIsInserted_();
1613  }
1614  function nodesWereAdded(nodes, parent) {
1615    var treeScope = getTreeScope(parent);
1616    for (var i = 0; i < nodes.length; i++) {
1617      nodeWasAdded(nodes[i], treeScope);
1618    }
1619  }
1620  function nodeWasRemoved(node) {
1621    setTreeScope(node, new TreeScope(node, null));
1622  }
1623  function nodesWereRemoved(nodes) {
1624    for (var i = 0; i < nodes.length; i++) {
1625      nodeWasRemoved(nodes[i]);
1626    }
1627  }
1628  function ensureSameOwnerDocument(parent, child) {
1629    var ownerDoc = parent.nodeType === Node.DOCUMENT_NODE ? parent : parent.ownerDocument;
1630    if (ownerDoc !== child.ownerDocument) ownerDoc.adoptNode(child);
1631  }
1632  function adoptNodesIfNeeded(owner, nodes) {
1633    if (!nodes.length) return;
1634    var ownerDoc = owner.ownerDocument;
1635    if (ownerDoc === nodes[0].ownerDocument) return;
1636    for (var i = 0; i < nodes.length; i++) {
1637      scope.adoptNodeNoRemove(nodes[i], ownerDoc);
1638    }
1639  }
1640  function unwrapNodesForInsertion(owner, nodes) {
1641    adoptNodesIfNeeded(owner, nodes);
1642    var length = nodes.length;
1643    if (length === 1) return unwrap(nodes[0]);
1644    var df = unwrap(owner.ownerDocument.createDocumentFragment());
1645    for (var i = 0; i < length; i++) {
1646      df.appendChild(unwrap(nodes[i]));
1647    }
1648    return df;
1649  }
1650  function clearChildNodes(wrapper) {
1651    if (wrapper.firstChild_ !== undefined) {
1652      var child = wrapper.firstChild_;
1653      while (child) {
1654        var tmp = child;
1655        child = child.nextSibling_;
1656        tmp.parentNode_ = tmp.previousSibling_ = tmp.nextSibling_ = undefined;
1657      }
1658    }
1659    wrapper.firstChild_ = wrapper.lastChild_ = undefined;
1660  }
1661  function removeAllChildNodes(wrapper) {
1662    if (wrapper.invalidateShadowRenderer()) {
1663      var childWrapper = wrapper.firstChild;
1664      while (childWrapper) {
1665        assert(childWrapper.parentNode === wrapper);
1666        var nextSibling = childWrapper.nextSibling;
1667        var childNode = unwrap(childWrapper);
1668        var parentNode = childNode.parentNode;
1669        if (parentNode) originalRemoveChild.call(parentNode, childNode);
1670        childWrapper.previousSibling_ = childWrapper.nextSibling_ = childWrapper.parentNode_ = null;
1671        childWrapper = nextSibling;
1672      }
1673      wrapper.firstChild_ = wrapper.lastChild_ = null;
1674    } else {
1675      var node = unwrap(wrapper);
1676      var child = node.firstChild;
1677      var nextSibling;
1678      while (child) {
1679        nextSibling = child.nextSibling;
1680        originalRemoveChild.call(node, child);
1681        child = nextSibling;
1682      }
1683    }
1684  }
1685  function invalidateParent(node) {
1686    var p = node.parentNode;
1687    return p && p.invalidateShadowRenderer();
1688  }
1689  function cleanupNodes(nodes) {
1690    for (var i = 0, n; i < nodes.length; i++) {
1691      n = nodes[i];
1692      n.parentNode.removeChild(n);
1693    }
1694  }
1695  var originalImportNode = document.importNode;
1696  var originalCloneNode = window.Node.prototype.cloneNode;
1697  function cloneNode(node, deep, opt_doc) {
1698    var clone;
1699    if (opt_doc) clone = wrap(originalImportNode.call(opt_doc, unsafeUnwrap(node), false)); else clone = wrap(originalCloneNode.call(unsafeUnwrap(node), false));
1700    if (deep) {
1701      for (var child = node.firstChild; child; child = child.nextSibling) {
1702        clone.appendChild(cloneNode(child, true, opt_doc));
1703      }
1704      if (node instanceof wrappers.HTMLTemplateElement) {
1705        var cloneContent = clone.content;
1706        for (var child = node.content.firstChild; child; child = child.nextSibling) {
1707          cloneContent.appendChild(cloneNode(child, true, opt_doc));
1708        }
1709      }
1710    }
1711    return clone;
1712  }
1713  function contains(self, child) {
1714    if (!child || getTreeScope(self) !== getTreeScope(child)) return false;
1715    for (var node = child; node; node = node.parentNode) {
1716      if (node === self) return true;
1717    }
1718    return false;
1719  }
1720  var OriginalNode = window.Node;
1721  function Node(original) {
1722    assert(original instanceof OriginalNode);
1723    EventTarget.call(this, original);
1724    this.parentNode_ = undefined;
1725    this.firstChild_ = undefined;
1726    this.lastChild_ = undefined;
1727    this.nextSibling_ = undefined;
1728    this.previousSibling_ = undefined;
1729    this.treeScope_ = undefined;
1730  }
1731  var OriginalDocumentFragment = window.DocumentFragment;
1732  var originalAppendChild = OriginalNode.prototype.appendChild;
1733  var originalCompareDocumentPosition = OriginalNode.prototype.compareDocumentPosition;
1734  var originalInsertBefore = OriginalNode.prototype.insertBefore;
1735  var originalRemoveChild = OriginalNode.prototype.removeChild;
1736  var originalReplaceChild = OriginalNode.prototype.replaceChild;
1737  var isIe = /Trident|Edge/.test(navigator.userAgent);
1738  var removeChildOriginalHelper = isIe ? function(parent, child) {
1739    try {
1740      originalRemoveChild.call(parent, child);
1741    } catch (ex) {
1742      if (!(parent instanceof OriginalDocumentFragment)) throw ex;
1743    }
1744  } : function(parent, child) {
1745    originalRemoveChild.call(parent, child);
1746  };
1747  Node.prototype = Object.create(EventTarget.prototype);
1748  mixin(Node.prototype, {
1749    appendChild: function(childWrapper) {
1750      return this.insertBefore(childWrapper, null);
1751    },
1752    insertBefore: function(childWrapper, refWrapper) {
1753      assertIsNodeWrapper(childWrapper);
1754      var refNode;
1755      if (refWrapper) {
1756        if (isWrapper(refWrapper)) {
1757          refNode = unwrap(refWrapper);
1758        } else {
1759          refNode = refWrapper;
1760          refWrapper = wrap(refNode);
1761        }
1762      } else {
1763        refWrapper = null;
1764        refNode = null;
1765      }
1766      refWrapper && assert(refWrapper.parentNode === this);
1767      var nodes;
1768      var previousNode = refWrapper ? refWrapper.previousSibling : this.lastChild;
1769      var useNative = !this.invalidateShadowRenderer() && !invalidateParent(childWrapper);
1770      if (useNative) nodes = collectNodesNative(childWrapper); else nodes = collectNodes(childWrapper, this, previousNode, refWrapper);
1771      if (useNative) {
1772        ensureSameOwnerDocument(this, childWrapper);
1773        clearChildNodes(this);
1774        originalInsertBefore.call(unsafeUnwrap(this), unwrap(childWrapper), refNode);
1775      } else {
1776        if (!previousNode) this.firstChild_ = nodes[0];
1777        if (!refWrapper) {
1778          this.lastChild_ = nodes[nodes.length - 1];
1779          if (this.firstChild_ === undefined) this.firstChild_ = this.firstChild;
1780        }
1781        var parentNode = refNode ? refNode.parentNode : unsafeUnwrap(this);
1782        if (parentNode) {
1783          originalInsertBefore.call(parentNode, unwrapNodesForInsertion(this, nodes), refNode);
1784        } else {
1785          adoptNodesIfNeeded(this, nodes);
1786        }
1787      }
1788      enqueueMutation(this, "childList", {
1789        addedNodes: nodes,
1790        nextSibling: refWrapper,
1791        previousSibling: previousNode
1792      });
1793      nodesWereAdded(nodes, this);
1794      return childWrapper;
1795    },
1796    removeChild: function(childWrapper) {
1797      assertIsNodeWrapper(childWrapper);
1798      if (childWrapper.parentNode !== this) {
1799        var found = false;
1800        var childNodes = this.childNodes;
1801        for (var ieChild = this.firstChild; ieChild; ieChild = ieChild.nextSibling) {
1802          if (ieChild === childWrapper) {
1803            found = true;
1804            break;
1805          }
1806        }
1807        if (!found) {
1808          throw new Error("NotFoundError");
1809        }
1810      }
1811      var childNode = unwrap(childWrapper);
1812      var childWrapperNextSibling = childWrapper.nextSibling;
1813      var childWrapperPreviousSibling = childWrapper.previousSibling;
1814      if (this.invalidateShadowRenderer()) {
1815        var thisFirstChild = this.firstChild;
1816        var thisLastChild = this.lastChild;
1817        var parentNode = childNode.parentNode;
1818        if (parentNode) removeChildOriginalHelper(parentNode, childNode);
1819        if (thisFirstChild === childWrapper) this.firstChild_ = childWrapperNextSibling;
1820        if (thisLastChild === childWrapper) this.lastChild_ = childWrapperPreviousSibling;
1821        if (childWrapperPreviousSibling) childWrapperPreviousSibling.nextSibling_ = childWrapperNextSibling;
1822        if (childWrapperNextSibling) {
1823          childWrapperNextSibling.previousSibling_ = childWrapperPreviousSibling;
1824        }
1825        childWrapper.previousSibling_ = childWrapper.nextSibling_ = childWrapper.parentNode_ = undefined;
1826      } else {
1827        clearChildNodes(this);
1828        removeChildOriginalHelper(unsafeUnwrap(this), childNode);
1829      }
1830      if (!surpressMutations) {
1831        enqueueMutation(this, "childList", {
1832          removedNodes: createOneElementNodeList(childWrapper),
1833          nextSibling: childWrapperNextSibling,
1834          previousSibling: childWrapperPreviousSibling
1835        });
1836      }
1837      registerTransientObservers(this, childWrapper);
1838      return childWrapper;
1839    },
1840    replaceChild: function(newChildWrapper, oldChildWrapper) {
1841      assertIsNodeWrapper(newChildWrapper);
1842      var oldChildNode;
1843      if (isWrapper(oldChildWrapper)) {
1844        oldChildNode = unwrap(oldChildWrapper);
1845      } else {
1846        oldChildNode = oldChildWrapper;
1847        oldChildWrapper = wrap(oldChildNode);
1848      }
1849      if (oldChildWrapper.parentNode !== this) {
1850        throw new Error("NotFoundError");
1851      }
1852      var nextNode = oldChildWrapper.nextSibling;
1853      var previousNode = oldChildWrapper.previousSibling;
1854      var nodes;
1855      var useNative = !this.invalidateShadowRenderer() && !invalidateParent(newChildWrapper);
1856      if (useNative) {
1857        nodes = collectNodesNative(newChildWrapper);
1858      } else {
1859        if (nextNode === newChildWrapper) nextNode = newChildWrapper.nextSibling;
1860        nodes = collectNodes(newChildWrapper, this, previousNode, nextNode);
1861      }
1862      if (!useNative) {
1863        if (this.firstChild === oldChildWrapper) this.firstChild_ = nodes[0];
1864        if (this.lastChild === oldChildWrapper) this.lastChild_ = nodes[nodes.length - 1];
1865        oldChildWrapper.previousSibling_ = oldChildWrapper.nextSibling_ = oldChildWrapper.parentNode_ = undefined;
1866        if (oldChildNode.parentNode) {
1867          originalReplaceChild.call(oldChildNode.parentNode, unwrapNodesForInsertion(this, nodes), oldChildNode);
1868        }
1869      } else {
1870        ensureSameOwnerDocument(this, newChildWrapper);
1871        clearChildNodes(this);
1872        originalReplaceChild.call(unsafeUnwrap(this), unwrap(newChildWrapper), oldChildNode);
1873      }
1874      enqueueMutation(this, "childList", {
1875        addedNodes: nodes,
1876        removedNodes: createOneElementNodeList(oldChildWrapper),
1877        nextSibling: nextNode,
1878        previousSibling: previousNode
1879      });
1880      nodeWasRemoved(oldChildWrapper);
1881      nodesWereAdded(nodes, this);
1882      return oldChildWrapper;
1883    },
1884    nodeIsInserted_: function() {
1885      for (var child = this.firstChild; child; child = child.nextSibling) {
1886        child.nodeIsInserted_();
1887      }
1888    },
1889    hasChildNodes: function() {
1890      return this.firstChild !== null;
1891    },
1892    get parentNode() {
1893      return this.parentNode_ !== undefined ? this.parentNode_ : wrap(unsafeUnwrap(this).parentNode);
1894    },
1895    get firstChild() {
1896      return this.firstChild_ !== undefined ? this.firstChild_ : wrap(unsafeUnwrap(this).firstChild);
1897    },
1898    get lastChild() {
1899      return this.lastChild_ !== undefined ? this.lastChild_ : wrap(unsafeUnwrap(this).lastChild);
1900    },
1901    get nextSibling() {
1902      return this.nextSibling_ !== undefined ? this.nextSibling_ : wrap(unsafeUnwrap(this).nextSibling);
1903    },
1904    get previousSibling() {
1905      return this.previousSibling_ !== undefined ? this.previousSibling_ : wrap(unsafeUnwrap(this).previousSibling);
1906    },
1907    get parentElement() {
1908      var p = this.parentNode;
1909      while (p && p.nodeType !== Node.ELEMENT_NODE) {
1910        p = p.parentNode;
1911      }
1912      return p;
1913    },
1914    get textContent() {
1915      var s = "";
1916      for (var child = this.firstChild; child; child = child.nextSibling) {
1917        if (child.nodeType != Node.COMMENT_NODE) {
1918          s += child.textContent;
1919        }
1920      }
1921      return s;
1922    },
1923    set textContent(textContent) {
1924      if (textContent == null) textContent = "";
1925      var removedNodes = snapshotNodeList(this.childNodes);
1926      if (this.invalidateShadowRenderer()) {
1927        removeAllChildNodes(this);
1928        if (textContent !== "") {
1929          var textNode = unsafeUnwrap(this).ownerDocument.createTextNode(textContent);
1930          this.appendChild(textNode);
1931        }
1932      } else {
1933        clearChildNodes(this);
1934        unsafeUnwrap(this).textContent = textContent;
1935      }
1936      var addedNodes = snapshotNodeList(this.childNodes);
1937      enqueueMutation(this, "childList", {
1938        addedNodes: addedNodes,
1939        removedNodes: removedNodes
1940      });
1941      nodesWereRemoved(removedNodes);
1942      nodesWereAdded(addedNodes, this);
1943    },
1944    get childNodes() {
1945      var wrapperList = new NodeList();
1946      var i = 0;
1947      for (var child = this.firstChild; child; child = child.nextSibling) {
1948        wrapperList[i++] = child;
1949      }
1950      wrapperList.length = i;
1951      return wrapperList;
1952    },
1953    cloneNode: function(deep) {
1954      return cloneNode(this, deep);
1955    },
1956    contains: function(child) {
1957      return contains(this, wrapIfNeeded(child));
1958    },
1959    compareDocumentPosition: function(otherNode) {
1960      return originalCompareDocumentPosition.call(unsafeUnwrap(this), unwrapIfNeeded(otherNode));
1961    },
1962    normalize: function() {
1963      var nodes = snapshotNodeList(this.childNodes);
1964      var remNodes = [];
1965      var s = "";
1966      var modNode;
1967      for (var i = 0, n; i < nodes.length; i++) {
1968        n = nodes[i];
1969        if (n.nodeType === Node.TEXT_NODE) {
1970          if (!modNode && !n.data.length) this.removeChild(n); else if (!modNode) modNode = n; else {
1971            s += n.data;
1972            remNodes.push(n);
1973          }
1974        } else {
1975          if (modNode && remNodes.length) {
1976            modNode.data += s;
1977            cleanupNodes(remNodes);
1978          }
1979          remNodes = [];
1980          s = "";
1981          modNode = null;
1982          if (n.childNodes.length) n.normalize();
1983        }
1984      }
1985      if (modNode && remNodes.length) {
1986        modNode.data += s;
1987        cleanupNodes(remNodes);
1988      }
1989    }
1990  });
1991  defineWrapGetter(Node, "ownerDocument");
1992  registerWrapper(OriginalNode, Node, document.createDocumentFragment());
1993  delete Node.prototype.querySelector;
1994  delete Node.prototype.querySelectorAll;
1995  Node.prototype = mixin(Object.create(EventTarget.prototype), Node.prototype);
1996  scope.cloneNode = cloneNode;
1997  scope.nodeWasAdded = nodeWasAdded;
1998  scope.nodeWasRemoved = nodeWasRemoved;
1999  scope.nodesWereAdded = nodesWereAdded;
2000  scope.nodesWereRemoved = nodesWereRemoved;
2001  scope.originalInsertBefore = originalInsertBefore;
2002  scope.originalRemoveChild = originalRemoveChild;
2003  scope.snapshotNodeList = snapshotNodeList;
2004  scope.wrappers.Node = Node;
2005})(window.ShadowDOMPolyfill);
2006
2007(function(scope) {
2008  "use strict";
2009  var HTMLCollection = scope.wrappers.HTMLCollection;
2010  var NodeList = scope.wrappers.NodeList;
2011  var getTreeScope = scope.getTreeScope;
2012  var unsafeUnwrap = scope.unsafeUnwrap;
2013  var wrap = scope.wrap;
2014  var originalDocumentQuerySelector = document.querySelector;
2015  var originalElementQuerySelector = document.documentElement.querySelector;
2016  var originalDocumentQuerySelectorAll = document.querySelectorAll;
2017  var originalElementQuerySelectorAll = document.documentElement.querySelectorAll;
2018  var originalDocumentGetElementsByTagName = document.getElementsByTagName;
2019  var originalElementGetElementsByTagName = document.documentElement.getElementsByTagName;
2020  var originalDocumentGetElementsByTagNameNS = document.getElementsByTagNameNS;
2021  var originalElementGetElementsByTagNameNS = document.documentElement.getElementsByTagNameNS;
2022  var OriginalElement = window.Element;
2023  var OriginalDocument = window.HTMLDocument || window.Document;
2024  function filterNodeList(list, index, result, deep) {
2025    var wrappedItem = null;
2026    var root = null;
2027    for (var i = 0, length = list.length; i < length; i++) {
2028      wrappedItem = wrap(list[i]);
2029      if (!deep && (root = getTreeScope(wrappedItem).root)) {
2030        if (root instanceof scope.wrappers.ShadowRoot) {
2031          continue;
2032        }
2033      }
2034      result[index++] = wrappedItem;
2035    }
2036    return index;
2037  }
2038  function shimSelector(selector) {
2039    return String(selector).replace(/\/deep\/|::shadow/g, " ");
2040  }
2041  function shimMatchesSelector(selector) {
2042    return String(selector).replace(/:host\(([^\s]+)\)/g, "$1").replace(/([^\s]):host/g, "$1").replace(":host", "*").replace(/\^|\/shadow\/|\/shadow-deep\/|::shadow|\/deep\/|::content/g, " ");
2043  }
2044  function findOne(node, selector) {
2045    var m, el = node.firstElementChild;
2046    while (el) {
2047      if (el.matches(selector)) return el;
2048      m = findOne(el, selector);
2049      if (m) return m;
2050      el = el.nextElementSibling;
2051    }
2052    return null;
2053  }
2054  function matchesSelector(el, selector) {
2055    return el.matches(selector);
2056  }
2057  var XHTML_NS = "http://www.w3.org/1999/xhtml";
2058  function matchesTagName(el, localName, localNameLowerCase) {
2059    var ln = el.localName;
2060    return ln === localName || ln === localNameLowerCase && el.namespaceURI === XHTML_NS;
2061  }
2062  function matchesEveryThing() {
2063    return true;
2064  }
2065  function matchesLocalNameOnly(el, ns, localName) {
2066    return el.localName === localName;
2067  }
2068  function matchesNameSpace(el, ns) {
2069    return el.namespaceURI === ns;
2070  }
2071  function matchesLocalNameNS(el, ns, localName) {
2072    return el.namespaceURI === ns && el.localName === localName;
2073  }
2074  function findElements(node, index, result, p, arg0, arg1) {
2075    var el = node.firstElementChild;
2076    while (el) {
2077      if (p(el, arg0, arg1)) result[index++] = el;
2078      index = findElements(el, index, result, p, arg0, arg1);
2079      el = el.nextElementSibling;
2080    }
2081    return index;
2082  }
2083  function querySelectorAllFiltered(p, index, result, selector, deep) {
2084    var target = unsafeUnwrap(this);
2085    var list;
2086    var root = getTreeScope(this).root;
2087    if (root instanceof scope.wrappers.ShadowRoot) {
2088      return findElements(this, index, result, p, selector, null);
2089    } else if (target instanceof OriginalElement) {
2090      list = originalElementQuerySelectorAll.call(target, selector);
2091    } else if (target instanceof OriginalDocument) {
2092      list = originalDocumentQuerySelectorAll.call(target, selector);
2093    } else {
2094      return findElements(this, index, result, p, selector, null);
2095    }
2096    return filterNodeList(list, index, result, deep);
2097  }
2098  var SelectorsInterface = {
2099    querySelector: function(selector) {
2100      var shimmed = shimSelector(selector);
2101      var deep = shimmed !== selector;
2102      selector = shimmed;
2103      var target = unsafeUnwrap(this);
2104      var wrappedItem;
2105      var root = getTreeScope(this).root;
2106      if (root instanceof scope.wrappers.ShadowRoot) {
2107        return findOne(this, selector);
2108      } else if (target instanceof OriginalElement) {
2109        wrappedItem = wrap(originalElementQuerySelector.call(target, selector));
2110      } else if (target instanceof OriginalDocument) {
2111        wrappedItem = wrap(originalDocumentQuerySelector.call(target, selector));
2112      } else {
2113        return findOne(this, selector);
2114      }
2115      if (!wrappedItem) {
2116        return wrappedItem;
2117      } else if (!deep && (root = getTreeScope(wrappedItem).root)) {
2118        if (root instanceof scope.wrappers.ShadowRoot) {
2119          return findOne(this, selector);
2120        }
2121      }
2122      return wrappedItem;
2123    },
2124    querySelectorAll: function(selector) {
2125      var shimmed = shimSelector(selector);
2126      var deep = shimmed !== selector;
2127      selector = shimmed;
2128      var result = new NodeList();
2129      result.length = querySelectorAllFiltered.call(this, matchesSelector, 0, result, selector, deep);
2130      return result;
2131    }
2132  };
2133  var MatchesInterface = {
2134    matches: function(selector) {
2135      selector = shimMatchesSelector(selector);
2136      return scope.originalMatches.call(unsafeUnwrap(this), selector);
2137    }
2138  };
2139  function getElementsByTagNameFiltered(p, index, result, localName, lowercase) {
2140    var target = unsafeUnwrap(this);
2141    var list;
2142    var root = getTreeScope(this).root;
2143    if (root instanceof scope.wrappers.ShadowRoot) {
2144      return findElements(this, index, result, p, localName, lowercase);
2145    } else if (target instanceof OriginalElement) {
2146      list = originalElementGetElementsByTagName.call(target, localName, lowercase);
2147    } else if (target instanceof OriginalDocument) {
2148      list = originalDocumentGetElementsByTagName.call(target, localName, lowercase);
2149    } else {
2150      return findElements(this, index, result, p, localName, lowercase);
2151    }
2152    return filterNodeList(list, index, result, false);
2153  }
2154  function getElementsByTagNameNSFiltered(p, index, result, ns, localName) {
2155    var target = unsafeUnwrap(this);
2156    var list;
2157    var root = getTreeScope(this).root;
2158    if (root instanceof scope.wrappers.ShadowRoot) {
2159      return findElements(this, index, result, p, ns, localName);
2160    } else if (target instanceof OriginalElement) {
2161      list = originalElementGetElementsByTagNameNS.call(target, ns, localName);
2162    } else if (target instanceof OriginalDocument) {
2163      list = originalDocumentGetElementsByTagNameNS.call(target, ns, localName);
2164    } else {
2165      return findElements(this, index, result, p, ns, localName);
2166    }
2167    return filterNodeList(list, index, result, false);
2168  }
2169  var GetElementsByInterface = {
2170    getElementsByTagName: function(localName) {
2171      var result = new HTMLCollection();
2172      var match = localName === "*" ? matchesEveryThing : matchesTagName;
2173      result.length = getElementsByTagNameFiltered.call(this, match, 0, result, localName, localName.toLowerCase());
2174      return result;
2175    },
2176    getElementsByClassName: function(className) {
2177      return this.querySelectorAll("." + className);
2178    },
2179    getElementsByTagNameNS: function(ns, localName) {
2180      var result = new HTMLCollection();
2181      var match = null;
2182      if (ns === "*") {
2183        match = localName === "*" ? matchesEveryThing : matchesLocalNameOnly;
2184      } else {
2185        match = localName === "*" ? matchesNameSpace : matchesLocalNameNS;
2186      }
2187      result.length = getElementsByTagNameNSFiltered.call(this, match, 0, result, ns || null, localName);
2188      return result;
2189    }
2190  };
2191  scope.GetElementsByInterface = GetElementsByInterface;
2192  scope.SelectorsInterface = SelectorsInterface;
2193  scope.MatchesInterface = MatchesInterface;
2194})(window.ShadowDOMPolyfill);
2195
2196(function(scope) {
2197  "use strict";
2198  var NodeList = scope.wrappers.NodeList;
2199  function forwardElement(node) {
2200    while (node && node.nodeType !== Node.ELEMENT_NODE) {
2201      node = node.nextSibling;
2202    }
2203    return node;
2204  }
2205  function backwardsElement(node) {
2206    while (node && node.nodeType !== Node.ELEMENT_NODE) {
2207      node = node.previousSibling;
2208    }
2209    return node;
2210  }
2211  var ParentNodeInterface = {
2212    get firstElementChild() {
2213      return forwardElement(this.firstChild);
2214    },
2215    get lastElementChild() {
2216      return backwardsElement(this.lastChild);
2217    },
2218    get childElementCount() {
2219      var count = 0;
2220      for (var child = this.firstElementChild; child; child = child.nextElementSibling) {
2221        count++;
2222      }
2223      return count;
2224    },
2225    get children() {
2226      var wrapperList = new NodeList();
2227      var i = 0;
2228      for (var child = this.firstElementChild; child; child = child.nextElementSibling) {
2229        wrapperList[i++] = child;
2230      }
2231      wrapperList.length = i;
2232      return wrapperList;
2233    },
2234    remove: function() {
2235      var p = this.parentNode;
2236      if (p) p.removeChild(this);
2237    }
2238  };
2239  var ChildNodeInterface = {
2240    get nextElementSibling() {
2241      return forwardElement(this.nextSibling);
2242    },
2243    get previousElementSibling() {
2244      return backwardsElement(this.previousSibling);
2245    }
2246  };
2247  scope.ChildNodeInterface = ChildNodeInterface;
2248  scope.ParentNodeInterface = ParentNodeInterface;
2249})(window.ShadowDOMPolyfill);
2250
2251(function(scope) {
2252  "use strict";
2253  var ChildNodeInterface = scope.ChildNodeInterface;
2254  var Node = scope.wrappers.Node;
2255  var enqueueMutation = scope.enqueueMutation;
2256  var mixin = scope.mixin;
2257  var registerWrapper = scope.registerWrapper;
2258  var unsafeUnwrap = scope.unsafeUnwrap;
2259  var OriginalCharacterData = window.CharacterData;
2260  function CharacterData(node) {
2261    Node.call(this, node);
2262  }
2263  CharacterData.prototype = Object.create(Node.prototype);
2264  mixin(CharacterData.prototype, {
2265    get textContent() {
2266      return this.data;
2267    },
2268    set textContent(value) {
2269      this.data = value;
2270    },
2271    get data() {
2272      return unsafeUnwrap(this).data;
2273    },
2274    set data(value) {
2275      var oldValue = unsafeUnwrap(this).data;
2276      enqueueMutation(this, "characterData", {
2277        oldValue: oldValue
2278      });
2279      unsafeUnwrap(this).data = value;
2280    }
2281  });
2282  mixin(CharacterData.prototype, ChildNodeInterface);
2283  registerWrapper(OriginalCharacterData, CharacterData, document.createTextNode(""));
2284  scope.wrappers.CharacterData = CharacterData;
2285})(window.ShadowDOMPolyfill);
2286
2287(function(scope) {
2288  "use strict";
2289  var CharacterData = scope.wrappers.CharacterData;
2290  var enqueueMutation = scope.enqueueMutation;
2291  var mixin = scope.mixin;
2292  var registerWrapper = scope.registerWrapper;
2293  function toUInt32(x) {
2294    return x >>> 0;
2295  }
2296  var OriginalText = window.Text;
2297  function Text(node) {
2298    CharacterData.call(this, node);
2299  }
2300  Text.prototype = Object.create(CharacterData.prototype);
2301  mixin(Text.prototype, {
2302    splitText: function(offset) {
2303      offset = toUInt32(offset);
2304      var s = this.data;
2305      if (offset > s.length) throw new Error("IndexSizeError");
2306      var head = s.slice(0, offset);
2307      var tail = s.slice(offset);
2308      this.data = head;
2309      var newTextNode = this.ownerDocument.createTextNode(tail);
2310      if (this.parentNode) this.parentNode.insertBefore(newTextNode, this.nextSibling);
2311      return newTextNode;
2312    }
2313  });
2314  registerWrapper(OriginalText, Text, document.createTextNode(""));
2315  scope.wrappers.Text = Text;
2316})(window.ShadowDOMPolyfill);
2317
2318(function(scope) {
2319  "use strict";
2320  if (!window.DOMTokenList) {
2321    console.warn("Missing DOMTokenList prototype, please include a " + "compatible classList polyfill such as http://goo.gl/uTcepH.");
2322    return;
2323  }
2324  var unsafeUnwrap = scope.unsafeUnwrap;
2325  var enqueueMutation = scope.enqueueMutation;
2326  function getClass(el) {
2327    return unsafeUnwrap(el).getAttribute("class");
2328  }
2329  function enqueueClassAttributeChange(el, oldValue) {
2330    enqueueMutation(el, "attributes", {
2331      name: "class",
2332      namespace: null,
2333      oldValue: oldValue
2334    });
2335  }
2336  function invalidateClass(el) {
2337    scope.invalidateRendererBasedOnAttribute(el, "class");
2338  }
2339  function changeClass(tokenList, method, args) {
2340    var ownerElement = tokenList.ownerElement_;
2341    if (ownerElement == null) {
2342      return method.apply(tokenList, args);
2343    }
2344    var oldValue = getClass(ownerElement);
2345    var retv = method.apply(tokenList, args);
2346    if (getClass(ownerElement) !== oldValue) {
2347      enqueueClassAttributeChange(ownerElement, oldValue);
2348      invalidateClass(ownerElement);
2349    }
2350    return retv;
2351  }
2352  var oldAdd = DOMTokenList.prototype.add;
2353  DOMTokenList.prototype.add = function() {
2354    changeClass(this, oldAdd, arguments);
2355  };
2356  var oldRemove = DOMTokenList.prototype.remove;
2357  DOMTokenList.prototype.remove = function() {
2358    changeClass(this, oldRemove, arguments);
2359  };
2360  var oldToggle = DOMTokenList.prototype.toggle;
2361  DOMTokenList.prototype.toggle = function() {
2362    return changeClass(this, oldToggle, arguments);
2363  };
2364})(window.ShadowDOMPolyfill);
2365
2366(function(scope) {
2367  "use strict";
2368  var ChildNodeInterface = scope.ChildNodeInterface;
2369  var GetElementsByInterface = scope.GetElementsByInterface;
2370  var Node = scope.wrappers.Node;
2371  var ParentNodeInterface = scope.ParentNodeInterface;
2372  var SelectorsInterface = scope.SelectorsInterface;
2373  var MatchesInterface = scope.MatchesInterface;
2374  var addWrapNodeListMethod = scope.addWrapNodeListMethod;
2375  var enqueueMutation = scope.enqueueMutation;
2376  var mixin = scope.mixin;
2377  var oneOf = scope.oneOf;
2378  var registerWrapper = scope.registerWrapper;
2379  var unsafeUnwrap = scope.unsafeUnwrap;
2380  var wrappers = scope.wrappers;
2381  var OriginalElement = window.Element;
2382  var matchesNames = [ "matches", "mozMatchesSelector", "msMatchesSelector", "webkitMatchesSelector" ].filter(function(name) {
2383    return OriginalElement.prototype[name];
2384  });
2385  var matchesName = matchesNames[0];
2386  var originalMatches = OriginalElement.prototype[matchesName];
2387  function invalidateRendererBasedOnAttribute(element, name) {
2388    var p = element.parentNode;
2389    if (!p || !p.shadowRoot) return;
2390    var renderer = scope.getRendererForHost(p);
2391    if (renderer.dependsOnAttribute(name)) renderer.invalidate();
2392  }
2393  function enqueAttributeChange(element, name, oldValue) {
2394    enqueueMutation(element, "attributes", {
2395      name: name,
2396      namespace: null,
2397      oldValue: oldValue
2398    });
2399  }
2400  var classListTable = new WeakMap();
2401  function Element(node) {
2402    Node.call(this, node);
2403  }
2404  Element.prototype = Object.create(Node.prototype);
2405  mixin(Element.prototype, {
2406    createShadowRoot: function() {
2407      var newShadowRoot = new wrappers.ShadowRoot(this);
2408      unsafeUnwrap(this).polymerShadowRoot_ = newShadowRoot;
2409      var renderer = scope.getRendererForHost(this);
2410      renderer.invalidate();
2411      return newShadowRoot;
2412    },
2413    get shadowRoot() {
2414      return unsafeUnwrap(this).polymerShadowRoot_ || null;
2415    },
2416    setAttribute: function(name, value) {
2417      var oldValue = unsafeUnwrap(this).getAttribute(name);
2418      unsafeUnwrap(this).setAttribute(name, value);
2419      enqueAttributeChange(this, name, oldValue);
2420      invalidateRendererBasedOnAttribute(this, name);
2421    },
2422    removeAttribute: function(name) {
2423      var oldValue = unsafeUnwrap(this).getAttribute(name);
2424      unsafeUnwrap(this).removeAttribute(name);
2425      enqueAttributeChange(this, name, oldValue);
2426      invalidateRendererBasedOnAttribute(this, name);
2427    },
2428    get classList() {
2429      var list = classListTable.get(this);
2430      if (!list) {
2431        list = unsafeUnwrap(this).classList;
2432        if (!list) return;
2433        list.ownerElement_ = this;
2434        classListTable.set(this, list);
2435      }
2436      return list;
2437    },
2438    get className() {
2439      return unsafeUnwrap(this).className;
2440    },
2441    set className(v) {
2442      this.setAttribute("class", v);
2443    },
2444    get id() {
2445      return unsafeUnwrap(this).id;
2446    },
2447    set id(v) {
2448      this.setAttribute("id", v);
2449    }
2450  });
2451  matchesNames.forEach(function(name) {
2452    if (name !== "matches") {
2453      Element.prototype[name] = function(selector) {
2454        return this.matches(selector);
2455      };
2456    }
2457  });
2458  if (OriginalElement.prototype.webkitCreateShadowRoot) {
2459    Element.prototype.webkitCreateShadowRoot = Element.prototype.createShadowRoot;
2460  }
2461  mixin(Element.prototype, ChildNodeInterface);
2462  mixin(Element.prototype, GetElementsByInterface);
2463  mixin(Element.prototype, ParentNodeInterface);
2464  mixin(Element.prototype, SelectorsInterface);
2465  mixin(Element.prototype, MatchesInterface);
2466  registerWrapper(OriginalElement, Element, document.createElementNS(null, "x"));
2467  scope.invalidateRendererBasedOnAttribute = invalidateRendererBasedOnAttribute;
2468  scope.matchesNames = matchesNames;
2469  scope.originalMatches = originalMatches;
2470  scope.wrappers.Element = Element;
2471})(window.ShadowDOMPolyfill);
2472
2473(function(scope) {
2474  "use strict";
2475  var Element = scope.wrappers.Element;
2476  var defineGetter = scope.defineGetter;
2477  var enqueueMutation = scope.enqueueMutation;
2478  var mixin = scope.mixin;
2479  var nodesWereAdded = scope.nodesWereAdded;
2480  var nodesWereRemoved = scope.nodesWereRemoved;
2481  var registerWrapper = scope.registerWrapper;
2482  var snapshotNodeList = scope.snapshotNodeList;
2483  var unsafeUnwrap = scope.unsafeUnwrap;
2484  var unwrap = scope.unwrap;
2485  var wrap = scope.wrap;
2486  var wrappers = scope.wrappers;
2487  var escapeAttrRegExp = /[&\u00A0"]/g;
2488  var escapeDataRegExp = /[&\u00A0<>]/g;
2489  function escapeReplace(c) {
2490    switch (c) {
2491     case "&":
2492      return "&amp;";
2493
2494     case "<":
2495      return "&lt;";
2496
2497     case ">":
2498      return "&gt;";
2499
2500     case '"':
2501      return "&quot;";
2502
2503     case " ":
2504      return "&nbsp;";
2505    }
2506  }
2507  function escapeAttr(s) {
2508    return s.replace(escapeAttrRegExp, escapeReplace);
2509  }
2510  function escapeData(s) {
2511    return s.replace(escapeDataRegExp, escapeReplace);
2512  }
2513  function makeSet(arr) {
2514    var set = {};
2515    for (var i = 0; i < arr.length; i++) {
2516      set[arr[i]] = true;
2517    }
2518    return set;
2519  }
2520  var voidElements = makeSet([ "area", "base", "br", "col", "command", "embed", "hr", "img", "input", "keygen", "link", "meta", "param", "source", "track", "wbr" ]);
2521  var plaintextParents = makeSet([ "style", "script", "xmp", "iframe", "noembed", "noframes", "plaintext", "noscript" ]);
2522  function getOuterHTML(node, parentNode) {
2523    switch (node.nodeType) {
2524     case Node.ELEMENT_NODE:
2525      var tagName = node.tagName.toLowerCase();
2526      var s = "<" + tagName;
2527      var attrs = node.attributes;
2528      for (var i = 0, attr; attr = attrs[i]; i++) {
2529        s += " " + attr.name + '="' + escapeAttr(attr.value) + '"';
2530      }
2531      s += ">";
2532      if (voidElements[tagName]) return s;
2533      return s + getInnerHTML(node) + "</" + tagName + ">";
2534
2535     case Node.TEXT_NODE:
2536      var data = node.data;
2537      if (parentNode && plaintextParents[parentNode.localName]) return data;
2538      return escapeData(data);
2539
2540     case Node.COMMENT_NODE:
2541      return "<!--" + node.data + "-->";
2542
2543     default:
2544      console.error(node);
2545      throw new Error("not implemented");
2546    }
2547  }
2548  function getInnerHTML(node) {
2549    if (node instanceof wrappers.HTMLTemplateElement) node = node.content;
2550    var s = "";
2551    for (var child = node.firstChild; child; child = child.nextSibling) {
2552      s += getOuterHTML(child, node);
2553    }
2554    return s;
2555  }
2556  function setInnerHTML(node, value, opt_tagName) {
2557    var tagName = opt_tagName || "div";
2558    node.textContent = "";
2559    var tempElement = unwrap(node.ownerDocument.createElement(tagName));
2560    tempElement.innerHTML = value;
2561    var firstChild;
2562    while (firstChild = tempElement.firstChild) {
2563      node.appendChild(wrap(firstChild));
2564    }
2565  }
2566  var oldIe = /MSIE/.test(navigator.userAgent);
2567  var OriginalHTMLElement = window.HTMLElement;
2568  var OriginalHTMLTemplateElement = window.HTMLTemplateElement;
2569  function HTMLElement(node) {
2570    Element.call(this, node);
2571  }
2572  HTMLElement.prototype = Object.create(Element.prototype);
2573  mixin(HTMLElement.prototype, {
2574    get innerHTML() {
2575      return getInnerHTML(this);
2576    },
2577    set innerHTML(value) {
2578      if (oldIe && plaintextParents[this.localName]) {
2579        this.textContent = value;
2580        return;
2581      }
2582      var removedNodes = snapshotNodeList(this.childNodes);
2583      if (this.invalidateShadowRenderer()) {
2584        if (this instanceof wrappers.HTMLTemplateElement) setInnerHTML(this.content, value); else setInnerHTML(this, value, this.tagName);
2585      } else if (!OriginalHTMLTemplateElement && this instanceof wrappers.HTMLTemplateElement) {
2586        setInnerHTML(this.content, value);
2587      } else {
2588        unsafeUnwrap(this).innerHTML = value;
2589      }
2590      var addedNodes = snapshotNodeList(this.childNodes);
2591      enqueueMutation(this, "childList", {
2592        addedNodes: addedNodes,
2593        removedNodes: removedNodes
2594      });
2595      nodesWereRemoved(removedNodes);
2596      nodesWereAdded(addedNodes, this);
2597    },
2598    get outerHTML() {
2599      return getOuterHTML(this, this.parentNode);
2600    },
2601    set outerHTML(value) {
2602      var p = this.parentNode;
2603      if (p) {
2604        p.invalidateShadowRenderer();
2605        var df = frag(p, value);
2606        p.replaceChild(df, this);
2607      }
2608    },
2609    insertAdjacentHTML: function(position, text) {
2610      var contextElement, refNode;
2611      switch (String(position).toLowerCase()) {
2612       case "beforebegin":
2613        contextElement = this.parentNode;
2614        refNode = this;
2615        break;
2616
2617       case "afterend":
2618        contextElement = this.parentNode;
2619        refNode = this.nextSibling;
2620        break;
2621
2622       case "afterbegin":
2623        contextElement = this;
2624        refNode = this.firstChild;
2625        break;
2626
2627       case "beforeend":
2628        contextElement = this;
2629        refNode = null;
2630        break;
2631
2632       default:
2633        return;
2634      }
2635      var df = frag(contextElement, text);
2636      contextElement.insertBefore(df, refNode);
2637    },
2638    get hidden() {
2639      return this.hasAttribute("hidden");
2640    },
2641    set hidden(v) {
2642      if (v) {
2643        this.setAttribute("hidden", "");
2644      } else {
2645        this.removeAttribute("hidden");
2646      }
2647    }
2648  });
2649  function frag(contextElement, html) {
2650    var p = unwrap(contextElement.cloneNode(false));
2651    p.innerHTML = html;
2652    var df = unwrap(document.createDocumentFragment());
2653    var c;
2654    while (c = p.firstChild) {
2655      df.appendChild(c);
2656    }
2657    return wrap(df);
2658  }
2659  function getter(name) {
2660    return function() {
2661      scope.renderAllPending();
2662      return unsafeUnwrap(this)[name];
2663    };
2664  }
2665  function getterRequiresRendering(name) {
2666    defineGetter(HTMLElement, name, getter(name));
2667  }
2668  [ "clientHeight", "clientLeft", "clientTop", "clientWidth", "offsetHeight", "offsetLeft", "offsetTop", "offsetWidth", "scrollHeight", "scrollWidth" ].forEach(getterRequiresRendering);
2669  function getterAndSetterRequiresRendering(name) {
2670    Object.defineProperty(HTMLElement.prototype, name, {
2671      get: getter(name),
2672      set: function(v) {
2673        scope.renderAllPending();
2674        unsafeUnwrap(this)[name] = v;
2675      },
2676      configurable: true,
2677      enumerable: true
2678    });
2679  }
2680  [ "scrollLeft", "scrollTop" ].forEach(getterAndSetterRequiresRendering);
2681  function methodRequiresRendering(name) {
2682    Object.defineProperty(HTMLElement.prototype, name, {
2683      value: function() {
2684        scope.renderAllPending();
2685        return unsafeUnwrap(this)[name].apply(unsafeUnwrap(this), arguments);
2686      },
2687      configurable: true,
2688      enumerable: true
2689    });
2690  }
2691  [ "getBoundingClientRect", "getClientRects", "scrollIntoView" ].forEach(methodRequiresRendering);
2692  registerWrapper(OriginalHTMLElement, HTMLElement, document.createElement("b"));
2693  scope.wrappers.HTMLElement = HTMLElement;
2694  scope.getInnerHTML = getInnerHTML;
2695  scope.setInnerHTML = setInnerHTML;
2696})(window.ShadowDOMPolyfill);
2697
2698(function(scope) {
2699  "use strict";
2700  var HTMLElement = scope.wrappers.HTMLElement;
2701  var mixin = scope.mixin;
2702  var registerWrapper = scope.registerWrapper;
2703  var unsafeUnwrap = scope.unsafeUnwrap;
2704  var wrap = scope.wrap;
2705  var OriginalHTMLCanvasElement = window.HTMLCanvasElement;
2706  function HTMLCanvasElement(node) {
2707    HTMLElement.call(this, node);
2708  }
2709  HTMLCanvasElement.prototype = Object.create(HTMLElement.prototype);
2710  mixin(HTMLCanvasElement.prototype, {
2711    getContext: function() {
2712      var context = unsafeUnwrap(this).getContext.apply(unsafeUnwrap(this), arguments);
2713      return context && wrap(context);
2714    }
2715  });
2716  registerWrapper(OriginalHTMLCanvasElement, HTMLCanvasElement, document.createElement("canvas"));
2717  scope.wrappers.HTMLCanvasElement = HTMLCanvasElement;
2718})(window.ShadowDOMPolyfill);
2719
2720(function(scope) {
2721  "use strict";
2722  var HTMLElement = scope.wrappers.HTMLElement;
2723  var mixin = scope.mixin;
2724  var registerWrapper = scope.registerWrapper;
2725  var OriginalHTMLContentElement = window.HTMLContentElement;
2726  function HTMLContentElement(node) {
2727    HTMLElement.call(this, node);
2728  }
2729  HTMLContentElement.prototype = Object.create(HTMLElement.prototype);
2730  mixin(HTMLContentElement.prototype, {
2731    constructor: HTMLContentElement,
2732    get select() {
2733      return this.getAttribute("select");
2734    },
2735    set select(value) {
2736      this.setAttribute("select", value);
2737    },
2738    setAttribute: function(n, v) {
2739      HTMLElement.prototype.setAttribute.call(this, n, v);
2740      if (String(n).toLowerCase() === "select") this.invalidateShadowRenderer(true);
2741    }
2742  });
2743  if (OriginalHTMLContentElement) registerWrapper(OriginalHTMLContentElement, HTMLContentElement);
2744  scope.wrappers.HTMLContentElement = HTMLContentElement;
2745})(window.ShadowDOMPolyfill);
2746
2747(function(scope) {
2748  "use strict";
2749  var HTMLElement = scope.wrappers.HTMLElement;
2750  var mixin = scope.mixin;
2751  var registerWrapper = scope.registerWrapper;
2752  var wrapHTMLCollection = scope.wrapHTMLCollection;
2753  var unwrap = scope.unwrap;
2754  var OriginalHTMLFormElement = window.HTMLFormElement;
2755  function HTMLFormElement(node) {
2756    HTMLElement.call(this, node);
2757  }
2758  HTMLFormElement.prototype = Object.create(HTMLElement.prototype);
2759  mixin(HTMLFormElement.prototype, {
2760    get elements() {
2761      return wrapHTMLCollection(unwrap(this).elements);
2762    }
2763  });
2764  registerWrapper(OriginalHTMLFormElement, HTMLFormElement, document.createElement("form"));
2765  scope.wrappers.HTMLFormElement = HTMLFormElement;
2766})(window.ShadowDOMPolyfill);
2767
2768(function(scope) {
2769  "use strict";
2770  var HTMLElement = scope.wrappers.HTMLElement;
2771  var registerWrapper = scope.registerWrapper;
2772  var unwrap = scope.unwrap;
2773  var rewrap = scope.rewrap;
2774  var OriginalHTMLImageElement = window.HTMLImageElement;
2775  function HTMLImageElement(node) {
2776    HTMLElement.call(this, node);
2777  }
2778  HTMLImageElement.prototype = Object.create(HTMLElement.prototype);
2779  registerWrapper(OriginalHTMLImageElement, HTMLImageElement, document.createElement("img"));
2780  function Image(width, height) {
2781    if (!(this instanceof Image)) {
2782      throw new TypeError("DOM object constructor cannot be called as a function.");
2783    }
2784    var node = unwrap(document.createElement("img"));
2785    HTMLElement.call(this, node);
2786    rewrap(node, this);
2787    if (width !== undefined) node.width = width;
2788    if (height !== undefined) node.height = height;
2789  }
2790  Image.prototype = HTMLImageElement.prototype;
2791  scope.wrappers.HTMLImageElement = HTMLImageElement;
2792  scope.wrappers.Image = Image;
2793})(window.ShadowDOMPolyfill);
2794
2795(function(scope) {
2796  "use strict";
2797  var HTMLElement = scope.wrappers.HTMLElement;
2798  var mixin = scope.mixin;
2799  var NodeList = scope.wrappers.NodeList;
2800  var registerWrapper = scope.registerWrapper;
2801  var OriginalHTMLShadowElement = window.HTMLShadowElement;
2802  function HTMLShadowElement(node) {
2803    HTMLElement.call(this, node);
2804  }
2805  HTMLShadowElement.prototype = Object.create(HTMLElement.prototype);
2806  HTMLShadowElement.prototype.constructor = HTMLShadowElement;
2807  if (OriginalHTMLShadowElement) registerWrapper(OriginalHTMLShadowElement, HTMLShadowElement);
2808  scope.wrappers.HTMLShadowElement = HTMLShadowElement;
2809})(window.ShadowDOMPolyfill);
2810
2811(function(scope) {
2812  "use strict";
2813  var HTMLElement = scope.wrappers.HTMLElement;
2814  var mixin = scope.mixin;
2815  var registerWrapper = scope.registerWrapper;
2816  var unsafeUnwrap = scope.unsafeUnwrap;
2817  var unwrap = scope.unwrap;
2818  var wrap = scope.wrap;
2819  var contentTable = new WeakMap();
2820  var templateContentsOwnerTable = new WeakMap();
2821  function getTemplateContentsOwner(doc) {
2822    if (!doc.defaultView) return doc;
2823    var d = templateContentsOwnerTable.get(doc);
2824    if (!d) {
2825      d = doc.implementation.createHTMLDocument("");
2826      while (d.lastChild) {
2827        d.removeChild(d.lastChild);
2828      }
2829      templateContentsOwnerTable.set(doc, d);
2830    }
2831    return d;
2832  }
2833  function extractContent(templateElement) {
2834    var doc = getTemplateContentsOwner(templateElement.ownerDocument);
2835    var df = unwrap(doc.createDocumentFragment());
2836    var child;
2837    while (child = templateElement.firstChild) {
2838      df.appendChild(child);
2839    }
2840    return df;
2841  }
2842  var OriginalHTMLTemplateElement = window.HTMLTemplateElement;
2843  function HTMLTemplateElement(node) {
2844    HTMLElement.call(this, node);
2845    if (!OriginalHTMLTemplateElement) {
2846      var content = extractContent(node);
2847      contentTable.set(this, wrap(content));
2848    }
2849  }
2850  HTMLTemplateElement.prototype = Object.create(HTMLElement.prototype);
2851  mixin(HTMLTemplateElement.prototype, {
2852    constructor: HTMLTemplateElement,
2853    get content() {
2854      if (OriginalHTMLTemplateElement) return wrap(unsafeUnwrap(this).content);
2855      return contentTable.get(this);
2856    }
2857  });
2858  if (OriginalHTMLTemplateElement) registerWrapper(OriginalHTMLTemplateElement, HTMLTemplateElement);
2859  scope.wrappers.HTMLTemplateElement = HTMLTemplateElement;
2860})(window.ShadowDOMPolyfill);
2861
2862(function(scope) {
2863  "use strict";
2864  var HTMLElement = scope.wrappers.HTMLElement;
2865  var registerWrapper = scope.registerWrapper;
2866  var OriginalHTMLMediaElement = window.HTMLMediaElement;
2867  if (!OriginalHTMLMediaElement) return;
2868  function HTMLMediaElement(node) {
2869    HTMLElement.call(this, node);
2870  }
2871  HTMLMediaElement.prototype = Object.create(HTMLElement.prototype);
2872  registerWrapper(OriginalHTMLMediaElement, HTMLMediaElement, document.createElement("audio"));
2873  scope.wrappers.HTMLMediaElement = HTMLMediaElement;
2874})(window.ShadowDOMPolyfill);
2875
2876(function(scope) {
2877  "use strict";
2878  var HTMLMediaElement = scope.wrappers.HTMLMediaElement;
2879  var registerWrapper = scope.registerWrapper;
2880  var unwrap = scope.unwrap;
2881  var rewrap = scope.rewrap;
2882  var OriginalHTMLAudioElement = window.HTMLAudioElement;
2883  if (!OriginalHTMLAudioElement) return;
2884  function HTMLAudioElement(node) {
2885    HTMLMediaElement.call(this, node);
2886  }
2887  HTMLAudioElement.prototype = Object.create(HTMLMediaElement.prototype);
2888  registerWrapper(OriginalHTMLAudioElement, HTMLAudioElement, document.createElement("audio"));
2889  function Audio(src) {
2890    if (!(this instanceof Audio)) {
2891      throw new TypeError("DOM object constructor cannot be called as a function.");
2892    }
2893    var node = unwrap(document.createElement("audio"));
2894    HTMLMediaElement.call(this, node);
2895    rewrap(node, this);
2896    node.setAttribute("preload", "auto");
2897    if (src !== undefined) node.setAttribute("src", src);
2898  }
2899  Audio.prototype = HTMLAudioElement.prototype;
2900  scope.wrappers.HTMLAudioElement = HTMLAudioElement;
2901  scope.wrappers.Audio = Audio;
2902})(window.ShadowDOMPolyfill);
2903
2904(function(scope) {
2905  "use strict";
2906  var HTMLElement = scope.wrappers.HTMLElement;
2907  var mixin = scope.mixin;
2908  var registerWrapper = scope.registerWrapper;
2909  var rewrap = scope.rewrap;
2910  var unwrap = scope.unwrap;
2911  var wrap = scope.wrap;
2912  var OriginalHTMLOptionElement = window.HTMLOptionElement;
2913  function trimText(s) {
2914    return s.replace(/\s+/g, " ").trim();
2915  }
2916  function HTMLOptionElement(node) {
2917    HTMLElement.call(this, node);
2918  }
2919  HTMLOptionElement.prototype = Object.create(HTMLElement.prototype);
2920  mixin(HTMLOptionElement.prototype, {
2921    get text() {
2922      return trimText(this.textContent);
2923    },
2924    set text(value) {
2925      this.textContent = trimText(String(value));
2926    },
2927    get form() {
2928      return wrap(unwrap(this).form);
2929    }
2930  });
2931  registerWrapper(OriginalHTMLOptionElement, HTMLOptionElement, document.createElement("option"));
2932  function Option(text, value, defaultSelected, selected) {
2933    if (!(this instanceof Option)) {
2934      throw new TypeError("DOM object constructor cannot be called as a function.");
2935    }
2936    var node = unwrap(document.createElement("option"));
2937    HTMLElement.call(this, node);
2938    rewrap(node, this);
2939    if (text !== undefined) node.text = text;
2940    if (value !== undefined) node.setAttribute("value", value);
2941    if (defaultSelected === true) node.setAttribute("selected", "");
2942    node.selected = selected === true;
2943  }
2944  Option.prototype = HTMLOptionElement.prototype;
2945  scope.wrappers.HTMLOptionElement = HTMLOptionElement;
2946  scope.wrappers.Option = Option;
2947})(window.ShadowDOMPolyfill);
2948
2949(function(scope) {
2950  "use strict";
2951  var HTMLElement = scope.wrappers.HTMLElement;
2952  var mixin = scope.mixin;
2953  var registerWrapper = scope.registerWrapper;
2954  var unwrap = scope.unwrap;
2955  var wrap = scope.wrap;
2956  var OriginalHTMLSelectElement = window.HTMLSelectElement;
2957  function HTMLSelectElement(node) {
2958    HTMLElement.call(this, node);
2959  }
2960  HTMLSelectElement.prototype = Object.create(HTMLElement.prototype);
2961  mixin(HTMLSelectElement.prototype, {
2962    add: function(element, before) {
2963      if (typeof before === "object") before = unwrap(before);
2964      unwrap(this).add(unwrap(element), before);
2965    },
2966    remove: function(indexOrNode) {
2967      if (indexOrNode === undefined) {
2968        HTMLElement.prototype.remove.call(this);
2969        return;
2970      }
2971      if (typeof indexOrNode === "object") indexOrNode = unwrap(indexOrNode);
2972      unwrap(this).remove(indexOrNode);
2973    },
2974    get form() {
2975      return wrap(unwrap(this).form);
2976    }
2977  });
2978  registerWrapper(OriginalHTMLSelectElement, HTMLSelectElement, document.createElement("select"));
2979  scope.wrappers.HTMLSelectElement = HTMLSelectElement;
2980})(window.ShadowDOMPolyfill);
2981
2982(function(scope) {
2983  "use strict";
2984  var HTMLElement = scope.wrappers.HTMLElement;
2985  var mixin = scope.mixin;
2986  var registerWrapper = scope.registerWrapper;
2987  var unwrap = scope.unwrap;
2988  var wrap = scope.wrap;
2989  var wrapHTMLCollection = scope.wrapHTMLCollection;
2990  var OriginalHTMLTableElement = window.HTMLTableElement;
2991  function HTMLTableElement(node) {
2992    HTMLElement.call(this, node);
2993  }
2994  HTMLTableElement.prototype = Object.create(HTMLElement.prototype);
2995  mixin(HTMLTableElement.prototype, {
2996    get caption() {
2997      return wrap(unwrap(this).caption);
2998    },
2999    createCaption: function() {
3000      return wrap(unwrap(this).createCaption());
3001    },
3002    get tHead() {
3003      return wrap(unwrap(this).tHead);
3004    },
3005    createTHead: function() {
3006      return wrap(unwrap(this).createTHead());
3007    },
3008    createTFoot: function() {
3009      return wrap(unwrap(this).createTFoot());
3010    },
3011    get tFoot() {
3012      return wrap(unwrap(this).tFoot);
3013    },
3014    get tBodies() {
3015      return wrapHTMLCollection(unwrap(this).tBodies);
3016    },
3017    createTBody: function() {
3018      return wrap(unwrap(this).createTBody());
3019    },
3020    get rows() {
3021      return wrapHTMLCollection(unwrap(this).rows);
3022    },
3023    insertRow: function(index) {
3024      return wrap(unwrap(this).insertRow(index));
3025    }
3026  });
3027  registerWrapper(OriginalHTMLTableElement, HTMLTableElement, document.createElement("table"));
3028  scope.wrappers.HTMLTableElement = HTMLTableElement;
3029})(window.ShadowDOMPolyfill);
3030
3031(function(scope) {
3032  "use strict";
3033  var HTMLElement = scope.wrappers.HTMLElement;
3034  var mixin = scope.mixin;
3035  var registerWrapper = scope.registerWrapper;
3036  var wrapHTMLCollection = scope.wrapHTMLCollection;
3037  var unwrap = scope.unwrap;
3038  var wrap = scope.wrap;
3039  var OriginalHTMLTableSectionElement = window.HTMLTableSectionElement;
3040  function HTMLTableSectionElement(node) {
3041    HTMLElement.call(this, node);
3042  }
3043  HTMLTableSectionElement.prototype = Object.create(HTMLElement.prototype);
3044  mixin(HTMLTableSectionElement.prototype, {
3045    constructor: HTMLTableSectionElement,
3046    get rows() {
3047      return wrapHTMLCollection(unwrap(this).rows);
3048    },
3049    insertRow: function(index) {
3050      return wrap(unwrap(this).insertRow(index));
3051    }
3052  });
3053  registerWrapper(OriginalHTMLTableSectionElement, HTMLTableSectionElement, document.createElement("thead"));
3054  scope.wrappers.HTMLTableSectionElement = HTMLTableSectionElement;
3055})(window.ShadowDOMPolyfill);
3056
3057(function(scope) {
3058  "use strict";
3059  var HTMLElement = scope.wrappers.HTMLElement;
3060  var mixin = scope.mixin;
3061  var registerWrapper = scope.registerWrapper;
3062  var wrapHTMLCollection = scope.wrapHTMLCollection;
3063  var unwrap = scope.unwrap;
3064  var wrap = scope.wrap;
3065  var OriginalHTMLTableRowElement = window.HTMLTableRowElement;
3066  function HTMLTableRowElement(node) {
3067    HTMLElement.call(this, node);
3068  }
3069  HTMLTableRowElement.prototype = Object.create(HTMLElement.prototype);
3070  mixin(HTMLTableRowElement.prototype, {
3071    get cells() {
3072      return wrapHTMLCollection(unwrap(this).cells);
3073    },
3074    insertCell: function(index) {
3075      return wrap(unwrap(this).insertCell(index));
3076    }
3077  });
3078  registerWrapper(OriginalHTMLTableRowElement, HTMLTableRowElement, document.createElement("tr"));
3079  scope.wrappers.HTMLTableRowElement = HTMLTableRowElement;
3080})(window.ShadowDOMPolyfill);
3081
3082(function(scope) {
3083  "use strict";
3084  var HTMLContentElement = scope.wrappers.HTMLContentElement;
3085  var HTMLElement = scope.wrappers.HTMLElement;
3086  var HTMLShadowElement = scope.wrappers.HTMLShadowElement;
3087  var HTMLTemplateElement = scope.wrappers.HTMLTemplateElement;
3088  var mixin = scope.mixin;
3089  var registerWrapper = scope.registerWrapper;
3090  var OriginalHTMLUnknownElement = window.HTMLUnknownElement;
3091  function HTMLUnknownElement(node) {
3092    switch (node.localName) {
3093     case "content":
3094      return new HTMLContentElement(node);
3095
3096     case "shadow":
3097      return new HTMLShadowElement(node);
3098
3099     case "template":
3100      return new HTMLTemplateElement(node);
3101    }
3102    HTMLElement.call(this, node);
3103  }
3104  HTMLUnknownElement.prototype = Object.create(HTMLElement.prototype);
3105  registerWrapper(OriginalHTMLUnknownElement, HTMLUnknownElement);
3106  scope.wrappers.HTMLUnknownElement = HTMLUnknownElement;
3107})(window.ShadowDOMPolyfill);
3108
3109(function(scope) {
3110  "use strict";
3111  var Element = scope.wrappers.Element;
3112  var HTMLElement = scope.wrappers.HTMLElement;
3113  var registerObject = scope.registerObject;
3114  var defineWrapGetter = scope.defineWrapGetter;
3115  var SVG_NS = "http://www.w3.org/2000/svg";
3116  var svgTitleElement = document.createElementNS(SVG_NS, "title");
3117  var SVGTitleElement = registerObject(svgTitleElement);
3118  var SVGElement = Object.getPrototypeOf(SVGTitleElement.prototype).constructor;
3119  if (!("classList" in svgTitleElement)) {
3120    var descr = Object.getOwnPropertyDescriptor(Element.prototype, "classList");
3121    Object.defineProperty(HTMLElement.prototype, "classList", descr);
3122    delete Element.prototype.classList;
3123  }
3124  defineWrapGetter(SVGElement, "ownerSVGElement");
3125  scope.wrappers.SVGElement = SVGElement;
3126})(window.ShadowDOMPolyfill);
3127
3128(function(scope) {
3129  "use strict";
3130  var mixin = scope.mixin;
3131  var registerWrapper = scope.registerWrapper;
3132  var unwrap = scope.unwrap;
3133  var wrap = scope.wrap;
3134  var OriginalSVGUseElement = window.SVGUseElement;
3135  var SVG_NS = "http://www.w3.org/2000/svg";
3136  var gWrapper = wrap(document.createElementNS(SVG_NS, "g"));
3137  var useElement = document.createElementNS(SVG_NS, "use");
3138  var SVGGElement = gWrapper.constructor;
3139  var parentInterfacePrototype = Object.getPrototypeOf(SVGGElement.prototype);
3140  var parentInterface = parentInterfacePrototype.constructor;
3141  function SVGUseElement(impl) {
3142    parentInterface.call(this, impl);
3143  }
3144  SVGUseElement.prototype = Object.create(parentInterfacePrototype);
3145  if ("instanceRoot" in useElement) {
3146    mixin(SVGUseElement.prototype, {
3147      get instanceRoot() {
3148        return wrap(unwrap(this).instanceRoot);
3149      },
3150      get animatedInstanceRoot() {
3151        return wrap(unwrap(this).animatedInstanceRoot);
3152      }
3153    });
3154  }
3155  registerWrapper(OriginalSVGUseElement, SVGUseElement, useElement);
3156  scope.wrappers.SVGUseElement = SVGUseElement;
3157})(window.ShadowDOMPolyfill);
3158
3159(function(scope) {
3160  "use strict";
3161  var EventTarget = scope.wrappers.EventTarget;
3162  var mixin = scope.mixin;
3163  var registerWrapper = scope.registerWrapper;
3164  var unsafeUnwrap = scope.unsafeUnwrap;
3165  var wrap = scope.wrap;
3166  var OriginalSVGElementInstance = window.SVGElementInstance;
3167  if (!OriginalSVGElementInstance) return;
3168  function SVGElementInstance(impl) {
3169    EventTarget.call(this, impl);
3170  }
3171  SVGElementInstance.prototype = Object.create(EventTarget.prototype);
3172  mixin(SVGElementInstance.prototype, {
3173    get correspondingElement() {
3174      return wrap(unsafeUnwrap(this).correspondingElement);
3175    },
3176    get correspondingUseElement() {
3177      return wrap(unsafeUnwrap(this).correspondingUseElement);
3178    },
3179    get parentNode() {
3180      return wrap(unsafeUnwrap(this).parentNode);
3181    },
3182    get childNodes() {
3183      throw new Error("Not implemented");
3184    },
3185    get firstChild() {
3186      return wrap(unsafeUnwrap(this).firstChild);
3187    },
3188    get lastChild() {
3189      return wrap(unsafeUnwrap(this).lastChild);
3190    },
3191    get previousSibling() {
3192      return wrap(unsafeUnwrap(this).previousSibling);
3193    },
3194    get nextSibling() {
3195      return wrap(unsafeUnwrap(this).nextSibling);
3196    }
3197  });
3198  registerWrapper(OriginalSVGElementInstance, SVGElementInstance);
3199  scope.wrappers.SVGElementInstance = SVGElementInstance;
3200})(window.ShadowDOMPolyfill);
3201
3202(function(scope) {
3203  "use strict";
3204  var mixin = scope.mixin;
3205  var registerWrapper = scope.registerWrapper;
3206  var setWrapper = scope.setWrapper;
3207  var unsafeUnwrap = scope.unsafeUnwrap;
3208  var unwrap = scope.unwrap;
3209  var unwrapIfNeeded = scope.unwrapIfNeeded;
3210  var wrap = scope.wrap;
3211  var OriginalCanvasRenderingContext2D = window.CanvasRenderingContext2D;
3212  function CanvasRenderingContext2D(impl) {
3213    setWrapper(impl, this);
3214  }
3215  mixin(CanvasRenderingContext2D.prototype, {
3216    get canvas() {
3217      return wrap(unsafeUnwrap(this).canvas);
3218    },
3219    drawImage: function() {
3220      arguments[0] = unwrapIfNeeded(arguments[0]);
3221      unsafeUnwrap(this).drawImage.apply(unsafeUnwrap(this), arguments);
3222    },
3223    createPattern: function() {
3224      arguments[0] = unwrap(arguments[0]);
3225      return unsafeUnwrap(this).createPattern.apply(unsafeUnwrap(this), arguments);
3226    }
3227  });
3228  registerWrapper(OriginalCanvasRenderingContext2D, CanvasRenderingContext2D, document.createElement("canvas").getContext("2d"));
3229  scope.wrappers.CanvasRenderingContext2D = CanvasRenderingContext2D;
3230})(window.ShadowDOMPolyfill);
3231
3232(function(scope) {
3233  "use strict";
3234  var mixin = scope.mixin;
3235  var registerWrapper = scope.registerWrapper;
3236  var setWrapper = scope.setWrapper;
3237  var unsafeUnwrap = scope.unsafeUnwrap;
3238  var unwrapIfNeeded = scope.unwrapIfNeeded;
3239  var wrap = scope.wrap;
3240  var OriginalWebGLRenderingContext = window.WebGLRenderingContext;
3241  if (!OriginalWebGLRenderingContext) return;
3242  function WebGLRenderingContext(impl) {
3243    setWrapper(impl, this);
3244  }
3245  mixin(WebGLRenderingContext.prototype, {
3246    get canvas() {
3247      return wrap(unsafeUnwrap(this).canvas);
3248    },
3249    texImage2D: function() {
3250      arguments[5] = unwrapIfNeeded(arguments[5]);
3251      unsafeUnwrap(this).texImage2D.apply(unsafeUnwrap(this), arguments);
3252    },
3253    texSubImage2D: function() {
3254      arguments[6] = unwrapIfNeeded(arguments[6]);
3255      unsafeUnwrap(this).texSubImage2D.apply(unsafeUnwrap(this), arguments);
3256    }
3257  });
3258  var instanceProperties = /WebKit/.test(navigator.userAgent) ? {
3259    drawingBufferHeight: null,
3260    drawingBufferWidth: null
3261  } : {};
3262  registerWrapper(OriginalWebGLRenderingContext, WebGLRenderingContext, instanceProperties);
3263  scope.wrappers.WebGLRenderingContext = WebGLRenderingContext;
3264})(window.ShadowDOMPolyfill);
3265
3266(function(scope) {
3267  "use strict";
3268  var registerWrapper = scope.registerWrapper;
3269  var setWrapper = scope.setWrapper;
3270  var unsafeUnwrap = scope.unsafeUnwrap;
3271  var unwrap = scope.unwrap;
3272  var unwrapIfNeeded = scope.unwrapIfNeeded;
3273  var wrap = scope.wrap;
3274  var OriginalRange = window.Range;
3275  function Range(impl) {
3276    setWrapper(impl, this);
3277  }
3278  Range.prototype = {
3279    get startContainer() {
3280      return wrap(unsafeUnwrap(this).startContainer);
3281    },
3282    get endContainer() {
3283      return wrap(unsafeUnwrap(this).endContainer);
3284    },
3285    get commonAncestorContainer() {
3286      return wrap(unsafeUnwrap(this).commonAncestorContainer);
3287    },
3288    setStart: function(refNode, offset) {
3289      unsafeUnwrap(this).setStart(unwrapIfNeeded(refNode), offset);
3290    },
3291    setEnd: function(refNode, offset) {
3292      unsafeUnwrap(this).setEnd(unwrapIfNeeded(refNode), offset);
3293    },
3294    setStartBefore: function(refNode) {
3295      unsafeUnwrap(this).setStartBefore(unwrapIfNeeded(refNode));
3296    },
3297    setStartAfter: function(refNode) {
3298      unsafeUnwrap(this).setStartAfter(unwrapIfNeeded(refNode));
3299    },
3300    setEndBefore: function(refNode) {
3301      unsafeUnwrap(this).setEndBefore(unwrapIfNeeded(refNode));
3302    },
3303    setEndAfter: function(refNode) {
3304      unsafeUnwrap(this).setEndAfter(unwrapIfNeeded(refNode));
3305    },
3306    selectNode: function(refNode) {
3307      unsafeUnwrap(this).selectNode(unwrapIfNeeded(refNode));
3308    },
3309    selectNodeContents: function(refNode) {
3310      unsafeUnwrap(this).selectNodeContents(unwrapIfNeeded(refNode));
3311    },
3312    compareBoundaryPoints: function(how, sourceRange) {
3313      return unsafeUnwrap(this).compareBoundaryPoints(how, unwrap(sourceRange));
3314    },
3315    extractContents: function() {
3316      return wrap(unsafeUnwrap(this).extractContents());
3317    },
3318    cloneContents: function() {
3319      return wrap(unsafeUnwrap(this).cloneContents());
3320    },
3321    insertNode: function(node) {
3322      unsafeUnwrap(this).insertNode(unwrapIfNeeded(node));
3323    },
3324    surroundContents: function(newParent) {
3325      unsafeUnwrap(this).surroundContents(unwrapIfNeeded(newParent));
3326    },
3327    cloneRange: function() {
3328      return wrap(unsafeUnwrap(this).cloneRange());
3329    },
3330    isPointInRange: function(node, offset) {
3331      return unsafeUnwrap(this).isPointInRange(unwrapIfNeeded(node), offset);
3332    },
3333    comparePoint: function(node, offset) {
3334      return unsafeUnwrap(this).comparePoint(unwrapIfNeeded(node), offset);
3335    },
3336    intersectsNode: function(node) {
3337      return unsafeUnwrap(this).intersectsNode(unwrapIfNeeded(node));
3338    },
3339    toString: function() {
3340      return unsafeUnwrap(this).toString();
3341    }
3342  };
3343  if (OriginalRange.prototype.createContextualFragment) {
3344    Range.prototype.createContextualFragment = function(html) {
3345      return wrap(unsafeUnwrap(this).createContextualFragment(html));
3346    };
3347  }
3348  registerWrapper(window.Range, Range, document.createRange());
3349  scope.wrappers.Range = Range;
3350})(window.ShadowDOMPolyfill);
3351
3352(function(scope) {
3353  "use strict";
3354  var GetElementsByInterface = scope.GetElementsByInterface;
3355  var ParentNodeInterface = scope.ParentNodeInterface;
3356  var SelectorsInterface = scope.SelectorsInterface;
3357  var mixin = scope.mixin;
3358  var registerObject = scope.registerObject;
3359  var DocumentFragment = registerObject(document.createDocumentFragment());
3360  mixin(DocumentFragment.prototype, ParentNodeInterface);
3361  mixin(DocumentFragment.prototype, SelectorsInterface);
3362  mixin(DocumentFragment.prototype, GetElementsByInterface);
3363  var Comment = registerObject(document.createComment(""));
3364  scope.wrappers.Comment = Comment;
3365  scope.wrappers.DocumentFragment = DocumentFragment;
3366})(window.ShadowDOMPolyfill);
3367
3368(function(scope) {
3369  "use strict";
3370  var DocumentFragment = scope.wrappers.DocumentFragment;
3371  var TreeScope = scope.TreeScope;
3372  var elementFromPoint = scope.elementFromPoint;
3373  var getInnerHTML = scope.getInnerHTML;
3374  var getTreeScope = scope.getTreeScope;
3375  var mixin = scope.mixin;
3376  var rewrap = scope.rewrap;
3377  var setInnerHTML = scope.setInnerHTML;
3378  var unsafeUnwrap = scope.unsafeUnwrap;
3379  var unwrap = scope.unwrap;
3380  var shadowHostTable = new WeakMap();
3381  var nextOlderShadowTreeTable = new WeakMap();
3382  var spaceCharRe = /[ \t\n\r\f]/;
3383  function ShadowRoot(hostWrapper) {
3384    var node = unwrap(unsafeUnwrap(hostWrapper).ownerDocument.createDocumentFragment());
3385    DocumentFragment.call(this, node);
3386    rewrap(node, this);
3387    var oldShadowRoot = hostWrapper.shadowRoot;
3388    nextOlderShadowTreeTable.set(this, oldShadowRoot);
3389    this.treeScope_ = new TreeScope(this, getTreeScope(oldShadowRoot || hostWrapper));
3390    shadowHostTable.set(this, hostWrapper);
3391  }
3392  ShadowRoot.prototype = Object.create(DocumentFragment.prototype);
3393  mixin(ShadowRoot.prototype, {
3394    constructor: ShadowRoot,
3395    get innerHTML() {
3396      return getInnerHTML(this);
3397    },
3398    set innerHTML(value) {
3399      setInnerHTML(this, value);
3400      this.invalidateShadowRenderer();
3401    },
3402    get olderShadowRoot() {
3403      return nextOlderShadowTreeTable.get(this) || null;
3404    },
3405    get host() {
3406      return shadowHostTable.get(this) || null;
3407    },
3408    invalidateShadowRenderer: function() {
3409      return shadowHostTable.get(this).invalidateShadowRenderer();
3410    },
3411    elementFromPoint: function(x, y) {
3412      return elementFromPoint(this, this.ownerDocument, x, y);
3413    },
3414    getElementById: function(id) {
3415      if (spaceCharRe.test(id)) return null;
3416      return this.querySelector('[id="' + id + '"]');
3417    }
3418  });
3419  scope.wrappers.ShadowRoot = ShadowRoot;
3420})(window.ShadowDOMPolyfill);
3421
3422(function(scope) {
3423  "use strict";
3424  var Element = scope.wrappers.Element;
3425  var HTMLContentElement = scope.wrappers.HTMLContentElement;
3426  var HTMLShadowElement = scope.wrappers.HTMLShadowElement;
3427  var Node = scope.wrappers.Node;
3428  var ShadowRoot = scope.wrappers.ShadowRoot;
3429  var assert = scope.assert;
3430  var getTreeScope = scope.getTreeScope;
3431  var mixin = scope.mixin;
3432  var oneOf = scope.oneOf;
3433  var unsafeUnwrap = scope.unsafeUnwrap;
3434  var unwrap = scope.unwrap;
3435  var wrap = scope.wrap;
3436  var ArraySplice = scope.ArraySplice;
3437  function updateWrapperUpAndSideways(wrapper) {
3438    wrapper.previousSibling_ = wrapper.previousSibling;
3439    wrapper.nextSibling_ = wrapper.nextSibling;
3440    wrapper.parentNode_ = wrapper.parentNode;
3441  }
3442  function updateWrapperDown(wrapper) {
3443    wrapper.firstChild_ = wrapper.firstChild;
3444    wrapper.lastChild_ = wrapper.lastChild;
3445  }
3446  function updateAllChildNodes(parentNodeWrapper) {
3447    assert(parentNodeWrapper instanceof Node);
3448    for (var childWrapper = parentNodeWrapper.firstChild; childWrapper; childWrapper = childWrapper.nextSibling) {
3449      updateWrapperUpAndSideways(childWrapper);
3450    }
3451    updateWrapperDown(parentNodeWrapper);
3452  }
3453  function insertBefore(parentNodeWrapper, newChildWrapper, refChildWrapper) {
3454    var parentNode = unwrap(parentNodeWrapper);
3455    var newChild = unwrap(newChildWrapper);
3456    var refChild = refChildWrapper ? unwrap(refChildWrapper) : null;
3457    remove(newChildWrapper);
3458    updateWrapperUpAndSideways(newChildWrapper);
3459    if (!refChildWrapper) {
3460      parentNodeWrapper.lastChild_ = parentNodeWrapper.lastChild;
3461      if (parentNodeWrapper.lastChild === parentNodeWrapper.firstChild) parentNodeWrapper.firstChild_ = parentNodeWrapper.firstChild;
3462      var lastChildWrapper = wrap(parentNode.lastChild);
3463      if (lastChildWrapper) lastChildWrapper.nextSibling_ = lastChildWrapper.nextSibling;
3464    } else {
3465      if (parentNodeWrapper.firstChild === refChildWrapper) parentNodeWrapper.firstChild_ = refChildWrapper;
3466      refChildWrapper.previousSibling_ = refChildWrapper.previousSibling;
3467    }
3468    scope.originalInsertBefore.call(parentNode, newChild, refChild);
3469  }
3470  function remove(nodeWrapper) {
3471    var node = unwrap(nodeWrapper);
3472    var parentNode = node.parentNode;
3473    if (!parentNode) return;
3474    var parentNodeWrapper = wrap(parentNode);
3475    updateWrapperUpAndSideways(nodeWrapper);
3476    if (nodeWrapper.previousSibling) nodeWrapper.previousSibling.nextSibling_ = nodeWrapper;
3477    if (nodeWrapper.nextSibling) nodeWrapper.nextSibling.previousSibling_ = nodeWrapper;
3478    if (parentNodeWrapper.lastChild === nodeWrapper) parentNodeWrapper.lastChild_ = nodeWrapper;
3479    if (parentNodeWrapper.firstChild === nodeWrapper) parentNodeWrapper.firstChild_ = nodeWrapper;
3480    scope.originalRemoveChild.call(parentNode, node);
3481  }
3482  var distributedNodesTable = new WeakMap();
3483  var destinationInsertionPointsTable = new WeakMap();
3484  var rendererForHostTable = new WeakMap();
3485  function resetDistributedNodes(insertionPoint) {
3486    distributedNodesTable.set(insertionPoint, []);
3487  }
3488  function getDistributedNodes(insertionPoint) {
3489    var rv = distributedNodesTable.get(insertionPoint);
3490    if (!rv) distributedNodesTable.set(insertionPoint, rv = []);
3491    return rv;
3492  }
3493  function getChildNodesSnapshot(node) {
3494    var result = [], i = 0;
3495    for (var child = node.firstChild; child; child = child.nextSibling) {
3496      result[i++] = child;
3497    }
3498    return result;
3499  }
3500  var request = oneOf(window, [ "requestAnimationFrame", "mozRequestAnimationFrame", "webkitRequestAnimationFrame", "setTimeout" ]);
3501  var pendingDirtyRenderers = [];
3502  var renderTimer;
3503  function renderAllPending() {
3504    for (var i = 0; i < pendingDirtyRenderers.length; i++) {
3505      var renderer = pendingDirtyRenderers[i];
3506      var parentRenderer = renderer.parentRenderer;
3507      if (parentRenderer && parentRenderer.dirty) continue;
3508      renderer.render();
3509    }
3510    pendingDirtyRenderers = [];
3511  }
3512  function handleRequestAnimationFrame() {
3513    renderTimer = null;
3514    renderAllPending();
3515  }
3516  function getRendererForHost(host) {
3517    var renderer = rendererForHostTable.get(host);
3518    if (!renderer) {
3519      renderer = new ShadowRenderer(host);
3520      rendererForHostTable.set(host, renderer);
3521    }
3522    return renderer;
3523  }
3524  function getShadowRootAncestor(node) {
3525    var root = getTreeScope(node).root;
3526    if (root instanceof ShadowRoot) return root;
3527    return null;
3528  }
3529  function getRendererForShadowRoot(shadowRoot) {
3530    return getRendererForHost(shadowRoot.host);
3531  }
3532  var spliceDiff = new ArraySplice();
3533  spliceDiff.equals = function(renderNode, rawNode) {
3534    return unwrap(renderNode.node) === rawNode;
3535  };
3536  function RenderNode(node) {
3537    this.skip = false;
3538    this.node = node;
3539    this.childNodes = [];
3540  }
3541  RenderNode.prototype = {
3542    append: function(node) {
3543      var rv = new RenderNode(node);
3544      this.childNodes.push(rv);
3545      return rv;
3546    },
3547    sync: function(opt_added) {
3548      if (this.skip) return;
3549      var nodeWrapper = this.node;
3550      var newChildren = this.childNodes;
3551      var oldChildren = getChildNodesSnapshot(unwrap(nodeWrapper));
3552      var added = opt_added || new WeakMap();
3553      var splices = spliceDiff.calculateSplices(newChildren, oldChildren);
3554      var newIndex = 0, oldIndex = 0;
3555      var lastIndex = 0;
3556      for (var i = 0; i < splices.length; i++) {
3557        var splice = splices[i];
3558        for (;lastIndex < splice.index; lastIndex++) {
3559          oldIndex++;
3560          newChildren[newIndex++].sync(added);
3561        }
3562        var removedCount = splice.removed.length;
3563        for (var j = 0; j < removedCount; j++) {
3564          var wrapper = wrap(oldChildren[oldIndex++]);
3565          if (!added.get(wrapper)) remove(wrapper);
3566        }
3567        var addedCount = splice.addedCount;
3568        var refNode = oldChildren[oldIndex] && wrap(oldChildren[oldIndex]);
3569        for (var j = 0; j < addedCount; j++) {
3570          var newChildRenderNode = newChildren[newIndex++];
3571          var newChildWrapper = newChildRenderNode.node;
3572          insertBefore(nodeWrapper, newChildWrapper, refNode);
3573          added.set(newChildWrapper, true);
3574          newChildRenderNode.sync(added);
3575        }
3576        lastIndex += addedCount;
3577      }
3578      for (var i = lastIndex; i < newChildren.length; i++) {
3579        newChildren[i].sync(added);
3580      }
3581    }
3582  };
3583  function ShadowRenderer(host) {
3584    this.host = host;
3585    this.dirty = false;
3586    this.invalidateAttributes();
3587    this.associateNode(host);
3588  }
3589  ShadowRenderer.prototype = {
3590    render: function(opt_renderNode) {
3591      if (!this.dirty) return;
3592      this.invalidateAttributes();
3593      var host = this.host;
3594      this.distribution(host);
3595      var renderNode = opt_renderNode || new RenderNode(host);
3596      this.buildRenderTree(renderNode, host);
3597      var topMostRenderer = !opt_renderNode;
3598      if (topMostRenderer) renderNode.sync();
3599      this.dirty = false;
3600    },
3601    get parentRenderer() {
3602      return getTreeScope(this.host).renderer;
3603    },
3604    invalidate: function() {
3605      if (!this.dirty) {
3606        this.dirty = true;
3607        var parentRenderer = this.parentRenderer;
3608        if (parentRenderer) parentRenderer.invalidate();
3609        pendingDirtyRenderers.push(this);
3610        if (renderTimer) return;
3611        renderTimer = window[request](handleRequestAnimationFrame, 0);
3612      }
3613    },
3614    distribution: function(root) {
3615      this.resetAllSubtrees(root);
3616      this.distributionResolution(root);
3617    },
3618    resetAll: function(node) {
3619      if (isInsertionPoint(node)) resetDistributedNodes(node); else resetDestinationInsertionPoints(node);
3620      this.resetAllSubtrees(node);
3621    },
3622    resetAllSubtrees: function(node) {
3623      for (var child = node.firstChild; child; child = child.nextSibling) {
3624        this.resetAll(child);
3625      }
3626      if (node.shadowRoot) this.resetAll(node.shadowRoot);
3627      if (node.olderShadowRoot) this.resetAll(node.olderShadowRoot);
3628    },
3629    distributionResolution: function(node) {
3630      if (isShadowHost(node)) {
3631        var shadowHost = node;
3632        var pool = poolPopulation(shadowHost);
3633        var shadowTrees = getShadowTrees(shadowHost);
3634        for (var i = 0; i < shadowTrees.length; i++) {
3635          this.poolDistribution(shadowTrees[i], pool);
3636        }
3637        for (var i = shadowTrees.length - 1; i >= 0; i--) {
3638          var shadowTree = shadowTrees[i];
3639          var shadow = getShadowInsertionPoint(shadowTree);
3640          if (shadow) {
3641            var olderShadowRoot = shadowTree.olderShadowRoot;
3642            if (olderShadowRoot) {
3643              pool = poolPopulation(olderShadowRoot);
3644            }
3645            for (var j = 0; j < pool.length; j++) {
3646              destributeNodeInto(pool[j], shadow);
3647            }
3648          }
3649          this.distributionResolution(shadowTree);
3650        }
3651      }
3652      for (var child = node.firstChild; child; child = child.nextSibling) {
3653        this.distributionResolution(child);
3654      }
3655    },
3656    poolDistribution: function(node, pool) {
3657      if (node instanceof HTMLShadowElement) return;
3658      if (node instanceof HTMLContentElement) {
3659        var content = node;
3660        this.updateDependentAttributes(content.getAttribute("select"));
3661        var anyDistributed = false;
3662        for (var i = 0; i < pool.length; i++) {
3663          var node = pool[i];
3664          if (!node) continue;
3665          if (matches(node, content)) {
3666            destributeNodeInto(node, content);
3667            pool[i] = undefined;
3668            anyDistributed = true;
3669          }
3670        }
3671        if (!anyDistributed) {
3672          for (var child = content.firstChild; child; child = child.nextSibling) {
3673            destributeNodeInto(child, content);
3674          }
3675        }
3676        return;
3677      }
3678      for (var child = node.firstChild; child; child = child.nextSibling) {
3679        this.poolDistribution(child, pool);
3680      }
3681    },
3682    buildRenderTree: function(renderNode, node) {
3683      var children = this.compose(node);
3684      for (var i = 0; i < children.length; i++) {
3685        var child = children[i];
3686        var childRenderNode = renderNode.append(child);
3687        this.buildRenderTree(childRenderNode, child);
3688      }
3689      if (isShadowHost(node)) {
3690        var renderer = getRendererForHost(node);
3691        renderer.dirty = false;
3692      }
3693    },
3694    compose: function(node) {
3695      var children = [];
3696      var p = node.shadowRoot || node;
3697      for (var child = p.firstChild; child; child = child.nextSibling) {
3698        if (isInsertionPoint(child)) {
3699          this.associateNode(p);
3700          var distributedNodes = getDistributedNodes(child);
3701          for (var j = 0; j < distributedNodes.length; j++) {
3702            var distributedNode = distributedNodes[j];
3703            if (isFinalDestination(child, distributedNode)) children.push(distributedNode);
3704          }
3705        } else {
3706          children.push(child);
3707        }
3708      }
3709      return children;
3710    },
3711    invalidateAttributes: function() {
3712      this.attributes = Object.create(null);
3713    },
3714    updateDependentAttributes: function(selector) {
3715      if (!selector) return;
3716      var attributes = this.attributes;
3717      if (/\.\w+/.test(selector)) attributes["class"] = true;
3718      if (/#\w+/.test(selector)) attributes["id"] = true;
3719      selector.replace(/\[\s*([^\s=\|~\]]+)/g, function(_, name) {
3720        attributes[name] = true;
3721      });
3722    },
3723    dependsOnAttribute: function(name) {
3724      return this.attributes[name];
3725    },
3726    associateNode: function(node) {
3727      unsafeUnwrap(node).polymerShadowRenderer_ = this;
3728    }
3729  };
3730  function poolPopulation(node) {
3731    var pool = [];
3732    for (var child = node.firstChild; child; child = child.nextSibling) {
3733      if (isInsertionPoint(child)) {
3734        pool.push.apply(pool, getDistributedNodes(child));
3735      } else {
3736        pool.push(child);
3737      }
3738    }
3739    return pool;
3740  }
3741  function getShadowInsertionPoint(node) {
3742    if (node instanceof HTMLShadowElement) return node;
3743    if (node instanceof HTMLContentElement) return null;
3744    for (var child = node.firstChild; child; child = child.nextSibling) {
3745      var res = getShadowInsertionPoint(child);
3746      if (res) return res;
3747    }
3748    return null;
3749  }
3750  function destributeNodeInto(child, insertionPoint) {
3751    getDistributedNodes(insertionPoint).push(child);
3752    var points = destinationInsertionPointsTable.get(child);
3753    if (!points) destinationInsertionPointsTable.set(child, [ insertionPoint ]); else points.push(insertionPoint);
3754  }
3755  function getDestinationInsertionPoints(node) {
3756    return destinationInsertionPointsTable.get(node);
3757  }
3758  function resetDestinationInsertionPoints(node) {
3759    destinationInsertionPointsTable.set(node, undefined);
3760  }
3761  var selectorStartCharRe = /^(:not\()?[*.#[a-zA-Z_|]/;
3762  function matches(node, contentElement) {
3763    var select = contentElement.getAttribute("select");
3764    if (!select) return true;
3765    select = select.trim();
3766    if (!select) return true;
3767    if (!(node instanceof Element)) return false;
3768    if (!selectorStartCharRe.test(select)) return false;
3769    try {
3770      return node.matches(select);
3771    } catch (ex) {
3772      return false;
3773    }
3774  }
3775  function isFinalDestination(insertionPoint, node) {
3776    var points = getDestinationInsertionPoints(node);
3777    return points && points[points.length - 1] === insertionPoint;
3778  }
3779  function isInsertionPoint(node) {
3780    return node instanceof HTMLContentElement || node instanceof HTMLShadowElement;
3781  }
3782  function isShadowHost(shadowHost) {
3783    return shadowHost.shadowRoot;
3784  }
3785  function getShadowTrees(host) {
3786    var trees = [];
3787    for (var tree = host.shadowRoot; tree; tree = tree.olderShadowRoot) {
3788      trees.push(tree);
3789    }
3790    return trees;
3791  }
3792  function render(host) {
3793    new ShadowRenderer(host).render();
3794  }
3795  Node.prototype.invalidateShadowRenderer = function(force) {
3796    var renderer = unsafeUnwrap(this).polymerShadowRenderer_;
3797    if (renderer) {
3798      renderer.invalidate();
3799      return true;
3800    }
3801    return false;
3802  };
3803  HTMLContentElement.prototype.getDistributedNodes = HTMLShadowElement.prototype.getDistributedNodes = function() {
3804    renderAllPending();
3805    return getDistributedNodes(this);
3806  };
3807  Element.prototype.getDestinationInsertionPoints = function() {
3808    renderAllPending();
3809    return getDestinationInsertionPoints(this) || [];
3810  };
3811  HTMLContentElement.prototype.nodeIsInserted_ = HTMLShadowElement.prototype.nodeIsInserted_ = function() {
3812    this.invalidateShadowRenderer();
3813    var shadowRoot = getShadowRootAncestor(this);
3814    var renderer;
3815    if (shadowRoot) renderer = getRendererForShadowRoot(shadowRoot);
3816    unsafeUnwrap(this).polymerShadowRenderer_ = renderer;
3817    if (renderer) renderer.invalidate();
3818  };
3819  scope.getRendererForHost = getRendererForHost;
3820  scope.getShadowTrees = getShadowTrees;
3821  scope.renderAllPending = renderAllPending;
3822  scope.getDestinationInsertionPoints = getDestinationInsertionPoints;
3823  scope.visual = {
3824    insertBefore: insertBefore,
3825    remove: remove
3826  };
3827})(window.ShadowDOMPolyfill);
3828
3829(function(scope) {
3830  "use strict";
3831  var HTMLElement = scope.wrappers.HTMLElement;
3832  var assert = scope.assert;
3833  var mixin = scope.mixin;
3834  var registerWrapper = scope.registerWrapper;
3835  var unwrap = scope.unwrap;
3836  var wrap = scope.wrap;
3837  var elementsWithFormProperty = [ "HTMLButtonElement", "HTMLFieldSetElement", "HTMLInputElement", "HTMLKeygenElement", "HTMLLabelElement", "HTMLLegendElement", "HTMLObjectElement", "HTMLOutputElement", "HTMLTextAreaElement" ];
3838  function createWrapperConstructor(name) {
3839    if (!window[name]) return;
3840    assert(!scope.wrappers[name]);
3841    var GeneratedWrapper = function(node) {
3842      HTMLElement.call(this, node);
3843    };
3844    GeneratedWrapper.prototype = Object.create(HTMLElement.prototype);
3845    mixin(GeneratedWrapper.prototype, {
3846      get form() {
3847        return wrap(unwrap(this).form);
3848      }
3849    });
3850    registerWrapper(window[name], GeneratedWrapper, document.createElement(name.slice(4, -7)));
3851    scope.wrappers[name] = GeneratedWrapper;
3852  }
3853  elementsWithFormProperty.forEach(createWrapperConstructor);
3854})(window.ShadowDOMPolyfill);
3855
3856(function(scope) {
3857  "use strict";
3858  var registerWrapper = scope.registerWrapper;
3859  var setWrapper = scope.setWrapper;
3860  var unsafeUnwrap = scope.unsafeUnwrap;
3861  var unwrap = scope.unwrap;
3862  var unwrapIfNeeded = scope.unwrapIfNeeded;
3863  var wrap = scope.wrap;
3864  var OriginalSelection = window.Selection;
3865  function Selection(impl) {
3866    setWrapper(impl, this);
3867  }
3868  Selection.prototype = {
3869    get anchorNode() {
3870      return wrap(unsafeUnwrap(this).anchorNode);
3871    },
3872    get focusNode() {
3873      return wrap(unsafeUnwrap(this).focusNode);
3874    },
3875    addRange: function(range) {
3876      unsafeUnwrap(this).addRange(unwrap(range));
3877    },
3878    collapse: function(node, index) {
3879      unsafeUnwrap(this).collapse(unwrapIfNeeded(node), index);
3880    },
3881    containsNode: function(node, allowPartial) {
3882      return unsafeUnwrap(this).containsNode(unwrapIfNeeded(node), allowPartial);
3883    },
3884    extend: function(node, offset) {
3885      unsafeUnwrap(this).extend(unwrapIfNeeded(node), offset);
3886    },
3887    getRangeAt: function(index) {
3888      return wrap(unsafeUnwrap(this).getRangeAt(index));
3889    },
3890    removeRange: function(range) {
3891      unsafeUnwrap(this).removeRange(unwrap(range));
3892    },
3893    selectAllChildren: function(node) {
3894      unsafeUnwrap(this).selectAllChildren(unwrapIfNeeded(node));
3895    },
3896    toString: function() {
3897      return unsafeUnwrap(this).toString();
3898    }
3899  };
3900  registerWrapper(window.Selection, Selection, window.getSelection());
3901  scope.wrappers.Selection = Selection;
3902})(window.ShadowDOMPolyfill);
3903
3904(function(scope) {
3905  "use strict";
3906  var GetElementsByInterface = scope.GetElementsByInterface;
3907  var Node = scope.wrappers.Node;
3908  var ParentNodeInterface = scope.ParentNodeInterface;
3909  var Selection = scope.wrappers.Selection;
3910  var SelectorsInterface = scope.SelectorsInterface;
3911  var ShadowRoot = scope.wrappers.ShadowRoot;
3912  var TreeScope = scope.TreeScope;
3913  var cloneNode = scope.cloneNode;
3914  var defineWrapGetter = scope.defineWrapGetter;
3915  var elementFromPoint = scope.elementFromPoint;
3916  var forwardMethodsToWrapper = scope.forwardMethodsToWrapper;
3917  var matchesNames = scope.matchesNames;
3918  var mixin = scope.mixin;
3919  var registerWrapper = scope.registerWrapper;
3920  var renderAllPending = scope.renderAllPending;
3921  var rewrap = scope.rewrap;
3922  var setWrapper = scope.setWrapper;
3923  var unsafeUnwrap = scope.unsafeUnwrap;
3924  var unwrap = scope.unwrap;
3925  var wrap = scope.wrap;
3926  var wrapEventTargetMethods = scope.wrapEventTargetMethods;
3927  var wrapNodeList = scope.wrapNodeList;
3928  var implementationTable = new WeakMap();
3929  function Document(node) {
3930    Node.call(this, node);
3931    this.treeScope_ = new TreeScope(this, null);
3932  }
3933  Document.prototype = Object.create(Node.prototype);
3934  defineWrapGetter(Document, "documentElement");
3935  defineWrapGetter(Document, "body");
3936  defineWrapGetter(Document, "head");
3937  function wrapMethod(name) {
3938    var original = document[name];
3939    Document.prototype[name] = function() {
3940      return wrap(original.apply(unsafeUnwrap(this), arguments));
3941    };
3942  }
3943  [ "createComment", "createDocumentFragment", "createElement", "createElementNS", "createEvent", "createEventNS", "createRange", "createTextNode", "getElementById" ].forEach(wrapMethod);
3944  var originalAdoptNode = document.adoptNode;
3945  function adoptNodeNoRemove(node, doc) {
3946    originalAdoptNode.call(unsafeUnwrap(doc), unwrap(node));
3947    adoptSubtree(node, doc);
3948  }
3949  function adoptSubtree(node, doc) {
3950    if (node.shadowRoot) doc.adoptNode(node.shadowRoot);
3951    if (node instanceof ShadowRoot) adoptOlderShadowRoots(node, doc);
3952    for (var child = node.firstChild; child; child = child.nextSibling) {
3953      adoptSubtree(child, doc);
3954    }
3955  }
3956  function adoptOlderShadowRoots(shadowRoot, doc) {
3957    var oldShadowRoot = shadowRoot.olderShadowRoot;
3958    if (oldShadowRoot) doc.adoptNode(oldShadowRoot);
3959  }
3960  var originalGetSelection = document.getSelection;
3961  mixin(Document.prototype, {
3962    adoptNode: function(node) {
3963      if (node.parentNode) node.parentNode.removeChild(node);
3964      adoptNodeNoRemove(node, this);
3965      return node;
3966    },
3967    elementFromPoint: function(x, y) {
3968      return elementFromPoint(this, this, x, y);
3969    },
3970    importNode: function(node, deep) {
3971      return cloneNode(node, deep, unsafeUnwrap(this));
3972    },
3973    getSelection: function() {
3974      renderAllPending();
3975      return new Selection(originalGetSelection.call(unwrap(this)));
3976    },
3977    getElementsByName: function(name) {
3978      return SelectorsInterface.querySelectorAll.call(this, "[name=" + JSON.stringify(String(name)) + "]");
3979    }
3980  });
3981  if (document.registerElement) {
3982    var originalRegisterElement = document.registerElement;
3983    Document.prototype.registerElement = function(tagName, object) {
3984      var prototype, extendsOption;
3985      if (object !== undefined) {
3986        prototype = object.prototype;
3987        extendsOption = object.extends;
3988      }
3989      if (!prototype) prototype = Object.create(HTMLElement.prototype);
3990      if (scope.nativePrototypeTable.get(prototype)) {
3991        throw new Error("NotSupportedError");
3992      }
3993      var proto = Object.getPrototypeOf(prototype);
3994      var nativePrototype;
3995      var prototypes = [];
3996      while (proto) {
3997        nativePrototype = scope.nativePrototypeTable.get(proto);
3998        if (nativePrototype) break;
3999        prototypes.push(proto);
4000        proto = Object.getPrototypeOf(proto);
4001      }
4002      if (!nativePrototype) {
4003        throw new Error("NotSupportedError");
4004      }
4005      var newPrototype = Object.create(nativePrototype);
4006      for (var i = prototypes.length - 1; i >= 0; i--) {
4007        newPrototype = Object.create(newPrototype);
4008      }
4009      [ "createdCallback", "attachedCallback", "detachedCallback", "attributeChangedCallback" ].forEach(function(name) {
4010        var f = prototype[name];
4011        if (!f) return;
4012        newPrototype[name] = function() {
4013          if (!(wrap(this) instanceof CustomElementConstructor)) {
4014            rewrap(this);
4015          }
4016          f.apply(wrap(this), arguments);
4017        };
4018      });
4019      var p = {
4020        prototype: newPrototype
4021      };
4022      if (extendsOption) p.extends = extendsOption;
4023      function CustomElementConstructor(node) {
4024        if (!node) {
4025          if (extendsOption) {
4026            return document.createElement(extendsOption, tagName);
4027          } else {
4028            return document.createElement(tagName);
4029          }
4030        }
4031        setWrapper(node, this);
4032      }
4033      CustomElementConstructor.prototype = prototype;
4034      CustomElementConstructor.prototype.constructor = CustomElementConstructor;
4035      scope.constructorTable.set(newPrototype, CustomElementConstructor);
4036      scope.nativePrototypeTable.set(prototype, newPrototype);
4037      var nativeConstructor = originalRegisterElement.call(unwrap(this), tagName, p);
4038      return CustomElementConstructor;
4039    };
4040    forwardMethodsToWrapper([ window.HTMLDocument || window.Document ], [ "registerElement" ]);
4041  }
4042  forwardMethodsToWrapper([ window.HTMLBodyElement, window.HTMLDocument || window.Document, window.HTMLHeadElement, window.HTMLHtmlElement ], [ "appendChild", "compareDocumentPosition", "contains", "getElementsByClassName", "getElementsByTagName", "getElementsByTagNameNS", "insertBefore", "querySelector", "querySelectorAll", "removeChild", "replaceChild" ]);
4043  forwardMethodsToWrapper([ window.HTMLBodyElement, window.HTMLHeadElement, window.HTMLHtmlElement ], matchesNames);
4044  forwardMethodsToWrapper([ window.HTMLDocument || window.Document ], [ "adoptNode", "importNode", "contains", "createComment", "createDocumentFragment", "createElement", "createElementNS", "createEvent", "createEventNS", "createRange", "createTextNode", "elementFromPoint", "getElementById", "getElementsByName", "getSelection" ]);
4045  mixin(Document.prototype, GetElementsByInterface);
4046  mixin(Document.prototype, ParentNodeInterface);
4047  mixin(Document.prototype, SelectorsInterface);
4048  mixin(Document.prototype, {
4049    get implementation() {
4050      var implementation = implementationTable.get(this);
4051      if (implementation) return implementation;
4052      implementation = new DOMImplementation(unwrap(this).implementation);
4053      implementationTable.set(this, implementation);
4054      return implementation;
4055    },
4056    get defaultView() {
4057      return wrap(unwrap(this).defaultView);
4058    }
4059  });
4060  registerWrapper(window.Document, Document, document.implementation.createHTMLDocument(""));
4061  if (window.HTMLDocument) registerWrapper(window.HTMLDocument, Document);
4062  wrapEventTargetMethods([ window.HTMLBodyElement, window.HTMLDocument || window.Document, window.HTMLHeadElement ]);
4063  function DOMImplementation(impl) {
4064    setWrapper(impl, this);
4065  }
4066  function wrapImplMethod(constructor, name) {
4067    var original = document.implementation[name];
4068    constructor.prototype[name] = function() {
4069      return wrap(original.apply(unsafeUnwrap(this), arguments));
4070    };
4071  }
4072  function forwardImplMethod(constructor, name) {
4073    var original = document.implementation[name];
4074    constructor.prototype[name] = function() {
4075      return original.apply(unsafeUnwrap(this), arguments);
4076    };
4077  }
4078  wrapImplMethod(DOMImplementation, "createDocumentType");
4079  wrapImplMethod(DOMImplementation, "createDocument");
4080  wrapImplMethod(DOMImplementation, "createHTMLDocument");
4081  forwardImplMethod(DOMImplementation, "hasFeature");
4082  registerWrapper(window.DOMImplementation, DOMImplementation);
4083  forwardMethodsToWrapper([ window.DOMImplementation ], [ "createDocumentType", "createDocument", "createHTMLDocument", "hasFeature" ]);
4084  scope.adoptNodeNoRemove = adoptNodeNoRemove;
4085  scope.wrappers.DOMImplementation = DOMImplementation;
4086  scope.wrappers.Document = Document;
4087})(window.ShadowDOMPolyfill);
4088
4089(function(scope) {
4090  "use strict";
4091  var EventTarget = scope.wrappers.EventTarget;
4092  var Selection = scope.wrappers.Selection;
4093  var mixin = scope.mixin;
4094  var registerWrapper = scope.registerWrapper;
4095  var renderAllPending = scope.renderAllPending;
4096  var unwrap = scope.unwrap;
4097  var unwrapIfNeeded = scope.unwrapIfNeeded;
4098  var wrap = scope.wrap;
4099  var OriginalWindow = window.Window;
4100  var originalGetComputedStyle = window.getComputedStyle;
4101  var originalGetDefaultComputedStyle = window.getDefaultComputedStyle;
4102  var originalGetSelection = window.getSelection;
4103  function Window(impl) {
4104    EventTarget.call(this, impl);
4105  }
4106  Window.prototype = Object.create(EventTarget.prototype);
4107  OriginalWindow.prototype.getComputedStyle = function(el, pseudo) {
4108    return wrap(this || window).getComputedStyle(unwrapIfNeeded(el), pseudo);
4109  };
4110  if (originalGetDefaultComputedStyle) {
4111    OriginalWindow.prototype.getDefaultComputedStyle = function(el, pseudo) {
4112      return wrap(this || window).getDefaultComputedStyle(unwrapIfNeeded(el), pseudo);
4113    };
4114  }
4115  OriginalWindow.prototype.getSelection = function() {
4116    return wrap(this || window).getSelection();
4117  };
4118  delete window.getComputedStyle;
4119  delete window.getDefaultComputedStyle;
4120  delete window.getSelection;
4121  [ "addEventListener", "removeEventListener", "dispatchEvent" ].forEach(function(name) {
4122    OriginalWindow.prototype[name] = function() {
4123      var w = wrap(this || window);
4124      return w[name].apply(w, arguments);
4125    };
4126    delete window[name];
4127  });
4128  mixin(Window.prototype, {
4129    getComputedStyle: function(el, pseudo) {
4130      renderAllPending();
4131      return originalGetComputedStyle.call(unwrap(this), unwrapIfNeeded(el), pseudo);
4132    },
4133    getSelection: function() {
4134      renderAllPending();
4135      return new Selection(originalGetSelection.call(unwrap(this)));
4136    },
4137    get document() {
4138      return wrap(unwrap(this).document);
4139    }
4140  });
4141  if (originalGetDefaultComputedStyle) {
4142    Window.prototype.getDefaultComputedStyle = function(el, pseudo) {
4143      renderAllPending();
4144      return originalGetDefaultComputedStyle.call(unwrap(this), unwrapIfNeeded(el), pseudo);
4145    };
4146  }
4147  registerWrapper(OriginalWindow, Window, window);
4148  scope.wrappers.Window = Window;
4149})(window.ShadowDOMPolyfill);
4150
4151(function(scope) {
4152  "use strict";
4153  var unwrap = scope.unwrap;
4154  var OriginalDataTransfer = window.DataTransfer || window.Clipboard;
4155  var OriginalDataTransferSetDragImage = OriginalDataTransfer.prototype.setDragImage;
4156  if (OriginalDataTransferSetDragImage) {
4157    OriginalDataTransfer.prototype.setDragImage = function(image, x, y) {
4158      OriginalDataTransferSetDragImage.call(this, unwrap(image), x, y);
4159    };
4160  }
4161})(window.ShadowDOMPolyfill);
4162
4163(function(scope) {
4164  "use strict";
4165  var registerWrapper = scope.registerWrapper;
4166  var setWrapper = scope.setWrapper;
4167  var unwrap = scope.unwrap;
4168  var OriginalFormData = window.FormData;
4169  if (!OriginalFormData) return;
4170  function FormData(formElement) {
4171    var impl;
4172    if (formElement instanceof OriginalFormData) {
4173      impl = formElement;
4174    } else {
4175      impl = new OriginalFormData(formElement && unwrap(formElement));
4176    }
4177    setWrapper(impl, this);
4178  }
4179  registerWrapper(OriginalFormData, FormData, new OriginalFormData());
4180  scope.wrappers.FormData = FormData;
4181})(window.ShadowDOMPolyfill);
4182
4183(function(scope) {
4184  "use strict";
4185  var unwrapIfNeeded = scope.unwrapIfNeeded;
4186  var originalSend = XMLHttpRequest.prototype.send;
4187  XMLHttpRequest.prototype.send = function(obj) {
4188    return originalSend.call(this, unwrapIfNeeded(obj));
4189  };
4190})(window.ShadowDOMPolyfill);
4191
4192(function(scope) {
4193  "use strict";
4194  var isWrapperFor = scope.isWrapperFor;
4195  var elements = {
4196    a: "HTMLAnchorElement",
4197    area: "HTMLAreaElement",
4198    audio: "HTMLAudioElement",
4199    base: "HTMLBaseElement",
4200    body: "HTMLBodyElement",
4201    br: "HTMLBRElement",
4202    button: "HTMLButtonElement",
4203    canvas: "HTMLCanvasElement",
4204    caption: "HTMLTableCaptionElement",
4205    col: "HTMLTableColElement",
4206    content: "HTMLContentElement",
4207    data: "HTMLDataElement",
4208    datalist: "HTMLDataListElement",
4209    del: "HTMLModElement",
4210    dir: "HTMLDirectoryElement",
4211    div: "HTMLDivElement",
4212    dl: "HTMLDListElement",
4213    embed: "HTMLEmbedElement",
4214    fieldset: "HTMLFieldSetElement",
4215    font: "HTMLFontElement",
4216    form: "HTMLFormElement",
4217    frame: "HTMLFrameElement",
4218    frameset: "HTMLFrameSetElement",
4219    h1: "HTMLHeadingElement",
4220    head: "HTMLHeadElement",
4221    hr: "HTMLHRElement",
4222    html: "HTMLHtmlElement",
4223    iframe: "HTMLIFrameElement",
4224    img: "HTMLImageElement",
4225    input: "HTMLInputElement",
4226    keygen: "HTMLKeygenElement",
4227    label: "HTMLLabelElement",
4228    legend: "HTMLLegendElement",
4229    li: "HTMLLIElement",
4230    link: "HTMLLinkElement",
4231    map: "HTMLMapElement",
4232    marquee: "HTMLMarqueeElement",
4233    menu: "HTMLMenuElement",
4234    menuitem: "HTMLMenuItemElement",
4235    meta: "HTMLMetaElement",
4236    meter: "HTMLMeterElement",
4237    object: "HTMLObjectElement",
4238    ol: "HTMLOListElement",
4239    optgroup: "HTMLOptGroupElement",
4240    option: "HTMLOptionElement",
4241    output: "HTMLOutputElement",
4242    p: "HTMLParagraphElement",
4243    param: "HTMLParamElement",
4244    pre: "HTMLPreElement",
4245    progress: "HTMLProgressElement",
4246    q: "HTMLQuoteElement",
4247    script: "HTMLScriptElement",
4248    select: "HTMLSelectElement",
4249    shadow: "HTMLShadowElement",
4250    source: "HTMLSourceElement",
4251    span: "HTMLSpanElement",
4252    style: "HTMLStyleElement",
4253    table: "HTMLTableElement",
4254    tbody: "HTMLTableSectionElement",
4255    template: "HTMLTemplateElement",
4256    textarea: "HTMLTextAreaElement",
4257    thead: "HTMLTableSectionElement",
4258    time: "HTMLTimeElement",
4259    title: "HTMLTitleElement",
4260    tr: "HTMLTableRowElement",
4261    track: "HTMLTrackElement",
4262    ul: "HTMLUListElement",
4263    video: "HTMLVideoElement"
4264  };
4265  function overrideConstructor(tagName) {
4266    var nativeConstructorName = elements[tagName];
4267    var nativeConstructor = window[nativeConstructorName];
4268    if (!nativeConstructor) return;
4269    var element = document.createElement(tagName);
4270    var wrapperConstructor = element.constructor;
4271    window[nativeConstructorName] = wrapperConstructor;
4272  }
4273  Object.keys(elements).forEach(overrideConstructor);
4274  Object.getOwnPropertyNames(scope.wrappers).forEach(function(name) {
4275    window[name] = scope.wrappers[name];
4276  });
4277})(window.ShadowDOMPolyfill);