@times-components/interactive-wrapper
Version:
Wrapper for legacy Interactive components
141 lines (114 loc) • 6.19 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.polyfillWCIfNecessary = polyfillWCIfNecessary;
exports.default = void 0;
var _react = _interopRequireWildcard(require("react"));
var _propTypes = _interopRequireDefault(require("prop-types"));
var _image = require("@times-components/image");
var _styles = require("./styles");
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function _getRequireWildcardCache(nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
function asyncGeneratorStep(gen, resolve, reject, _next, _throw, key, arg) { try { var info = gen[key](arg); var value = info.value; } catch (error) { reject(error); return; } if (info.done) { resolve(value); } else { Promise.resolve(value).then(_next, _throw); } }
function _asyncToGenerator(fn) { return function () { var self = this, args = arguments; return new Promise(function (resolve, reject) { var gen = fn.apply(self, args); function _next(value) { asyncGeneratorStep(gen, resolve, reject, _next, _throw, "next", value); } function _throw(err) { asyncGeneratorStep(gen, resolve, reject, _next, _throw, "throw", err); } _next(undefined); }); }; }
function ensureElement(selector, createElement) {
if (document.body.querySelector(selector)) {
return Promise.resolve(null);
}
return new Promise((resolve, reject) => {
const element = createElement();
element.onload = resolve;
element.onerror = reject;
document.body.appendChild(element);
});
}
function ensureScript(src) {
return ensureElement("script[src=\"".concat(src, "\"]"), () => {
const script = document.createElement("script");
script.setAttribute("async", "async");
script.setAttribute("src", src);
return script;
});
}
function ensureImport(src) {
return ensureElement("link[href=\"".concat(src, "\"]"), () => {
const link = document.createElement("link");
link.setAttribute("href", src);
link.setAttribute("rel", "import");
return link;
});
}
function polyfillWCIfNecessary() {
const htmlImportsSupported = ("import" in document.createElement("link"));
const registerElementSupported = !!document.registerElement;
if (!htmlImportsSupported || !registerElementSupported) {
return Promise.all([ensureScript("https://cdnjs.cloudflare.com/ajax/libs/webcomponentsjs/0.7.24/webcomponents-lite.min.js"), new Promise(resolve => {
window.addEventListener("WebComponentsReady", resolve);
})]);
}
return Promise.resolve();
}
class InteractiveWrapper extends _react.Component {
constructor(props) {
super(props);
this.placeholder = _react.default.createRef(null);
this.component = _react.default.createRef(null);
}
componentDidMount() {
const fetchPolyfill = this.props.fetchPolyfill;
fetchPolyfill().then(() => {
this.insertComponent();
});
}
componentDidUpdate() {
this.insertComponent();
}
insertComponent() {
var _this = this;
return _asyncToGenerator(function* () {
const _this$props = _this.props,
attributes = _this$props.attributes,
element = _this$props.element,
source = _this$props.source;
const placeholder = _this.placeholder.current;
const component = _this.component.current;
component.innerHTML = "";
placeholder.style.cssText += "display: block !important"; // It is possible for insertComponent to have been called again whilst the
// import link tag was loading. and therefore it is possible for multiple
// interactives to be inserted – therefore, we ensure that the interactive
// container is empty before inserting
component.innerHTML = "";
const newElement = document.createElement(element);
Object.keys(attributes).forEach(key => newElement.setAttribute(key, attributes[key]));
component.appendChild(newElement); // Do not remove this. This seems to notify polymer to correctly
// render the web component in more circumstances, specifically,
// its required to correctly re-render after a react re-render
newElement.outerHTML += "";
placeholder.style.cssText += "display: none !important";
yield ensureImport(source);
})();
}
render() {
const attributes = this.props.attributes;
return /*#__PURE__*/_react.default.createElement(_styles.InteractiveWrapperContainer, null, /*#__PURE__*/_react.default.createElement(_styles.Container, {
ref: this.placeholder,
$height: attributes.height
}, /*#__PURE__*/_react.default.createElement(_image.Placeholder, null)), /*#__PURE__*/_react.default.createElement(_styles.InteractiveContainer, {
ref: this.component,
$height: attributes.height
}));
}
}
exports.default = InteractiveWrapper;
InteractiveWrapper.propTypes = {
attributes: _propTypes.default.object,
element: _propTypes.default.string.isRequired,
source: _propTypes.default.string.isRequired,
fetchPolyfill: _propTypes.default.func
};
InteractiveWrapper.defaultProps = {
attributes: {},
fetchPolyfill: polyfillWCIfNecessary
};