@khanacademy/perseus-editor 8.0.0 → 8.2.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.
package/dist/es/index.js CHANGED
@@ -1,5 +1,5 @@
1
1
  import { addLibraryVersionToPerseusDebug, PerseusError, Errors } from '@khanacademy/perseus-core';
2
- import { constants, components, Widgets, icons, WIDGET_PROP_DENYLIST, Util, Log, PerseusMarkdown, preprocessTex, ApiOptions, buildMapper, itemToTree, buildEmptyItemTreeForShape, shapes, ItemExtras, itemDataVersion, ClassNames, MultiItems, traverse, Categorizer as Categorizer$1, Changeable, EditorJsonify, Dependencies, WidgetJsonifyDeprecated, PerseusExpressionAnswerFormConsidered, Expression, interactiveSizes, KhanMath, GrapherWidget, GrapherUtil, SizingUtils, PerseusI18nContext, KhanColors, ColorPicker, DashPicker, ArrowPicker, ElementContainer, lockedFigureColors, lockedFigureFillStyles, InteractiveGraphWidget, globalStyles, globalConstants, MatrixWidget, PlotterWidget, plotterPlotTypes, BaseRadio, TableWidget, displaySigFigs, widgets } from '@khanacademy/perseus';
2
+ import { constants, components, Widgets, icons, WIDGET_PROP_DENYLIST, Util, Log, PerseusMarkdown, preprocessTex, ApiOptions, buildMapper, itemToTree, buildEmptyItemTreeForShape, shapes, ItemExtras, itemDataVersion, ClassNames, MultiItems, traverse, Categorizer as Categorizer$1, Changeable, EditorJsonify, Dependencies, WidgetJsonifyDeprecated, PerseusExpressionAnswerFormConsidered, Expression, interactiveSizes, KhanMath, GrapherWidget, GrapherUtil, SizingUtils, PerseusI18nContext, KhanColors, ColorPicker, DashPicker, ArrowPicker, ElementContainer, lockedFigureColors, lockedFigureFillStyles, getLineCoords, InteractiveGraphWidget, globalStyles, globalConstants, MatrixWidget, PlotterWidget, plotterPlotTypes, BaseRadio, TableWidget, displaySigFigs, widgets } from '@khanacademy/perseus';
3
3
  import * as React from 'react';
4
4
  import { useRef, useEffect } from 'react';
5
5
  import _ from 'underscore';
@@ -20,7 +20,7 @@ import { isTruthy, UnreachableCaseError } from '@khanacademy/wonder-stuff-core';
20
20
  import { useMathInputI18n, createMathField } from '@khanacademy/math-input';
21
21
  import { ActionMenu, ActionItem, SingleSelect, OptionItem } from '@khanacademy/wonder-blocks-dropdown';
22
22
  import { TextField, Checkbox as Checkbox$1 } from '@khanacademy/wonder-blocks-form';
23
- import { LabelSmall, LabelMedium, LabelLarge, BodyMonospace } from '@khanacademy/wonder-blocks-typography';
23
+ import { LabelSmall, LabelLarge, LabelMedium, LabelXSmall, BodyMonospace } from '@khanacademy/wonder-blocks-typography';
24
24
  import Button from '@khanacademy/wonder-blocks-button';
25
25
  import { AccordionSection } from '@khanacademy/wonder-blocks-accordion';
26
26
  import IconButton from '@khanacademy/wonder-blocks-icon-button';
@@ -33,10 +33,11 @@ import Switch from '@khanacademy/wonder-blocks-switch';
33
33
  import minusCircle from '@phosphor-icons/core/regular/minus-circle.svg';
34
34
  import plusCircle from '@phosphor-icons/core/regular/plus-circle.svg';
35
35
  import Banner from '@khanacademy/wonder-blocks-banner';
36
+ import arrowCounterClockwise from '@phosphor-icons/core/bold/arrow-counter-clockwise-bold.svg';
36
37
 
37
38
  // This file is processed by a Rollup plugin (replace) to inject the production
38
39
  const libName = "@khanacademy/perseus-editor";
39
- const libVersion = "8.0.0";
40
+ const libVersion = "8.2.0";
40
41
  addLibraryVersionToPerseusDebug(libName, libVersion);
41
42
 
42
43
  function _extends() {
@@ -226,7 +227,7 @@ class SectionControlButton extends React.Component {
226
227
  role: "button",
227
228
  hideDefaultFocusRing: true,
228
229
  "aria-label": title,
229
- style: styles$G.button
230
+ style: styles$H.button
230
231
  }, ({
231
232
  hovered,
232
233
  focused,
@@ -234,7 +235,7 @@ class SectionControlButton extends React.Component {
234
235
  }) => /*#__PURE__*/React.createElement(InlineIcon$b, icon));
235
236
  }
236
237
  }
