@pie-lib/render-ui 4.15.9 → 4.16.1-beta.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (58) hide show
  1. package/CHANGELOG.md +20 -52
  2. package/NEXT.CHANGELOG.json +1 -0
  3. package/package.json +6 -4
  4. package/src/__tests__/__snapshots__/html-and-math.test.js.snap +11 -0
  5. package/src/__tests__/__snapshots__/preview-prompt.test.jsx.snap +37 -0
  6. package/src/__tests__/__snapshots__/purpose.test.jsx.snap +42 -0
  7. package/src/__tests__/__snapshots__/readable.test.jsx.snap +64 -0
  8. package/src/__tests__/__snapshots__/response-indicators.test.jsx.snap +95 -0
  9. package/src/__tests__/color.test.js +12 -0
  10. package/src/__tests__/has-media.test.js +20 -0
  11. package/src/__tests__/has-text.test.js +21 -0
  12. package/src/__tests__/html-and-math.test.js +46 -0
  13. package/src/__tests__/preview-prompt.test.jsx +56 -0
  14. package/src/__tests__/purpose.test.jsx +47 -0
  15. package/src/__tests__/readable.test.jsx +64 -0
  16. package/src/__tests__/response-indicators.test.jsx +16 -0
  17. package/src/__tests__/ui-layout.test.jsx +34 -0
  18. package/src/__tests__/withUndoReset.test.jsx +254 -0
  19. package/src/append-css-rules.js +51 -0
  20. package/src/assets/enableAudioAutoplayImage.js +1 -0
  21. package/src/collapsible/__tests__/__snapshots__/index.test.jsx.snap +18 -0
  22. package/src/collapsible/__tests__/index.test.jsx +13 -0
  23. package/src/collapsible/index.jsx +1 -0
  24. package/src/color.js +40 -0
  25. package/src/feedback.jsx +0 -1
  26. package/src/has-media.js +16 -0
  27. package/src/has-text.js +5 -1
  28. package/src/index.js +8 -0
  29. package/src/preview-layout.jsx +14 -3
  30. package/src/preview-prompt.jsx +150 -26
  31. package/src/ui-layout.jsx +66 -0
  32. package/README.md +0 -33
  33. package/lib/collapsible/index.js +0 -134
  34. package/lib/collapsible/index.js.map +0 -1
  35. package/lib/color.js +0 -157
  36. package/lib/color.js.map +0 -1
  37. package/lib/feedback.js +0 -151
  38. package/lib/feedback.js.map +0 -1
  39. package/lib/has-text.js +0 -24
  40. package/lib/has-text.js.map +0 -1
  41. package/lib/html-and-math.js +0 -90
  42. package/lib/html-and-math.js.map +0 -1
  43. package/lib/index.js +0 -104
  44. package/lib/index.js.map +0 -1
  45. package/lib/input-container.js +0 -60
  46. package/lib/input-container.js.map +0 -1
  47. package/lib/preview-layout.js +0 -133
  48. package/lib/preview-layout.js.map +0 -1
  49. package/lib/preview-prompt.js +0 -206
  50. package/lib/preview-prompt.js.map +0 -1
  51. package/lib/purpose.js +0 -28
  52. package/lib/purpose.js.map +0 -1
  53. package/lib/readable.js +0 -28
  54. package/lib/readable.js.map +0 -1
  55. package/lib/response-indicators.js +0 -151
  56. package/lib/response-indicators.js.map +0 -1
  57. package/lib/withUndoReset.js +0 -181
  58. package/lib/withUndoReset.js.map +0 -1
package/src/index.js CHANGED
@@ -3,6 +3,7 @@ import Feedback from './feedback';
3
3
  import Collapsible from './collapsible';
4
4
  import withUndoReset from './withUndoReset';
5
5
  import PreviewLayout from './preview-layout';
6
+ import UiLayout from './ui-layout';
6
7
  import HtmlAndMath from './html-and-math';
