@khanacademy/perseus-editor 6.7.0 → 6.10.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/index.js CHANGED
@@ -67,7 +67,7 @@ var trashIcon__default = /*#__PURE__*/_interopDefaultLegacy(trashIcon);
67
67
 
68
68
  // This file is processed by a Rollup plugin (replace) to inject the production
69
69
  const libName = "@khanacademy/perseus-editor";
70
- const libVersion = "6.7.0";
70
+ const libVersion = "6.10.0";
71
71
  perseusCore.addLibraryVersionToPerseusDebug(libName, libVersion);
72
72
 
73
73
  function _extends() {
@@ -262,13 +262,13 @@ class SectionControlButton extends React__namespace.Component {
262
262
  role: "button",
263
263
  hideDefaultFocusRing: true,
264
264
  "aria-label": title,
265
- style: styles$z.button
265
+ style: styles$D.button
266
266
  }, _ref => {
267
267
  return /*#__PURE__*/React__namespace.createElement(InlineIcon$b, icon);
268
268
  });
269
269
  }
270
270
  }
271
- const styles$z = aphrodite.StyleSheet.create({
271
+ const styles$D = aphrodite.StyleSheet.create({
272
272
  button: {
273
273
  backgroundColor: wonderBlocksTokens.color.gold,
274
274
  margin: 2,
@@ -20773,13 +20773,13 @@ class WidgetSelect extends React__namespace.Component {
20773
20773
  * that collapse a region.
20774
20774
  */
20775
20775
  function ToggleableCaret(props) {
20776
- const iconStyle = props.isExpanded ? styles$y.expanded : styles$y.collapsed;
20776
+ const iconStyle = props.isExpanded ? styles$C.expanded : styles$C.collapsed;
20777
20777
  return /*#__PURE__*/React__namespace.createElement(wonderBlocksIcon.PhosphorIcon, {
20778
20778
  icon: caretRight__default["default"],
20779
20779
  style: iconStyle
20780
20780
  });
20781
20781
  }
20782
- const styles$y = aphrodite.StyleSheet.create({
20782
+ const styles$C = aphrodite.StyleSheet.create({
20783
20783
  collapsed: {
20784
20784
  transition: ".15s"
20785
20785
  },
@@ -20809,16 +20809,16 @@ class TexErrorView extends React__namespace.Component {
20809
20809
  showErrors
20810
20810
  } = this.state;
20811
20811
  return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
20812
- style: styles$x.errorContainer
20812
+ style: styles$B.errorContainer
20813
20813
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
20814
- style: styles$x.title,
20814
+ style: styles$B.title,
20815
20815
  onClick: this.handleToggleTexErrors
20816
20816
  }, /*#__PURE__*/React__namespace.createElement(ToggleableCaret, {
20817
20817
  isExpanded: showErrors
20818
20818
  }), "\xA0 TeX Errors (", errorList.length, ")"), showErrors && /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
20819
- style: styles$x.errorExplanation
20819
+ style: styles$B.errorExplanation
20820
20820
  }, "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__namespace.createElement(wonderBlocksCore.View, {
20821
- style: styles$x.error,
20821
+ style: styles$B.error,
20822
20822
  key: index
20823
20823
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
20824
20824
  style: {
@@ -20827,7 +20827,7 @@ class TexErrorView extends React__namespace.Component {
20827
20827
  }, e.math), /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, null, e.message))));
20828
20828
  }
20829
20829
  }
20830
- const styles$x = aphrodite.StyleSheet.create({
20830
+ const styles$B = aphrodite.StyleSheet.create({
20831
20831
  title: {
20832
20832
  backgroundColor: "#eee",
20833
20833
  fontSize: "1.25em",
@@ -23464,7 +23464,7 @@ class StructuredItemDiff extends React__namespace.Component {
23464
23464
 
23465
23465
  /* eslint-disable @khanacademy/ts-no-error-suppressions */
23466
23466
  const {
23467
- InfoTip: InfoTip$l,
23467
+ InfoTip: InfoTip$n,
23468
23468
  InlineIcon: InlineIcon$7
23469
23469
  } = perseus.components;
23470
23470
  const {
@@ -23538,7 +23538,7 @@ class HintEditor extends React__namespace.Component {
23538
23538
  type: "button",
23539
23539
  className: this.props.isFirst ? "hidden" : "",
23540
23540
  onClick: ___default["default"].partial(this.props.onMove, -1)
23541
- }, /*#__PURE__*/React__namespace.createElement(InlineIcon$7, iconCircleArrowUp)), " ", this.props.isLast && /*#__PURE__*/React__namespace.createElement(InfoTip$l, null, /*#__PURE__*/React__namespace.createElement("p", null, "The last hint is automatically bolded."))), /*#__PURE__*/React__namespace.createElement("input", {
23541
+ }, /*#__PURE__*/React__namespace.createElement(InlineIcon$7, iconCircleArrowUp)), " ", this.props.isLast && /*#__PURE__*/React__namespace.createElement(InfoTip$n, null, /*#__PURE__*/React__namespace.createElement("p", null, "The last hint is automatically bolded."))), /*#__PURE__*/React__namespace.createElement("input", {
23542
23542
  type: "checkbox"
23543
23543
  // @ts-expect-error - TS2322 - Type 'boolean | null | undefined' is not assignable to type 'boolean | undefined'.
23544
23544
  ,
@@ -23773,7 +23773,7 @@ class CombinedHintsEditor extends React__namespace.Component {
23773
23773
  }
23774
23774
 
23775
23775
  const {
23776
- InfoTip: InfoTip$k
23776
+ InfoTip: InfoTip$m
23777
23777
  } = perseus.components;
23778
23778
  class ItemExtrasEditor extends React__namespace.Component {
23779
23779
  static defaultProps = {
@@ -23918,7 +23918,7 @@ const ItemExtraCheckbox = props => /*#__PURE__*/React__namespace.createElement("
23918
23918
  type: "checkbox",
23919
23919
  checked: props.checked,
23920
23920
  onChange: props.onChange
23921
- })), /*#__PURE__*/React__namespace.createElement(InfoTip$k, null, props.infoTip));
23921
+ })), /*#__PURE__*/React__namespace.createElement(InfoTip$m, null, props.infoTip));
23922
23922
 
23923
23923
  const ITEM_DATA_VERSION = perseus.itemDataVersion;
23924
23924
  class ItemEditor extends React__namespace.Component {
@@ -24577,12 +24577,12 @@ class SimpleButton extends React__namespace.Component {
24577
24577
  ...otherProps
24578
24578
  } = this.props;
24579
24579
  return /*#__PURE__*/React__namespace.createElement("div", _extends({
24580
- className: aphrodite.css(styles$w.baseButton, color === "green" && styles$w.green, color === "orange" && styles$w.orange),
24580
+ className: aphrodite.css(styles$A.baseButton, color === "green" && styles$A.green, color === "orange" && styles$A.orange),
24581
24581
  onClick: onClick
24582
24582
  }, otherProps), children);
24583
24583
  }
24584
24584
  }
24585
- const styles$w = aphrodite.StyleSheet.create({
24585
+ const styles$A = aphrodite.StyleSheet.create({
24586
24586
  baseButton: {
24587
24587
  top: "0",
24588
24588
  fontSize: "11px",
@@ -24795,23 +24795,23 @@ const LeafContainer = _ref2 => {
24795
24795
  } = _ref2;
24796
24796
  const hasPreviewHeading = shape.type === "content" || shape.type === "hint";
24797
24797
  const previewHeading = hasPreviewHeading && /*#__PURE__*/React__namespace.createElement("div", {
24798
- className: aphrodite.css(styles$v.containerHeader)
24798
+ className: aphrodite.css(styles$z.containerHeader)
24799
24799
  }, /*#__PURE__*/React__namespace.createElement(Header, {
24800
24800
  depth: path.length,
24801
- className: aphrodite.css(styles$v.containerTitle)
24801
+ className: aphrodite.css(styles$z.containerTitle)
24802
24802
  }, capitalize(name)));
24803
24803
  return /*#__PURE__*/React__namespace.createElement("div", {
24804
- className: aphrodite.css(styles$v.container)
24804
+ className: aphrodite.css(styles$z.container)
24805
24805
  }, /*#__PURE__*/React__namespace.createElement("span", {
24806
- className: aphrodite.css(styles$v.row, styles$v.rowHeading)
24806
+ className: aphrodite.css(styles$z.row, styles$z.rowHeading)
24807
24807
  }, /*#__PURE__*/React__namespace.createElement("div", {
24808
- className: aphrodite.css(styles$v.columnLeft)
24808
+ className: aphrodite.css(styles$z.columnLeft)
24809
24809
  }, /*#__PURE__*/React__namespace.createElement("div", {
24810
- className: "pod-title " + aphrodite.css(styles$v.containerHeader)
24810
+ className: "pod-title " + aphrodite.css(styles$z.containerHeader)
24811
24811
  }, /*#__PURE__*/React__namespace.createElement("div", {
24812
- className: aphrodite.css(styles$v.containerTitle)
24812
+ className: aphrodite.css(styles$z.containerTitle)
24813
24813
  }, capitalize(name)), controls)), /*#__PURE__*/React__namespace.createElement("div", {
24814
- className: aphrodite.css(styles$v.columnRight)
24814
+ className: aphrodite.css(styles$z.columnRight)
24815
24815
  }, previewHeading)), children);
24816
24816
  };
24817
24817
  const ArrayContainer = props => {
@@ -24824,11 +24824,11 @@ const ArrayContainer = props => {
24824
24824
  actions
24825
24825
  } = props;
24826
24826
  return /*#__PURE__*/React__namespace.createElement("div", {
24827
- className: aphrodite.css(styles$v.container)
24827
+ className: aphrodite.css(styles$z.container)
24828
24828
  }, controls && /*#__PURE__*/React__namespace.createElement("div", {
24829
- className: aphrodite.css(styles$v.columnLeft, styles$v.containerHeader)
24829
+ className: aphrodite.css(styles$z.columnLeft, styles$z.containerHeader)
24830
24830
  }, controls), /*#__PURE__*/React__namespace.createElement("div", null, children), /*#__PURE__*/React__namespace.createElement("div", {
24831
- className: aphrodite.css(styles$v.columnLeft)
24831
+ className: aphrodite.css(styles$z.columnLeft)
24832
24832
  }, /*#__PURE__*/React__namespace.createElement("a", {
24833
24833
  href: "javascript:void 0",
24834
24834
  onClick: () => actions.addArrayElement(path, shape.elementShape)
@@ -24842,28 +24842,28 @@ const ObjectContainer = _ref3 => {
24842
24842
  path
24843
24843
  } = _ref3;
24844
24844
  const headingEditor = /*#__PURE__*/React__namespace.createElement("div", {
24845
- className: aphrodite.css(styles$v.containerHeader)
24845
+ className: aphrodite.css(styles$z.containerHeader)
24846
24846
  }, /*#__PURE__*/React__namespace.createElement(Header, {
24847
24847
  depth: path.length,
24848
- className: aphrodite.css(styles$v.containerTitle)
24848
+ className: aphrodite.css(styles$z.containerTitle)
24849
24849
  }, capitalize(name)), controls);
24850
24850
  const headingPreview = (name || controls) && /*#__PURE__*/React__namespace.createElement("div", {
24851
- className: aphrodite.css(styles$v.containerHeader, styles$v.previewCollectionHeader)
24851
+ className: aphrodite.css(styles$z.containerHeader, styles$z.previewCollectionHeader)
24852
24852
  }, /*#__PURE__*/React__namespace.createElement(Header, {
24853
24853
  depth: path.length,
24854
- className: aphrodite.css(styles$v.containerTitle)
24854
+ className: aphrodite.css(styles$z.containerTitle)
24855
24855
  }, capitalize(name)));
24856
24856
  const hasBothHeadings = headingEditor && headingPreview;
24857
24857
  return /*#__PURE__*/React__namespace.createElement("div", {
24858
- className: aphrodite.css(styles$v.container)
24858
+ className: aphrodite.css(styles$z.container)
24859
24859
  }, hasBothHeadings && /*#__PURE__*/React__namespace.createElement("span", {
24860
- className: aphrodite.css(styles$v.row)
24860
+ className: aphrodite.css(styles$z.row)
24861
24861
  }, /*#__PURE__*/React__namespace.createElement("div", {
24862
- className: aphrodite.css(styles$v.columnLeft)
24862
+ className: aphrodite.css(styles$z.columnLeft)
24863
24863
  }, headingEditor), /*#__PURE__*/React__namespace.createElement("div", {
24864
- className: aphrodite.css(styles$v.columnRight)
24864
+ className: aphrodite.css(styles$z.columnRight)
24865
24865
  }, headingPreview)), /*#__PURE__*/React__namespace.createElement("div", {
24866
- className: aphrodite.css(path.length > 0 && styles$v.contentIndent)
24866
+ className: aphrodite.css(path.length > 0 && styles$z.contentIndent)
24867
24867
  }, children));
24868
24868
  };
24869
24869
 
@@ -24983,11 +24983,11 @@ const ItemNodeContent = withStickiness(props => {
24983
24983
  className: "framework-perseus"
24984
24984
  }, lens(renderers).get(path));
24985
24985
  return /*#__PURE__*/React__namespace.createElement("span", null, /*#__PURE__*/React__namespace.createElement("div", {
24986
- className: aphrodite.css(styles$v.row)
24986
+ className: aphrodite.css(styles$z.row)
24987
24987
  }, /*#__PURE__*/React__namespace.createElement("div", {
24988
- className: aphrodite.css(styles$v.columnLeft)
24988
+ className: aphrodite.css(styles$z.columnLeft)
24989
24989
  }, /*#__PURE__*/React__namespace.createElement("div", {
24990
- className: aphrodite.css(sticky && styles$v.sticky)
24990
+ className: aphrodite.css(sticky && styles$z.sticky)
24991
24991
  },
24992
24992
  /*#__PURE__*/
24993
24993
  // @ts-expect-error - TS2769 - No overload matches this call.
@@ -24995,9 +24995,9 @@ const ItemNodeContent = withStickiness(props => {
24995
24995
  onChange: newVal => actions.mergeValueAtPath(path, newVal),
24996
24996
  apiOptions: apiOptions
24997
24997
  })))), /*#__PURE__*/React__namespace.createElement("div", {
24998
- className: aphrodite.css(styles$v.columnRight)
24998
+ className: aphrodite.css(styles$z.columnRight)
24999
24999
  }, /*#__PURE__*/React__namespace.createElement("div", {
25000
- className: aphrodite.css(sticky && styles$v.sticky)
25000
+ className: aphrodite.css(sticky && styles$z.sticky)
25001
25001
  }, preview))));
25002
25002
  });
25003
25003
  const HintNodeContent = withStickiness(props => {
@@ -25013,13 +25013,13 @@ const HintNodeContent = withStickiness(props => {
25013
25013
  className: "framework-perseus"
25014
25014
  }, lens(renderers).get(path));
25015
25015
  return /*#__PURE__*/React__namespace.createElement("div", {
25016
- className: aphrodite.css(styles$v.row)
25016
+ className: aphrodite.css(styles$z.row)
25017
25017
  }, /*#__PURE__*/React__namespace.createElement("div", {
25018
- className: aphrodite.css(styles$v.columnLeft)
25018
+ className: aphrodite.css(styles$z.columnLeft)
25019
25019
  }, /*#__PURE__*/React__namespace.createElement("div", {
25020
- className: aphrodite.css(sticky && styles$v.sticky)
25020
+ className: aphrodite.css(sticky && styles$z.sticky)
25021
25021
  }, /*#__PURE__*/React__namespace.createElement(HintEditor, _extends({}, data, {
25022
- className: aphrodite.css(styles$v.hintEditor),
25022
+ className: aphrodite.css(styles$z.hintEditor),
25023
25023
  onChange: newVal => actions.mergeValueAtPath(path, newVal),
25024
25024
  apiOptions: apiOptions,
25025
25025
  showTitle: false,
@@ -25034,9 +25034,9 @@ const HintNodeContent = withStickiness(props => {
25034
25034
  isFirst: true,
25035
25035
  isLast: true
25036
25036
  })))), /*#__PURE__*/React__namespace.createElement("div", {
25037
- className: aphrodite.css(styles$v.columnRight)
25037
+ className: aphrodite.css(styles$z.columnRight)
25038
25038
  }, /*#__PURE__*/React__namespace.createElement("div", {
25039
- className: aphrodite.css(sticky && styles$v.sticky)
25039
+ className: aphrodite.css(sticky && styles$z.sticky)
25040
25040
  }, preview)));
25041
25041
  });
25042
25042
  const TagsNodeContent = props => {
@@ -25053,9 +25053,9 @@ const TagsNodeContent = props => {
25053
25053
  return null;
25054
25054
  }
25055
25055
  return /*#__PURE__*/React__namespace.createElement("div", {
25056
- className: aphrodite.css(styles$v.columnLeft)
25056
+ className: aphrodite.css(styles$z.columnLeft)
25057
25057
  }, /*#__PURE__*/React__namespace.createElement("div", {
25058
- className: aphrodite.css(styles$v.tagsEditor)
25058
+ className: aphrodite.css(styles$z.tagsEditor)
25059
25059
  }, /*#__PURE__*/React__namespace.createElement(GroupMetadataEditor, {
25060
25060
  value: data,
25061
25061
  onChange: newVal => actions.setValueAtPath(path, newVal),
@@ -25086,23 +25086,23 @@ const ArrayNodeContent = props => {
25086
25086
  const subpath = path.concat(i);
25087
25087
  const controls = [i > 0 && /*#__PURE__*/React__namespace.createElement("div", {
25088
25088
  key: "moveArrayElementUp",
25089
- className: aphrodite.css(styles$v.control)
25089
+ className: aphrodite.css(styles$z.control)
25090
25090
  }, /*#__PURE__*/React__namespace.createElement(SimpleButton, {
25091
25091
  color: "orange",
25092
25092
  title: "Move up",
25093
25093
  onClick: () => actions.moveArrayElementUp(subpath)
25094
25094
  }, /*#__PURE__*/React__namespace.createElement("div", {
25095
- className: aphrodite.css(styles$v.verticalFlip)
25095
+ className: aphrodite.css(styles$z.verticalFlip)
25096
25096
  }, /*#__PURE__*/React__namespace.createElement(InlineIcon$6, iconChevronDown)))), i < data.length - 1 && /*#__PURE__*/React__namespace.createElement("div", {
25097
25097
  key: "moveArrayElementDown",
25098
- className: aphrodite.css(styles$v.control)
25098
+ className: aphrodite.css(styles$z.control)
25099
25099
  }, /*#__PURE__*/React__namespace.createElement(SimpleButton, {
25100
25100
  color: "orange",
25101
25101
  title: "Move down",
25102
25102
  onClick: () => actions.moveArrayElementDown(subpath)
25103
25103
  }, /*#__PURE__*/React__namespace.createElement(InlineIcon$6, iconChevronDown))), /*#__PURE__*/React__namespace.createElement("div", {
25104
25104
  key: "removeArrayElement",
25105
- className: aphrodite.css(styles$v.control)
25105
+ className: aphrodite.css(styles$z.control)
25106
25106
  }, /*#__PURE__*/React__namespace.createElement(SimpleButton, {
25107
25107
  color: "orange",
25108
25108
  title: "Delete",
@@ -25110,7 +25110,7 @@ const ArrayNodeContent = props => {
25110
25110
  }, /*#__PURE__*/React__namespace.createElement(InlineIcon$6, iconTrash$4)))];
25111
25111
  return /*#__PURE__*/React__namespace.createElement("div", {
25112
25112
  key: i,
25113
- className: aphrodite.css(styles$v.arrayElement, !elementIsLeaf && styles$v.arrayElementAndNotLeaf)
25113
+ className: aphrodite.css(styles$z.arrayElement, !elementIsLeaf && styles$z.arrayElementAndNotLeaf)
25114
25114
  }, /*#__PURE__*/React__namespace.createElement(NodeContainer, _extends({}, otherProps, {
25115
25115
  key: i,
25116
25116
  shape: shape.elementShape,
@@ -25136,7 +25136,7 @@ const ObjectNodeContent = props => {
25136
25136
  // made sense to the shape's author is the order in which we'll iterate :)
25137
25137
  const children = Object.keys(shape.shape).map(subkey => /*#__PURE__*/React__namespace.createElement("div", {
25138
25138
  key: subkey,
25139
- className: aphrodite.css(styles$v.objectElement)
25139
+ className: aphrodite.css(styles$z.objectElement)
25140
25140
  }, /*#__PURE__*/React__namespace.createElement(NodeContainer, _extends({}, otherProps, {
25141
25141
  shape: shape.shape[subkey],
25142
25142
  data: data[subkey],
@@ -25306,7 +25306,7 @@ class MultiRendererEditor extends React__namespace.Component {
25306
25306
  }, this._renderContent());
25307
25307
  }
25308
25308
  }
25309
- const styles$v = aphrodite.StyleSheet.create({
25309
+ const styles$z = aphrodite.StyleSheet.create({
25310
25310
  // This is used in a number of places throughout this file.
25311
25311
  container: {},
25312
25312
  // eslint-disable-next-line react-native/no-unused-styles
@@ -25458,47 +25458,47 @@ const StatefulArticleEditor = createReactClass__default["default"]({
25458
25458
  screen
25459
25459
  } = this.state;
25460
25460
  return /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("div", {
25461
- style: styles$u.controlBar
25461
+ style: styles$y.controlBar
25462
25462
  }, /*#__PURE__*/React__namespace.createElement("span", {
25463
- style: styles$u.controls
25463
+ style: styles$y.controls
25464
25464
  }, "Mode:", " ", /*#__PURE__*/React__namespace.createElement("span", {
25465
25465
  onClick: () => this.setState({
25466
25466
  mode: "edit"
25467
25467
  }),
25468
- style: mode === "edit" ? styles$u.controlSelected : styles$u.control
25468
+ style: mode === "edit" ? styles$y.controlSelected : styles$y.control
25469
25469
  }, "EDIT"), " | ", /*#__PURE__*/React__namespace.createElement("span", {
25470
25470
  onClick: () => this.setState({
25471
25471
  mode: "preview"
25472
25472
  }),
25473
- style: mode === "preview" ? styles$u.controlSelected : styles$u.control
25473
+ style: mode === "preview" ? styles$y.controlSelected : styles$y.control
25474
25474
  }, "PREVIEW"), " | ", /*#__PURE__*/React__namespace.createElement("span", {
25475
25475
  onClick: () => this.setState({
25476
25476
  mode: "json"
25477
25477
  }),
25478
- style: mode === "json" ? styles$u.controlSelected : styles$u.control
25478
+ style: mode === "json" ? styles$y.controlSelected : styles$y.control
25479
25479
  }, "JSON")), /*#__PURE__*/React__namespace.createElement("span", {
25480
- style: styles$u.controls
25480
+ style: styles$y.controls
25481
25481
  }, "Screen:", " ", /*#__PURE__*/React__namespace.createElement("span", {
25482
25482
  onClick: () => this.setState({
25483
25483
  screen: "phone"
25484
25484
  }),
25485
- style: screen === "phone" ? styles$u.controlSelected : styles$u.control
25485
+ style: screen === "phone" ? styles$y.controlSelected : styles$y.control
25486
25486
  }, "PHONE"), " | ", /*#__PURE__*/React__namespace.createElement("span", {
25487
25487
  onClick: () => this.setState({
25488
25488
  screen: "tablet"
25489
25489
  }),
25490
- style: screen === "tablet" ? styles$u.controlSelected : styles$u.control
25490
+ style: screen === "tablet" ? styles$y.controlSelected : styles$y.control
25491
25491
  }, "TABLET"), " | ", /*#__PURE__*/React__namespace.createElement("span", {
25492
25492
  onClick: () => this.setState({
25493
25493
  screen: "desktop"
25494
25494
  }),
25495
- style: screen === "desktop" ? styles$u.controlSelected : styles$u.control
25495
+ style: screen === "desktop" ? styles$y.controlSelected : styles$y.control
25496
25496
  }, "DESKTOP"))), /*#__PURE__*/React__namespace.createElement("div", {
25497
- style: styles$u.editor
25497
+ style: styles$y.editor
25498
25498
  }, /*#__PURE__*/React__namespace.createElement(ArticleEditor, this.state)));
25499
25499
  }
25500
25500
  });
25501
- const styles$u = {
25501
+ const styles$y = {
25502
25502
  controlBar: {
25503
25503
  marginBottom: 25,
25504
25504
  marginTop: 5
@@ -25713,7 +25713,7 @@ class BlurInput extends React__namespace.Component {
25713
25713
 
25714
25714
  /* eslint-disable no-useless-escape */
25715
25715
  const {
25716
- InfoTip: InfoTip$j,
25716
+ InfoTip: InfoTip$l,
25717
25717
  PropCheckBox: PropCheckBox$b
25718
25718
  } = perseus.components;
25719
25719
  const DEFAULT_WIDTH = 400;
@@ -25901,7 +25901,7 @@ class CSProgramEditor extends React__namespace.Component {
25901
25901
  label: "Show Editor",
25902
25902
  showEditor: this.props.showEditor,
25903
25903
  onChange: this.props.onChange
25904
- }), /*#__PURE__*/React__namespace.createElement(InfoTip$j, null, "If you show the editor, you should use the \"full-width\" alignment to make room for the width of the editor."), /*#__PURE__*/React__namespace.createElement("br", null), /*#__PURE__*/React__namespace.createElement(PropCheckBox$b, {
25904
+ }), /*#__PURE__*/React__namespace.createElement(InfoTip$l, null, "If you show the editor, you should use the \"full-width\" alignment to make room for the width of the editor."), /*#__PURE__*/React__namespace.createElement("br", null), /*#__PURE__*/React__namespace.createElement(PropCheckBox$b, {
25905
25905
  label: "Show Buttons",
25906
25906
  showButtons: this.props.showButtons,
25907
25907
  onChange: this.props.onChange
@@ -25909,7 +25909,7 @@ class CSProgramEditor extends React__namespace.Component {
25909
25909
  name: "settings",
25910
25910
  pairs: this.props.settings,
25911
25911
  onChange: this._handleSettingsChange
25912
- }), /*#__PURE__*/React__namespace.createElement(InfoTip$j, null, "Settings that you add here are available to the program as an object returned by ", /*#__PURE__*/React__namespace.createElement("code", null, "Program.settings()"))));
25912
+ }), /*#__PURE__*/React__namespace.createElement(InfoTip$l, null, "Settings that you add here are available to the program as an object returned by ", /*#__PURE__*/React__namespace.createElement("code", null, "Program.settings()"))));
25913
25913
  }
25914
25914
  }
25915
25915
 
@@ -25986,7 +25986,7 @@ class DeprecatedStandinEditor extends React__namespace.Component {
25986
25986
 
25987
25987
  /* eslint-disable @khanacademy/ts-no-error-suppressions */
25988
25988
  const {
25989
- InfoTip: InfoTip$i,
25989
+ InfoTip: InfoTip$k,
25990
25990
  InlineIcon: InlineIcon$5
25991
25991
  } = perseus.components;
25992
25992
  const {
@@ -26067,14 +26067,14 @@ class DropdownEditor extends React__namespace.Component {
26067
26067
  className: "perseus-widget-dropdown"
26068
26068
  }, /*#__PURE__*/React__namespace.createElement("div", {
26069
26069
  className: "dropdown-info"
26070
- }, "Dropdown", /*#__PURE__*/React__namespace.createElement(InfoTip$i, null, /*#__PURE__*/React__namespace.createElement("p", null, "The drop down is useful for making inequalities in a custom format. We normally use the symbols ", "<", ",", " ", ">", ", \u2264, \u2265 (in that order) which you can copy into the choices. When possible, use the \"multiple choice\" answer type instead."))), /*#__PURE__*/React__namespace.createElement("div", {
26070
+ }, "Dropdown", /*#__PURE__*/React__namespace.createElement(InfoTip$k, null, /*#__PURE__*/React__namespace.createElement("p", null, "The drop down is useful for making inequalities in a custom format. We normally use the symbols ", "<", ",", " ", ">", ", \u2264, \u2265 (in that order) which you can copy into the choices. When possible, use the \"multiple choice\" answer type instead."))), /*#__PURE__*/React__namespace.createElement("div", {
26071
26071
  className: "dropdown-placeholder"
26072
26072
  }, /*#__PURE__*/React__namespace.createElement("input", {
26073
26073
  type: "text",
26074
26074
  placeholder: "Placeholder value",
26075
26075
  value: this.props.placeholder,
26076
26076
  onChange: this.onPlaceholderChange
26077
- }), /*#__PURE__*/React__namespace.createElement(InfoTip$i, null, /*#__PURE__*/React__namespace.createElement("p", null, "This value will appear as the drop down default. It should give the user some indication of the values available in the drop down itself, e.g., Yes/No/Maybe."))), /*#__PURE__*/React__namespace.createElement("div", {
26077
+ }), /*#__PURE__*/React__namespace.createElement(InfoTip$k, null, /*#__PURE__*/React__namespace.createElement("p", null, "This value will appear as the drop down default. It should give the user some indication of the values available in the drop down itself, e.g., Yes/No/Maybe."))), /*#__PURE__*/React__namespace.createElement("div", {
26078
26078
  className: "clearfix"
26079
26079
  }), /*#__PURE__*/React__namespace.createElement("ul", {
26080
26080
  className: "dropdown-choices"
@@ -26608,7 +26608,7 @@ const SortableItem = createReactClass__default["default"]({
26608
26608
  });
26609
26609
 
26610
26610
  const {
26611
- InfoTip: InfoTip$h,
26611
+ InfoTip: InfoTip$j,
26612
26612
  PropCheckBox: PropCheckBox$a
26613
26613
  } = perseus.components;
26614
26614
 
@@ -26734,11 +26734,11 @@ class ExpressionEditor extends React__namespace.Component {
26734
26734
  onChange: this.props.onChange,
26735
26735
  labelAlignment: "right",
26736
26736
  label: "Use \xD7 for rendering multiplication instead of a center dot."
26737
- }), /*#__PURE__*/React__namespace.createElement(InfoTip$h, null, /*#__PURE__*/React__namespace.createElement("p", null, "For pre-algebra problems this option displays multiplication as \\times instead of \\cdot in both the rendered output and the acceptable formats examples."))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, "Function variables: ", /*#__PURE__*/React__namespace.createElement("input", {
26737
+ }), /*#__PURE__*/React__namespace.createElement(InfoTip$j, null, /*#__PURE__*/React__namespace.createElement("p", null, "For pre-algebra problems this option displays multiplication as \\times instead of \\cdot in both the rendered output and the acceptable formats examples."))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, "Function variables: ", /*#__PURE__*/React__namespace.createElement("input", {
26738
26738
  type: "text",
26739
26739
  defaultValue: this.props.functions.join(" "),
26740
26740
  onChange: this.handleFunctions
26741
- })), /*#__PURE__*/React__namespace.createElement(InfoTip$h, null, /*#__PURE__*/React__namespace.createElement("p", null, "Single-letter variables listed here will be interpreted as functions. This let us know that f(x) means \"f of x\" and not \"f times x\"."))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("div", null, "Button sets:"), buttonSetChoices), /*#__PURE__*/React__namespace.createElement("h3", {
26741
+ })), /*#__PURE__*/React__namespace.createElement(InfoTip$j, null, /*#__PURE__*/React__namespace.createElement("p", null, "Single-letter variables listed here will be interpreted as functions. This let us know that f(x) means \"f of x\" and not \"f times x\"."))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("div", null, "Button sets:"), buttonSetChoices), /*#__PURE__*/React__namespace.createElement("h3", {
26742
26742
  className: "expression-editor-h3"
26743
26743
  }, "Answers"), /*#__PURE__*/React__namespace.createElement("p", {
26744
26744
  style: {
@@ -26952,14 +26952,14 @@ class AnswerOption extends React__namespace.Component {
26952
26952
  onChange: this.props.onChange,
26953
26953
  labelAlignment: "right",
26954
26954
  label: "Answer expression must have the same form."
26955
- }), /*#__PURE__*/React__namespace.createElement(InfoTip$h, null, /*#__PURE__*/React__namespace.createElement("p", null, "The student's answer must be in the same form. Commutativity and excess negative signs are ignored."))), /*#__PURE__*/React__namespace.createElement("div", {
26955
+ }), /*#__PURE__*/React__namespace.createElement(InfoTip$j, null, /*#__PURE__*/React__namespace.createElement("p", null, "The student's answer must be in the same form. Commutativity and excess negative signs are ignored."))), /*#__PURE__*/React__namespace.createElement("div", {
26956
26956
  className: "answer-option"
26957
26957
  }, /*#__PURE__*/React__namespace.createElement(PropCheckBox$a, {
26958
26958
  simplify: this.props.simplify,
26959
26959
  onChange: this.props.onChange,
26960
26960
  labelAlignment: "right",
26961
26961
  label: "Answer expression must be fully expanded and simplified."
26962
- }), /*#__PURE__*/React__namespace.createElement(InfoTip$h, null, /*#__PURE__*/React__namespace.createElement("p", null, "The student's answer must be fully expanded and simplified. Answering this equation (x^2+2x+1) with this factored equation (x+1)^2 will render this response \"Your answer is not fully expanded and simplified.\""))), /*#__PURE__*/React__namespace.createElement("div", {
26962
+ }), /*#__PURE__*/React__namespace.createElement(InfoTip$j, null, /*#__PURE__*/React__namespace.createElement("p", null, "The student's answer must be fully expanded and simplified. Answering this equation (x^2+2x+1) with this factored equation (x+1)^2 will render this response \"Your answer is not fully expanded and simplified.\""))), /*#__PURE__*/React__namespace.createElement("div", {
26963
26963
  className: "remove-container"
26964
26964
  }, removeButton)));
26965
26965
  }
@@ -27037,10 +27037,10 @@ class GradedGroupEditor extends React__namespace.Component {
27037
27037
  }, /*#__PURE__*/React__namespace.createElement("div", {
27038
27038
  className: "perseus-widget-row"
27039
27039
  }, /*#__PURE__*/React__namespace.createElement("label", {
27040
- className: aphrodite.css(styles$t.title)
27040
+ className: aphrodite.css(styles$x.title)
27041
27041
  }, "Title:", " ", /*#__PURE__*/React__namespace.createElement(TextInput$6, {
27042
27042
  value: this.props.title,
27043
- className: aphrodite.css(styles$t.input)
27043
+ className: aphrodite.css(styles$x.input)
27044
27044
  // @ts-expect-error - TS2554 - Expected 3 arguments, but got 1.
27045
27045
  ,
27046
27046
  onChange: this.change("title")
@@ -27065,7 +27065,7 @@ class GradedGroupEditor extends React__namespace.Component {
27065
27065
  }, /*#__PURE__*/React__namespace.createElement(InlineIcon$4, iconPlus$1), " Add a hint"), this.props.hint && /*#__PURE__*/React__namespace.createElement("div", {
27066
27066
  className: "perseus-hint-editor"
27067
27067
  }, /*#__PURE__*/React__namespace.createElement("div", {
27068
- className: aphrodite.css(styles$t.hintsTitle)
27068
+ className: aphrodite.css(styles$x.hintsTitle)
27069
27069
  }, "Hint"), /*#__PURE__*/React__namespace.createElement(Editor, {
27070
27070
  ref: this.hintEditor,
27071
27071
  content: this.props.hint ? this.props.hint.content : "",
@@ -27097,7 +27097,7 @@ class GradedGroupEditor extends React__namespace.Component {
27097
27097
  };
27098
27098
  };
27099
27099
  }
27100
- const styles$t = aphrodite.StyleSheet.create({
27100
+ const styles$x = aphrodite.StyleSheet.create({
27101
27101
  title: {
27102
27102
  fontSize: 18,
27103
27103
  fontWeight: "bold"
@@ -27184,7 +27184,7 @@ const setArrayItem = (list, i, value) => [...list.slice(0, i), value, ...list.sl
27184
27184
  /* eslint-disable react/forbid-prop-types, react/no-unsafe */
27185
27185
  const {
27186
27186
  ButtonGroup: ButtonGroup$4,
27187
- InfoTip: InfoTip$g,
27187
+ InfoTip: InfoTip$i,
27188
27188
  PropCheckBox: PropCheckBox$9,
27189
27189
  RangeInput: RangeInput$6
27190
27190
  } = perseus.components;
@@ -27645,7 +27645,7 @@ const GraphSettings = createReactClass__default["default"]({
27645
27645
  },
27646
27646
  onKeyPress: this.changeBackgroundUrl,
27647
27647
  onBlur: this.changeBackgroundUrl
27648
- }), /*#__PURE__*/React__namespace.createElement(InfoTip$g, null, /*#__PURE__*/React__namespace.createElement("p", null, "Create an image in graphie, or use the \"Add image\" function to create a background.")))), ___default["default"].contains(this.props.editableSettings, "measure") && /*#__PURE__*/React__namespace.createElement("div", {
27648
+ }), /*#__PURE__*/React__namespace.createElement(InfoTip$i, null, /*#__PURE__*/React__namespace.createElement("p", null, "Create an image in graphie, or use the \"Add image\" function to create a background.")))), ___default["default"].contains(this.props.editableSettings, "measure") && /*#__PURE__*/React__namespace.createElement("div", {
27649
27649
  className: "misc-settings"
27650
27650
  }, /*#__PURE__*/React__namespace.createElement("div", {
27651
27651
  className: "perseus-widget-row"
@@ -27683,7 +27683,7 @@ const GraphSettings = createReactClass__default["default"]({
27683
27683
  });
27684
27684
 
27685
27685
  const {
27686
- InfoTip: InfoTip$f,
27686
+ InfoTip: InfoTip$h,
27687
27687
  MultiButtonGroup: MultiButtonGroup$1
27688
27688
  } = perseus.components;
27689
27689
  const {
@@ -27757,7 +27757,7 @@ class GrapherEditor extends React__namespace.Component {
27757
27757
  className: "perseus-error"
27758
27758
  }, this.props.graph.valid);
27759
27759
  }
27760
- return /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("div", null, "Correct answer", " ", /*#__PURE__*/React__namespace.createElement(InfoTip$f, null, /*#__PURE__*/React__namespace.createElement("p", null, "Graph the correct answer in the graph below and ensure the equation or point coordinates displayed represent the correct answer.")), " ", ": ", equationString), /*#__PURE__*/React__namespace.createElement(GraphSettings, {
27760
+ return /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("div", null, "Correct answer", " ", /*#__PURE__*/React__namespace.createElement(InfoTip$h, null, /*#__PURE__*/React__namespace.createElement("p", null, "Graph the correct answer in the graph below and ensure the equation or point coordinates displayed represent the correct answer.")), " ", ": ", equationString), /*#__PURE__*/React__namespace.createElement(GraphSettings, {
27761
27761
  editableSettings: ["graph", "snap", "image"],
27762
27762
  box: getInteractiveBoxFromSizeClass$1(sizeClass),
27763
27763
  range: this.props.graph.range,
@@ -28032,7 +28032,7 @@ class IframeEditor extends React__namespace.Component {
28032
28032
 
28033
28033
  /* eslint-disable jsx-a11y/anchor-is-valid, react/sort-comp */
28034
28034
  const {
28035
- InfoTip: InfoTip$e,
28035
+ InfoTip: InfoTip$g,
28036
28036
  InlineIcon: InlineIcon$3,
28037
28037
  RangeInput: RangeInput$5
28038
28038
  } = perseus.components;
@@ -28089,7 +28089,7 @@ class ImageEditor extends React__namespace.Component {
28089
28089
  style: {
28090
28090
  width: "100%"
28091
28091
  }
28092
- }))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, /*#__PURE__*/React__namespace.createElement("div", null, "Dimensions:"), /*#__PURE__*/React__namespace.createElement("p", null, backgroundImage.width, "x", backgroundImage.height))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, /*#__PURE__*/React__namespace.createElement("div", null, "Alt text:", /*#__PURE__*/React__namespace.createElement(InfoTip$e, null, "This is important for screenreaders. The content of this alt text will be formatted as markdown (tables, emphasis, etc. are supported).")), /*#__PURE__*/React__namespace.createElement(Editor, {
28092
+ }))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, /*#__PURE__*/React__namespace.createElement("div", null, "Dimensions:"), /*#__PURE__*/React__namespace.createElement("p", null, backgroundImage.width, "x", backgroundImage.height))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, /*#__PURE__*/React__namespace.createElement("div", null, "Alt text:", /*#__PURE__*/React__namespace.createElement(InfoTip$g, null, "This is important for screenreaders. The content of this alt text will be formatted as markdown (tables, emphasis, etc. are supported).")), /*#__PURE__*/React__namespace.createElement(Editor, {
28093
28093
  apiOptions: this.props.apiOptions,
28094
28094
  content: this.props.alt,
28095
28095
  onChange: props => {
@@ -28113,7 +28113,7 @@ class ImageEditor extends React__namespace.Component {
28113
28113
  }, this.state.backgroundImageError);
28114
28114
  return /*#__PURE__*/React__namespace.createElement("div", {
28115
28115
  className: "perseus-image-editor"
28116
- }, /*#__PURE__*/React__namespace.createElement("label", null, "Image url:", /*#__PURE__*/React__namespace.createElement(InfoTip$e, null, "Paste an image or graphie image URL."), this.state.backgroundImageError && backgroundImageErrorText, /*#__PURE__*/React__namespace.createElement(BlurInput, {
28116
+ }, /*#__PURE__*/React__namespace.createElement("label", null, "Image url:", /*#__PURE__*/React__namespace.createElement(InfoTip$g, null, "Paste an image or graphie image URL."), this.state.backgroundImageError && backgroundImageErrorText, /*#__PURE__*/React__namespace.createElement(BlurInput, {
28117
28117
  value: backgroundImage.url || "",
28118
28118
  style: {
28119
28119
  width: 332
@@ -28269,7 +28269,7 @@ class ImageEditor extends React__namespace.Component {
28269
28269
 
28270
28270
  /* eslint-disable react/sort-comp */
28271
28271
  const {
28272
- InfoTip: InfoTip$d
28272
+ InfoTip: InfoTip$f
28273
28273
  } = perseus.components;
28274
28274
  const answerTypes = {
28275
28275
  number: {
@@ -28349,7 +28349,7 @@ class InputNumberEditor extends React__namespace.Component {
28349
28349
  value: "optional"
28350
28350
  }, "will be accepted"), /*#__PURE__*/React__namespace.createElement("option", {
28351
28351
  value: "enforced"
28352
- }, "will be marked wrong"))), /*#__PURE__*/React__namespace.createElement(InfoTip$d, null, /*#__PURE__*/React__namespace.createElement("p", null, "Normally select \"will not be graded\". This will give the user a message saying the answer is correct but not simplified. The user will then have to simplify it and re-enter, but will not be penalized. (5th grade and anything after)"), /*#__PURE__*/React__namespace.createElement("p", null, "Select \"will be accepted\" only if the user is not expected to know how to simplify fractions yet. (Anything prior to 5th grade)"), /*#__PURE__*/React__namespace.createElement("p", null, "Select \"will be marked wrong\" only if we are specifically assessing the ability to simplify."))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, /*#__PURE__*/React__namespace.createElement("input", {
28352
+ }, "will be marked wrong"))), /*#__PURE__*/React__namespace.createElement(InfoTip$f, null, /*#__PURE__*/React__namespace.createElement("p", null, "Normally select \"will not be graded\". This will give the user a message saying the answer is correct but not simplified. The user will then have to simplify it and re-enter, but will not be penalized. (5th grade and anything after)"), /*#__PURE__*/React__namespace.createElement("p", null, "Select \"will be accepted\" only if the user is not expected to know how to simplify fractions yet. (Anything prior to 5th grade)"), /*#__PURE__*/React__namespace.createElement("p", null, "Select \"will be marked wrong\" only if we are specifically assessing the ability to simplify."))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, /*#__PURE__*/React__namespace.createElement("input", {
28353
28353
  type: "checkbox",
28354
28354
  checked: this.props.inexact,
28355
28355
  onChange: e => {
@@ -28385,7 +28385,7 @@ class InputNumberEditor extends React__namespace.Component {
28385
28385
  });
28386
28386
  },
28387
28387
  "aria-label": "Answer type"
28388
- }, answerTypeOptions), /*#__PURE__*/React__namespace.createElement(InfoTip$d, null, /*#__PURE__*/React__namespace.createElement("p", null, "Use the default \"Numbers\" unless the answer must be in a specific form (e.g., question is about converting decimals to fractions)."))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, "Width", " ", /*#__PURE__*/React__namespace.createElement("select", {
28388
+ }, answerTypeOptions), /*#__PURE__*/React__namespace.createElement(InfoTip$f, null, /*#__PURE__*/React__namespace.createElement("p", null, "Use the default \"Numbers\" unless the answer must be in a specific form (e.g., question is about converting decimals to fractions)."))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, "Width", " ", /*#__PURE__*/React__namespace.createElement("select", {
28389
28389
  value: this.props.size,
28390
28390
  onChange: e => {
28391
28391
  // @ts-expect-error - TS2322 - Type 'string' is not assignable to type '"small" | "normal" | undefined'.
@@ -28397,7 +28397,7 @@ class InputNumberEditor extends React__namespace.Component {
28397
28397
  value: "normal"
28398
28398
  }, "Normal (80px)"), /*#__PURE__*/React__namespace.createElement("option", {
28399
28399
  value: "small"
28400
- }, "Small (40px)"))), /*#__PURE__*/React__namespace.createElement(InfoTip$d, null, /*#__PURE__*/React__namespace.createElement("p", null, "Use size \"Normal\" for all text boxes, unless there are multiple text boxes in one line and the answer area is too narrow to fit them."))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, /*#__PURE__*/React__namespace.createElement("input", {
28400
+ }, "Small (40px)"))), /*#__PURE__*/React__namespace.createElement(InfoTip$f, null, /*#__PURE__*/React__namespace.createElement("p", null, "Use size \"Normal\" for all text boxes, unless there are multiple text boxes in one line and the answer area is too narrow to fit them."))), /*#__PURE__*/React__namespace.createElement("div", null, /*#__PURE__*/React__namespace.createElement("label", null, /*#__PURE__*/React__namespace.createElement("input", {
28401
28401
  type: "checkbox",
28402
28402
  checked: this.props.rightAlign,
28403
28403
  onChange: e => {
@@ -28468,13 +28468,13 @@ function MathquillInput(props) {
28468
28468
  }
28469
28469
  });
28470
28470
  return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
28471
- style: styles$s.outerWrapper
28471
+ style: styles$w.outerWrapper
28472
28472
  }, /*#__PURE__*/React__namespace.createElement("span", {
28473
28473
  ref: mathFieldWrapperRef,
28474
28474
  className: "perseus-math-input mq-editable-field mq-math-mode"
28475
28475
  }));
28476
28476
  }
28477
- const styles$s = aphrodite.StyleSheet.create({
28477
+ const styles$w = aphrodite.StyleSheet.create({
28478
28478
  outerWrapper: {
28479
28479
  display: "inline-block",
28480
28480
  borderStyle: "solid",
@@ -29560,7 +29560,7 @@ const GraphPointsCountSelector = _ref => {
29560
29560
  // Never uses placeholder, always has value
29561
29561
  ,
29562
29562
  placeholder: "",
29563
- style: styles$r.singleSelectShort
29563
+ style: styles$v.singleSelectShort
29564
29564
  }, [...[...Array(7).keys()].map(n => /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.OptionItem, {
29565
29565
  key: n,
29566
29566
  value: `${n}`,
@@ -29571,7 +29571,7 @@ const GraphPointsCountSelector = _ref => {
29571
29571
  label: "unlimited"
29572
29572
  })]);
29573
29573
  };
29574
- const styles$r = aphrodite.StyleSheet.create({
29574
+ const styles$v = aphrodite.StyleSheet.create({
29575
29575
  singleSelectShort: {
29576
29576
  // Non-standard spacing, but it's the smallest we can go
29577
29577
  // without running into styling issues with the dropdown.
@@ -29584,7 +29584,7 @@ const GraphTypeSelector = props => {
29584
29584
  selectedValue: props.graphType,
29585
29585
  onChange: props.onChange,
29586
29586
  placeholder: "Select a graph type",
29587
- style: styles$q.singleSelectShort
29587
+ style: styles$u.singleSelectShort
29588
29588
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.OptionItem, {
29589
29589
  value: "linear",
29590
29590
  label: "Linear function"
@@ -29617,7 +29617,7 @@ const GraphTypeSelector = props => {
29617
29617
  label: "Angle"
29618
29618
  }));
29619
29619
  };
29620
- const styles$q = aphrodite.StyleSheet.create({
29620
+ const styles$u = aphrodite.StyleSheet.create({
29621
29621
  singleSelectShort: {
29622
29622
  // Non-standard spacing, but it's the smallest we can go
29623
29623
  // without running into styling issues with the dropdown.
@@ -29634,16 +29634,16 @@ const LabeledRow = props => {
29634
29634
  style
29635
29635
  } = props;
29636
29636
  return /*#__PURE__*/React__namespace.createElement("label", {
29637
- className: aphrodite.css(styles$p.label)
29637
+ className: aphrodite.css(styles$t.label)
29638
29638
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
29639
- style: [styles$p.row, style]
29639
+ style: [styles$t.row, style]
29640
29640
  }, labelSide === "start" || /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelSmall, {
29641
- style: styles$p.spaceEnd
29641
+ style: styles$t.spaceEnd
29642
29642
  }, label), children, labelSide === "end" && /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelSmall, {
29643
- style: styles$p.spaceStart
29643
+ style: styles$t.spaceStart
29644
29644
  }, label)));
29645
29645
  };
29646
- const styles$p = aphrodite.StyleSheet.create({
29646
+ const styles$t = aphrodite.StyleSheet.create({
29647
29647
  label: {
29648
29648
  width: "fit-content"
29649
29649
  },
@@ -29664,7 +29664,7 @@ const styles$p = aphrodite.StyleSheet.create({
29664
29664
  /* eslint-disable react/forbid-prop-types, react/no-unsafe */
29665
29665
  const {
29666
29666
  ButtonGroup: ButtonGroup$2,
29667
- InfoTip: InfoTip$c,
29667
+ InfoTip: InfoTip$e,
29668
29668
  PropCheckBox: PropCheckBox$7,
29669
29669
  RangeInput: RangeInput$4
29670
29670
  } = perseus.components;
@@ -30099,10 +30099,10 @@ class InteractiveGraphSettings extends React__namespace.Component {
30099
30099
  onChange: this.change
30100
30100
  }))), /*#__PURE__*/React__namespace.createElement(LabeledRow, {
30101
30101
  label: "Background image URL:",
30102
- style: styles$o.resetSpaceTop
30102
+ style: styles$s.resetSpaceTop
30103
30103
  }, /*#__PURE__*/React__namespace.createElement("input", {
30104
30104
  type: "text",
30105
- className: aphrodite.css(styles$o.backgroundUrlInput),
30105
+ className: aphrodite.css(styles$s.backgroundUrlInput),
30106
30106
  ref: this.bgUrlRef,
30107
30107
  value: this.state.backgroundImage.url || "",
30108
30108
  onChange: e => {
@@ -30117,29 +30117,29 @@ class InteractiveGraphSettings extends React__namespace.Component {
30117
30117
  },
30118
30118
  onKeyPress: this.changeBackgroundUrl,
30119
30119
  onBlur: this.changeBackgroundUrl
30120
- }), /*#__PURE__*/React__namespace.createElement(InfoTip$c, null, /*#__PURE__*/React__namespace.createElement("p", null, "Create an image in graphie, or use the \"Add image\" function to create a background."))), /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30121
- style: styles$o.rulerSection
30120
+ }), /*#__PURE__*/React__namespace.createElement(InfoTip$e, null, /*#__PURE__*/React__namespace.createElement("p", null, "Create an image in graphie, or use the \"Add image\" function to create a background."))), /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30121
+ style: styles$s.rulerSection
30122
30122
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30123
- style: styles$o.checkboxRow
30123
+ style: styles$s.checkboxRow
30124
30124
  }, /*#__PURE__*/React__namespace.createElement(PropCheckBox$7, {
30125
30125
  label: "Show ruler",
30126
30126
  showRuler: this.props.showRuler,
30127
30127
  onChange: this.change,
30128
- style: styles$o.resetSpaceTop
30128
+ style: styles$s.resetSpaceTop
30129
30129
  }), /*#__PURE__*/React__namespace.createElement(PropCheckBox$7, {
30130
30130
  label: "Show protractor",
30131
30131
  showProtractor: this.props.showProtractor,
30132
30132
  onChange: this.change,
30133
- style: styles$o.resetSpaceTop
30133
+ style: styles$s.resetSpaceTop
30134
30134
  })), (this.props.showRuler || this.props.showProtractor) && /*#__PURE__*/React__namespace.createElement(Banner__default["default"], {
30135
30135
  layout: "floating",
30136
30136
  text: "The ruler and protractor are not accessible. Please consider an alternate approach.",
30137
30137
  kind: "warning"
30138
30138
  }), this.props.showRuler && /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30139
- style: styles$o.spaceTop
30139
+ style: styles$s.spaceTop
30140
30140
  }, /*#__PURE__*/React__namespace.createElement(LabeledRow, {
30141
30141
  label: "Ruler label:",
30142
- style: styles$o.resetSpaceTop
30142
+ style: styles$s.resetSpaceTop
30143
30143
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.SingleSelect, {
30144
30144
  id: "ruler-label-select",
30145
30145
  selectedValue: this.props.rulerLabel,
@@ -30149,7 +30149,7 @@ class InteractiveGraphSettings extends React__namespace.Component {
30149
30149
  });
30150
30150
  },
30151
30151
  placeholder: "None",
30152
- style: styles$o.singleSelectShort
30152
+ style: styles$s.singleSelectShort
30153
30153
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.OptionItem, {
30154
30154
  value: "",
30155
30155
  label: "None",
@@ -30190,7 +30190,7 @@ class InteractiveGraphSettings extends React__namespace.Component {
30190
30190
  });
30191
30191
  },
30192
30192
  placeholder: "10",
30193
- style: styles$o.singleSelectShort
30193
+ style: styles$s.singleSelectShort
30194
30194
  }, [1, 2, 4, 8, 10, 16].map(value => /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.OptionItem, {
30195
30195
  key: value,
30196
30196
  value: `${value}`,
@@ -30198,7 +30198,7 @@ class InteractiveGraphSettings extends React__namespace.Component {
30198
30198
  }))))))));
30199
30199
  }
30200
30200
  }
30201
- const styles$o = aphrodite.StyleSheet.create({
30201
+ const styles$s = aphrodite.StyleSheet.create({
30202
30202
  resetSpaceTop: {
30203
30203
  marginTop: 0
30204
30204
  },
@@ -30322,22 +30322,19 @@ const LockedFigureSelect = props => {
30322
30322
  id,
30323
30323
  onChange
30324
30324
  } = props;
30325
+ const figureTypes = props.showM2Features ? ["point", "line", "ellipse", "vector"] : ["point", "line"];
30325
30326
  return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30326
- style: styles$n.container
30327
+ style: styles$r.container
30327
30328
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.ActionMenu, {
30328
30329
  menuText: "Add locked figure",
30329
- style: styles$n.addElementSelect
30330
- }, [/*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.ActionItem, {
30331
- key: `${id}-point`,
30332
- label: "Point",
30333
- onClick: () => onChange("point")
30334
- }, "Point"), /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.ActionItem, {
30335
- key: `${id}-line`,
30336
- label: "Line",
30337
- onClick: () => onChange("line")
30338
- }, "Line")]));
30330
+ style: styles$r.addElementSelect
30331
+ }, figureTypes.map(figureType => /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.ActionItem, {
30332
+ key: `${id}-${figureType}`,
30333
+ label: figureType,
30334
+ onClick: () => onChange(figureType)
30335
+ }, figureType))));
30339
30336
  };
30340
- const styles$n = aphrodite.StyleSheet.create({
30337
+ const styles$r = aphrodite.StyleSheet.create({
30341
30338
  container: {
30342
30339
  marginTop: wonderBlocksTokens.spacing.xSmall_8
30343
30340
  },
@@ -30347,6 +30344,80 @@ const styles$n = aphrodite.StyleSheet.create({
30347
30344
  }
30348
30345
  });
30349
30346
 
30347
+ const {
30348
+ InfoTip: InfoTip$d
30349
+ } = perseus.components;
30350
+ const degreeToRadian = degrees => {
30351
+ return degrees / 180 * Math.PI;
30352
+ };
30353
+ const AngleInput = props => {
30354
+ const {
30355
+ angle,
30356
+ onChange
30357
+ } = props;
30358
+ const [angleInput, setAngleInput] = React__namespace.useState(angle.toString());
30359
+ const [isInDegrees, setIsInDegrees] = React__namespace.useState(false);
30360
+ function handleAngleChange(newValue) {
30361
+ let useDegrees = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : isInDegrees;
30362
+ // Update the local state (update the input field value).
30363
+ setAngleInput(newValue);
30364
+ try {
30365
+ // If the new value is a valid expression, update the props.
30366
+ // Save the angle in radians.
30367
+ const evaluatedAngle = KAS__namespace.parse(newValue).expr.eval();
30368
+ if (useDegrees) {
30369
+ onChange(degreeToRadian(evaluatedAngle));
30370
+ } else {
30371
+ onChange(evaluatedAngle);
30372
+ }
30373
+ } catch (e) {
30374
+ // The user likely has not finished typing the expression.
30375
+ // Do nothing.
30376
+ return;
30377
+ }
30378
+ }
30379
+ function handleAngleTypeChange() {
30380
+ // Change the angle based on the new angle type.
30381
+ handleAngleChange(angleInput, !isInDegrees);
30382
+
30383
+ // Update the angle to the new type.
30384
+ setIsInDegrees(usingDegrees => !usingDegrees);
30385
+ }
30386
+ return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30387
+ style: [styles$q.row, styles$q.spaceUnder]
30388
+ }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30389
+ tag: "label",
30390
+ style: styles$q.row
30391
+ }, "angle", /*#__PURE__*/React__namespace.createElement(Strut, {
30392
+ size: wonderBlocksTokens.spacing.xxSmall_6
30393
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksForm.TextField, {
30394
+ value: angleInput,
30395
+ onChange: handleAngleChange,
30396
+ style: styles$q.textField
30397
+ })), /*#__PURE__*/React__namespace.createElement(Strut, {
30398
+ size: wonderBlocksTokens.spacing.xxSmall_6
30399
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelSmall, null, "radians"), /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30400
+ style: styles$q.switch
30401
+ }, /*#__PURE__*/React__namespace.createElement(Switch__default["default"], {
30402
+ onChange: handleAngleTypeChange,
30403
+ checked: isInDegrees
30404
+ })), /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelSmall, null, "degrees"), /*#__PURE__*/React__namespace.createElement(InfoTip$d, null, /*#__PURE__*/React__namespace.createElement("p", null, "The angle of rotation for the ellipse (if the x radius and y radius are different)."), /*#__PURE__*/React__namespace.createElement("p", null, "Expressions will be evaluted (e.g. \"pi/2\" or \"5pi/4\").")));
30405
+ };
30406
+ const styles$q = aphrodite.StyleSheet.create({
30407
+ row: {
30408
+ display: "flex",
30409
+ flexDirection: "row",
30410
+ alignItems: "center"
30411
+ },
30412
+ switch: {
30413
+ marginLeft: wonderBlocksTokens.spacing.xxSmall_6,
30414
+ marginRight: wonderBlocksTokens.spacing.xxSmall_6
30415
+ },
30416
+ textField: {
30417
+ maxWidth: wonderBlocksTokens.spacing.xxxLarge_64
30418
+ }
30419
+ });
30420
+
30350
30421
  const ColorSwatch = props => {
30351
30422
  const {
30352
30423
  color,
@@ -30357,13 +30428,13 @@ const ColorSwatch = props => {
30357
30428
  "aria-label":
30358
30429
  // Don't include an aria label for decorative circles.
30359
30430
  !decorative ? `${color}, ${filled ? "filled" : "open"}` : undefined,
30360
- style: [styles$m.colorSwatch, {
30431
+ style: [styles$p.colorSwatch, {
30361
30432
  border: `4px solid ${perseus.lockedFigureColors[color]}`,
30362
30433
  backgroundColor: filled ? perseus.lockedFigureColors[color] : wonderBlocksTokens.color.white
30363
30434
  }]
30364
30435
  });
30365
30436
  };
30366
- const styles$m = aphrodite.StyleSheet.create({
30437
+ const styles$p = aphrodite.StyleSheet.create({
30367
30438
  colorSwatch: {
30368
30439
  // Add a white outline so that the color swatch is visible when
30369
30440
  // the dropdown option is highlighted with its blue background.
@@ -30381,16 +30452,14 @@ const ColorSelect = props => {
30381
30452
  style,
30382
30453
  onChange
30383
30454
  } = props;
30384
- const ids = wonderBlocksCore.useUniqueIdWithMock();
30385
- const id = ids.get("color-select");
30386
30455
  return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30387
- style: [styles$l.row, style]
30456
+ style: [styles$o.row, style]
30388
30457
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30389
- htmlFor: id,
30390
- style: styles$l.label,
30391
- tag: "label"
30392
- }, "color"), /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.SingleSelect, {
30393
- id: id,
30458
+ tag: "label",
30459
+ style: styles$o.row
30460
+ }, "color", /*#__PURE__*/React__namespace.createElement(Strut, {
30461
+ size: wonderBlocksTokens.spacing.xxSmall_6
30462
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.SingleSelect, {
30394
30463
  selectedValue: selectedValue,
30395
30464
  onChange: onChange
30396
30465
  // Placeholder is required, but never gets used.
@@ -30404,23 +30473,22 @@ const ColorSelect = props => {
30404
30473
  color: colorName,
30405
30474
  decorative: true
30406
30475
  })
30407
- }, colorName))));
30476
+ }, colorName)))));
30408
30477
  };
30409
- const styles$l = aphrodite.StyleSheet.create({
30478
+ const styles$o = aphrodite.StyleSheet.create({
30410
30479
  row: {
30480
+ display: "flex",
30411
30481
  flexDirection: "row",
30412
30482
  alignItems: "center"
30413
- },
30414
- label: {
30415
- marginInlineEnd: wonderBlocksTokens.spacing.xxxSmall_4
30416
30483
  }
30417
30484
  });
30418
30485
 
30419
30486
  const CoordinatePairInput = props => {
30420
30487
  const {
30421
30488
  coord,
30489
+ labels,
30422
30490
  error,
30423
- onChangeProps
30491
+ onChange
30424
30492
  } = props;
30425
30493
 
30426
30494
  // Keep track of the coordinates via state as the user is editing them,
@@ -30428,12 +30496,6 @@ const CoordinatePairInput = props => {
30428
30496
  const [coordState, setCoordState] = React__namespace.useState([
30429
30497
  // Using strings to make it easier to work with the text fields.
30430
30498
  coord[0].toString(), coord[1].toString()]);
30431
-
30432
- // Generate unique IDs so that the programmatic labels can be associated
30433
- // with their respective text fields.
30434
- const ids = wonderBlocksCore.useUniqueIdWithMock();
30435
- const xCoordId = ids.get("x-coord");
30436
- const yCoordId = ids.get("y-coord");
30437
30499
  function handleCoordChange(newValue, coordIndex) {
30438
30500
  // Update the local state (update the input field value).
30439
30501
  const newCoordState = [...coordState];
@@ -30449,47 +30511,43 @@ const CoordinatePairInput = props => {
30449
30511
  // Update the props (update the graph).
30450
30512
  const newCoords = [...coord];
30451
30513
  newCoords[coordIndex] = +newValue;
30452
- onChangeProps({
30453
- coord: newCoords
30454
- });
30514
+ onChange(newCoords);
30455
30515
  }
30456
30516
  return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, null, /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30457
- style: [styles$k.row, styles$k.spaceUnder]
30517
+ style: [styles$n.row, styles$n.spaceUnder]
30458
30518
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30459
- htmlFor: xCoordId,
30460
- style: styles$k.label,
30461
- tag: "label"
30462
- }, "x coord"), /*#__PURE__*/React__namespace.createElement(wonderBlocksForm.TextField, {
30463
- id: xCoordId,
30519
+ tag: "label",
30520
+ style: styles$n.row
30521
+ }, labels ? labels[0] : "x coord", /*#__PURE__*/React__namespace.createElement(Strut, {
30522
+ size: wonderBlocksTokens.spacing.xxSmall_6
30523
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksForm.TextField, {
30464
30524
  type: "number",
30465
30525
  value: coordState[0],
30466
30526
  onChange: newValue => handleCoordChange(newValue, 0),
30467
- style: [styles$k.textField, error ? styles$k.errorField : undefined]
30468
- }), /*#__PURE__*/React__namespace.createElement(Strut, {
30527
+ style: [styles$n.textField, error ? styles$n.errorField : undefined]
30528
+ })), /*#__PURE__*/React__namespace.createElement(Strut, {
30469
30529
  size: wonderBlocksTokens.spacing.medium_16
30470
30530
  }), /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30471
- htmlFor: yCoordId,
30472
- style: styles$k.label,
30473
- tag: "label"
30474
- }, "y coord"), /*#__PURE__*/React__namespace.createElement(wonderBlocksForm.TextField, {
30475
- id: yCoordId,
30531
+ tag: "label",
30532
+ style: styles$n.row
30533
+ }, labels ? labels[1] : "y coord", /*#__PURE__*/React__namespace.createElement(Strut, {
30534
+ size: wonderBlocksTokens.spacing.xxSmall_6
30535
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksForm.TextField, {
30476
30536
  type: "number",
30477
30537
  value: coordState[1],
30478
30538
  onChange: newValue => handleCoordChange(newValue, 1),
30479
- style: [styles$k.textField, error ? styles$k.errorField : undefined]
30480
- })));
30539
+ style: [styles$n.textField, error ? styles$n.errorField : undefined]
30540
+ }))));
30481
30541
  };
30482
- const styles$k = aphrodite.StyleSheet.create({
30542
+ const styles$n = aphrodite.StyleSheet.create({
30483
30543
  row: {
30544
+ display: "flex",
30484
30545
  flexDirection: "row",
30485
30546
  alignItems: "center"
30486
30547
  },
30487
30548
  spaceUnder: {
30488
30549
  marginBottom: wonderBlocksTokens.spacing.xSmall_8
30489
30550
  },
30490
- label: {
30491
- marginInlineEnd: wonderBlocksTokens.spacing.xxSmall_6
30492
- },
30493
30551
  textField: {
30494
30552
  width: wonderBlocksTokens.spacing.xxxLarge_64
30495
30553
  },
@@ -30499,32 +30557,40 @@ const styles$k = aphrodite.StyleSheet.create({
30499
30557
  }
30500
30558
  });
30501
30559
 
30502
- const LabeledSwitch = props => {
30560
+ const EllipseSwatch = props => {
30503
30561
  const {
30504
- checked,
30505
- label,
30506
- style,
30507
- onChange
30562
+ color,
30563
+ fillStyle,
30564
+ strokeStyle
30508
30565
  } = props;
30509
- const ids = wonderBlocksCore.useUniqueIdWithMock();
30510
- const switchId = ids.get("switch");
30511
30566
  return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30512
- style: [styles$j.row, style]
30513
- }, /*#__PURE__*/React__namespace.createElement(Switch__default["default"], {
30514
- id: switchId,
30515
- checked: checked,
30516
- onChange: onChange
30517
- }), /*#__PURE__*/React__namespace.createElement(Strut, {
30518
- size: wonderBlocksTokens.spacing.xSmall_8
30519
- }), /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30520
- tag: "label",
30521
- htmlFor: switchId
30522
- }, label));
30567
+ "aria-label": `${color}, stroke ${strokeStyle}, fill ${fillStyle}`,
30568
+ style: [styles$m.container, {
30569
+ border: `4px ${strokeStyle} ${perseus.lockedFigureColors[color]}`
30570
+ }]
30571
+ }, /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30572
+ style: [styles$m.innerCircle, {
30573
+ backgroundColor: perseus.lockedFigureColors[color],
30574
+ opacity: perseus.lockedEllipseFillStyles[fillStyle]
30575
+ }]
30576
+ }));
30523
30577
  };
30524
- const styles$j = aphrodite.StyleSheet.create({
30525
- row: {
30526
- flexDirection: "row",
30527
- alignItems: "center"
30578
+ const styles$m = aphrodite.StyleSheet.create({
30579
+ container: {
30580
+ // Add a white outline so that the color swatch is visible when
30581
+ // the dropdown option is highlighted with its blue background.
30582
+ outline: `2px solid ${wonderBlocksTokens.color.offWhite}`,
30583
+ borderRadius: "50%",
30584
+ width: wonderBlocksTokens.spacing.xLarge_32,
30585
+ height: wonderBlocksTokens.spacing.large_24,
30586
+ backgroundColor: wonderBlocksTokens.color.white,
30587
+ alignItems: "center",
30588
+ justifyContent: "center"
30589
+ },
30590
+ innerCircle: {
30591
+ width: 28,
30592
+ height: 20,
30593
+ borderRadius: "50%"
30528
30594
  }
30529
30595
  });
30530
30596
 
@@ -30546,14 +30612,14 @@ const LockedFigureSettingsAccordion = props => {
30546
30612
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksAccordion.AccordionSection, {
30547
30613
  expanded: expanded,
30548
30614
  onToggle: onToggle,
30549
- style: [styles$i.container, containerStyle],
30550
- headerStyle: styles$i.accordionHeader,
30615
+ style: [styles$l.container, containerStyle],
30616
+ headerStyle: styles$l.accordionHeader,
30551
30617
  header: header
30552
30618
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30553
- style: [styles$i.accordionPanel, panelStyle]
30619
+ style: [styles$l.accordionPanel, panelStyle]
30554
30620
  }, children)));
30555
30621
  };
30556
- const styles$i = aphrodite.StyleSheet.create({
30622
+ const styles$l = aphrodite.StyleSheet.create({
30557
30623
  container: {
30558
30624
  backgroundColor: wonderBlocksTokens.color.fadedBlue8,
30559
30625
  marginTop: wonderBlocksTokens.spacing.xSmall_8
@@ -30574,6 +30640,185 @@ const styles$i = aphrodite.StyleSheet.create({
30574
30640
  }
30575
30641
  });
30576
30642
 
30643
+ /**
30644
+ * The part of a locked figure settings panel that contains actions
30645
+ * for this panel and its associated locked figure, including
30646
+ * the delete button.
30647
+ */
30648
+ const LockedFigureSettingsActions = props => {
30649
+ const {
30650
+ onRemove,
30651
+ figureAriaLabel
30652
+ } = props;
30653
+ return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30654
+ style: styles$k.container
30655
+ }, /*#__PURE__*/React__namespace.createElement(Button__default["default"], {
30656
+ startIcon: trashIcon__default["default"],
30657
+ "aria-label": `Delete ${figureAriaLabel}`,
30658
+ onClick: onRemove,
30659
+ kind: "tertiary",
30660
+ style: styles$k.deleteButton
30661
+ }, "Delete"));
30662
+ };
30663
+ const styles$k = aphrodite.StyleSheet.create({
30664
+ container: {
30665
+ width: "100%",
30666
+ flexDirection: "row",
30667
+ alignItems: "center",
30668
+ marginTop: wonderBlocksTokens.spacing.xxxSmall_4
30669
+ },
30670
+ deleteButton: {
30671
+ // Line up the delete icon with the rest of the content.
30672
+ marginInlineStart: -wonderBlocksTokens.spacing.xxxSmall_4
30673
+ }
30674
+ });
30675
+
30676
+ const {
30677
+ InfoTip: InfoTip$c
30678
+ } = perseus.components;
30679
+ const LockedEllipseSettings = props => {
30680
+ const {
30681
+ center,
30682
+ radius,
30683
+ angle,
30684
+ color,
30685
+ fillStyle,
30686
+ strokeStyle,
30687
+ expanded,
30688
+ onToggle,
30689
+ onChangeProps,
30690
+ onRemove
30691
+ } = props;
30692
+ function handleColorChange(newValue) {
30693
+ onChangeProps({
30694
+ color: newValue
30695
+ });
30696
+ }
30697
+ return /*#__PURE__*/React__namespace.createElement(LockedFigureSettingsAccordion, {
30698
+ expanded: expanded,
30699
+ onToggle: onToggle,
30700
+ header:
30701
+ /*#__PURE__*/
30702
+ // Summary: Ellipse, center, radius, color (opacity, dashed)
30703
+ React__namespace.createElement(wonderBlocksCore.View, {
30704
+ style: styles$j.row
30705
+ }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelLarge, null, `Ellipse (${center[0]}, ${center[1]}), radius ${radius[0]}, ${radius[1]}`), /*#__PURE__*/React__namespace.createElement(Strut, {
30706
+ size: wonderBlocksTokens.spacing.xSmall_8
30707
+ }), /*#__PURE__*/React__namespace.createElement(EllipseSwatch, {
30708
+ color: props.color,
30709
+ fillStyle: fillStyle,
30710
+ strokeStyle: strokeStyle
30711
+ }))
30712
+ }, /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30713
+ style: styles$j.row
30714
+ }, /*#__PURE__*/React__namespace.createElement(CoordinatePairInput, {
30715
+ coord: center,
30716
+ onChange: newCoords => onChangeProps({
30717
+ center: newCoords
30718
+ })
30719
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30720
+ style: styles$j.spaceUnder
30721
+ }, /*#__PURE__*/React__namespace.createElement(InfoTip$c, null, "The coordinates for the center of the ellipse."))), /*#__PURE__*/React__namespace.createElement(CoordinatePairInput, {
30722
+ coord: radius,
30723
+ labels: ["x radius", "y radius"],
30724
+ onChange: newCoords => onChangeProps({
30725
+ radius: newCoords
30726
+ })
30727
+ }), /*#__PURE__*/React__namespace.createElement(AngleInput, {
30728
+ angle: angle,
30729
+ onChange: newAngle => onChangeProps({
30730
+ angle: newAngle
30731
+ })
30732
+ }), /*#__PURE__*/React__namespace.createElement(Strut, {
30733
+ size: wonderBlocksTokens.spacing.xSmall_8
30734
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30735
+ style: [styles$j.row, styles$j.spaceUnder]
30736
+ }, /*#__PURE__*/React__namespace.createElement(ColorSelect, {
30737
+ selectedValue: color,
30738
+ onChange: handleColorChange
30739
+ }), /*#__PURE__*/React__namespace.createElement(Strut, {
30740
+ size: wonderBlocksTokens.spacing.medium_16
30741
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30742
+ tag: "label",
30743
+ style: styles$j.row
30744
+ }, "fill", /*#__PURE__*/React__namespace.createElement(Strut, {
30745
+ size: wonderBlocksTokens.spacing.xxSmall_6
30746
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.SingleSelect, {
30747
+ selectedValue: fillStyle,
30748
+ onChange: value => onChangeProps({
30749
+ fillStyle: value
30750
+ })
30751
+ // Placeholder is required, but never gets used.
30752
+ ,
30753
+ placeholder: ""
30754
+ }, Object.keys(perseus.lockedEllipseFillStyles).map(option => /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.OptionItem, {
30755
+ key: option,
30756
+ value: option,
30757
+ label: option
30758
+ }, option))))), /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30759
+ tag: "label",
30760
+ style: styles$j.row
30761
+ }, "stroke", /*#__PURE__*/React__namespace.createElement(Strut, {
30762
+ size: wonderBlocksTokens.spacing.xxSmall_6
30763
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.SingleSelect, {
30764
+ selectedValue: strokeStyle,
30765
+ onChange: value => onChangeProps({
30766
+ strokeStyle: value
30767
+ })
30768
+ // Placeholder is required, but never gets used.
30769
+ ,
30770
+ placeholder: ""
30771
+ }, /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.OptionItem, {
30772
+ value: "solid",
30773
+ label: "solid"
30774
+ }, "solid"), /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.OptionItem, {
30775
+ value: "dashed",
30776
+ label: "dashed"
30777
+ }, "dashed"))), /*#__PURE__*/React__namespace.createElement(LockedFigureSettingsActions, {
30778
+ onRemove: onRemove,
30779
+ figureAriaLabel: `locked ellipse at ${center[0]}, ${center[1]}`
30780
+ }));
30781
+ };
30782
+ const styles$j = aphrodite.StyleSheet.create({
30783
+ row: {
30784
+ display: "flex",
30785
+ flexDirection: "row",
30786
+ alignItems: "center"
30787
+ },
30788
+ spaceUnder: {
30789
+ marginBottom: wonderBlocksTokens.spacing.xSmall_8
30790
+ }
30791
+ });
30792
+
30793
+ const LabeledSwitch = props => {
30794
+ const {
30795
+ checked,
30796
+ label,
30797
+ style,
30798
+ onChange
30799
+ } = props;
30800
+ const ids = wonderBlocksCore.useUniqueIdWithMock();
30801
+ const switchId = ids.get("switch");
30802
+ return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30803
+ style: [styles$i.row, style]
30804
+ }, /*#__PURE__*/React__namespace.createElement(Switch__default["default"], {
30805
+ id: switchId,
30806
+ checked: checked,
30807
+ onChange: onChange
30808
+ }), /*#__PURE__*/React__namespace.createElement(Strut, {
30809
+ size: wonderBlocksTokens.spacing.xSmall_8
30810
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30811
+ tag: "label",
30812
+ htmlFor: switchId
30813
+ }, label));
30814
+ };
30815
+ const styles$i = aphrodite.StyleSheet.create({
30816
+ row: {
30817
+ flexDirection: "row",
30818
+ alignItems: "center"
30819
+ }
30820
+ });
30821
+
30577
30822
  /**
30578
30823
  * DefiningPointSettings is a component that allows the user to edit the
30579
30824
  * settings of a point that defines a locked figure (ex. line) on the graph.
@@ -30615,7 +30860,11 @@ const DefiningPointSettings = props => {
30615
30860
  }, /*#__PURE__*/React__namespace.createElement(CoordinatePairInput, {
30616
30861
  coord: coord,
30617
30862
  error: !!error,
30618
- onChangeProps: onChangeProps
30863
+ onChange: newCoords => {
30864
+ onChangeProps({
30865
+ coord: newCoords
30866
+ });
30867
+ }
30619
30868
  }), onTogglePoint && /*#__PURE__*/React__namespace.createElement(LabeledSwitch, {
30620
30869
  label: "show point on graph",
30621
30870
  checked: !!showPoint,
@@ -30682,39 +30931,6 @@ const styles$g = aphrodite.StyleSheet.create({
30682
30931
  }
30683
30932
  });
30684
30933
 
30685
- /**
30686
- * The part of a locked figure settings panel that contains actions
30687
- * for this panel and its associated locked figure, including
30688
- * the delete button.
30689
- */
30690
- const LockedFigureSettingsActions = props => {
30691
- const {
30692
- onRemove,
30693
- figureAriaLabel
30694
- } = props;
30695
- return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30696
- style: styles$f.container
30697
- }, /*#__PURE__*/React__namespace.createElement(Button__default["default"], {
30698
- startIcon: trashIcon__default["default"],
30699
- "aria-label": `Delete ${figureAriaLabel}`,
30700
- onClick: onRemove,
30701
- kind: "tertiary",
30702
- style: styles$f.deleteButton
30703
- }, "Delete"));
30704
- };
30705
- const styles$f = aphrodite.StyleSheet.create({
30706
- container: {
30707
- width: "100%",
30708
- flexDirection: "row",
30709
- alignItems: "center",
30710
- marginTop: wonderBlocksTokens.spacing.xxxSmall_4
30711
- },
30712
- deleteButton: {
30713
- // Line up the delete icon with the rest of the content.
30714
- marginInlineStart: -wonderBlocksTokens.spacing.xxxSmall_4
30715
- }
30716
- });
30717
-
30718
30934
  const lengthZeroStr = "The line cannot have length 0.";
30719
30935
  const LockedLineSettings = props => {
30720
30936
  const {
@@ -30728,12 +30944,6 @@ const LockedLineSettings = props => {
30728
30944
  onRemove
30729
30945
  } = props;
30730
30946
  const [point1, point2] = points;
30731
-
30732
- // Generate unique IDs so that the programmatic labels can be associated
30733
- // with their respective text fields.
30734
- const ids = wonderBlocksCore.useUniqueIdWithMock();
30735
- const kindSelectId = ids.get("line-kind-select");
30736
- const styleSelectId = ids.get("line-style-select");
30737
30947
  const capitalizeKind = kind.charAt(0).toUpperCase() + kind.slice(1);
30738
30948
  const lineLabel = `${capitalizeKind} (${point1.coord[0]},
30739
30949
  ${point1.coord[1]}), (${point2.coord[0]}, ${point2.coord[1]})`;
@@ -30767,21 +30977,19 @@ const LockedLineSettings = props => {
30767
30977
  expanded: props.expanded,
30768
30978
  onToggle: props.onToggle,
30769
30979
  header: /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30770
- style: styles$e.row
30980
+ style: styles$f.row
30771
30981
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelLarge, null, lineLabel), /*#__PURE__*/React__namespace.createElement(Strut, {
30772
30982
  size: wonderBlocksTokens.spacing.xSmall_8
30773
30983
  }), /*#__PURE__*/React__namespace.createElement(LineSwatch, {
30774
30984
  color: lineColor,
30775
30985
  lineStyle: lineStyle
30776
30986
  }))
30777
- }, /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30778
- style: [styles$e.row, styles$e.spaceUnder]
30779
30987
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30780
- htmlFor: kindSelectId,
30781
- style: styles$e.label,
30782
- tag: "label"
30783
- }, "kind"), /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.SingleSelect, {
30784
- id: kindSelectId,
30988
+ tag: "label",
30989
+ style: [styles$f.row, styles$f.spaceUnder]
30990
+ }, "kind", /*#__PURE__*/React__namespace.createElement(Strut, {
30991
+ size: wonderBlocksTokens.spacing.xxxSmall_4
30992
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.SingleSelect, {
30785
30993
  selectedValue: kind,
30786
30994
  onChange: value => onChangeProps({
30787
30995
  kind: value
@@ -30799,20 +31007,18 @@ const LockedLineSettings = props => {
30799
31007
  value: "segment",
30800
31008
  label: "segment"
30801
31009
  }))), /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30802
- style: [styles$e.row, styles$e.spaceUnder]
31010
+ style: styles$f.row
30803
31011
  }, /*#__PURE__*/React__namespace.createElement(ColorSelect, {
30804
31012
  selectedValue: lineColor,
30805
31013
  onChange: handleColorChange
30806
31014
  }), /*#__PURE__*/React__namespace.createElement(Strut, {
30807
31015
  size: wonderBlocksTokens.spacing.small_12
30808
- }), /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
30809
- style: styles$e.row
30810
- }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30811
- htmlFor: styleSelectId,
30812
- style: styles$e.label,
30813
- tag: "label"
30814
- }, "style"), /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.SingleSelect, {
30815
- id: styleSelectId,
31016
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
31017
+ tag: "label",
31018
+ style: styles$f.row
31019
+ }, "style", /*#__PURE__*/React__namespace.createElement(Strut, {
31020
+ size: wonderBlocksTokens.spacing.xxxSmall_4
31021
+ }), /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.SingleSelect, {
30816
31022
  selectedValue: lineStyle,
30817
31023
  onChange: value => onChangeProps({
30818
31024
  lineStyle: value
@@ -30820,7 +31026,7 @@ const LockedLineSettings = props => {
30820
31026
  // Placeholder is required, but never gets used.
30821
31027
  ,
30822
31028
  placeholder: "",
30823
- style: styles$e.selectMarginOffset
31029
+ style: styles$f.selectMarginOffset
30824
31030
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksDropdown.OptionItem, {
30825
31031
  value: "solid",
30826
31032
  label: "solid"
@@ -30828,7 +31034,7 @@ const LockedLineSettings = props => {
30828
31034
  value: "dashed",
30829
31035
  label: "dashed"
30830
31036
  })))), isInvalid && /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
30831
- style: styles$e.errorText
31037
+ style: styles$f.errorText
30832
31038
  }, lengthZeroStr), /*#__PURE__*/React__namespace.createElement(DefiningPointSettings, _extends({
30833
31039
  label: "Point 1",
30834
31040
  showPoint: showPoint1,
@@ -30854,7 +31060,7 @@ const LockedLineSettings = props => {
30854
31060
  ${point2.coord[0]}, ${point2.coord[1]}.`
30855
31061
  }));
30856
31062
  };
30857
- const styles$e = aphrodite.StyleSheet.create({
31063
+ const styles$f = aphrodite.StyleSheet.create({
30858
31064
  row: {
30859
31065
  flexDirection: "row",
30860
31066
  alignItems: "center"
@@ -30862,9 +31068,6 @@ const styles$e = aphrodite.StyleSheet.create({
30862
31068
  spaceUnder: {
30863
31069
  marginBottom: wonderBlocksTokens.spacing.xSmall_8
30864
31070
  },
30865
- label: {
30866
- marginInlineEnd: wonderBlocksTokens.spacing.xxxSmall_4
30867
- },
30868
31071
  selectMarginOffset: {
30869
31072
  // Align with the point settings accordions.
30870
31073
  marginInlineEnd: -wonderBlocksTokens.spacing.xxxSmall_4
@@ -30900,7 +31103,7 @@ const LockedPointSettings = props => {
30900
31103
  /*#__PURE__*/
30901
31104
  // Summary: Point, coords, color (filled/open)
30902
31105
  React__namespace.createElement(wonderBlocksCore.View, {
30903
- style: styles$d.row
31106
+ style: styles$e.row
30904
31107
  }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelLarge, null, `Point (${coord[0]}, ${coord[1]})`), /*#__PURE__*/React__namespace.createElement(Strut, {
30905
31108
  size: wonderBlocksTokens.spacing.xSmall_8
30906
31109
  }), /*#__PURE__*/React__namespace.createElement(ColorSwatch, {
@@ -30909,11 +31112,15 @@ const LockedPointSettings = props => {
30909
31112
  }))
30910
31113
  }, /*#__PURE__*/React__namespace.createElement(CoordinatePairInput, {
30911
31114
  coord: coord,
30912
- onChangeProps: onChangeProps
31115
+ onChange: newCoord => {
31116
+ onChangeProps({
31117
+ coord: newCoord
31118
+ });
31119
+ }
30913
31120
  }), /*#__PURE__*/React__namespace.createElement(ColorSelect, {
30914
31121
  selectedValue: pointColor,
30915
31122
  onChange: handleColorChange,
30916
- style: styles$d.spaceUnder
31123
+ style: styles$e.spaceUnder
30917
31124
  }), /*#__PURE__*/React__namespace.createElement(LabeledSwitch, {
30918
31125
  label: "open point",
30919
31126
  checked: !filled,
@@ -30927,7 +31134,7 @@ const LockedPointSettings = props => {
30927
31134
  figureAriaLabel: `locked point at ${coord[0]}, ${coord[1]}`
30928
31135
  }));
30929
31136
  };
30930
- const styles$d = aphrodite.StyleSheet.create({
31137
+ const styles$e = aphrodite.StyleSheet.create({
30931
31138
  row: {
30932
31139
  flexDirection: "row",
30933
31140
  alignItems: "center"
@@ -30937,6 +31144,113 @@ const styles$d = aphrodite.StyleSheet.create({
30937
31144
  }
30938
31145
  });
30939
31146
 
31147
+ /**
31148
+ * LockedVectorSettings is a component that allows the user to edit the
31149
+ * settings of specifically a locked vector on the graph.
31150
+ *
31151
+ * Used in the interactive graph editor's locked figures section.
31152
+ */
31153
+ const lengthErrorMessage = "The vector cannot have length 0.";
31154
+ const LockedVectorSettings = props => {
31155
+ const {
31156
+ points,
31157
+ color: lineColor,
31158
+ onChangeProps,
31159
+ onRemove
31160
+ } = props;
31161
+ const [tail, tip] = points;
31162
+ const lineLabel = `Vector (${tail[0]}, ${tail[1]}), (${tip[0]}, ${tip[1]})`;
31163
+
31164
+ // Check if the line has length 0.
31165
+ const isInvalid = kmath.vector.equal(tail, tip);
31166
+ function handleChangePoint(newCoord, index) {
31167
+ if (typeof newCoord !== "undefined") {
31168
+ const newPoints = [...points];
31169
+ newPoints[index] = [...newCoord];
31170
+ onChangeProps({
31171
+ points: newPoints
31172
+ });
31173
+ }
31174
+ }
31175
+ function handleColorChange(newColor) {
31176
+ onChangeProps({
31177
+ color: newColor
31178
+ });
31179
+ }
31180
+ return /*#__PURE__*/React__namespace.createElement(LockedFigureSettingsAccordion, {
31181
+ expanded: props.expanded,
31182
+ onToggle: props.onToggle,
31183
+ header: /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
31184
+ style: styles$d.row
31185
+ }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelLarge, null, lineLabel), /*#__PURE__*/React__namespace.createElement(Strut, {
31186
+ size: wonderBlocksTokens.spacing.xSmall_8
31187
+ }), /*#__PURE__*/React__namespace.createElement(LineSwatch, {
31188
+ color: lineColor,
31189
+ lineStyle: "solid"
31190
+ }))
31191
+ }, /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
31192
+ style: [styles$d.row, styles$d.spaceUnder]
31193
+ }, /*#__PURE__*/React__namespace.createElement(ColorSelect, {
31194
+ selectedValue: lineColor,
31195
+ onChange: handleColorChange
31196
+ })), isInvalid && /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelMedium, {
31197
+ style: styles$d.errorText
31198
+ }, lengthErrorMessage), /*#__PURE__*/React__namespace.createElement(LockedFigureSettingsAccordion, {
31199
+ expanded: true // Initial state is expanded
31200
+ ,
31201
+ containerStyle: styles$d.container,
31202
+ panelStyle: styles$d.accordionPanel,
31203
+ header: /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
31204
+ style: styles$d.row
31205
+ }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelLarge, null, `Tail (${tail[0]}, ${tail[1]})`))
31206
+ }, /*#__PURE__*/React__namespace.createElement(CoordinatePairInput, {
31207
+ coord: tail,
31208
+ error: isInvalid,
31209
+ onChange: newProps => {
31210
+ handleChangePoint(newProps, 0);
31211
+ }
31212
+ })), /*#__PURE__*/React__namespace.createElement(LockedFigureSettingsAccordion, {
31213
+ expanded: true // Initial state is expanded
31214
+ ,
31215
+ containerStyle: styles$d.container,
31216
+ panelStyle: styles$d.accordionPanel,
31217
+ header: /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
31218
+ style: styles$d.row
31219
+ }, /*#__PURE__*/React__namespace.createElement(wonderBlocksTypography.LabelLarge, null, `Tip (${tip[0]}, ${tip[1]})`))
31220
+ }, /*#__PURE__*/React__namespace.createElement(CoordinatePairInput, {
31221
+ coord: tip,
31222
+ error: isInvalid,
31223
+ onChange: newProps => {
31224
+ handleChangePoint(newProps, 1);
31225
+ }
31226
+ })), /*#__PURE__*/React__namespace.createElement(LockedFigureSettingsActions, {
31227
+ onRemove: onRemove,
31228
+ figureAriaLabel: `locked vector defined by starting point
31229
+ ${tail[0]}, ${tail[1]} and extending to
31230
+ ${tip[0]}, ${tip[1]}.`
31231
+ }));
31232
+ };
31233
+ const styles$d = aphrodite.StyleSheet.create({
31234
+ accordionPanel: {
31235
+ paddingBottom: wonderBlocksTokens.spacing.medium_16
31236
+ },
31237
+ container: {
31238
+ marginTop: wonderBlocksTokens.spacing.xSmall_8,
31239
+ marginBottom: 0,
31240
+ marginLeft: -wonderBlocksTokens.spacing.xxxSmall_4,
31241
+ marginRight: -wonderBlocksTokens.spacing.xxxSmall_4,
31242
+ backgroundColor: wonderBlocksTokens.color.white
31243
+ },
31244
+ errorText: {
31245
+ color: wonderBlocksTokens.color.red,
31246
+ marginTop: wonderBlocksTokens.spacing.xSmall_8
31247
+ },
31248
+ row: {
31249
+ flexDirection: "row",
31250
+ alignItems: "center"
31251
+ }
31252
+ });
31253
+
30940
31254
  /**
30941
31255
  * LockedFigureSettings takes in a figure and renders the
30942
31256
  * respective settings for that figure type.
@@ -30952,6 +31266,16 @@ const LockedFigureSettings = props => {
30952
31266
  return /*#__PURE__*/React__namespace.createElement(LockedPointSettings, props);
30953
31267
  case "line":
30954
31268
  return /*#__PURE__*/React__namespace.createElement(LockedLineSettings, props);
31269
+ case "ellipse":
31270
+ if (props.showM2Features) {
31271
+ return /*#__PURE__*/React__namespace.createElement(LockedEllipseSettings, props);
31272
+ }
31273
+ break;
31274
+ case "vector":
31275
+ if (props.showM2Features) {
31276
+ return /*#__PURE__*/React__namespace.createElement(LockedVectorSettings, props);
31277
+ }
31278
+ break;
30955
31279
  }
30956
31280
  return null;
30957
31281
  };
@@ -31019,15 +31343,22 @@ function getDefaultFigureForType(type) {
31019
31343
  showPoint1: false,
31020
31344
  showPoint2: false
31021
31345
  };
31022
- case "circle":
31346
+ case "ellipse":
31023
31347
  return {
31024
- type: "circle",
31348
+ type: "ellipse",
31025
31349
  center: [0, 0],
31026
- radius: 1,
31350
+ radius: [1, 1],
31351
+ angle: 0,
31027
31352
  color: DEFAULT_COLOR,
31028
31353
  fillStyle: "none",
31029
31354
  strokeStyle: "solid"
31030
31355
  };
31356
+ case "vector":
31357
+ return {
31358
+ type: "vector",
31359
+ points: [[0, 0], [2, 2]],
31360
+ color: DEFAULT_COLOR
31361
+ };
31031
31362
  default:
31032
31363
  throw new wonderStuffCore.UnreachableCaseError(type);
31033
31364
  }
@@ -31085,21 +31416,15 @@ const LockedFiguresSection = props => {
31085
31416
  const buttonLabel = allCollapsed ? "Expand all" : "Collapse all";
31086
31417
  const showExpandButton = !!figures?.length;
31087
31418
  return /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, null, figures?.map((figure, index) => {
31088
- if (figure.type === "circle") {
31089
- // TODO(LEMS-1941): Implement circle locked figure settings.
31090
- // Remove this block once circle locked figure settings are
31091
- // implemented.
31092
- return;
31093
- }
31094
31419
  return /*#__PURE__*/React__namespace.createElement(LockedFigureSettings, _extends({
31420
+ key: `${uniqueId}-locked-${figure}-${index}`,
31095
31421
  showM2Features: props.showM2Features,
31096
31422
  expanded: expandedStates[index],
31097
31423
  onToggle: newValue => {
31098
31424
  const newExpanded = [...expandedStates];
31099
31425
  newExpanded[index] = newValue;
31100
31426
  setExpandedStates(newExpanded);
31101
- },
31102
- key: `${uniqueId}-locked-${figure}-${index}`
31427
+ }
31103
31428
  }, figure, {
31104
31429
  onChangeProps: newProps => changeProps(index, newProps),
31105
31430
  onRemove: () => removeLockedFigure(index)
@@ -31107,6 +31432,7 @@ const LockedFiguresSection = props => {
31107
31432
  }), /*#__PURE__*/React__namespace.createElement(wonderBlocksCore.View, {
31108
31433
  style: styles$c.buttonContainer
31109
31434
  }, /*#__PURE__*/React__namespace.createElement(LockedFigureSelect, {
31435
+ showM2Features: props.showM2Features,
31110
31436
  id: `${uniqueId}-select`,
31111
31437
  onChange: addLockedFigure
31112
31438
  }), /*#__PURE__*/React__namespace.createElement(Strut, {
@@ -31468,7 +31794,7 @@ class InteractiveGraphEditor extends React__namespace.Component {
31468
31794
  }, equationString), /*#__PURE__*/React__namespace.createElement(InfoTip$b, null, /*#__PURE__*/React__namespace.createElement("p", null, "Graph the correct answer in the graph below and ensure the equation or point coordinates displayed represent the correct answer."))), graph,
31469
31795
  // Only show the "Add locked figure" dropdown if the graph
31470
31796
  // is using Mafs.
31471
- this.props.graph && this.props.apiOptions?.flags?.mafs?.["interactive-graph-locked-features-m1"] && this.props.apiOptions?.flags?.mafs?.[this.props.graph.type] && /*#__PURE__*/React__namespace.createElement(LockedFiguresSection, {
31797
+ this.props.graph && this.props.apiOptions?.flags?.mafs?.[this.props.graph.type] && /*#__PURE__*/React__namespace.createElement(LockedFiguresSection, {
31472
31798
  showM2Features: this.props.apiOptions?.flags?.mafs?.["interactive-graph-locked-features-m2"],
31473
31799
  figures: this.props.lockedFigures,
31474
31800
  onChange: this.props.onChange