@pie-lib/mask-markup 3.1.4 → 4.0.0-next.37

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 (113) hide show
  1. package/dist/_virtual/_rolldown/runtime.js +4 -0
  2. package/dist/choices/choice.d.ts +28 -0
  3. package/dist/choices/choice.js +92 -0
  4. package/dist/choices/index.d.ts +29 -0
  5. package/dist/choices/index.js +59 -0
  6. package/dist/componentize.d.ts +12 -0
  7. package/dist/componentize.js +4 -0
  8. package/dist/components/blank.d.ts +45 -0
  9. package/dist/components/blank.js +273 -0
  10. package/dist/components/correct-input.d.ts +11 -0
  11. package/dist/components/dropdown.d.ts +37 -0
  12. package/dist/components/dropdown.js +311 -0
  13. package/dist/components/input.d.ts +37 -0
  14. package/dist/constructed-response.d.ts +44 -0
  15. package/dist/constructed-response.js +56 -0
  16. package/dist/customizable.d.ts +43 -0
  17. package/dist/customizable.js +8 -0
  18. package/dist/drag-in-the-blank.d.ts +47 -0
  19. package/dist/drag-in-the-blank.js +220 -0
  20. package/dist/index.d.ts +15 -0
  21. package/dist/index.js +7 -0
  22. package/dist/inline-dropdown.d.ts +44 -0
  23. package/dist/inline-dropdown.js +24 -0
  24. package/dist/keyboard-coordinates.d.ts +25 -0
  25. package/dist/keyboard-coordinates.js +49 -0
  26. package/dist/mask.d.ts +30 -0
  27. package/dist/mask.js +95 -0
  28. package/dist/node_modules/.bun/clsx@2.1.1/node_modules/clsx/dist/clsx.js +16 -0
  29. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/index.js +17 -0
  30. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/cssPrefix.js +9 -0
  31. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/cssUnitless.js +26 -0
  32. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/hasOwn.js +11 -0
  33. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/isFunction.js +11 -0
  34. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/isObject.js +11 -0
  35. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/prefixInfo.js +24 -0
  36. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/prefixProperties.js +32 -0
  37. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/prefixer.js +29 -0
  38. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/stringUtils/camelize.js +14 -0
  39. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/stringUtils/hyphenRe.js +8 -0
  40. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/stringUtils/hyphenate.js +12 -0
  41. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/stringUtils/separate.js +11 -0
  42. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/stringUtils/toLowerFirst.js +10 -0
  43. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/stringUtils/toUpperFirst.js +10 -0
  44. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/toStyleObject.js +55 -0
  45. package/dist/node_modules/.bun/to-style@1.3.3/node_modules/to-style/src/toStyleString.js +16 -0
  46. package/dist/serialization.d.ts +34 -0
  47. package/dist/serialization.js +132 -0
  48. package/dist/with-mask.d.ts +55 -0
  49. package/dist/with-mask.js +45 -0
  50. package/package.json +35 -19
  51. package/CHANGELOG.json +0 -17
  52. package/CHANGELOG.md +0 -1357
  53. package/LICENSE.md +0 -5
  54. package/lib/choices/choice.js +0 -138
  55. package/lib/choices/choice.js.map +0 -1
  56. package/lib/choices/index.js +0 -126
  57. package/lib/choices/index.js.map +0 -1
  58. package/lib/componentize.js +0 -21
  59. package/lib/componentize.js.map +0 -1
  60. package/lib/components/blank.js +0 -489
  61. package/lib/components/blank.js.map +0 -1
  62. package/lib/components/correct-input.js +0 -94
  63. package/lib/components/correct-input.js.map +0 -1
  64. package/lib/components/dropdown.js +0 -480
  65. package/lib/components/dropdown.js.map +0 -1
  66. package/lib/components/input.js +0 -50
  67. package/lib/components/input.js.map +0 -1
  68. package/lib/constructed-response.js +0 -101
  69. package/lib/constructed-response.js.map +0 -1
  70. package/lib/customizable.js +0 -42
  71. package/lib/customizable.js.map +0 -1
  72. package/lib/drag-in-the-blank.js +0 -363
  73. package/lib/drag-in-the-blank.js.map +0 -1
  74. package/lib/index.js +0 -55
  75. package/lib/index.js.map +0 -1
  76. package/lib/inline-dropdown.js +0 -40
  77. package/lib/inline-dropdown.js.map +0 -1
  78. package/lib/keyboard-coordinates.js +0 -156
  79. package/lib/keyboard-coordinates.js.map +0 -1
  80. package/lib/mask.js +0 -203
  81. package/lib/mask.js.map +0 -1
  82. package/lib/serialization.js +0 -261
  83. package/lib/serialization.js.map +0 -1
  84. package/lib/with-mask.js +0 -97
  85. package/lib/with-mask.js.map +0 -1
  86. package/src/__tests__/drag-in-the-blank.test.js +0 -256
  87. package/src/__tests__/index.test.js +0 -38
  88. package/src/__tests__/keyboard-coordinates.test.js +0 -202
  89. package/src/__tests__/mask.test.js +0 -479
  90. package/src/__tests__/serialization.test.js +0 -54
  91. package/src/__tests__/utils.js +0 -1
  92. package/src/__tests__/with-mask.test.js +0 -76
  93. package/src/choices/__tests__/index.test.js +0 -212
  94. package/src/choices/choice.jsx +0 -113
  95. package/src/choices/index.jsx +0 -88
  96. package/src/componentize.js +0 -13
  97. package/src/components/__tests__/blank.test.js +0 -413
  98. package/src/components/__tests__/correct-input.test.js +0 -90
  99. package/src/components/__tests__/dropdown.test.js +0 -129
  100. package/src/components/__tests__/input.test.js +0 -102
  101. package/src/components/blank.jsx +0 -504
  102. package/src/components/correct-input.jsx +0 -82
  103. package/src/components/dropdown.jsx +0 -421
  104. package/src/components/input.jsx +0 -48
  105. package/src/constructed-response.jsx +0 -87
  106. package/src/customizable.jsx +0 -34
  107. package/src/drag-in-the-blank.jsx +0 -351
  108. package/src/index.js +0 -16
  109. package/src/inline-dropdown.jsx +0 -29
  110. package/src/keyboard-coordinates.js +0 -147
  111. package/src/mask.jsx +0 -174
  112. package/src/serialization.js +0 -260
  113. package/src/with-mask.jsx +0 -75
