Search code examples
javascriptangularjsinternet-explorercloneweb-component

Web Components with angular.js & IE11 compatibility


I have angular.js application in which I would like to initialize a web component.

It works perfectly fine on other browsers but it seems that IE11 has issues with

document.importNode

angular.js onInit function:

           vm.$onInit = function() {
                vm.params = $location.search();

                if(vm.params.merchantId  && vm.params.apiToken && vm.params.amount && vm.params.orderId) {
                    vm.mid = vm.params.merchantId;
                    vm.apiToken = vm.params.apiToken;
                    vm.amount = vm.params.amount;
                    vm.orderId = vm.params.orderId;

                    let template = document.querySelector('#template');
                    let clone = document.importNode(template.content, true);
                    let cmp = clone.querySelector('cmp-request');
                    
                    cmp.setAttribute('mid', vm.mid);

                    template.replaceWith(clone);
                    
                }
            }

HTML:

<template id="template"> 
    <cmp-request></cmp-request>
</template>

Is there any other way to clone web component and pass params inside without using importNode so it would work on IE11?


Solution

  • IE 11 doesn't support importNode and replaceWith. For importNode, I use children to get <template>'s children to get the web component in IE 11. For replaceWith, I use this polyfill to support it in IE 11.

    You can refer to my code sample with dummy values:

    function ReplaceWithPolyfill() {
      'use-strict'; // For safari, and IE > 10
      var parent = this.parentNode,
        i = arguments.length,
        currentNode;
      if (!parent) return;
      if (!i) // if there are no arguments
        parent.removeChild(this);
      while (i--) { // i-- decrements i and returns the value of i before the decrement
        currentNode = arguments[i];
        if (typeof currentNode !== 'object') {
          currentNode = this.ownerDocument.createTextNode(currentNode);
        } else if (currentNode.parentNode) {
          currentNode.parentNode.removeChild(currentNode);
        }
        // the value of "i" below is after the decrement
        if (!i) // if currentNode is the first argument (currentNode === arguments[0])
          parent.replaceChild(currentNode, this);
        else // if currentNode isn't the first
          parent.insertBefore(currentNode, this.nextSibling);
      }
    }
    if (!Element.prototype.replaceWith)
      Element.prototype.replaceWith = ReplaceWithPolyfill;
    if (!CharacterData.prototype.replaceWith)
      CharacterData.prototype.replaceWith = ReplaceWithPolyfill;
    if (!DocumentType.prototype.replaceWith)
      DocumentType.prototype.replaceWith = ReplaceWithPolyfill;
    
    
    var template = document.querySelector('#template');
    if (navigator.userAgent.indexOf('MSIE') !== -1 || navigator.appVersion.indexOf('Trident/') > -1) { //IE11
      var clone = template.children[0];
      clone.setAttribute('mid', 'test');
    } else {
      var clone = document.importNode(template.content, true);
      var cmp = clone.querySelector('cmp-request');
      cmp.setAttribute('mid', 'test');
    }
    template.replaceWith(clone);
    <template id="template">
       <cmp-request></cmp-request>
    </template>