(win, ctor)
| 885 | * @param {!Function=} ctor |
| 886 | */ |
| 887 | export function install(win, ctor) { |
| 888 | // Don't install in no-DOM environments e.g. worker. |
| 889 | const shouldInstall = win.document; |
| 890 | const hasCE = hasCustomElements(win); |
| 891 | if (!shouldInstall || (hasCE && isPatched(win))) { |
| 892 | return; |
| 893 | } |
| 894 | |
| 895 | let install = true; |
| 896 | let installWrapper = false; |
| 897 | |
| 898 | if (ctor && hasCE) { |
| 899 | // If ctor is constructable without new, it's a function. That means it was |
| 900 | // compiled down, and we need to do the minimal polyfill because all you |
| 901 | // cannot extend HTMLElement without native classes. |
| 902 | try { |
| 903 | const {Reflect} = win; |
| 904 | |
| 905 | // "Construct" ctor using ES5 idioms |
| 906 | // I'm not sure why, but Closure will complain at the |
| 907 | // `Function.call.call()` below unless we cast to a Function instance |
| 908 | // here. |
| 909 | const instance = /** @type {!Function} */ (Object.create(ctor.prototype)); |
| 910 | |
| 911 | // This will throw an error unless we're in a transpiled environment. |
| 912 | // Native classes must be called as `new Ctor`, not `Ctor.call(instance)`. |
| 913 | // We use `Function.call.call` because Closure is too smart for regular |
| 914 | // `Ctor.call`. |
| 915 | Function.call.call(ctor, instance); |
| 916 | |
| 917 | // If that didn't throw, we're transpiled. |
| 918 | // Let's find out if we can wrap HTMLElement and avoid a full patch. |
| 919 | installWrapper = !!Reflect?.construct; |
| 920 | } catch (e) { |
| 921 | // The ctor threw when we constructed it via ES5, so it's a real class. |
| 922 | // We're ok to not install the polyfill. |
| 923 | install = false; |
| 924 | } |
| 925 | } |
| 926 | |
| 927 | if (installWrapper) { |
| 928 | wrapHTMLElement(win); |
| 929 | } else if (install) { |
| 930 | polyfill(win); |
| 931 | } |
| 932 | } |
no test coverage detected