@hhgtech/hhg-components
Version:
Hello Health Group common components
233 lines (224 loc) • 11 kB
JavaScript
'use strict';
var tslib_es6 = require('./tslib.es6-92cccef3.js');
var React = require('react');
var core = require('@mantine/core');
var useScreenSize = require('./useScreenSize-30f50b76.js');
var togetherComponentGlobalContext = require('./utils-aea77f4a.js');
var styled = require('@emotion/styled');
var togetherApiPaths = require('./togetherApiPaths.js');
var constants = require('./constants-bb30dda6.js');
var post = require('./post-ca5ee38c.js');
var index = require('./index-33cb6efd.js');
function _interopDefault (e) { return e && e.__esModule ? e : { 'default': e }; }
var React__default = /*#__PURE__*/_interopDefault(React);
var styled__default = /*#__PURE__*/_interopDefault(styled);
const StyledSocialLinkPreview = styled__default["default"].div `
.link-info-container {
padding: 0.5rem 1rem;
background: ${(props) => props.color || '#f4faff'};
}
.link-image-wrapper {
position: relative;
overflow: hidden;
width: 100%;
padding-top: 56.25%;
&.fetching {
background: lightgray;
}
.loading-spinner {
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
.link-image {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
object-fit: cover;
object-position: center;
}
}
a {
text-decoration: none;
}
&[data-is-marrybaby='true'] {
overflow: hidden;
border-radius: 1rem;
}
`;
const useExternalScript = ({ url, onLoad, onError }) => {
const [state, setState] = React.useState(url ? 'loading' : 'idle');
React.useEffect(() => {
if (!url) {
setState('idle');
return;
}
let script = document.querySelector(`script[src="${url}"]`);
const handleLoadScript = () => {
setState('ready');
onLoad === null || onLoad === void 0 ? void 0 : onLoad();
};
const handleErrorScript = () => {
setState('error');
onError === null || onError === void 0 ? void 0 : onError();
};
if (!script) {
script = document.createElement('script');
script.type = 'application/javascript';
script.src = url;
script.async = true;
document.body.appendChild(script);
script.addEventListener('load', handleLoadScript);
script.addEventListener('error', handleErrorScript);
}
script.addEventListener('load', handleLoadScript);
script.addEventListener('error', handleErrorScript);
return () => {
script.removeEventListener('load', handleLoadScript);
script.removeEventListener('error', handleErrorScript);
};
}, [url]);
return state;
};
const YoutubePlyr = ({ id, autoplay }) => {
const ref = React.useRef(null);
const state = useExternalScript({ url: 'https://cdn.plyr.io/3.7.8/plyr.js' });
React.useEffect(() => {
if (!document.getElementById('hhg-plyr-player')) {
const link = document.createElement('link');
link.rel = 'stylesheet';
link.type = 'text/css';
link.href = 'https://cdn.plyr.io/3.7.8/plyr.css';
link.id = 'hhg-plyr-player';
document.head.appendChild(link);
}
if (state === 'ready' || typeof Plyr !== 'undefined') {
new Plyr(ref.current.querySelector('[data-id="player"]'), {
autoplay,
muted: true,
});
}
}, [state]);
return (React__default["default"].createElement(React__default["default"].Fragment, null,
React__default["default"].createElement(core.Box, { ref: ref, sx: {
position: 'absolute',
top: 0,
left: 0,
right: 0,
bottom: 0,
backgroundColor: '#000',
'&, > div': {
width: '100%',
height: '100%',
},
} },
React__default["default"].createElement("div", { "data-id": "player" },
React__default["default"].createElement("iframe", { width: "100%", height: "100%", src: `https://www.youtube.com/embed/${id}?&mute=1&enablejsapi=1&rel=0`, allowFullScreen: true, frameBorder: "0" })))));
};
const SocialLinkPreview = ({ url, image, className, style, baseUrl = '', autoPlay = true, onPushStatus, }) => {
const { data: { locale }, } = React.useContext(togetherComponentGlobalContext.TogetherComponentGlobalContext);
const [previewData, setPreviewData] = React.useState(null);
React.useEffect(() => {
(() => tslib_es6.__awaiter(void 0, void 0, void 0, function* () {
if (image)
return;
if (!url)
return setPreviewData(null);
setPreviewData((_data) => (Object.assign(Object.assign({}, _data), { isFetching: true })));
// fetch('./api/fetch-meta?url=' + encodeURIComponent(url))
// .then((res) => res.json())
// .then((res) =>
// setPreviewData({
// url,
// image: res?.image || res?.logo,
// }),
// )
togetherComponentGlobalContext.callApi(togetherComponentGlobalContext.getApiPath(togetherApiPaths.PATHS.FETCH_PREVIEW, {
_locale: locale,
}, undefined, baseUrl), 'POST', {
data: {
link: url,
},
headers: {
'Content-Type': 'application/json',
},
}, !!baseUrl)
.then((res) => {
var _a, _b;
setPreviewData({
url,
image: ((_a = res === null || res === void 0 ? void 0 : res.data) === null || _a === void 0 ? void 0 : _a.image) || ((_b = res === null || res === void 0 ? void 0 : res.data) === null || _b === void 0 ? void 0 : _b.logo),
});
})
.catch(() => {
setPreviewData(null);
});
}))();
}, [url, image]);
const displayImage = image || (previewData === null || previewData === void 0 ? void 0 : previewData.image);
const displayUrl = (previewData === null || previewData === void 0 ? void 0 : previewData.url) || url;
const youtubeVidId = React.useMemo(() => {
return post.youtubeVidIdGetter(displayUrl);
}, [displayUrl]);
const facebookVidId = React.useMemo(() => {
return (displayUrl.includes('facebook.com') || displayUrl.includes('fb.watch'));
}, [displayUrl]);
const responsiveWidth = React.useRef(0);
const responsiveHeight = React.useRef(0);
const [forceRerenderFB, setForceRerenderFB] = React.useState(false);
// FACEBOOK Video is not responsive for desktop browser
// => hack: set size to same as container, if size change too large, re-render facebook iframe with new config
React.useEffect(() => {
const handleResize = () => {
var _a;
const containerRect = (_a = containerRef.current) === null || _a === void 0 ? void 0 : _a.getBoundingClientRect();
let toChangeSize = false;
if (containerRect &&
(!responsiveWidth.current ||
Math.abs((responsiveWidth.current - containerRect.width) /
(containerRect === null || containerRect === void 0 ? void 0 : containerRect.width)) > 0.2)) {
responsiveWidth.current = Math.floor(containerRect.width);
toChangeSize = true;
}
if (containerRect &&
(!responsiveHeight.current ||
Math.abs((responsiveHeight.current - containerRect.height) /
(containerRect === null || containerRect === void 0 ? void 0 : containerRect.height)) > 0.2)) {
responsiveHeight.current = Math.floor(containerRect.height);
toChangeSize = true;
}
if (toChangeSize) {
setForceRerenderFB((v) => !v);
}
};
handleResize();
window.addEventListener('resize', handleResize, {
passive: true,
});
return () => {
window.removeEventListener('resize', handleResize);
};
}, []);
React.useEffect(() => {
if ((previewData === null || previewData === void 0 ? void 0 : previewData.image) && (previewData === null || previewData === void 0 ? void 0 : previewData.url)) {
onPushStatus === null || onPushStatus === void 0 ? void 0 : onPushStatus(true);
}
}, [previewData]);
const containerRef = React.useRef(null);
const _theme = core.useMantineTheme();
return (React__default["default"].createElement(StyledSocialLinkPreview, { className: `${className} no-replace-click`, style: style, ref: containerRef, color: _theme.colors[_theme.primaryColor][0] }, !image && (youtubeVidId || facebookVidId) ? (React__default["default"].createElement("div", { className: "link-image-wrapper" }, youtubeVidId ? (React__default["default"].createElement(YoutubePlyr, { id: youtubeVidId, autoplay: autoPlay })) : facebookVidId ? (React__default["default"].createElement("iframe", { key: String(forceRerenderFB), src: `https://www.facebook.com/plugins/video.php?href=${encodeURIComponent(displayUrl)}&autoplay=${autoPlay ? 1 : 0}&show_text=false&t=0&width=${responsiveWidth.current}&height=${responsiveHeight.current}`, style: {
position: 'absolute',
top: '50%',
left: '50%',
border: 'none',
overflow: 'hidden',
height: responsiveHeight.current,
width: responsiveWidth.current,
transform: 'translate(-50%, -50%)',
}, scrolling: "no", frameBorder: "0", allowFullScreen: true, allow: "autoplay; clipboard-write; encrypted-media; picture-in-picture; web-share", loading: "lazy" })) : null)) : (React__default["default"].createElement("a", { href: displayUrl, target: "_blank", rel: "noreferrer" },
React__default["default"].createElement("div", { className: `link-image-wrapper ${(previewData === null || previewData === void 0 ? void 0 : previewData.isFetching) ? 'fetching' : ''}` }, (previewData === null || previewData === void 0 ? void 0 : previewData.isFetching) ? (React__default["default"].createElement(index.Loading, { className: "loading-spinner" })) : (React__default["default"].createElement(useScreenSize.ImageWrap, { className: "link-image", src: displayImage || constants.DEFAULT_IMG, backupSrc: constants.DEFAULT_IMG, alt: displayUrl })))))));
};
exports.SocialLinkPreview = SocialLinkPreview;