package/src/mask.jsx DELETED
@@ -1,174 +0,0 @@
1
- import React from 'react';
2
- import PropTypes from 'prop-types';
3
- import { get } from 'lodash-es';
4
- import { styled } from '@mui/material/styles';
5
- import { renderMath } from '@pie-lib/math-rendering';
6
- import { MARK_TAGS } from './serialization';
7
-
8
- const Paragraph = styled('div')(({ theme }) => ({
9
- paddingTop: theme.spacing(0.5),
10
- paddingBottom: theme.spacing(0.5),
11
- }));
12
-
13
- const Spacer = styled('span')(() => ({
14
- display: 'inline-block',
15
- width: '.75em',
16
- }));
17
-
18
- const restrictWhitespaceTypes = ['tbody', 'tr'];
19
-
20
- const addText = (parentNode, text) => {
21
- const isWhitespace = text.trim() === '';
22
- const parentType = parentNode && parentNode.type;
23
-
24
- if (isWhitespace && restrictWhitespaceTypes.includes(parentType)) {
25
- return undefined;
26
- } else {
27
- return text;
28
- }
29
- };
30
-
31
- const getMark = (n) => {
32
- const mark = n.leaves.find((leave) => get(leave, 'marks', []).length);
33
-
34
- if (mark) {
35
- return mark.marks;
36
- }
37
-
38
- return null;
39
- };
40
-
41
- export const renderChildren = (layout, value, onChange, rootRenderChildren, parentNode, elementType) => {
42
- if (!value) {
43
- return null;
44
- }
45
-
46
- const children = [];
47
-
48
- (layout.nodes || []).forEach((n, index) => {
49
- const key = n.type ? `${n.type}-${index}` : `${index}`;
50
-
51
- if (n.isMath) {
52
- children.push(
53
- <span
54
- dangerouslySetInnerHTML={{
55
- __html: `<math displaystyle="true">${n.nodes[0].innerHTML}</math>`,
56
- }}
57
- />,
58
- );
59
- return children;
60
- }
61
-
62
- if (rootRenderChildren) {
63
- const c = rootRenderChildren(n, value, onChange);
64
- if (c) {
65
- const isDndComponent = n.data?.dataset?.component === 'blank';
66
-
67
- if (isDndComponent) {
68
- children.push(<Spacer key={`spacer-${index}`} />);
69
- }
70
-
71
- children.push(c);
72
-
73
- if (isDndComponent) {
74
- children.push(<Spacer key={`spacer-${index}`} />);
75
- }
76
- return;
77
- }
78
- }
79
-
80
- if (n.object === 'text') {
81
- const content = n.leaves.reduce((acc, l) => {
82
- const t = l.text;
83
- const extraText = addText(parentNode, t);
84
- return extraText ? acc + extraText : acc;
85
- }, '');
86
- const marks = getMark(n);
87
-
88
- if (marks?.length > 0) {
89
- const tagsToWrap = marks
90
- .map((mark) => Object.keys(MARK_TAGS).find((markKey) => MARK_TAGS[markKey] === mark.type))
91
- .filter(Boolean);
92
-
93
- if (tagsToWrap.length > 0) {
94
- // nest from the inside out so the first mark ends up as the outermost tag: <b><em>content</em></b>
95
- children.push(
96
- tagsToWrap.reduceRight((acc, Tag, tagIndex) => <Tag key={`${key}-${Tag}-${tagIndex}`}>{acc}</Tag>, content),
97
- );
98
- } else {
99
- children.push(content);
100
- }
101
- } else if (content.length > 0) {
102
- children.push(content);
103
- }
104
- } else {
105
- const subNodes = renderChildren(n, value, onChange, rootRenderChildren, n, elementType);
106
- if (n.type === 'p' || n.type === 'paragraph') {
107
- children.push(<Paragraph key={key}>{subNodes}</Paragraph>);
108
- } else {
109
- const Tag = n.type;
110
- if (n.nodes && n.nodes.length > 0) {
111
- children.push(
112
- <Tag key={key} {...n.data.attributes}>
113
- {subNodes}
114
- </Tag>,
115
- );
116
- } else {
117
- children.push(<Tag key={key} {...n.data.attributes} />);
118
- }
119
- }
120
- }
121
- });
122
- return children;
123
- };
124
-
125
- const MaskContainer = styled('div')(() => ({
126
- display: 'initial',
127
- '&:not(.MathJax) table': {
128
- borderCollapse: 'collapse',
129
- },
130
- // align table content to left as per STAR requirement PD-3687
131
- '&:not(.MathJax) table td, &:not(.MathJax) table th': {
132
- padding: '8px 12px',
133
- textAlign: 'left',
134
- },
135
- }));
136
-
137
- /**
138
- * Renders a layout that uses the slate.js Value model structure.
139
- */
140
- export default class Mask extends React.Component {
141
- constructor(props) {
142
- super(props);
143
- this.internalContainerRef = React.createRef();
144
- }
145
-
146
- static propTypes = {
147
- renderChildren: PropTypes.func,
148
- layout: PropTypes.object,
149
- value: PropTypes.object,
150
- onChange: PropTypes.func,
151
- elementType: PropTypes.string,
152
- containerRef: PropTypes.oneOfType([PropTypes.func, PropTypes.shape({ current: PropTypes.instanceOf(Element) })]),
153
- };
154
-
155
- componentDidMount() {
156
- const containerRef = this.props.containerRef || this.internalContainerRef;
157
- if (containerRef.current && typeof renderMath === 'function') {
158
- renderMath(containerRef.current);
159
- }
160
- }
161
-
162
- handleChange = (id, value) => {
163
- const data = { ...this.props.value, [id]: value };
164
- this.props.onChange(data);
165
- };
166
-
167
- render() {
168
- const { value, layout, elementType, containerRef } = this.props;
169
- const children = renderChildren(layout, value, this.handleChange, this.props.renderChildren, null, elementType);
170
- const ref = containerRef || this.internalContainerRef;
171
-
172
- return <MaskContainer ref={ref}>{children}</MaskContainer>;
173
- }
174
- }
@@ -1,260 +0,0 @@
1
- import { object as toStyleObject } from 'to-style';
2
- import debug from 'debug';
3
-
4
- const log = debug('@pie-lib:mask-markup:serialization');
5
-
6
- const INLINE = ['span'];
7
- const MARK = ['em', 'strong', 'u'];
8
- const TEXT_NODE = 3;
9
- const COMMENT_NODE = 8;
10
- const ELEMENT_NODE = 1;
11
-
12
- const attr = (el) => {
13
- if (!el.attributes || el.attributes.length <= 0) {
14
- return undefined;
15
- }
16
-
17
- const out = {};
18
- let i;
19
-
20
- for (i = 0; i < el.attributes.length; i++) {
21
- const a = el.attributes[i];
22
-
23
- out[a.name] = a.value;
24
- }
25
-
26
- return out;
27
- };
28
-
29
- const getObject = (type) => {
30
- if (INLINE.includes(type)) {
31
- return 'inline';
32
- } else if (MARK.includes(type)) {
33
- return 'mark';
34
- }
35
- return 'block';
36
- };
37
-
38
- export const parseStyleString = (s) => {
39
- const regex = /([\w-]*)\s*:\s*([^;]*)/g;
40
- let match;
41
- const result = {};
42
- while ((match = regex.exec(s))) {
43
- result[match[1]] = match[2].trim();
44
- }
45
- return result;
46
- };
47
-
48
- export const reactAttributes = (o) => toStyleObject(o, { camelize: true, addUnits: false });
49
-
50
- const handleStyles = (el, attribute) => {
51
- const styleString = el.getAttribute(attribute);
52
-
53
- return reactAttributes(parseStyleString(styleString));
54
- };
55
-
56
- const handleClass = (el, acc, attribute) => {
57
- const classNames = el.getAttribute(attribute);
58
-
59
- delete acc.class;
60
-
61
- return classNames;
62
- };
63
-
64
- const attributesToMap = (el) => (acc, attribute) => {
65
- if (!el.getAttribute) {
66
- return acc;
67
- }
68
-
69
- const value = el.getAttribute(attribute);
70
-
71
- if (value) {
72
- switch (attribute) {
73
- case 'style':
74
- acc.style = handleStyles(el, attribute);
75
- break;
76
- case 'class':
77
- acc.className = handleClass(el, acc, attribute);
78
- break;
79
- default:
80
- acc[attribute] = el.getAttribute(attribute);
81
- break;
82
- }
83
- }
84
-
85
- return acc;
86
- };
87
-
88
- const attributes = ['border', 'class', 'style'];
89
-
90
- /**
91
- * Tags to marks.
92
- *
93
- * @type {Object}
94
- */
95
-
96
- export const MARK_TAGS = {
97
- b: 'bold',
98
- em: 'italic',
99
- u: 'underline',
100
- s: 'strikethrough',
101
- code: 'code',
102
- strong: 'strong',
103
- };
104
-
105
- /**
106
- * Recursively process DOM nodes and convert them to Slate JSON format
107
- */
108
- const processNode = (node, marks = []) => {
109
- // Skip comment nodes
110
- if (node.nodeType === COMMENT_NODE) {
111
- return null;
112
- }
113
-
114
- // Handle text nodes
115
- if (node.nodeType === TEXT_NODE) {
116
- const text = node.textContent;
117
- const leaf = { text };
118
-
119
- if (marks.length > 0) {
120
- leaf.marks = marks.map((m) => ({ type: m, data: undefined }));
121
- }
122
-
123
- return {
124
- object: 'text',
125
- leaves: [leaf],
126
- };
127
- }
128
-
129
- // Handle element nodes
130
- if (node.nodeType === ELEMENT_NODE) {
131
- const type = node.tagName.toLowerCase();
132
-
133
- // Check if this is a mark tag
134
- const markType = MARK_TAGS[type];
135
- if (markType) {
136
- log('[deserialize] mark: ', markType);
137
- // Process children with this mark added and return them flattened
138
- const childNodes = processNodes(node.childNodes, [...marks, markType]);
139
- // Return an array indicator with the nodes (will be flattened by parent)
140
- return { _flatten: true, nodes: childNodes };
141
- }
142
-
143
- // Handle math elements specially
144
- if (type === 'math') {
145
- return {
146
- isMath: true,
147
- nodes: [node],
148
- };
149
- }
150
-
151
- // Process regular elements
152
- const normalAttrs = attr(node) || {};
153
-
154
- if (type === 'audio' && normalAttrs.controls === '') {
155
- normalAttrs.controls = true;
156
- }
157
-
158
- const allAttrs = attributes.reduce(attributesToMap(node), { ...normalAttrs });
159
- const object = getObject(type);
160
-
161
- const childNodes = processNodes(node.childNodes, marks);
162
-
163
- return {
164
- object,
165
- type,
166
- data: { dataset: { ...node.dataset }, attributes: { ...allAttrs } },
167
- nodes: childNodes,
168
- };
169
- }
170
-
171
- return null;
172
- };
173
-
174
- /**
175
- * Process a NodeList and convert to array of Slate nodes
176
- */
177
- const processNodes = (nodeList, marks = []) => {
178
- const nodes = [];
179
- for (let i = 0; i < nodeList.length; i++) {
180
- const result = processNode(nodeList[i], marks);
181
- if (result !== null) {
182
- // Handle flattening for mark nodes
183
- if (result._flatten && result.nodes) {
184
- nodes.push(...result.nodes);
185
- } else {
186
- nodes.push(result);
187
- }
188
- }
189
- }
190
- return nodes;
191
- };
192
-
193
- /**
194
- * Deserialize HTML string to Slate JSON format
195
- */
196
- export const deserialize = (htmlString) => {
197
- // Handle empty or whitespace-only strings
198
- if (!htmlString || !htmlString.trim()) {
199
- return {
200
- object: 'value',
201
- document: {
202
- object: 'document',
203
- data: {},
204
- nodes: [
205
- {
206
- object: 'block',
207
- type: 'span',
208
- data: {},
209
- isVoid: false,
210
- nodes: [],
211
- },
212
- ],
213
- },
214
- };
215
- }
216
-
217
- // Use DOMParser to parse the HTML
218
- const parser = new DOMParser();
219
- const doc = parser.parseFromString(htmlString, 'text/html');
220
-
221
- // Process all nodes in the body
222
- let nodes = processNodes(doc.body.childNodes);
223
-
224
- // If we only have text nodes (no block elements), wrap in default span block
225
- const hasBlockElements = nodes.some((node) => node.object === 'block' || node.object === 'inline');
226
-
227
- if (!hasBlockElements && nodes.length > 0) {
228
- nodes = [
229
- {
230
- object: 'block',
231
- type: 'span',
232
- data: {},
233
- isVoid: false,
234
- nodes: nodes,
235
- },
236
- ];
237
- }
238
-
239
- // If no nodes were produced, add a default span block
240
- if (nodes.length === 0) {
241
- nodes = [
242
- {
243
- object: 'block',
244
- type: 'span',
245
- data: {},
246
- isVoid: false,
247
- nodes: [],
248
- },
249
- ];
250
- }
251
-
252
- return {
253
- object: 'value',
254
- document: {
255
- object: 'document',
256
- data: {},
257
- nodes,
258
- },
259
- };
260
- };
package/src/with-mask.jsx DELETED
@@ -1,75 +0,0 @@
1
- import React from 'react';
2
- import PropTypes from 'prop-types';
3
- import Mask from './mask';
4
- import componentize from './componentize';
5
- import { deserialize } from './serialization';
6
-
7
- export const buildLayoutFromMarkup = (markup, type) => {
8
- const { markup: processed } = componentize(markup, type);
9
- const value = deserialize(processed);
10
- return value.document;
11
- };
12
-
13
- export const withMask = (type, renderChildren) => {
14
- return class WithMask extends React.Component {
15
- static propTypes = {
16
- /**
17
- * At the start we'll probably work with markup
18
- */
19
- markup: PropTypes.string,
20
- /**
21
- * Once we start authoring, it may make sense for use to us layout, which will be a simple js object that maps to `slate.Value`.
22
- */
23
- layout: PropTypes.object,
24
- value: PropTypes.object,
25
- onChange: PropTypes.func,
26
- customMarkMarkupComponent: PropTypes.func,
27
- elementType: PropTypes.string,
28
- };
29
-
30
- constructor(props) {
31
- super(props);
32
- this.containerRef = React.createRef();
33
- }
34
-
35
- componentDidUpdate(prevProps) {
36
- if (this.props.markup !== prevProps.markup) {
37
- const domNode = this.containerRef.current;
38
- const mathElements = domNode && domNode.querySelectorAll('[data-latex][data-math-handled="true"]');
39
-
40
- // Clean up for fresh MathJax processing
41
- (mathElements || []).forEach((el) => {
42
- // Remove the MathJax container to allow for clean updates
43
- const mjxContainer = el.querySelector('mjx-container');
44
-
45
- if (mjxContainer) {
46
- el.removeChild(mjxContainer);
47
- }
48
-
49
- // Update the innerHTML to match the raw LaTeX data, ensuring it is reprocessed correctly
50
- const latexCode = el.getAttribute('data-raw');
51
- el.innerHTML = latexCode;
52
-
53
- // Remove the attribute to signal that MathJax should reprocess this element
54
- el.removeAttribute('data-math-handled');
55
- });
56
- }
57
- }
58
-
59
- render() {
60
- const { markup, layout, value, onChange, elementType } = this.props;
61
-
62
- const maskLayout = layout ? layout : buildLayoutFromMarkup(markup, type);
63
- return (
64
- <Mask
65
- containerRef={this.containerRef}
66
- elementType={elementType}
67
- layout={maskLayout}
68
- value={value}
69
- onChange={onChange}
70
- renderChildren={renderChildren(this.props)}
71
- />
72
- );
73
- }
74
- };
75
- };