237
- const styles$G = StyleSheet.create({
238
+ const styles$H = StyleSheet.create({
238
239
  button: {
239
240
  backgroundColor: color.gold,
240
241
  margin: 2,
@@ -20739,13 +20740,13 @@ class WidgetSelect extends React.Component {
20739
20740
  * that collapse a region.
20740
20741
  */
20741
20742
  function ToggleableCaret(props) {
20742
- const iconStyle = props.isExpanded ? styles$F.expanded : styles$F.collapsed;
20743
+ const iconStyle = props.isExpanded ? styles$G.expanded : styles$G.collapsed;
20743
20744
  return /*#__PURE__*/React.createElement(PhosphorIcon, {
20744
20745
  icon: caretRight,
20745
20746
  style: iconStyle
20746
20747
  });
20747
20748
  }
20748
- const styles$F = StyleSheet.create({
20749
+ const styles$G = StyleSheet.create({
20749
20750
  collapsed: {
20750
20751
  transition: ".15s"
20751
20752
  },
@@ -20778,16 +20779,16 @@ class TexErrorView extends React.Component {
20778
20779
  showErrors
20779
20780
  } = this.state;
20780
20781
  return /*#__PURE__*/React.createElement(View, {
20781
- style: styles$E.errorContainer
20782
+ style: styles$F.errorContainer
20782
20783
  }, /*#__PURE__*/React.createElement(View, {
20783
- style: styles$E.title,
20784
+ style: styles$F.title,
20784
20785
  onClick: this.handleToggleTexErrors
20785
20786
  }, /*#__PURE__*/React.createElement(ToggleableCaret, {
20786
20787
  isExpanded: showErrors
20787
20788
  }), "\xA0 TeX Errors (", errorList.length, ")"), showErrors && /*#__PURE__*/React.createElement(View, {
20788
- style: styles$E.errorExplanation
20789
+ style: styles$F.errorExplanation
20789
20790
  }, "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, {
20790
- style: styles$E.error,
20791
+ style: styles$F.error,
20791
20792
  key: index
20792
20793
  }, /*#__PURE__*/React.createElement(View, {
20793
20794
  style: {
@@ -20796,7 +20797,7 @@ class TexErrorView extends React.Component {
20796
20797
  }, e.math), /*#__PURE__*/React.createElement(View, null, e.message))));
20797
20798
  }
20798
20799
  }
20799
- const styles$E = StyleSheet.create({
20800
+ const styles$F = StyleSheet.create({
20800
20801
  title: {
20801
20802
  backgroundColor: "#eee",
20802
20803
  fontSize: "1.25em",
@@ -24590,7 +24591,7 @@ class SimpleButton extends React.Component {
24590
24591
  } = _this$props,
24591
24592
  otherProps = _objectWithoutPropertiesLoose(_this$props, _excluded$3);
24592
24593
  return /*#__PURE__*/React.createElement("div", _extends({
24593
- className: css(styles$D.baseButton, color === "green" && styles$D.green, color === "orange" && styles$D.orange),
24594
+ className: css(styles$E.baseButton, color === "green" && styles$E.green, color === "orange" && styles$E.orange),
24594
24595
  onClick: onClick
24595
24596
  }, otherProps), children);
24596
24597
  }
@@ -24605,7 +24606,7 @@ SimpleButton.defaultProps = {
24605
24606
  color: "green",
24606
24607
  onClick: () => {}
24607
24608
  };
24608
- const styles$D = StyleSheet.create({
24609
+ const styles$E = StyleSheet.create({
24609
24610
  baseButton: {
24610
24611
  top: "0",
24611
24612
  fontSize: "11px",
@@ -24825,23 +24826,23 @@ const LeafContainer = ({
24825
24826
  }) => {
24826
24827
  const hasPreviewHeading = shape.type === "content" || shape.type === "hint";
24827
24828
  const previewHeading = hasPreviewHeading && /*#__PURE__*/React.createElement("div", {
24828
- className: css(styles$C.containerHeader)
24829
+ className: css(styles$D.containerHeader)
24829
24830
  }, /*#__PURE__*/React.createElement(Header, {
24830
24831
  depth: path.length,
24831
- className: css(styles$C.containerTitle)
24832
+ className: css(styles$D.containerTitle)
24832
24833
  }, capitalize(name)));
24833
24834
  return /*#__PURE__*/React.createElement("div", {
24834
- className: css(styles$C.container)
24835
+ className: css(styles$D.container)
24835
24836
  }, /*#__PURE__*/React.createElement("span", {
24836
- className: css(styles$C.row, styles$C.rowHeading)
24837
+ className: css(styles$D.row, styles$D.rowHeading)
24837
24838
  }, /*#__PURE__*/React.createElement("div", {
24838
- className: css(styles$C.columnLeft)
24839
+ className: css(styles$D.columnLeft)
24839
24840
  }, /*#__PURE__*/React.createElement("div", {
24840
- className: "pod-title " + css(styles$C.containerHeader)
24841
+ className: "pod-title " + css(styles$D.containerHeader)
24841
24842
  }, /*#__PURE__*/React.createElement("div", {
24842
- className: css(styles$C.containerTitle)
24843
+ className: css(styles$D.containerTitle)
24843
24844
  }, capitalize(name)), controls)), /*#__PURE__*/React.createElement("div", {
24844
- className: css(styles$C.columnRight)
24845
+ className: css(styles$D.columnRight)
24845
24846
  }, previewHeading)), children);
24846
24847
  };
24847
24848
  const ArrayContainer = props => {
@@ -24854,11 +24855,11 @@ const ArrayContainer = props => {
24854
24855
  actions
24855
24856
  } = props;
24856
24857
  return /*#__PURE__*/React.createElement("div", {
24857
- className: css(styles$C.container)
24858
+ className: css(styles$D.container)
24858
24859
  }, controls && /*#__PURE__*/React.createElement("div", {
24859
- className: css(styles$C.columnLeft, styles$C.containerHeader)
24860
+ className: css(styles$D.columnLeft, styles$D.containerHeader)
24860
24861
  }, controls), /*#__PURE__*/React.createElement("div", null, children), /*#__PURE__*/React.createElement("div", {
24861
- className: css(styles$C.columnLeft)
24862
+ className: css(styles$D.columnLeft)
24862
24863
  }, /*#__PURE__*/React.createElement("a", {
24863
24864
  href: "javascript:void 0",
24864
24865
  onClick: () => actions.addArrayElement(path, shape.elementShape)
@@ -24871,28 +24872,28 @@ const ObjectContainer = ({
24871
24872
  path
24872
24873
  }) => {
24873
24874
  const headingEditor = /*#__PURE__*/React.createElement("div", {
24874
- className: css(styles$C.containerHeader)
24875
+ className: css(styles$D.containerHeader)
24875
24876
  }, /*#__PURE__*/React.createElement(Header, {
24876
24877
  depth: path.length,
24877
- className: css(styles$C.containerTitle)
24878
+ className: css(styles$D.containerTitle)
24878
24879
  }, capitalize(name)), controls);
24879
24880
  const headingPreview = (name || controls) && /*#__PURE__*/React.createElement("div", {
24880
- className: css(styles$C.containerHeader, styles$C.previewCollectionHeader)
24881
+ className: css(styles$D.containerHeader, styles$D.previewCollectionHeader)
24881
24882
  }, /*#__PURE__*/React.createElement(Header, {
24882
24883
  depth: path.length,
24883
- className: css(styles$C.containerTitle)
24884
+ className: css(styles$D.containerTitle)
24884
24885
  }, capitalize(name)));
24885
24886
  const hasBothHeadings = headingEditor && headingPreview;
24886
24887
  return /*#__PURE__*/React.createElement("div", {
24887
- className: css(styles$C.container)
24888
+ className: css(styles$D.container)
24888
24889
  }, hasBothHeadings && /*#__PURE__*/React.createElement("span", {
24889
- className: css(styles$C.row)
24890
+ className: css(styles$D.row)
24890
24891
  }, /*#__PURE__*/React.createElement("div", {
24891
- className: css(styles$C.columnLeft)
24892
+ className: css(styles$D.columnLeft)
24892
24893
  }, headingEditor), /*#__PURE__*/React.createElement("div", {
24893
- className: css(styles$C.columnRight)
24894
+ className: css(styles$D.columnRight)
24894
24895
  }, headingPreview)), /*#__PURE__*/React.createElement("div", {
24895
- className: css(path.length > 0 && styles$C.contentIndent)
24896
+ className: css(path.length > 0 && styles$D.contentIndent)
24896
24897
  }, children));
24897
24898
  };
24898
24899
 
@@ -25015,11 +25016,11 @@ const ItemNodeContent = withStickiness(props => {
25015
25016
  className: "framework-perseus"
25016
25017
  }, lens(renderers).get(path));
25017
25018
  return /*#__PURE__*/React.createElement("span", null, /*#__PURE__*/React.createElement("div", {
25018
- className: css(styles$C.row)
25019
+ className: css(styles$D.row)
25019
25020
  }, /*#__PURE__*/React.createElement("div", {
25020
- className: css(styles$C.columnLeft)
25021
+ className: css(styles$D.columnLeft)
25021
25022
  }, /*#__PURE__*/React.createElement("div", {
25022
- className: css(sticky && styles$C.sticky)
25023
+ className: css(sticky && styles$D.sticky)
25023
25024
  },
25024
25025
  /*#__PURE__*/
25025
25026
  // @ts-expect-error - TS2769 - No overload matches this call.
@@ -25027,9 +25028,9 @@ const ItemNodeContent = withStickiness(props => {
25027
25028
  onChange: newVal => actions.mergeValueAtPath(path, newVal),
25028
25029
  apiOptions: apiOptions
25029
25030
  })))), /*#__PURE__*/React.createElement("div", {
25030
- className: css(styles$C.columnRight)
25031
+ className: css(styles$D.columnRight)
25031
25032
  }, /*#__PURE__*/React.createElement("div", {
25032
- className: css(sticky && styles$C.sticky)
25033
+ className: css(sticky && styles$D.sticky)
25033
25034
  }, preview))));
25034
25035
  });
25035
25036
  const HintNodeContent = withStickiness(props => {
@@ -25045,13 +25046,13 @@ const HintNodeContent = withStickiness(props => {
25045
25046
  className: "framework-perseus"
25046
25047
  }, lens(renderers).get(path));
25047
25048
  return /*#__PURE__*/React.createElement("div", {
25048
- className: css(styles$C.row)
25049
+ className: css(styles$D.row)
25049
25050
  }, /*#__PURE__*/React.createElement("div", {
25050
- className: css(styles$C.columnLeft)
25051
+ className: css(styles$D.columnLeft)
25051
25052
  }, /*#__PURE__*/React.createElement("div", {
25052
- className: css(sticky && styles$C.sticky)
25053
+ className: css(sticky && styles$D.sticky)
25053
25054
  }, /*#__PURE__*/React.createElement(HintEditor, _extends({}, data, {
25054
- className: css(styles$C.hintEditor),
25055
+ className: css(styles$D.hintEditor),
25055
25056
  onChange: newVal => actions.mergeValueAtPath(path, newVal),
25056
25057
  apiOptions: apiOptions,
25057
25058
  showTitle: false,
@@ -25066,9 +25067,9 @@ const HintNodeContent = withStickiness(props => {
25066
25067
  isFirst: true,
25067
25068
  isLast: true
25068
25069
  })))), /*#__PURE__*/React.createElement("div", {
25069
- className: css(styles$C.columnRight)
25070
+ className: css(styles$D.columnRight)
25070
25071
  }, /*#__PURE__*/React.createElement("div", {
25071
- className: css(sticky && styles$C.sticky)
25072
+ className: css(sticky && styles$D.sticky)
25072
25073
  }, preview)));
25073
25074
  });
25074
25075
  const TagsNodeContent = props => {
@@ -25085,9 +25086,9 @@ const TagsNodeContent = props => {
25085
25086
  return null;
25086
25087
  }
25087
25088
  return /*#__PURE__*/React.createElement("div", {
25088
- className: css(styles$C.columnLeft)
25089
+ className: css(styles$D.columnLeft)
25089
25090
  }, /*#__PURE__*/React.createElement("div", {
25090
- className: css(styles$C.tagsEditor)
25091
+ className: css(styles$D.tagsEditor)
25091
25092
  }, /*#__PURE__*/React.createElement(GroupMetadataEditor, {
25092
25093
  value: data,
25093
25094
  onChange: newVal => actions.setValueAtPath(path, newVal),
@@ -25118,23 +25119,23 @@ const ArrayNodeContent = props => {
25118
25119
  const subpath = path.concat(i);
25119
25120
  const controls = [i > 0 && /*#__PURE__*/React.createElement("div", {
25120
25121
  key: "moveArrayElementUp",
25121
- className: css(styles$C.control)
25122
+ className: css(styles$D.control)
25122
25123
  }, /*#__PURE__*/React.createElement(SimpleButton, {
25123
25124
  color: "orange",
25124
25125
  title: "Move up",
25125
25126
  onClick: () => actions.moveArrayElementUp(subpath)
25126
25127
  }, /*#__PURE__*/React.createElement("div", {
25127
- className: css(styles$C.verticalFlip)
25128
+ className: css(styles$D.verticalFlip)
25128
25129
  }, /*#__PURE__*/React.createElement(InlineIcon$6, iconChevronDown)))), i < data.length - 1 && /*#__PURE__*/React.createElement("div", {
25129
25130
  key: "moveArrayElementDown",
25130
- className: css(styles$C.control)
25131
+ className: css(styles$D.control)
25131
25132
  }, /*#__PURE__*/React.createElement(SimpleButton, {
25132
25133
  color: "orange",
25133
25134
  title: "Move down",
25134
25135
  onClick: () => actions.moveArrayElementDown(subpath)
25135
25136
  }, /*#__PURE__*/React.createElement(InlineIcon$6, iconChevronDown))), /*#__PURE__*/React.createElement("div", {
25136
25137
  key: "removeArrayElement",
25137
- className: css(styles$C.control)
25138
+ className: css(styles$D.control)
25138
25139
  }, /*#__PURE__*/React.createElement(SimpleButton, {
25139
25140
  color: "orange",
25140
25141
  title: "Delete",
@@ -25142,7 +25143,7 @@ const ArrayNodeContent = props => {
25142
25143
  }, /*#__PURE__*/React.createElement(InlineIcon$6, iconTrash$4)))];
25143
25144
  return /*#__PURE__*/React.createElement("div", {
25144
25145
  key: i,
25145
- className: css(styles$C.arrayElement, !elementIsLeaf && styles$C.arrayElementAndNotLeaf)
25146
+ className: css(styles$D.arrayElement, !elementIsLeaf && styles$D.arrayElementAndNotLeaf)
25146
25147
  }, /*#__PURE__*/React.createElement(NodeContainer, _extends({}, otherProps, {
25147
25148
  key: i,
25148
25149
  shape: shape.elementShape,
@@ -25168,7 +25169,7 @@ const ObjectNodeContent = props => {
25168
25169
  // made sense to the shape's author is the order in which we'll iterate :)
25169
25170
  const children = Object.keys(shape.shape).map(subkey => /*#__PURE__*/React.createElement("div", {
25170
25171
  key: subkey,
25171
- className: css(styles$C.objectElement)
25172
+ className: css(styles$D.objectElement)
25172
25173
  }, /*#__PURE__*/React.createElement(NodeContainer, _extends({}, otherProps, {
25173
25174
  shape: shape.shape[subkey],
25174
25175
  data: data[subkey],
@@ -25335,7 +25336,7 @@ class MultiRendererEditor extends React.Component {
25335
25336
  }, this._renderContent());
25336
25337
  }
25337
25338
  }
25338
- const styles$C = StyleSheet.create({
25339
+ const styles$D = StyleSheet.create({
25339
25340
  // This is used in a number of places throughout this file.
25340
25341
  container: {},
25341
25342
  // eslint-disable-next-line react-native/no-unused-styles
@@ -25487,47 +25488,47 @@ const StatefulArticleEditor = createReactClass({
25487
25488
  screen
25488
25489
  } = this.state;
25489
25490
  return /*#__PURE__*/React.createElement("div", null, /*#__PURE__*/React.createElement("div", {
25490
- style: styles$B.controlBar
25491
+ style: styles$C.controlBar
25491
25492
  }, /*#__PURE__*/React.createElement("span", {
25492
- style: styles$B.controls
25493
+ style: styles$C.controls
25493
25494
  }, "Mode:", " ", /*#__PURE__*/React.createElement("span", {
25494
25495
  onClick: () => this.setState({
25495
25496
  mode: "edit"
25496
25497
  }),
25497
- style: mode === "edit" ? styles$B.controlSelected : styles$B.control
25498
+ style: mode === "edit" ? styles$C.controlSelected : styles$C.control
25498
25499
  }, "EDIT"), " | ", /*#__PURE__*/React.createElement("span", {
25499
25500
  onClick: () => this.setState({
25500
25501
  mode: "preview"
25501
25502
  }),
25502
- style: mode === "preview" ? styles$B.controlSelected : styles$B.control
25503
+ style: mode === "preview" ? styles$C.controlSelected : styles$C.control
25503
25504
  }, "PREVIEW"), " | ", /*#__PURE__*/React.createElement("span", {
25504
25505
  onClick: () => this.setState({
25505
25506
  mode: "json"
25506
25507
  }),
25507
- style: mode === "json" ? styles$B.controlSelected : styles$B.control
25508
+ style: mode === "json" ? styles$C.controlSelected : styles$C.control
25508
25509
  }, "JSON")), /*#__PURE__*/React.createElement("span", {
25509
- style: styles$B.controls
25510
+ style: styles$C.controls
25510
25511
  }, "Screen:", " ", /*#__PURE__*/React.createElement("span", {
25511
25512
  onClick: () => this.setState({
25512
25513
  screen: "phone"
25513
25514
  }),
25514
- style: screen === "phone" ? styles$B.controlSelected : styles$B.control
25515
+ style: screen === "phone" ? styles$C.controlSelected : styles$C.control
25515
25516
  }, "PHONE"), " | ", /*#__PURE__*/React.createElement("span", {
25516
25517
  onClick: () => this.setState({
25517
25518
  screen: "tablet"
25518
25519
  }),
25519
- style: screen === "tablet" ? styles$B.controlSelected : styles$B.control
25520
+ style: screen === "tablet" ? styles$C.controlSelected : styles$C.control
25520
25521
  }, "TABLET"), " | ", /*#__PURE__*/React.createElement("span", {
25521
25522
  onClick: () => this.setState({
25522
25523
  screen: "desktop"
25523
25524
  }),
25524
- style: screen === "desktop" ? styles$B.controlSelected : styles$B.control
25525
+ style: screen === "desktop" ? styles$C.controlSelected : styles$C.control
25525
25526
  }, "DESKTOP"))), /*#__PURE__*/React.createElement("div", {
25526
- style: styles$B.editor
25527
+ style: styles$C.editor
25527
25528
  }, /*#__PURE__*/React.createElement(ArticleEditor, this.state)));
25528
25529
  }
25529
25530
  });
25530
- const styles$B = {
25531
+ const styles$C = {
25531
25532
  controlBar: {
25532
25533
  marginBottom: 25,
25533
25534
  marginTop: 5
@@ -27017,10 +27018,10 @@ class GradedGroupEditor extends React.Component {
27017
27018
  }, /*#__PURE__*/React.createElement("div", {
27018
27019
  className: "perseus-widget-row"
27019
27020
  }, /*#__PURE__*/React.createElement("label", {
27020
- className: css(styles$A.title)
27021
+ className: css(styles$B.title)
27021
27022
  }, "Title:", " ", /*#__PURE__*/React.createElement(TextInput$6, {
27022
27023
  value: this.props.title,
27023
- className: css(styles$A.input)
27024
+ className: css(styles$B.input)
27024
27025
  // @ts-expect-error - TS2554 - Expected 3 arguments, but got 1.
27025
27026
  ,
27026
27027
  onChange: this.change("title")
@@ -27045,7 +27046,7 @@ class GradedGroupEditor extends React.Component {
27045
27046
  }, /*#__PURE__*/React.createElement(InlineIcon$4, iconPlus$1), " Add a hint"), this.props.hint && /*#__PURE__*/React.createElement("div", {
27046
27047
  className: "perseus-hint-editor"
27047
27048
  }, /*#__PURE__*/React.createElement("div", {
27048
- className: css(styles$A.hintsTitle)
27049
+ className: css(styles$B.hintsTitle)
27049
27050
  }, "Hint"), /*#__PURE__*/React.createElement(Editor, {
27050
27051
  ref: this.hintEditor,
27051
27052
  content: this.props.hint ? this.props.hint.content : "",
@@ -27082,7 +27083,7 @@ GradedGroupEditor.defaultProps = {
27082
27083
  images: {},
27083
27084
  hint: null
27084
27085
  };
27085
- const styles$A = StyleSheet.create({
27086
+ const styles$B = StyleSheet.create({
27086
27087
  title: {
27087
27088
  fontSize: 18,
27088
27089
  fontWeight: "bold"
@@ -28421,13 +28422,13 @@ function MathquillInput(props) {
28421
28422
  }
28422
28423
  });
28423
28424
  return /*#__PURE__*/React.createElement(View, {
28424
- style: styles$z.outerWrapper
28425
+ style: styles$A.outerWrapper
28425
28426
  }, /*#__PURE__*/React.createElement("span", {
28426
28427
  ref: mathFieldWrapperRef,
28427
28428
  className: "perseus-math-input mq-editable-field mq-math-mode"
28428
28429
  }));
28429
28430
  }
28430
- const styles$z = StyleSheet.create({
28431
+ const styles$A = StyleSheet.create({
28431
28432
  outerWrapper: {
28432
28433
  display: "inline-block",
28433
28434
  borderStyle: "solid",
@@ -29473,16 +29474,16 @@ const LabeledRow = props => {
29473
29474
  style
29474
29475
  } = props;
29475
29476
  return /*#__PURE__*/React.createElement("label", {
29476
- className: css(styles$y.label)
29477
+ className: css(styles$z.label)
29477
29478
  }, /*#__PURE__*/React.createElement(View, {
29478
- style: [styles$y.row, style]
29479
+ style: [styles$z.row, style]
29479
29480
  }, labelSide === "start" || /*#__PURE__*/React.createElement(LabelSmall, {
29480
- style: styles$y.spaceEnd
29481
+ style: styles$z.spaceEnd
29481
29482
  }, label), children, labelSide === "end" && /*#__PURE__*/React.createElement(LabelSmall, {
29482
- style: styles$y.spaceStart
29483
+ style: styles$z.spaceStart
29483
29484
  }, label)));
29484
29485
  };
29485
- const styles$y = StyleSheet.create({
29486
+ const styles$z = StyleSheet.create({
29486
29487
  label: {
29487
29488
  width: "fit-content"
29488
29489
  },
@@ -29559,11 +29560,11 @@ class Spring extends React.Component {
29559
29560
  } = this.props;
29560
29561
  return React.createElement(View, {
29561
29562
  "aria-hidden": "true",
29562
- style: [styles$x.grow, style]
29563
+ style: [styles$y.grow, style]
29563
29564
  });
29564
29565
  }
29565
29566
  }
29566
- const styles$x = StyleSheet.create({
29567
+ const styles$y = StyleSheet.create({
29567
29568
  grow: {
29568
29569
  flexGrow: 1
29569
29570
  }
@@ -29592,6 +29593,38 @@ const strutStyle = size => {
29592
29593
  };
29593
29594
  };
29594
29595
 
29596
+ function Heading({
29597
+ title,
29598
+ isOpen,
29599
+ isCollapsible,
29600
+ onToggle
29601
+ }) {
29602
+ return /*#__PURE__*/React.createElement(View, {
29603
+ style: {
29604
+ flexDirection: "row",
29605
+ justifyContent: "space-between",
29606
+ backgroundColor: color.offBlack8,
29607
+ padding: spacing.xSmall_8,
29608
+ marginTop: spacing.small_12,
29609
+ // NOTE(jeremy): This is the inverse of the @editorPadding CSS
29610
+ // variable found in perseus-editor.less. For now, it must
29611
+ // match otherwise there's a gap from this header to the edge
29612
+ // of the editor borders.
29613
+ marginInline: -10,
29614
+ cursor: isCollapsible ? "pointer" : "default",
29615
+ userSelect: "none"
29616
+ },
29617
+ onClick: () => isCollapsible && (onToggle == null ? void 0 : onToggle(!isOpen))
29618
+ }, /*#__PURE__*/React.createElement(LabelLarge, {
29619
+ style: {
29620
+ fontSize: 14,
29621
+ fontWeight: 600
29622
+ }
29623
+ }, title), isCollapsible && /*#__PURE__*/React.createElement(ToggleableCaret, {
29624
+ isExpanded: isOpen
29625
+ }));
29626
+ }
29627
+
29595
29628
  function focusWithChromeStickyFocusBugWorkaround(element) {
29596
29629
  // NOTE(marksandstrom) Chrome sticky focus bug.
29597
29630
  //
@@ -29712,17 +29745,17 @@ const LockedFigureSelect = props => {
29712
29745
  } = props;
29713
29746
  const figureTypes = props.showM2Features ? ["point", "line", "vector", "ellipse", "polygon"] : ["point", "line"];
29714
29747
  return /*#__PURE__*/React.createElement(View, {
29715
- style: styles$w.container
29748
+ style: styles$x.container
29716
29749
  }, /*#__PURE__*/React.createElement(ActionMenu, {
29717
29750
  menuText: "Add locked figure",
29718
- style: styles$w.addElementSelect
29751
+ style: styles$x.addElementSelect
29719
29752
  }, figureTypes.map(figureType => /*#__PURE__*/React.createElement(ActionItem, {
29720
29753
  key: `${id}-${figureType}`,
29721
29754
  label: figureType,
29722
29755
  onClick: () => onChange(figureType)
29723
29756
  }, figureType))));
29724
29757
  };
29725
- const styles$w = StyleSheet.create({
29758
+ const styles$x = StyleSheet.create({
29726
29759
  container: {
29727
29760
  marginTop: spacing.xSmall_8
29728
29761
  },
@@ -29753,19 +29786,19 @@ const AngleInput = props => {
29753
29786
  }
29754
29787
  return /*#__PURE__*/React.createElement(LabelMedium, {
29755
29788
  tag: "label",
29756
- style: styles$v.row
29789
+ style: styles$w.row
29757
29790
  }, "angle (degrees)", /*#__PURE__*/React.createElement(Strut, {
29758
29791
  size: spacing.xxSmall_6
29759
29792
  }), /*#__PURE__*/React.createElement(TextField, {
29760
29793
  type: "number",
29761
29794
  value: angleInput,
29762
29795
  onChange: handleAngleChange,
29763
- style: styles$v.textField
29796
+ style: styles$w.textField
29764
29797
  }), /*#__PURE__*/React.createElement(Strut, {
29765
29798
  size: spacing.xxSmall_6
29766
29799
  }));
29767
29800
  };
29768
- const styles$v = StyleSheet.create({
29801
+ const styles$w = StyleSheet.create({
29769
29802
  row: {
29770
29803
  display: "flex",
29771
29804
  flexDirection: "row",
@@ -29790,6 +29823,12 @@ const CoordinatePairInput = props => {
29790
29823
  const [coordState, setCoordState] = React.useState([
29791
29824
  // Using strings to make it easier to work with the text fields.
29792
29825
  coord[0].toString(), coord[1].toString()]);
29826
+
29827
+ // Update the local state when the props change. (Such as when the graph
29828
+ // type is changed, and the coordinates are reset.)
29829
+ React.useEffect(() => {
29830
+ setCoordState([coord[0].toString(), coord[1].toString()]);
29831
+ }, [coord]);
29793
29832
  function handleCoordChange(newValue, coordIndex) {
29794
29833
  // Update the local state (update the input field value).
29795
29834
  const newCoordState = [...coordState];
@@ -29808,32 +29847,32 @@ const CoordinatePairInput = props => {
29808
29847
  onChange(newCoords);
29809
29848
  }
29810
29849
  return /*#__PURE__*/React.createElement(View, {
29811
- style: [styles$u.row, style]
29850
+ style: [styles$v.row, style]
29812
29851
  }, /*#__PURE__*/React.createElement(LabelMedium, {
29813
29852
  tag: "label",
29814
- style: styles$u.row
29853
+ style: styles$v.row
29815
29854
  }, labels ? labels[0] : "x coord", /*#__PURE__*/React.createElement(Strut, {
29816
29855
  size: spacing.xxSmall_6
29817
29856
  }), /*#__PURE__*/React.createElement(TextField, {
29818
29857
  type: "number",
29819
29858
  value: coordState[0],
29820
29859
  onChange: newValue => handleCoordChange(newValue, 0),
29821
- style: [styles$u.textField, error ? styles$u.errorField : undefined]
29860
+ style: [styles$v.textField, error ? styles$v.errorField : undefined]
29822
29861
  })), /*#__PURE__*/React.createElement(Strut, {
29823
29862
  size: spacing.medium_16
29824
29863
  }), /*#__PURE__*/React.createElement(LabelMedium, {
29825
29864
  tag: "label",
29826
- style: styles$u.row
29865
+ style: styles$v.row
29827
29866
  }, labels ? labels[1] : "y coord", /*#__PURE__*/React.createElement(Strut, {
29828
29867
  size: spacing.xxSmall_6
29829
29868
  }), /*#__PURE__*/React.createElement(TextField, {
29830
29869
  type: "number",
29831
29870
  value: coordState[1],
29832
29871
  onChange: newValue => handleCoordChange(newValue, 1),
29833
- style: [styles$u.textField, error ? styles$u.errorField : undefined]
29872
+ style: [styles$v.textField, error ? styles$v.errorField : undefined]
29834
29873
  })));
29835
29874
  };
29836
- const styles$u = StyleSheet.create({
29875
+ const styles$v = StyleSheet.create({
29837
29876
  row: {
29838
29877
  display: "flex",
29839
29878
  flexDirection: "row",
@@ -29866,14 +29905,14 @@ const PerseusEditorAccordion = props => {
29866
29905
  }, /*#__PURE__*/React.createElement(AccordionSection, {
29867
29906
  expanded: expanded,
29868
29907
  onToggle: onToggle,
29869
- style: [styles$t.container, containerStyle],
29870
- headerStyle: styles$t.accordionHeader,
29908
+ style: [styles$u.container, containerStyle],
29909
+ headerStyle: styles$u.accordionHeader,
29871
29910
  header: header
29872
29911
  }, /*#__PURE__*/React.createElement(View, {
29873
- style: [styles$t.accordionPanel, panelStyle]
29912
+ style: [styles$u.accordionPanel, panelStyle]
29874
29913
  }, children)));
29875
29914
  };
29876
- const styles$t = StyleSheet.create({
29915
+ const styles$u = StyleSheet.create({
29877
29916
  container: {
29878
29917
  backgroundColor: color.fadedBlue8,
29879
29918
  marginTop: spacing.xSmall_8
@@ -29904,13 +29943,13 @@ const ColorSwatch = props => {
29904
29943
  "aria-label":
29905
29944
  // Don't include an aria label for decorative circles.
29906
29945
  !decorative ? `${color$1}, ${filled ? "filled" : "open"}` : undefined,
29907
- style: [styles$s.colorSwatch, {
29946
+ style: [styles$t.colorSwatch, {
29908
29947
  border: `4px solid ${lockedFigureColors[color$1]}`,
29909
29948
  backgroundColor: filled ? lockedFigureColors[color$1] : color.white
29910
29949
  }]
29911
29950
  });
29912
29951
  };
29913
- const styles$s = StyleSheet.create({
29952
+ const styles$t = StyleSheet.create({
29914
29953
  colorSwatch: {
29915
29954
  // Add a white outline so that the color swatch is visible when
29916
29955
  // the dropdown option is highlighted with its blue background.
@@ -29929,10 +29968,10 @@ const ColorSelect = props => {
29929
29968
  onChange
29930
29969
  } = props;
29931
29970
  return /*#__PURE__*/React.createElement(View, {
29932
- style: [styles$r.row, style]
29971
+ style: [styles$s.row, style]
29933
29972
  }, /*#__PURE__*/React.createElement(LabelMedium, {
29934
29973
  tag: "label",
29935
- style: styles$r.row
29974
+ style: styles$s.row
29936
29975
  }, "color", /*#__PURE__*/React.createElement(Strut, {
29937
29976
  size: spacing.xxSmall_6
29938
29977
  }), /*#__PURE__*/React.createElement(SingleSelect, {
@@ -29951,7 +29990,7 @@ const ColorSelect = props => {
29951
29990
  })
29952
29991
  }, colorName)))));
29953
29992
  };
29954
- const styles$r = StyleSheet.create({
29993
+ const styles$s = StyleSheet.create({
29955
29994
  row: {
29956
29995
  display: "flex",
29957
29996
  flexDirection: "row",
@@ -29967,17 +30006,17 @@ const EllipseSwatch = props => {
29967
30006
  } = props;
29968
30007
  return /*#__PURE__*/React.createElement(View, {
29969
30008
  "aria-label": `${color}, stroke ${strokeStyle}, fill ${fillStyle}`,
29970
- style: [styles$q.container, {
30009
+ style: [styles$r.container, {
29971
30010
  border: `4px ${strokeStyle} ${lockedFigureColors[color]}`
29972
30011
  }]
29973
30012
  }, /*#__PURE__*/React.createElement(View, {
29974
- style: [styles$q.innerCircle, {
30013
+ style: [styles$r.innerCircle, {
29975
30014
  backgroundColor: lockedFigureColors[color],
29976
30015
  opacity: lockedFigureFillStyles[fillStyle]
29977
30016
  }]
29978
30017
  }));
29979
30018
  };
29980
- const styles$q = StyleSheet.create({
30019
+ const styles$r = StyleSheet.create({
29981
30020
  container: {
29982
30021
  // Add a white outline so that the color swatch is visible when
29983
30022
  // the dropdown option is highlighted with its blue background.
@@ -30008,40 +30047,40 @@ const LockedFigureSettingsActions = props => {
30008
30047
  onRemove
30009
30048
  } = props;
30010
30049
  return /*#__PURE__*/React.createElement(View, {
30011
- style: styles$p.container
30050
+ style: styles$q.container
30012
30051
  }, /*#__PURE__*/React.createElement(Button, {
30013
30052
  startIcon: trashIcon,
30014
30053
  "aria-label": `Delete locked ${figureType}`,
30015
30054
  onClick: onRemove,
30016
30055
  kind: "tertiary",
30017
- style: styles$p.deleteButton
30056
+ style: styles$q.deleteButton
30018
30057
  }, "Delete"), /*#__PURE__*/React.createElement(Spring, null), props.showM2Features && /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(IconButton, {
30019
30058
  icon: caretDoubleUpIcon,
30020
30059
  size: "small",
30021
30060
  "aria-label": `Move locked ${figureType} to the back`,
30022
30061
  onClick: () => onMove("back"),
30023
- style: styles$p.iconButton
30062
+ style: styles$q.iconButton
30024
30063
  }), /*#__PURE__*/React.createElement(IconButton, {
30025
30064
  icon: caretUpIcon,
30026
30065
  size: "small",
30027
30066
  "aria-label": `Move locked ${figureType} backward`,
30028
30067
  onClick: () => onMove("backward"),
30029
- style: styles$p.iconButton
30068
+ style: styles$q.iconButton
30030
30069
  }), /*#__PURE__*/React.createElement(IconButton, {
30031
30070
  icon: caretDownIcon,
30032
30071
  size: "small",
30033
30072
  "aria-label": `Move locked ${figureType} forward`,
30034
30073
  onClick: () => onMove("forward"),
30035
- style: styles$p.iconButton
30074
+ style: styles$q.iconButton
30036
30075
  }), /*#__PURE__*/React.createElement(IconButton, {
30037
30076
  icon: caretDoubleDownIcon,
30038
30077
  size: "small",
30039
30078
  "aria-label": `Move locked ${figureType} to the front`,
30040
30079
  onClick: () => onMove("front"),
30041
- style: styles$p.iconButton
30080
+ style: styles$q.iconButton
30042
30081
  })));
30043
30082
  };
30044
- const styles$p = StyleSheet.create({
30083
+ const styles$q = StyleSheet.create({
30045
30084
  container: {
30046
30085
  width: "100%",
30047
30086
  flexDirection: "row",
@@ -30088,7 +30127,7 @@ const LockedEllipseSettings = props => {
30088
30127
  /*#__PURE__*/
30089
30128
  // Summary: Ellipse, center, radius, color (opacity, dashed)
30090
30129
  React.createElement(View, {
30091
- style: styles$o.row
30130
+ style: styles$p.row
30092
30131
  }, /*#__PURE__*/React.createElement(LabelLarge, null, `Ellipse (${center[0]}, ${center[1]}), radius ${radius[0]}, ${radius[1]}`), /*#__PURE__*/React.createElement(Strut, {
30093
30132
  size: spacing.xSmall_8
30094
30133
  }), /*#__PURE__*/React.createElement(EllipseSwatch, {
@@ -30097,19 +30136,19 @@ const LockedEllipseSettings = props => {
30097
30136
  strokeStyle: strokeStyle
30098
30137
  }))
30099
30138
  }, /*#__PURE__*/React.createElement(View, {
30100
- style: styles$o.row
30139
+ style: styles$p.row
30101
30140
  }, /*#__PURE__*/React.createElement(CoordinatePairInput, {
30102
30141
  coord: center,
30103
- style: styles$o.spaceUnder,
30142
+ style: styles$p.spaceUnder,
30104
30143
  onChange: newCoords => onChangeProps({
30105
30144
  center: newCoords
30106
30145
  })
30107
30146
  }), /*#__PURE__*/React.createElement(View, {
30108
- style: styles$o.spaceUnder
30147
+ style: styles$p.spaceUnder
30109
30148
  }, /*#__PURE__*/React.createElement(InfoTip$d, null, "The coordinates for the center of the ellipse."))), /*#__PURE__*/React.createElement(CoordinatePairInput, {
30110
30149
  coord: radius,
30111
30150
  labels: ["x radius", "y radius"],
30112
- style: styles$o.spaceUnder,
30151
+ style: styles$p.spaceUnder,
30113
30152
  onChange: newCoords => onChangeProps({
30114
30153
  radius: newCoords
30115
30154
  })
@@ -30121,7 +30160,7 @@ const LockedEllipseSettings = props => {
30121
30160
  }), /*#__PURE__*/React.createElement(Strut, {
30122
30161
  size: spacing.xSmall_8
30123
30162
  }), /*#__PURE__*/React.createElement(View, {
30124
- style: [styles$o.row, styles$o.spaceUnder]
30163
+ style: [styles$p.row, styles$p.spaceUnder]
30125
30164
  }, /*#__PURE__*/React.createElement(ColorSelect, {
30126
30165
  selectedValue: color,
30127
30166
  onChange: handleColorChange
@@ -30129,7 +30168,7 @@ const LockedEllipseSettings = props => {
30129
30168
  size: spacing.medium_16
30130
30169
  }), /*#__PURE__*/React.createElement(LabelMedium, {
30131
30170
  tag: "label",
30132
- style: styles$o.row
30171
+ style: styles$p.row
30133
30172
  }, "fill", /*#__PURE__*/React.createElement(Strut, {
30134
30173
  size: spacing.xxSmall_6
30135
30174
  }), /*#__PURE__*/React.createElement(SingleSelect, {
@@ -30146,7 +30185,7 @@ const LockedEllipseSettings = props => {
30146
30185
  label: option
30147
30186
  }, option))))), /*#__PURE__*/React.createElement(LabelMedium, {
30148
30187
  tag: "label",
30149
- style: styles$o.row
30188
+ style: styles$p.row
30150
30189
  }, "stroke", /*#__PURE__*/React.createElement(Strut, {
30151
30190
  size: spacing.xxSmall_6
30152
30191
  }), /*#__PURE__*/React.createElement(SingleSelect, {
@@ -30170,7 +30209,7 @@ const LockedEllipseSettings = props => {
30170
30209
  onRemove: onRemove
30171
30210
  }));
30172
30211
  };
30173
- const styles$o = StyleSheet.create({
30212
+ const styles$p = StyleSheet.create({
30174
30213
  row: {
30175
30214
  display: "flex",
30176
30215
  flexDirection: "row",
@@ -30191,7 +30230,7 @@ const LabeledSwitch = props => {
30191
30230
  const ids = useUniqueIdWithMock();
30192
30231
  const switchId = ids.get("switch");
30193
30232
  return /*#__PURE__*/React.createElement(View, {
30194
- style: [styles$n.row, style]
30233
+ style: [styles$o.row, style]
30195
30234
  }, /*#__PURE__*/React.createElement(Switch, {
30196
30235
  id: switchId,
30197
30236
  checked: checked,
@@ -30203,7 +30242,7 @@ const LabeledSwitch = props => {
30203
30242
  htmlFor: switchId
30204
30243
  }, label));
30205
30244
  };
30206
- const styles$n = StyleSheet.create({
30245
+ const styles$o = StyleSheet.create({
30207
30246
  row: {
30208
30247
  flexDirection: "row",
30209
30248
  alignItems: "center"
@@ -30237,13 +30276,13 @@ const DefiningPointSettings = props => {
30237
30276
  return /*#__PURE__*/React.createElement(PerseusEditorAccordion, {
30238
30277
  expanded: expanded,
30239
30278
  onToggle: onToggle,
30240
- containerStyle: styles$m.container,
30241
- panelStyle: styles$m.accordionPanel,
30279
+ containerStyle: styles$n.container,
30280
+ panelStyle: styles$n.accordionPanel,
30242
30281
  header:
30243
30282
  /*#__PURE__*/
30244
30283
  // Summary: Point, coords, color (filled/open)
30245
30284
  React.createElement(View, {
30246
- style: styles$m.row
30285
+ style: styles$n.row
30247
30286
  }, /*#__PURE__*/React.createElement(LabelLarge, null, `${label || "Point"} (${coord[0]}, ${coord[1]})`), /*#__PURE__*/React.createElement(Strut, {
30248
30287
  size: spacing.xSmall_8
30249
30288
  }), showPoint && /*#__PURE__*/React.createElement(ColorSwatch, {
@@ -30253,7 +30292,7 @@ const DefiningPointSettings = props => {
30253
30292
  }, /*#__PURE__*/React.createElement(CoordinatePairInput, {
30254
30293
  coord: coord,
30255
30294
  error: !!error,
30256
- style: styles$m.spaceUnder,
30295
+ style: styles$n.spaceUnder,
30257
30296
  onChange: newCoords => {
30258
30297
  onChangeProps({
30259
30298
  coord: newCoords
@@ -30262,12 +30301,12 @@ const DefiningPointSettings = props => {
30262
30301
  }), onTogglePoint && /*#__PURE__*/React.createElement(LabeledSwitch, {
30263
30302
  label: "show point on graph",
30264
30303
  checked: !!showPoint,
30265
- style: showPoint && styles$m.spaceUnder,
30304
+ style: showPoint && styles$n.spaceUnder,
30266
30305
  onChange: onTogglePoint
30267
30306
  }), showPoint && /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(ColorSelect, {
30268
30307
  selectedValue: pointColor,
30269
30308
  onChange: handleColorChange,
30270
- style: styles$m.spaceUnder
30309
+ style: styles$n.spaceUnder
30271
30310
  }), /*#__PURE__*/React.createElement(LabeledSwitch, {
30272
30311
  label: "open point",
30273
30312
  checked: !filled,
@@ -30278,7 +30317,7 @@ const DefiningPointSettings = props => {
30278
30317
  }
30279
30318
  })));
30280
30319
  };
30281
- const styles$m = StyleSheet.create({
30320
+ const styles$n = StyleSheet.create({
30282
30321
  container: {
30283
30322
  marginTop: spacing.xSmall_8,
30284
30323
  marginBottom: 0,
@@ -30305,15 +30344,15 @@ const LineSwatch = props => {
30305
30344
  lineStyle
30306
30345
  } = props;
30307
30346
  return /*#__PURE__*/React.createElement(View, {
30308
- style: styles$l.container
30347
+ style: styles$m.container
30309
30348
  }, /*#__PURE__*/React.createElement(View, {
30310
30349
  "aria-label": `${color}, ${lineStyle}`,
30311
- style: [styles$l.lineSwatch, {
30350
+ style: [styles$m.lineSwatch, {
30312
30351
  border: `5px ${lineStyle} ${lockedFigureColors[color]}`
30313
30352
  }]
30314
30353
  }));
30315
30354
  };
30316
- const styles$l = StyleSheet.create({
30355
+ const styles$m = StyleSheet.create({
30317
30356
  container: {
30318
30357
  backgroundColor: color.white,
30319
30358
  justifyContent: "center",
@@ -30367,7 +30406,7 @@ const LockedLineSettings = props => {
30367
30406
  expanded: props.expanded,
30368
30407
  onToggle: props.onToggle,
30369
30408
  header: /*#__PURE__*/React.createElement(View, {
30370
- style: styles$k.row
30409
+ style: styles$l.row
30371
30410
  }, /*#__PURE__*/React.createElement(LabelLarge, null, lineLabel), /*#__PURE__*/React.createElement(Strut, {
30372
30411
  size: spacing.xSmall_8
30373
30412
  }), /*#__PURE__*/React.createElement(LineSwatch, {
@@ -30376,7 +30415,7 @@ const LockedLineSettings = props => {
30376
30415
  }))
30377
30416
  }, /*#__PURE__*/React.createElement(LabelMedium, {
30378
30417
  tag: "label",
30379
- style: [styles$k.row, styles$k.spaceUnder]
30418
+ style: [styles$l.row, styles$l.spaceUnder]
30380
30419
  }, "kind", /*#__PURE__*/React.createElement(Strut, {
30381
30420
  size: spacing.xxxSmall_4
30382
30421
  }), /*#__PURE__*/React.createElement(SingleSelect, {
@@ -30397,7 +30436,7 @@ const LockedLineSettings = props => {
30397
30436
  value: "segment",
30398
30437
  label: "segment"
30399
30438
  }))), /*#__PURE__*/React.createElement(View, {
30400
- style: styles$k.row
30439
+ style: styles$l.row
30401
30440
  }, /*#__PURE__*/React.createElement(ColorSelect, {
30402
30441
  selectedValue: lineColor,
30403
30442
  onChange: handleColorChange
@@ -30405,7 +30444,7 @@ const LockedLineSettings = props => {
30405
30444
  size: spacing.small_12
30406
30445
  }), /*#__PURE__*/React.createElement(LabelMedium, {
30407
30446
  tag: "label",
30408
- style: styles$k.row
30447
+ style: styles$l.row
30409
30448
  }, "style", /*#__PURE__*/React.createElement(Strut, {
30410
30449
  size: spacing.xxxSmall_4
30411
30450
  }), /*#__PURE__*/React.createElement(SingleSelect, {
@@ -30416,7 +30455,7 @@ const LockedLineSettings = props => {
30416
30455
  // Placeholder is required, but never gets used.
30417
30456
  ,
30418
30457
  placeholder: "",
30419
- style: styles$k.selectMarginOffset
30458
+ style: styles$l.selectMarginOffset
30420
30459
  }, /*#__PURE__*/React.createElement(OptionItem, {
30421
30460
  value: "solid",
30422
30461
  label: "solid"
@@ -30424,7 +30463,7 @@ const LockedLineSettings = props => {
30424
30463
  value: "dashed",
30425
30464
  label: "dashed"
30426
30465
  })))), isInvalid && /*#__PURE__*/React.createElement(LabelMedium, {
30427
- style: styles$k.errorText
30466
+ style: styles$l.errorText
30428
30467
  }, lengthZeroStr), /*#__PURE__*/React.createElement(DefiningPointSettings, _extends({
30429
30468
  label: "Point 1",
30430
30469
  showPoint: showPoint1,
@@ -30450,7 +30489,7 @@ const LockedLineSettings = props => {
30450
30489
  onRemove: onRemove
30451
30490
  }));
30452
30491
  };
30453
- const styles$k = StyleSheet.create({
30492
+ const styles$l = StyleSheet.create({
30454
30493
  row: {
30455
30494
  display: "flex",
30456
30495
  flexDirection: "row",
@@ -30495,7 +30534,7 @@ const LockedPointSettings = props => {
30495
30534
  /*#__PURE__*/
30496
30535
  // Summary: Point, coords, color (filled/open)
30497
30536
  React.createElement(View, {
30498
- style: styles$j.row
30537
+ style: styles$k.row
30499
30538
  }, /*#__PURE__*/React.createElement(LabelLarge, null, `Point (${coord[0]}, ${coord[1]})`), /*#__PURE__*/React.createElement(Strut, {
30500
30539
  size: spacing.xSmall_8
30501
30540
  }), /*#__PURE__*/React.createElement(ColorSwatch, {
@@ -30504,7 +30543,7 @@ const LockedPointSettings = props => {
30504
30543
  }))
30505
30544
  }, /*#__PURE__*/React.createElement(CoordinatePairInput, {
30506
30545
  coord: coord,
30507
- style: styles$j.spaceUnder,
30546
+ style: styles$k.spaceUnder,
30508
30547
  onChange: newCoord => {
30509
30548
  onChangeProps({
30510
30549
  coord: newCoord
@@ -30513,7 +30552,7 @@ const LockedPointSettings = props => {
30513
30552
  }), /*#__PURE__*/React.createElement(ColorSelect, {
30514
30553
  selectedValue: pointColor,
30515
30554
  onChange: handleColorChange,
30516
- style: styles$j.spaceUnder
30555
+ style: styles$k.spaceUnder
30517
30556
  }), /*#__PURE__*/React.createElement(LabeledSwitch, {
30518
30557
  label: "open point",
30519
30558
  checked: !filled,
@@ -30529,7 +30568,7 @@ const LockedPointSettings = props => {
30529
30568
  onRemove: onRemove
30530
30569
  }));
30531
30570
  };
30532
- const styles$j = StyleSheet.create({
30571
+ const styles$k = StyleSheet.create({
30533
30572
  row: {
30534
30573
  flexDirection: "row",
30535
30574
  alignItems: "center"
@@ -30547,17 +30586,17 @@ const PolygonSwatch = props => {
30547
30586
  } = props;
30548
30587
  return /*#__PURE__*/React.createElement(View, {
30549
30588
  "aria-label": `${color}, stroke ${strokeStyle}, fill ${fillStyle}`,
30550
- style: [styles$i.container, {
30589
+ style: [styles$j.container, {
30551
30590
  border: `4px ${strokeStyle} ${lockedFigureColors[color]}`
30552
30591
  }]
30553
30592
  }, /*#__PURE__*/React.createElement(View, {
30554
- style: [styles$i.innerSquare, {
30593
+ style: [styles$j.innerSquare, {
30555
30594
  backgroundColor: lockedFigureColors[color],
30556
30595
  opacity: lockedFigureFillStyles[fillStyle]
30557
30596
  }]
30558
30597
  }));
30559
30598
  };
30560
- const styles$i = StyleSheet.create({
30599
+ const styles$j = StyleSheet.create({
30561
30600
  container: {
30562
30601
  // Add a white outline so that the color swatch is visible when
30563
30602
  // the dropdown option is highlighted with its blue background.
@@ -30599,7 +30638,7 @@ const LockedPolygonSettings = props => {
30599
30638
  /*#__PURE__*/
30600
30639
  // Summary: Polygon, number of sides, style swatch
30601
30640
  React.createElement(View, {
30602
- style: styles$h.row
30641
+ style: styles$i.row
30603
30642
  }, /*#__PURE__*/React.createElement(LabelLarge, null, `Polygon, ${points.length} sides`), /*#__PURE__*/React.createElement(Strut, {
30604
30643
  size: spacing.xSmall_8
30605
30644
  }), /*#__PURE__*/React.createElement(PolygonSwatch, {
@@ -30608,7 +30647,7 @@ const LockedPolygonSettings = props => {
30608
30647
  strokeStyle: strokeStyle
30609
30648
  }))
30610
30649
  }, /*#__PURE__*/React.createElement(View, {
30611
- style: [styles$h.row, styles$h.spaceUnder]
30650
+ style: [styles$i.row, styles$i.spaceUnder]
30612
30651
  }, /*#__PURE__*/React.createElement(ColorSelect, {
30613
30652
  selectedValue: color,
30614
30653
  onChange: handleColorChange
@@ -30616,7 +30655,7 @@ const LockedPolygonSettings = props => {
30616
30655
  size: spacing.medium_16
30617
30656
  }), /*#__PURE__*/React.createElement(LabelMedium, {
30618
30657
  tag: "label",
30619
- style: styles$h.row
30658
+ style: styles$i.row
30620
30659
  }, "fill", /*#__PURE__*/React.createElement(Strut, {
30621
30660
  size: spacing.xxSmall_6
30622
30661
  }), /*#__PURE__*/React.createElement(SingleSelect, {
@@ -30633,7 +30672,7 @@ const LockedPolygonSettings = props => {
30633
30672
  label: option
30634
30673
  }, option))))), /*#__PURE__*/React.createElement(LabelMedium, {
30635
30674
  tag: "label",
30636
- style: [styles$h.row, styles$h.spaceUnder]
30675
+ style: [styles$i.row, styles$i.spaceUnder]
30637
30676
  }, "stroke", /*#__PURE__*/React.createElement(Strut, {
30638
30677
  size: spacing.xxSmall_6
30639
30678
  }), /*#__PURE__*/React.createElement(SingleSelect, {
@@ -30656,17 +30695,17 @@ const LockedPolygonSettings = props => {
30656
30695
  onChange: newValue => onChangeProps({
30657
30696
  showVertices: newValue
30658
30697
  }),
30659
- style: styles$h.spaceUnder
30698
+ style: styles$i.spaceUnder
30660
30699
  }), /*#__PURE__*/React.createElement(PerseusEditorAccordion, {
30661
30700
  header: /*#__PURE__*/React.createElement(LabelLarge, null, "Points"),
30662
30701
  expanded: true,
30663
- containerStyle: styles$h.pointAccordionContainer,
30664
- panelStyle: styles$h.pointAccordionPanel
30702
+ containerStyle: styles$i.pointAccordionContainer,
30703
+ panelStyle: styles$i.pointAccordionPanel
30665
30704
  }, points.map((point, index) => {
30666
30705
  const pointLabel = String.fromCharCode(65 + index);
30667
30706
  return /*#__PURE__*/React.createElement(View, {
30668
30707
  key: `locked-polygon-point-${point[0]}-${point[1]}-index-${index}`,
30669
- style: [styles$h.row, styles$h.spaceUnder]
30708
+ style: [styles$i.row, styles$i.spaceUnder]
30670
30709
  }, /*#__PURE__*/React.createElement(LabelLarge, null, `${pointLabel}:`), /*#__PURE__*/React.createElement(Strut, {
30671
30710
  size: spacing.medium_16
30672
30711
  }), /*#__PURE__*/React.createElement(CoordinatePairInput, {
@@ -30694,7 +30733,7 @@ const LockedPolygonSettings = props => {
30694
30733
  points: newPoints
30695
30734
  });
30696
30735
  },
30697
- style: styles$h.icon
30736
+ style: styles$i.icon
30698
30737
  }));
30699
30738
  }), /*#__PURE__*/React.createElement(Button, {
30700
30739
  kind: "tertiary",
@@ -30711,7 +30750,7 @@ const LockedPolygonSettings = props => {
30711
30750
  onRemove: onRemove
30712
30751
  }));
30713
30752
  };
30714
- const styles$h = StyleSheet.create({
30753
+ const styles$i = StyleSheet.create({
30715
30754
  row: {
30716
30755
  display: "flex",
30717
30756
  flexDirection: "row",
@@ -30769,7 +30808,7 @@ const LockedVectorSettings = props => {
30769
30808
  expanded: props.expanded,
30770
30809
  onToggle: props.onToggle,
30771
30810
  header: /*#__PURE__*/React.createElement(View, {
30772
- style: styles$g.row
30811
+ style: styles$h.row
30773
30812
  }, /*#__PURE__*/React.createElement(LabelLarge, null, lineLabel), /*#__PURE__*/React.createElement(Strut, {
30774
30813
  size: spacing.xSmall_8
30775
30814
  }), /*#__PURE__*/React.createElement(LineSwatch, {
@@ -30777,19 +30816,19 @@ const LockedVectorSettings = props => {
30777
30816
  lineStyle: "solid"
30778
30817
  }))
30779
30818
  }, /*#__PURE__*/React.createElement(View, {
30780
- style: [styles$g.row, styles$g.spaceUnder]
30819
+ style: [styles$h.row, styles$h.spaceUnder]
30781
30820
  }, /*#__PURE__*/React.createElement(ColorSelect, {
30782
30821
  selectedValue: lineColor,
30783
30822
  onChange: handleColorChange
30784
30823
  })), isInvalid && /*#__PURE__*/React.createElement(LabelMedium, {
30785
- style: styles$g.errorText
30824
+ style: styles$h.errorText
30786
30825
  }, lengthErrorMessage), /*#__PURE__*/React.createElement(PerseusEditorAccordion, {
30787
30826
  expanded: true // Initial state is expanded
30788
30827
  ,
30789
- containerStyle: styles$g.container,
30790
- panelStyle: styles$g.accordionPanel,
30828
+ containerStyle: styles$h.container,
30829
+ panelStyle: styles$h.accordionPanel,
30791
30830
  header: /*#__PURE__*/React.createElement(View, {
30792
- style: styles$g.row
30831
+ style: styles$h.row
30793
30832
  }, /*#__PURE__*/React.createElement(LabelLarge, null, `Tail (${tail[0]}, ${tail[1]})`))
30794
30833
  }, /*#__PURE__*/React.createElement(CoordinatePairInput, {
30795
30834
  coord: tail,
@@ -30800,10 +30839,10 @@ const LockedVectorSettings = props => {
30800
30839
  })), /*#__PURE__*/React.createElement(PerseusEditorAccordion, {
30801
30840
  expanded: true // Initial state is expanded
30802
30841
  ,
30803
- containerStyle: styles$g.container,
30804
- panelStyle: styles$g.accordionPanel,
30842
+ containerStyle: styles$h.container,
30843
+ panelStyle: styles$h.accordionPanel,
30805
30844
  header: /*#__PURE__*/React.createElement(View, {
30806
- style: styles$g.row
30845
+ style: styles$h.row
30807
30846
  }, /*#__PURE__*/React.createElement(LabelLarge, null, `Tip (${tip[0]}, ${tip[1]})`))
30808
30847
  }, /*#__PURE__*/React.createElement(CoordinatePairInput, {
30809
30848
  coord: tip,
@@ -30818,7 +30857,7 @@ const LockedVectorSettings = props => {
30818
30857
  onRemove: onRemove
30819
30858
  }));
30820
30859
  };
30821
- const styles$g = StyleSheet.create({
30860
+ const styles$h = StyleSheet.create({
30822
30861
  accordionPanel: {
30823
30862
  paddingBottom: spacing.medium_16
30824
30863
  },
@@ -30878,6 +30917,7 @@ const LockedFiguresSection = props => {
30878
30917
  // expand/collapse all button. Set the whole array to false initially.
30879
30918
  const collapsedStateArray = Array(((_props$figures = props.figures) != null ? _props$figures : []).length).fill(false);
30880
30919
  const [expandedStates, setExpandedStates] = React.useState(collapsedStateArray);
30920
+ const [isExpanded, setIsExpanded] = React.useState(true);
30881
30921
  const uniqueId = useUniqueIdWithMock().get("locked-figures-section");
30882
30922
  const {
30883
30923
  figures,
@@ -30964,7 +31004,12 @@ const LockedFiguresSection = props => {
30964
31004
  const allCollapsed = expandedStates.every(value => !value);
30965
31005
  const buttonLabel = allCollapsed ? "Expand all" : "Collapse all";
30966
31006
  const showExpandButton = !!(figures != null && figures.length);
30967
- return /*#__PURE__*/React.createElement(View, null, figures == null ? void 0 : figures.map((figure, index) => {
31007
+ return /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(Heading, {
31008
+ title: "Locked Figures",
31009
+ isOpen: isExpanded,
31010
+ onToggle: () => setIsExpanded(!isExpanded),
31011
+ isCollapsible: true
31012
+ }), isExpanded && /*#__PURE__*/React.createElement(View, null, figures == null ? void 0 : figures.map((figure, index) => {
30968
31013
  if (figure.type === "function") {
30969
31014
  // TODO(LEMS-1947): Add locked function settings.
30970
31015
  // Remove this block once function locked figure settings are
@@ -30987,7 +31032,7 @@ const LockedFiguresSection = props => {
30987
31032
  onRemove: () => removeLockedFigure(index)
30988
31033
  }));
30989
31034
  }), /*#__PURE__*/React.createElement(View, {
30990
- style: styles$f.buttonContainer
31035
+ style: styles$g.buttonContainer
30991
31036
  }, /*#__PURE__*/React.createElement(LockedFigureSelect, {
30992
31037
  showM2Features: props.showM2Features,
30993
31038
  showM2bFeatures: props.showM2bFeatures,
@@ -30998,10 +31043,10 @@ const LockedFiguresSection = props => {
30998
31043
  }), showExpandButton && /*#__PURE__*/React.createElement(Button, {
30999
31044
  kind: "secondary",
31000
31045
  onClick: () => toggleExpanded(allCollapsed),
31001
- style: styles$f.button
31002
- }, buttonLabel)));
31046
+ style: styles$g.button
31047
+ }, buttonLabel))));
31003
31048
  };
31004
- const styles$f = StyleSheet.create({
31049
+ const styles$g = StyleSheet.create({
31005
31050
  buttonContainer: {
31006
31051
  flexDirection: "row",
31007
31052
  alignItems: "center"
@@ -31036,7 +31081,7 @@ const GraphPointsCountSelector = ({
31036
31081
  // Never uses placeholder, always has value
31037
31082
  ,
31038
31083
  placeholder: "",
31039
- style: styles$e.singleSelectShort
31084
+ style: styles$f.singleSelectShort
31040
31085
  }, [...[...Array(7).keys()].map(n => /*#__PURE__*/React.createElement(OptionItem, {
31041
31086
  key: n,
31042
31087
  value: `${n}`,
@@ -31047,7 +31092,7 @@ const GraphPointsCountSelector = ({
31047
31092
  label: "unlimited"
31048
31093
  })]);
31049
31094
  };
31050
- const styles$e = StyleSheet.create({
31095
+ const styles$f = StyleSheet.create({
31051
31096
  singleSelectShort: {
31052
31097
  // Non-standard spacing, but it's the smallest we can go
31053
31098
  // without running into styling issues with the dropdown.
@@ -31060,7 +31105,7 @@ const GraphTypeSelector = props => {
31060
31105
  selectedValue: props.graphType,
31061
31106
  onChange: props.onChange,
31062
31107
  placeholder: "Select a graph type",
31063
- style: styles$d.singleSelectShort
31108
+ style: styles$e.singleSelectShort
31064
31109
  }, /*#__PURE__*/React.createElement(OptionItem, {
31065
31110
  value: "linear",
31066
31111
  label: "Linear function"
@@ -31093,7 +31138,7 @@ const GraphTypeSelector = props => {
31093
31138
  label: "Angle"
31094
31139
  }));
31095
31140
  };
31096
- const styles$d = StyleSheet.create({
31141
+ const styles$e = StyleSheet.create({
31097
31142
  singleSelectShort: {
31098
31143
  // Non-standard spacing, but it's the smallest we can go
31099
31144
  // without running into styling issues with the dropdown.
@@ -31101,29 +31146,27 @@ const styles$d = StyleSheet.create({
31101
31146
  }
31102
31147
  });
31103
31148
 
31104
- function Heading({
31105
- title,
31106
- isOpen,
31107
- onToggle
31108
- }) {
31109
- return /*#__PURE__*/React.createElement(View, {
31149
+ function InteractiveGraphCorrectAnswer(props) {
31150
+ return /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(Heading, {
31151
+ title: "Correct Answer",
31152
+ isOpen: true,
31153
+ isCollapsible: false
31154
+ }), /*#__PURE__*/React.createElement(View, null, /*#__PURE__*/React.createElement(View, null, /*#__PURE__*/React.createElement(LabelXSmall, {
31110
31155
  style: {
31111
- flexDirection: "row",
31112
- justifyContent: "space-between",
31113
- backgroundColor: color.offBlack8,
31114
- padding: spacing.xSmall_8,
31115
- marginTop: spacing.small_12,
31116
- // NOTE(jeremy): This is the inverse of the @editorPadding CSS
31117
- // variable found in perseus-editor.less. For now, it must
31118
- // match otherwise there's a gap from this header to the edge
31119
- // of the editor borders.
31120
- marginInline: -10,
31121
- cursor: "pointer"
31122
- },
31123
- onClick: () => onToggle == null ? void 0 : onToggle(!isOpen)
31124
- }, /*#__PURE__*/React.createElement(LabelSmall, null, title), /*#__PURE__*/React.createElement(ToggleableCaret, {
31125
- isExpanded: isOpen
31126
- }));
31156
+ paddingTop: spacing.xxSmall_6,
31157
+ paddingBottom: spacing.xxSmall_6,
31158
+ color: color.offBlack64
31159
+ }
31160
+ }, "Graph the correct answer in the graph below and ensure the equation or point coordinates displayed represent the correct answer."), /*#__PURE__*/React.createElement(BodyMonospace, {
31161
+ style: {
31162
+ fontSize: 12,
31163
+ backgroundColor: "#eee",
31164
+ paddingInline: spacing.xxSmall_6,
31165
+ borderColor: "#ccc",
31166
+ borderStyle: "solid",
31167
+ borderWidth: 1
31168
+ }
31169
+ }, props.equationString)), props.children));
31127
31170
  }
31128
31171
 
31129
31172
  const {
@@ -31416,6 +31459,7 @@ class InteractiveGraphSettings extends React.Component {
31416
31459
  return /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(Heading, {
31417
31460
  title: "Common Graph Settings",
31418
31461
  isOpen: this.state.isExpanded,
31462
+ isCollapsible: true,
31419
31463
  onToggle: () => this.setState({
31420
31464
  isExpanded: !this.state.isExpanded
31421
31465
  })
@@ -31510,10 +31554,10 @@ class InteractiveGraphSettings extends React.Component {
31510
31554
  onChange: this.change
31511
31555
  }))), /*#__PURE__*/React.createElement(LabeledRow, {
31512
31556
  label: "Background image URL:",
31513
- style: styles$c.resetSpaceTop
31557
+ style: styles$d.resetSpaceTop
31514
31558
  }, /*#__PURE__*/React.createElement("input", {
31515
31559
  type: "text",
31516
- className: css(styles$c.backgroundUrlInput),
31560
+ className: css(styles$d.backgroundUrlInput),
31517
31561
  ref: this.bgUrlRef,
31518
31562
  value: this.state.backgroundImage.url || "",
31519
31563
  onChange: e => {
@@ -31527,28 +31571,28 @@ class InteractiveGraphSettings extends React.Component {
31527
31571
  onKeyPress: this.changeBackgroundUrl,
31528
31572
  onBlur: this.changeBackgroundUrl
31529
31573
  }), /*#__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, {
31530
- style: styles$c.rulerSection
31574
+ style: styles$d.rulerSection
31531
31575
  }, /*#__PURE__*/React.createElement(View, {
31532
- style: styles$c.checkboxRow
31576
+ style: styles$d.checkboxRow
31533
31577
  }, /*#__PURE__*/React.createElement(PropCheckBox$7, {
31534
31578
  label: "Show ruler",
31535
31579
  showRuler: this.props.showRuler,
31536
31580
  onChange: this.change,
31537
- style: styles$c.resetSpaceTop
31581
+ style: styles$d.resetSpaceTop
31538
31582
  }), /*#__PURE__*/React.createElement(PropCheckBox$7, {
31539
31583
  label: "Show protractor",
31540
31584
  showProtractor: this.props.showProtractor,
31541
31585
  onChange: this.change,
31542
- style: styles$c.resetSpaceTop
31586
+ style: styles$d.resetSpaceTop
31543
31587
  })), (this.props.showRuler || this.props.showProtractor) && /*#__PURE__*/React.createElement(Banner, {
31544
31588
  layout: "floating",
31545
31589
  text: "The ruler and protractor are not accessible. Please consider an alternate approach.",
31546
31590
  kind: "warning"
31547
31591
  }), this.props.showRuler && /*#__PURE__*/React.createElement(View, {
31548
- style: styles$c.spaceTop
31592
+ style: styles$d.spaceTop
31549
31593
  }, /*#__PURE__*/React.createElement(LabeledRow, {
31550
31594
  label: "Ruler label:",
31551
- style: styles$c.resetSpaceTop
31595
+ style: styles$d.resetSpaceTop
31552
31596
  }, /*#__PURE__*/React.createElement(SingleSelect, {
31553
31597
  id: "ruler-label-select",
31554
31598
  selectedValue: this.props.rulerLabel,
@@ -31558,7 +31602,7 @@ class InteractiveGraphSettings extends React.Component {
31558
31602
  });
31559
31603
  },
31560
31604
  placeholder: "None",
31561
- style: styles$c.singleSelectShort
31605
+ style: styles$d.singleSelectShort
31562
31606
  }, /*#__PURE__*/React.createElement(OptionItem, {
31563
31607
  value: "",
31564
31608
  label: "None",
@@ -31599,7 +31643,7 @@ class InteractiveGraphSettings extends React.Component {
31599
31643
  });
31600
31644
  },
31601
31645
  placeholder: "10",
31602
- style: styles$c.singleSelectShort
31646
+ style: styles$d.singleSelectShort
31603
31647
  }, [1, 2, 4, 8, 10, 16].map(value => /*#__PURE__*/React.createElement(OptionItem, {
31604
31648
  key: value,
31605
31649
  value: `${value}`,
@@ -31623,7 +31667,7 @@ InteractiveGraphSettings.defaultProps = {
31623
31667
  rulerLabel: "",
31624
31668
  rulerTicks: 10
31625
31669
  };
31626
- const styles$c = StyleSheet.create({
31670
+ const styles$d = StyleSheet.create({
31627
31671
  resetSpaceTop: {
31628
31672
  marginTop: 0
31629
31673
  },
@@ -31668,13 +31712,13 @@ const SegmentCountSelector = ({
31668
31712
  const num = +newValue;
31669
31713
  onChange(num);
31670
31714
  },
31671
- style: styles$b.singleSelectShort
31715
+ style: styles$c.singleSelectShort
31672
31716
  }, _.range(1, 7).map(n => /*#__PURE__*/React.createElement(OptionItem, {
31673
31717
  key: n,
31674
31718
  value: `${n}`,
31675
31719
  label: `${n} segment${n > 1 ? "s" : ""}`
31676
31720
  })));
31677
- const styles$b = StyleSheet.create({
31721
+ const styles$c = StyleSheet.create({
31678
31722
  singleSelectShort: {
31679
31723
  // Non-standard spacing, but it's the smallest we can go
31680
31724
  // without running into styling issues with the dropdown.
@@ -31682,6 +31726,78 @@ const styles$b = StyleSheet.create({
31682
31726
  }
31683
31727
  });
31684
31728
 
31729
+ const StartCoordSettingsInner = props => {
31730
+ const {
31731
+ type,
31732
+ startCoords,
31733
+ onChange
31734
+ } = props;
31735
+
31736
+ // Check if coords is of type CollinearTuple
31737
+ switch (type) {
31738
+ case "linear":
31739
+ case "ray":
31740
+ return /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(View, {
31741
+ style: styles$b.tile
31742
+ }, /*#__PURE__*/React.createElement(LabelLarge, null, "Point 1"), /*#__PURE__*/React.createElement(CoordinatePairInput, {
31743
+ coord: startCoords[0],
31744
+ onChange: value => onChange([value, startCoords[1]])
31745
+ })), /*#__PURE__*/React.createElement(View, {
31746
+ style: styles$b.tile
31747
+ }, /*#__PURE__*/React.createElement(LabelLarge, null, "Point 2"), /*#__PURE__*/React.createElement(CoordinatePairInput, {
31748
+ coord: startCoords[1],
31749
+ onChange: value => onChange([startCoords[0], value])
31750
+ })));
31751
+ default:
31752
+ return null;
31753
+ }
31754
+ };
31755
+ const StartCoordSettings = props => {
31756
+ var _props$startCoords;
31757
+ const {
31758
+ type,
31759
+ range,
31760
+ step,
31761
+ onChange
31762
+ } = props;
31763
+ const [isOpen, setIsOpen] = React.useState(true);
31764
+ if (type !== "linear" && type !== "ray") {
31765
+ return null;
31766
+ }
31767
+ const defaultStartCoords = getLineCoords({
31768
+ type: type
31769
+ }, range, step);
31770
+ return /*#__PURE__*/React.createElement(View, {
31771
+ style: styles$b.container
31772
+ }, /*#__PURE__*/React.createElement(Heading, {
31773
+ isCollapsible: true,
31774
+ title: "Start coordinates",
31775
+ isOpen: isOpen,
31776
+ onToggle: () => setIsOpen(!isOpen)
31777
+ }), isOpen && /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(StartCoordSettingsInner, {
31778
+ type: type,
31779
+ startCoords: (_props$startCoords = props.startCoords) != null ? _props$startCoords : defaultStartCoords,
31780
+ onChange: onChange
31781
+ }), /*#__PURE__*/React.createElement(Strut, {
31782
+ size: spacing.small_12
31783
+ }), /*#__PURE__*/React.createElement(Button, {
31784
+ startIcon: arrowCounterClockwise,
31785
+ kind: "tertiary",
31786
+ size: "small",
31787
+ onClick: () => {
31788
+ onChange(defaultStartCoords);
31789
+ }
31790
+ }, "Use default start coords")));
31791
+ };
31792
+ const styles$b = StyleSheet.create({
31793
+ tile: {
31794
+ backgroundColor: color.fadedBlue8,
31795
+ marginTop: spacing.xSmall_8,
31796
+ padding: spacing.small_12,
31797
+ borderRadius: spacing.xSmall_8
31798
+ }
31799
+ });
31800
+
31685
31801
  const {
31686
31802
  InfoTip: InfoTip$b
31687
31803
  } = components;
@@ -31729,6 +31845,18 @@ class InteractiveGraphEditor extends React.Component {
31729
31845
  correct: correct
31730
31846
  });
31731
31847
  };
31848
+ this.changeStartCoords = coords => {
31849
+ var _this$props$graph, _this$props$graph2;
31850
+ if (((_this$props$graph = this.props.graph) == null ? void 0 : _this$props$graph.type) !== "linear" && ((_this$props$graph2 = this.props.graph) == null ? void 0 : _this$props$graph2.type) !== "ray") {
31851
+ return;
31852
+ }
31853
+ const graph = _extends({}, this.props.graph, {
31854
+ startCoords: coords
31855
+ });
31856
+ this.props.onChange({
31857
+ graph: graph
31858
+ });
31859
+ };
31732
31860
  this.getSaveWarnings = () => {
31733
31861
  const issues = [];
31734
31862
 
@@ -31747,7 +31875,7 @@ class InteractiveGraphEditor extends React.Component {
31747
31875
  DeprecationMixin.UNSAFE_componentWillMount.call(this);
31748
31876
  }
31749
31877
  render() {
31750
- 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, _this$props$apiOption2, _this$props$apiOption3;
31878
+ var _this$props$graph$typ, _this$props$graph3, _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$graph6, _this$props$graph7, _this$props$apiOption, _this$props$apiOption2, _this$props$apiOption3, _this$props$apiOption4;
31751
31879
  let graph;
31752
31880
  let equationString;
31753
31881
  const gridStep = this.props.gridStep || Util.getGridStep(this.props.range, this.props.step, interactiveSizes.defaultBoxSize);
@@ -31779,13 +31907,14 @@ class InteractiveGraphEditor extends React.Component {
31779
31907
  let correct = this.props.correct;
31780
31908
  // @ts-expect-error - TS2532 - Object is possibly 'undefined'.
31781
31909
  if (correct.type === newProps.graph.type) {
31782
- correct = _.extend({}, correct, newProps.graph);
31910
+ correct = _extends({}, correct, newProps.graph);
31783
31911
  } else {
31784
31912
  // Clear options from previous graph
31785
31913
  correct = newProps.graph;
31786
31914
  }
31787
31915
  this.props.onChange({
31788
- correct: correct
31916
+ correct: correct,
31917
+ graph: this.props.graph
31789
31918
  });
31790
31919
  }
31791
31920
  };
@@ -31813,7 +31942,7 @@ class InteractiveGraphEditor extends React.Component {
31813
31942
  return /*#__PURE__*/React.createElement(View, null, /*#__PURE__*/React.createElement(LabeledRow, {
31814
31943
  label: "Type of Graph:"
31815
31944
  }, /*#__PURE__*/React.createElement(GraphTypeSelector, {
31816
- graphType: (_this$props$graph$typ = (_this$props$graph = this.props.graph) == null ? void 0 : _this$props$graph.type) != null ? _this$props$graph$typ : InteractiveGraph.defaultProps.graph.type,
31945
+ graphType: (_this$props$graph$typ = (_this$props$graph3 = this.props.graph) == null ? void 0 : _this$props$graph3.type) != null ? _this$props$graph$typ : InteractiveGraph.defaultProps.graph.type,
31817
31946
  onChange: type => {
31818
31947
  this.props.onChange({
31819
31948
  graph: {
@@ -31824,7 +31953,9 @@ class InteractiveGraphEditor extends React.Component {
31824
31953
  }
31825
31954
  });
31826
31955
  }
31827
- })), ((_this$props$correct = this.props.correct) == null ? void 0 : _this$props$correct.type) === "point" && /*#__PURE__*/React.createElement(LabeledRow, {
31956
+ })), /*#__PURE__*/React.createElement(InteractiveGraphCorrectAnswer, {
31957
+ equationString: equationString
31958
+ }, graph), ((_this$props$correct = this.props.correct) == null ? void 0 : _this$props$correct.type) === "point" && /*#__PURE__*/React.createElement(LabeledRow, {
31828
31959
  label: "Number of Points:"
31829
31960
  }, /*#__PURE__*/React.createElement(GraphPointsCountSelector, {
31830
31961
  numPoints: (_this$props$correct2 = this.props.correct) == null ? void 0 : _this$props$correct2.numPoints,
@@ -31899,8 +32030,8 @@ class InteractiveGraphEditor extends React.Component {
31899
32030
  // Don't show indeterminate checkbox state
31900
32031
  !!((_this$props$correct8 = this.props.correct) != null && _this$props$correct8.showAngles),
31901
32032
  onChange: () => {
31902
- var _this$props$graph2;
31903
- if (((_this$props$graph2 = this.props.graph) == null ? void 0 : _this$props$graph2.type) === "polygon") {
32033
+ var _this$props$graph4;
32034
+ if (((_this$props$graph4 = this.props.graph) == null ? void 0 : _this$props$graph4.type) === "polygon") {
31904
32035
  this.props.onChange({
31905
32036
  correct: _extends({}, this.props.correct, {
31906
32037
  showAngles: !this.props.correct.showAngles
@@ -31919,8 +32050,8 @@ class InteractiveGraphEditor extends React.Component {
31919
32050
  // Don't show indeterminate checkbox state
31920
32051
  !!((_this$props$correct9 = this.props.correct) != null && _this$props$correct9.showSides),
31921
32052
  onChange: () => {
31922
- var _this$props$graph3;
31923
- if (((_this$props$graph3 = this.props.graph) == null ? void 0 : _this$props$graph3.type) === "polygon") {
32053
+ var _this$props$graph5;
32054
+ if (((_this$props$graph5 = this.props.graph) == null ? void 0 : _this$props$graph5.type) === "polygon") {
31924
32055
  this.props.onChange({
31925
32056
  correct: _extends({}, this.props.correct, {
31926
32057
  showSides: !this.props.correct.showSides
@@ -31948,6 +32079,10 @@ class InteractiveGraphEditor extends React.Component {
31948
32079
  }
31949
32080
  });
31950
32081
  }
32082
+ })), (((_this$props$graph6 = this.props.graph) == null ? void 0 : _this$props$graph6.type) === "linear" || ((_this$props$graph7 = this.props.graph) == null ? void 0 : _this$props$graph7.type) === "ray") && ((_this$props$apiOption = this.props.apiOptions.flags) == null || (_this$props$apiOption = _this$props$apiOption.mafs) == null ? void 0 : _this$props$apiOption["start-coords-ui"]) && /*#__PURE__*/React.createElement(StartCoordSettings, _extends({}, this.props.graph, {
32083
+ range: this.props.range,
32084
+ step: this.props.step,
32085
+ onChange: this.changeStartCoords
31951
32086
  })), /*#__PURE__*/React.createElement(InteractiveGraphSettings, {
31952
32087
  box: getInteractiveBoxFromSizeClass(sizeClass),
31953
32088
  range: this.props.range,
@@ -32000,38 +32135,33 @@ class InteractiveGraphEditor extends React.Component {
32000
32135
  }), /*#__PURE__*/React.createElement(OptionItem, {
32001
32136
  value: "congruent",
32002
32137
  label: "be congruent"
32003
- })), /*#__PURE__*/React.createElement(InfoTip$b, null, /*#__PURE__*/React.createElement("p", null, "Congruency requires only that the angle measures are the same. An exact match implies congruency, but also requires that the angles have the same orientation and that the vertices are in the same position."))), /*#__PURE__*/React.createElement(LabeledRow, {
32004
- label: "Correct answer:"
32005
- }, /*#__PURE__*/React.createElement(BodyMonospace, {
32006
- style: {
32007
- fontSize: 12,
32008
- backgroundColor: "#eee",
32009
- paddingInline: spacing.xxSmall_6,
32010
- borderColor: "#ccc",
32011
- borderStyle: "solid",
32012
- borderWidth: 1
32013
- }
32014
- }, 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,
32138
+ })), /*#__PURE__*/React.createElement(InfoTip$b, null, /*#__PURE__*/React.createElement("p", null, "Congruency requires only that the angle measures are the same. An exact match implies congruency, but also requires that the angles have the same orientation and that the vertices are in the same position."))),
32015
32139
  // Only show the "Add locked figure" dropdown if the graph
32016
32140
  // is using Mafs.
32017
- 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, {
32018
- showM2Features: (_this$props$apiOption2 = this.props.apiOptions) == null || (_this$props$apiOption2 = _this$props$apiOption2.flags) == null || (_this$props$apiOption2 = _this$props$apiOption2.mafs) == null ? void 0 : _this$props$apiOption2["interactive-graph-locked-features-m2"],
32019
- showM2bFeatures: (_this$props$apiOption3 = this.props.apiOptions) == null || (_this$props$apiOption3 = _this$props$apiOption3.flags) == null || (_this$props$apiOption3 = _this$props$apiOption3.mafs) == null ? void 0 : _this$props$apiOption3["interactive-graph-locked-features-m2b"],
32141
+ this.props.graph && ((_this$props$apiOption2 = this.props.apiOptions) == null || (_this$props$apiOption2 = _this$props$apiOption2.flags) == null || (_this$props$apiOption2 = _this$props$apiOption2.mafs) == null ? void 0 : _this$props$apiOption2[this.props.graph.type]) && /*#__PURE__*/React.createElement(LockedFiguresSection, {
32142
+ showM2Features: (_this$props$apiOption3 = this.props.apiOptions) == null || (_this$props$apiOption3 = _this$props$apiOption3.flags) == null || (_this$props$apiOption3 = _this$props$apiOption3.mafs) == null ? void 0 : _this$props$apiOption3["interactive-graph-locked-features-m2"],
32143
+ showM2bFeatures: (_this$props$apiOption4 = this.props.apiOptions) == null || (_this$props$apiOption4 = _this$props$apiOption4.flags) == null || (_this$props$apiOption4 = _this$props$apiOption4.mafs) == null ? void 0 : _this$props$apiOption4["interactive-graph-locked-features-m2b"],
32020
32144
  figures: this.props.lockedFigures,
32021
32145
  onChange: this.props.onChange
32022
32146
  }));
32023
32147
  }
32148
+ // serialize() is what makes copy/paste work. All the properties included
32149
+ // in the serialization json are included when, for example, a graph
32150
+ // is copied from the question editor and pasted into the hint editor
32151
+ // (double brackets in the markdown).
32024
32152
  serialize() {
32025
32153
  const json = _.pick(this.props, "step", "backgroundImage", "markings", "labels", "showProtractor", "showRuler", "showTooltips", "rulerLabel", "rulerTicks", "range", "gridStep", "snapStep", "lockedFigures");
32026
32154
 
32027
32155
  // eslint-disable-next-line react/no-string-refs
32028
32156
  const graph = this.refs.graph;
32029
32157
  if (graph) {
32158
+ var _this$props$graph8;
32030
32159
  // @ts-expect-error TS2339 Property 'getUserInput' does not exist on type 'ReactInstance'. Property 'getUserInput' does not exist on type 'Component<any, {}, any>'.
32031
32160
  const correct = graph && graph.getUserInput();
32032
32161
  _.extend(json, {
32033
32162
  graph: {
32034
- type: correct.type
32163
+ type: correct.type,
32164
+ startCoords: (_this$props$graph8 = this.props.graph) == null ? void 0 : _this$props$graph8.startCoords
32035
32165
  },
32036
32166
  correct: correct
32037
32167
  });