aboutsummaryrefslogtreecommitdiff
path: root/src/client/react/components/presentational/Schedule.js
diff options
context:
space:
mode:
Diffstat (limited to 'src/client/react/components/presentational/Schedule.js')
-rw-r--r--src/client/react/components/presentational/Schedule.js63
1 files changed, 53 insertions, 10 deletions
diff --git a/src/client/react/components/presentational/Schedule.js b/src/client/react/components/presentational/Schedule.js
index 256c1b4..e62039c 100644
--- a/src/client/react/components/presentational/Schedule.js
+++ b/src/client/react/components/presentational/Schedule.js
@@ -2,18 +2,61 @@ import React from 'react';
import PropTypes from 'prop-types';
import createDOMPurify from 'dompurify';
-const Schedule = ({ htmlStr }) => {
- const DOMPurify = createDOMPurify(window);
+class Schedule extends React.Component {
+ constructor(props) {
+ super(props);
- const cleanHTML = DOMPurify.sanitize(htmlStr, {
- ADD_ATTR: ['rules'],
- });
+ this.updateScaling = this.updateScaling.bind(this);
+ }
- return (
- // eslint-disable-next-line react/no-danger
- <div dangerouslySetInnerHTML={{ __html: cleanHTML }} />
- );
-};
+ componentDidMount() {
+ window.addEventListener('resize', this.updateScaling);
+ this.updateScaling();
+ }
+
+ componentDidUpdate() {
+ this.updateScaling();
+ }
+
+ componentWillUnmount() {
+ window.removeEventListener('resize', this.updateScaling);
+ }
+
+ updateScaling() {
+ const windowWidth = window.innerWidth;
+ const tableNode = this.scheduleDiv.querySelector('table');
+ if (!tableNode) return;
+
+ // We want a 16px margin on both sides, this marging will be scaled with
+ // the entire schedule.
+ const tableWidth = tableNode.offsetWidth + 32;
+
+ let scale = windowWidth / tableWidth;
+ if (scale > 1) {
+ scale = 1;
+ }
+
+ this.scheduleDiv.style.transform = `scale(${scale})`;
+ this.scheduleDiv.style.transformOrigin = 'left top';
+ this.scheduleDiv.style.margin = `${16 * scale}px`;
+ }
+
+ render() {
+ const DOMPurify = createDOMPurify(window);
+
+ const cleanHTML = DOMPurify.sanitize(this.props.htmlStr, {
+ ADD_ATTR: ['rules'],
+ });
+
+ return (
+ <div
+ // eslint-disable-next-line react/no-danger
+ dangerouslySetInnerHTML={{ __html: cleanHTML }}
+ ref={(div) => { this.scheduleDiv = div; }}
+ />
+ );
+ }
+}
Schedule.propTypes = {
htmlStr: PropTypes.string.isRequired,