quran-madina-html 0.1.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,4784 @@
1
+ // DOMTokenList polyfill for IE9
2
+ (function () {
3
+
4
+ if (typeof window.Element === "undefined" || "classList" in document.documentElement) return;
5
+
6
+ var prototype = Array.prototype,
7
+ indexOf = prototype.indexOf,
8
+ slice = prototype.slice,
9
+ push = prototype.push,
10
+ splice = prototype.splice,
11
+ join = prototype.join;
12
+
13
+ function DOMTokenList(el) {
14
+ this._element = el;
15
+ if (el.className != this._classCache) {
16
+ this._classCache = el.className;
17
+
18
+ if (!this._classCache) return;
19
+
20
+ // The className needs to be trimmed and split on whitespace
21
+ // to retrieve a list of classes.
22
+ var classes = this._classCache.replace(/^\s+|\s+$/g,'').split(/\s+/),
23
+ i;
24
+ for (i = 0; i < classes.length; i++) {
25
+ push.call(this, classes[i]);
26
+ }
27
+ }
28
+ };
29
+
30
+ function setToClassName(el, classes) {
31
+ el.className = classes.join(' ');
32
+ }
33
+
34
+ DOMTokenList.prototype = {
35
+ add: function(token) {
36
+ if(this.contains(token)) return;
37
+ push.call(this, token);
38
+ setToClassName(this._element, slice.call(this, 0));
39
+ },
40
+ contains: function(token) {
41
+ return indexOf.call(this, token) !== -1;
42
+ },
43
+ item: function(index) {
44
+ return this[index] || null;
45
+ },
46
+ remove: function(token) {
47
+ var i = indexOf.call(this, token);
48
+ if (i === -1) {
49
+ return;
50
+ }
51
+ splice.call(this, i, 1);
52
+ setToClassName(this._element, slice.call(this, 0));
53
+ },
54
+ toString: function() {
55
+ return join.call(this, ' ');
56
+ },
57
+ toggle: function(token) {
58
+ if (indexOf.call(this, token) === -1) {
59
+ this.add(token);
60
+ } else {
61
+ this.remove(token);
62
+ }
63
+ }
64
+ };
65
+
66
+ window.DOMTokenList = DOMTokenList;
67
+
68
+ function defineElementGetter (obj, prop, getter) {
69
+ if (Object.defineProperty) {
70
+ Object.defineProperty(obj, prop,{
71
+ get : getter
72
+ })
73
+ } else {
74
+ obj.__defineGetter__(prop, getter);
75
+ }
76
+ }
77
+
78
+ defineElementGetter(Element.prototype, 'classList', function () {
79
+ return new DOMTokenList(this);
80
+ });
81
+
82
+ })();
83
+
84
+
85
+ /**
86
+ * @license
87
+ * Copyright (c) 2014 The Polymer Project Authors. All rights reserved.
88
+ * This code may only be used under the BSD style license found at http://polymer.github.io/LICENSE.txt
89
+ * The complete set of authors may be found at http://polymer.github.io/AUTHORS.txt
90
+ * The complete set of contributors may be found at http://polymer.github.io/CONTRIBUTORS.txt
91
+ * Code distributed by Google as part of the polymer project is also
92
+ * subject to an additional IP rights grant found at http://polymer.github.io/PATENTS.txt
93
+ */
94
+ // @version 0.7.20
95
+ (function() {
96
+ window.WebComponents = window.WebComponents || {
97
+ flags: {}
98
+ };
99
+ var file = "webcomponents-lite.js";
100
+ var script = document.querySelector('script[src*="' + file + '"]');
101
+ var flags = {};
102
+ if (!flags.noOpts) {
103
+ location.search.slice(1).split("&").forEach(function(option) {
104
+ var parts = option.split("=");
105
+ var match;
106
+ if (parts[0] && (match = parts[0].match(/wc-(.+)/))) {
107
+ flags[match[1]] = parts[1] || true;
108
+ }
109
+ });
110
+ if (script) {
111
+ for (var i = 0, a; a = script.attributes[i]; i++) {
112
+ if (a.name !== "src") {
113
+ flags[a.name] = a.value || true;
114
+ }
115
+ }
116
+ }
117
+ if (flags.log && flags.log.split) {
118
+ var parts = flags.log.split(",");
119
+ flags.log = {};
120
+ parts.forEach(function(f) {
121
+ flags.log[f] = true;
122
+ });
123
+ } else {
124
+ flags.log = {};
125
+ }
126
+ }
127
+ if (flags.register) {
128
+ window.CustomElements = window.CustomElements || {
129
+ flags: {}
130
+ };
131
+ window.CustomElements.flags.register = flags.register;
132
+ }
133
+ WebComponents.flags = flags;
134
+ })();
135
+
136
+ (function(scope) {
137
+ "use strict";
138
+ var hasWorkingUrl = false;
139
+ if (!scope.forceJURL) {
140
+ try {
141
+ var u = new URL("b", "http://a");
142
+ u.pathname = "c%20d";
143
+ hasWorkingUrl = u.href === "http://a/c%20d";
144
+ } catch (e) {}
145
+ }
146
+ if (hasWorkingUrl) return;
147
+ var relative = Object.create(null);
148
+ relative["ftp"] = 21;
149
+ relative["file"] = 0;
150
+ relative["gopher"] = 70;
151
+ relative["http"] = 80;
152
+ relative["https"] = 443;
153
+ relative["ws"] = 80;
154
+ relative["wss"] = 443;
155
+ var relativePathDotMapping = Object.create(null);
156
+ relativePathDotMapping["%2e"] = ".";
157
+ relativePathDotMapping[".%2e"] = "..";
158
+ relativePathDotMapping["%2e."] = "..";
159
+ relativePathDotMapping["%2e%2e"] = "..";
160
+ function isRelativeScheme(scheme) {
161
+ return relative[scheme] !== undefined;
162
+ }
163
+ function invalid() {
164
+ clear.call(this);
165
+ this._isInvalid = true;
166
+ }
167
+ function IDNAToASCII(h) {
168
+ if ("" == h) {
169
+ invalid.call(this);
170
+ }
171
+ return h.toLowerCase();
172
+ }
173
+ function percentEscape(c) {
174
+ var unicode = c.charCodeAt(0);
175
+ if (unicode > 32 && unicode < 127 && [ 34, 35, 60, 62, 63, 96 ].indexOf(unicode) == -1) {
176
+ return c;
177
+ }
178
+ return encodeURIComponent(c);
179
+ }
180
+ function percentEscapeQuery(c) {
181
+ var unicode = c.charCodeAt(0);
182
+ if (unicode > 32 && unicode < 127 && [ 34, 35, 60, 62, 96 ].indexOf(unicode) == -1) {
183
+ return c;
184
+ }
185
+ return encodeURIComponent(c);
186
+ }
187
+ var EOF = undefined, ALPHA = /[a-zA-Z]/, ALPHANUMERIC = /[a-zA-Z0-9\+\-\.]/;
188
+ function parse(input, stateOverride, base) {
189
+ function err(message) {
190
+ errors.push(message);
191
+ }
192
+ var state = stateOverride || "scheme start", cursor = 0, buffer = "", seenAt = false, seenBracket = false, errors = [];
193
+ loop: while ((input[cursor - 1] != EOF || cursor == 0) && !this._isInvalid) {
194
+ var c = input[cursor];
195
+ switch (state) {
196
+ case "scheme start":
197
+ if (c && ALPHA.test(c)) {
198
+ buffer += c.toLowerCase();
199
+ state = "scheme";
200
+ } else if (!stateOverride) {
201
+ buffer = "";
202
+ state = "no scheme";
203
+ continue;
204
+ } else {
205
+ err("Invalid scheme.");
206
+ break loop;
207
+ }
208
+ break;
209
+
210
+ case "scheme":
211
+ if (c && ALPHANUMERIC.test(c)) {
212
+ buffer += c.toLowerCase();
213
+ } else if (":" == c) {
214
+ this._scheme = buffer;
215
+ buffer = "";
216
+ if (stateOverride) {
217
+ break loop;
218
+ }
219
+ if (isRelativeScheme(this._scheme)) {
220
+ this._isRelative = true;
221
+ }
222
+ if ("file" == this._scheme) {
223
+ state = "relative";
224
+ } else if (this._isRelative && base && base._scheme == this._scheme) {
225
+ state = "relative or authority";
226
+ } else if (this._isRelative) {
227
+ state = "authority first slash";
228
+ } else {
229
+ state = "scheme data";
230
+ }
231
+ } else if (!stateOverride) {
232
+ buffer = "";
233
+ cursor = 0;
234
+ state = "no scheme";
235
+ continue;
236
+ } else if (EOF == c) {
237
+ break loop;
238
+ } else {
239
+ err("Code point not allowed in scheme: " + c);
240
+ break loop;
241
+ }
242
+ break;
243
+
244
+ case "scheme data":
245
+ if ("?" == c) {
246
+ this._query = "?";
247
+ state = "query";
248
+ } else if ("#" == c) {
249
+ this._fragment = "#";
250
+ state = "fragment";
251
+ } else {
252
+ if (EOF != c && " " != c && "\n" != c && "\r" != c) {
253
+ this._schemeData += percentEscape(c);
254
+ }
255
+ }
256
+ break;
257
+
258
+ case "no scheme":
259
+ if (!base || !isRelativeScheme(base._scheme)) {
260
+ err("Missing scheme.");
261
+ invalid.call(this);
262
+ } else {
263
+ state = "relative";
264
+ continue;
265
+ }
266
+ break;
267
+
268
+ case "relative or authority":
269
+ if ("/" == c && "/" == input[cursor + 1]) {
270
+ state = "authority ignore slashes";
271
+ } else {
272
+ err("Expected /, got: " + c);
273
+ state = "relative";
274
+ continue;
275
+ }
276
+ break;
277
+
278
+ case "relative":
279
+ this._isRelative = true;
280
+ if ("file" != this._scheme) this._scheme = base._scheme;
281
+ if (EOF == c) {
282
+ this._host = base._host;
283
+ this._port = base._port;
284
+ this._path = base._path.slice();
285
+ this._query = base._query;
286
+ this._username = base._username;
287
+ this._password = base._password;
288
+ break loop;
289
+ } else if ("/" == c || "\\" == c) {
290
+ if ("\\" == c) err("\\ is an invalid code point.");
291
+ state = "relative slash";
292
+ } else if ("?" == c) {
293
+ this._host = base._host;
294
+ this._port = base._port;
295
+ this._path = base._path.slice();
296
+ this._query = "?";
297
+ this._username = base._username;
298
+ this._password = base._password;
299
+ state = "query";
300
+ } else if ("#" == c) {
301
+ this._host = base._host;
302
+ this._port = base._port;
303
+ this._path = base._path.slice();
304
+ this._query = base._query;
305
+ this._fragment = "#";
306
+ this._username = base._username;
307
+ this._password = base._password;
308
+ state = "fragment";
309
+ } else {
310
+ var nextC = input[cursor + 1];
311
+ var nextNextC = input[cursor + 2];
312
+ if ("file" != this._scheme || !ALPHA.test(c) || nextC != ":" && nextC != "|" || EOF != nextNextC && "/" != nextNextC && "\\" != nextNextC && "?" != nextNextC && "#" != nextNextC) {
313
+ this._host = base._host;
314
+ this._port = base._port;
315
+ this._username = base._username;
316
+ this._password = base._password;
317
+ this._path = base._path.slice();
318
+ this._path.pop();
319
+ }
320
+ state = "relative path";
321
+ continue;
322
+ }
323
+ break;
324
+
325
+ case "relative slash":
326
+ if ("/" == c || "\\" == c) {
327
+ if ("\\" == c) {
328
+ err("\\ is an invalid code point.");
329
+ }
330
+ if ("file" == this._scheme) {
331
+ state = "file host";
332
+ } else {
333
+ state = "authority ignore slashes";
334
+ }
335
+ } else {
336
+ if ("file" != this._scheme) {
337
+ this._host = base._host;
338
+ this._port = base._port;
339
+ this._username = base._username;
340
+ this._password = base._password;
341
+ }
342
+ state = "relative path";
343
+ continue;
344
+ }
345
+ break;
346
+
347
+ case "authority first slash":
348
+ if ("/" == c) {
349
+ state = "authority second slash";
350
+ } else {
351
+ err("Expected '/', got: " + c);
352
+ state = "authority ignore slashes";
353
+ continue;
354
+ }
355
+ break;
356
+
357
+ case "authority second slash":
358
+ state = "authority ignore slashes";
359
+ if ("/" != c) {
360
+ err("Expected '/', got: " + c);
361
+ continue;
362
+ }
363
+ break;
364
+
365
+ case "authority ignore slashes":
366
+ if ("/" != c && "\\" != c) {
367
+ state = "authority";
368
+ continue;
369
+ } else {
370
+ err("Expected authority, got: " + c);
371
+ }
372
+ break;
373
+
374
+ case "authority":
375
+ if ("@" == c) {
376
+ if (seenAt) {
377
+ err("@ already seen.");
378
+ buffer += "%40";
379
+ }
380
+ seenAt = true;
381
+ for (var i = 0; i < buffer.length; i++) {
382
+ var cp = buffer[i];
383
+ if (" " == cp || "\n" == cp || "\r" == cp) {
384
+ err("Invalid whitespace in authority.");
385
+ continue;
386
+ }
387
+ if (":" == cp && null === this._password) {
388
+ this._password = "";
389
+ continue;
390
+ }
391
+ var tempC = percentEscape(cp);
392
+ null !== this._password ? this._password += tempC : this._username += tempC;
393
+ }
394
+ buffer = "";
395
+ } else if (EOF == c || "/" == c || "\\" == c || "?" == c || "#" == c) {
396
+ cursor -= buffer.length;
397
+ buffer = "";
398
+ state = "host";
399
+ continue;
400
+ } else {
401
+ buffer += c;
402
+ }
403
+ break;
404
+
405
+ case "file host":
406
+ if (EOF == c || "/" == c || "\\" == c || "?" == c || "#" == c) {
407
+ if (buffer.length == 2 && ALPHA.test(buffer[0]) && (buffer[1] == ":" || buffer[1] == "|")) {
408
+ state = "relative path";
409
+ } else if (buffer.length == 0) {
410
+ state = "relative path start";
411
+ } else {
412
+ this._host = IDNAToASCII.call(this, buffer);
413
+ buffer = "";
414
+ state = "relative path start";
415
+ }
416
+ continue;
417
+ } else if (" " == c || "\n" == c || "\r" == c) {
418
+ err("Invalid whitespace in file host.");
419
+ } else {
420
+ buffer += c;
421
+ }
422
+ break;
423
+
424
+ case "host":
425
+ case "hostname":
426
+ if (":" == c && !seenBracket) {
427
+ this._host = IDNAToASCII.call(this, buffer);
428
+ buffer = "";
429
+ state = "port";
430
+ if ("hostname" == stateOverride) {
431
+ break loop;
432
+ }
433
+ } else if (EOF == c || "/" == c || "\\" == c || "?" == c || "#" == c) {
434
+ this._host = IDNAToASCII.call(this, buffer);
435
+ buffer = "";
436
+ state = "relative path start";
437
+ if (stateOverride) {
438
+ break loop;
439
+ }
440
+ continue;
441
+ } else if (" " != c && "\n" != c && "\r" != c) {
442
+ if ("[" == c) {
443
+ seenBracket = true;
444
+ } else if ("]" == c) {
445
+ seenBracket = false;
446
+ }
447
+ buffer += c;
448
+ } else {
449
+ err("Invalid code point in host/hostname: " + c);
450
+ }
451
+ break;
452
+
453
+ case "port":
454
+ if (/[0-9]/.test(c)) {
455
+ buffer += c;
456
+ } else if (EOF == c || "/" == c || "\\" == c || "?" == c || "#" == c || stateOverride) {
457
+ if ("" != buffer) {
458
+ var temp = parseInt(buffer, 10);
459
+ if (temp != relative[this._scheme]) {
460
+ this._port = temp + "";
461
+ }
462
+ buffer = "";
463
+ }
464
+ if (stateOverride) {
465
+ break loop;
466
+ }
467
+ state = "relative path start";
468
+ continue;
469
+ } else if (" " == c || "\n" == c || "\r" == c) {
470
+ err("Invalid code point in port: " + c);
471
+ } else {
472
+ invalid.call(this);
473
+ }
474
+ break;
475
+
476
+ case "relative path start":
477
+ if ("\\" == c) err("'\\' not allowed in path.");
478
+ state = "relative path";
479
+ if ("/" != c && "\\" != c) {
480
+ continue;
481
+ }
482
+ break;
483
+
484
+ case "relative path":
485
+ if (EOF == c || "/" == c || "\\" == c || !stateOverride && ("?" == c || "#" == c)) {
486
+ if ("\\" == c) {
487
+ err("\\ not allowed in relative path.");
488
+ }
489
+ var tmp;
490
+ if (tmp = relativePathDotMapping[buffer.toLowerCase()]) {
491
+ buffer = tmp;
492
+ }
493
+ if (".." == buffer) {
494
+ this._path.pop();
495
+ if ("/" != c && "\\" != c) {
496
+ this._path.push("");
497
+ }
498
+ } else if ("." == buffer && "/" != c && "\\" != c) {
499
+ this._path.push("");
500
+ } else if ("." != buffer) {
501
+ if ("file" == this._scheme && this._path.length == 0 && buffer.length == 2 && ALPHA.test(buffer[0]) && buffer[1] == "|") {
502
+ buffer = buffer[0] + ":";
503
+ }
504
+ this._path.push(buffer);
505
+ }
506
+ buffer = "";
507
+ if ("?" == c) {
508
+ this._query = "?";
509
+ state = "query";
510
+ } else if ("#" == c) {
511
+ this._fragment = "#";
512
+ state = "fragment";
513
+ }
514
+ } else if (" " != c && "\n" != c && "\r" != c) {
515
+ buffer += percentEscape(c);
516
+ }
517
+ break;
518
+
519
+ case "query":
520
+ if (!stateOverride && "#" == c) {
521
+ this._fragment = "#";
522
+ state = "fragment";
523
+ } else if (EOF != c && " " != c && "\n" != c && "\r" != c) {
524
+ this._query += percentEscapeQuery(c);
525
+ }
526
+ break;
527
+
528
+ case "fragment":
529
+ if (EOF != c && " " != c && "\n" != c && "\r" != c) {
530
+ this._fragment += c;
531
+ }
532
+ break;
533
+ }
534
+ cursor++;
535
+ }
536
+ }
537
+ function clear() {
538
+ this._scheme = "";
539
+ this._schemeData = "";
540
+ this._username = "";
541
+ this._password = null;
542
+ this._host = "";
543
+ this._port = "";
544
+ this._path = [];
545
+ this._query = "";
546
+ this._fragment = "";
547
+ this._isInvalid = false;
548
+ this._isRelative = false;
549
+ }
550
+ function jURL(url, base) {
551
+ if (base !== undefined && !(base instanceof jURL)) base = new jURL(String(base));
552
+ this._url = url;
553
+ clear.call(this);
554
+ var input = url.replace(/^[ \t\r\n\f]+|[ \t\r\n\f]+$/g, "");
555
+ parse.call(this, input, null, base);
556
+ }
557
+ jURL.prototype = {
558
+ toString: function() {
559
+ return this.href;
560
+ },
561
+ get href() {
562
+ if (this._isInvalid) return this._url;
563
+ var authority = "";
564
+ if ("" != this._username || null != this._password) {
565
+ authority = this._username + (null != this._password ? ":" + this._password : "") + "@";
566
+ }
567
+ return this.protocol + (this._isRelative ? "//" + authority + this.host : "") + this.pathname + this._query + this._fragment;
568
+ },
569
+ set href(href) {
570
+ clear.call(this);
571
+ parse.call(this, href);
572
+ },
573
+ get protocol() {
574
+ return this._scheme + ":";
575
+ },
576
+ set protocol(protocol) {
577
+ if (this._isInvalid) return;
578
+ parse.call(this, protocol + ":", "scheme start");
579
+ },
580
+ get host() {
581
+ return this._isInvalid ? "" : this._port ? this._host + ":" + this._port : this._host;
582
+ },
583
+ set host(host) {
584
+ if (this._isInvalid || !this._isRelative) return;
585
+ parse.call(this, host, "host");
586
+ },
587
+ get hostname() {
588
+ return this._host;
589
+ },
590
+ set hostname(hostname) {
591
+ if (this._isInvalid || !this._isRelative) return;
592
+ parse.call(this, hostname, "hostname");
593
+ },
594
+ get port() {
595
+ return this._port;
596
+ },
597
+ set port(port) {
598
+ if (this._isInvalid || !this._isRelative) return;
599
+ parse.call(this, port, "port");
600
+ },
601
+ get pathname() {
602
+ return this._isInvalid ? "" : this._isRelative ? "/" + this._path.join("/") : this._schemeData;
603
+ },
604
+ set pathname(pathname) {
605
+ if (this._isInvalid || !this._isRelative) return;
606
+ this._path = [];
607
+ parse.call(this, pathname, "relative path start");
608
+ },
609
+ get search() {
610
+ return this._isInvalid || !this._query || "?" == this._query ? "" : this._query;
611
+ },
612
+ set search(search) {
613
+ if (this._isInvalid || !this._isRelative) return;
614
+ this._query = "?";
615
+ if ("?" == search[0]) search = search.slice(1);
616
+ parse.call(this, search, "query");
617
+ },
618
+ get hash() {
619
+ return this._isInvalid || !this._fragment || "#" == this._fragment ? "" : this._fragment;
620
+ },
621
+ set hash(hash) {
622
+ if (this._isInvalid) return;
623
+ this._fragment = "#";
624
+ if ("#" == hash[0]) hash = hash.slice(1);
625
+ parse.call(this, hash, "fragment");
626
+ },
627
+ get origin() {
628
+ var host;
629
+ if (this._isInvalid || !this._scheme) {
630
+ return "";
631
+ }
632
+ switch (this._scheme) {
633
+ case "data":
634
+ case "file":
635
+ case "javascript":
636
+ case "mailto":
637
+ return "null";
638
+ }
639
+ host = this.host;
640
+ if (!host) {
641
+ return "";
642
+ }
643
+ return this._scheme + "://" + host;
644
+ }
645
+ };
646
+ var OriginalURL = scope.URL;
647
+ if (OriginalURL) {
648
+ jURL.createObjectURL = function(blob) {
649
+ return OriginalURL.createObjectURL.apply(OriginalURL, arguments);
650
+ };
651
+ jURL.revokeObjectURL = function(url) {
652
+ OriginalURL.revokeObjectURL(url);
653
+ };
654
+ }
655
+ scope.URL = jURL;
656
+ })(self);
657
+
658
+ if (typeof WeakMap === "undefined") {
659
+ (function() {
660
+ var defineProperty = Object.defineProperty;
661
+ var counter = Date.now() % 1e9;
662
+ var WeakMap = function() {
663
+ this.name = "__st" + (Math.random() * 1e9 >>> 0) + (counter++ + "__");
664
+ };
665
+ WeakMap.prototype = {
666
+ set: function(key, value) {
667
+ var entry = key[this.name];
668
+ if (entry && entry[0] === key) entry[1] = value; else defineProperty(key, this.name, {
669
+ value: [ key, value ],
670
+ writable: true
671
+ });
672
+ return this;
673
+ },
674
+ get: function(key) {
675
+ var entry;
676
+ return (entry = key[this.name]) && entry[0] === key ? entry[1] : undefined;
677
+ },
678
+ "delete": function(key) {
679
+ var entry = key[this.name];
680
+ if (!entry || entry[0] !== key) return false;
681
+ entry[0] = entry[1] = undefined;
682
+ return true;
683
+ },
684
+ has: function(key) {
685
+ var entry = key[this.name];
686
+ if (!entry) return false;
687
+ return entry[0] === key;
688
+ }
689
+ };
690
+ window.WeakMap = WeakMap;
691
+ })();
692
+ }
693
+
694
+ (function(global) {
695
+ if (global.JsMutationObserver) {
696
+ return;
697
+ }
698
+ var registrationsTable = new WeakMap();
699
+ var setImmediate;
700
+ if (/Trident|Edge/.test(navigator.userAgent)) {
701
+ setImmediate = setTimeout;
702
+ } else if (window.setImmediate) {
703
+ setImmediate = window.setImmediate;
704
+ } else {
705
+ var setImmediateQueue = [];
706
+ var sentinel = String(Math.random());
707
+ window.addEventListener("message", function(e) {
708
+ if (e.data === sentinel) {
709
+ var queue = setImmediateQueue;
710
+ setImmediateQueue = [];
711
+ queue.forEach(function(func) {
712
+ func();
713
+ });
714
+ }
715
+ });
716
+ setImmediate = function(func) {
717
+ setImmediateQueue.push(func);
718
+ window.postMessage(sentinel, "*");
719
+ };
720
+ }
721
+ var isScheduled = false;
722
+ var scheduledObservers = [];
723
+ function scheduleCallback(observer) {
724
+ scheduledObservers.push(observer);
725
+ if (!isScheduled) {
726
+ isScheduled = true;
727
+ setImmediate(dispatchCallbacks);
728
+ }
729
+ }
730
+ function wrapIfNeeded(node) {
731
+ return window.ShadowDOMPolyfill && window.ShadowDOMPolyfill.wrapIfNeeded(node) || node;
732
+ }
733
+ function dispatchCallbacks() {
734
+ isScheduled = false;
735
+ var observers = scheduledObservers;
736
+ scheduledObservers = [];
737
+ observers.sort(function(o1, o2) {
738
+ return o1.uid_ - o2.uid_;
739
+ });
740
+ var anyNonEmpty = false;
741
+ observers.forEach(function(observer) {
742
+ var queue = observer.takeRecords();
743
+ removeTransientObserversFor(observer);
744
+ if (queue.length) {
745
+ observer.callback_(queue, observer);
746
+ anyNonEmpty = true;
747
+ }
748
+ });
749
+ if (anyNonEmpty) dispatchCallbacks();
750
+ }
751
+ function removeTransientObserversFor(observer) {
752
+ observer.nodes_.forEach(function(node) {
753
+ var registrations = registrationsTable.get(node);
754
+ if (!registrations) return;
755
+ registrations.forEach(function(registration) {
756
+ if (registration.observer === observer) registration.removeTransientObservers();
757
+ });
758
+ });
759
+ }
760
+ function forEachAncestorAndObserverEnqueueRecord(target, callback) {
761
+ for (var node = target; node; node = node.parentNode) {
762
+ var registrations = registrationsTable.get(node);
763
+ if (registrations) {
764
+ for (var j = 0; j < registrations.length; j++) {
765
+ var registration = registrations[j];
766
+ var options = registration.options;
767
+ if (node !== target && !options.subtree) continue;
768
+ var record = callback(options);
769
+ if (record) registration.enqueue(record);
770
+ }
771
+ }
772
+ }
773
+ }
774
+ var uidCounter = 0;
775
+ function JsMutationObserver(callback) {
776
+ this.callback_ = callback;
777
+ this.nodes_ = [];
778
+ this.records_ = [];
779
+ this.uid_ = ++uidCounter;
780
+ }
781
+ JsMutationObserver.prototype = {
782
+ observe: function(target, options) {
783
+ target = wrapIfNeeded(target);
784
+ if (!options.childList && !options.attributes && !options.characterData || options.attributeOldValue && !options.attributes || options.attributeFilter && options.attributeFilter.length && !options.attributes || options.characterDataOldValue && !options.characterData) {
785
+ throw new SyntaxError();
786
+ }
787
+ var registrations = registrationsTable.get(target);
788
+ if (!registrations) registrationsTable.set(target, registrations = []);
789
+ var registration;
790
+ for (var i = 0; i < registrations.length; i++) {
791
+ if (registrations[i].observer === this) {
792
+ registration = registrations[i];
793
+ registration.removeListeners();
794
+ registration.options = options;
795
+ break;
796
+ }
797
+ }
798
+ if (!registration) {
799
+ registration = new Registration(this, target, options);
800
+ registrations.push(registration);
801
+ this.nodes_.push(target);
802
+ }
803
+ registration.addListeners();
804
+ },
805
+ disconnect: function() {
806
+ this.nodes_.forEach(function(node) {
807
+ var registrations = registrationsTable.get(node);
808
+ for (var i = 0; i < registrations.length; i++) {
809
+ var registration = registrations[i];
810
+ if (registration.observer === this) {
811
+ registration.removeListeners();
812
+ registrations.splice(i, 1);
813
+ break;
814
+ }
815
+ }
816
+ }, this);
817
+ this.records_ = [];
818
+ },
819
+ takeRecords: function() {
820
+ var copyOfRecords = this.records_;
821
+ this.records_ = [];
822
+ return copyOfRecords;
823
+ }
824
+ };
825
+ function MutationRecord(type, target) {
826
+ this.type = type;
827
+ this.target = target;
828
+ this.addedNodes = [];
829
+ this.removedNodes = [];
830
+ this.previousSibling = null;
831
+ this.nextSibling = null;
832
+ this.attributeName = null;
833
+ this.attributeNamespace = null;
834
+ this.oldValue = null;
835
+ }
836
+ function copyMutationRecord(original) {
837
+ var record = new MutationRecord(original.type, original.target);
838
+ record.addedNodes = original.addedNodes.slice();
839
+ record.removedNodes = original.removedNodes.slice();
840
+ record.previousSibling = original.previousSibling;
841
+ record.nextSibling = original.nextSibling;
842
+ record.attributeName = original.attributeName;
843
+ record.attributeNamespace = original.attributeNamespace;
844
+ record.oldValue = original.oldValue;
845
+ return record;
846
+ }
847
+ var currentRecord, recordWithOldValue;
848
+ function getRecord(type, target) {
849
+ return currentRecord = new MutationRecord(type, target);
850
+ }
851
+ function getRecordWithOldValue(oldValue) {
852
+ if (recordWithOldValue) return recordWithOldValue;
853
+ recordWithOldValue = copyMutationRecord(currentRecord);
854
+ recordWithOldValue.oldValue = oldValue;
855
+ return recordWithOldValue;
856
+ }
857
+ function clearRecords() {
858
+ currentRecord = recordWithOldValue = undefined;
859
+ }
860
+ function recordRepresentsCurrentMutation(record) {
861
+ return record === recordWithOldValue || record === currentRecord;
862
+ }
863
+ function selectRecord(lastRecord, newRecord) {
864
+ if (lastRecord === newRecord) return lastRecord;
865
+ if (recordWithOldValue && recordRepresentsCurrentMutation(lastRecord)) return recordWithOldValue;
866
+ return null;
867
+ }
868
+ function Registration(observer, target, options) {
869
+ this.observer = observer;
870
+ this.target = target;
871
+ this.options = options;
872
+ this.transientObservedNodes = [];
873
+ }
874
+ Registration.prototype = {
875
+ enqueue: function(record) {
876
+ var records = this.observer.records_;
877
+ var length = records.length;
878
+ if (records.length > 0) {
879
+ var lastRecord = records[length - 1];
880
+ var recordToReplaceLast = selectRecord(lastRecord, record);
881
+ if (recordToReplaceLast) {
882
+ records[length - 1] = recordToReplaceLast;
883
+ return;
884
+ }
885
+ } else {
886
+ scheduleCallback(this.observer);
887
+ }
888
+ records[length] = record;
889
+ },
890
+ addListeners: function() {
891
+ this.addListeners_(this.target);
892
+ },
893
+ addListeners_: function(node) {
894
+ var options = this.options;
895
+ if (options.attributes) node.addEventListener("DOMAttrModified", this, true);
896
+ if (options.characterData) node.addEventListener("DOMCharacterDataModified", this, true);
897
+ if (options.childList) node.addEventListener("DOMNodeInserted", this, true);
898
+ if (options.childList || options.subtree) node.addEventListener("DOMNodeRemoved", this, true);
899
+ },
900
+ removeListeners: function() {
901
+ this.removeListeners_(this.target);
902
+ },
903
+ removeListeners_: function(node) {
904
+ var options = this.options;
905
+ if (options.attributes) node.removeEventListener("DOMAttrModified", this, true);
906
+ if (options.characterData) node.removeEventListener("DOMCharacterDataModified", this, true);
907
+ if (options.childList) node.removeEventListener("DOMNodeInserted", this, true);
908
+ if (options.childList || options.subtree) node.removeEventListener("DOMNodeRemoved", this, true);
909
+ },
910
+ addTransientObserver: function(node) {
911
+ if (node === this.target) return;
912
+ this.addListeners_(node);
913
+ this.transientObservedNodes.push(node);
914
+ var registrations = registrationsTable.get(node);
915
+ if (!registrations) registrationsTable.set(node, registrations = []);
916
+ registrations.push(this);
917
+ },
918
+ removeTransientObservers: function() {
919
+ var transientObservedNodes = this.transientObservedNodes;
920
+ this.transientObservedNodes = [];
921
+ transientObservedNodes.forEach(function(node) {
922
+ this.removeListeners_(node);
923
+ var registrations = registrationsTable.get(node);
924
+ for (var i = 0; i < registrations.length; i++) {
925
+ if (registrations[i] === this) {
926
+ registrations.splice(i, 1);
927
+ break;
928
+ }
929
+ }
930
+ }, this);
931
+ },
932
+ handleEvent: function(e) {
933
+ e.stopImmediatePropagation();
934
+ switch (e.type) {
935
+ case "DOMAttrModified":
936
+ var name = e.attrName;
937
+ var namespace = e.relatedNode.namespaceURI;
938
+ var target = e.target;
939
+ var record = new getRecord("attributes", target);
940
+ record.attributeName = name;
941
+ record.attributeNamespace = namespace;
942
+ var oldValue = e.attrChange === MutationEvent.ADDITION ? null : e.prevValue;
943
+ forEachAncestorAndObserverEnqueueRecord(target, function(options) {
944
+ if (!options.attributes) return;
945
+ if (options.attributeFilter && options.attributeFilter.length && options.attributeFilter.indexOf(name) === -1 && options.attributeFilter.indexOf(namespace) === -1) {
946
+ return;
947
+ }
948
+ if (options.attributeOldValue) return getRecordWithOldValue(oldValue);
949
+ return record;
950
+ });
951
+ break;
952
+
953
+ case "DOMCharacterDataModified":
954
+ var target = e.target;
955
+ var record = getRecord("characterData", target);
956
+ var oldValue = e.prevValue;
957
+ forEachAncestorAndObserverEnqueueRecord(target, function(options) {
958
+ if (!options.characterData) return;
959
+ if (options.characterDataOldValue) return getRecordWithOldValue(oldValue);
960
+ return record;
961
+ });
962
+ break;
963
+
964
+ case "DOMNodeRemoved":
965
+ this.addTransientObserver(e.target);
966
+
967
+ case "DOMNodeInserted":
968
+ var changedNode = e.target;
969
+ var addedNodes, removedNodes;
970
+ if (e.type === "DOMNodeInserted") {
971
+ addedNodes = [ changedNode ];
972
+ removedNodes = [];
973
+ } else {
974
+ addedNodes = [];
975
+ removedNodes = [ changedNode ];
976
+ }
977
+ var previousSibling = changedNode.previousSibling;
978
+ var nextSibling = changedNode.nextSibling;
979
+ var record = getRecord("childList", e.target.parentNode);
980
+ record.addedNodes = addedNodes;
981
+ record.removedNodes = removedNodes;
982
+ record.previousSibling = previousSibling;
983
+ record.nextSibling = nextSibling;
984
+ forEachAncestorAndObserverEnqueueRecord(e.relatedNode, function(options) {
985
+ if (!options.childList) return;
986
+ return record;
987
+ });
988
+ }
989
+ clearRecords();
990
+ }
991
+ };
992
+ global.JsMutationObserver = JsMutationObserver;
993
+ if (!global.MutationObserver) {
994
+ global.MutationObserver = JsMutationObserver;
995
+ JsMutationObserver._isPolyfilled = true;
996
+ }
997
+ })(self);
998
+
999
+ if (typeof HTMLTemplateElement === "undefined") {
1000
+ (function() {
1001
+ var TEMPLATE_TAG = "template";
1002
+ var contentDoc = document.implementation.createHTMLDocument("template");
1003
+ var canDecorate = true;
1004
+ HTMLTemplateElement = function() {};
1005
+ HTMLTemplateElement.prototype = Object.create(HTMLElement.prototype);
1006
+ HTMLTemplateElement.decorate = function(template) {
1007
+ if (template.content) {
1008
+ return;
1009
+ }
1010
+ template.content = contentDoc.createDocumentFragment();
1011
+ var child;
1012
+ while (child = template.firstChild) {
1013
+ template.content.appendChild(child);
1014
+ }
1015
+ if (canDecorate) {
1016
+ try {
1017
+ Object.defineProperty(template, "innerHTML", {
1018
+ get: function() {
1019
+ var o = "";
1020
+ for (var e = this.content.firstChild; e; e = e.nextSibling) {
1021
+ o += e.outerHTML || escapeData(e.data);
1022
+ }
1023
+ return o;
1024
+ },
1025
+ set: function(text) {
1026
+ contentDoc.body.innerHTML = text;
1027
+ HTMLTemplateElement.bootstrap(contentDoc);
1028
+ while (this.content.firstChild) {
1029
+ this.content.removeChild(this.content.firstChild);
1030
+ }
1031
+ while (contentDoc.body.firstChild) {
1032
+ this.content.appendChild(contentDoc.body.firstChild);
1033
+ }
1034
+ },
1035
+ configurable: true
1036
+ });
1037
+ } catch (err) {
1038
+ canDecorate = false;
1039
+ }
1040
+ }
1041
+ HTMLTemplateElement.bootstrap(template.content);
1042
+ };
1043
+ HTMLTemplateElement.bootstrap = function(doc) {
1044
+ var templates = doc.querySelectorAll(TEMPLATE_TAG);
1045
+ for (var i = 0, l = templates.length, t; i < l && (t = templates[i]); i++) {
1046
+ HTMLTemplateElement.decorate(t);
1047
+ }
1048
+ };
1049
+ document.addEventListener("DOMContentLoaded", function() {
1050
+ HTMLTemplateElement.bootstrap(document);
1051
+ });
1052
+ var createElement = document.createElement;
1053
+ document.createElement = function() {
1054
+ "use strict";
1055
+ var el = createElement.apply(document, arguments);
1056
+ if (el.localName == "template") {
1057
+ HTMLTemplateElement.decorate(el);
1058
+ }
1059
+ return el;
1060
+ };
1061
+ var escapeDataRegExp = /[&\u00A0<>]/g;
1062
+ function escapeReplace(c) {
1063
+ switch (c) {
1064
+ case "&":
1065
+ return "&amp;";
1066
+
1067
+ case "<":
1068
+ return "&lt;";
1069
+
1070
+ case ">":
1071
+ return "&gt;";
1072
+
1073
+ case " ":
1074
+ return "&nbsp;";
1075
+ }
1076
+ }
1077
+ function escapeData(s) {
1078
+ return s.replace(escapeDataRegExp, escapeReplace);
1079
+ }
1080
+ })();
1081
+ }
1082
+
1083
+ (function(scope) {
1084
+ "use strict";
1085
+ if (!window.performance) {
1086
+ var start = Date.now();
1087
+ window.performance = {
1088
+ now: function() {
1089
+ return Date.now() - start;
1090
+ }
1091
+ };
1092
+ }
1093
+ if (!window.requestAnimationFrame) {
1094
+ window.requestAnimationFrame = function() {
1095
+ var nativeRaf = window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame;
1096
+ return nativeRaf ? function(callback) {
1097
+ return nativeRaf(function() {
1098
+ callback(performance.now());
1099
+ });
1100
+ } : function(callback) {
1101
+ return window.setTimeout(callback, 1e3 / 60);
1102
+ };
1103
+ }();
1104
+ }
1105
+ if (!window.cancelAnimationFrame) {
1106
+ window.cancelAnimationFrame = function() {
1107
+ return window.webkitCancelAnimationFrame || window.mozCancelAnimationFrame || function(id) {
1108
+ clearTimeout(id);
1109
+ };
1110
+ }();
1111
+ }
1112
+ var workingDefaultPrevented = function() {
1113
+ var e = document.createEvent("Event");
1114
+ e.initEvent("foo", true, true);
1115
+ e.preventDefault();
1116
+ return e.defaultPrevented;
1117
+ }();
1118
+ if (!workingDefaultPrevented) {
1119
+ var origPreventDefault = Event.prototype.preventDefault;
1120
+ Event.prototype.preventDefault = function() {
1121
+ if (!this.cancelable) {
1122
+ return;
1123
+ }
1124
+ origPreventDefault.call(this);
1125
+ Object.defineProperty(this, "defaultPrevented", {
1126
+ get: function() {
1127
+ return true;
1128
+ },
1129
+ configurable: true
1130
+ });
1131
+ };
1132
+ }
1133
+ var isIE = /Trident/.test(navigator.userAgent);
1134
+ if (!window.CustomEvent || isIE && typeof window.CustomEvent !== "function") {
1135
+ window.CustomEvent = function(inType, params) {
1136
+ params = params || {};
1137
+ var e = document.createEvent("CustomEvent");
1138
+ e.initCustomEvent(inType, Boolean(params.bubbles), Boolean(params.cancelable), params.detail);
1139
+ return e;
1140
+ };
1141
+ window.CustomEvent.prototype = window.Event.prototype;
1142
+ }
1143
+ if (!window.Event || isIE && typeof window.Event !== "function") {
1144
+ var origEvent = window.Event;
1145
+ window.Event = function(inType, params) {
1146
+ params = params || {};
1147
+ var e = document.createEvent("Event");
1148
+ e.initEvent(inType, Boolean(params.bubbles), Boolean(params.cancelable));
1149
+ return e;
1150
+ };
1151
+ window.Event.prototype = origEvent.prototype;
1152
+ }
1153
+ })(window.WebComponents);
1154
+
1155
+ window.HTMLImports = window.HTMLImports || {
1156
+ flags: {}
1157
+ };
1158
+
1159
+ (function(scope) {
1160
+ var IMPORT_LINK_TYPE = "import";
1161
+ var useNative = Boolean(IMPORT_LINK_TYPE in document.createElement("link"));
1162
+ var hasShadowDOMPolyfill = Boolean(window.ShadowDOMPolyfill);
1163
+ var wrap = function(node) {
1164
+ return hasShadowDOMPolyfill ? window.ShadowDOMPolyfill.wrapIfNeeded(node) : node;
1165
+ };
1166
+ var rootDocument = wrap(document);
1167
+ var currentScriptDescriptor = {
1168
+ get: function() {
1169
+ var script = window.HTMLImports.currentScript || document.currentScript || (document.readyState !== "complete" ? document.scripts[document.scripts.length - 1] : null);
1170
+ return wrap(script);
1171
+ },
1172
+ configurable: true
1173
+ };
1174
+ Object.defineProperty(document, "_currentScript", currentScriptDescriptor);
1175
+ Object.defineProperty(rootDocument, "_currentScript", currentScriptDescriptor);
1176
+ var isIE = /Trident/.test(navigator.userAgent);
1177
+ function whenReady(callback, doc) {
1178
+ doc = doc || rootDocument;
1179
+ whenDocumentReady(function() {
1180
+ watchImportsLoad(callback, doc);
1181
+ }, doc);
1182
+ }
1183
+ var requiredReadyState = isIE ? "complete" : "interactive";
1184
+ var READY_EVENT = "readystatechange";
1185
+ function isDocumentReady(doc) {
1186
+ return doc.readyState === "complete" || doc.readyState === requiredReadyState;
1187
+ }
1188
+ function whenDocumentReady(callback, doc) {
1189
+ if (!isDocumentReady(doc)) {
1190
+ var checkReady = function() {
1191
+ if (doc.readyState === "complete" || doc.readyState === requiredReadyState) {
1192
+ doc.removeEventListener(READY_EVENT, checkReady);
1193
+ whenDocumentReady(callback, doc);
1194
+ }
1195
+ };
1196
+ doc.addEventListener(READY_EVENT, checkReady);
1197
+ } else if (callback) {
1198
+ callback();
1199
+ }
1200
+ }
1201
+ function markTargetLoaded(event) {
1202
+ event.target.__loaded = true;
1203
+ }
1204
+ function watchImportsLoad(callback, doc) {
1205
+ var imports = doc.querySelectorAll("link[rel=import]");
1206
+ var parsedCount = 0, importCount = imports.length, newImports = [], errorImports = [];
1207
+ function checkDone() {
1208
+ if (parsedCount == importCount && callback) {
1209
+ callback({
1210
+ allImports: imports,
1211
+ loadedImports: newImports,
1212
+ errorImports: errorImports
1213
+ });
1214
+ }
1215
+ }
1216
+ function loadedImport(e) {
1217
+ markTargetLoaded(e);
1218
+ newImports.push(this);
1219
+ parsedCount++;
1220
+ checkDone();
1221
+ }
1222
+ function errorLoadingImport(e) {
1223
+ errorImports.push(this);
1224
+ parsedCount++;
1225
+ checkDone();
1226
+ }
1227
+ if (importCount) {
1228
+ for (var i = 0, imp; i < importCount && (imp = imports[i]); i++) {
1229
+ if (isImportLoaded(imp)) {
1230
+ newImports.push(this);
1231
+ parsedCount++;
1232
+ checkDone();
1233
+ } else {
1234
+ imp.addEventListener("load", loadedImport);
1235
+ imp.addEventListener("error", errorLoadingImport);
1236
+ }
1237
+ }
1238
+ } else {
1239
+ checkDone();
1240
+ }
1241
+ }
1242
+ function isImportLoaded(link) {
1243
+ return useNative ? link.__loaded || link.import && link.import.readyState !== "loading" : link.__importParsed;
1244
+ }
1245
+ if (useNative) {
1246
+ new MutationObserver(function(mxns) {
1247
+ for (var i = 0, l = mxns.length, m; i < l && (m = mxns[i]); i++) {
1248
+ if (m.addedNodes) {
1249
+ handleImports(m.addedNodes);
1250
+ }
1251
+ }
1252
+ }).observe(document.head, {
1253
+ childList: true
1254
+ });
1255
+ function handleImports(nodes) {
1256
+ for (var i = 0, l = nodes.length, n; i < l && (n = nodes[i]); i++) {
1257
+ if (isImport(n)) {
1258
+ handleImport(n);
1259
+ }
1260
+ }
1261
+ }
1262
+ function isImport(element) {
1263
+ return element.localName === "link" && element.rel === "import";
1264
+ }
1265
+ function handleImport(element) {
1266
+ var loaded = element.import;
1267
+ if (loaded) {
1268
+ markTargetLoaded({
1269
+ target: element
1270
+ });
1271
+ } else {
1272
+ element.addEventListener("load", markTargetLoaded);
1273
+ element.addEventListener("error", markTargetLoaded);
1274
+ }
1275
+ }
1276
+ (function() {
1277
+ if (document.readyState === "loading") {
1278
+ var imports = document.querySelectorAll("link[rel=import]");
1279
+ for (var i = 0, l = imports.length, imp; i < l && (imp = imports[i]); i++) {
1280
+ handleImport(imp);
1281
+ }
1282
+ }
1283
+ })();
1284
+ }
1285
+ whenReady(function(detail) {
1286
+ window.HTMLImports.ready = true;
1287
+ window.HTMLImports.readyTime = new Date().getTime();
1288
+ var evt = rootDocument.createEvent("CustomEvent");
1289
+ evt.initCustomEvent("HTMLImportsLoaded", true, true, detail);
1290
+ rootDocument.dispatchEvent(evt);
1291
+ });
1292
+ scope.IMPORT_LINK_TYPE = IMPORT_LINK_TYPE;
1293
+ scope.useNative = useNative;
1294
+ scope.rootDocument = rootDocument;
1295
+ scope.whenReady = whenReady;
1296
+ scope.isIE = isIE;
1297
+ })(window.HTMLImports);
1298
+
1299
+ (function(scope) {
1300
+ var modules = [];
1301
+ var addModule = function(module) {
1302
+ modules.push(module);
1303
+ };
1304
+ var initializeModules = function() {
1305
+ modules.forEach(function(module) {
1306
+ module(scope);
1307
+ });
1308
+ };
1309
+ scope.addModule = addModule;
1310
+ scope.initializeModules = initializeModules;
1311
+ })(window.HTMLImports);
1312
+
1313
+ window.HTMLImports.addModule(function(scope) {
1314
+ var CSS_URL_REGEXP = /(url\()([^)]*)(\))/g;
1315
+ var CSS_IMPORT_REGEXP = /(@import[\s]+(?!url\())([^;]*)(;)/g;
1316
+ var path = {
1317
+ resolveUrlsInStyle: function(style, linkUrl) {
1318
+ var doc = style.ownerDocument;
1319
+ var resolver = doc.createElement("a");
1320
+ style.textContent = this.resolveUrlsInCssText(style.textContent, linkUrl, resolver);
1321
+ return style;
1322
+ },
1323
+ resolveUrlsInCssText: function(cssText, linkUrl, urlObj) {
1324
+ var r = this.replaceUrls(cssText, urlObj, linkUrl, CSS_URL_REGEXP);
1325
+ r = this.replaceUrls(r, urlObj, linkUrl, CSS_IMPORT_REGEXP);
1326
+ return r;
1327
+ },
1328
+ replaceUrls: function(text, urlObj, linkUrl, regexp) {
1329
+ return text.replace(regexp, function(m, pre, url, post) {
1330
+ var urlPath = url.replace(/["']/g, "");
1331
+ if (linkUrl) {
1332
+ urlPath = new URL(urlPath, linkUrl).href;
1333
+ }
1334
+ urlObj.href = urlPath;
1335
+ urlPath = urlObj.href;
1336
+ return pre + "'" + urlPath + "'" + post;
1337
+ });
1338
+ }
1339
+ };
1340
+ scope.path = path;
1341
+ });
1342
+
1343
+ window.HTMLImports.addModule(function(scope) {
1344
+ var xhr = {
1345
+ async: true,
1346
+ ok: function(request) {
1347
+ return request.status >= 200 && request.status < 300 || request.status === 304 || request.status === 0;
1348
+ },
1349
+ load: function(url, next, nextContext) {
1350
+ var request = new XMLHttpRequest();
1351
+ if (scope.flags.debug || scope.flags.bust) {
1352
+ url += "?" + Math.random();
1353
+ }
1354
+ request.open("GET", url, xhr.async);
1355
+ request.addEventListener("readystatechange", function(e) {
1356
+ if (request.readyState === 4) {
1357
+ var redirectedUrl = null;
1358
+ try {
1359
+ var locationHeader = request.getResponseHeader("Location");
1360
+ if (locationHeader) {
1361
+ redirectedUrl = locationHeader.substr(0, 1) === "/" ? location.origin + locationHeader : locationHeader;
1362
+ }
1363
+ } catch (e) {
1364
+ console.error(e.message);
1365
+ }
1366
+ next.call(nextContext, !xhr.ok(request) && request, request.response || request.responseText, redirectedUrl);
1367
+ }
1368
+ });
1369
+ request.send();
1370
+ return request;
1371
+ },
1372
+ loadDocument: function(url, next, nextContext) {
1373
+ this.load(url, next, nextContext).responseType = "document";
1374
+ }
1375
+ };
1376
+ scope.xhr = xhr;
1377
+ });
1378
+
1379
+ window.HTMLImports.addModule(function(scope) {
1380
+ var xhr = scope.xhr;
1381
+ var flags = scope.flags;
1382
+ var Loader = function(onLoad, onComplete) {
1383
+ this.cache = {};
1384
+ this.onload = onLoad;
1385
+ this.oncomplete = onComplete;
1386
+ this.inflight = 0;
1387
+ this.pending = {};
1388
+ };
1389
+ Loader.prototype = {
1390
+ addNodes: function(nodes) {
1391
+ this.inflight += nodes.length;
1392
+ for (var i = 0, l = nodes.length, n; i < l && (n = nodes[i]); i++) {
1393
+ this.require(n);
1394
+ }
1395
+ this.checkDone();
1396
+ },
1397
+ addNode: function(node) {
1398
+ this.inflight++;
1399
+ this.require(node);
1400
+ this.checkDone();
1401
+ },
1402
+ require: function(elt) {
1403
+ var url = elt.src || elt.href;
1404
+ elt.__nodeUrl = url;
1405
+ if (!this.dedupe(url, elt)) {
1406
+ this.fetch(url, elt);
1407
+ }
1408
+ },
1409
+ dedupe: function(url, elt) {
1410
+ if (this.pending[url]) {
1411
+ this.pending[url].push(elt);
1412
+ return true;
1413
+ }
1414
+ var resource;
1415
+ if (this.cache[url]) {
1416
+ this.onload(url, elt, this.cache[url]);
1417
+ this.tail();
1418
+ return true;
1419
+ }
1420
+ this.pending[url] = [ elt ];
1421
+ return false;
1422
+ },
1423
+ fetch: function(url, elt) {
1424
+ flags.load && console.log("fetch", url, elt);
1425
+ if (!url) {
1426
+ setTimeout(function() {
1427
+ this.receive(url, elt, {
1428
+ error: "href must be specified"
1429
+ }, null);
1430
+ }.bind(this), 0);
1431
+ } else if (url.match(/^data:/)) {
1432
+ var pieces = url.split(",");
1433
+ var header = pieces[0];
1434
+ var body = pieces[1];
1435
+ if (header.indexOf(";base64") > -1) {
1436
+ body = atob(body);
1437
+ } else {
1438
+ body = decodeURIComponent(body);
1439
+ }
1440
+ setTimeout(function() {
1441
+ this.receive(url, elt, null, body);
1442
+ }.bind(this), 0);
1443
+ } else {
1444
+ var receiveXhr = function(err, resource, redirectedUrl) {
1445
+ this.receive(url, elt, err, resource, redirectedUrl);
1446
+ }.bind(this);
1447
+ xhr.load(url, receiveXhr);
1448
+ }
1449
+ },
1450
+ receive: function(url, elt, err, resource, redirectedUrl) {
1451
+ this.cache[url] = resource;
1452
+ var $p = this.pending[url];
1453
+ for (var i = 0, l = $p.length, p; i < l && (p = $p[i]); i++) {
1454
+ this.onload(url, p, resource, err, redirectedUrl);
1455
+ this.tail();
1456
+ }
1457
+ this.pending[url] = null;
1458
+ },
1459
+ tail: function() {
1460
+ --this.inflight;
1461
+ this.checkDone();
1462
+ },
1463
+ checkDone: function() {
1464
+ if (!this.inflight) {
1465
+ this.oncomplete();
1466
+ }
1467
+ }
1468
+ };
1469
+ scope.Loader = Loader;
1470
+ });
1471
+
1472
+ window.HTMLImports.addModule(function(scope) {
1473
+ var Observer = function(addCallback) {
1474
+ this.addCallback = addCallback;
1475
+ this.mo = new MutationObserver(this.handler.bind(this));
1476
+ };
1477
+ Observer.prototype = {
1478
+ handler: function(mutations) {
1479
+ for (var i = 0, l = mutations.length, m; i < l && (m = mutations[i]); i++) {
1480
+ if (m.type === "childList" && m.addedNodes.length) {
1481
+ this.addedNodes(m.addedNodes);
1482
+ }
1483
+ }
1484
+ },
1485
+ addedNodes: function(nodes) {
1486
+ if (this.addCallback) {
1487
+ this.addCallback(nodes);
1488
+ }
1489
+ for (var i = 0, l = nodes.length, n, loading; i < l && (n = nodes[i]); i++) {
1490
+ if (n.children && n.children.length) {
1491
+ this.addedNodes(n.children);
1492
+ }
1493
+ }
1494
+ },
1495
+ observe: function(root) {
1496
+ this.mo.observe(root, {
1497
+ childList: true,
1498
+ subtree: true
1499
+ });
1500
+ }
1501
+ };
1502
+ scope.Observer = Observer;
1503
+ });
1504
+
1505
+ window.HTMLImports.addModule(function(scope) {
1506
+ var path = scope.path;
1507
+ var rootDocument = scope.rootDocument;
1508
+ var flags = scope.flags;
1509
+ var isIE = scope.isIE;
1510
+ var IMPORT_LINK_TYPE = scope.IMPORT_LINK_TYPE;
1511
+ var IMPORT_SELECTOR = "link[rel=" + IMPORT_LINK_TYPE + "]";
1512
+ var importParser = {
1513
+ documentSelectors: IMPORT_SELECTOR,
1514
+ importsSelectors: [ IMPORT_SELECTOR, "link[rel=stylesheet]:not([type])", "style:not([type])", "script:not([type])", 'script[type="application/javascript"]', 'script[type="text/javascript"]' ].join(","),
1515
+ map: {
1516
+ link: "parseLink",
1517
+ script: "parseScript",
1518
+ style: "parseStyle"
1519
+ },
1520
+ dynamicElements: [],
1521
+ parseNext: function() {
1522
+ var next = this.nextToParse();
1523
+ if (next) {
1524
+ this.parse(next);
1525
+ }
1526
+ },
1527
+ parse: function(elt) {
1528
+ if (this.isParsed(elt)) {
1529
+ flags.parse && console.log("[%s] is already parsed", elt.localName);
1530
+ return;
1531
+ }
1532
+ var fn = this[this.map[elt.localName]];
1533
+ if (fn) {
1534
+ this.markParsing(elt);
1535
+ fn.call(this, elt);
1536
+ }
1537
+ },
1538
+ parseDynamic: function(elt, quiet) {
1539
+ this.dynamicElements.push(elt);
1540
+ if (!quiet) {
1541
+ this.parseNext();
1542
+ }
1543
+ },
1544
+ markParsing: function(elt) {
1545
+ flags.parse && console.log("parsing", elt);
1546
+ this.parsingElement = elt;
1547
+ },
1548
+ markParsingComplete: function(elt) {
1549
+ elt.__importParsed = true;
1550
+ this.markDynamicParsingComplete(elt);
1551
+ if (elt.__importElement) {
1552
+ elt.__importElement.__importParsed = true;
1553
+ this.markDynamicParsingComplete(elt.__importElement);
1554
+ }
1555
+ this.parsingElement = null;
1556
+ flags.parse && console.log("completed", elt);
1557
+ },
1558
+ markDynamicParsingComplete: function(elt) {
1559
+ var i = this.dynamicElements.indexOf(elt);
1560
+ if (i >= 0) {
1561
+ this.dynamicElements.splice(i, 1);
1562
+ }
1563
+ },
1564
+ parseImport: function(elt) {
1565
+ elt.import = elt.__doc;
1566
+ if (window.HTMLImports.__importsParsingHook) {
1567
+ window.HTMLImports.__importsParsingHook(elt);
1568
+ }
1569
+ if (elt.import) {
1570
+ elt.import.__importParsed = true;
1571
+ }
1572
+ this.markParsingComplete(elt);
1573
+ if (elt.__resource && !elt.__error) {
1574
+ elt.dispatchEvent(new CustomEvent("load", {
1575
+ bubbles: false
1576
+ }));
1577
+ } else {
1578
+ elt.dispatchEvent(new CustomEvent("error", {
1579
+ bubbles: false
1580
+ }));
1581
+ }
1582
+ if (elt.__pending) {
1583
+ var fn;
1584
+ while (elt.__pending.length) {
1585
+ fn = elt.__pending.shift();
1586
+ if (fn) {
1587
+ fn({
1588
+ target: elt
1589
+ });
1590
+ }
1591
+ }
1592
+ }
1593
+ this.parseNext();
1594
+ },
1595
+ parseLink: function(linkElt) {
1596
+ if (nodeIsImport(linkElt)) {
1597
+ this.parseImport(linkElt);
1598
+ } else {
1599
+ linkElt.href = linkElt.href;
1600
+ this.parseGeneric(linkElt);
1601
+ }
1602
+ },
1603
+ parseStyle: function(elt) {
1604
+ var src = elt;
1605
+ elt = cloneStyle(elt);
1606
+ src.__appliedElement = elt;
1607
+ elt.__importElement = src;
1608
+ this.parseGeneric(elt);
1609
+ },
1610
+ parseGeneric: function(elt) {
1611
+ this.trackElement(elt);
1612
+ this.addElementToDocument(elt);
1613
+ },
1614
+ rootImportForElement: function(elt) {
1615
+ var n = elt;
1616
+ while (n.ownerDocument.__importLink) {
1617
+ n = n.ownerDocument.__importLink;
1618
+ }
1619
+ return n;
1620
+ },
1621
+ addElementToDocument: function(elt) {
1622
+ var port = this.rootImportForElement(elt.__importElement || elt);
1623
+ port.parentNode.insertBefore(elt, port);
1624
+ },
1625
+ trackElement: function(elt, callback) {
1626
+ var self = this;
1627
+ var done = function(e) {
1628
+ elt.removeEventListener("load", done);
1629
+ elt.removeEventListener("error", done);
1630
+ if (callback) {
1631
+ callback(e);
1632
+ }
1633
+ self.markParsingComplete(elt);
1634
+ self.parseNext();
1635
+ };
1636
+ elt.addEventListener("load", done);
1637
+ elt.addEventListener("error", done);
1638
+ if (isIE && elt.localName === "style") {
1639
+ var fakeLoad = false;
1640
+ if (elt.textContent.indexOf("@import") == -1) {
1641
+ fakeLoad = true;
1642
+ } else if (elt.sheet) {
1643
+ fakeLoad = true;
1644
+ var csr = elt.sheet.cssRules;
1645
+ var len = csr ? csr.length : 0;
1646
+ for (var i = 0, r; i < len && (r = csr[i]); i++) {
1647
+ if (r.type === CSSRule.IMPORT_RULE) {
1648
+ fakeLoad = fakeLoad && Boolean(r.styleSheet);
1649
+ }
1650
+ }
1651
+ }
1652
+ if (fakeLoad) {
1653
+ setTimeout(function() {
1654
+ elt.dispatchEvent(new CustomEvent("load", {
1655
+ bubbles: false
1656
+ }));
1657
+ });
1658
+ }
1659
+ }
1660
+ },
1661
+ parseScript: function(scriptElt) {
1662
+ var script = document.createElement("script");
1663
+ script.__importElement = scriptElt;
1664
+ script.src = scriptElt.src ? scriptElt.src : generateScriptDataUrl(scriptElt);
1665
+ scope.currentScript = scriptElt;
1666
+ this.trackElement(script, function(e) {
1667
+ if (script.parentNode) {
1668
+ script.parentNode.removeChild(script);
1669
+ }
1670
+ scope.currentScript = null;
1671
+ });
1672
+ this.addElementToDocument(script);
1673
+ },
1674
+ nextToParse: function() {
1675
+ this._mayParse = [];
1676
+ return !this.parsingElement && (this.nextToParseInDoc(rootDocument) || this.nextToParseDynamic());
1677
+ },
1678
+ nextToParseInDoc: function(doc, link) {
1679
+ if (doc && this._mayParse.indexOf(doc) < 0) {
1680
+ this._mayParse.push(doc);
1681
+ var nodes = doc.querySelectorAll(this.parseSelectorsForNode(doc));
1682
+ for (var i = 0, l = nodes.length, p = 0, n; i < l && (n = nodes[i]); i++) {
1683
+ if (!this.isParsed(n)) {
1684
+ if (this.hasResource(n)) {
1685
+ return nodeIsImport(n) ? this.nextToParseInDoc(n.__doc, n) : n;
1686
+ } else {
1687
+ return;
1688
+ }
1689
+ }
1690
+ }
1691
+ }
1692
+ return link;
1693
+ },
1694
+ nextToParseDynamic: function() {
1695
+ return this.dynamicElements[0];
1696
+ },
1697
+ parseSelectorsForNode: function(node) {
1698
+ var doc = node.ownerDocument || node;
1699
+ return doc === rootDocument ? this.documentSelectors : this.importsSelectors;
1700
+ },
1701
+ isParsed: function(node) {
1702
+ return node.__importParsed;
1703
+ },
1704
+ needsDynamicParsing: function(elt) {
1705
+ return this.dynamicElements.indexOf(elt) >= 0;
1706
+ },
1707
+ hasResource: function(node) {
1708
+ if (nodeIsImport(node) && node.__doc === undefined) {
1709
+ return false;
1710
+ }
1711
+ return true;
1712
+ }
1713
+ };
1714
+ function nodeIsImport(elt) {
1715
+ return elt.localName === "link" && elt.rel === IMPORT_LINK_TYPE;
1716
+ }
1717
+ function generateScriptDataUrl(script) {
1718
+ var scriptContent = generateScriptContent(script);
1719
+ return "data:text/javascript;charset=utf-8," + encodeURIComponent(scriptContent);
1720
+ }
1721
+ function generateScriptContent(script) {
1722
+ return script.textContent + generateSourceMapHint(script);
1723
+ }
1724
+ function generateSourceMapHint(script) {
1725
+ var owner = script.ownerDocument;
1726
+ owner.__importedScripts = owner.__importedScripts || 0;
1727
+ var moniker = script.ownerDocument.baseURI;
1728
+ var num = owner.__importedScripts ? "-" + owner.__importedScripts : "";
1729
+ owner.__importedScripts++;
1730
+ return "\n//# sourceURL=" + moniker + num + ".js\n";
1731
+ }
1732
+ function cloneStyle(style) {
1733
+ var clone = style.ownerDocument.createElement("style");
1734
+ clone.textContent = style.textContent;
1735
+ path.resolveUrlsInStyle(clone);
1736
+ return clone;
1737
+ }
1738
+ scope.parser = importParser;
1739
+ scope.IMPORT_SELECTOR = IMPORT_SELECTOR;
1740
+ });
1741
+
1742
+ window.HTMLImports.addModule(function(scope) {
1743
+ var flags = scope.flags;
1744
+ var IMPORT_LINK_TYPE = scope.IMPORT_LINK_TYPE;
1745
+ var IMPORT_SELECTOR = scope.IMPORT_SELECTOR;
1746
+ var rootDocument = scope.rootDocument;
1747
+ var Loader = scope.Loader;
1748
+ var Observer = scope.Observer;
1749
+ var parser = scope.parser;
1750
+ var importer = {
1751
+ documents: {},
1752
+ documentPreloadSelectors: IMPORT_SELECTOR,
1753
+ importsPreloadSelectors: [ IMPORT_SELECTOR ].join(","),
1754
+ loadNode: function(node) {
1755
+ importLoader.addNode(node);
1756
+ },
1757
+ loadSubtree: function(parent) {
1758
+ var nodes = this.marshalNodes(parent);
1759
+ importLoader.addNodes(nodes);
1760
+ },
1761
+ marshalNodes: function(parent) {
1762
+ return parent.querySelectorAll(this.loadSelectorsForNode(parent));
1763
+ },
1764
+ loadSelectorsForNode: function(node) {
1765
+ var doc = node.ownerDocument || node;
1766
+ return doc === rootDocument ? this.documentPreloadSelectors : this.importsPreloadSelectors;
1767
+ },
1768
+ loaded: function(url, elt, resource, err, redirectedUrl) {
1769
+ flags.load && console.log("loaded", url, elt);
1770
+ elt.__resource = resource;
1771
+ elt.__error = err;
1772
+ if (isImportLink(elt)) {
1773
+ var doc = this.documents[url];
1774
+ if (doc === undefined) {
1775
+ doc = err ? null : makeDocument(resource, redirectedUrl || url);
1776
+ if (doc) {
1777
+ doc.__importLink = elt;
1778
+ this.bootDocument(doc);
1779
+ }
1780
+ this.documents[url] = doc;
1781
+ }
1782
+ elt.__doc = doc;
1783
+ }
1784
+ parser.parseNext();
1785
+ },
1786
+ bootDocument: function(doc) {
1787
+ this.loadSubtree(doc);
1788
+ this.observer.observe(doc);
1789
+ parser.parseNext();
1790
+ },
1791
+ loadedAll: function() {
1792
+ parser.parseNext();
1793
+ }
1794
+ };
1795
+ var importLoader = new Loader(importer.loaded.bind(importer), importer.loadedAll.bind(importer));
1796
+ importer.observer = new Observer();
1797
+ function isImportLink(elt) {
1798
+ return isLinkRel(elt, IMPORT_LINK_TYPE);
1799
+ }
1800
+ function isLinkRel(elt, rel) {
1801
+ return elt.localName === "link" && elt.getAttribute("rel") === rel;
1802
+ }
1803
+ function hasBaseURIAccessor(doc) {
1804
+ return !!Object.getOwnPropertyDescriptor(doc, "baseURI");
1805
+ }
1806
+ function makeDocument(resource, url) {
1807
+ var doc = document.implementation.createHTMLDocument(IMPORT_LINK_TYPE);
1808
+ doc._URL = url;
1809
+ var base = doc.createElement("base");
1810
+ base.setAttribute("href", url);
1811
+ if (!doc.baseURI && !hasBaseURIAccessor(doc)) {
1812
+ Object.defineProperty(doc, "baseURI", {
1813
+ value: url
1814
+ });
1815
+ }
1816
+ var meta = doc.createElement("meta");
1817
+ meta.setAttribute("charset", "utf-8");
1818
+ doc.head.appendChild(meta);
1819
+ doc.head.appendChild(base);
1820
+ doc.body.innerHTML = resource;
1821
+ if (window.HTMLTemplateElement && HTMLTemplateElement.bootstrap) {
1822
+ HTMLTemplateElement.bootstrap(doc);
1823
+ }
1824
+ return doc;
1825
+ }
1826
+ if (!document.baseURI) {
1827
+ var baseURIDescriptor = {
1828
+ get: function() {
1829
+ var base = document.querySelector("base");
1830
+ return base ? base.href : window.location.href;
1831
+ },
1832
+ configurable: true
1833
+ };
1834
+ Object.defineProperty(document, "baseURI", baseURIDescriptor);
1835
+ Object.defineProperty(rootDocument, "baseURI", baseURIDescriptor);
1836
+ }
1837
+ scope.importer = importer;
1838
+ scope.importLoader = importLoader;
1839
+ });
1840
+
1841
+ window.HTMLImports.addModule(function(scope) {
1842
+ var parser = scope.parser;
1843
+ var importer = scope.importer;
1844
+ var dynamic = {
1845
+ added: function(nodes) {
1846
+ var owner, parsed, loading;
1847
+ for (var i = 0, l = nodes.length, n; i < l && (n = nodes[i]); i++) {
1848
+ if (!owner) {
1849
+ owner = n.ownerDocument;
1850
+ parsed = parser.isParsed(owner);
1851
+ }
1852
+ loading = this.shouldLoadNode(n);
1853
+ if (loading) {
1854
+ importer.loadNode(n);
1855
+ }
1856
+ if (this.shouldParseNode(n) && parsed) {
1857
+ parser.parseDynamic(n, loading);
1858
+ }
1859
+ }
1860
+ },
1861
+ shouldLoadNode: function(node) {
1862
+ return node.nodeType === 1 && matches.call(node, importer.loadSelectorsForNode(node));
1863
+ },
1864
+ shouldParseNode: function(node) {
1865
+ return node.nodeType === 1 && matches.call(node, parser.parseSelectorsForNode(node));
1866
+ }
1867
+ };
1868
+ importer.observer.addCallback = dynamic.added.bind(dynamic);
1869
+ var matches = HTMLElement.prototype.matches || HTMLElement.prototype.matchesSelector || HTMLElement.prototype.webkitMatchesSelector || HTMLElement.prototype.mozMatchesSelector || HTMLElement.prototype.msMatchesSelector;
1870
+ });
1871
+
1872
+ (function(scope) {
1873
+ var initializeModules = scope.initializeModules;
1874
+ var isIE = scope.isIE;
1875
+ if (scope.useNative) {
1876
+ return;
1877
+ }
1878
+ initializeModules();
1879
+ var rootDocument = scope.rootDocument;
1880
+ function bootstrap() {
1881
+ window.HTMLImports.importer.bootDocument(rootDocument);
1882
+ }
1883
+ if (document.readyState === "complete" || document.readyState === "interactive" && !window.attachEvent) {
1884
+ bootstrap();
1885
+ } else {
1886
+ document.addEventListener("DOMContentLoaded", bootstrap);
1887
+ }
1888
+ })(window.HTMLImports);
1889
+
1890
+ window.CustomElements = window.CustomElements || {
1891
+ flags: {}
1892
+ };
1893
+
1894
+ (function(scope) {
1895
+ var flags = scope.flags;
1896
+ var modules = [];
1897
+ var addModule = function(module) {
1898
+ modules.push(module);
1899
+ };
1900
+ var initializeModules = function() {
1901
+ modules.forEach(function(module) {
1902
+ module(scope);
1903
+ });
1904
+ };
1905
+ scope.addModule = addModule;
1906
+ scope.initializeModules = initializeModules;
1907
+ scope.hasNative = Boolean(document.registerElement);
1908
+ scope.isIE = /Trident/.test(navigator.userAgent);
1909
+ scope.useNative = !flags.register && scope.hasNative && !window.ShadowDOMPolyfill && (!window.HTMLImports || window.HTMLImports.useNative);
1910
+ })(window.CustomElements);
1911
+
1912
+ window.CustomElements.addModule(function(scope) {
1913
+ var IMPORT_LINK_TYPE = window.HTMLImports ? window.HTMLImports.IMPORT_LINK_TYPE : "none";
1914
+ function forSubtree(node, cb) {
1915
+ findAllElements(node, function(e) {
1916
+ if (cb(e)) {
1917
+ return true;
1918
+ }
1919
+ forRoots(e, cb);
1920
+ });
1921
+ forRoots(node, cb);
1922
+ }
1923
+ function findAllElements(node, find, data) {
1924
+ var e = node.firstElementChild;
1925
+ if (!e) {
1926
+ e = node.firstChild;
1927
+ while (e && e.nodeType !== Node.ELEMENT_NODE) {
1928
+ e = e.nextSibling;
1929
+ }
1930
+ }
1931
+ while (e) {
1932
+ if (find(e, data) !== true) {
1933
+ findAllElements(e, find, data);
1934
+ }
1935
+ e = e.nextElementSibling;
1936
+ }
1937
+ return null;
1938
+ }
1939
+ function forRoots(node, cb) {
1940
+ var root = node.shadowRoot;
1941
+ while (root) {
1942
+ forSubtree(root, cb);
1943
+ root = root.olderShadowRoot;
1944
+ }
1945
+ }
1946
+ function forDocumentTree(doc, cb) {
1947
+ _forDocumentTree(doc, cb, []);
1948
+ }
1949
+ function _forDocumentTree(doc, cb, processingDocuments) {
1950
+ doc = window.wrap(doc);
1951
+ if (processingDocuments.indexOf(doc) >= 0) {
1952
+ return;
1953
+ }
1954
+ processingDocuments.push(doc);
1955
+ var imports = doc.querySelectorAll("link[rel=" + IMPORT_LINK_TYPE + "]");
1956
+ for (var i = 0, l = imports.length, n; i < l && (n = imports[i]); i++) {
1957
+ if (n.import) {
1958
+ _forDocumentTree(n.import, cb, processingDocuments);
1959
+ }
1960
+ }
1961
+ cb(doc);
1962
+ }
1963
+ scope.forDocumentTree = forDocumentTree;
1964
+ scope.forSubtree = forSubtree;
1965
+ });
1966
+
1967
+ window.CustomElements.addModule(function(scope) {
1968
+ var flags = scope.flags;
1969
+ var forSubtree = scope.forSubtree;
1970
+ var forDocumentTree = scope.forDocumentTree;
1971
+ function addedNode(node, isAttached) {
1972
+ return added(node, isAttached) || addedSubtree(node, isAttached);
1973
+ }
1974
+ function added(node, isAttached) {
1975
+ if (scope.upgrade(node, isAttached)) {
1976
+ return true;
1977
+ }
1978
+ if (isAttached) {
1979
+ attached(node);
1980
+ }
1981
+ }
1982
+ function addedSubtree(node, isAttached) {
1983
+ forSubtree(node, function(e) {
1984
+ if (added(e, isAttached)) {
1985
+ return true;
1986
+ }
1987
+ });
1988
+ }
1989
+ var hasThrottledAttached = window.MutationObserver._isPolyfilled && flags["throttle-attached"];
1990
+ scope.hasPolyfillMutations = hasThrottledAttached;
1991
+ scope.hasThrottledAttached = hasThrottledAttached;
1992
+ var isPendingMutations = false;
1993
+ var pendingMutations = [];
1994
+ function deferMutation(fn) {
1995
+ pendingMutations.push(fn);
1996
+ if (!isPendingMutations) {
1997
+ isPendingMutations = true;
1998
+ setTimeout(takeMutations);
1999
+ }
2000
+ }
2001
+ function takeMutations() {
2002
+ isPendingMutations = false;
2003
+ var $p = pendingMutations;
2004
+ for (var i = 0, l = $p.length, p; i < l && (p = $p[i]); i++) {
2005
+ p();
2006
+ }
2007
+ pendingMutations = [];
2008
+ }
2009
+ function attached(element) {
2010
+ if (hasThrottledAttached) {
2011
+ deferMutation(function() {
2012
+ _attached(element);
2013
+ });
2014
+ } else {
2015
+ _attached(element);
2016
+ }
2017
+ }
2018
+ function _attached(element) {
2019
+ if (element.__upgraded__ && !element.__attached) {
2020
+ element.__attached = true;
2021
+ if (element.attachedCallback) {
2022
+ element.attachedCallback();
2023
+ }
2024
+ }
2025
+ }
2026
+ function detachedNode(node) {
2027
+ detached(node);
2028
+ forSubtree(node, function(e) {
2029
+ detached(e);
2030
+ });
2031
+ }
2032
+ function detached(element) {
2033
+ if (hasThrottledAttached) {
2034
+ deferMutation(function() {
2035
+ _detached(element);
2036
+ });
2037
+ } else {
2038
+ _detached(element);
2039
+ }
2040
+ }
2041
+ function _detached(element) {
2042
+ if (element.__upgraded__ && element.__attached) {
2043
+ element.__attached = false;
2044
+ if (element.detachedCallback) {
2045
+ element.detachedCallback();
2046
+ }
2047
+ }
2048
+ }
2049
+ function inDocument(element) {
2050
+ var p = element;
2051
+ var doc = window.wrap(document);
2052
+ while (p) {
2053
+ if (p == doc) {
2054
+ return true;
2055
+ }
2056
+ p = p.parentNode || p.nodeType === Node.DOCUMENT_FRAGMENT_NODE && p.host;
2057
+ }
2058
+ }
2059
+ function watchShadow(node) {
2060
+ if (node.shadowRoot && !node.shadowRoot.__watched) {
2061
+ flags.dom && console.log("watching shadow-root for: ", node.localName);
2062
+ var root = node.shadowRoot;
2063
+ while (root) {
2064
+ observe(root);
2065
+ root = root.olderShadowRoot;
2066
+ }
2067
+ }
2068
+ }
2069
+ function handler(root, mutations) {
2070
+ if (flags.dom) {
2071
+ var mx = mutations[0];
2072
+ if (mx && mx.type === "childList" && mx.addedNodes) {
2073
+ if (mx.addedNodes) {
2074
+ var d = mx.addedNodes[0];
2075
+ while (d && d !== document && !d.host) {
2076
+ d = d.parentNode;
2077
+ }
2078
+ var u = d && (d.URL || d._URL || d.host && d.host.localName) || "";
2079
+ u = u.split("/?").shift().split("/").pop();
2080
+ }
2081
+ }
2082
+ console.group("mutations (%d) [%s]", mutations.length, u || "");
2083
+ }
2084
+ var isAttached = inDocument(root);
2085
+ mutations.forEach(function(mx) {
2086
+ if (mx.type === "childList") {
2087
+ forEach(mx.addedNodes, function(n) {
2088
+ if (!n.localName) {
2089
+ return;
2090
+ }
2091
+ addedNode(n, isAttached);
2092
+ });
2093
+ forEach(mx.removedNodes, function(n) {
2094
+ if (!n.localName) {
2095
+ return;
2096
+ }
2097
+ detachedNode(n);
2098
+ });
2099
+ }
2100
+ });
2101
+ flags.dom && console.groupEnd();
2102
+ }
2103
+ function takeRecords(node) {
2104
+ node = window.wrap(node);
2105
+ if (!node) {
2106
+ node = window.wrap(document);
2107
+ }
2108
+ while (node.parentNode) {
2109
+ node = node.parentNode;
2110
+ }
2111
+ var observer = node.__observer;
2112
+ if (observer) {
2113
+ handler(node, observer.takeRecords());
2114
+ takeMutations();
2115
+ }
2116
+ }
2117
+ var forEach = Array.prototype.forEach.call.bind(Array.prototype.forEach);
2118
+ function observe(inRoot) {
2119
+ if (inRoot.__observer) {
2120
+ return;
2121
+ }
2122
+ var observer = new MutationObserver(handler.bind(this, inRoot));
2123
+ observer.observe(inRoot, {
2124
+ childList: true,
2125
+ subtree: true
2126
+ });
2127
+ inRoot.__observer = observer;
2128
+ }
2129
+ function upgradeDocument(doc) {
2130
+ doc = window.wrap(doc);
2131
+ flags.dom && console.group("upgradeDocument: ", doc.baseURI.split("/").pop());
2132
+ var isMainDocument = doc === window.wrap(document);
2133
+ addedNode(doc, isMainDocument);
2134
+ observe(doc);
2135
+ flags.dom && console.groupEnd();
2136
+ }
2137
+ function upgradeDocumentTree(doc) {
2138
+ forDocumentTree(doc, upgradeDocument);
2139
+ }
2140
+ var originalCreateShadowRoot = Element.prototype.createShadowRoot;
2141
+ if (originalCreateShadowRoot) {
2142
+ Element.prototype.createShadowRoot = function() {
2143
+ var root = originalCreateShadowRoot.call(this);
2144
+ window.CustomElements.watchShadow(this);
2145
+ return root;
2146
+ };
2147
+ }
2148
+ scope.watchShadow = watchShadow;
2149
+ scope.upgradeDocumentTree = upgradeDocumentTree;
2150
+ scope.upgradeDocument = upgradeDocument;
2151
+ scope.upgradeSubtree = addedSubtree;
2152
+ scope.upgradeAll = addedNode;
2153
+ scope.attached = attached;
2154
+ scope.takeRecords = takeRecords;
2155
+ });
2156
+
2157
+ window.CustomElements.addModule(function(scope) {
2158
+ var flags = scope.flags;
2159
+ function upgrade(node, isAttached) {
2160
+ if (node.localName === "template") {
2161
+ if (window.HTMLTemplateElement && HTMLTemplateElement.decorate) {
2162
+ HTMLTemplateElement.decorate(node);
2163
+ }
2164
+ }
2165
+ if (!node.__upgraded__ && node.nodeType === Node.ELEMENT_NODE) {
2166
+ var is = node.getAttribute("is");
2167
+ var definition = scope.getRegisteredDefinition(node.localName) || scope.getRegisteredDefinition(is);
2168
+ if (definition) {
2169
+ if (is && definition.tag == node.localName || !is && !definition.extends) {
2170
+ return upgradeWithDefinition(node, definition, isAttached);
2171
+ }
2172
+ }
2173
+ }
2174
+ }
2175
+ function upgradeWithDefinition(element, definition, isAttached) {
2176
+ flags.upgrade && console.group("upgrade:", element.localName);
2177
+ if (definition.is) {
2178
+ element.setAttribute("is", definition.is);
2179
+ }
2180
+ implementPrototype(element, definition);
2181
+ element.__upgraded__ = true;
2182
+ created(element);
2183
+ if (isAttached) {
2184
+ scope.attached(element);
2185
+ }
2186
+ scope.upgradeSubtree(element, isAttached);
2187
+ flags.upgrade && console.groupEnd();
2188
+ return element;
2189
+ }
2190
+ function implementPrototype(element, definition) {
2191
+ if (Object.__proto__) {
2192
+ element.__proto__ = definition.prototype;
2193
+ } else {
2194
+ customMixin(element, definition.prototype, definition.native);
2195
+ element.__proto__ = definition.prototype;
2196
+ }
2197
+ }
2198
+ function customMixin(inTarget, inSrc, inNative) {
2199
+ var used = {};
2200
+ var p = inSrc;
2201
+ while (p !== inNative && p !== HTMLElement.prototype) {
2202
+ var keys = Object.getOwnPropertyNames(p);
2203
+ for (var i = 0, k; k = keys[i]; i++) {
2204
+ if (!used[k]) {
2205
+ Object.defineProperty(inTarget, k, Object.getOwnPropertyDescriptor(p, k));
2206
+ used[k] = 1;
2207
+ }
2208
+ }
2209
+ p = Object.getPrototypeOf(p);
2210
+ }
2211
+ }
2212
+ function created(element) {
2213
+ if (element.createdCallback) {
2214
+ element.createdCallback();
2215
+ }
2216
+ }
2217
+ scope.upgrade = upgrade;
2218
+ scope.upgradeWithDefinition = upgradeWithDefinition;
2219
+ scope.implementPrototype = implementPrototype;
2220
+ });
2221
+
2222
+ window.CustomElements.addModule(function(scope) {
2223
+ var isIE = scope.isIE;
2224
+ var upgradeDocumentTree = scope.upgradeDocumentTree;
2225
+ var upgradeAll = scope.upgradeAll;
2226
+ var upgradeWithDefinition = scope.upgradeWithDefinition;
2227
+ var implementPrototype = scope.implementPrototype;
2228
+ var useNative = scope.useNative;
2229
+ function register(name, options) {
2230
+ var definition = options || {};
2231
+ if (!name) {
2232
+ throw new Error("document.registerElement: first argument `name` must not be empty");
2233
+ }
2234
+ if (name.indexOf("-") < 0) {
2235
+ throw new Error("document.registerElement: first argument ('name') must contain a dash ('-'). Argument provided was '" + String(name) + "'.");
2236
+ }
2237
+ if (isReservedTag(name)) {
2238
+ throw new Error("Failed to execute 'registerElement' on 'Document': Registration failed for type '" + String(name) + "'. The type name is invalid.");
2239
+ }
2240
+ if (getRegisteredDefinition(name)) {
2241
+ throw new Error("DuplicateDefinitionError: a type with name '" + String(name) + "' is already registered");
2242
+ }
2243
+ if (!definition.prototype) {
2244
+ definition.prototype = Object.create(HTMLElement.prototype);
2245
+ }
2246
+ definition.__name = name.toLowerCase();
2247
+ definition.lifecycle = definition.lifecycle || {};
2248
+ definition.ancestry = ancestry(definition.extends);
2249
+ resolveTagName(definition);
2250
+ resolvePrototypeChain(definition);
2251
+ overrideAttributeApi(definition.prototype);
2252
+ registerDefinition(definition.__name, definition);
2253
+ definition.ctor = generateConstructor(definition);
2254
+ definition.ctor.prototype = definition.prototype;
2255
+ definition.prototype.constructor = definition.ctor;
2256
+ if (scope.ready) {
2257
+ upgradeDocumentTree(document);
2258
+ }
2259
+ return definition.ctor;
2260
+ }
2261
+ function overrideAttributeApi(prototype) {
2262
+ if (prototype.setAttribute._polyfilled) {
2263
+ return;
2264
+ }
2265
+ var setAttribute = prototype.setAttribute;
2266
+ prototype.setAttribute = function(name, value) {
2267
+ changeAttribute.call(this, name, value, setAttribute);
2268
+ };
2269
+ var removeAttribute = prototype.removeAttribute;
2270
+ prototype.removeAttribute = function(name) {
2271
+ changeAttribute.call(this, name, null, removeAttribute);
2272
+ };
2273
+ prototype.setAttribute._polyfilled = true;
2274
+ }
2275
+ function changeAttribute(name, value, operation) {
2276
+ name = name.toLowerCase();
2277
+ var oldValue = this.getAttribute(name);
2278
+ operation.apply(this, arguments);
2279
+ var newValue = this.getAttribute(name);
2280
+ if (this.attributeChangedCallback && newValue !== oldValue) {
2281
+ this.attributeChangedCallback(name, oldValue, newValue);
2282
+ }
2283
+ }
2284
+ function isReservedTag(name) {
2285
+ for (var i = 0; i < reservedTagList.length; i++) {
2286
+ if (name === reservedTagList[i]) {
2287
+ return true;
2288
+ }
2289
+ }
2290
+ }
2291
+ var reservedTagList = [ "annotation-xml", "color-profile", "font-face", "font-face-src", "font-face-uri", "font-face-format", "font-face-name", "missing-glyph" ];
2292
+ function ancestry(extnds) {
2293
+ var extendee = getRegisteredDefinition(extnds);
2294
+ if (extendee) {
2295
+ return ancestry(extendee.extends).concat([ extendee ]);
2296
+ }
2297
+ return [];
2298
+ }
2299
+ function resolveTagName(definition) {
2300
+ var baseTag = definition.extends;
2301
+ for (var i = 0, a; a = definition.ancestry[i]; i++) {
2302
+ baseTag = a.is && a.tag;
2303
+ }
2304
+ definition.tag = baseTag || definition.__name;
2305
+ if (baseTag) {
2306
+ definition.is = definition.__name;
2307
+ }
2308
+ }
2309
+ function resolvePrototypeChain(definition) {
2310
+ if (!Object.__proto__) {
2311
+ var nativePrototype = HTMLElement.prototype;
2312
+ if (definition.is) {
2313
+ var inst = document.createElement(definition.tag);
2314
+ nativePrototype = Object.getPrototypeOf(inst);
2315
+ }
2316
+ var proto = definition.prototype, ancestor;
2317
+ var foundPrototype = false;
2318
+ while (proto) {
2319
+ if (proto == nativePrototype) {
2320
+ foundPrototype = true;
2321
+ }
2322
+ ancestor = Object.getPrototypeOf(proto);
2323
+ if (ancestor) {
2324
+ proto.__proto__ = ancestor;
2325
+ }
2326
+ proto = ancestor;
2327
+ }
2328
+ if (!foundPrototype) {
2329
+ console.warn(definition.tag + " prototype not found in prototype chain for " + definition.is);
2330
+ }
2331
+ definition.native = nativePrototype;
2332
+ }
2333
+ }
2334
+ function instantiate(definition) {
2335
+ return upgradeWithDefinition(domCreateElement(definition.tag), definition);
2336
+ }
2337
+ var registry = {};
2338
+ function getRegisteredDefinition(name) {
2339
+ if (name) {
2340
+ return registry[name.toLowerCase()];
2341
+ }
2342
+ }
2343
+ function registerDefinition(name, definition) {
2344
+ registry[name] = definition;
2345
+ }
2346
+ function generateConstructor(definition) {
2347
+ return function() {
2348
+ return instantiate(definition);
2349
+ };
2350
+ }
2351
+ var HTML_NAMESPACE = "http://www.w3.org/1999/xhtml";
2352
+ function createElementNS(namespace, tag, typeExtension) {
2353
+ if (namespace === HTML_NAMESPACE) {
2354
+ return createElement(tag, typeExtension);
2355
+ } else {
2356
+ return domCreateElementNS(namespace, tag);
2357
+ }
2358
+ }
2359
+ function createElement(tag, typeExtension) {
2360
+ if (tag) {
2361
+ tag = tag.toLowerCase();
2362
+ }
2363
+ if (typeExtension) {
2364
+ typeExtension = typeExtension.toLowerCase();
2365
+ }
2366
+ var definition = getRegisteredDefinition(typeExtension || tag);
2367
+ if (definition) {
2368
+ if (tag == definition.tag && typeExtension == definition.is) {
2369
+ return new definition.ctor();
2370
+ }
2371
+ if (!typeExtension && !definition.is) {
2372
+ return new definition.ctor();
2373
+ }
2374
+ }
2375
+ var element;
2376
+ if (typeExtension) {
2377
+ element = createElement(tag);
2378
+ element.setAttribute("is", typeExtension);
2379
+ return element;
2380
+ }
2381
+ element = domCreateElement(tag);
2382
+ if (tag.indexOf("-") >= 0) {
2383
+ implementPrototype(element, HTMLElement);
2384
+ }
2385
+ return element;
2386
+ }
2387
+ var domCreateElement = document.createElement.bind(document);
2388
+ var domCreateElementNS = document.createElementNS.bind(document);
2389
+ var isInstance;
2390
+ if (!Object.__proto__ && !useNative) {
2391
+ isInstance = function(obj, ctor) {
2392
+ if (obj instanceof ctor) {
2393
+ return true;
2394
+ }
2395
+ var p = obj;
2396
+ while (p) {
2397
+ if (p === ctor.prototype) {
2398
+ return true;
2399
+ }
2400
+ p = p.__proto__;
2401
+ }
2402
+ return false;
2403
+ };
2404
+ } else {
2405
+ isInstance = function(obj, base) {
2406
+ return obj instanceof base;
2407
+ };
2408
+ }
2409
+ function wrapDomMethodToForceUpgrade(obj, methodName) {
2410
+ var orig = obj[methodName];
2411
+ obj[methodName] = function() {
2412
+ var n = orig.apply(this, arguments);
2413
+ upgradeAll(n);
2414
+ return n;
2415
+ };
2416
+ }
2417
+ wrapDomMethodToForceUpgrade(Node.prototype, "cloneNode");
2418
+ wrapDomMethodToForceUpgrade(document, "importNode");
2419
+ if (isIE) {
2420
+ (function() {
2421
+ var importNode = document.importNode;
2422
+ document.importNode = function() {
2423
+ var n = importNode.apply(document, arguments);
2424
+ if (n.nodeType == n.DOCUMENT_FRAGMENT_NODE) {
2425
+ var f = document.createDocumentFragment();
2426
+ f.appendChild(n);
2427
+ return f;
2428
+ } else {
2429
+ return n;
2430
+ }
2431
+ };
2432
+ })();
2433
+ }
2434
+ document.registerElement = register;
2435
+ document.createElement = createElement;
2436
+ document.createElementNS = createElementNS;
2437
+ scope.registry = registry;
2438
+ scope.instanceof = isInstance;
2439
+ scope.reservedTagList = reservedTagList;
2440
+ scope.getRegisteredDefinition = getRegisteredDefinition;
2441
+ document.register = document.registerElement;
2442
+ });
2443
+
2444
+ (function(scope) {
2445
+ var useNative = scope.useNative;
2446
+ var initializeModules = scope.initializeModules;
2447
+ var isIE = scope.isIE;
2448
+ if (useNative) {
2449
+ var nop = function() {};
2450
+ scope.watchShadow = nop;
2451
+ scope.upgrade = nop;
2452
+ scope.upgradeAll = nop;
2453
+ scope.upgradeDocumentTree = nop;
2454
+ scope.upgradeSubtree = nop;
2455
+ scope.takeRecords = nop;
2456
+ scope.instanceof = function(obj, base) {
2457
+ return obj instanceof base;
2458
+ };
2459
+ } else {
2460
+ initializeModules();
2461
+ }
2462
+ var upgradeDocumentTree = scope.upgradeDocumentTree;
2463
+ var upgradeDocument = scope.upgradeDocument;
2464
+ if (!window.wrap) {
2465
+ if (window.ShadowDOMPolyfill) {
2466
+ window.wrap = window.ShadowDOMPolyfill.wrapIfNeeded;
2467
+ window.unwrap = window.ShadowDOMPolyfill.unwrapIfNeeded;
2468
+ } else {
2469
+ window.wrap = window.unwrap = function(node) {
2470
+ return node;
2471
+ };
2472
+ }
2473
+ }
2474
+ if (window.HTMLImports) {
2475
+ window.HTMLImports.__importsParsingHook = function(elt) {
2476
+ if (elt.import) {
2477
+ upgradeDocument(wrap(elt.import));
2478
+ }
2479
+ };
2480
+ }
2481
+ function bootstrap() {
2482
+ upgradeDocumentTree(window.wrap(document));
2483
+ window.CustomElements.ready = true;
2484
+ var requestAnimationFrame = window.requestAnimationFrame || function(f) {
2485
+ setTimeout(f, 16);
2486
+ };
2487
+ requestAnimationFrame(function() {
2488
+ setTimeout(function() {
2489
+ window.CustomElements.readyTime = Date.now();
2490
+ if (window.HTMLImports) {
2491
+ window.CustomElements.elapsed = window.CustomElements.readyTime - window.HTMLImports.readyTime;
2492
+ }
2493
+ document.dispatchEvent(new CustomEvent("WebComponentsReady", {
2494
+ bubbles: true
2495
+ }));
2496
+ });
2497
+ });
2498
+ }
2499
+ if (document.readyState === "complete" || scope.flags.eager) {
2500
+ bootstrap();
2501
+ } else if (document.readyState === "interactive" && !window.attachEvent && (!window.HTMLImports || window.HTMLImports.ready)) {
2502
+ bootstrap();
2503
+ } else {
2504
+ var loadEvent = window.HTMLImports && !window.HTMLImports.ready ? "HTMLImportsLoaded" : "DOMContentLoaded";
2505
+ window.addEventListener(loadEvent, bootstrap);
2506
+ }
2507
+ })(window.CustomElements);
2508
+
2509
+ (function(scope) {
2510
+ var style = document.createElement("style");
2511
+ style.textContent = "" + "body {" + "transition: opacity ease-in 0.2s;" + " } \n" + "body[unresolved] {" + "opacity: 0; display: block; overflow: hidden; position: relative;" + " } \n";
2512
+ var head = document.querySelector("head");
2513
+ head.insertBefore(style, head.firstChild);
2514
+ })(window.WebComponents);
2515
+ /*!
2516
+ * PEP v0.4.0 | https://github.com/jquery/PEP
2517
+ * Copyright jQuery Foundation and other contributors | http://jquery.org/license
2518
+ */
2519
+ (function (global, factory) {
2520
+ typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
2521
+ typeof define === 'function' && define.amd ? define(factory) :
2522
+ global.PointerEventsPolyfill = factory()
2523
+ }(this, function () { 'use strict';
2524
+
2525
+ /**
2526
+ * This is the constructor for new PointerEvents.
2527
+ *
2528
+ * New Pointer Events must be given a type, and an optional dictionary of
2529
+ * initialization properties.
2530
+ *
2531
+ * Due to certain platform requirements, events returned from the constructor
2532
+ * identify as MouseEvents.
2533
+ *
2534
+ * @constructor
2535
+ * @param {String} inType The type of the event to create.
2536
+ * @param {Object} [inDict] An optional dictionary of initial event properties.
2537
+ * @return {Event} A new PointerEvent of type `inType`, initialized with properties from `inDict`.
2538
+ */
2539
+ var MOUSE_PROPS = [
2540
+ 'bubbles',
2541
+ 'cancelable',
2542
+ 'view',
2543
+ 'detail',
2544
+ 'screenX',
2545
+ 'screenY',
2546
+ 'clientX',
2547
+ 'clientY',
2548
+ 'ctrlKey',
2549
+ 'altKey',
2550
+ 'shiftKey',
2551
+ 'metaKey',
2552
+ 'button',
2553
+ 'relatedTarget',
2554
+ 'pageX',
2555
+ 'pageY'
2556
+ ];
2557
+
2558
+ var MOUSE_DEFAULTS = [
2559
+ false,
2560
+ false,
2561
+ null,
2562
+ null,
2563
+ 0,
2564
+ 0,
2565
+ 0,
2566
+ 0,
2567
+ false,
2568
+ false,
2569
+ false,
2570
+ false,
2571
+ 0,
2572
+ null,
2573
+ 0,
2574
+ 0
2575
+ ];
2576
+
2577
+ function PointerEvent(inType, inDict) {
2578
+ inDict = inDict || Object.create(null);
2579
+
2580
+ var e = document.createEvent('Event');
2581
+ e.initEvent(inType, inDict.bubbles || false, inDict.cancelable || false);
2582
+
2583
+ // define inherited MouseEvent properties
2584
+ // skip bubbles and cancelable since they're set above in initEvent()
2585
+ for (var i = 2, p; i < MOUSE_PROPS.length; i++) {
2586
+ p = MOUSE_PROPS[i];
2587
+ e[p] = inDict[p] || MOUSE_DEFAULTS[i];
2588
+ }
2589
+ e.buttons = inDict.buttons || 0;
2590
+
2591
+ // Spec requires that pointers without pressure specified use 0.5 for down
2592
+ // state and 0 for up state.
2593
+ var pressure = 0;
2594
+ if (inDict.pressure) {
2595
+ pressure = inDict.pressure;
2596
+ } else {
2597
+ pressure = e.buttons ? 0.5 : 0;
2598
+ }
2599
+
2600
+ // add x/y properties aliased to clientX/Y
2601
+ e.x = e.clientX;
2602
+ e.y = e.clientY;
2603
+
2604
+ // define the properties of the PointerEvent interface
2605
+ e.pointerId = inDict.pointerId || 0;
2606
+ e.width = inDict.width || 0;
2607
+ e.height = inDict.height || 0;
2608
+ e.pressure = pressure;
2609
+ e.tiltX = inDict.tiltX || 0;
2610
+ e.tiltY = inDict.tiltY || 0;
2611
+ e.pointerType = inDict.pointerType || '';
2612
+ e.hwTimestamp = inDict.hwTimestamp || 0;
2613
+ e.isPrimary = inDict.isPrimary || false;
2614
+ return e;
2615
+ }
2616
+
2617
+ var _PointerEvent = PointerEvent;
2618
+
2619
+ /**
2620
+ * This module implements a map of pointer states
2621
+ */
2622
+ var USE_MAP = window.Map && window.Map.prototype.forEach;
2623
+ var PointerMap = USE_MAP ? Map : SparseArrayMap;
2624
+
2625
+ function SparseArrayMap() {
2626
+ this.array = [];
2627
+ this.size = 0;
2628
+ }
2629
+
2630
+ SparseArrayMap.prototype = {
2631
+ set: function(k, v) {
2632
+ if (v === undefined) {
2633
+ return this.delete(k);
2634
+ }
2635
+ if (!this.has(k)) {
2636
+ this.size++;
2637
+ }
2638
+ this.array[k] = v;
2639
+ },
2640
+ has: function(k) {
2641
+ return this.array[k] !== undefined;
2642
+ },
2643
+ delete: function(k) {
2644
+ if (this.has(k)) {
2645
+ delete this.array[k];
2646
+ this.size--;
2647
+ }
2648
+ },
2649
+ get: function(k) {
2650
+ return this.array[k];
2651
+ },
2652
+ clear: function() {
2653
+ this.array.length = 0;
2654
+ this.size = 0;
2655
+ },
2656
+
2657
+ // return value, key, map
2658
+ forEach: function(callback, thisArg) {
2659
+ return this.array.forEach(function(v, k) {
2660
+ callback.call(thisArg, v, k, this);
2661
+ }, this);
2662
+ }
2663
+ };
2664
+
2665
+ var _pointermap = PointerMap;
2666
+
2667
+ var CLONE_PROPS = [
2668
+
2669
+ // MouseEvent
2670
+ 'bubbles',
2671
+ 'cancelable',
2672
+ 'view',
2673
+ 'detail',
2674
+ 'screenX',
2675
+ 'screenY',
2676
+ 'clientX',
2677
+ 'clientY',
2678
+ 'ctrlKey',
2679
+ 'altKey',
2680
+ 'shiftKey',
2681
+ 'metaKey',
2682
+ 'button',
2683
+ 'relatedTarget',
2684
+
2685
+ // DOM Level 3
2686
+ 'buttons',
2687
+
2688
+ // PointerEvent
2689
+ 'pointerId',
2690
+ 'width',
2691
+ 'height',
2692
+ 'pressure',
2693
+ 'tiltX',
2694
+ 'tiltY',
2695
+ 'pointerType',
2696
+ 'hwTimestamp',
2697
+ 'isPrimary',
2698
+
2699
+ // event instance
2700
+ 'type',
2701
+ 'target',
2702
+ 'currentTarget',
2703
+ 'which',
2704
+ 'pageX',
2705
+ 'pageY',
2706
+ 'timeStamp'
2707
+ ];
2708
+
2709
+ var CLONE_DEFAULTS = [
2710
+
2711
+ // MouseEvent
2712
+ false,
2713
+ false,
2714
+ null,
2715
+ null,
2716
+ 0,
2717
+ 0,
2718
+ 0,
2719
+ 0,
2720
+ false,
2721
+ false,
2722
+ false,
2723
+ false,
2724
+ 0,
2725
+ null,
2726
+
2727
+ // DOM Level 3
2728
+ 0,
2729
+
2730
+ // PointerEvent
2731
+ 0,
2732
+ 0,
2733
+ 0,
2734
+ 0,
2735
+ 0,
2736
+ 0,
2737
+ '',
2738
+ 0,
2739
+ false,
2740
+
2741
+ // event instance
2742
+ '',
2743
+ null,
2744
+ null,
2745
+ 0,
2746
+ 0,
2747
+ 0,
2748
+ 0
2749
+ ];
2750
+
2751
+ var HAS_SVG_INSTANCE = (typeof SVGElementInstance !== 'undefined');
2752
+
2753
+ /**
2754
+ * This module is for normalizing events. Mouse and Touch events will be
2755
+ * collected here, and fire PointerEvents that have the same semantics, no
2756
+ * matter the source.
2757
+ * Events fired:
2758
+ * - pointerdown: a pointing is added
2759
+ * - pointerup: a pointer is removed
2760
+ * - pointermove: a pointer is moved
2761
+ * - pointerover: a pointer crosses into an element
2762
+ * - pointerout: a pointer leaves an element
2763
+ * - pointercancel: a pointer will no longer generate events
2764
+ */
2765
+ var dispatcher = {
2766
+ pointermap: new _pointermap(),
2767
+ eventMap: Object.create(null),
2768
+ captureInfo: Object.create(null),
2769
+
2770
+ // Scope objects for native events.
2771
+ // This exists for ease of testing.
2772
+ eventSources: Object.create(null),
2773
+ eventSourceList: [],
2774
+ /**
2775
+ * Add a new event source that will generate pointer events.
2776
+ *
2777
+ * `inSource` must contain an array of event names named `events`, and
2778
+ * functions with the names specified in the `events` array.
2779
+ * @param {string} name A name for the event source
2780
+ * @param {Object} source A new source of platform events.
2781
+ */
2782
+ registerSource: function(name, source) {
2783
+ var s = source;
2784
+ var newEvents = s.events;
2785
+ if (newEvents) {
2786
+ newEvents.forEach(function(e) {
2787
+ if (s[e]) {
2788
+ this.eventMap[e] = s[e].bind(s);
2789
+ }
2790
+ }, this);
2791
+ this.eventSources[name] = s;
2792
+ this.eventSourceList.push(s);
2793
+ }
2794
+ },
2795
+ register: function(element) {
2796
+ var l = this.eventSourceList.length;
2797
+ for (var i = 0, es; (i < l) && (es = this.eventSourceList[i]); i++) {
2798
+
2799
+ // call eventsource register
2800
+ es.register.call(es, element);
2801
+ }
2802
+ },
2803
+ unregister: function(element) {
2804
+ var l = this.eventSourceList.length;
2805
+ for (var i = 0, es; (i < l) && (es = this.eventSourceList[i]); i++) {
2806
+
2807
+ // call eventsource register
2808
+ es.unregister.call(es, element);
2809
+ }
2810
+ },
2811
+ contains: /*scope.external.contains || */function(container, contained) {
2812
+ try {
2813
+ return container.contains(contained);
2814
+ } catch (ex) {
2815
+
2816
+ // most likely: https://bugzilla.mozilla.org/show_bug.cgi?id=208427
2817
+ return false;
2818
+ }
2819
+ },
2820
+
2821
+ // EVENTS
2822
+ down: function(inEvent) {
2823
+ inEvent.bubbles = true;
2824
+ this.fireEvent('pointerdown', inEvent);
2825
+ },
2826
+ move: function(inEvent) {
2827
+ inEvent.bubbles = true;
2828
+ this.fireEvent('pointermove', inEvent);
2829
+ },
2830
+ up: function(inEvent) {
2831
+ inEvent.bubbles = true;
2832
+ this.fireEvent('pointerup', inEvent);
2833
+ },
2834
+ enter: function(inEvent) {
2835
+ inEvent.bubbles = false;
2836
+ this.fireEvent('pointerenter', inEvent);
2837
+ },
2838
+ leave: function(inEvent) {
2839
+ inEvent.bubbles = false;
2840
+ this.fireEvent('pointerleave', inEvent);
2841
+ },
2842
+ over: function(inEvent) {
2843
+ inEvent.bubbles = true;
2844
+ this.fireEvent('pointerover', inEvent);
2845
+ },
2846
+ out: function(inEvent) {
2847
+ inEvent.bubbles = true;
2848
+ this.fireEvent('pointerout', inEvent);
2849
+ },
2850
+ cancel: function(inEvent) {
2851
+ inEvent.bubbles = true;
2852
+ this.fireEvent('pointercancel', inEvent);
2853
+ },
2854
+ leaveOut: function(event) {
2855
+ this.out(event);
2856
+ if (!this.contains(event.target, event.relatedTarget)) {
2857
+ this.leave(event);
2858
+ }
2859
+ },
2860
+ enterOver: function(event) {
2861
+ this.over(event);
2862
+ if (!this.contains(event.target, event.relatedTarget)) {
2863
+ this.enter(event);
2864
+ }
2865
+ },
2866
+
2867
+ // LISTENER LOGIC
2868
+ eventHandler: function(inEvent) {
2869
+
2870
+ // This is used to prevent multiple dispatch of pointerevents from
2871
+ // platform events. This can happen when two elements in different scopes
2872
+ // are set up to create pointer events, which is relevant to Shadow DOM.
2873
+ if (inEvent._handledByPE) {
2874
+ return;
2875
+ }
2876
+ var type = inEvent.type;
2877
+ var fn = this.eventMap && this.eventMap[type];
2878
+ if (fn) {
2879
+ fn(inEvent);
2880
+ }
2881
+ inEvent._handledByPE = true;
2882
+ },
2883
+
2884
+ // set up event listeners
2885
+ listen: function(target, events) {
2886
+ events.forEach(function(e) {
2887
+ this.addEvent(target, e);
2888
+ }, this);
2889
+ },
2890
+
2891
+ // remove event listeners
2892
+ unlisten: function(target, events) {
2893
+ events.forEach(function(e) {
2894
+ this.removeEvent(target, e);
2895
+ }, this);
2896
+ },
2897
+ addEvent: /*scope.external.addEvent || */function(target, eventName) {
2898
+ target.addEventListener(eventName, this.boundHandler);
2899
+ },
2900
+ removeEvent: /*scope.external.removeEvent || */function(target, eventName) {
2901
+ target.removeEventListener(eventName, this.boundHandler);
2902
+ },
2903
+
2904
+ // EVENT CREATION AND TRACKING
2905
+ /**
2906
+ * Creates a new Event of type `inType`, based on the information in
2907
+ * `inEvent`.
2908
+ *
2909
+ * @param {string} inType A string representing the type of event to create
2910
+ * @param {Event} inEvent A platform event with a target
2911
+ * @return {Event} A PointerEvent of type `inType`
2912
+ */
2913
+ makeEvent: function(inType, inEvent) {
2914
+
2915
+ // relatedTarget must be null if pointer is captured
2916
+ if (this.captureInfo[inEvent.pointerId]) {
2917
+ inEvent.relatedTarget = null;
2918
+ }
2919
+ var e = new _PointerEvent(inType, inEvent);
2920
+ if (inEvent.preventDefault) {
2921
+ e.preventDefault = inEvent.preventDefault;
2922
+ }
2923
+ e._target = e._target || inEvent.target;
2924
+ return e;
2925
+ },
2926
+
2927
+ // make and dispatch an event in one call
2928
+ fireEvent: function(inType, inEvent) {
2929
+ var e = this.makeEvent(inType, inEvent);
2930
+ return this.dispatchEvent(e);
2931
+ },
2932
+ /**
2933
+ * Returns a snapshot of inEvent, with writable properties.
2934
+ *
2935
+ * @param {Event} inEvent An event that contains properties to copy.
2936
+ * @return {Object} An object containing shallow copies of `inEvent`'s
2937
+ * properties.
2938
+ */
2939
+ cloneEvent: function(inEvent) {
2940
+ var eventCopy = Object.create(null);
2941
+ var p;
2942
+ for (var i = 0; i < CLONE_PROPS.length; i++) {
2943
+ p = CLONE_PROPS[i];
2944
+ eventCopy[p] = inEvent[p] || CLONE_DEFAULTS[i];
2945
+
2946
+ // Work around SVGInstanceElement shadow tree
2947
+ // Return the <use> element that is represented by the instance for Safari, Chrome, IE.
2948
+ // This is the behavior implemented by Firefox.
2949
+ if (HAS_SVG_INSTANCE && (p === 'target' || p === 'relatedTarget')) {
2950
+ if (eventCopy[p] instanceof SVGElementInstance) {
2951
+ eventCopy[p] = eventCopy[p].correspondingUseElement;
2952
+ }
2953
+ }
2954
+ }
2955
+
2956
+ // keep the semantics of preventDefault
2957
+ if (inEvent.preventDefault) {
2958
+ eventCopy.preventDefault = function() {
2959
+ inEvent.preventDefault();
2960
+ };
2961
+ }
2962
+ return eventCopy;
2963
+ },
2964
+ getTarget: function(inEvent) {
2965
+
2966
+ // if pointer capture is set, route all events for the specified pointerId
2967
+ // to the capture target
2968
+ return this.captureInfo[inEvent.pointerId] || inEvent._target;
2969
+ },
2970
+ setCapture: function(inPointerId, inTarget) {
2971
+ if (this.captureInfo[inPointerId]) {
2972
+ this.releaseCapture(inPointerId);
2973
+ }
2974
+ this.captureInfo[inPointerId] = inTarget;
2975
+ var e = document.createEvent('Event');
2976
+ e.initEvent('gotpointercapture', true, false);
2977
+ e.pointerId = inPointerId;
2978
+ this.implicitRelease = this.releaseCapture.bind(this, inPointerId);
2979
+ document.addEventListener('pointerup', this.implicitRelease);
2980
+ document.addEventListener('pointercancel', this.implicitRelease);
2981
+ e._target = inTarget;
2982
+ this.asyncDispatchEvent(e);
2983
+ },
2984
+ releaseCapture: function(inPointerId) {
2985
+ var t = this.captureInfo[inPointerId];
2986
+ if (t) {
2987
+ var e = document.createEvent('Event');
2988
+ e.initEvent('lostpointercapture', true, false);
2989
+ e.pointerId = inPointerId;
2990
+ this.captureInfo[inPointerId] = undefined;
2991
+ document.removeEventListener('pointerup', this.implicitRelease);
2992
+ document.removeEventListener('pointercancel', this.implicitRelease);
2993
+ e._target = t;
2994
+ this.asyncDispatchEvent(e);
2995
+ }
2996
+ },
2997
+ /**
2998
+ * Dispatches the event to its target.
2999
+ *
3000
+ * @param {Event} inEvent The event to be dispatched.
3001
+ * @return {Boolean} True if an event handler returns true, false otherwise.
3002
+ */
3003
+ dispatchEvent: /*scope.external.dispatchEvent || */function(inEvent) {
3004
+ var t = this.getTarget(inEvent);
3005
+ if (t) {
3006
+ return t.dispatchEvent(inEvent);
3007
+ }
3008
+ },
3009
+ asyncDispatchEvent: function(inEvent) {
3010
+ requestAnimationFrame(this.dispatchEvent.bind(this, inEvent));
3011
+ }
3012
+ };
3013
+ dispatcher.boundHandler = dispatcher.eventHandler.bind(dispatcher);
3014
+
3015
+ var _dispatcher = dispatcher;
3016
+
3017
+ var targeting = {
3018
+ shadow: function(inEl) {
3019
+ if (inEl) {
3020
+ return inEl.shadowRoot || inEl.webkitShadowRoot;
3021
+ }
3022
+ },
3023
+ canTarget: function(shadow) {
3024
+ return shadow && Boolean(shadow.elementFromPoint);
3025
+ },
3026
+ targetingShadow: function(inEl) {
3027
+ var s = this.shadow(inEl);
3028
+ if (this.canTarget(s)) {
3029
+ return s;
3030
+ }
3031
+ },
3032
+ olderShadow: function(shadow) {
3033
+ var os = shadow.olderShadowRoot;
3034
+ if (!os) {
3035
+ var se = shadow.querySelector('shadow');
3036
+ if (se) {
3037
+ os = se.olderShadowRoot;
3038
+ }
3039
+ }
3040
+ return os;
3041
+ },
3042
+ allShadows: function(element) {
3043
+ var shadows = [];
3044
+ var s = this.shadow(element);
3045
+ while (s) {
3046
+ shadows.push(s);
3047
+ s = this.olderShadow(s);
3048
+ }
3049
+ return shadows;
3050
+ },
3051
+ searchRoot: function(inRoot, x, y) {
3052
+ if (inRoot) {
3053
+ var t = inRoot.elementFromPoint(x, y);
3054
+ var st, sr;
3055
+
3056
+ // is element a shadow host?
3057
+ sr = this.targetingShadow(t);
3058
+ while (sr) {
3059
+
3060
+ // find the the element inside the shadow root
3061
+ st = sr.elementFromPoint(x, y);
3062
+ if (!st) {
3063
+
3064
+ // check for older shadows
3065
+ sr = this.olderShadow(sr);
3066
+ } else {
3067
+
3068
+ // shadowed element may contain a shadow root
3069
+ var ssr = this.targetingShadow(st);
3070
+ return this.searchRoot(ssr, x, y) || st;
3071
+ }
3072
+ }
3073
+
3074
+ // light dom element is the target
3075
+ return t;
3076
+ }
3077
+ },
3078
+ owner: function(element) {
3079
+ var s = element;
3080
+
3081
+ // walk up until you hit the shadow root or document
3082
+ while (s.parentNode) {
3083
+ s = s.parentNode;
3084
+ }
3085
+
3086
+ // the owner element is expected to be a Document or ShadowRoot
3087
+ if (s.nodeType !== Node.DOCUMENT_NODE && s.nodeType !== Node.DOCUMENT_FRAGMENT_NODE) {
3088
+ s = document;
3089
+ }
3090
+ return s;
3091
+ },
3092
+ findTarget: function(inEvent) {
3093
+ var x = inEvent.clientX;
3094
+ var y = inEvent.clientY;
3095
+
3096
+ // if the listener is in the shadow root, it is much faster to start there
3097
+ var s = this.owner(inEvent.target);
3098
+
3099
+ // if x, y is not in this root, fall back to document search
3100
+ if (!s.elementFromPoint(x, y)) {
3101
+ s = document;
3102
+ }
3103
+ return this.searchRoot(s, x, y);
3104
+ }
3105
+ };
3106
+
3107
+ /**
3108
+ * This module uses Mutation Observers to dynamically adjust which nodes will
3109
+ * generate Pointer Events.
3110
+ *
3111
+ * All nodes that wish to generate Pointer Events must have the attribute
3112
+ * `touch-action` set to `none`.
3113
+ */
3114
+ var forEach = Array.prototype.forEach.call.bind(Array.prototype.forEach);
3115
+ var map = Array.prototype.map.call.bind(Array.prototype.map);
3116
+ var toArray = Array.prototype.slice.call.bind(Array.prototype.slice);
3117
+ var filter = Array.prototype.filter.call.bind(Array.prototype.filter);
3118
+ var MO = window.MutationObserver || window.WebKitMutationObserver;
3119
+ var SELECTOR = '[touch-action]';
3120
+ var OBSERVER_INIT = {
3121
+ subtree: true,
3122
+ childList: true,
3123
+ attributes: true,
3124
+ attributeOldValue: true,
3125
+ attributeFilter: ['touch-action']
3126
+ };
3127
+
3128
+ function Installer(add, remove, changed, binder) {
3129
+ this.addCallback = add.bind(binder);
3130
+ this.removeCallback = remove.bind(binder);
3131
+ this.changedCallback = changed.bind(binder);
3132
+ if (MO) {
3133
+ this.observer = new MO(this.mutationWatcher.bind(this));
3134
+ }
3135
+ }
3136
+
3137
+ Installer.prototype = {
3138
+ watchSubtree: function(target) {
3139
+
3140
+ // Only watch scopes that can target find, as these are top-level.
3141
+ // Otherwise we can see duplicate additions and removals that add noise.
3142
+ //
3143
+ // TODO(dfreedman): For some instances with ShadowDOMPolyfill, we can see
3144
+ // a removal without an insertion when a node is redistributed among
3145
+ // shadows. Since it all ends up correct in the document, watching only
3146
+ // the document will yield the correct mutations to watch.
3147
+ if (this.observer && targeting.canTarget(target)) {
3148
+ this.observer.observe(target, OBSERVER_INIT);
3149
+ }
3150
+ },
3151
+ enableOnSubtree: function(target) {
3152
+ this.watchSubtree(target);
3153
+ if (target === document && document.readyState !== 'complete') {
3154
+ this.installOnLoad();
3155
+ } else {
3156
+ this.installNewSubtree(target);
3157
+ }
3158
+ },
3159
+ installNewSubtree: function(target) {
3160
+ forEach(this.findElements(target), this.addElement, this);
3161
+ },
3162
+ findElements: function(target) {
3163
+ if (target.querySelectorAll) {
3164
+ return target.querySelectorAll(SELECTOR);
3165
+ }
3166
+ return [];
3167
+ },
3168
+ removeElement: function(el) {
3169
+ this.removeCallback(el);
3170
+ },
3171
+ addElement: function(el) {
3172
+ this.addCallback(el);
3173
+ },
3174
+ elementChanged: function(el, oldValue) {
3175
+ this.changedCallback(el, oldValue);
3176
+ },
3177
+ concatLists: function(accum, list) {
3178
+ return accum.concat(toArray(list));
3179
+ },
3180
+
3181
+ // register all touch-action = none nodes on document load
3182
+ installOnLoad: function() {
3183
+ document.addEventListener('readystatechange', function() {
3184
+ if (document.readyState === 'complete') {
3185
+ this.installNewSubtree(document);
3186
+ }
3187
+ }.bind(this));
3188
+ },
3189
+ isElement: function(n) {
3190
+ return n.nodeType === Node.ELEMENT_NODE;
3191
+ },
3192
+ flattenMutationTree: function(inNodes) {
3193
+
3194
+ // find children with touch-action
3195
+ var tree = map(inNodes, this.findElements, this);
3196
+
3197
+ // make sure the added nodes are accounted for
3198
+ tree.push(filter(inNodes, this.isElement));
3199
+
3200
+ // flatten the list
3201
+ return tree.reduce(this.concatLists, []);
3202
+ },
3203
+ mutationWatcher: function(mutations) {
3204
+ mutations.forEach(this.mutationHandler, this);
3205
+ },
3206
+ mutationHandler: function(m) {
3207
+ if (m.type === 'childList') {
3208
+ var added = this.flattenMutationTree(m.addedNodes);
3209
+ added.forEach(this.addElement, this);
3210
+ var removed = this.flattenMutationTree(m.removedNodes);
3211
+ removed.forEach(this.removeElement, this);
3212
+ } else if (m.type === 'attributes') {
3213
+ this.elementChanged(m.target, m.oldValue);
3214
+ }
3215
+ }
3216
+ };
3217
+
3218
+ var installer = Installer;
3219
+
3220
+ function shadowSelector(v) {
3221
+ return 'body /shadow-deep/ ' + selector(v);
3222
+ }
3223
+ function selector(v) {
3224
+ return '[touch-action="' + v + '"]';
3225
+ }
3226
+ function rule(v) {
3227
+ return '{ -ms-touch-action: ' + v + '; touch-action: ' + v + '; touch-action-delay: none; }';
3228
+ }
3229
+ var attrib2css = [
3230
+ 'none',
3231
+ 'auto',
3232
+ 'pan-x',
3233
+ 'pan-y',
3234
+ {
3235
+ rule: 'pan-x pan-y',
3236
+ selectors: [
3237
+ 'pan-x pan-y',
3238
+ 'pan-y pan-x'
3239
+ ]
3240
+ }
3241
+ ];
3242
+ var styles = '';
3243
+
3244
+ // only install stylesheet if the browser has touch action support
3245
+ var hasNativePE = window.PointerEvent || window.MSPointerEvent;
3246
+
3247
+ // only add shadow selectors if shadowdom is supported
3248
+ var hasShadowRoot = !window.ShadowDOMPolyfill && document.head.createShadowRoot;
3249
+
3250
+ function applyAttributeStyles() {
3251
+ if (hasNativePE) {
3252
+ attrib2css.forEach(function(r) {
3253
+ if (String(r) === r) {
3254
+ styles += selector(r) + rule(r) + '\n';
3255
+ if (hasShadowRoot) {
3256
+ styles += shadowSelector(r) + rule(r) + '\n';
3257
+ }
3258
+ } else {
3259
+ styles += r.selectors.map(selector) + rule(r.rule) + '\n';
3260
+ if (hasShadowRoot) {
3261
+ styles += r.selectors.map(shadowSelector) + rule(r.rule) + '\n';
3262
+ }
3263
+ }
3264
+ });
3265
+
3266
+ var el = document.createElement('style');
3267
+ el.textContent = styles;
3268
+ document.head.appendChild(el);
3269
+ }
3270
+ }
3271
+
3272
+ var mouse__pointermap = _dispatcher.pointermap;
3273
+
3274
+ // radius around touchend that swallows mouse events
3275
+ var DEDUP_DIST = 25;
3276
+
3277
+ // left, middle, right, back, forward
3278
+ var BUTTON_TO_BUTTONS = [1, 4, 2, 8, 16];
3279
+
3280
+ var HAS_BUTTONS = false;
3281
+ try {
3282
+ HAS_BUTTONS = new MouseEvent('test', { buttons: 1 }).buttons === 1;
3283
+ } catch (e) {}
3284
+
3285
+ // handler block for native mouse events
3286
+ var mouseEvents = {
3287
+ POINTER_ID: 1,
3288
+ POINTER_TYPE: 'mouse',
3289
+ events: [
3290
+ 'mousedown',
3291
+ 'mousemove',
3292
+ 'mouseup',
3293
+ 'mouseover',
3294
+ 'mouseout'
3295
+ ],
3296
+ register: function(target) {
3297
+ _dispatcher.listen(target, this.events);
3298
+ },
3299
+ unregister: function(target) {
3300
+ _dispatcher.unlisten(target, this.events);
3301
+ },
3302
+ lastTouches: [],
3303
+
3304
+ // collide with the global mouse listener
3305
+ isEventSimulatedFromTouch: function(inEvent) {
3306
+ var lts = this.lastTouches;
3307
+ var x = inEvent.clientX;
3308
+ var y = inEvent.clientY;
3309
+ for (var i = 0, l = lts.length, t; i < l && (t = lts[i]); i++) {
3310
+
3311
+ // simulated mouse events will be swallowed near a primary touchend
3312
+ var dx = Math.abs(x - t.x);
3313
+ var dy = Math.abs(y - t.y);
3314
+ if (dx <= DEDUP_DIST && dy <= DEDUP_DIST) {
3315
+ return true;
3316
+ }
3317
+ }
3318
+ },
3319
+ prepareEvent: function(inEvent) {
3320
+ var e = _dispatcher.cloneEvent(inEvent);
3321
+
3322
+ // forward mouse preventDefault
3323
+ var pd = e.preventDefault;
3324
+ e.preventDefault = function() {
3325
+ inEvent.preventDefault();
3326
+ pd();
3327
+ };
3328
+ e.pointerId = this.POINTER_ID;
3329
+ e.isPrimary = true;
3330
+ e.pointerType = this.POINTER_TYPE;
3331
+ return e;
3332
+ },
3333
+ prepareButtonsForMove: function(e, inEvent) {
3334
+ var p = mouse__pointermap.get(this.POINTER_ID);
3335
+ e.buttons = p ? p.buttons : 0;
3336
+ inEvent.buttons = e.buttons;
3337
+ },
3338
+ mousedown: function(inEvent) {
3339
+ if (!this.isEventSimulatedFromTouch(inEvent)) {
3340
+ var p = mouse__pointermap.get(this.POINTER_ID);
3341
+ var e = this.prepareEvent(inEvent);
3342
+ if (!HAS_BUTTONS) {
3343
+ e.buttons = BUTTON_TO_BUTTONS[e.button];
3344
+ if (p) { e.buttons |= p.buttons; }
3345
+ inEvent.buttons = e.buttons;
3346
+ }
3347
+ mouse__pointermap.set(this.POINTER_ID, inEvent);
3348
+ if (!p) {
3349
+ _dispatcher.down(e);
3350
+ } else {
3351
+ _dispatcher.move(e);
3352
+ }
3353
+ }
3354
+ },
3355
+ mousemove: function(inEvent) {
3356
+ if (!this.isEventSimulatedFromTouch(inEvent)) {
3357
+ var e = this.prepareEvent(inEvent);
3358
+ if (!HAS_BUTTONS) { this.prepareButtonsForMove(e, inEvent); }
3359
+ _dispatcher.move(e);
3360
+ }
3361
+ },
3362
+ mouseup: function(inEvent) {
3363
+ if (!this.isEventSimulatedFromTouch(inEvent)) {
3364
+ var p = mouse__pointermap.get(this.POINTER_ID);
3365
+ var e = this.prepareEvent(inEvent);
3366
+ if (!HAS_BUTTONS) {
3367
+ var up = BUTTON_TO_BUTTONS[e.button];
3368
+
3369
+ // Produces wrong state of buttons in Browsers without `buttons` support
3370
+ // when a mouse button that was pressed outside the document is released
3371
+ // inside and other buttons are still pressed down.
3372
+ e.buttons = p ? p.buttons & ~up : 0;
3373
+ inEvent.buttons = e.buttons;
3374
+ }
3375
+ mouse__pointermap.set(this.POINTER_ID, inEvent);
3376
+ if (e.buttons === 0 || e.buttons === BUTTON_TO_BUTTONS[e.button]) {
3377
+ this.cleanupMouse();
3378
+ _dispatcher.up(e);
3379
+ } else {
3380
+ _dispatcher.move(e);
3381
+ }
3382
+ }
3383
+ },
3384
+ mouseover: function(inEvent) {
3385
+ if (!this.isEventSimulatedFromTouch(inEvent)) {
3386
+ var e = this.prepareEvent(inEvent);
3387
+ if (!HAS_BUTTONS) { this.prepareButtonsForMove(e, inEvent); }
3388
+ _dispatcher.enterOver(e);
3389
+ }
3390
+ },
3391
+ mouseout: function(inEvent) {
3392
+ if (!this.isEventSimulatedFromTouch(inEvent)) {
3393
+ var e = this.prepareEvent(inEvent);
3394
+ if (!HAS_BUTTONS) { this.prepareButtonsForMove(e, inEvent); }
3395
+ _dispatcher.leaveOut(e);
3396
+ }
3397
+ },
3398
+ cancel: function(inEvent) {
3399
+ var e = this.prepareEvent(inEvent);
3400
+ _dispatcher.cancel(e);
3401
+ this.cleanupMouse();
3402
+ },
3403
+ cleanupMouse: function() {
3404
+ mouse__pointermap.delete(this.POINTER_ID);
3405
+ }
3406
+ };
3407
+
3408
+ var mouse = mouseEvents;
3409
+
3410
+ var captureInfo = _dispatcher.captureInfo;
3411
+ var findTarget = targeting.findTarget.bind(targeting);
3412
+ var allShadows = targeting.allShadows.bind(targeting);
3413
+ var touch__pointermap = _dispatcher.pointermap;
3414
+
3415
+ // This should be long enough to ignore compat mouse events made by touch
3416
+ var DEDUP_TIMEOUT = 2500;
3417
+ var CLICK_COUNT_TIMEOUT = 200;
3418
+ var ATTRIB = 'touch-action';
3419
+ var INSTALLER;
3420
+
3421
+ // The presence of touch event handlers blocks scrolling, and so we must be careful to
3422
+ // avoid adding handlers unnecessarily. Chrome plans to add a touch-action-delay property
3423
+ // (crbug.com/329559) to address this, and once we have that we can opt-in to a simpler
3424
+ // handler registration mechanism. Rather than try to predict how exactly to opt-in to
3425
+ // that we'll just leave this disabled until there is a build of Chrome to test.
3426
+ var HAS_TOUCH_ACTION_DELAY = false;
3427
+
3428
+ // handler block for native touch events
3429
+ var touchEvents = {
3430
+ events: [
3431
+ 'touchstart',
3432
+ 'touchmove',
3433
+ 'touchend',
3434
+ 'touchcancel'
3435
+ ],
3436
+ register: function(target) {
3437
+ if (HAS_TOUCH_ACTION_DELAY) {
3438
+ _dispatcher.listen(target, this.events);
3439
+ } else {
3440
+ INSTALLER.enableOnSubtree(target);
3441
+ }
3442
+ },
3443
+ unregister: function(target) {
3444
+ if (HAS_TOUCH_ACTION_DELAY) {
3445
+ _dispatcher.unlisten(target, this.events);
3446
+ } else {
3447
+
3448
+ // TODO(dfreedman): is it worth it to disconnect the MO?
3449
+ }
3450
+ },
3451
+ elementAdded: function(el) {
3452
+ var a = el.getAttribute(ATTRIB);
3453
+ var st = this.touchActionToScrollType(a);
3454
+ if (st) {
3455
+ el._scrollType = st;
3456
+ _dispatcher.listen(el, this.events);
3457
+
3458
+ // set touch-action on shadows as well
3459
+ allShadows(el).forEach(function(s) {
3460
+ s._scrollType = st;
3461
+ _dispatcher.listen(s, this.events);
3462
+ }, this);
3463
+ }
3464
+ },
3465
+ elementRemoved: function(el) {
3466
+ el._scrollType = undefined;
3467
+ _dispatcher.unlisten(el, this.events);
3468
+
3469
+ // remove touch-action from shadow
3470
+ allShadows(el).forEach(function(s) {
3471
+ s._scrollType = undefined;
3472
+ _dispatcher.unlisten(s, this.events);
3473
+ }, this);
3474
+ },
3475
+ elementChanged: function(el, oldValue) {
3476
+ var a = el.getAttribute(ATTRIB);
3477
+ var st = this.touchActionToScrollType(a);
3478
+ var oldSt = this.touchActionToScrollType(oldValue);
3479
+
3480
+ // simply update scrollType if listeners are already established
3481
+ if (st && oldSt) {
3482
+ el._scrollType = st;
3483
+ allShadows(el).forEach(function(s) {
3484
+ s._scrollType = st;
3485
+ }, this);
3486
+ } else if (oldSt) {
3487
+ this.elementRemoved(el);
3488
+ } else if (st) {
3489
+ this.elementAdded(el);
3490
+ }
3491
+ },
3492
+ scrollTypes: {
3493
+ EMITTER: 'none',
3494
+ XSCROLLER: 'pan-x',
3495
+ YSCROLLER: 'pan-y',
3496
+ SCROLLER: /^(?:pan-x pan-y)|(?:pan-y pan-x)|auto$/
3497
+ },
3498
+ touchActionToScrollType: function(touchAction) {
3499
+ var t = touchAction;
3500
+ var st = this.scrollTypes;
3501
+ if (t === 'none') {
3502
+ return 'none';
3503
+ } else if (t === st.XSCROLLER) {
3504
+ return 'X';
3505
+ } else if (t === st.YSCROLLER) {
3506
+ return 'Y';
3507
+ } else if (st.SCROLLER.exec(t)) {
3508
+ return 'XY';
3509
+ }
3510
+ },
3511
+ POINTER_TYPE: 'touch',
3512
+ firstTouch: null,
3513
+ isPrimaryTouch: function(inTouch) {
3514
+ return this.firstTouch === inTouch.identifier;
3515
+ },
3516
+ setPrimaryTouch: function(inTouch) {
3517
+
3518
+ // set primary touch if there no pointers, or the only pointer is the mouse
3519
+ if (touch__pointermap.size === 0 || (touch__pointermap.size === 1 && touch__pointermap.has(1))) {
3520
+ this.firstTouch = inTouch.identifier;
3521
+ this.firstXY = { X: inTouch.clientX, Y: inTouch.clientY };
3522
+ this.scrolling = false;
3523
+ this.cancelResetClickCount();
3524
+ }
3525
+ },
3526
+ removePrimaryPointer: function(inPointer) {
3527
+ if (inPointer.isPrimary) {
3528
+ this.firstTouch = null;
3529
+ this.firstXY = null;
3530
+ this.resetClickCount();
3531
+ }
3532
+ },
3533
+ clickCount: 0,
3534
+ resetId: null,
3535
+ resetClickCount: function() {
3536
+ var fn = function() {
3537
+ this.clickCount = 0;
3538
+ this.resetId = null;
3539
+ }.bind(this);
3540
+ this.resetId = setTimeout(fn, CLICK_COUNT_TIMEOUT);
3541
+ },
3542
+ cancelResetClickCount: function() {
3543
+ if (this.resetId) {
3544
+ clearTimeout(this.resetId);
3545
+ }
3546
+ },
3547
+ typeToButtons: function(type) {
3548
+ var ret = 0;
3549
+ if (type === 'touchstart' || type === 'touchmove') {
3550
+ ret = 1;
3551
+ }
3552
+ return ret;
3553
+ },
3554
+ touchToPointer: function(inTouch) {
3555
+ var cte = this.currentTouchEvent;
3556
+ var e = _dispatcher.cloneEvent(inTouch);
3557
+
3558
+ // We reserve pointerId 1 for Mouse.
3559
+ // Touch identifiers can start at 0.
3560
+ // Add 2 to the touch identifier for compatibility.
3561
+ var id = e.pointerId = inTouch.identifier + 2;
3562
+ e.target = captureInfo[id] || findTarget(e);
3563
+ e.bubbles = true;
3564
+ e.cancelable = true;
3565
+ e.detail = this.clickCount;
3566
+ e.button = 0;
3567
+ e.buttons = this.typeToButtons(cte.type);
3568
+ e.width = inTouch.radiusX || inTouch.webkitRadiusX || 0;
3569
+ e.height = inTouch.radiusY || inTouch.webkitRadiusY || 0;
3570
+ e.pressure = inTouch.force || inTouch.webkitForce || 0.5;
3571
+ e.isPrimary = this.isPrimaryTouch(inTouch);
3572
+ e.pointerType = this.POINTER_TYPE;
3573
+
3574
+ // forward touch preventDefaults
3575
+ var self = this;
3576
+ e.preventDefault = function() {
3577
+ self.scrolling = false;
3578
+ self.firstXY = null;
3579
+ cte.preventDefault();
3580
+ };
3581
+ return e;
3582
+ },
3583
+ processTouches: function(inEvent, inFunction) {
3584
+ var tl = inEvent.changedTouches;
3585
+ this.currentTouchEvent = inEvent;
3586
+ for (var i = 0, t; i < tl.length; i++) {
3587
+ t = tl[i];
3588
+ inFunction.call(this, this.touchToPointer(t));
3589
+ }
3590
+ },
3591
+
3592
+ // For single axis scrollers, determines whether the element should emit
3593
+ // pointer events or behave as a scroller
3594
+ shouldScroll: function(inEvent) {
3595
+ if (this.firstXY) {
3596
+ var ret;
3597
+ var scrollAxis = inEvent.currentTarget._scrollType;
3598
+ if (scrollAxis === 'none') {
3599
+
3600
+ // this element is a touch-action: none, should never scroll
3601
+ ret = false;
3602
+ } else if (scrollAxis === 'XY') {
3603
+
3604
+ // this element should always scroll
3605
+ ret = true;
3606
+ } else {
3607
+ var t = inEvent.changedTouches[0];
3608
+
3609
+ // check the intended scroll axis, and other axis
3610
+ var a = scrollAxis;
3611
+ var oa = scrollAxis === 'Y' ? 'X' : 'Y';
3612
+ var da = Math.abs(t['client' + a] - this.firstXY[a]);
3613
+ var doa = Math.abs(t['client' + oa] - this.firstXY[oa]);
3614
+
3615
+ // if delta in the scroll axis > delta other axis, scroll instead of
3616
+ // making events
3617
+ ret = da >= doa;
3618
+ }
3619
+ this.firstXY = null;
3620
+ return ret;
3621
+ }
3622
+ },
3623
+ findTouch: function(inTL, inId) {
3624
+ for (var i = 0, l = inTL.length, t; i < l && (t = inTL[i]); i++) {
3625
+ if (t.identifier === inId) {
3626
+ return true;
3627
+ }
3628
+ }
3629
+ },
3630
+
3631
+ // In some instances, a touchstart can happen without a touchend. This
3632
+ // leaves the pointermap in a broken state.
3633
+ // Therefore, on every touchstart, we remove the touches that did not fire a
3634
+ // touchend event.
3635
+ // To keep state globally consistent, we fire a
3636
+ // pointercancel for this "abandoned" touch
3637
+ vacuumTouches: function(inEvent) {
3638
+ var tl = inEvent.touches;
3639
+
3640
+ // pointermap.size should be < tl.length here, as the touchstart has not
3641
+ // been processed yet.
3642
+ if (touch__pointermap.size >= tl.length) {
3643
+ var d = [];
3644
+ touch__pointermap.forEach(function(value, key) {
3645
+
3646
+ // Never remove pointerId == 1, which is mouse.
3647
+ // Touch identifiers are 2 smaller than their pointerId, which is the
3648
+ // index in pointermap.
3649
+ if (key !== 1 && !this.findTouch(tl, key - 2)) {
3650
+ var p = value.out;
3651
+ d.push(p);
3652
+ }
3653
+ }, this);
3654
+ d.forEach(this.cancelOut, this);
3655
+ }
3656
+ },
3657
+ touchstart: function(inEvent) {
3658
+ this.vacuumTouches(inEvent);
3659
+ this.setPrimaryTouch(inEvent.changedTouches[0]);
3660
+ this.dedupSynthMouse(inEvent);
3661
+ if (!this.scrolling) {
3662
+ this.clickCount++;
3663
+ this.processTouches(inEvent, this.overDown);
3664
+ }
3665
+ },
3666
+ overDown: function(inPointer) {
3667
+ touch__pointermap.set(inPointer.pointerId, {
3668
+ target: inPointer.target,
3669
+ out: inPointer,
3670
+ outTarget: inPointer.target
3671
+ });
3672
+ _dispatcher.over(inPointer);
3673
+ _dispatcher.enter(inPointer);
3674
+ _dispatcher.down(inPointer);
3675
+ },
3676
+ touchmove: function(inEvent) {
3677
+ if (!this.scrolling) {
3678
+ if (this.shouldScroll(inEvent)) {
3679
+ this.scrolling = true;
3680
+ this.touchcancel(inEvent);
3681
+ } else {
3682
+ inEvent.preventDefault();
3683
+ this.processTouches(inEvent, this.moveOverOut);
3684
+ }
3685
+ }
3686
+ },
3687
+ moveOverOut: function(inPointer) {
3688
+ var event = inPointer;
3689
+ var pointer = touch__pointermap.get(event.pointerId);
3690
+
3691
+ // a finger drifted off the screen, ignore it
3692
+ if (!pointer) {
3693
+ return;
3694
+ }
3695
+ var outEvent = pointer.out;
3696
+ var outTarget = pointer.outTarget;
3697
+ _dispatcher.move(event);
3698
+ if (outEvent && outTarget !== event.target) {
3699
+ outEvent.relatedTarget = event.target;
3700
+ event.relatedTarget = outTarget;
3701
+
3702
+ // recover from retargeting by shadow
3703
+ outEvent.target = outTarget;
3704
+ if (event.target) {
3705
+ _dispatcher.leaveOut(outEvent);
3706
+ _dispatcher.enterOver(event);
3707
+ } else {
3708
+
3709
+ // clean up case when finger leaves the screen
3710
+ event.target = outTarget;
3711
+ event.relatedTarget = null;
3712
+ this.cancelOut(event);
3713
+ }
3714
+ }
3715
+ pointer.out = event;
3716
+ pointer.outTarget = event.target;
3717
+ },
3718
+ touchend: function(inEvent) {
3719
+ this.dedupSynthMouse(inEvent);
3720
+ this.processTouches(inEvent, this.upOut);
3721
+ },
3722
+ upOut: function(inPointer) {
3723
+ if (!this.scrolling) {
3724
+ _dispatcher.up(inPointer);
3725
+ _dispatcher.out(inPointer);
3726
+ _dispatcher.leave(inPointer);
3727
+ }
3728
+ this.cleanUpPointer(inPointer);
3729
+ },
3730
+ touchcancel: function(inEvent) {
3731
+ this.processTouches(inEvent, this.cancelOut);
3732
+ },
3733
+ cancelOut: function(inPointer) {
3734
+ _dispatcher.cancel(inPointer);
3735
+ _dispatcher.out(inPointer);
3736
+ _dispatcher.leave(inPointer);
3737
+ this.cleanUpPointer(inPointer);
3738
+ },
3739
+ cleanUpPointer: function(inPointer) {
3740
+ touch__pointermap.delete(inPointer.pointerId);
3741
+ this.removePrimaryPointer(inPointer);
3742
+ },
3743
+
3744
+ // prevent synth mouse events from creating pointer events
3745
+ dedupSynthMouse: function(inEvent) {
3746
+ var lts = mouse.lastTouches;
3747
+ var t = inEvent.changedTouches[0];
3748
+
3749
+ // only the primary finger will synth mouse events
3750
+ if (this.isPrimaryTouch(t)) {
3751
+
3752
+ // remember x/y of last touch
3753
+ var lt = { x: t.clientX, y: t.clientY };
3754
+ lts.push(lt);
3755
+ var fn = (function(lts, lt) {
3756
+ var i = lts.indexOf(lt);
3757
+ if (i > -1) {
3758
+ lts.splice(i, 1);
3759
+ }
3760
+ }).bind(null, lts, lt);
3761
+ setTimeout(fn, DEDUP_TIMEOUT);
3762
+ }
3763
+ }
3764
+ };
3765
+
3766
+ if (!HAS_TOUCH_ACTION_DELAY) {
3767
+ INSTALLER = new installer(touchEvents.elementAdded, touchEvents.elementRemoved,
3768
+ touchEvents.elementChanged, touchEvents);
3769
+ }
3770
+
3771
+ var touch = touchEvents;
3772
+
3773
+ var ms__pointermap = _dispatcher.pointermap;
3774
+ var HAS_BITMAP_TYPE = window.MSPointerEvent &&
3775
+ typeof window.MSPointerEvent.MSPOINTER_TYPE_MOUSE === 'number';
3776
+ var msEvents = {
3777
+ events: [
3778
+ 'MSPointerDown',
3779
+ 'MSPointerMove',
3780
+ 'MSPointerUp',
3781
+ 'MSPointerOut',
3782
+ 'MSPointerOver',
3783
+ 'MSPointerCancel',
3784
+ 'MSGotPointerCapture',
3785
+ 'MSLostPointerCapture'
3786
+ ],
3787
+ register: function(target) {
3788
+ _dispatcher.listen(target, this.events);
3789
+ },
3790
+ unregister: function(target) {
3791
+ _dispatcher.unlisten(target, this.events);
3792
+ },
3793
+ POINTER_TYPES: [
3794
+ '',
3795
+ 'unavailable',
3796
+ 'touch',
3797
+ 'pen',
3798
+ 'mouse'
3799
+ ],
3800
+ prepareEvent: function(inEvent) {
3801
+ var e = inEvent;
3802
+ if (HAS_BITMAP_TYPE) {
3803
+ e = _dispatcher.cloneEvent(inEvent);
3804
+ e.pointerType = this.POINTER_TYPES[inEvent.pointerType];
3805
+ }
3806
+ return e;
3807
+ },
3808
+ cleanup: function(id) {
3809
+ ms__pointermap.delete(id);
3810
+ },
3811
+ MSPointerDown: function(inEvent) {
3812
+ ms__pointermap.set(inEvent.pointerId, inEvent);
3813
+ var e = this.prepareEvent(inEvent);
3814
+ _dispatcher.down(e);
3815
+ },
3816
+ MSPointerMove: function(inEvent) {
3817
+ var e = this.prepareEvent(inEvent);
3818
+ _dispatcher.move(e);
3819
+ },
3820
+ MSPointerUp: function(inEvent) {
3821
+ var e = this.prepareEvent(inEvent);
3822
+ _dispatcher.up(e);
3823
+ this.cleanup(inEvent.pointerId);
3824
+ },
3825
+ MSPointerOut: function(inEvent) {
3826
+ var e = this.prepareEvent(inEvent);
3827
+ _dispatcher.leaveOut(e);
3828
+ },
3829
+ MSPointerOver: function(inEvent) {
3830
+ var e = this.prepareEvent(inEvent);
3831
+ _dispatcher.enterOver(e);
3832
+ },
3833
+ MSPointerCancel: function(inEvent) {
3834
+ var e = this.prepareEvent(inEvent);
3835
+ _dispatcher.cancel(e);
3836
+ this.cleanup(inEvent.pointerId);
3837
+ },
3838
+ MSLostPointerCapture: function(inEvent) {
3839
+ var e = _dispatcher.makeEvent('lostpointercapture', inEvent);
3840
+ _dispatcher.dispatchEvent(e);
3841
+ },
3842
+ MSGotPointerCapture: function(inEvent) {
3843
+ var e = _dispatcher.makeEvent('gotpointercapture', inEvent);
3844
+ _dispatcher.dispatchEvent(e);
3845
+ }
3846
+ };
3847
+
3848
+ var ms = msEvents;
3849
+
3850
+ function platform_events__applyPolyfill() {
3851
+
3852
+ // only activate if this platform does not have pointer events
3853
+ if (!window.PointerEvent) {
3854
+ window.PointerEvent = _PointerEvent;
3855
+
3856
+ if (window.navigator.msPointerEnabled) {
3857
+ var tp = window.navigator.msMaxTouchPoints;
3858
+ Object.defineProperty(window.navigator, 'maxTouchPoints', {
3859
+ value: tp,
3860
+ enumerable: true
3861
+ });
3862
+ _dispatcher.registerSource('ms', ms);
3863
+ } else {
3864
+ _dispatcher.registerSource('mouse', mouse);
3865
+ if (window.ontouchstart !== undefined) {
3866
+ _dispatcher.registerSource('touch', touch);
3867
+ }
3868
+ }
3869
+
3870
+ _dispatcher.register(document);
3871
+ }
3872
+ }
3873
+
3874
+ var n = window.navigator;
3875
+ var s, r;
3876
+ function assertDown(id) {
3877
+ if (!_dispatcher.pointermap.has(id)) {
3878
+ throw new Error('InvalidPointerId');
3879
+ }
3880
+ }
3881
+ if (n.msPointerEnabled) {
3882
+ s = function(pointerId) {
3883
+ assertDown(pointerId);
3884
+ this.msSetPointerCapture(pointerId);
3885
+ };
3886
+ r = function(pointerId) {
3887
+ assertDown(pointerId);
3888
+ this.msReleasePointerCapture(pointerId);
3889
+ };
3890
+ } else {
3891
+ s = function setPointerCapture(pointerId) {
3892
+ assertDown(pointerId);
3893
+ _dispatcher.setCapture(pointerId, this);
3894
+ };
3895
+ r = function releasePointerCapture(pointerId) {
3896
+ assertDown(pointerId);
3897
+ _dispatcher.releaseCapture(pointerId, this);
3898
+ };
3899
+ }
3900
+
3901
+ function capture__applyPolyfill() {
3902
+ if (window.Element && !Element.prototype.setPointerCapture) {
3903
+ Object.defineProperties(Element.prototype, {
3904
+ 'setPointerCapture': {
3905
+ value: s
3906
+ },
3907
+ 'releasePointerCapture': {
3908
+ value: r
3909
+ }
3910
+ });
3911
+ }
3912
+ }
3913
+
3914
+ applyAttributeStyles();
3915
+ platform_events__applyPolyfill();
3916
+ capture__applyPolyfill();
3917
+
3918
+ var pointerevents = {
3919
+ dispatcher: _dispatcher,
3920
+ Installer: installer,
3921
+ PointerEvent: _PointerEvent,
3922
+ PointerMap: _pointermap,
3923
+ targetFinding: targeting
3924
+ };
3925
+
3926
+ return pointerevents;
3927
+
3928
+ }));
3929
+
3930
+ (function () {
3931
+
3932
+ /*** Variables ***/
3933
+
3934
+ var win = window,
3935
+ doc = document,
3936
+ attrProto = {
3937
+ setAttribute: Element.prototype.setAttribute,
3938
+ removeAttribute: Element.prototype.removeAttribute
3939
+ },
3940
+ hasShadow = Element.prototype.createShadowRoot,
3941
+ container = doc.createElement('div'),
3942
+ noop = function(){},
3943
+ trueop = function(){ return true; },
3944
+ regexReplaceCommas = /,/g,
3945
+ regexCamelToDash = /([a-z])([A-Z])/g,
3946
+ regexPseudoParens = /\(|\)/g,
3947
+ regexPseudoCapture = /:(\w+)\u276A(.+?(?=\u276B))|:(\w+)/g,
3948
+ regexDigits = /(\d+)/g,
3949
+ keypseudo = {
3950
+ action: function (pseudo, event) {
3951
+ return pseudo.value.match(regexDigits).indexOf(String(event.keyCode)) > -1 == (pseudo.name == 'keypass') || null;
3952
+ }
3953
+ },
3954
+ /*
3955
+ - The prefix object generated here is added to the xtag object as xtag.prefix later in the code
3956
+ - Prefix provides a variety of prefix variations for the browser in which your code is running
3957
+ - The 4 variations of prefix are as follows:
3958
+ * prefix.dom: the correct prefix case and form when used on DOM elements/style properties
3959
+ * prefix.lowercase: a lowercase version of the prefix for use in various user-code situations
3960
+ * prefix.css: the lowercase, dashed version of the prefix
3961
+ * prefix.js: addresses prefixed APIs present in global and non-Element contexts
3962
+ */
3963
+ prefix = (function () {
3964
+ var styles = win.getComputedStyle(doc.documentElement, ''),
3965
+ pre = (Array.prototype.slice
3966
+ .call(styles)
3967
+ .join('')
3968
+ .match(/-(moz|webkit|ms)-/) || (styles.OLink === '' && ['', 'o'])
3969
+ )[1];
3970
+ return {
3971
+ dom: pre == 'ms' ? 'MS' : pre,
3972
+ lowercase: pre,
3973
+ css: '-' + pre + '-',
3974
+ js: pre == 'ms' ? pre : pre[0].toUpperCase() + pre.substr(1)
3975
+ };
3976
+ })(),
3977
+ matchSelector = Element.prototype.matches || Element.prototype.matchesSelector || Element.prototype[prefix.lowercase + 'MatchesSelector'];
3978
+
3979
+ /*** Functions ***/
3980
+
3981
+ // Utilities
3982
+
3983
+ /*
3984
+ This is an enhanced typeof check for all types of objects. Where typeof would normaly return
3985
+ 'object' for many common DOM objects (like NodeLists and HTMLCollections).
3986
+ - For example: typeOf(document.children) will correctly return 'htmlcollection'
3987
+ */
3988
+ var typeCache = {},
3989
+ typeString = typeCache.toString,
3990
+ typeRegexp = /\s([a-zA-Z]+)/;
3991
+ function typeOf(obj) {
3992
+ var type = typeString.call(obj);
3993
+ return typeCache[type] || (typeCache[type] = type.match(typeRegexp)[1].toLowerCase());
3994
+ }
3995
+
3996
+ function clone(item, type){
3997
+ var fn = clone[type || typeOf(item)];
3998
+ return fn ? fn(item) : item;
3999
+ }
4000
+ clone.object = function(src){
4001
+ var obj = {};
4002
+ for (var key in src) obj[key] = clone(src[key]);
4003
+ return obj;
4004
+ };
4005
+ clone.array = function(src){
4006
+ var i = src.length, array = new Array(i);
4007
+ while (i--) array[i] = clone(src[i]);
4008
+ return array;
4009
+ };
4010
+
4011
+ /*
4012
+ The toArray() method allows for conversion of any object to a true array. For types that
4013
+ cannot be converted to an array, the method returns a 1 item array containing the passed-in object.
4014
+ */
4015
+ var unsliceable = { 'undefined': 1, 'null': 1, 'number': 1, 'boolean': 1, 'string': 1, 'function': 1 };
4016
+ function toArray(obj){
4017
+ return unsliceable[typeOf(obj)] ? [obj] : Array.prototype.slice.call(obj, 0);
4018
+ }
4019
+
4020
+ // DOM
4021
+
4022
+ var str = '';
4023
+ function query(element, selector){
4024
+ return (selector || str).length ? toArray(element.querySelectorAll(selector)) : [];
4025
+ }
4026
+
4027
+ // Pseudos
4028
+
4029
+ function parsePseudo(fn){fn();}
4030
+
4031
+ // Mixins
4032
+
4033
+ function mergeOne(source, key, current){
4034
+ var type = typeOf(current);
4035
+ if (type == 'object' && typeOf(source[key]) == 'object') xtag.merge(source[key], current);
4036
+ else source[key] = clone(current, type);
4037
+ return source;
4038
+ }
4039
+
4040
+ function mergeMixin(tag, original, mixin, name) {
4041
+ var key, keys = {};
4042
+ for (var z in original) keys[z.split(':')[0]] = z;
4043
+ for (z in mixin) {
4044
+ key = keys[z.split(':')[0]];
4045
+ if (typeof original[key] == 'function') {
4046
+ if (!key.match(':mixins')) {
4047
+ original[key + ':mixins'] = original[key];
4048
+ delete original[key];
4049
+ key = key + ':mixins';
4050
+ }
4051
+ original[key].__mixin__ = xtag.applyPseudos(z + (z.match(':mixins') ? '' : ':mixins'), mixin[z], tag.pseudos, original[key].__mixin__);
4052
+ }
4053
+ else {
4054
+ original[z] = mixin[z];
4055
+ delete original[key];
4056
+ }
4057
+ }
4058
+ }
4059
+
4060
+ var uniqueMixinCount = 0;
4061
+ function addMixin(tag, original, mixin){
4062
+ for (var z in mixin){
4063
+ original[z + ':__mixin__(' + (uniqueMixinCount++) + ')'] = xtag.applyPseudos(z, mixin[z], tag.pseudos);
4064
+ }
4065
+ }
4066
+
4067
+ function resolveMixins(mixins, output){
4068
+ var index = mixins.length;
4069
+ while (index--){
4070
+ output.unshift(mixins[index]);
4071
+ if (xtag.mixins[mixins[index]].mixins) resolveMixins(xtag.mixins[mixins[index]].mixins, output);
4072
+ }
4073
+ return output;
4074
+ }
4075
+
4076
+ function applyMixins(tag) {
4077
+ resolveMixins(tag.mixins, []).forEach(function(name){
4078
+ var mixin = xtag.mixins[name];
4079
+ for (var type in mixin) {
4080
+ var item = mixin[type],
4081
+ original = tag[type];
4082
+ if (!original) tag[type] = item;
4083
+ else {
4084
+ switch (type){
4085
+ case 'mixins': break;
4086
+ case 'events': addMixin(tag, original, item); break;
4087
+ case 'accessors':
4088
+ case 'prototype':
4089
+ for (var z in item) {
4090
+ if (!original[z]) original[z] = item[z];
4091
+ else mergeMixin(tag, original[z], item[z], name);
4092
+ }
4093
+ break;
4094
+ default: mergeMixin(tag, original, item, name);
4095
+ }
4096
+ }
4097
+ }
4098
+ });
4099
+ return tag;
4100
+ }
4101
+
4102
+ // Events
4103
+
4104
+ function delegateAction(pseudo, event) {
4105
+ var match,
4106
+ target = event.target,
4107
+ root = event.currentTarget;
4108
+ while (!match && target && target != root) {
4109
+ if (target.tagName && matchSelector.call(target, pseudo.value)) match = target;
4110
+ target = target.parentNode;
4111
+ }
4112
+ if (!match && root.tagName && matchSelector.call(root, pseudo.value)) match = root;
4113
+ return match ? pseudo.listener = pseudo.listener.bind(match) : null;
4114
+ }
4115
+
4116
+ function touchFilter(event){
4117
+ return event.button === 0;
4118
+ }
4119
+
4120
+ function writeProperty(key, event, base, desc){
4121
+ if (desc) event[key] = base[key];
4122
+ else Object.defineProperty(event, key, {
4123
+ writable: true,
4124
+ enumerable: true,
4125
+ value: base[key]
4126
+ });
4127
+ }
4128
+
4129
+ var skipProps = {};
4130
+ for (var z in doc.createEvent('CustomEvent')) skipProps[z] = 1;
4131
+ function inheritEvent(event, base){
4132
+ var desc = Object.getOwnPropertyDescriptor(event, 'target');
4133
+ for (var z in base) {
4134
+ if (!skipProps[z]) writeProperty(z, event, base, desc);
4135
+ }
4136
+ event.baseEvent = base;
4137
+ }
4138
+
4139
+ // Accessors
4140
+
4141
+ function modAttr(element, attr, name, value, method){
4142
+ attrProto[method].call(element, name, attr && attr.boolean ? '' : value);
4143
+ }
4144
+
4145
+ function syncAttr(element, attr, name, value, method){
4146
+ if (attr && (attr.property || attr.selector)) {
4147
+ var nodes = attr.property ? [element.xtag[attr.property]] : attr.selector ? xtag.query(element, attr.selector) : [],
4148
+ index = nodes.length;
4149
+ while (index--) nodes[index][method](name, value);
4150
+ }
4151
+ }
4152
+
4153
+ function attachProperties(tag, prop, z, accessor, attr, name){
4154
+ var key = z.split(':'), type = key[0];
4155
+ if (type == 'get') {
4156
+ key[0] = prop;
4157
+ tag.prototype[prop].get = xtag.applyPseudos(key.join(':'), accessor[z], tag.pseudos, accessor[z]);
4158
+ }
4159
+ else if (type == 'set') {
4160
+ key[0] = prop;
4161
+ var setter = tag.prototype[prop].set = xtag.applyPseudos(key.join(':'), attr ? function(value){
4162
+ var old, method = 'setAttribute';
4163
+ if (attr.boolean){
4164
+ value = !!value;
4165
+ old = this.hasAttribute(name);
4166
+ if (!value) method = 'removeAttribute';
4167
+ }
4168
+ else {
4169
+ value = attr.validate ? attr.validate.call(this, value) : value;
4170
+ old = this.getAttribute(name);
4171
+ }
4172
+ modAttr(this, attr, name, value, method);
4173
+ accessor[z].call(this, value, old);
4174
+ syncAttr(this, attr, name, value, method);
4175
+ } : accessor[z] ? function(value){
4176
+ accessor[z].call(this, value);
4177
+ } : null, tag.pseudos, accessor[z]);
4178
+
4179
+ if (attr) attr.setter = accessor[z];
4180
+ }
4181
+ else tag.prototype[prop][z] = accessor[z];
4182
+ }
4183
+
4184
+ function parseAccessor(tag, prop){
4185
+ tag.prototype[prop] = {};
4186
+ var accessor = tag.accessors[prop],
4187
+ attr = accessor.attribute,
4188
+ name;
4189
+
4190
+ if (attr) {
4191
+ name = attr.name = (attr ? (attr.name || prop.replace(regexCamelToDash, '$1-$2')) : prop).toLowerCase();
4192
+ attr.key = prop;
4193
+ tag.attributes[name] = attr;
4194
+ }
4195
+
4196
+ for (var z in accessor) attachProperties(tag, prop, z, accessor, attr, name);
4197
+
4198
+ if (attr) {
4199
+ if (!tag.prototype[prop].get) {
4200
+ var method = (attr.boolean ? 'has' : 'get') + 'Attribute';
4201
+ tag.prototype[prop].get = function(){
4202
+ return this[method](name);
4203
+ };
4204
+ }
4205
+ if (!tag.prototype[prop].set) tag.prototype[prop].set = function(value){
4206
+ value = attr.boolean ? !!value : attr.validate ? attr.validate.call(this, value) : value;
4207
+ var method = attr.boolean ? (value ? 'setAttribute' : 'removeAttribute') : 'setAttribute';
4208
+ modAttr(this, attr, name, value, method);
4209
+ syncAttr(this, attr, name, value, method);
4210
+ };
4211
+ }
4212
+ }
4213
+
4214
+ var unwrapComment = /\/\*!?(?:\@preserve)?[ \t]*(?:\r\n|\n)([\s\S]*?)(?:\r\n|\n)\s*\*\//;
4215
+ function parseMultiline(fn){
4216
+ return typeof fn == 'function' ? unwrapComment.exec(fn.toString())[1] : fn;
4217
+ }
4218
+
4219
+ /*** X-Tag Object Definition ***/
4220
+
4221
+ var xtag = {
4222
+ tags: {},
4223
+ defaultOptions: {
4224
+ pseudos: [],
4225
+ mixins: [],
4226
+ events: {},
4227
+ methods: {},
4228
+ accessors: {},
4229
+ lifecycle: {},
4230
+ attributes: {},
4231
+ 'prototype': {
4232
+ xtag: {
4233
+ get: function(){
4234
+ return this.__xtag__ ? this.__xtag__ : (this.__xtag__ = { data: {} });
4235
+ }
4236
+ }
4237
+ }
4238
+ },
4239
+ register: function (name, options) {
4240
+ var _name;
4241
+ if (typeof name == 'string') _name = name.toLowerCase();
4242
+ else throw 'First argument must be a Custom Element string name';
4243
+ xtag.tags[_name] = options || {};
4244
+
4245
+ var basePrototype = options.prototype;
4246
+ delete options.prototype;
4247
+ var tag = xtag.tags[_name].compiled = applyMixins(xtag.merge({}, xtag.defaultOptions, options));
4248
+
4249
+ for (var z in tag.events) tag.events[z] = xtag.parseEvent(z, tag.events[z]);
4250
+ for (z in tag.lifecycle) tag.lifecycle[z.split(':')[0]] = xtag.applyPseudos(z, tag.lifecycle[z], tag.pseudos, tag.lifecycle[z]);
4251
+ for (z in tag.methods) tag.prototype[z.split(':')[0]] = { value: xtag.applyPseudos(z, tag.methods[z], tag.pseudos, tag.methods[z]), enumerable: true };
4252
+ for (z in tag.accessors) parseAccessor(tag, z);
4253
+
4254
+ if (tag.shadow) tag.shadow = tag.shadow.nodeName ? tag.shadow : xtag.createFragment(tag.shadow);
4255
+ if (tag.content) tag.content = tag.content.nodeName ? tag.content.innerHTML : parseMultiline(tag.content);
4256
+ var created = tag.lifecycle.created;
4257
+ var finalized = tag.lifecycle.finalized;
4258
+ tag.prototype.createdCallback = {
4259
+ enumerable: true,
4260
+ value: function(){
4261
+ var element = this;
4262
+ if (tag.shadow && hasShadow) this.createShadowRoot().appendChild(tag.shadow.cloneNode(true));
4263
+ if (tag.content) this.appendChild(document.createElement('div')).outerHTML = tag.content;
4264
+ var output = created ? created.apply(this, arguments) : null;
4265
+ xtag.addEvents(this, tag.events);
4266
+ for (var name in tag.attributes) {
4267
+ var attr = tag.attributes[name],
4268
+ hasAttr = this.hasAttribute(name),
4269
+ hasDefault = attr.def !== undefined;
4270
+ if (hasAttr || attr.boolean || hasDefault) {
4271
+ this[attr.key] = attr.boolean ? hasAttr : !hasAttr && hasDefault ? attr.def : this.getAttribute(name);
4272
+ }
4273
+ }
4274
+ tag.pseudos.forEach(function(obj){
4275
+ obj.onAdd.call(element, obj);
4276
+ });
4277
+ this.xtagComponentReady = true;
4278
+ if (finalized) finalized.apply(this, arguments);
4279
+ return output;
4280
+ }
4281
+ };
4282
+
4283
+ var inserted = tag.lifecycle.inserted,
4284
+ removed = tag.lifecycle.removed;
4285
+ if (inserted || removed) {
4286
+ tag.prototype.attachedCallback = { value: function(){
4287
+ if (removed) this.xtag.__parentNode__ = this.parentNode;
4288
+ if (inserted) return inserted.apply(this, arguments);
4289
+ }, enumerable: true };
4290
+ }
4291
+ if (removed) {
4292
+ tag.prototype.detachedCallback = { value: function(){
4293
+ var args = toArray(arguments);
4294
+ args.unshift(this.xtag.__parentNode__);
4295
+ var output = removed.apply(this, args);
4296
+ delete this.xtag.__parentNode__;
4297
+ return output;
4298
+ }, enumerable: true };
4299
+ }
4300
+ if (tag.lifecycle.attributeChanged) tag.prototype.attributeChangedCallback = { value: tag.lifecycle.attributeChanged, enumerable: true };
4301
+
4302
+ tag.prototype.setAttribute = {
4303
+ writable: true,
4304
+ enumerable: true,
4305
+ value: function (name, value){
4306
+ var old;
4307
+ var _name = name.toLowerCase();
4308
+ var attr = tag.attributes[_name];
4309
+ if (attr) {
4310
+ old = this.getAttribute(_name);
4311
+ value = attr.boolean ? '' : attr.validate ? attr.validate.call(this, value) : value;
4312
+ }
4313
+ modAttr(this, attr, _name, value, 'setAttribute');
4314
+ if (attr) {
4315
+ if (attr.setter) attr.setter.call(this, attr.boolean ? true : value, old);
4316
+ syncAttr(this, attr, _name, value, 'setAttribute');
4317
+ }
4318
+ }
4319
+ };
4320
+
4321
+ tag.prototype.removeAttribute = {
4322
+ writable: true,
4323
+ enumerable: true,
4324
+ value: function (name){
4325
+ var _name = name.toLowerCase();
4326
+ var attr = tag.attributes[_name];
4327
+ var old = this.hasAttribute(_name);
4328
+ modAttr(this, attr, _name, '', 'removeAttribute');
4329
+ if (attr) {
4330
+ if (attr.setter) attr.setter.call(this, attr.boolean ? false : undefined, old);
4331
+ syncAttr(this, attr, _name, '', 'removeAttribute');
4332
+ }
4333
+ }
4334
+ };
4335
+
4336
+ var elementProto = basePrototype ?
4337
+ basePrototype :
4338
+ tag['extends'] ?
4339
+ Object.create(doc.createElement(tag['extends']).constructor).prototype :
4340
+ win.HTMLElement.prototype;
4341
+
4342
+ var definition = {
4343
+ 'prototype': Object.create(elementProto, tag.prototype)
4344
+ };
4345
+ if (tag['extends']) {
4346
+ definition['extends'] = tag['extends'];
4347
+ }
4348
+ var reg = doc.registerElement(_name, definition);
4349
+ return reg;
4350
+ },
4351
+
4352
+ /* Exposed Variables */
4353
+
4354
+ mixins: {},
4355
+ prefix: prefix,
4356
+ captureEvents: { focus: 1, blur: 1, scroll: 1, DOMMouseScroll: 1 },
4357
+ customEvents: {
4358
+ animationstart: {
4359
+ attach: [prefix.dom + 'AnimationStart']
4360
+ },
4361
+ animationend: {
4362
+ attach: [prefix.dom + 'AnimationEnd']
4363
+ },
4364
+ transitionend: {
4365
+ attach: [prefix.dom + 'TransitionEnd']
4366
+ },
4367
+ move: {
4368
+ attach: ['pointermove']
4369
+ },
4370
+ enter: {
4371
+ attach: ['pointerenter']
4372
+ },
4373
+ leave: {
4374
+ attach: ['pointerleave']
4375
+ },
4376
+ scrollwheel: {
4377
+ attach: ['DOMMouseScroll', 'mousewheel'],
4378
+ condition: function(event){
4379
+ event.delta = event.wheelDelta ? event.wheelDelta / 40 : Math.round(event.detail / 3.5 * -1);
4380
+ return true;
4381
+ }
4382
+ },
4383
+ tap: {
4384
+ attach: ['pointerdown', 'pointerup'],
4385
+ condition: function(event, custom){
4386
+ if (event.type == 'pointerdown') {
4387
+ custom.startX = event.clientX;
4388
+ custom.startY = event.clientY;
4389
+ }
4390
+ else if (event.button === 0 &&
4391
+ Math.abs(custom.startX - event.clientX) < 10 &&
4392
+ Math.abs(custom.startY - event.clientY) < 10) return true;
4393
+ }
4394
+ },
4395
+ tapstart: {
4396
+ attach: ['pointerdown'],
4397
+ condition: touchFilter
4398
+ },
4399
+ tapend: {
4400
+ attach: ['pointerup'],
4401
+ condition: touchFilter
4402
+ },
4403
+ tapmove: {
4404
+ attach: ['pointerdown', 'pointerup'],
4405
+ condition: function(event, custom){
4406
+ if (event.type == 'pointerdown') {
4407
+ if (!custom.moveListener) custom.moveListener = xtag.addEvent(this, 'pointermove', custom.listener);
4408
+ }
4409
+ else if (event.type == 'pointerup') {
4410
+ xtag.removeEvent(this, custom.moveListener);
4411
+ custom.moveListener = null;
4412
+ }
4413
+ else return true;
4414
+ }
4415
+ },
4416
+ taphold: {
4417
+ attach: ['pointerdown', 'pointerup'],
4418
+ condition: function(event, custom){
4419
+ if (event.type == 'pointerdown') {
4420
+ (custom.pointers = custom.pointers || {})[event.pointerId] = setTimeout(
4421
+ xtag.fireEvent.bind(null, this, 'taphold'),
4422
+ custom.duration || 1000
4423
+ );
4424
+ }
4425
+ else if (event.type == 'pointerup') {
4426
+ if (custom.pointers) {
4427
+ clearTimeout(custom.pointers[event.pointerId]);
4428
+ delete custom.pointers[event.pointerId];
4429
+ }
4430
+ }
4431
+ else return true;
4432
+ }
4433
+ }
4434
+ },
4435
+ pseudos: {
4436
+ __mixin__: {},
4437
+ mixins: {
4438
+ onCompiled: function(fn, pseudo){
4439
+ var mixin = pseudo.source && pseudo.source.__mixin__ || pseudo.source;
4440
+ if (mixin) switch (pseudo.value) {
4441
+ case null: case '': case 'before': return function(){
4442
+ mixin.apply(this, arguments);
4443
+ return fn.apply(this, arguments);
4444
+ };
4445
+ case 'after': return function(){
4446
+ var returns = fn.apply(this, arguments);
4447
+ mixin.apply(this, arguments);
4448
+ return returns;
4449
+ };
4450
+ case 'none': return fn;
4451
+ }
4452
+ else return fn;
4453
+ }
4454
+ },
4455
+ keypass: keypseudo,
4456
+ keyfail: keypseudo,
4457
+ delegate: {
4458
+ action: delegateAction
4459
+ },
4460
+ preventable: {
4461
+ action: function (pseudo, event) {
4462
+ return !event.defaultPrevented;
4463
+ }
4464
+ },
4465
+ duration: {
4466
+ onAdd: function(pseudo){
4467
+ pseudo.source.duration = Number(pseudo.value);
4468
+ }
4469
+ },
4470
+ capture: {
4471
+ onCompiled: function(fn, pseudo){
4472
+ if (pseudo.source) pseudo.source.capture = true;
4473
+ }
4474
+ }
4475
+ },
4476
+
4477
+ /* UTILITIES */
4478
+
4479
+ clone: clone,
4480
+ typeOf: typeOf,
4481
+ toArray: toArray,
4482
+
4483
+ wrap: function (original, fn) {
4484
+ return function(){
4485
+ var output = original.apply(this, arguments);
4486
+ fn.apply(this, arguments);
4487
+ return output;
4488
+ };
4489
+ },
4490
+ /*
4491
+ Recursively merges one object with another. The first argument is the destination object,
4492
+ all other objects passed in as arguments are merged from right to left, conflicts are overwritten
4493
+ */
4494
+ merge: function(source, k, v){
4495
+ if (typeOf(k) == 'string') return mergeOne(source, k, v);
4496
+ for (var i = 1, l = arguments.length; i < l; i++){
4497
+ var object = arguments[i];
4498
+ for (var key in object) mergeOne(source, key, object[key]);
4499
+ }
4500
+ return source;
4501
+ },
4502
+
4503
+ /*
4504
+ ----- This should be simplified! -----
4505
+ Generates a random ID string
4506
+ */
4507
+ uid: function(){
4508
+ return Math.random().toString(36).substr(2,10);
4509
+ },
4510
+
4511
+ /* DOM */
4512
+
4513
+ query: query,
4514
+
4515
+ skipTransition: function(element, fn, bind){
4516
+ var prop = prefix.js + 'TransitionProperty';
4517
+ element.style[prop] = element.style.transitionProperty = 'none';
4518
+ var callback = fn ? fn.call(bind || element) : null;
4519
+ return xtag.skipFrame(function(){
4520
+ element.style[prop] = element.style.transitionProperty = '';
4521
+ if (callback) callback.call(bind || element);
4522
+ });
4523
+ },
4524
+
4525
+ requestFrame: (function(){
4526
+ var raf = win.requestAnimationFrame ||
4527
+ win[prefix.lowercase + 'RequestAnimationFrame'] ||
4528
+ function(fn){ return win.setTimeout(fn, 20); };
4529
+ return function(fn){ return raf(fn); };
4530
+ })(),
4531
+
4532
+ cancelFrame: (function(){
4533
+ var cancel = win.cancelAnimationFrame ||
4534
+ win[prefix.lowercase + 'CancelAnimationFrame'] ||
4535
+ win.clearTimeout;
4536
+ return function(id){ return cancel(id); };
4537
+ })(),
4538
+
4539
+ skipFrame: function(fn){
4540
+ var id = xtag.requestFrame(function(){ id = xtag.requestFrame(fn); });
4541
+ return id;
4542
+ },
4543
+
4544
+ matchSelector: function (element, selector) {
4545
+ return matchSelector.call(element, selector);
4546
+ },
4547
+
4548
+ set: function (element, method, value) {
4549
+ element[method] = value;
4550
+ if (window.CustomElements) CustomElements.upgradeAll(element);
4551
+ },
4552
+
4553
+ innerHTML: function(el, html){
4554
+ xtag.set(el, 'innerHTML', html);
4555
+ },
4556
+
4557
+ hasClass: function (element, klass) {
4558
+ return element.className.split(' ').indexOf(klass.trim())>-1;
4559
+ },
4560
+
4561
+ addClass: function (element, klass) {
4562
+ var list = element.className.trim().split(' ');
4563
+ klass.trim().split(' ').forEach(function (name) {
4564
+ if (!~list.indexOf(name)) list.push(name);
4565
+ });
4566
+ element.className = list.join(' ').trim();
4567
+ return element;
4568
+ },
4569
+
4570
+ removeClass: function (element, klass) {
4571
+ var classes = klass.trim().split(' ');
4572
+ element.className = element.className.trim().split(' ').filter(function (name) {
4573
+ return name && !~classes.indexOf(name);
4574
+ }).join(' ');
4575
+ return element;
4576
+ },
4577
+
4578
+ toggleClass: function (element, klass) {
4579
+ return xtag[xtag.hasClass(element, klass) ? 'removeClass' : 'addClass'].call(null, element, klass);
4580
+ },
4581
+
4582
+ /*
4583
+ Runs a query on only the children of an element
4584
+ */
4585
+ queryChildren: function (element, selector) {
4586
+ var id = element.id,
4587
+ attr = '#' + (element.id = id || 'x_' + xtag.uid()) + ' > ',
4588
+ parent = element.parentNode || !container.appendChild(element);
4589
+ selector = attr + (selector + '').replace(regexReplaceCommas, ',' + attr);
4590
+ var result = element.parentNode.querySelectorAll(selector);
4591
+ if (!id) element.removeAttribute('id');
4592
+ if (!parent) container.removeChild(element);
4593
+ return toArray(result);
4594
+ },
4595
+
4596
+ /*
4597
+ Creates a document fragment with the content passed in - content can be
4598
+ a string of HTML, an element, or an array/collection of elements
4599
+ */
4600
+ createFragment: function(content) {
4601
+ var template = document.createElement('template');
4602
+ if (content) {
4603
+ if (content.nodeName) toArray(arguments).forEach(function(e){
4604
+ template.content.appendChild(e);
4605
+ });
4606
+ else template.innerHTML = parseMultiline(content);
4607
+ }
4608
+ return document.importNode(template.content, true);
4609
+ },
4610
+
4611
+ /*
4612
+ Removes an element from the DOM for more performant node manipulation. The element
4613
+ is placed back into the DOM at the place it was taken from.
4614
+ */
4615
+ manipulate: function(element, fn){
4616
+ var next = element.nextSibling,
4617
+ parent = element.parentNode,
4618
+ returned = fn.call(element) || element;
4619
+ if (next) parent.insertBefore(returned, next);
4620
+ else parent.appendChild(returned);
4621
+ },
4622
+
4623
+ /* PSEUDOS */
4624
+
4625
+ applyPseudos: function(key, fn, target, source) {
4626
+ var listener = fn,
4627
+ pseudos = {};
4628
+ if (key.match(':')) {
4629
+ var matches = [],
4630
+ valueFlag = 0;
4631
+ key.replace(regexPseudoParens, function(match){
4632
+ if (match == '(') return ++valueFlag == 1 ? '\u276A' : '(';
4633
+ return !--valueFlag ? '\u276B' : ')';
4634
+ }).replace(regexPseudoCapture, function(z, name, value, solo){
4635
+ matches.push([name || solo, value]);
4636
+ });
4637
+ var i = matches.length;
4638
+ while (i--) parsePseudo(function(){
4639
+ var name = matches[i][0],
4640
+ value = matches[i][1];
4641
+ if (!xtag.pseudos[name]) throw "pseudo not found: " + name + " " + value;
4642
+ value = (value === '' || typeof value == 'undefined') ? null : value;
4643
+ var pseudo = pseudos[i] = Object.create(xtag.pseudos[name]);
4644
+ pseudo.key = key;
4645
+ pseudo.name = name;
4646
+ pseudo.value = value;
4647
+ pseudo['arguments'] = (value || '').split(',');
4648
+ pseudo.action = pseudo.action || trueop;
4649
+ pseudo.source = source;
4650
+ pseudo.onAdd = pseudo.onAdd || noop;
4651
+ pseudo.onRemove = pseudo.onRemove || noop;
4652
+ var original = pseudo.listener = listener;
4653
+ listener = function(){
4654
+ var output = pseudo.action.apply(this, [pseudo].concat(toArray(arguments)));
4655
+ if (output === null || output === false) return output;
4656
+ output = pseudo.listener.apply(this, arguments);
4657
+ pseudo.listener = original;
4658
+ return output;
4659
+ };
4660
+ if (!target) pseudo.onAdd.call(fn, pseudo);
4661
+ else target.push(pseudo);
4662
+ });
4663
+ }
4664
+ for (var z in pseudos) {
4665
+ if (pseudos[z].onCompiled) listener = pseudos[z].onCompiled(listener, pseudos[z]) || listener;
4666
+ }
4667
+ return listener;
4668
+ },
4669
+
4670
+ removePseudos: function(target, pseudos){
4671
+ pseudos.forEach(function(obj){
4672
+ obj.onRemove.call(target, obj);
4673
+ });
4674
+ },
4675
+
4676
+ /*** Events ***/
4677
+
4678
+ parseEvent: function(type, fn) {
4679
+ var pseudos = type.split(':'),
4680
+ key = pseudos.shift(),
4681
+ custom = xtag.customEvents[key],
4682
+ event = xtag.merge({
4683
+ type: key,
4684
+ stack: noop,
4685
+ condition: trueop,
4686
+ capture: xtag.captureEvents[key],
4687
+ attach: [],
4688
+ _attach: [],
4689
+ pseudos: '',
4690
+ _pseudos: [],
4691
+ onAdd: noop,
4692
+ onRemove: noop
4693
+ }, custom || {});
4694
+ event.attach = toArray(event.base || event.attach);
4695
+ event.chain = key + (event.pseudos.length ? ':' + event.pseudos : '') + (pseudos.length ? ':' + pseudos.join(':') : '');
4696
+ var stack = xtag.applyPseudos(event.chain, fn, event._pseudos, event);
4697
+ event.stack = function(e){
4698
+ e.currentTarget = e.currentTarget || this;
4699
+ var detail = e.detail || {};
4700
+ if (!detail.__stack__) return stack.apply(this, arguments);
4701
+ else if (detail.__stack__ == stack) {
4702
+ e.stopPropagation();
4703
+ e.cancelBubble = true;
4704
+ return stack.apply(this, arguments);
4705
+ }
4706
+ };
4707
+ event.listener = function(e){
4708
+ var args = toArray(arguments),
4709
+ output = event.condition.apply(this, args.concat([event]));
4710
+ if (!output) return output;
4711
+ // The second condition in this IF is to address the following Blink regression: https://code.google.com/p/chromium/issues/detail?id=367537
4712
+ // Remove this when affected browser builds with this regression fall below 5% marketshare
4713
+ if (e.type != key && (e.baseEvent && e.type != e.baseEvent.type)) {
4714
+ xtag.fireEvent(e.target, key, {
4715
+ baseEvent: e,
4716
+ detail: output !== true && (output.__stack__ = stack) ? output : { __stack__: stack }
4717
+ });
4718
+ }
4719
+ else return event.stack.apply(this, args);
4720
+ };
4721
+ event.attach.forEach(function(name) {
4722
+ event._attach.push(xtag.parseEvent(name, event.listener));
4723
+ });
4724
+ return event;
4725
+ },
4726
+
4727
+ addEvent: function (element, type, fn, capture) {
4728
+ var event = typeof fn == 'function' ? xtag.parseEvent(type, fn) : fn;
4729
+ event._pseudos.forEach(function(obj){
4730
+ obj.onAdd.call(element, obj);
4731
+ });
4732
+ event._attach.forEach(function(obj) {
4733
+ xtag.addEvent(element, obj.type, obj);
4734
+ });
4735
+ event.onAdd.call(element, event, event.listener);
4736
+ element.addEventListener(event.type, event.stack, capture || event.capture);
4737
+ return event;
4738
+ },
4739
+
4740
+ addEvents: function (element, obj) {
4741
+ var events = {};
4742
+ for (var z in obj) {
4743
+ events[z] = xtag.addEvent(element, z, obj[z]);
4744
+ }
4745
+ return events;
4746
+ },
4747
+
4748
+ removeEvent: function (element, type, event) {
4749
+ event = event || type;
4750
+ event.onRemove.call(element, event, event.listener);
4751
+ xtag.removePseudos(element, event._pseudos);
4752
+ event._attach.forEach(function(obj) {
4753
+ xtag.removeEvent(element, obj);
4754
+ });
4755
+ element.removeEventListener(event.type, event.stack);
4756
+ },
4757
+
4758
+ removeEvents: function(element, obj){
4759
+ for (var z in obj) xtag.removeEvent(element, obj[z]);
4760
+ },
4761
+
4762
+ fireEvent: function(element, type, options){
4763
+ var event = doc.createEvent('CustomEvent');
4764
+ options = options || {};
4765
+ event.initCustomEvent(type,
4766
+ options.bubbles !== false,
4767
+ options.cancelable !== false,
4768
+ options.detail
4769
+ );
4770
+ if (options.baseEvent) inheritEvent(event, options.baseEvent);
4771
+ element.dispatchEvent(event);
4772
+ }
4773
+
4774
+ };
4775
+
4776
+ if (typeof define === 'function' && define.amd) define(xtag);
4777
+ else if (typeof module !== 'undefined' && module.exports) module.exports = xtag;
4778
+ else win.xtag = xtag;
4779
+
4780
+ doc.addEventListener('WebComponentsReady', function(){
4781
+ xtag.fireEvent(doc.body, 'DOMComponentsLoaded');
4782
+ });
4783
+
4784
+ })();