DEV: adds polyfill to fully support DOMTokenList in IE (#7765)

DEV: adds polyfill to fully support DOMTokenList in IE (#7765)

diff --git a/app/assets/javascripts/polyfills.js b/app/assets/javascripts/polyfills.js
index ab97aeb..e39b2d5 100644
--- a/app/assets/javascripts/polyfills.js
+++ b/app/assets/javascripts/polyfills.js
@@ -189,4 +189,335 @@ if (RegExp.prototype.flags === undefined) {
   });
 }
 
+// https://developer.mozilla.org/en-US/docs/Web/API/Element/classList
+// IE10/11 polyfill to fully support classList
+// 1. String.prototype.trim polyfill
+if (!"".trim)
+  String.prototype.trim = function() {
+    return this.replace(/^[\s]+|[\s]+$/g, "");
+  };
+(function(window) {
+  "use strict"; // prevent global namespace pollution
+  function checkIfValidClassListEntry(O, V) {
+    if (V === "")
+      throw new DOMException(
+        "Failed to execute '" +
+          O +
+          "' on 'DOMTokenList': The token provided must not be empty."
+      );
+    if ((wsI = V.search(wsRE)) !== -1)
+      throw new DOMException(
+        "Failed to execute '" +
+          O +
+          "' on 'DOMTokenList': " +
+          "The token provided ('" +
+          V[wsI] +
+          "') contains HTML space characters, which are not valid in tokens."
+      );
+  }
+  // 2. Implement the barebones DOMTokenList livelyness polyfill
+  if (typeof DOMTokenList !== "function")
+    (function(window) {
+      var document = window.document,
+        Object = window.Object,
+        hasOwnProp = Object.prototype.hasOwnProperty;
+      var defineProperty = Object.defineProperty,
+        allowTokenListConstruction = 0,
+        skipPropChange = 0;
+      var Element = window.Element,
+        wsI = 0,
+        wsRE = /[\11\12\14\15\40]/; // WhiteSpace Regular Expression
+      function DOMTokenList() {
+        if (!allowTokenListConstruction) throw TypeError("Illegal constructor"); // internally let it through
+      }
+      DOMTokenList.prototype.toString = DOMTokenList.prototype.toLocaleString = function() {
+        return this.value;
+      };
+      DOMTokenList.prototype.add = function() {
+        a: for (
+          var v = 0,
+            argLen = arguments.length,
+            val = "",
+            ele = this["uCL"],
+            proto = ele[" uCLp"];
+          v !== argLen;
+          ++v
+        ) {
+          (val = arguments[v] + ""), checkIfValidClassListEntry("add", val);
+          for (var i = 0, Len = proto.length, resStr = val; i !== Len; ++i)
+            if (this[i] === val) continue a;
+            else resStr += " " + this[i];
+          (this[Len] = val), (proto.length += 1), (proto.value = resStr);
+        }
+        (skipPropChange = 1),
+          (ele.className = proto.value),
+          (skipPropChange = 0);
+      };
+      DOMTokenList.prototype.remove = function() {
+        for (
+          var v = 0,
+            argLen = arguments.length,
+            val = "",
+            ele = this["uCL"],
+            proto = ele[" uCLp"];
+          v !== argLen;
+          ++v
+        ) {
+          (val = arguments[v] + ""), checkIfValidClassListEntry("remove", val);
+          for (
+            var i = 0, Len = proto.length, resStr = "", is = 0;
+            i !== Len;
+            ++i
+          )
+            if (is) {
+              this[i - 1] = this[i];
+            } else {
+              if (this[i] !== val) {
+                resStr += this[i] + " ";
+              } else {
+                is = 1;
+              }
+            }
+          if (!is) continue;
+          delete this[Len], (proto.length -= 1), (proto.value = resStr);
+        }
+        (skipPropChange = 1),
+          (ele.className = proto.value),
+          (skipPropChange = 0);
+      };
+      window.DOMTokenList = DOMTokenList;
+      function whenPropChanges() {
+        var evt = window.event,
+          prop = evt.propertyName;
+        if (
+          !skipPropChange &&
+          (prop === "className" || (prop === "classList" && !defineProperty))
+        ) {
+          var target = evt.srcElement,
+            protoObjProto = target[" uCLp"],
+            strval = "" + target[prop];
+          var tokens = strval.trim().split(wsRE),
+            resTokenList = target[prop === "classList" ? " uCL" : "classList"];
+          var oldLen = protoObjProto.length;
+          a: for (
+            var cI = 0, cLen = (protoObjProto.length = tokens.length), sub = 0;
+            cI !== cLen;
+            ++cI
+          ) {
+            for (var innerI = 0; innerI !== cI; ++innerI)
+              if (tokens[innerI] === tokens[cI]) {
+                sub++;
+                continue a;
+              }
+            resTokenList[cI - sub] = tokens[cI];
+          }
+          for (var i = cLen - sub; i < oldLen; ++i) delete resTokenList[i]; //remove trailing indexs
+          if (prop !== "classList") return;
+          (skipPropChange = 1),
+            (target.classList = resTokenList),
+            (target.className = strval);
+          (skipPropChange = 0), (resTokenList.length = tokens.length - sub);
+        }
+      }
+      function polyfillClassList(ele) {
+        if (!ele || !("innerHTML" in ele))
+          throw TypeError("Illegal invocation");
+        srcEle.detachEvent("onpropertychange", whenPropChanges); // prevent duplicate handler infinite loop
+        allowTokenListConstruction = 1;
+        try {
+          function protoObj() {}
+          protoObj.prototype = new DOMTokenList();
+        } finally {
+          allowTokenListConstruction = 0;
+        }
+        var protoObjProto = protoObj.prototype,
+          resTokenList = new protoObj();
+        a: for (
+          var toks = ele.className.trim().split(wsRE),
+            cI = 0,
+            cLen = toks.length,
+            sub = 0;
+          cI !== cLen;
+          ++cI
+        ) {
+          for (var innerI = 0; innerI !== cI; ++innerI)
+            if (toks[innerI] === toks[cI]) {
+              sub++;
+              continue a;
+            }
+          this[cI - sub] = toks[cI];
+        }
+        (protoObjProto.length = Len - sub),
+          (protoObjProto.value = ele.className),
+          (protoObjProto[" uCL"] = ele);
+        if (defineProperty) {
+          defineProperty(ele, "classList", {
+            // IE8 & IE9 allow defineProperty on the DOM
+            enumerable: 1,
+            get: function() {
+              return resTokenList;
+            },
+            configurable: 0,
+            set: function(newVal) {
+              (skipPropChange = 1),
+                (ele.className = protoObjProto.value = newVal += ""),
+                (skipPropChange = 0);
+              var toks = newVal.trim().split(wsRE),
+                oldLen = protoObjProto.length;
+              a: for (
+                var cI = 0,
+                  cLen = (protoObjProto.length = toks.length),
+                  sub = 0;
+                cI !== cLen;
+                ++cI
+              ) {
+                for (var innerI = 0; innerI !== cI; ++innerI)
+                  if (toks[innerI] === toks[cI]) {
+                    sub++;
+                    continue a;
+                  }
+                resTokenList[cI - sub] = toks[cI];
+              }
+              for (var i = cLen - sub; i < oldLen; ++i) delete resTokenList[i]; //remove trailing indexs
+            }
+          });
+          defineProperty(ele, " uCLp", {
+            // for accessing the hidden prototype
+            enumerable: 0,
+            configurable: 0,
+            writeable: 0,
+            value: protoObj.prototype
+          });
+          defineProperty(protoObjProto, " uCL", {
+            enumerable: 0,
+            configurable: 0,
+            writeable: 0,
+            value: ele
+          });
+        } else {
+          (ele.classList = resTokenList),
+            (ele[" uCL"] = resTokenList),
+            (ele[" uCLp"] = protoObj.prototype);
+        }
+        srcEle.attachEvent("onpropertychange", whenPropChanges);
+      }
+      try {
+        // Much faster & cleaner version for IE8 & IE9:

[... diff too long, it was truncated ...]

GitHub sha: 1cbe2dd2