@khanacademy/perseus-editor 5.0.3 → 5.1.1
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.
- package/dist/components/locked-figure-select.d.ts +7 -0
- package/dist/components/locked-figure-settings.d.ts +11 -0
- package/dist/components/locked-figures-section.d.ts +9 -0
- package/dist/components/locked-point-settings.d.ts +8 -0
- package/dist/components/util.d.ts +3 -0
- package/dist/es/index.js +419 -137
- package/dist/es/index.js.map +1 -1
- package/dist/index.js +417 -132
- package/dist/index.js.map +1 -1
- package/dist/widgets/interactive-graph-editor.d.ts +466 -660
- package/package.json +4 -2
package/dist/es/index.js
CHANGED
|
@@ -9,7 +9,7 @@ import Clickable from '@khanacademy/wonder-blocks-clickable';
|
|
|
9
9
|
import Color from '@khanacademy/wonder-blocks-color';
|
|
10
10
|
import { StyleSheet, css } from 'aphrodite';
|
|
11
11
|
import $ from 'jquery';
|
|
12
|
-
import { View } from '@khanacademy/wonder-blocks-core';
|
|
12
|
+
import { View, useUniqueIdWithMock } from '@khanacademy/wonder-blocks-core';
|
|
13
13
|
import { PhosphorIcon } from '@khanacademy/wonder-blocks-icon';
|
|
14
14
|
import caretRight from '@phosphor-icons/core/bold/caret-right-bold.svg';
|
|
15
15
|
import classNames from 'classnames';
|
|
@@ -18,17 +18,19 @@ import { point, number } from '@khanacademy/kmath';
|
|
|
18
18
|
import * as KAS from '@khanacademy/kas';
|
|
19
19
|
import { isTruthy } from '@khanacademy/wonder-stuff-core';
|
|
20
20
|
import { createMathField } from '@khanacademy/math-input';
|
|
21
|
-
import { SingleSelect, OptionItem } from '@khanacademy/wonder-blocks-dropdown';
|
|
22
|
-
import { Checkbox as Checkbox$1 } from '@khanacademy/wonder-blocks-form';
|
|
21
|
+
import { SingleSelect, OptionItem, ActionMenu, ActionItem } from '@khanacademy/wonder-blocks-dropdown';
|
|
22
|
+
import { TextField, Checkbox as Checkbox$1 } from '@khanacademy/wonder-blocks-form';
|
|
23
23
|
import Spacing from '@khanacademy/wonder-blocks-spacing';
|
|
24
|
-
import { LabelSmall, BodyMonospace } from '@khanacademy/wonder-blocks-typography';
|
|
24
|
+
import { LabelSmall, LabelLarge, LabelMedium, BodyMonospace } from '@khanacademy/wonder-blocks-typography';
|
|
25
25
|
import { spacing, color } from '@khanacademy/wonder-blocks-tokens';
|
|
26
|
+
import IconButton from '@khanacademy/wonder-blocks-icon-button';
|
|
27
|
+
import trashIcon from '@phosphor-icons/core/bold/trash-bold.svg';
|
|
26
28
|
import Button from '@khanacademy/wonder-blocks-button';
|
|
27
29
|
import * as i18n$1 from '@khanacademy/wonder-blocks-i18n';
|
|
28
30
|
|
|
29
31
|
// This file is processed by a Rollup plugin (replace) to inject the production
|
|
30
32
|
const libName = "@khanacademy/perseus-editor";
|
|
31
|
-
const libVersion = "5.
|
|
33
|
+
const libVersion = "5.1.1";
|
|
32
34
|
addLibraryVersionToPerseusDebug(libName, libVersion);
|
|
33
35
|
|
|
34
36
|
function _extends() {
|
|
@@ -224,7 +226,7 @@ class SectionControlButton extends React.Component {
|
|
|
224
226
|
role: "button",
|
|
225
227
|
hideDefaultFocusRing: true,
|
|
226
228
|
"aria-label": title,
|
|
227
|
-
style: styles$
|
|
229
|
+
style: styles$q.button
|
|
228
230
|
}, ({
|
|
229
231
|
hovered,
|
|
230
232
|
focused,
|
|
@@ -232,7 +234,7 @@ class SectionControlButton extends React.Component {
|
|
|
232
234
|
}) => /*#__PURE__*/React.createElement(InlineIcon$b, icon));
|
|
233
235
|
}
|
|
234
236
|
}
|
|
235
|
-
const styles$
|
|
237
|
+
const styles$q = StyleSheet.create({
|
|
236
238
|
button: {
|
|
237
239
|
backgroundColor: Color.gold,
|
|
238
240
|
margin: 2,
|
|
@@ -20754,19 +20756,19 @@ class TexErrorView extends React.Component {
|
|
|
20754
20756
|
const {
|
|
20755
20757
|
showErrors
|
|
20756
20758
|
} = this.state;
|
|
20757
|
-
const iconStyle = showErrors ? styles$
|
|
20759
|
+
const iconStyle = showErrors ? styles$p.iconExpanded : styles$p.iconCollapsed;
|
|
20758
20760
|
return /*#__PURE__*/React.createElement(View, {
|
|
20759
|
-
style: styles$
|
|
20761
|
+
style: styles$p.errorContainer
|
|
20760
20762
|
}, /*#__PURE__*/React.createElement(View, {
|
|
20761
|
-
style: styles$
|
|
20763
|
+
style: styles$p.title,
|
|
20762
20764
|
onClick: this.handleToggleTexErrors
|
|
20763
20765
|
}, /*#__PURE__*/React.createElement(PhosphorIcon, {
|
|
20764
20766
|
icon: caretRight,
|
|
20765
20767
|
style: iconStyle
|
|
20766
20768
|
}), "\xA0 TeX Errors (", errorList.length, ")"), showErrors && /*#__PURE__*/React.createElement(View, {
|
|
20767
|
-
style: styles$
|
|
20769
|
+
style: styles$p.errorExplanation
|
|
20768
20770
|
}, "If your math doesn't display correctly, these errors might help you troubleshoot. Message #content-kitchen for help."), showErrors && errorList.map((e, index) => /*#__PURE__*/React.createElement(View, {
|
|
20769
|
-
style: styles$
|
|
20771
|
+
style: styles$p.error,
|
|
20770
20772
|
key: index
|
|
20771
20773
|
}, /*#__PURE__*/React.createElement(View, {
|
|
20772
20774
|
style: {
|
|
@@ -20775,7 +20777,7 @@ class TexErrorView extends React.Component {
|
|
|
20775
20777
|
}, e.math), /*#__PURE__*/React.createElement(View, null, e.message))));
|
|
20776
20778
|
}
|
|
20777
20779
|
}
|
|
20778
|
-
const styles$
|
|
20780
|
+
const styles$p = StyleSheet.create({
|
|
20779
20781
|
title: {
|
|
20780
20782
|
backgroundColor: "#eee",
|
|
20781
20783
|
fontSize: "1.25em",
|
|
@@ -24606,7 +24608,7 @@ class SimpleButton extends React.Component {
|
|
|
24606
24608
|
} = _this$props,
|
|
24607
24609
|
otherProps = _objectWithoutPropertiesLoose(_this$props, _excluded$3);
|
|
24608
24610
|
return /*#__PURE__*/React.createElement("div", _extends({
|
|
24609
|
-
className: css(styles$
|
|
24611
|
+
className: css(styles$o.baseButton, color === "green" && styles$o.green, color === "orange" && styles$o.orange),
|
|
24610
24612
|
onClick: onClick
|
|
24611
24613
|
}, otherProps), children);
|
|
24612
24614
|
}
|
|
@@ -24621,7 +24623,7 @@ SimpleButton.defaultProps = {
|
|
|
24621
24623
|
color: "green",
|
|
24622
24624
|
onClick: () => {}
|
|
24623
24625
|
};
|
|
24624
|
-
const styles$
|
|
24626
|
+
const styles$o = StyleSheet.create({
|
|
24625
24627
|
baseButton: {
|
|
24626
24628
|
top: "0",
|
|
24627
24629
|
fontSize: "11px",
|
|
@@ -24841,23 +24843,23 @@ const LeafContainer = ({
|
|
|
24841
24843
|
}) => {
|
|
24842
24844
|
const hasPreviewHeading = shape.type === "content" || shape.type === "hint";
|
|
24843
24845
|
const previewHeading = hasPreviewHeading && /*#__PURE__*/React.createElement("div", {
|
|
24844
|
-
className: css(styles$
|
|
24846
|
+
className: css(styles$n.containerHeader)
|
|
24845
24847
|
}, /*#__PURE__*/React.createElement(Header, {
|
|
24846
24848
|
depth: path.length,
|
|
24847
|
-
className: css(styles$
|
|
24849
|
+
className: css(styles$n.containerTitle)
|
|
24848
24850
|
}, capitalize(name)));
|
|
24849
24851
|
return /*#__PURE__*/React.createElement("div", {
|
|
24850
|
-
className: css(styles$
|
|
24852
|
+
className: css(styles$n.container)
|
|
24851
24853
|
}, /*#__PURE__*/React.createElement("span", {
|
|
24852
|
-
className: css(styles$
|
|
24854
|
+
className: css(styles$n.row, styles$n.rowHeading)
|
|
24853
24855
|
}, /*#__PURE__*/React.createElement("div", {
|
|
24854
|
-
className: css(styles$
|
|
24856
|
+
className: css(styles$n.columnLeft)
|
|
24855
24857
|
}, /*#__PURE__*/React.createElement("div", {
|
|
24856
|
-
className: "pod-title " + css(styles$
|
|
24858
|
+
className: "pod-title " + css(styles$n.containerHeader)
|
|
24857
24859
|
}, /*#__PURE__*/React.createElement("div", {
|
|
24858
|
-
className: css(styles$
|
|
24860
|
+
className: css(styles$n.containerTitle)
|
|
24859
24861
|
}, capitalize(name)), controls)), /*#__PURE__*/React.createElement("div", {
|
|
24860
|
-
className: css(styles$
|
|
24862
|
+
className: css(styles$n.columnRight)
|
|
24861
24863
|
}, previewHeading)), children);
|
|
24862
24864
|
};
|
|
24863
24865
|
const ArrayContainer = props => {
|
|
@@ -24870,11 +24872,11 @@ const ArrayContainer = props => {
|
|
|
24870
24872
|
actions
|
|
24871
24873
|
} = props;
|
|
24872
24874
|
return /*#__PURE__*/React.createElement("div", {
|
|
24873
|
-
className: css(styles$
|
|
24875
|
+
className: css(styles$n.container)
|
|
24874
24876
|
}, controls && /*#__PURE__*/React.createElement("div", {
|
|
24875
|
-
className: css(styles$
|
|
24877
|
+
className: css(styles$n.columnLeft, styles$n.containerHeader)
|
|
24876
24878
|
}, controls), /*#__PURE__*/React.createElement("div", null, children), /*#__PURE__*/React.createElement("div", {
|
|
24877
|
-
className: css(styles$
|
|
24879
|
+
className: css(styles$n.columnLeft)
|
|
24878
24880
|
}, /*#__PURE__*/React.createElement("a", {
|
|
24879
24881
|
href: "javascript:void 0",
|
|
24880
24882
|
onClick: () => actions.addArrayElement(path, shape.elementShape)
|
|
@@ -24887,28 +24889,28 @@ const ObjectContainer = ({
|
|
|
24887
24889
|
path
|
|
24888
24890
|
}) => {
|
|
24889
24891
|
const headingEditor = /*#__PURE__*/React.createElement("div", {
|
|
24890
|
-
className: css(styles$
|
|
24892
|
+
className: css(styles$n.containerHeader)
|
|
24891
24893
|
}, /*#__PURE__*/React.createElement(Header, {
|
|
24892
24894
|
depth: path.length,
|
|
24893
|
-
className: css(styles$
|
|
24895
|
+
className: css(styles$n.containerTitle)
|
|
24894
24896
|
}, capitalize(name)), controls);
|
|
24895
24897
|
const headingPreview = (name || controls) && /*#__PURE__*/React.createElement("div", {
|
|
24896
|
-
className: css(styles$
|
|
24898
|
+
className: css(styles$n.containerHeader, styles$n.previewCollectionHeader)
|
|
24897
24899
|
}, /*#__PURE__*/React.createElement(Header, {
|
|
24898
24900
|
depth: path.length,
|
|
24899
|
-
className: css(styles$
|
|
24901
|
+
className: css(styles$n.containerTitle)
|
|
24900
24902
|
}, capitalize(name)));
|
|
24901
24903
|
const hasBothHeadings = headingEditor && headingPreview;
|
|
24902
24904
|
return /*#__PURE__*/React.createElement("div", {
|
|
24903
|
-
className: css(styles$
|
|
24905
|
+
className: css(styles$n.container)
|
|
24904
24906
|
}, hasBothHeadings && /*#__PURE__*/React.createElement("span", {
|
|
24905
|
-
className: css(styles$
|
|
24907
|
+
className: css(styles$n.row)
|
|
24906
24908
|
}, /*#__PURE__*/React.createElement("div", {
|
|
24907
|
-
className: css(styles$
|
|
24909
|
+
className: css(styles$n.columnLeft)
|
|
24908
24910
|
}, headingEditor), /*#__PURE__*/React.createElement("div", {
|
|
24909
|
-
className: css(styles$
|
|
24911
|
+
className: css(styles$n.columnRight)
|
|
24910
24912
|
}, headingPreview)), /*#__PURE__*/React.createElement("div", {
|
|
24911
|
-
className: css(path.length > 0 && styles$
|
|
24913
|
+
className: css(path.length > 0 && styles$n.contentIndent)
|
|
24912
24914
|
}, children));
|
|
24913
24915
|
};
|
|
24914
24916
|
|
|
@@ -25031,11 +25033,11 @@ const ItemNodeContent = withStickiness(props => {
|
|
|
25031
25033
|
className: "framework-perseus"
|
|
25032
25034
|
}, lens(renderers).get(path));
|
|
25033
25035
|
return /*#__PURE__*/React.createElement("span", null, /*#__PURE__*/React.createElement("div", {
|
|
25034
|
-
className: css(styles$
|
|
25036
|
+
className: css(styles$n.row)
|
|
25035
25037
|
}, /*#__PURE__*/React.createElement("div", {
|
|
25036
|
-
className: css(styles$
|
|
25038
|
+
className: css(styles$n.columnLeft)
|
|
25037
25039
|
}, /*#__PURE__*/React.createElement("div", {
|
|
25038
|
-
className: css(sticky && styles$
|
|
25040
|
+
className: css(sticky && styles$n.sticky)
|
|
25039
25041
|
},
|
|
25040
25042
|
/*#__PURE__*/
|
|
25041
25043
|
// @ts-expect-error - TS2769 - No overload matches this call.
|
|
@@ -25043,9 +25045,9 @@ const ItemNodeContent = withStickiness(props => {
|
|
|
25043
25045
|
onChange: newVal => actions.mergeValueAtPath(path, newVal),
|
|
25044
25046
|
apiOptions: apiOptions
|
|
25045
25047
|
})))), /*#__PURE__*/React.createElement("div", {
|
|
25046
|
-
className: css(styles$
|
|
25048
|
+
className: css(styles$n.columnRight)
|
|
25047
25049
|
}, /*#__PURE__*/React.createElement("div", {
|
|
25048
|
-
className: css(sticky && styles$
|
|
25050
|
+
className: css(sticky && styles$n.sticky)
|
|
25049
25051
|
}, preview))));
|
|
25050
25052
|
});
|
|
25051
25053
|
const HintNodeContent = withStickiness(props => {
|
|
@@ -25061,13 +25063,13 @@ const HintNodeContent = withStickiness(props => {
|
|
|
25061
25063
|
className: "framework-perseus"
|
|
25062
25064
|
}, lens(renderers).get(path));
|
|
25063
25065
|
return /*#__PURE__*/React.createElement("div", {
|
|
25064
|
-
className: css(styles$
|
|
25066
|
+
className: css(styles$n.row)
|
|
25065
25067
|
}, /*#__PURE__*/React.createElement("div", {
|
|
25066
|
-
className: css(styles$
|
|
25068
|
+
className: css(styles$n.columnLeft)
|
|
25067
25069
|
}, /*#__PURE__*/React.createElement("div", {
|
|
25068
|
-
className: css(sticky && styles$
|
|
25070
|
+
className: css(sticky && styles$n.sticky)
|
|
25069
25071
|
}, /*#__PURE__*/React.createElement(HintEditor, _extends({}, data, {
|
|
25070
|
-
className: css(styles$
|
|
25072
|
+
className: css(styles$n.hintEditor),
|
|
25071
25073
|
onChange: newVal => actions.mergeValueAtPath(path, newVal),
|
|
25072
25074
|
apiOptions: apiOptions,
|
|
25073
25075
|
showTitle: false,
|
|
@@ -25082,9 +25084,9 @@ const HintNodeContent = withStickiness(props => {
|
|
|
25082
25084
|
isFirst: true,
|
|
25083
25085
|
isLast: true
|
|
25084
25086
|
})))), /*#__PURE__*/React.createElement("div", {
|
|
25085
|
-
className: css(styles$
|
|
25087
|
+
className: css(styles$n.columnRight)
|
|
25086
25088
|
}, /*#__PURE__*/React.createElement("div", {
|
|
25087
|
-
className: css(sticky && styles$
|
|
25089
|
+
className: css(sticky && styles$n.sticky)
|
|
25088
25090
|
}, preview)));
|
|
25089
25091
|
});
|
|
25090
25092
|
const TagsNodeContent = props => {
|
|
@@ -25101,9 +25103,9 @@ const TagsNodeContent = props => {
|
|
|
25101
25103
|
return null;
|
|
25102
25104
|
}
|
|
25103
25105
|
return /*#__PURE__*/React.createElement("div", {
|
|
25104
|
-
className: css(styles$
|
|
25106
|
+
className: css(styles$n.columnLeft)
|
|
25105
25107
|
}, /*#__PURE__*/React.createElement("div", {
|
|
25106
|
-
className: css(styles$
|
|
25108
|
+
className: css(styles$n.tagsEditor)
|
|
25107
25109
|
}, /*#__PURE__*/React.createElement(GroupMetadataEditor, {
|
|
25108
25110
|
value: data,
|
|
25109
25111
|
onChange: newVal => actions.setValueAtPath(path, newVal),
|
|
@@ -25134,23 +25136,23 @@ const ArrayNodeContent = props => {
|
|
|
25134
25136
|
const subpath = path.concat(i);
|
|
25135
25137
|
const controls = [i > 0 && /*#__PURE__*/React.createElement("div", {
|
|
25136
25138
|
key: "moveArrayElementUp",
|
|
25137
|
-
className: css(styles$
|
|
25139
|
+
className: css(styles$n.control)
|
|
25138
25140
|
}, /*#__PURE__*/React.createElement(SimpleButton, {
|
|
25139
25141
|
color: "orange",
|
|
25140
25142
|
title: "Move up",
|
|
25141
25143
|
onClick: () => actions.moveArrayElementUp(subpath)
|
|
25142
25144
|
}, /*#__PURE__*/React.createElement("div", {
|
|
25143
|
-
className: css(styles$
|
|
25145
|
+
className: css(styles$n.verticalFlip)
|
|
25144
25146
|
}, /*#__PURE__*/React.createElement(InlineIcon$6, iconChevronDown)))), i < data.length - 1 && /*#__PURE__*/React.createElement("div", {
|
|
25145
25147
|
key: "moveArrayElementDown",
|
|
25146
|
-
className: css(styles$
|
|
25148
|
+
className: css(styles$n.control)
|
|
25147
25149
|
}, /*#__PURE__*/React.createElement(SimpleButton, {
|
|
25148
25150
|
color: "orange",
|
|
25149
25151
|
title: "Move down",
|
|
25150
25152
|
onClick: () => actions.moveArrayElementDown(subpath)
|
|
25151
25153
|
}, /*#__PURE__*/React.createElement(InlineIcon$6, iconChevronDown))), /*#__PURE__*/React.createElement("div", {
|
|
25152
25154
|
key: "removeArrayElement",
|
|
25153
|
-
className: css(styles$
|
|
25155
|
+
className: css(styles$n.control)
|
|
25154
25156
|
}, /*#__PURE__*/React.createElement(SimpleButton, {
|
|
25155
25157
|
color: "orange",
|
|
25156
25158
|
title: "Delete",
|
|
@@ -25158,7 +25160,7 @@ const ArrayNodeContent = props => {
|
|
|
25158
25160
|
}, /*#__PURE__*/React.createElement(InlineIcon$6, iconTrash$4)))];
|
|
25159
25161
|
return /*#__PURE__*/React.createElement("div", {
|
|
25160
25162
|
key: i,
|
|
25161
|
-
className: css(styles$
|
|
25163
|
+
className: css(styles$n.arrayElement, !elementIsLeaf && styles$n.arrayElementAndNotLeaf)
|
|
25162
25164
|
}, /*#__PURE__*/React.createElement(NodeContainer, _extends({}, otherProps, {
|
|
25163
25165
|
key: i,
|
|
25164
25166
|
shape: shape.elementShape,
|
|
@@ -25184,7 +25186,7 @@ const ObjectNodeContent = props => {
|
|
|
25184
25186
|
// made sense to the shape's author is the order in which we'll iterate :)
|
|
25185
25187
|
const children = Object.keys(shape.shape).map(subkey => /*#__PURE__*/React.createElement("div", {
|
|
25186
25188
|
key: subkey,
|
|
25187
|
-
className: css(styles$
|
|
25189
|
+
className: css(styles$n.objectElement)
|
|
25188
25190
|
}, /*#__PURE__*/React.createElement(NodeContainer, _extends({}, otherProps, {
|
|
25189
25191
|
shape: shape.shape[subkey],
|
|
25190
25192
|
data: data[subkey],
|
|
@@ -25351,7 +25353,7 @@ class MultiRendererEditor extends React.Component {
|
|
|
25351
25353
|
}, this._renderContent());
|
|
25352
25354
|
}
|
|
25353
25355
|
}
|
|
25354
|
-
const styles$
|
|
25356
|
+
const styles$n = StyleSheet.create({
|
|
25355
25357
|
// This is used in a number of places throughout this file.
|
|
25356
25358
|
container: {},
|
|
25357
25359
|
// eslint-disable-next-line react-native/no-unused-styles
|
|
@@ -25503,47 +25505,47 @@ const StatefulArticleEditor = createReactClass({
|
|
|
25503
25505
|
screen
|
|
25504
25506
|
} = this.state;
|
|
25505
25507
|
return /*#__PURE__*/React.createElement("div", null, /*#__PURE__*/React.createElement("div", {
|
|
25506
|
-
style: styles$
|
|
25508
|
+
style: styles$m.controlBar
|
|
25507
25509
|
}, /*#__PURE__*/React.createElement("span", {
|
|
25508
|
-
style: styles$
|
|
25510
|
+
style: styles$m.controls
|
|
25509
25511
|
}, "Mode:", " ", /*#__PURE__*/React.createElement("span", {
|
|
25510
25512
|
onClick: () => this.setState({
|
|
25511
25513
|
mode: "edit"
|
|
25512
25514
|
}),
|
|
25513
|
-
style: mode === "edit" ? styles$
|
|
25515
|
+
style: mode === "edit" ? styles$m.controlSelected : styles$m.control
|
|
25514
25516
|
}, "EDIT"), " | ", /*#__PURE__*/React.createElement("span", {
|
|
25515
25517
|
onClick: () => this.setState({
|
|
25516
25518
|
mode: "preview"
|
|
25517
25519
|
}),
|
|
25518
|
-
style: mode === "preview" ? styles$
|
|
25520
|
+
style: mode === "preview" ? styles$m.controlSelected : styles$m.control
|
|
25519
25521
|
}, "PREVIEW"), " | ", /*#__PURE__*/React.createElement("span", {
|
|
25520
25522
|
onClick: () => this.setState({
|
|
25521
25523
|
mode: "json"
|
|
25522
25524
|
}),
|
|
25523
|
-
style: mode === "json" ? styles$
|
|
25525
|
+
style: mode === "json" ? styles$m.controlSelected : styles$m.control
|
|
25524
25526
|
}, "JSON")), /*#__PURE__*/React.createElement("span", {
|
|
25525
|
-
style: styles$
|
|
25527
|
+
style: styles$m.controls
|
|
25526
25528
|
}, "Screen:", " ", /*#__PURE__*/React.createElement("span", {
|
|
25527
25529
|
onClick: () => this.setState({
|
|
25528
25530
|
screen: "phone"
|
|
25529
25531
|
}),
|
|
25530
|
-
style: screen === "phone" ? styles$
|
|
25532
|
+
style: screen === "phone" ? styles$m.controlSelected : styles$m.control
|
|
25531
25533
|
}, "PHONE"), " | ", /*#__PURE__*/React.createElement("span", {
|
|
25532
25534
|
onClick: () => this.setState({
|
|
25533
25535
|
screen: "tablet"
|
|
25534
25536
|
}),
|
|
25535
|
-
style: screen === "tablet" ? styles$
|
|
25537
|
+
style: screen === "tablet" ? styles$m.controlSelected : styles$m.control
|
|
25536
25538
|
}, "TABLET"), " | ", /*#__PURE__*/React.createElement("span", {
|
|
25537
25539
|
onClick: () => this.setState({
|
|
25538
25540
|
screen: "desktop"
|
|
25539
25541
|
}),
|
|
25540
|
-
style: screen === "desktop" ? styles$
|
|
25542
|
+
style: screen === "desktop" ? styles$m.controlSelected : styles$m.control
|
|
25541
25543
|
}, "DESKTOP"))), /*#__PURE__*/React.createElement("div", {
|
|
25542
|
-
style: styles$
|
|
25544
|
+
style: styles$m.editor
|
|
25543
25545
|
}, /*#__PURE__*/React.createElement(ArticleEditor, this.state)));
|
|
25544
25546
|
}
|
|
25545
25547
|
});
|
|
25546
|
-
const styles$
|
|
25548
|
+
const styles$m = {
|
|
25547
25549
|
controlBar: {
|
|
25548
25550
|
marginBottom: 25,
|
|
25549
25551
|
marginTop: 5
|
|
@@ -27032,10 +27034,10 @@ class GradedGroupEditor extends React.Component {
|
|
|
27032
27034
|
}, /*#__PURE__*/React.createElement("div", {
|
|
27033
27035
|
className: "perseus-widget-row"
|
|
27034
27036
|
}, /*#__PURE__*/React.createElement("label", {
|
|
27035
|
-
className: css(styles$
|
|
27037
|
+
className: css(styles$l.title)
|
|
27036
27038
|
}, "Title:", " ", /*#__PURE__*/React.createElement(TextInput$6, {
|
|
27037
27039
|
value: this.props.title,
|
|
27038
|
-
className: css(styles$
|
|
27040
|
+
className: css(styles$l.input)
|
|
27039
27041
|
// @ts-expect-error - TS2554 - Expected 3 arguments, but got 1.
|
|
27040
27042
|
,
|
|
27041
27043
|
onChange: this.change("title")
|
|
@@ -27060,7 +27062,7 @@ class GradedGroupEditor extends React.Component {
|
|
|
27060
27062
|
}, /*#__PURE__*/React.createElement(InlineIcon$4, iconPlus$1), " Add a hint"), this.props.hint && /*#__PURE__*/React.createElement("div", {
|
|
27061
27063
|
className: "perseus-hint-editor"
|
|
27062
27064
|
}, /*#__PURE__*/React.createElement("div", {
|
|
27063
|
-
className: css(styles$
|
|
27065
|
+
className: css(styles$l.hintsTitle)
|
|
27064
27066
|
}, "Hint"), /*#__PURE__*/React.createElement(Editor, {
|
|
27065
27067
|
ref: this.hintEditor,
|
|
27066
27068
|
content: this.props.hint ? this.props.hint.content : "",
|
|
@@ -27097,7 +27099,7 @@ GradedGroupEditor.defaultProps = {
|
|
|
27097
27099
|
images: {},
|
|
27098
27100
|
hint: null
|
|
27099
27101
|
};
|
|
27100
|
-
const styles$
|
|
27102
|
+
const styles$l = StyleSheet.create({
|
|
27101
27103
|
title: {
|
|
27102
27104
|
fontSize: 18,
|
|
27103
27105
|
fontWeight: "bold"
|
|
@@ -28429,13 +28431,13 @@ function MathquillInput(props) {
|
|
|
28429
28431
|
}
|
|
28430
28432
|
});
|
|
28431
28433
|
return /*#__PURE__*/React.createElement(View, {
|
|
28432
|
-
style: styles$
|
|
28434
|
+
style: styles$k.outerWrapper
|
|
28433
28435
|
}, /*#__PURE__*/React.createElement("span", {
|
|
28434
28436
|
ref: mathFieldWrapperRef,
|
|
28435
28437
|
className: "perseus-math-input mq-editable-field mq-math-mode"
|
|
28436
28438
|
}));
|
|
28437
28439
|
}
|
|
28438
|
-
const styles$
|
|
28440
|
+
const styles$k = StyleSheet.create({
|
|
28439
28441
|
outerWrapper: {
|
|
28440
28442
|
display: "inline-block",
|
|
28441
28443
|
borderStyle: "solid",
|
|
@@ -29496,7 +29498,7 @@ const GraphPointsCountSelector = ({
|
|
|
29496
29498
|
// Never uses placeholder, always has value
|
|
29497
29499
|
,
|
|
29498
29500
|
placeholder: "",
|
|
29499
|
-
style: styles$
|
|
29501
|
+
style: styles$j.singleSelectShort
|
|
29500
29502
|
}, [...[...Array(7).keys()].map(n => /*#__PURE__*/React.createElement(OptionItem, {
|
|
29501
29503
|
key: n,
|
|
29502
29504
|
value: `${n}`,
|
|
@@ -29506,7 +29508,7 @@ const GraphPointsCountSelector = ({
|
|
|
29506
29508
|
label: "unlimited"
|
|
29507
29509
|
})]);
|
|
29508
29510
|
};
|
|
29509
|
-
const styles$
|
|
29511
|
+
const styles$j = StyleSheet.create({
|
|
29510
29512
|
singleSelectShort: {
|
|
29511
29513
|
// Non-standard spacing, but it's the smallest we can go
|
|
29512
29514
|
// without running into styling issues with the dropdown.
|
|
@@ -29519,7 +29521,7 @@ const GraphTypeSelector = props => {
|
|
|
29519
29521
|
selectedValue: props.graphType,
|
|
29520
29522
|
onChange: props.onChange,
|
|
29521
29523
|
placeholder: "Select a graph type",
|
|
29522
|
-
style: styles$
|
|
29524
|
+
style: styles$i.singleSelectShort
|
|
29523
29525
|
}, /*#__PURE__*/React.createElement(OptionItem, {
|
|
29524
29526
|
value: "linear",
|
|
29525
29527
|
label: "Linear function"
|
|
@@ -29552,7 +29554,7 @@ const GraphTypeSelector = props => {
|
|
|
29552
29554
|
label: "Angle"
|
|
29553
29555
|
}));
|
|
29554
29556
|
};
|
|
29555
|
-
const styles$
|
|
29557
|
+
const styles$i = StyleSheet.create({
|
|
29556
29558
|
singleSelectShort: {
|
|
29557
29559
|
// Non-standard spacing, but it's the smallest we can go
|
|
29558
29560
|
// without running into styling issues with the dropdown.
|
|
@@ -29568,19 +29570,25 @@ const LabeledRow = props => {
|
|
|
29568
29570
|
labelSide = "left",
|
|
29569
29571
|
style
|
|
29570
29572
|
} = props;
|
|
29571
|
-
return /*#__PURE__*/React.createElement("label",
|
|
29572
|
-
|
|
29573
|
+
return /*#__PURE__*/React.createElement("label", {
|
|
29574
|
+
className: css(styles$h.label)
|
|
29575
|
+
}, /*#__PURE__*/React.createElement(View, {
|
|
29576
|
+
style: [styles$h.row, style]
|
|
29573
29577
|
}, labelSide === "start" || /*#__PURE__*/React.createElement(LabelSmall, {
|
|
29574
|
-
style: styles$
|
|
29578
|
+
style: styles$h.spaceEnd
|
|
29575
29579
|
}, label), children, labelSide === "end" && /*#__PURE__*/React.createElement(LabelSmall, {
|
|
29576
|
-
style: styles$
|
|
29580
|
+
style: styles$h.spaceStart
|
|
29577
29581
|
}, label)));
|
|
29578
29582
|
};
|
|
29579
|
-
const styles$
|
|
29583
|
+
const styles$h = StyleSheet.create({
|
|
29584
|
+
label: {
|
|
29585
|
+
width: "fit-content"
|
|
29586
|
+
},
|
|
29580
29587
|
row: {
|
|
29581
29588
|
flexDirection: "row",
|
|
29582
29589
|
marginTop: spacing.xSmall_8,
|
|
29583
|
-
alignItems: "center"
|
|
29590
|
+
alignItems: "center",
|
|
29591
|
+
width: "fit-content"
|
|
29584
29592
|
},
|
|
29585
29593
|
spaceStart: {
|
|
29586
29594
|
marginInlineStart: spacing.xSmall_8
|
|
@@ -29966,10 +29974,10 @@ class InteractiveGraphSettings extends React.Component {
|
|
|
29966
29974
|
onChange: this.change
|
|
29967
29975
|
}))), /*#__PURE__*/React.createElement(LabeledRow, {
|
|
29968
29976
|
label: "Background image URL:",
|
|
29969
|
-
style: styles$
|
|
29977
|
+
style: styles$g.resetSpaceTop
|
|
29970
29978
|
}, /*#__PURE__*/React.createElement("input", {
|
|
29971
29979
|
type: "text",
|
|
29972
|
-
className: css(styles$
|
|
29980
|
+
className: css(styles$g.backgroundUrlInput),
|
|
29973
29981
|
ref: this.bgUrlRef,
|
|
29974
29982
|
value: this.state.backgroundImage.url || "",
|
|
29975
29983
|
onChange: e => {
|
|
@@ -29983,24 +29991,24 @@ class InteractiveGraphSettings extends React.Component {
|
|
|
29983
29991
|
onKeyPress: this.changeBackgroundUrl,
|
|
29984
29992
|
onBlur: this.changeBackgroundUrl
|
|
29985
29993
|
}), /*#__PURE__*/React.createElement(InfoTip$c, null, /*#__PURE__*/React.createElement("p", null, "Create an image in graphie, or use the \"Add image\" function to create a background."))), /*#__PURE__*/React.createElement(View, {
|
|
29986
|
-
style: styles$
|
|
29994
|
+
style: styles$g.rulerSection
|
|
29987
29995
|
}, /*#__PURE__*/React.createElement(View, {
|
|
29988
|
-
style: styles$
|
|
29996
|
+
style: styles$g.checkboxRow
|
|
29989
29997
|
}, /*#__PURE__*/React.createElement(PropCheckBox$7, {
|
|
29990
29998
|
label: "Show ruler",
|
|
29991
29999
|
showRuler: this.props.showRuler,
|
|
29992
30000
|
onChange: this.change,
|
|
29993
|
-
style: styles$
|
|
30001
|
+
style: styles$g.resetSpaceTop
|
|
29994
30002
|
}), /*#__PURE__*/React.createElement(PropCheckBox$7, {
|
|
29995
30003
|
label: "Show protractor",
|
|
29996
30004
|
showProtractor: this.props.showProtractor,
|
|
29997
30005
|
onChange: this.change,
|
|
29998
|
-
style: styles$
|
|
30006
|
+
style: styles$g.resetSpaceTop
|
|
29999
30007
|
})), this.props.showRuler && /*#__PURE__*/React.createElement(View, {
|
|
30000
|
-
style: styles$
|
|
30008
|
+
style: styles$g.spaceTop
|
|
30001
30009
|
}, /*#__PURE__*/React.createElement(LabeledRow, {
|
|
30002
30010
|
label: "Ruler label:",
|
|
30003
|
-
style: styles$
|
|
30011
|
+
style: styles$g.resetSpaceTop
|
|
30004
30012
|
}, /*#__PURE__*/React.createElement(SingleSelect, {
|
|
30005
30013
|
id: "ruler-label-select",
|
|
30006
30014
|
selectedValue: this.props.rulerLabel,
|
|
@@ -30010,7 +30018,7 @@ class InteractiveGraphSettings extends React.Component {
|
|
|
30010
30018
|
});
|
|
30011
30019
|
},
|
|
30012
30020
|
placeholder: "None",
|
|
30013
|
-
style: styles$
|
|
30021
|
+
style: styles$g.singleSelectShort
|
|
30014
30022
|
}, /*#__PURE__*/React.createElement(OptionItem, {
|
|
30015
30023
|
value: "",
|
|
30016
30024
|
label: "None",
|
|
@@ -30051,7 +30059,7 @@ class InteractiveGraphSettings extends React.Component {
|
|
|
30051
30059
|
});
|
|
30052
30060
|
},
|
|
30053
30061
|
placeholder: "10",
|
|
30054
|
-
style: styles$
|
|
30062
|
+
style: styles$g.singleSelectShort
|
|
30055
30063
|
}, [1, 2, 4, 8, 10, 16].map(value => /*#__PURE__*/React.createElement(OptionItem, {
|
|
30056
30064
|
key: value,
|
|
30057
30065
|
value: `${value}`,
|
|
@@ -30075,7 +30083,7 @@ InteractiveGraphSettings.defaultProps = {
|
|
|
30075
30083
|
rulerLabel: "",
|
|
30076
30084
|
rulerTicks: 10
|
|
30077
30085
|
};
|
|
30078
|
-
const styles$
|
|
30086
|
+
const styles$g = StyleSheet.create({
|
|
30079
30087
|
resetSpaceTop: {
|
|
30080
30088
|
marginTop: 0
|
|
30081
30089
|
},
|
|
@@ -30106,6 +30114,314 @@ const styles$c = StyleSheet.create({
|
|
|
30106
30114
|
}
|
|
30107
30115
|
});
|
|
30108
30116
|
|
|
30117
|
+
/**
|
|
30118
|
+
* Dropdown for selecting a locked figure to add to an interactive graph.
|
|
30119
|
+
* Locked figures are elements (points, segmeents, etc.) that are not
|
|
30120
|
+
* interactive, just present in the graph's background.
|
|
30121
|
+
*
|
|
30122
|
+
* Used in the interactive graph editor's locked figures section.
|
|
30123
|
+
*/
|
|
30124
|
+
const LockedFigureSelect = props => {
|
|
30125
|
+
const {
|
|
30126
|
+
id,
|
|
30127
|
+
onChange
|
|
30128
|
+
} = props;
|
|
30129
|
+
return /*#__PURE__*/React.createElement(View, {
|
|
30130
|
+
style: styles$f.container
|
|
30131
|
+
}, /*#__PURE__*/React.createElement(ActionMenu, {
|
|
30132
|
+
menuText: "Add element",
|
|
30133
|
+
style: styles$f.addElementSelect
|
|
30134
|
+
}, [/*#__PURE__*/React.createElement(ActionItem, {
|
|
30135
|
+
key: `${id}-point`,
|
|
30136
|
+
label: "Point",
|
|
30137
|
+
onClick: () => onChange("point")
|
|
30138
|
+
}, "Point")]));
|
|
30139
|
+
};
|
|
30140
|
+
const styles$f = StyleSheet.create({
|
|
30141
|
+
container: {
|
|
30142
|
+
marginTop: spacing.medium_16
|
|
30143
|
+
},
|
|
30144
|
+
addElementSelect: {
|
|
30145
|
+
backgroundColor: color.fadedBlue16,
|
|
30146
|
+
borderRadius: spacing.xxxSmall_4
|
|
30147
|
+
}
|
|
30148
|
+
});
|
|
30149
|
+
|
|
30150
|
+
const mediaDefaultSpecLargeMarginWidth = spacing.large_24;
|
|
30151
|
+
const MEDIA_DEFAULT_SPEC = {
|
|
30152
|
+
small: {
|
|
30153
|
+
query: "(max-width: 767px)",
|
|
30154
|
+
totalColumns: 4,
|
|
30155
|
+
gutterWidth: spacing.medium_16,
|
|
30156
|
+
marginWidth: spacing.medium_16
|
|
30157
|
+
},
|
|
30158
|
+
medium: {
|
|
30159
|
+
query: "(min-width: 768px) and (max-width: 1023px)",
|
|
30160
|
+
totalColumns: 8,
|
|
30161
|
+
gutterWidth: spacing.xLarge_32,
|
|
30162
|
+
marginWidth: spacing.large_24
|
|
30163
|
+
},
|
|
30164
|
+
large: {
|
|
30165
|
+
query: "(min-width: 1024px)",
|
|
30166
|
+
totalColumns: 12,
|
|
30167
|
+
gutterWidth: spacing.xLarge_32,
|
|
30168
|
+
marginWidth: mediaDefaultSpecLargeMarginWidth,
|
|
30169
|
+
maxWidth: 1120 + mediaDefaultSpecLargeMarginWidth * 2
|
|
30170
|
+
}
|
|
30171
|
+
};
|
|
30172
|
+
({
|
|
30173
|
+
large: {
|
|
30174
|
+
query: "(min-width: 1px)",
|
|
30175
|
+
totalColumns: 12,
|
|
30176
|
+
gutterWidth: spacing.xLarge_32,
|
|
30177
|
+
marginWidth: spacing.medium_16
|
|
30178
|
+
}
|
|
30179
|
+
});
|
|
30180
|
+
({
|
|
30181
|
+
small: {
|
|
30182
|
+
query: "(max-width: 767px)",
|
|
30183
|
+
totalColumns: 4,
|
|
30184
|
+
gutterWidth: spacing.medium_16,
|
|
30185
|
+
marginWidth: spacing.medium_16
|
|
30186
|
+
},
|
|
30187
|
+
large: {
|
|
30188
|
+
query: "(min-width: 768px)",
|
|
30189
|
+
totalColumns: 12,
|
|
30190
|
+
gutterWidth: spacing.xLarge_32,
|
|
30191
|
+
marginWidth: spacing.xxLarge_48
|
|
30192
|
+
}
|
|
30193
|
+
});
|
|
30194
|
+
|
|
30195
|
+
const defaultContext = {
|
|
30196
|
+
ssrSize: "large",
|
|
30197
|
+
mediaSpec: MEDIA_DEFAULT_SPEC
|
|
30198
|
+
};
|
|
30199
|
+
const MediaLayoutContext = React.createContext(defaultContext);
|
|
30200
|
+
MediaLayoutContext.displayName = "MediaLayoutContext";
|
|
30201
|
+
|
|
30202
|
+
class Spring extends React.Component {
|
|
30203
|
+
render() {
|
|
30204
|
+
const {
|
|
30205
|
+
style
|
|
30206
|
+
} = this.props;
|
|
30207
|
+
return React.createElement(View, {
|
|
30208
|
+
"aria-hidden": "true",
|
|
30209
|
+
style: [styles$e.grow, style]
|
|
30210
|
+
});
|
|
30211
|
+
}
|
|
30212
|
+
}
|
|
30213
|
+
const styles$e = StyleSheet.create({
|
|
30214
|
+
grow: {
|
|
30215
|
+
flexGrow: 1
|
|
30216
|
+
}
|
|
30217
|
+
});
|
|
30218
|
+
|
|
30219
|
+
function focusWithChromeStickyFocusBugWorkaround(element) {
|
|
30220
|
+
// NOTE(marksandstrom) Chrome sticky focus bug.
|
|
30221
|
+
//
|
|
30222
|
+
// There is a bug in Chrome related to sticky positioning and
|
|
30223
|
+
// focus: When a child of an element with sticky positioning is
|
|
30224
|
+
// focused with the focus() method, the scrollable area
|
|
30225
|
+
// containing that element will scroll to the top (even though
|
|
30226
|
+
// the element is already visble on the page). For a dropdown
|
|
30227
|
+
// this means that the area will be scrolled to the top when
|
|
30228
|
+
// the user interacts with the dropdown (since we actively
|
|
30229
|
+
// manage dropdown header and option focus for keyboard users).
|
|
30230
|
+
//
|
|
30231
|
+
// To work around this bug the `preventScroll` focus option is
|
|
30232
|
+
// used.
|
|
30233
|
+
//
|
|
30234
|
+
// Using `focusOptions` is an experimental browser feature
|
|
30235
|
+
// "that should not be used in production code". However, since
|
|
30236
|
+
// Chrome is the only browser we support that exhibits this
|
|
30237
|
+
// buggy behavior and using `focusOptions` works around the
|
|
30238
|
+
// bug, it is perfectly reasonable to use the feature in this
|
|
30239
|
+
// case. We are not relying on the effect of the
|
|
30240
|
+
// `preventScroll` option otherwise.
|
|
30241
|
+
//
|
|
30242
|
+
// focusOptions documentation:
|
|
30243
|
+
//
|
|
30244
|
+
// https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/focus
|
|
30245
|
+
//
|
|
30246
|
+
// Note that there could be cases where we want default focus() behavior.
|
|
30247
|
+
// One that comes to mind is a dropdown with a long list of options that
|
|
30248
|
+
// might be rendered off screen when opened. With this workaround the
|
|
30249
|
+
// selected option would not be scrolled into view if the option is near
|
|
30250
|
+
// the end of the list. We're not aware of any uses of the dropdown where
|
|
30251
|
+
// this is an issue, however, so there isn't currently a way to out of the
|
|
30252
|
+
// `preventScroll` behavior.
|
|
30253
|
+
|
|
30254
|
+
// @ts-expect-error - TS2339 - Property 'focus' does not exist on type 'Element'.
|
|
30255
|
+
element.focus({
|
|
30256
|
+
preventScroll: true
|
|
30257
|
+
});
|
|
30258
|
+
}
|
|
30259
|
+
function getValidNumberFromString(value) {
|
|
30260
|
+
const parsed = parseInt(value);
|
|
30261
|
+
// If the value is not a number, return 0.
|
|
30262
|
+
return isNaN(parsed) ? 0 : parsed;
|
|
30263
|
+
}
|
|
30264
|
+
function getDefaultFigureForFigureType(type) {
|
|
30265
|
+
switch (type) {
|
|
30266
|
+
case "point":
|
|
30267
|
+
return {
|
|
30268
|
+
type: "point",
|
|
30269
|
+
coord: [0, 0]
|
|
30270
|
+
};
|
|
30271
|
+
}
|
|
30272
|
+
}
|
|
30273
|
+
|
|
30274
|
+
/**
|
|
30275
|
+
* LockedPointSettings is a component that allows the user to edit the
|
|
30276
|
+
* settings of specifically a locked point on the graph.
|
|
30277
|
+
*
|
|
30278
|
+
* Used in the interactive graph editor's locked figures section.
|
|
30279
|
+
*/
|
|
30280
|
+
const LockedPointSettings = props => {
|
|
30281
|
+
const {
|
|
30282
|
+
coord,
|
|
30283
|
+
onRemove,
|
|
30284
|
+
onChangeCoord
|
|
30285
|
+
} = props;
|
|
30286
|
+
const [coordState, setCoordState] = React.useState([
|
|
30287
|
+
// Using strings to make it easier to work with the text fields.
|
|
30288
|
+
coord[0].toString(), coord[1].toString()]);
|
|
30289
|
+
|
|
30290
|
+
// Generate unique IDs so that the programmatic labels can be associated
|
|
30291
|
+
// with their respective text fields.
|
|
30292
|
+
const ids = useUniqueIdWithMock();
|
|
30293
|
+
const xCoordId = ids.get("x-coord");
|
|
30294
|
+
const yCoordId = ids.get("y-coord");
|
|
30295
|
+
function handleBlur() {
|
|
30296
|
+
const validCoord = [getValidNumberFromString(coordState[0]), getValidNumberFromString(coordState[1])];
|
|
30297
|
+
|
|
30298
|
+
// Make the text field only show valid numbers after blur.
|
|
30299
|
+
setCoordState([validCoord[0].toString(), validCoord[1].toString()]);
|
|
30300
|
+
// Update the graph with the new coordinates.
|
|
30301
|
+
onChangeCoord(validCoord);
|
|
30302
|
+
}
|
|
30303
|
+
function handleChange(newValue, coordIndex) {
|
|
30304
|
+
const newCoord = [...coordState];
|
|
30305
|
+
newCoord[coordIndex] = newValue;
|
|
30306
|
+
setCoordState(newCoord);
|
|
30307
|
+
}
|
|
30308
|
+
return /*#__PURE__*/React.createElement(View, {
|
|
30309
|
+
style: styles$d.container
|
|
30310
|
+
}, /*#__PURE__*/React.createElement(View, {
|
|
30311
|
+
style: styles$d.row
|
|
30312
|
+
}, /*#__PURE__*/React.createElement(LabelLarge, null, "Point"), /*#__PURE__*/React.createElement(Spring, null), /*#__PURE__*/React.createElement(IconButton, {
|
|
30313
|
+
icon: trashIcon,
|
|
30314
|
+
"aria-label": `Delete locked point at ${coordState[0]}, ${coordState[1]}`,
|
|
30315
|
+
onClick: onRemove
|
|
30316
|
+
})), /*#__PURE__*/React.createElement(View, null, /*#__PURE__*/React.createElement(View, {
|
|
30317
|
+
style: styles$d.row
|
|
30318
|
+
}, /*#__PURE__*/React.createElement(LabelMedium, {
|
|
30319
|
+
htmlFor: xCoordId,
|
|
30320
|
+
style: styles$d.label,
|
|
30321
|
+
tag: "label"
|
|
30322
|
+
}, "x Coordinate"), /*#__PURE__*/React.createElement(TextField, {
|
|
30323
|
+
id: xCoordId,
|
|
30324
|
+
value: coordState[0],
|
|
30325
|
+
onChange: newValue => handleChange(newValue, 0),
|
|
30326
|
+
onBlur: handleBlur,
|
|
30327
|
+
style: styles$d.textField
|
|
30328
|
+
})), /*#__PURE__*/React.createElement(View, {
|
|
30329
|
+
style: styles$d.row
|
|
30330
|
+
}, /*#__PURE__*/React.createElement(LabelMedium, {
|
|
30331
|
+
htmlFor: yCoordId,
|
|
30332
|
+
style: styles$d.label,
|
|
30333
|
+
tag: "label"
|
|
30334
|
+
}, "y Coordinate"), /*#__PURE__*/React.createElement(TextField, {
|
|
30335
|
+
id: yCoordId,
|
|
30336
|
+
value: coordState[1],
|
|
30337
|
+
onChange: newValue => handleChange(newValue, 1),
|
|
30338
|
+
onBlur: handleBlur,
|
|
30339
|
+
style: styles$d.textField
|
|
30340
|
+
}))));
|
|
30341
|
+
};
|
|
30342
|
+
const styles$d = StyleSheet.create({
|
|
30343
|
+
container: {
|
|
30344
|
+
backgroundColor: color.fadedBlue8,
|
|
30345
|
+
marginBottom: spacing.xSmall_8,
|
|
30346
|
+
padding: spacing.medium_16,
|
|
30347
|
+
borderRadius: spacing.xSmall_8
|
|
30348
|
+
},
|
|
30349
|
+
row: {
|
|
30350
|
+
flexDirection: "row",
|
|
30351
|
+
alignItems: "center",
|
|
30352
|
+
marginBottom: spacing.xSmall_8
|
|
30353
|
+
},
|
|
30354
|
+
label: {
|
|
30355
|
+
marginInlineEnd: spacing.xSmall_8
|
|
30356
|
+
},
|
|
30357
|
+
textField: {
|
|
30358
|
+
width: spacing.xxxLarge_64
|
|
30359
|
+
}
|
|
30360
|
+
});
|
|
30361
|
+
|
|
30362
|
+
/**
|
|
30363
|
+
* LockedFigureSettings takes in a figure and renders the
|
|
30364
|
+
* respective settings for that figure type.
|
|
30365
|
+
*
|
|
30366
|
+
* Used in the interactive graph editor's locked figures section.
|
|
30367
|
+
*/
|
|
30368
|
+
|
|
30369
|
+
// Union this type with other locked figure types when they are added.
|
|
30370
|
+
|
|
30371
|
+
const LockedFigureSettings = props => {
|
|
30372
|
+
switch (props.type) {
|
|
30373
|
+
case "point":
|
|
30374
|
+
return /*#__PURE__*/React.createElement(LockedPointSettings, props);
|
|
30375
|
+
}
|
|
30376
|
+
return null;
|
|
30377
|
+
};
|
|
30378
|
+
|
|
30379
|
+
const LockedFiguresSection = props => {
|
|
30380
|
+
const uniqueId = useUniqueIdWithMock().get("locked-figures-section");
|
|
30381
|
+
const {
|
|
30382
|
+
figures,
|
|
30383
|
+
onChange
|
|
30384
|
+
} = props;
|
|
30385
|
+
function addLockedFigure(newFigure) {
|
|
30386
|
+
const lockedFigures = figures || [];
|
|
30387
|
+
const newProps = {
|
|
30388
|
+
lockedFigures: [...lockedFigures, getDefaultFigureForFigureType(newFigure)]
|
|
30389
|
+
};
|
|
30390
|
+
onChange(newProps);
|
|
30391
|
+
}
|
|
30392
|
+
function removeLockedFigure(index) {
|
|
30393
|
+
const lockedFigures = figures || [];
|
|
30394
|
+
onChange({
|
|
30395
|
+
lockedFigures: [...lockedFigures.slice(0, index), ...lockedFigures.slice(index + 1)]
|
|
30396
|
+
});
|
|
30397
|
+
}
|
|
30398
|
+
function changeCoord(index, coord) {
|
|
30399
|
+
const lockedFigures = figures || [];
|
|
30400
|
+
const newProps = {
|
|
30401
|
+
lockedFigures: [...lockedFigures.slice(0, index), _extends({}, lockedFigures[index], {
|
|
30402
|
+
coord
|
|
30403
|
+
}), ...lockedFigures.slice(index + 1)]
|
|
30404
|
+
};
|
|
30405
|
+
onChange(newProps);
|
|
30406
|
+
}
|
|
30407
|
+
return /*#__PURE__*/React.createElement(View, {
|
|
30408
|
+
style: styles$c.container
|
|
30409
|
+
}, figures == null ? void 0 : figures.map((figure, index) => /*#__PURE__*/React.createElement(LockedFigureSettings, _extends({
|
|
30410
|
+
key: `${uniqueId}-locked-${figure}-${index}`
|
|
30411
|
+
}, figure, {
|
|
30412
|
+
onRemove: () => removeLockedFigure(index),
|
|
30413
|
+
onChangeCoord: coord => changeCoord(index, coord)
|
|
30414
|
+
}))), /*#__PURE__*/React.createElement(LockedFigureSelect, {
|
|
30415
|
+
id: `${uniqueId}-select`,
|
|
30416
|
+
onChange: addLockedFigure
|
|
30417
|
+
}));
|
|
30418
|
+
};
|
|
30419
|
+
const styles$c = StyleSheet.create({
|
|
30420
|
+
container: {
|
|
30421
|
+
paddingTop: spacing.large_24
|
|
30422
|
+
}
|
|
30423
|
+
});
|
|
30424
|
+
|
|
30109
30425
|
const SegmentCountSelector = ({
|
|
30110
30426
|
numSegments: _numSegments = 1,
|
|
30111
30427
|
onChange
|
|
@@ -30186,7 +30502,7 @@ class InteractiveGraphEditor extends React.Component {
|
|
|
30186
30502
|
DeprecationMixin.UNSAFE_componentWillMount.call(this);
|
|
30187
30503
|
}
|
|
30188
30504
|
render() {
|
|
30189
|
-
var _this$props$graph$typ, _this$props$graph, _this$props$correct, _this$props$correct2, _this$props$correct3, _this$props$correct4, _this$props$correct5, _this$props$correct6, _this$props$correct7, _this$props$correct8, _this$props$correct9, _this$props$correct10, _this$props$correct11;
|
|
30505
|
+
var _this$props$graph$typ, _this$props$graph, _this$props$correct, _this$props$correct2, _this$props$correct3, _this$props$correct4, _this$props$correct5, _this$props$correct6, _this$props$correct7, _this$props$correct8, _this$props$correct9, _this$props$correct10, _this$props$correct11, _this$props$apiOption;
|
|
30190
30506
|
let graph;
|
|
30191
30507
|
let equationString;
|
|
30192
30508
|
const gridStep = this.props.gridStep || Util.getGridStep(this.props.range, this.props.step, interactiveSizes.defaultBoxSize);
|
|
@@ -30210,6 +30526,7 @@ class InteractiveGraphEditor extends React.Component {
|
|
|
30210
30526
|
showTooltips: this.props.showTooltips,
|
|
30211
30527
|
rulerLabel: this.props.rulerLabel,
|
|
30212
30528
|
rulerTicks: this.props.rulerTicks,
|
|
30529
|
+
lockedFigures: this.props.lockedFigures,
|
|
30213
30530
|
trackInteraction: function () {},
|
|
30214
30531
|
onChange: newProps => {
|
|
30215
30532
|
let correct = this.props.correct;
|
|
@@ -30425,10 +30742,16 @@ class InteractiveGraphEditor extends React.Component {
|
|
|
30425
30742
|
borderStyle: "solid",
|
|
30426
30743
|
borderWidth: 1
|
|
30427
30744
|
}
|
|
30428
|
-
}, equationString), /*#__PURE__*/React.createElement(InfoTip$b, null, /*#__PURE__*/React.createElement("p", null, "Graph the correct answer in the graph below and ensure the equation or point coordinates displayed represent the correct answer."))), graph
|
|
30745
|
+
}, equationString), /*#__PURE__*/React.createElement(InfoTip$b, null, /*#__PURE__*/React.createElement("p", null, "Graph the correct answer in the graph below and ensure the equation or point coordinates displayed represent the correct answer."))), graph,
|
|
30746
|
+
// Only show the "Add element" dropdown if the graph is
|
|
30747
|
+
// using Mafs.
|
|
30748
|
+
this.props.graph && ((_this$props$apiOption = this.props.apiOptions) == null || (_this$props$apiOption = _this$props$apiOption.flags) == null || (_this$props$apiOption = _this$props$apiOption["mafs"]) == null ? void 0 : _this$props$apiOption[this.props.graph.type]) && /*#__PURE__*/React.createElement(LockedFiguresSection, {
|
|
30749
|
+
figures: this.props.lockedFigures,
|
|
30750
|
+
onChange: this.props.onChange
|
|
30751
|
+
}));
|
|
30429
30752
|
}
|
|
30430
30753
|
serialize() {
|
|
30431
|
-
const json = _.pick(this.props, "step", "backgroundImage", "markings", "labels", "showProtractor", "showRuler", "showTooltips", "rulerLabel", "rulerTicks", "range", "gridStep", "snapStep");
|
|
30754
|
+
const json = _.pick(this.props, "step", "backgroundImage", "markings", "labels", "showProtractor", "showRuler", "showTooltips", "rulerLabel", "rulerTicks", "range", "gridStep", "snapStep", "lockedFigures");
|
|
30432
30755
|
|
|
30433
30756
|
// eslint-disable-next-line react/no-string-refs
|
|
30434
30757
|
const graph = this.refs.graph;
|
|
@@ -31188,47 +31511,6 @@ const styles$5 = StyleSheet.create({
|
|
|
31188
31511
|
})
|
|
31189
31512
|
});
|
|
31190
31513
|
|
|
31191
|
-
function focusWithChromeStickyFocusBugWorkaround(element) {
|
|
31192
|
-
// NOTE(marksandstrom) Chrome sticky focus bug.
|
|
31193
|
-
//
|
|
31194
|
-
// There is a bug in Chrome related to sticky positioning and
|
|
31195
|
-
// focus: When a child of an element with sticky positioning is
|
|
31196
|
-
// focused with the focus() method, the scrollable area
|
|
31197
|
-
// containing that element will scroll to the top (even though
|
|
31198
|
-
// the element is already visble on the page). For a dropdown
|
|
31199
|
-
// this means that the area will be scrolled to the top when
|
|
31200
|
-
// the user interacts with the dropdown (since we actively
|
|
31201
|
-
// manage dropdown header and option focus for keyboard users).
|
|
31202
|
-
//
|
|
31203
|
-
// To work around this bug the `preventScroll` focus option is
|
|
31204
|
-
// used.
|
|
31205
|
-
//
|
|
31206
|
-
// Using `focusOptions` is an experimental browser feature
|
|
31207
|
-
// "that should not be used in production code". However, since
|
|
31208
|
-
// Chrome is the only browser we support that exhibits this
|
|
31209
|
-
// buggy behavior and using `focusOptions` works around the
|
|
31210
|
-
// bug, it is perfectly reasonable to use the feature in this
|
|
31211
|
-
// case. We are not relying on the effect of the
|
|
31212
|
-
// `preventScroll` option otherwise.
|
|
31213
|
-
//
|
|
31214
|
-
// focusOptions documentation:
|
|
31215
|
-
//
|
|
31216
|
-
// https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/focus
|
|
31217
|
-
//
|
|
31218
|
-
// Note that there could be cases where we want default focus() behavior.
|
|
31219
|
-
// One that comes to mind is a dropdown with a long list of options that
|
|
31220
|
-
// might be rendered off screen when opened. With this workaround the
|
|
31221
|
-
// selected option would not be scrolled into view if the option is near
|
|
31222
|
-
// the end of the list. We're not aware of any uses of the dropdown where
|
|
31223
|
-
// this is an issue, however, so there isn't currently a way to out of the
|
|
31224
|
-
// `preventScroll` behavior.
|
|
31225
|
-
|
|
31226
|
-
// @ts-expect-error - TS2339 - Property 'focus' does not exist on type 'Element'.
|
|
31227
|
-
element.focus({
|
|
31228
|
-
preventScroll: true
|
|
31229
|
-
});
|
|
31230
|
-
}
|
|
31231
|
-
|
|
31232
31514
|
const {
|
|
31233
31515
|
Icon
|
|
31234
31516
|
} = components;
|