I have been playing around with Angular Elements and trying to achieve the best browser compatibility possible. However I seem to have hit a dead end, since when I add an IE polyfill for Shadow DOM, it breaks the Element in chrome.
Initially I had the error 'Failed to construct HTML element', so I changed the 'target' in my tsconfig.json to es2015/es6.
tsconfig.json
{
"compileOnSave": false,
"compilerOptions": {
"baseUrl": "./",
"outDir": "./dist/out-tsc",
"sourceMap": true,
"declaration": false,
"module": "es2015",
"moduleResolution": "node",
"emitDecoratorMetadata": true,
"experimentalDecorators": true,
"target": "es5",
"typeRoots": [
"node_modules/@types"
],
"lib": [
"es2018",
"dom"
]
}
}
Component
// @dynamic
@Component({
selector: 'flexybox-cardmanagement',
templateUrl: './card-management.component.html',
styleUrls: ['./card-management.component.scss'],
encapsulation: ViewEncapsulation.ShadowDom
})
Changing the target happened to break IE though, since es2015/es6+ is not supported. So I happened to find the custom-elements-es5-adapter in the @webcomponents package, which wraps ES5 to provide the neccessary ES6 functionality to the browsers that needs it. And then I also had to add support for custom-elements.
polyfills.ts
/*****************************************************************************************
* APPLICATION IMPORTS
*/
import '@webcomponents/webcomponentsjs/custom-elements-es5-adapter.js';
import '@webcomponents/custom-elements/custom-elements.min';
At this point it works in Chrome but i get the following error in IE
SCRIPT438: Object doesn't support property or method 'attachShadow'
So I tried adding polyfill for Shadow DOM by adding the following to my polyfills.ts:
import '@webcomponents/shadydom';
Which seems to fix the issue in IE, but now gives me the following error in chrome:
Uncaught TypeError: Cannot read property 'defineProperties' of undefined
Getting custom elements to work in IE11 is really a torture. I may not bring you there, but at least one step further.
I think you did almost everything right, I've gone through the same steps, but I used diffrent polyfills, so maybe you want to try these:
angular.json
"scripts": [
// removed polyfill `document-register-element.js` that may be included with ng add @angular/elements
]
polyfills.ts
import '@webcomponents/shadydom/shadydom.min.js';
import '@webcomponents/custom-elements/src/native-shim';
import '@webcomponents/custom-elements/custom-elements.min';
To check if it might be a version problem:
package.json (relevant parts)
{
"dependencies": {
"@angular/**": "~7.2.1",
"@webcomponents/custom-elements": "^1.2.1",
"@webcomponents/shadydom": "^1.4.2",
"core-js": "^2.5.4",
}
}
Info: With this configuration, the custom element works in Chrome, Firefox and IE11 for me, but I don't get output bindings to work in IE11. I don't know why this is caused, if you are interested in this and find a solution to it, you may provide it here.
Genral tip for IE11:
Not your problem now, but if IE11 throws one of its various erros, it helped me a lot to use import 'core-js/shim'
in polyfills.ts
. This imports all shims at once to check if IE11 misses one of those. If so, you can tackle it down further, if not you know you have to look elsewhere.
Angular Elements polyfill
If you want to stay with the polyfill used by Angular, you may try to use version 1.8.1
. I read somewhere (but can't remember where) that later versions cause problems in IE at the moment.
If I understand it correctly the issue relates to the fact that IE11 doesn't support classes and that Chrome must have classes for webcomponents. There is a wrapper that lets you have one bundle and then wrap the functional-approach in a class for chrome, but I would recommend having two seperate bundles for this instead, and not compile to es5 for browsers that understand classes.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With