7
8
  import InputContainer from './input-container';
8
9
  import PreviewPrompt from './preview-prompt';
@@ -10,12 +11,17 @@ import Readable from './readable';
10
11
  import Purpose from './purpose';
11
12
  import * as color from './color';
12
13
  import { hasText } from './has-text';
14
+ import { hasMedia } from './has-media';
15
+ import EnableAudioAutoplayImage from './assets/enableAudioAutoplayImage';
16
+ import AppendCSSRules from './append-css-rules';
13
17
 
14
18
  export {
19
+ AppendCSSRules,
15
20
  HtmlAndMath,
16
21
  indicators,
17
22
  withUndoReset,
18
23
  Feedback,
24
+ UiLayout,
19
25
  PreviewLayout,
20
26
  Collapsible,
21
27
  InputContainer,
@@ -24,4 +30,6 @@ export {
24
30
  Readable,
25
31
  Purpose,
26
32
  hasText,
33
+ hasMedia,
34
+ EnableAudioAutoplayImage,
27
35
  };
@@ -1,6 +1,7 @@
1
1
  import React from 'react';
2
2
  import { withStyles, createMuiTheme, MuiThemeProvider } from '@material-ui/core/styles';
3
3
  import PropTypes from 'prop-types';
4
+ import UiLayout from './ui-layout';
4
5
 
5
6
  class PreviewLayout extends React.Component {
6
7
  static propTypes = {
@@ -8,16 +9,26 @@ class PreviewLayout extends React.Component {
8
9
  children: PropTypes.oneOfType([PropTypes.arrayOf(PropTypes.node), PropTypes.node]).isRequired,
9
10
  classes: PropTypes.object,
10
11
  role: PropTypes.string,
12
+ extraCSSRules: PropTypes.shape({
13
+ names: PropTypes.arrayOf(PropTypes.string),
14
+ rules: PropTypes.string,
15
+ }),
16
+ fontSizeFactor: PropTypes.number,
11
17
  };
12
18
 
13
19
  render() {
14
- const { children, classes, ariaLabel, role } = this.props;
20
+ const { children, classes, ariaLabel, role, extraCSSRules, fontSizeFactor } = this.props;
15
21
  const accessibility = ariaLabel ? { 'aria-label': ariaLabel, role } : {};
16
22
 
17
23
  return (
18
- <div className={classes.container} {...accessibility}>
24
+ <UiLayout
25
+ className={classes.container}
26
+ {...accessibility}
27
+ extraCSSRules={extraCSSRules}
28
+ fontSizeFactor={fontSizeFactor}
29
+ >
19
30
  {children}
20
- </div>
31
+ </UiLayout>
21
32
  );
22
33
  }
23
34
  }
@@ -15,6 +15,11 @@ export class PreviewPrompt extends Component {
15
15
  className: PropTypes.string,
16
16
  onClick: PropTypes.func,
17
17
  defaultClassName: PropTypes.string,
18
+ autoplayAudioEnabled: PropTypes.bool,
19
+ customAudioButton: {
20
+ playImage: PropTypes.string,
21
+ pauseImage: PropTypes.string,
22
+ },
18
23
  };
19
24
 
20
25
  static defaultProps = {
@@ -22,7 +27,7 @@ export class PreviewPrompt extends Component {
22
27
  };
23
28
 
24
29
  parsedText = (text) => {
25
- // fix imported audio content for Safari PD-1419
30
+ const { customAudioButton } = this.props;
26
31
  const div = document.createElement('div');
27
32
  div.innerHTML = text;
28
33
 
@@ -34,38 +39,150 @@ export class PreviewPrompt extends Component {
34
39
  source.setAttribute('src', audio.getAttribute('src'));
35
40
 
36
41
  audio.removeAttribute('src');
42
+ audio.setAttribute('id', 'pie-prompt-audio-player');
43
+
37
44
  audio.appendChild(source);
45
+
46
+ if (customAudioButton) {
47
+ audio.style.display = 'none';
48
+
49
+ const playButton = document.createElement('div');
50
+ playButton.id = 'play-audio-button';
51
+
52
+ Object.assign(playButton.style, {
53
+ cursor: 'pointer',
54
+ display: 'block',
55
+ width: '128px',
56
+ height: '128px',
57
+ backgroundImage: `url(${customAudioButton.pauseImage})`,
58
+ backgroundSize: 'cover',
59
+ borderRadius: '50%',
60
+ border: '1px solid #326295',
61
+ });
62
+
63
+ audio.parentNode.insertBefore(playButton, audio);
64
+ }
38
65
  }
39
66
 
40
67
  return div.innerHTML;
41
68
  };
42
69
 
70
+ addCustomAudioButtonControls() {
71
+ const { autoplayAudioEnabled, customAudioButton } = this.props;
72
+ const playButton = document.getElementById('play-audio-button');
73
+ const audio = document.getElementById('pie-prompt-audio-player');
74
+
75
+ if (autoplayAudioEnabled && audio) {
76
+ audio
77
+ .play()
78
+ .then(() => {
79
+ if (playButton && customAudioButton) {
80
+ audio.addEventListener('ended', handleAudioEnded);
81
+ }
82
+ })
83
+ .catch((error) => {
84
+ console.error('Error playing audio', error);
85
+ });
86
+ }
87
+
88
+ if (!playButton || !audio || !customAudioButton) return;
89
+
90
+ const handlePlayClick = () => {
91
+ // if already playing, don't play again
92
+ if (!audio.paused) return;
93
+ if (playButton.style.backgroundImage.includes(customAudioButton.pauseImage)) return;
94
+
95
+ audio.play();
96
+ };
97
+
98
+ const handleAudioEnded = () => {
99
+ playButton.style.backgroundImage = `url(${customAudioButton.playImage})`;
100
+ };
101
+
102
+ const handleAudioPlay = () => {
103
+ Object.assign(playButton.style, {
104
+ backgroundImage: `url(${customAudioButton.pauseImage})`,
105
+ border: '1px solid #ccc',
106
+ });
107
+ };
108
+
109
+ const handleAudioPause = () => {
110
+ Object.assign(playButton.style, {
111
+ backgroundImage: `url(${customAudioButton.playImage})`,
112
+ border: '1px solid #326295',
113
+ });
114
+ };
115
+
116
+ playButton.addEventListener('click', handlePlayClick);
117
+ audio.addEventListener('play', handleAudioPlay);
118
+ audio.addEventListener('pause', handleAudioPause);
119
+ audio.addEventListener('ended', handleAudioEnded);
120
+
121
+ // store event handler references so they can be removed later
122
+ this._handlePlayClick = handlePlayClick;
123
+ this._handleAudioPlay = handleAudioPlay;
124
+ this._handleAudioPause = handleAudioPause;
125
+ this._handleAudioEnded = handleAudioEnded;
126
+ }
127
+
128
+ removeCustomAudioButtonListeners() {
129
+ const playButton = document.getElementById('play-audio-button');
130
+ const audio = document.querySelector('audio');
131
+
132
+ if (!playButton || !audio) return;
133
+
134
+ // remove event listeners using stored references
135
+ playButton.removeEventListener('click', this._handlePlayClick);
136
+ audio.removeEventListener('play', this._handleAudioPlay);
137
+ audio.removeEventListener('pause', this._handleAudioPause);
138
+ audio.removeEventListener('ended', this._handleAudioEnded);
139
+ }
140
+
141
+ componentDidMount() {
142
+ this.alignImages();
143
+ this.addCustomAudioButtonControls();
144
+ }
145
+
43
146
  componentDidUpdate() {
44
- // set image parent style so it can be horizontally aligned
45
- const previewPrompt = document.querySelector('#preview-prompt');
46
- const images = previewPrompt && previewPrompt.getElementsByTagName('img');
47
-
48
- if (images && images.length) {
49
- for (let image of images) {
50
- // check if alignment property was set
51
- if (image.attributes && image.attributes.alignment && image.attributes.alignment.value) {
52
- const parentNode = image.parentElement;
53
-
54
- // check if div is not already added to dom and replace current image with wrapped image
55
- if (
56
- !(parentNode.tagName === 'DIV' && parentNode.style.display === 'flex' && parentNode.style.width === '100%')
57
- ) {
58
- const div = document.createElement('div');
59
- div.style.display = 'flex';
60
- div.style.width = '100%';
61
-
62
- const copyImage = image.cloneNode(true);
63
- div.appendChild(copyImage);
64
- parentNode.replaceChild(div, image);
147
+ this.alignImages();
148
+ }
149
+
150
+ componentWillUnmount() {
151
+ this.removeCustomAudioButtonListeners();
152
+ }
153
+
154
+ alignImages() {
155
+ const previewPrompts = document.querySelectorAll('#preview-prompt');
156
+
157
+ previewPrompts.forEach((previewPrompt) => {
158
+ const images = previewPrompt.getElementsByTagName('img');
159
+
160
+ if (images && images.length) {
161
+ for (let image of images) {
162
+ // check if alignment property was set
163
+ if (image.attributes && image.attributes.alignment && image.attributes.alignment.value) {
164
+ const parentNode = image.parentElement;
165
+
166
+ // check if div is not already added to dom and replace current image with wrapped image
167
+ if (
168
+ !(
169
+ parentNode.tagName === 'DIV' &&
170
+ parentNode.style.display === 'flex' &&
171
+ parentNode.style.width === '100%'
172
+ )
173
+ ) {
174
+ const div = document.createElement('div');
175
+ div.style.display = 'flex';
176
+ div.style.width = '100%';
177
+
178
+ const copyImage = image.cloneNode(true);
179
+ div.appendChild(copyImage);
180
+ parentNode.replaceChild(div, image);
181
+ }
65
182
  }
66
183
  }
67
184
  }
68
- }
185
+ });
69
186
  }
70
187
 
71
188
  render() {
@@ -105,7 +222,8 @@ const styles = (theme) => ({
105
222
  },
106
223
  label: {
107
224
  color: `${color.text()} !important`, //'var(--choice-input-color, black)',
108
- display: 'inline-block',
225
+ display: 'flex',
226
+ flexDirection: 'column',
109
227
  verticalAlign: 'middle',
110
228
  cursor: 'pointer',
111
229
  '& > p': {
@@ -119,11 +237,17 @@ const styles = (theme) => ({
119
237
  '&:not(.MathJax) > table tr': {
120
238
  '&:nth-child(2n)': {
121
239
  backgroundColor: '#f6f8fa',
240
+ color: theme.palette.common.black,
122
241
  },
123
242
  },
124
- '&:not(.MathJax) > table td, &:not(.MathJax) > table th': {
243
+ // align table content to left as per STAR requirement PD-3687
244
+ '&:not(.MathJax) table td, &:not(.MathJax) table th': {
125
245
  padding: '.6em 1em',
126
- textAlign: 'center',
246
+ textAlign: 'left',
247
+ },
248
+ // added this to fix alignment of text in prompt imported from studio (PD-3423)
249
+ '&:not(.MathJax) > table td > p.kds-indent': {
250
+ textAlign: 'initial',
127
251
  },
128
252
  },
129
253
  });
@@ -0,0 +1,66 @@
1
+ import React from 'react';
2
+ import { withStyles } from '@material-ui/core/styles';
3
+ import PropTypes from 'prop-types';
4
+ import classNames from 'classnames';
5
+ import AppendCSSRules from './append-css-rules';
6
+
7
+ class UiLayout extends AppendCSSRules {
8
+ static propTypes = {
9
+ classes: PropTypes.object,
10
+ className: PropTypes.string,
11
+ children: PropTypes.array,
12
+ extraCSSRules: PropTypes.shape({
13
+ names: PropTypes.arrayOf(PropTypes.string),
14
+ rules: PropTypes.string,
15
+ }),
16
+ fontSizeFactor: PropTypes.number,
17
+ };
18
+
19
+ static defaultProps = {
20
+ extraCSSRules: {},
21
+ fontSizeFactor: 1,
22
+ };
23
+
24
+ constructor(props) {
25
+ super(props);
26
+ this.classesSheet = document.createElement('style');
27
+ }
28
+
29
+ computeStyle(fontSizeFactor) {
30
+ const getFontSize = (element) => parseFloat(getComputedStyle(element).fontSize);
31
+
32
+ const rootFontSize = getFontSize(document.documentElement);
33
+ const bodyFontSize = getFontSize(document.body);
34
+ const effectiveFontSize = Math.max(rootFontSize, bodyFontSize);
35
+
36
+ return fontSizeFactor !== 1 ? { fontSize: `${effectiveFontSize * fontSizeFactor}px` } : null;
37
+ }
38
+
39
+ render() {
40
+ const { children, className, classes, fontSizeFactor, ...rest } = this.props;
41
+
42
+ const finalClass = classNames(className, classes.extraCSSRules, classes.uiLayoutContainer);
43
+ const { extraCSSRules, ...restProps } = rest;
44
+ const style = this.computeStyle(fontSizeFactor);
45
+
46
+ return (
47
+ <div className={finalClass} {...restProps} {...(style && { style })}>
48
+ {children}
49
+ </div>
50
+ );
51
+ }
52
+ }
53
+
54
+ const styles = {
55
+ extraCSSRules: {},
56
+ // need this because some browsers set their own style on table
57
+ uiLayoutContainer: {
58
+ '& table, th, td': {
59
+ fontSize: 'inherit' /* Ensure table elements inherit font size */,
60
+ },
61
+ },
62
+ };
63
+
64
+ const Styled = withStyles(styles)(UiLayout);
65
+
66
+ export default Styled;
package/README.md DELETED
@@ -1,33 +0,0 @@
1
- # @pie-lib/render-ui
2
-
3
- Some shared ui components for player rendering that are so small that they don't warrant their own package..
4
-
5
- ## install
6
-
7
- ```
8
- npm install
9
- ```
10
-
11
- ## demo
12
-
13
- ```
14
- cd demo
15
- ../node_modules/.bin/webpack-dev-server --hot --inline
16
- ```
17
-
18
- go to http://localhost:8080
19
-
20
- # colors
21
-
22
- This package contains a color module that defines the css custom properties that all pie elements should use. It loosely follows the material design naming scheme with a few additions.
23
-
24
- | name | description | fallback |
25
- | ---------------------- | --------------------------------------- | ------------------ |
26
- | `--pie-text` | the color of the text | defaults.TEXT |
27
- | `--pie-primary` | the primary fill color | defaults.PRIMARY |
28
- | `--pie-primary-text` | the color of primary text | `--pie-text` |
29
- | `--pie-secondary` | the secondary fill color | defaults.SECONDARY |
30
- | `--pie-secondary-text` | the color of secondary text | `--pie-text` |
31
- | `--pie-correct` | the fill color for correct ui widgets | defaults.CORRECT |
32
- | `--pie-incorrect` | the fill color for incorrect ui widgets | defaults.INCORRECT |
33
- | `--pie-disabled` | the disabled color | defaults.DISABLED |
@@ -1,134 +0,0 @@
1
- "use strict";
2
-
3
- var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
4
-
5
- Object.defineProperty(exports, "__esModule", {
6
- value: true
7
- });
8
- exports["default"] = exports.Collapsible = void 0;
9
-
10
- var _classCallCheck2 = _interopRequireDefault(require("@babel/runtime/helpers/classCallCheck"));
11
-
12
- var _createClass2 = _interopRequireDefault(require("@babel/runtime/helpers/createClass"));
13
-
14
- var _assertThisInitialized2 = _interopRequireDefault(require("@babel/runtime/helpers/assertThisInitialized"));
15
-
16
- var _inherits2 = _interopRequireDefault(require("@babel/runtime/helpers/inherits"));
17
-
18
- var _possibleConstructorReturn2 = _interopRequireDefault(require("@babel/runtime/helpers/possibleConstructorReturn"));
19
-
20
- var _getPrototypeOf2 = _interopRequireDefault(require("@babel/runtime/helpers/getPrototypeOf"));
21
-
22
- var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
23
-
24
- var _react = _interopRequireDefault(require("react"));
25
-
26
- var _index = require("@material-ui/core/styles/index");
27
-
28
- var _index2 = _interopRequireDefault(require("@material-ui/core/Collapse/index"));
29
-
30
- var _mathRendering = require("@pie-lib/math-rendering");
31
-
32
- var _propTypes = _interopRequireDefault(require("prop-types"));
33
-
34
- function _createSuper(Derived) { var hasNativeReflectConstruct = _isNativeReflectConstruct(); return function _createSuperInternal() { var Super = (0, _getPrototypeOf2["default"])(Derived), result; if (hasNativeReflectConstruct) { var NewTarget = (0, _getPrototypeOf2["default"])(this).constructor; result = Reflect.construct(Super, arguments, NewTarget); } else { result = Super.apply(this, arguments); } return (0, _possibleConstructorReturn2["default"])(this, result); }; }
35
-
36
- function _isNativeReflectConstruct() { if (typeof Reflect === "undefined" || !Reflect.construct) return false; if (Reflect.construct.sham) return false; if (typeof Proxy === "function") return true; try { Boolean.prototype.valueOf.call(Reflect.construct(Boolean, [], function () {})); return true; } catch (e) { return false; } }
37
-
38
- var Collapsible = /*#__PURE__*/function (_React$Component) {
39
- (0, _inherits2["default"])(Collapsible, _React$Component);
40
-
41
- var _super = _createSuper(Collapsible);
42
-
43
- function Collapsible() {
44
- var _this;
45
-
46
- (0, _classCallCheck2["default"])(this, Collapsible);
47
-
48
- for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
49
- args[_key] = arguments[_key];
50
- }
51
-
52
- _this = _super.call.apply(_super, [this].concat(args));
53
- (0, _defineProperty2["default"])((0, _assertThisInitialized2["default"])(_this), "state", {
54
- expanded: false
55
- });
56
- (0, _defineProperty2["default"])((0, _assertThisInitialized2["default"])(_this), "toggleExpanded", function () {
57
- _this.setState(function (state) {
58
- return {
59
- expanded: !state.expanded
60
- };
61
- });
62
- });
63
- return _this;
64
- }
65
-
66
- (0, _createClass2["default"])(Collapsible, [{
67
- key: "componentDidMount",
68
- value: function componentDidMount() {
69
- (0, _mathRendering.renderMath)(this.root);
70
- }
71
- }, {
72
- key: "componentDidUpdate",
73
- value: function componentDidUpdate() {
74
- (0, _mathRendering.renderMath)(this.root);
75
- }
76
- }, {
77
- key: "render",
78
- value: function render() {
79
- var _this2 = this;
80
-
81
- var _this$props = this.props,
82
- classes = _this$props.classes,
83
- labels = _this$props.labels,
84
- children = _this$props.children,
85
- className = _this$props.className;
86
- var title = this.state.expanded ? labels.visible || 'Hide' : labels.hidden || 'Show';
87
- return /*#__PURE__*/_react["default"].createElement("div", {
88
- className: className,
89
- ref: function ref(r) {
90
- return _this2.root = r;
91
- }
92
- }, /*#__PURE__*/_react["default"].createElement("div", {
93
- onClick: this.toggleExpanded
94
- }, /*#__PURE__*/_react["default"].createElement("span", {
95
- className: classes.title
96
- }, title)), /*#__PURE__*/_react["default"].createElement(_index2["default"], {
97
- "in": this.state.expanded,
98
- timeout: "auto",
99
- unmountOnExit: true,
100
- className: classes.collapsible
101
- }, children));
102
- }
103
- }]);
104
- return Collapsible;
105
- }(_react["default"].Component);
106
-
107
- exports.Collapsible = Collapsible;
108
- (0, _defineProperty2["default"])(Collapsible, "propTypes", {
109
- classes: _propTypes["default"].object.isRequired,
110
- className: _propTypes["default"].string,
111
- children: _propTypes["default"].object,
112
- labels: _propTypes["default"].shape({
113
- visible: _propTypes["default"].string,
114
- hidden: _propTypes["default"].string
115
- })
116
- });
117
- (0, _defineProperty2["default"])(Collapsible, "defaultProps", {
118
- labels: {}
119
- });
120
-
121
- var _default = (0, _index.withStyles)(function (theme) {
122
- return {
123
- title: {
124
- color: theme.palette.primary.light,
125
- borderBottom: "1px dotted ".concat(theme.palette.primary.light)
126
- },
127
- collapsible: {
128
- paddingTop: theme.spacing.unit * 2
129
- }
130
- };
131
- })(Collapsible);
132
-
133
- exports["default"] = _default;
134
- //# sourceMappingURL=index.js.map
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../../src/collapsible/index.jsx"],"names":["Collapsible","expanded","setState","state","root","props","classes","labels","children","className","title","visible","hidden","r","toggleExpanded","collapsible","React","Component","PropTypes","object","isRequired","string","shape","theme","color","palette","primary","light","borderBottom","paddingTop","spacing","unit"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;AAAA;;AACA;;AACA;;AACA;;AACA;;;;;;IAEaA,W;;;;;;;;;;;;;;;8FAeH;AACNC,MAAAA,QAAQ,EAAE;AADJ,K;uGAIS,YAAM;AACrB,YAAKC,QAAL,CAAc,UAACC,KAAD;AAAA,eAAY;AAAEF,UAAAA,QAAQ,EAAE,CAACE,KAAK,CAACF;AAAnB,SAAZ;AAAA,OAAd;AACD,K;;;;;;WAED,6BAAoB;AAClB,qCAAW,KAAKG,IAAhB;AACD;;;WAED,8BAAqB;AACnB,qCAAW,KAAKA,IAAhB;AACD;;;WAED,kBAAS;AAAA;;AACP,wBAAiD,KAAKC,KAAtD;AAAA,UAAQC,OAAR,eAAQA,OAAR;AAAA,UAAiBC,MAAjB,eAAiBA,MAAjB;AAAA,UAAyBC,QAAzB,eAAyBA,QAAzB;AAAA,UAAmCC,SAAnC,eAAmCA,SAAnC;AACA,UAAMC,KAAK,GAAG,KAAKP,KAAL,CAAWF,QAAX,GAAsBM,MAAM,CAACI,OAAP,IAAkB,MAAxC,GAAiDJ,MAAM,CAACK,MAAP,IAAiB,MAAhF;AAEA,0BACE;AAAK,QAAA,SAAS,EAAEH,SAAhB;AAA2B,QAAA,GAAG,EAAE,aAACI,CAAD;AAAA,iBAAQ,MAAI,CAACT,IAAL,GAAYS,CAApB;AAAA;AAAhC,sBACE;AAAK,QAAA,OAAO,EAAE,KAAKC;AAAnB,sBACE;AAAM,QAAA,SAAS,EAAER,OAAO,CAACI;AAAzB,SAAiCA,KAAjC,CADF,CADF,eAIE,gCAAC,kBAAD;AAAU,cAAI,KAAKP,KAAL,CAAWF,QAAzB;AAAmC,QAAA,OAAO,EAAC,MAA3C;AAAkD,QAAA,aAAa,MAA/D;AAAgE,QAAA,SAAS,EAAEK,OAAO,CAACS;AAAnF,SACGP,QADH,CAJF,CADF;AAUD;;;EA7C8BQ,kBAAMC,S;;;iCAA1BjB,W,eACQ;AACjBM,EAAAA,OAAO,EAAEY,sBAAUC,MAAV,CAAiBC,UADT;AAEjBX,EAAAA,SAAS,EAAES,sBAAUG,MAFJ;AAGjBb,EAAAA,QAAQ,EAAEU,sBAAUC,MAHH;AAIjBZ,EAAAA,MAAM,EAAEW,sBAAUI,KAAV,CAAgB;AACtBX,IAAAA,OAAO,EAAEO,sBAAUG,MADG;AAEtBT,IAAAA,MAAM,EAAEM,sBAAUG;AAFI,GAAhB;AAJS,C;iCADRrB,W,kBAWW;AACpBO,EAAAA,MAAM,EAAE;AADY,C;;eAqCT,uBAAW,UAACgB,KAAD;AAAA,SAAY;AACpCb,IAAAA,KAAK,EAAE;AACLc,MAAAA,KAAK,EAAED,KAAK,CAACE,OAAN,CAAcC,OAAd,CAAsBC,KADxB;AAELC,MAAAA,YAAY,uBAAgBL,KAAK,CAACE,OAAN,CAAcC,OAAd,CAAsBC,KAAtC;AAFP,KAD6B;AAKpCZ,IAAAA,WAAW,EAAE;AACXc,MAAAA,UAAU,EAAEN,KAAK,CAACO,OAAN,CAAcC,IAAd,GAAqB;AADtB;AALuB,GAAZ;AAAA,CAAX,EAQX/B,WARW,C","sourcesContent":["import React from 'react';\nimport { withStyles } from '@material-ui/core/styles/index';\nimport Collapse from '@material-ui/core/Collapse/index';\nimport { renderMath } from '@pie-lib/math-rendering';\nimport PropTypes from 'prop-types';\n\nexport class Collapsible extends React.Component {\n static propTypes = {\n classes: PropTypes.object.isRequired,\n className: PropTypes.string,\n children: PropTypes.object,\n labels: PropTypes.shape({\n visible: PropTypes.string,\n hidden: PropTypes.string,\n }),\n };\n\n static defaultProps = {\n labels: {},\n };\n\n state = {\n expanded: false,\n };\n\n toggleExpanded = () => {\n this.setState((state) => ({ expanded: !state.expanded }));\n };\n\n componentDidMount() {\n renderMath(this.root);\n }\n\n componentDidUpdate() {\n renderMath(this.root);\n }\n\n render() {\n const { classes, labels, children, className } = this.props;\n const title = this.state.expanded ? labels.visible || 'Hide' : labels.hidden || 'Show';\n\n return (\n <div className={className} ref={(r) => (this.root = r)}>\n <div onClick={this.toggleExpanded}>\n <span className={classes.title}>{title}</span>\n </div>\n <Collapse in={this.state.expanded} timeout=\"auto\" unmountOnExit className={classes.collapsible}>\n {children}\n </Collapse>\n </div>\n );\n }\n}\n\nexport default withStyles((theme) => ({\n title: {\n color: theme.palette.primary.light,\n borderBottom: `1px dotted ${theme.palette.primary.light}`,\n },\n collapsible: {\n paddingTop: theme.spacing.unit * 2,\n },\n}))(Collapsible);\n"],"file":"index.js"}