@khanacademy/perseus 77.0.3 → 77.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/es/index.css +2 -2
- package/dist/es/index.css.map +1 -1
- package/dist/es/index.js +16 -18
- package/dist/es/index.js.map +1 -1
- package/dist/index.css +2 -2
- package/dist/index.css.map +1 -1
- package/dist/index.js +14 -16
- package/dist/index.js.map +1 -1
- package/dist/types.d.ts +0 -6
- package/dist/widget-ai-utils/radio/radio-ai-utils.d.ts +1 -1
- package/dist/widgets/dropdown/dropdown.d.ts +0 -1
- package/dist/widgets/expression/expression.d.ts +0 -2
- package/dist/widgets/interactive-graphs/interactive-graph.d.ts +3 -2
- package/dist/widgets/label-image/label-image.d.ts +0 -1
- package/dist/widgets/mock-widgets/mock-widget.d.ts +0 -1
- package/dist/widgets/numeric-input/numeric-input.class.d.ts +0 -1
- package/dist/widgets/numeric-input/numeric-input.d.ts +0 -1
- package/dist/widgets/radio/index.d.ts +16 -1
- package/dist/widgets/radio/{multiple-choice-component.d.ts → radio-component.d.ts} +7 -7
- package/dist/widgets/radio/radio-widget.d.ts +49 -0
- package/dist/widgets/radio/util.d.ts +1 -1
- package/dist/widgets/radio/utils/general-utils.d.ts +1 -1
- package/dist/widgets/table/table.d.ts +0 -1
- package/package.json +16 -16
- package/dist/widgets/radio/multiple-choice-widget.d.ts +0 -110
- package/dist/widgets/radio/radio.d.ts +0 -16
- package/dist/widgets/radio/radio.ff.d.ts +0 -112
package/dist/index.js
CHANGED
|
@@ -1466,7 +1466,7 @@ var a11y = aphrodite.StyleSheet.create({srOnly:{border:0,clip:"rect(0,0,0,0)",he
|
|
|
1466
1466
|
|
|
1467
1467
|
const debounce=(func,delay)=>{let timer=null;return (...args)=>{if(timer){clearTimeout(timer);}timer=window.setTimeout(()=>{func(...args);},delay);}};
|
|
1468
1468
|
|
|
1469
|
-
class InnerMathInput extends React__namespace.Component{componentDidMount(){this.mathField()?.latex(this.props.value);}componentDidUpdate(prevProps){if(prevProps.value!==this.props.value){if(this.state.focused){return}const field=this.mathField();if(!field){return}const current=field.latex();if(this.props.value!==current){field.latex(this.props.value);}}}openKeypad(){if(this.props.buttonsVisible==="never"){return}this.setState({keypadOpen:true});}closeKeypad(){this.setState({keypadOpen:false});}render(){let className=classNames__default.default({"perseus-math-input":true,"mq-editable-field":true,"mq-math-mode":true});const popoverContentUniqueId=uuid.v4().slice(0,8);if(this.props.className){className=className+" "+this.props.className;}return jsxRuntimeExports.jsx(wonderBlocksCore.View,{style:[styles$D.outerWrapper,this.state.focused&&styles$D.wrapperFocused],children:jsxRuntimeExports.jsxs("div",{style:{display:"flex",padding:1},onClick:e=>{e.stopPropagation();const mathField=this.mathField();if(!mathField){return}this.setState({cursorContext:mathInput.getCursorContext(mathField)});},children:[jsxRuntimeExports.jsx("span",{className:className,ref:ref=>this.__mathFieldWrapperRef=ref,onFocus:()=>this.focus(),onBlur:()=>this.blur()}),jsxRuntimeExports.jsx(wonderBlocksPopover.Popover,{opened:this.state.keypadOpen,dismissEnabled:true,rootBoundary:"document","aria-label":this.context.strings.mathInputTitle,"aria-describedby":`popover-content-${popoverContentUniqueId}`,onClose:()=>this.closeKeypad(),content:()=>jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx(wonderBlocksTypography.
|
|
1469
|
+
class InnerMathInput extends React__namespace.Component{componentDidMount(){this.mathField()?.latex(this.props.value);}componentDidUpdate(prevProps){if(prevProps.value!==this.props.value){if(this.state.focused){return}const field=this.mathField();if(!field){return}const current=field.latex();if(this.props.value!==current){field.latex(this.props.value);}}}openKeypad(){if(this.props.buttonsVisible==="never"){return}this.setState({keypadOpen:true});}closeKeypad(){this.setState({keypadOpen:false});}render(){let className=classNames__default.default({"perseus-math-input":true,"mq-editable-field":true,"mq-math-mode":true});const popoverContentUniqueId=uuid.v4().slice(0,8);if(this.props.className){className=className+" "+this.props.className;}return jsxRuntimeExports.jsx(wonderBlocksCore.View,{style:[styles$D.outerWrapper,this.state.focused&&styles$D.wrapperFocused],children:jsxRuntimeExports.jsxs("div",{style:{display:"flex",padding:1},onClick:e=>{e.stopPropagation();const mathField=this.mathField();if(!mathField){return}this.setState({cursorContext:mathInput.getCursorContext(mathField)});},children:[jsxRuntimeExports.jsx("span",{className:className,ref:ref=>this.__mathFieldWrapperRef=ref,onFocus:()=>this.focus(),onBlur:()=>this.blur()}),jsxRuntimeExports.jsx(wonderBlocksPopover.Popover,{opened:this.state.keypadOpen,dismissEnabled:true,rootBoundary:"document","aria-label":this.context.strings.mathInputTitle,"aria-describedby":`popover-content-${popoverContentUniqueId}`,onClose:()=>this.closeKeypad(),content:()=>jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx(wonderBlocksTypography.Heading,{size:"large",id:`popover-content-${popoverContentUniqueId}`,style:a11y.srOnly,children:this.context.strings.mathInputDescription}),jsxRuntimeExports.jsx(wonderBlocksPopover.PopoverContentCore,{style:styles$D.popoverContent,children:jsxRuntimeExports.jsx(mathInput.DesktopKeypad,{onAnalyticsEvent:this.props.onAnalyticsEvent,extraKeys:this.props.extraKeys,onClickKey:this.handleKeypadPress,cursorContext:this.state.cursorContext,convertDotToTimes:this.props.convertDotToTimes,...this.props.keypadButtonSets??mapButtonSets(this.props?.buttonSets),showDismiss:true})})]}),children:this.props.buttonsVisible==="never"?jsxRuntimeExports.jsx(MathInputIcon,{hovered:false,focused:false,active:false}):jsxRuntimeExports.jsx(Clickable__default.default,{"aria-label":this.state.keypadOpen?this.context.strings.closeKeypad:this.context.strings.openKeypad,role:"button",onClick:()=>this.state.keypadOpen?this.closeKeypad():this.openKeypad(),children:props=>jsxRuntimeExports.jsx(MathInputIcon,{active:this.state.keypadOpen,...props})})})]})})}constructor(...args){super(...args),this.__mathFieldWrapperRef=null,this.__mathField=null,this.state={focused:false,keypadOpen:this.props.buttonsVisible==="always"?true:false,cursorContext:mathInput.CursorContext.NONE},this.insert=value=>{const input=this.mathField();const{locale}=this.context;const customKeyTranslator={...mathInput.getKeyTranslator(locale,this.context.strings),FRAC:mathQuill=>{const contents=mathQuill.latex();mathQuill.typedText("/");if(mathQuill.latex()===contents){mathQuill.cmd("\\frac");}}};const inputModifier=customKeyTranslator[value];if(inputModifier){inputModifier(input,value);input?.focus();return}if(___default.default(value).isFunction()){value(input);}else if(value[0]==="\\"){input?.cmd(value).focus();}else {input?.write(value).focus();}input?.focus();},this.mathField=()=>{if(!this.__mathField&&this.__mathFieldWrapperRef){const{locale}=this.context;this.__mathField=mathInput.createMathField(this.__mathFieldWrapperRef,locale,this.props.mathInputStrings,baseConfig=>({...baseConfig,handlers:{edit:debounce(mathField=>{let value=mathField.latex();value=value.replace(/<>/g,"\\ne");if(mathInput.convertDotToTimesByLocale(locale,this.props.convertDotToTimes)){value=value.replace(/\\cdot/g,"\\times");const left=mathField.cursor()[mathInput.mathQuillInstance.L];if(left&&left.ctrlSeq==="\\cdot "){mathField.controller().backspace();mathField.cmd("\\times");}}else {value=value.replace(/\\times/g,"\\cdot");}if(this.props.value!==value){this.props.onChange(value);}this.setState({cursorContext:mathInput.getCursorContext(mathField)});},100),enter:()=>{if(this.__mathFieldWrapperRef){$__default.default(this.__mathFieldWrapperRef).submit();}},upOutOf:mathField=>{mathField.typedText("^");}}}));}this.__mathField?.setAriaLabel(this.props.ariaLabel);return this.__mathField},this.focus=()=>{this.mathField()?.focus();this.setState({focused:true});},this.blur=()=>this.setState({focused:false}),this.handleKeypadPress=(key,e)=>{if(key==="DISMISS"){this.closeKeypad();return}const{locale}=this.context;const translator=mathInput.getKeyTranslator(locale,this.context.strings)[key];const mathField=this.mathField();if(mathField){if(translator){translator(mathField,key);}this.setState({cursorContext:mathInput.getCursorContext(mathField)});}if(e?.type==="click"){this.focus();}};}}InnerMathInput.contextType=PerseusI18nContext;InnerMathInput.defaultProps={value:"",convertDotToTimes:false};class MathInput extends React__namespace.Component{blur(){this.inputRef.current?.blur();}focus(){this.inputRef.current?.focus();}insert(value){this.inputRef.current?.insert(value);}render(){return jsxRuntimeExports.jsx(InnerMathInput,{...this.props,ref:this.inputRef,mathInputStrings:this.context.strings})}constructor(...args){super(...args),this.inputRef=React__namespace.createRef();}}MathInput.contextType=mathInput.MathInputI18nContext;MathInput.defaultProps={ariaLabel:"Math input"};const MathInputIcon=({hovered,focused,active})=>{let fillColor;switch(true){case focused||active:fillColor=wonderBlocksTokens.semanticColor.action.primary.progressive.default.foreground;break;case hovered:fillColor=wonderBlocksTokens.semanticColor.action.primary.progressive.hover.background;break;default:fillColor=wonderBlocksTokens.semanticColor.core.foreground.neutral.strong;break}const dynamicClass=active||focused?styles$D.iconActive:styles$D.iconInactive;return jsxRuntimeExports.jsx(wonderBlocksCore.View,{style:[styles$D.iconContainer,dynamicClass],children:jsxRuntimeExports.jsx("svg",{xmlns:"http://www.w3.org/2000/svg",width:"16",height:"16",fill:fillColor,viewBox:"0 0 256 256",children:jsxRuntimeExports.jsx("path",{d:"M112,72a8,8,0,0,1-8,8H40a8,8,0,0,1,0-16h64A8,8,0,0,1,112,72Zm-8,104H80V152a8,8,0,0,0-16,0v24H40a8,8,0,0,0,0,16H64v24a8,8,0,0,0,16,0V192h24a8,8,0,0,0,0-16Zm48,0h64a8,8,0,0,0,0-16H152a8,8,0,0,0,0,16Zm64,16H152a8,8,0,0,0,0,16h64a8,8,0,0,0,0-16Zm-61.66-90.34a8,8,0,0,0,11.32,0L184,83.31l18.34,18.35a8,8,0,0,0,11.32-11.32L195.31,72l18.35-18.34a8,8,0,0,0-11.32-11.32L184,60.69,165.66,42.34a8,8,0,0,0-11.32,11.32L172.69,72,154.34,90.34A8,8,0,0,0,154.34,101.66Z"})})})};const mapButtonSets=buttonSets=>{const keypadButtonSets={};if(!buttonSets){return keypadButtonSets}buttonSets.forEach(buttonSet=>{switch(buttonSet){case "advanced relations":keypadButtonSets.advancedRelations=true;break;case "basic relations":keypadButtonSets.basicRelations=true;break;case "basic+div":keypadButtonSets.divisionKey=true;break;case "logarithms":keypadButtonSets.logarithms=true;break;case "prealgebra":keypadButtonSets.preAlgebra=true;break;case "trig":keypadButtonSets.trigonometry=true;break;case "scientific":keypadButtonSets.scientific=true;break;}});return keypadButtonSets};const inputFocused={borderWidth:2,borderColor:wonderBlocksTokens.semanticColor.core.border.instructive.default,margin:-1};const styles$D=aphrodite.StyleSheet.create({iconContainer:{display:"flex",justifyContent:"center",height:"100%",padding:wonderBlocksTokens.sizing.size_040,borderRadius:1},iconInactive:{border:"2px solid transparent",backgroundColor:wonderBlocksTokens.semanticColor.core.background.neutral.subtle},iconActive:{border:`2px solid ${wonderBlocksTokens.semanticColor.core.border.knockout.default}`,backgroundColor:wonderBlocksTokens.semanticColor.core.background.neutral.default},outerWrapper:{display:"inline-block",borderStyle:"solid",borderWidth:1,borderColor:wonderBlocksTokens.semanticColor.core.border.neutral.default,borderRadius:3,background:wonderBlocksTokens.semanticColor.core.background.base.default,":hover":inputFocused},wrapperFocused:inputFocused,popoverContent:{padding:0,paddingBottom:wonderBlocksTokens.sizing.size_060,maxWidth:"initial"}});
|
|
1470
1470
|
|
|
1471
1471
|
let _dependencies=null;const setDependencies=dependencies=>{_dependencies=dependencies;};const getDependencies=()=>{if(_dependencies){return _dependencies}throw new Error(["Perseus has not been provided required dependencies.","setDependencies(dependencies) must be called first.","Make sure Perseus is being imported from javascript/perseus/perseus.js."].join("\n"))};const DependenciesContext=React__namespace.createContext({analytics:{onAnalyticsEvent:async()=>{}},generateUrl:()=>{throw new Error("generateUrl dependency not provided in Perseus dependencies")},useVideo:()=>{throw new Error("useVideo dependency not provided in Perseus dependencies")}});const useDependencies=()=>{const deps=React__namespace.useContext(DependenciesContext);return deps};
|
|
1472
1472
|
|
|
@@ -1482,7 +1482,7 @@ const ApiOptions={propTypes:PropTypes__default.default.shape({isArticle:PropType
|
|
|
1482
1482
|
|
|
1483
1483
|
const getPromptJSON$r=(label,userInput)=>{return {type:"expression",label,userInput:{value:userInput}}};
|
|
1484
1484
|
|
|
1485
|
-
const englishOperators={arctg:"arctan",cosec:"csc",cossec:"csc",cotg:"cot",ctg:"cot",sen:"sin",tg:"tan"};const anglicizeOperators=tex=>{return tex.replace(/\\operatorname{([a-z]+)}/g,(_,op)=>`\\${englishOperators[op]??op} `)};const normalizeTex=tex=>{return anglicizeOperators(tex)};const defaultButtonSets=["basic","trig","prealgebra","logarithms"];const defaultOnFocus=()=>{};const defaultOnBlur=()=>{};const KeypadInputWithInterface=React__namespace.forwardRef(function KeypadInputWithInterface(props,ref){const keypadInputRef=React__namespace.useRef(null);const noopKeypadActivation=_keypadActive=>{};React__namespace.useImperativeHandle(ref,()=>({focus:(cb=noopKeypadActivation)=>keypadInputRef.current?.focus(cb),blur:()=>keypadInputRef.current?.blur(),insert:val=>{keypadInputRef.current?.mathField?.pressKey?.(val);}}));return jsxRuntimeExports.jsx(mathInput.KeypadInput,{ref:keypadInputRef,...props})});const Expression=React.forwardRef(function Expression({apiOptions=ApiOptions.defaults,buttonSets=defaultButtonSets,times=false,onFocus=defaultOnFocus,onBlur=defaultOnBlur,userInput="",visibleLabel,ariaLabel,keypadElement,extraKeys,handleUserInput,trackInteraction,widgetId,answerForms,...rest},ref){const{strings}=usePerseusI18n();const{analytics}=useDependencies();const{setKeypadActive}=React__namespace.useContext(keypadContext.KeypadContext);const textareaId=React.useId();const inputRef=React.useRef(null);const rootRef=React.useRef(null);React.useEffect(()=>{analytics?.onAnalyticsEvent({type:"perseus:widget:rendered:ti",payload:{widgetSubType:"null",widgetType:"expression",widgetId}});if(rootRef.current){const isMobile=apiOptions.customKeypad;const selector=isMobile?".mq-textarea > span":"textarea";const inputElement=rootRef.current.querySelector(selector);if(inputElement instanceof HTMLElement){inputElement.setAttribute("id",textareaId);}}},[]);const handleFocus=()=>{analytics?.onAnalyticsEvent({type:"perseus:expression-focused",payload:null});onFocus([]);};const handleBlur=()=>{onBlur([]);};const changeAndTrack=(value,cb)=>{const normalized=normalizeTex(value);handleUserInput(normalized,cb);trackInteraction();};const mobileHandleFocus=()=>{keypadElement?.configure(getKeypadConfiguration(),()=>{if(rootRef.current){handleFocus();}});};const getKeypadConfiguration=React.useCallback(()=>{return {keypadType:"EXPRESSION",extraKeys:extraKeys,times:times}},[extraKeys,times]);const getFocusTarget=React.useCallback(()=>{if(!rootRef.current){return null}const isMobile=apiOptions.customKeypad;const selector=isMobile?".mq-textarea > span":"textarea";const element=rootRef.current.querySelector(selector);return element instanceof HTMLElement?element:null},[apiOptions.customKeypad]);React.useImperativeHandle(ref,()=>({focus:()=>{const targetBefore=getFocusTarget();inputRef.current?.focus?.(setKeypadActive);const targetAfter=getFocusTarget()??targetBefore??(document.activeElement instanceof HTMLElement?document.activeElement:null);if(!targetAfter){return false}if(document.activeElement!==targetAfter){targetAfter.focus();}return document.activeElement===targetAfter},focusInputPath:path=>{inputRef.current?.focus?.(setKeypadActive);},blurInputPath:path=>{if(typeof inputRef.current?.blur==="function"){inputRef.current?.blur();}},insert:keyPressed=>{inputRef.current?.insert?.(keyPressed);},getInputPaths:()=>[[]],getUserInput:()=>{return normalizeTex(userInput)},getKeypadConfiguration,getPromptJSON:()=>{return getPromptJSON$r(visibleLabel,normalizeTex(userInput))},getSerializedState:()=>{return {...rest,value:userInput,keypadConfiguration:getKeypadConfiguration(),times,buttonSets}}}),[userInput,setKeypadActive,getKeypadConfiguration,getFocusTarget,rest,visibleLabel,buttonSets,times]);const keypadConfiguration=getKeypadConfiguration();if(apiOptions.customKeypad){return jsxRuntimeExports.jsxs(wonderBlocksCore.View,{ref:rootRef,style:styles$C.mobileLabelInputWrapper,children:[!!visibleLabel&&jsxRuntimeExports.jsx(wonderBlocksTypography.
|
|
1485
|
+
const englishOperators={arctg:"arctan",cosec:"csc",cossec:"csc",cotg:"cot",ctg:"cot",sen:"sin",tg:"tan"};const anglicizeOperators=tex=>{return tex.replace(/\\operatorname{([a-z]+)}/g,(_,op)=>`\\${englishOperators[op]??op} `)};const normalizeTex=tex=>{return anglicizeOperators(tex)};const defaultButtonSets=["basic","trig","prealgebra","logarithms"];const defaultOnFocus=()=>{};const defaultOnBlur=()=>{};const KeypadInputWithInterface=React__namespace.forwardRef(function KeypadInputWithInterface(props,ref){const keypadInputRef=React__namespace.useRef(null);const noopKeypadActivation=_keypadActive=>{};React__namespace.useImperativeHandle(ref,()=>({focus:(cb=noopKeypadActivation)=>keypadInputRef.current?.focus(cb),blur:()=>keypadInputRef.current?.blur(),insert:val=>{keypadInputRef.current?.mathField?.pressKey?.(val);}}));return jsxRuntimeExports.jsx(mathInput.KeypadInput,{ref:keypadInputRef,...props})});const Expression=React.forwardRef(function Expression({apiOptions=ApiOptions.defaults,buttonSets=defaultButtonSets,times=false,onFocus=defaultOnFocus,onBlur=defaultOnBlur,userInput="",visibleLabel,ariaLabel,keypadElement,extraKeys,handleUserInput,trackInteraction,widgetId,answerForms,...rest},ref){const{strings}=usePerseusI18n();const{analytics}=useDependencies();const{setKeypadActive}=React__namespace.useContext(keypadContext.KeypadContext);const textareaId=React.useId();const inputRef=React.useRef(null);const rootRef=React.useRef(null);React.useEffect(()=>{analytics?.onAnalyticsEvent({type:"perseus:widget:rendered:ti",payload:{widgetSubType:"null",widgetType:"expression",widgetId}});if(rootRef.current){const isMobile=apiOptions.customKeypad;const selector=isMobile?".mq-textarea > span":"textarea";const inputElement=rootRef.current.querySelector(selector);if(inputElement instanceof HTMLElement){inputElement.setAttribute("id",textareaId);}}},[]);const handleFocus=()=>{analytics?.onAnalyticsEvent({type:"perseus:expression-focused",payload:null});onFocus([]);};const handleBlur=()=>{onBlur([]);};const changeAndTrack=(value,cb)=>{const normalized=normalizeTex(value);handleUserInput(normalized,cb);trackInteraction();};const mobileHandleFocus=()=>{keypadElement?.configure(getKeypadConfiguration(),()=>{if(rootRef.current){handleFocus();}});};const getKeypadConfiguration=React.useCallback(()=>{return {keypadType:"EXPRESSION",extraKeys:extraKeys,times:times}},[extraKeys,times]);const getFocusTarget=React.useCallback(()=>{if(!rootRef.current){return null}const isMobile=apiOptions.customKeypad;const selector=isMobile?".mq-textarea > span":"textarea";const element=rootRef.current.querySelector(selector);return element instanceof HTMLElement?element:null},[apiOptions.customKeypad]);React.useImperativeHandle(ref,()=>({focus:()=>{const targetBefore=getFocusTarget();inputRef.current?.focus?.(setKeypadActive);const targetAfter=getFocusTarget()??targetBefore??(document.activeElement instanceof HTMLElement?document.activeElement:null);if(!targetAfter){return false}if(document.activeElement!==targetAfter){targetAfter.focus();}return document.activeElement===targetAfter},focusInputPath:path=>{inputRef.current?.focus?.(setKeypadActive);},blurInputPath:path=>{if(typeof inputRef.current?.blur==="function"){inputRef.current?.blur();}},insert:keyPressed=>{inputRef.current?.insert?.(keyPressed);},getInputPaths:()=>[[]],getUserInput:()=>{return normalizeTex(userInput)},getKeypadConfiguration,getPromptJSON:()=>{return getPromptJSON$r(visibleLabel,normalizeTex(userInput))},getSerializedState:()=>{return {...rest,value:userInput,keypadConfiguration:getKeypadConfiguration(),times,buttonSets}}}),[userInput,setKeypadActive,getKeypadConfiguration,getFocusTarget,rest,visibleLabel,buttonSets,times]);const keypadConfiguration=getKeypadConfiguration();if(apiOptions.customKeypad){return jsxRuntimeExports.jsxs(wonderBlocksCore.View,{ref:rootRef,style:styles$C.mobileLabelInputWrapper,children:[!!visibleLabel&&jsxRuntimeExports.jsx(wonderBlocksTypography.BodyText,{size:"small",htmlFor:textareaId,tag:"label",children:visibleLabel}),jsxRuntimeExports.jsx(KeypadInputWithInterface,{ref:inputRef,ariaLabel:ariaLabel||strings.mathInputBox,value:userInput,keypadElement:keypadElement,onChange:changeAndTrack,onFocus:mobileHandleFocus,onBlur:handleBlur})]})}return jsxRuntimeExports.jsxs(wonderBlocksCore.View,{ref:rootRef,style:styles$C.desktopLabelInputWrapper,children:[!!visibleLabel&&jsxRuntimeExports.jsx(wonderBlocksTypography.BodyText,{size:"small",htmlFor:textareaId,tag:"label",children:visibleLabel}),jsxRuntimeExports.jsx("div",{className:"perseus-widget-expression",children:jsxRuntimeExports.jsx(MathInput,{ref:inputRef,value:userInput,onChange:changeAndTrack,convertDotToTimes:times,buttonSets:buttonSets,onFocus:handleFocus,onBlur:handleBlur,ariaLabel:ariaLabel||strings.mathInputBox,extraKeys:keypadConfiguration.extraKeys,onAnalyticsEvent:analytics?.onAnalyticsEvent??(async()=>{})})})]})});const styles$C=aphrodite.StyleSheet.create({mobileLabelInputWrapper:{padding:"15px 4px 0"},desktopLabelInputWrapper:{margin:"5px 5px 0"}});function getUserInputFromSerializedState$i(serializedState){return normalizeTex(serializedState.value)}function getStartUserInput$j(){return ""}function getOneCorrectAnswerFromRubric$1(rubric){const correctAnswers=(rubric.answerForms||[]).filter(answerForm=>answerForm.considered==="correct");if(correctAnswers.length===0){return}return correctAnswers[0].value}function getCorrectUserInput$a(options){for(const form of options.answerForms){if(form.considered==="correct"){return form.value}}return ""}var Expression$1 = {name:"expression",displayName:"Expression / Equation",widget:Expression,version:perseusCore.expressionLogic.version,isLintable:true,getOneCorrectAnswerFromRubric: getOneCorrectAnswerFromRubric$1,getStartUserInput: getStartUserInput$j,getCorrectUserInput: getCorrectUserInput$a,getUserInputFromSerializedState: getUserInputFromSerializedState$i};
|
|
1486
1486
|
|
|
1487
1487
|
class SimpleKeypadInput extends React__namespace.Component{componentDidMount(){this._isMounted=true;}componentWillUnmount(){this._isMounted=false;}focus(){this.inputRef.current?.focus(this.context.setKeypadActive);}blur(){this.inputRef.current?.blur();}getValue(){return this.props.value}render(){const _this=this;const{keypadElement,onFocus,value,...rest}=_this.props;return jsxRuntimeExports.jsx(mathInput.KeypadInput,{ref:this.inputRef,keypadElement:keypadElement,onFocus:()=>{if(keypadElement){keypadElement.configure({keypadType:"FRACTION"},()=>{if(_this._isMounted){onFocus?.();}});}else {onFocus?.();}},value:value==null?"":""+value,...rest})}constructor(...args){super(...args),this._isMounted=false,this.inputRef=React__namespace.createRef();}}SimpleKeypadInput.contextType=keypadContext.KeypadContext;SimpleKeypadInput.propTypes={keypadElement:mathInput.keypadElementPropType,onFocus:PropTypes__default.default.func,value:PropTypes__default.default.oneOfType([PropTypes__default.default.string,PropTypes__default.default.number])};
|
|
1488
1488
|
|
|
@@ -1745,11 +1745,11 @@ class NumericInput extends React__namespace.Component{getPromptJSON(){return get
|
|
|
1745
1745
|
|
|
1746
1746
|
const MathRenderingContext=React__namespace.createContext({shouldAddAriaLabels:false});
|
|
1747
1747
|
|
|
1748
|
-
const getPromptJSON$o=(widgetData,userInput)=>{const choices=widgetData.choices||[];const options=choices.map(choice=>{const option={value:choice.content,id:choice.id};if(choice.rationale){option.rationale=choice.rationale;}return option});return {type:"radio",hasNoneOfTheAbove
|
|
1748
|
+
const getPromptJSON$o=(widgetData,userInput)=>{const choices=widgetData.choices||[];const options=choices.map(choice=>{const option={value:choice.content,id:choice.id};if(choice.rationale){option.rationale=choice.rationale;}return option});const hasNoneOfTheAbove=choices.some(choice=>choice.isNoneOfTheAbove);return {type:"radio",hasNoneOfTheAbove,options,userInput:{selectedOptions:userInput?.selectedChoiceIds??[]}}};
|
|
1749
1749
|
|
|
1750
1750
|
var styles$v = {"scrollButtonsContainer":"perseus_kjDHiWdD"};
|
|
1751
1751
|
|
|
1752
|
-
const SCROLL_DISTANCE=100;const scrollInstances=new Map;function ScrollableArea({overflowX,overflowY,children,className,scrollDescription,style,role="group",id:providedId,...additionalProps}){const{strings}=usePerseusI18n();const containerRef=React.useRef(null);const[isScrollable,setIsScrollable]=React.useState(false);const[isScrolling,setIsScrolling]=React.useState(false);const generatedId=React__namespace.useId();const id=providedId||generatedId;const scrollableThreshold=React__namespace.useMemo(()=>{return window.innerWidth<=767?8:5},[]);const scroll=React__namespace.useCallback(direction=>{if(!containerRef.current||isScrolling){return}setIsScrolling(true);const contentIsRtl=getComputedStyle(containerRef.current).direction==="rtl";const scrollNegative=contentIsRtl&&direction==="end"||!contentIsRtl&&direction==="start";const scrollAmount=scrollNegative?-100:SCROLL_DISTANCE;containerRef.current.scrollBy({left:scrollAmount,behavior:"smooth"});setTimeout(()=>{setIsScrolling(false);},150);},[isScrolling]);const updateScrollState=React__namespace.useCallback(()=>{if(!containerRef.current){return}const{scrollLeft,scrollWidth,clientWidth}=containerRef.current;const newIsRtl=getComputedStyle(containerRef.current).direction==="rtl";const newIsScrollable=scrollWidth>clientWidth+scrollableThreshold;setIsScrollable(newIsScrollable);let newCanScrollStart;let newCanScrollEnd;if(newIsRtl){newCanScrollStart=scrollLeft<-scrollableThreshold;newCanScrollEnd=Math.abs(scrollLeft)<scrollWidth-clientWidth-scrollableThreshold;}else {newCanScrollStart=scrollLeft>scrollableThreshold;newCanScrollEnd=scrollLeft+clientWidth<scrollWidth-scrollableThreshold;}const scrollState={isScrollable:newIsScrollable,canScrollStart:newCanScrollStart,canScrollEnd:newCanScrollEnd,isRTL:newIsRtl,scroll,scrollDescription:scrollDescription||strings.scrollAnswers};scrollInstances.set(id,scrollState);},[id,scrollableThreshold,scrollDescription,strings.scrollAnswers,scroll]);React.useEffect(()=>{const container=containerRef.current;if(!container){return}updateScrollState();container.addEventListener("scroll",updateScrollState);window.addEventListener("resize",updateScrollState);return ()=>{container.removeEventListener("scroll",updateScrollState);window.removeEventListener("resize",updateScrollState);scrollInstances.delete(id);}},[children,updateScrollState,id]);const mergeStyle={overflowX:isScrollable&&overflowX==="auto"?"scroll":overflowX,overflowY:isScrollable&&overflowY==="auto"?"scroll":overflowY,scrollbarWidth:"thin",...style};return jsxRuntimeExports.jsx("div",{...additionalProps,id:id,role:role,className:className,style:mergeStyle,ref:containerRef,children:children})}function ScrollControls({target,scrollDescription:overrideDescription}){const{strings}=usePerseusI18n();const[scrollState,setScrollState]=React.useState(null);React.useEffect(()=>{if(!target){return}const checkForScrollState=()=>{const state=scrollInstances.get(target);if(state){setScrollState(state);}};checkForScrollState();const interval=setInterval(checkForScrollState,100);return ()=>{clearInterval(interval);}},[target]);if(!scrollState||!scrollState.isScrollable){return null}const description=overrideDescription||scrollState.scrollDescription;return jsxRuntimeExports.jsxs("div",{className:styles$v.scrollButtonsContainer,"aria-live":"polite",role:"group","aria-label":description,children:[jsxRuntimeExports.jsx(IconButton__default.default,{icon:scrollState.isRTL?caretRightIcon__default.default:caretLeftIcon__default.default,actionType:"neutral",kind:"secondary",size:"small",onClick:()=>scrollState.scroll("start"),"aria-label":strings.scrollStart,disabled:!scrollState.canScrollStart}),jsxRuntimeExports.jsx(IconButton__default.default,{icon:scrollState.isRTL?caretLeftIcon__default.default:caretRightIcon__default.default,actionType:"neutral",kind:"secondary",size:"small",onClick:()=>scrollState.scroll("end"),"aria-label":strings.scrollEnd,disabled:!scrollState.canScrollEnd}),jsxRuntimeExports.jsx(wonderBlocksTypography.
|
|
1752
|
+
const SCROLL_DISTANCE=100;const scrollInstances=new Map;function ScrollableArea({overflowX,overflowY,children,className,scrollDescription,style,role="group",id:providedId,...additionalProps}){const{strings}=usePerseusI18n();const containerRef=React.useRef(null);const[isScrollable,setIsScrollable]=React.useState(false);const[isScrolling,setIsScrolling]=React.useState(false);const generatedId=React__namespace.useId();const id=providedId||generatedId;const scrollableThreshold=React__namespace.useMemo(()=>{return window.innerWidth<=767?8:5},[]);const scroll=React__namespace.useCallback(direction=>{if(!containerRef.current||isScrolling){return}setIsScrolling(true);const contentIsRtl=getComputedStyle(containerRef.current).direction==="rtl";const scrollNegative=contentIsRtl&&direction==="end"||!contentIsRtl&&direction==="start";const scrollAmount=scrollNegative?-100:SCROLL_DISTANCE;containerRef.current.scrollBy({left:scrollAmount,behavior:"smooth"});setTimeout(()=>{setIsScrolling(false);},150);},[isScrolling]);const updateScrollState=React__namespace.useCallback(()=>{if(!containerRef.current){return}const{scrollLeft,scrollWidth,clientWidth}=containerRef.current;const newIsRtl=getComputedStyle(containerRef.current).direction==="rtl";const newIsScrollable=scrollWidth>clientWidth+scrollableThreshold;setIsScrollable(newIsScrollable);let newCanScrollStart;let newCanScrollEnd;if(newIsRtl){newCanScrollStart=scrollLeft<-scrollableThreshold;newCanScrollEnd=Math.abs(scrollLeft)<scrollWidth-clientWidth-scrollableThreshold;}else {newCanScrollStart=scrollLeft>scrollableThreshold;newCanScrollEnd=scrollLeft+clientWidth<scrollWidth-scrollableThreshold;}const scrollState={isScrollable:newIsScrollable,canScrollStart:newCanScrollStart,canScrollEnd:newCanScrollEnd,isRTL:newIsRtl,scroll,scrollDescription:scrollDescription||strings.scrollAnswers};scrollInstances.set(id,scrollState);},[id,scrollableThreshold,scrollDescription,strings.scrollAnswers,scroll]);React.useEffect(()=>{const container=containerRef.current;if(!container){return}updateScrollState();container.addEventListener("scroll",updateScrollState);window.addEventListener("resize",updateScrollState);return ()=>{container.removeEventListener("scroll",updateScrollState);window.removeEventListener("resize",updateScrollState);scrollInstances.delete(id);}},[children,updateScrollState,id]);const mergeStyle={overflowX:isScrollable&&overflowX==="auto"?"scroll":overflowX,overflowY:isScrollable&&overflowY==="auto"?"scroll":overflowY,scrollbarWidth:"thin",...style};return jsxRuntimeExports.jsx("div",{...additionalProps,id:id,role:role,className:className,style:mergeStyle,ref:containerRef,children:children})}function ScrollControls({target,scrollDescription:overrideDescription}){const{strings}=usePerseusI18n();const[scrollState,setScrollState]=React.useState(null);React.useEffect(()=>{if(!target){return}const checkForScrollState=()=>{const state=scrollInstances.get(target);if(state){setScrollState(state);}};checkForScrollState();const interval=setInterval(checkForScrollState,100);return ()=>{clearInterval(interval);}},[target]);if(!scrollState||!scrollState.isScrollable){return null}const description=overrideDescription||scrollState.scrollDescription;return jsxRuntimeExports.jsxs("div",{className:styles$v.scrollButtonsContainer,"aria-live":"polite",role:"group","aria-label":description,children:[jsxRuntimeExports.jsx(IconButton__default.default,{icon:scrollState.isRTL?caretRightIcon__default.default:caretLeftIcon__default.default,actionType:"neutral",kind:"secondary",size:"small",onClick:()=>scrollState.scroll("start"),"aria-label":strings.scrollStart,disabled:!scrollState.canScrollStart}),jsxRuntimeExports.jsx(IconButton__default.default,{icon:scrollState.isRTL?caretLeftIcon__default.default:caretRightIcon__default.default,actionType:"neutral",kind:"secondary",size:"small",onClick:()=>scrollState.scroll("end"),"aria-label":strings.scrollEnd,disabled:!scrollState.canScrollEnd}),jsxRuntimeExports.jsx(wonderBlocksTypography.BodyText,{size:"small",children:description})]})}const ScrollableView=ScrollableArea;ScrollableView.Controls=ScrollControls;
|
|
1753
1753
|
|
|
1754
1754
|
var styles$u = {"base":"perseus_C4cWo-dY","is-correct":"perseus_vWc7XkhJ","isCorrect":"perseus_vWc7XkhJ","is-wrong":"perseus_yVmsF9sA","isWrong":"perseus_yVmsF9sA","icon":"perseus_brEUCVvd","circle-shape":"perseus_irgRpkgB","circleShape":"perseus_irgRpkgB","square-shape":"perseus_JsUZt48D","squareShape":"perseus_JsUZt48D"};
|
|
1755
1755
|
|
|
@@ -1759,19 +1759,17 @@ var styles$t = {"choice":"perseus_hm3uu-sq","is-correct":"perseus_qpU2z5U7","isC
|
|
|
1759
1759
|
|
|
1760
1760
|
const Choice=props=>{const showCorrectness=props.showCorrectness;const buttonRef=React.useRef(null);const indicatorShape=props.isMultiSelect?"square":"circle";const clickHandler=showCorrectness?undefined:()=>{buttonRef.current?.click();};const classes=[styles$t.choice].concat(showCorrectness?[styles$t["is-"+showCorrectness]]:[]).join(" ");return jsxRuntimeExports.jsxs("li",{className:classes,onClick:clickHandler,role:"listitem",children:[jsxRuntimeExports.jsx(Indicator,{buttonRef:buttonRef,checked:props.checked,content:props.indicatorContent,shape:indicatorShape,showCorrectness:showCorrectness,updateChecked:props.updateChecked}),props.children]})};
|
|
1761
1761
|
|
|
1762
|
-
var styles$s = {"container":"
|
|
1762
|
+
var styles$s = {"container":"perseus_yewUvpCl","choiceList":"perseus_ejJezW-c","content":"perseus_zAWs4E3G","instructions":"perseus_WyGpYl3q","rationale":"perseus_6vMrWVz0","isCorrect":"perseus_Zv66BVdg","reviewAnswers":"perseus_hJzSXKwq"};
|
|
1763
1763
|
|
|
1764
1764
|
function getChoiceLetter(pos,strings){const lettersString=strings.letters;const letters=lettersString.split(" ");if(pos<letters.length){return letters[pos]}return " "}function hasChoiceData(state){return state!=null&&typeof state==="object"&&"choiceStates"in state&&"choices"in state&&Array.isArray(state.choiceStates)&&Array.isArray(state.choices)}function getUserInputFromSerializedState$f(serializedState){const selectedChoiceIds=[];if(hasChoiceData(serializedState)){const{choiceStates,choices}=serializedState;for(let i=0;i<choiceStates.length;i++){const choiceState=choiceStates[i];const choice=choices[i];if(choiceState?.selected&&choice?.id){selectedChoiceIds.push(choice.id);}}}return {selectedChoiceIds}}function moveNoneOfTheAboveToEnd(choices){let noneOfTheAbove=null;const newChoices=choices.filter((choice,index)=>{if(choice.isNoneOfTheAbove){noneOfTheAbove=choice;return false}return true});if(noneOfTheAbove){newChoices.push(noneOfTheAbove);}return newChoices}function enforceOrdering(choices,strings){const ReversedChoices=[[strings.false,strings.true],[strings.no,strings.yes]];const content=choices.map(c=>c.content);if(ReversedChoices.some(reversed=>___default.default.isEqual(content,reversed))){return [choices[1],choices[0]]}return choices}function choiceTransform(choices,randomize,strings,seed){const choicesWithMetadata=choices.map((choice,i)=>{return {...choice,originalIndex:i,correct:Boolean(choice.correct)}});return moveNoneOfTheAboveToEnd(enforceOrdering(randomize?perseusCore.shuffle(choicesWithMetadata,seed):choicesWithMetadata,strings))}
|
|
1765
1765
|
|
|
1766
1766
|
const getInstructionsText=({multipleSelect,countChoices,numCorrect,strings})=>{if(multipleSelect){if(perseusCore.usesNumCorrect(multipleSelect,!!countChoices,numCorrect)){return strings.chooseNumAnswers({numCorrect:String(numCorrect)})}return strings.chooseAllAnswers}return strings.chooseOneAnswer};
|
|
1767
1767
|
|
|
1768
|
-
const
|
|
1768
|
+
const RadioComponent=({choices,countChoices,multipleSelect=false,numCorrect,onChoiceChange,reviewMode})=>{const{strings}=usePerseusI18n();const legendId=React.useId();const containerRef=React.useRef(null);const[backgroundColor,setBackgroundColor]=React.useState("transparent");React.useEffect(()=>{const container=containerRef.current;if(container){setBackgroundColor(getBackgroundColor(container));}},[]);wonderBlocksTiming.useTimeout(()=>{const container=containerRef.current;if(container){setBackgroundColor(getBackgroundColor(container));}},100);const instructions=getInstructionsText({multipleSelect,countChoices,numCorrect,strings});const choiceListClasses=reviewMode?`${styles$s.choiceList} ${styles$s.reviewAnswers}`:styles$s.choiceList;const cssVariableDeclaration=backgroundColor!=="transparent"?{"--perseus-widget-background-color":backgroundColor}:undefined;const scrollId=React.useId()+"-scroll";return jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsxs("fieldset",{className:styles$s.container,ref:containerRef,style:cssVariableDeclaration,children:[jsxRuntimeExports.jsx("legend",{id:legendId,"aria-hidden":"true",className:styles$s.instructions,children:instructions}),jsxRuntimeExports.jsx(ScrollableView,{id:scrollId,overflowX:"auto",children:jsxRuntimeExports.jsx("ul",{"data-widget":"radio","aria-labelledby":legendId,className:choiceListClasses,role:"list",children:jsxRuntimeExports.jsx(ChoiceListItems,{choices:choices,i18nStrings:strings,onChoiceChange:onChoiceChange,reviewMode:reviewMode,multipleSelect:multipleSelect})})})]}),jsxRuntimeExports.jsx(ScrollableView.Controls,{target:scrollId})]})};const ChoiceListItems=props=>{const{choices,i18nStrings,multipleSelect,onChoiceChange,reviewMode}=props;const listId=React.useId();const items=choices.map((choice,i)=>{const updateChecked=isChecked=>{onChoiceChange(choice.id,isChecked);};const contentId=`${listId}-choice-${i+1}`;const choiceLetter=getChoiceLetter(i,i18nStrings);const srContent=reviewMode&&choice.correct?i18nStrings.choiceCorrect:i18nStrings.choice;const indicatorContent={visible:choiceLetter,screenReader:srContent({letter:choiceLetter}),labelledBy:contentId};const showCorrectness=reviewMode?choice.correct?"correct":"wrong":undefined;const content=choice.isNoneOfTheAbove?i18nStrings.noneOfTheAbove:choice.content;let rationale;if(reviewMode&&choice.hasRationale){const rationaleId=`${contentId}-rationale`;indicatorContent.describedBy=rationaleId;const rationaleClasses=showCorrectness==="correct"?`${styles$s.rationale} ${styles$s.isCorrect}`:styles$s.rationale;rationale=jsxRuntimeExports.jsx("div",{id:rationaleId,className:rationaleClasses,children:choice.rationale});}return jsxRuntimeExports.jsx(Choice,{checked:choice.checked,indicatorContent:indicatorContent,isMultiSelect:multipleSelect,showCorrectness:showCorrectness,updateChecked:updateChecked,children:jsxRuntimeExports.jsxs("div",{className:styles$s.content,children:[jsxRuntimeExports.jsx("div",{id:contentId,children:content}),rationale]})},choice.id)});return jsxRuntimeExports.jsx(jsxRuntimeExports.Fragment,{children:items})};
|
|
1769
1769
|
|
|
1770
|
-
const getChoiceStates=({choices,showSolutions,choiceStates,reviewMode})=>{
|
|
1770
|
+
const getChoiceStates=({choices,showSolutions,choiceStates,reviewMode})=>{if(showSolutions==="all"||reviewMode){return choices.map(choice=>({selected:!!choice.correct}))}if(choiceStates){return choiceStates}return choices.map(()=>({selected:false}))};
|
|
1771
1771
|
|
|
1772
|
-
const
|
|
1773
|
-
|
|
1774
|
-
function initChoiceStates(choices){return choices.map(()=>({highlighted:false,rationaleShown:false,correctnessShown:false,previouslyAnswered:false,readOnly:false}))}let Radio$1 = class Radio extends React__namespace.Component{UNSAFE_componentWillUpdate(nextProps){if(!___default.default.isEqual(nextProps.choices,this.props.choices)){this.setState({choiceStates:initChoiceStates(nextProps.choices)});}}getSerializedState(){const{userInput:_,randomize:__,static:___,...rest}=this._mergePropsAndState();return {...rest,hasNoneOfTheAbove:rest.hasNoneOfTheAbove??false}}getPromptJSON(){if(!this.radioRef.current){throw new Error("Radio widget is not mounted; getPromptJSON is unavailable.")}return this.radioRef.current.getPromptJSON()}_mergePropsAndState(){const randomSeed=(this.props.problemNum??0)+(this.props.widgetIndex??0);const choices=[...choiceTransform(this.props.choices,this.props.randomize,this.context.strings,randomSeed)];return {...this.props,numCorrect:this.props.numCorrect??0,choices,choiceStates:this.state.choiceStates?.map((choiceState,index)=>{const choice=choices[index];const selected=this.props.userInput?.selectedChoiceIds.includes(choice?.id)??false;return {...choiceState,selected}})}}render(){const props=this._mergePropsAndState();return jsxRuntimeExports.jsx(Radio$2,{ref:this.radioRef,...props})}constructor(props){super(props),this.radioRef=React__namespace.createRef(),this.state={choiceStates:[]};this.state={choiceStates:initChoiceStates(props.choices)};}};Radio$1.contextType=PerseusI18nContext;
|
|
1772
|
+
const RadioWidget=React.forwardRef(function RadioWidget(props,ref){const{multipleSelect=false,countChoices=false,showSolutions="none",apiOptions,handleUserInput,trackInteraction,findWidgets,reviewMode,widgetId}=props;const{strings}=usePerseusI18n();const{analytics}=useDependencies();const randomSeed=(props.problemNum??0)+(props.widgetIndex??0);const choices=React.useMemo(()=>{return [...choiceTransform(props.choices,props.randomize,strings,randomSeed)]},[props.choices,props.randomize,strings,randomSeed]);wonderBlocksCore.useOnMountEffect(()=>{analytics.onAnalyticsEvent({type:"perseus:widget:rendered:ti",payload:{widgetSubType:multipleSelect?"multiple-select":"single-select",widgetType:"radio",widgetId:widgetId}});});React.useImperativeHandle(ref,()=>({getPromptJSON:()=>{return getPromptJSON$o({...props,choices},props.userInput)},getSerializedState(){const{userInput:_,randomize:__,static:___,...rest}=props;return {...rest,numCorrect:props.numCorrect??0,choices,hasNoneOfTheAbove:props.hasNoneOfTheAbove??false,choiceStates:choices.map(choice=>{const selected=props.userInput?.selectedChoiceIds.includes(choice?.id)??false;return {selected,highlighted:false,readOnly:false,rationaleShown:false,correctnessShown:false,previouslyAnswered:false}})}}}),[choices,props]);const renderContent=(content="")=>{const linterContext={contentType:"radio",highlightLint:false,paths:[],stack:[]};return jsxRuntimeExports.jsx(MathRenderingContext.Provider,{value:{shouldAddAriaLabels:true},children:jsxRuntimeExports.jsx(Renderer,{content:content,findExternalWidgets:findWidgets,alwaysUpdate:true,linterContext:linterContext,strings:strings},"choiceContentRenderer")})};const handleChoiceChange=(choiceId,newCheckedState)=>{const checkedChoiceIds=[];const choiceStates=choices.map(choice=>{return {selected:props.userInput?.selectedChoiceIds.includes(choice.id)??false,id:choice.id}});const currentSelectedIds=choiceStates.filter(choice=>choice.selected).map(choice=>choice.id);if(newCheckedState&&!multipleSelect){checkedChoiceIds.push(choiceId);}else if(newCheckedState&&multipleSelect){checkedChoiceIds.push(...currentSelectedIds,choiceId);}else {checkedChoiceIds.push(...currentSelectedIds.filter(id=>id!==choiceId));}handleUserInput({selectedChoiceIds:checkedChoiceIds});trackInteraction();announceChoiceChange(checkedChoiceIds.length);};const announceChoiceChange=newCheckedCount=>{let screenReaderMessage="";if(!props.multipleSelect){screenReaderMessage=newCheckedCount===0?strings.notSelected:"";}else {screenReaderMessage=strings.choicesSelected({num:newCheckedCount});}wonderBlocksAnnouncer.announceMessage({message:screenReaderMessage});if(props.multipleSelect){setTimeout(()=>{wonderBlocksAnnouncer.announceMessage({message:""});},300);}};const buildChoiceProps=choiceStates=>{return choices.map((choice,i)=>{const content=choice.isNoneOfTheAbove&&!choice.content?strings.noneOfTheAbove:choice.content;const{selected=false}=choiceStates[i]??{};return {id:choice.id,content:renderContent(content),checked:selected,correct:!!choice.correct,hasRationale:!!choice.rationale,rationale:renderContent(choice.rationale),isNoneOfTheAbove:!!choice.isNoneOfTheAbove}})};const prepareChoicesProps=()=>{const choiceStates=choices.map(choice=>{return {selected:props.userInput?.selectedChoiceIds.includes(choice.id)??false}});const processedChoiceStates=getChoiceStates({choices,showSolutions,choiceStates,reviewMode});return buildChoiceProps(processedChoiceStates)};const choicesProps=prepareChoicesProps();const numCorrect=props.numCorrect;const isReviewMode=reviewMode||showSolutions==="all";const onChoiceChange=apiOptions.readOnly||isReviewMode?()=>{}:handleChoiceChange;return jsxRuntimeExports.jsx(RadioComponent,{reviewMode:isReviewMode,multipleSelect:multipleSelect,countChoices:countChoices,numCorrect:numCorrect,choices:choicesProps,onChoiceChange:onChoiceChange})});let Radio$1 = class Radio extends React__namespace.Component{getSerializedState(){if(!this.radioRef.current){throw new Error("Radio widget is not mounted; getSerializedState is unavailable.")}return this.radioRef.current.getSerializedState()}getPromptJSON(){if(!this.radioRef.current){throw new Error("Radio widget is not mounted; getPromptJSON is unavailable.")}return this.radioRef.current.getPromptJSON()}render(){return jsxRuntimeExports.jsx(RadioWidget,{ref:this.radioRef,...this.props})}constructor(...args){super(...args),this.radioRef=React__namespace.createRef();}};
|
|
1775
1773
|
|
|
1776
1774
|
function getStartUserInput$g(){return {selectedChoiceIds:[]}}var Radio = {name:"radio",displayName:"Radio / Multiple choice",widget:Radio$1,getStartUserInput: getStartUserInput$g,version:perseusCore.radioLogic.version,isLintable:true,getUserInputFromSerializedState:serializedState=>{return getUserInputFromSerializedState$f(serializedState)}};
|
|
1777
1775
|
|
|
@@ -1807,7 +1805,7 @@ class DeprecatedStandin extends React__namespace.default.Component{render(){retu
|
|
|
1807
1805
|
|
|
1808
1806
|
const getPromptJSON$k=widgetData=>{return {type:"dropdown",options:{items:widgetData.choices.map(choice=>choice.content)},userInput:{selectedIndex:widgetData.userInput.value-1}}};
|
|
1809
1807
|
|
|
1810
|
-
const Dropdown=React.forwardRef(function Dropdown(props,ref){const{strings}=usePerseusI18n();const dropdownId=React.useId();const{choices=[],placeholder="",apiOptions=ApiOptions.defaults,userInput={value:0},static:isStatic=false,dependencies,visibleLabel,ariaLabel,widgetId,trackInteraction,handleUserInput}=props;React.useEffect(()=>{dependencies.analytics.onAnalyticsEvent({type:"perseus:widget:rendered:ti",payload:{widgetSubType:"null",widgetType:"dropdown",widgetId:widgetId}});},[]);const handleChange=selected=>{trackInteraction();handleUserInput({value:selected});};const rootRef=React.useRef(null);React.useImperativeHandle(ref,()=>({focus:()=>{if(apiOptions.readOnly||isStatic){return false}if(!rootRef.current){return false}const button=rootRef.current.querySelector("[role='combobox']");if(!(button instanceof HTMLElement)){return false}if(button instanceof HTMLButtonElement&&button.disabled||button.getAttribute("aria-disabled")==="true"){return false}const previouslyFocused=document.activeElement;button.focus();return document.activeElement===button&&previouslyFocused!==button},getPromptJSON:()=>{return getPromptJSON$k(props)},getSerializedState:()=>{const{userInput,choices,...rest}=props;return {...rest,choices:choices.map(choice=>choice.content),selected:userInput.value}}}));const children=[jsxRuntimeExports.jsx(wonderBlocksDropdown.OptionItem,{value:"0",disabled:true,label:jsxRuntimeExports.jsx(Renderer,{content:placeholder,strings:strings}),labelAsText:placeholder},"placeholder"),...choices.map((choice,i)=>jsxRuntimeExports.jsx(wonderBlocksDropdown.OptionItem,{value:String(i+1),label:jsxRuntimeExports.jsx(Renderer,{content:choice.content,strings:strings}),labelAsText:choice.content},String(i+1)))];return jsxRuntimeExports.jsxs(wonderBlocksCore.View,{ref:rootRef,onClick:e=>{e.stopPropagation();},onTouchStart:e=>{e.stopPropagation();},children:[visibleLabel&&jsxRuntimeExports.jsx(wonderBlocksTypography.
|
|
1808
|
+
const Dropdown=React.forwardRef(function Dropdown(props,ref){const{strings}=usePerseusI18n();const dropdownId=React.useId();const{choices=[],placeholder="",apiOptions=ApiOptions.defaults,userInput={value:0},static:isStatic=false,dependencies,visibleLabel,ariaLabel,widgetId,trackInteraction,handleUserInput}=props;React.useEffect(()=>{dependencies.analytics.onAnalyticsEvent({type:"perseus:widget:rendered:ti",payload:{widgetSubType:"null",widgetType:"dropdown",widgetId:widgetId}});},[]);const handleChange=selected=>{trackInteraction();handleUserInput({value:selected});};const rootRef=React.useRef(null);React.useImperativeHandle(ref,()=>({focus:()=>{if(apiOptions.readOnly||isStatic){return false}if(!rootRef.current){return false}const button=rootRef.current.querySelector("[role='combobox']");if(!(button instanceof HTMLElement)){return false}if(button instanceof HTMLButtonElement&&button.disabled||button.getAttribute("aria-disabled")==="true"){return false}const previouslyFocused=document.activeElement;button.focus();return document.activeElement===button&&previouslyFocused!==button},getPromptJSON:()=>{return getPromptJSON$k(props)},getSerializedState:()=>{const{userInput,choices,...rest}=props;return {...rest,choices:choices.map(choice=>choice.content),selected:userInput.value}}}));const children=[jsxRuntimeExports.jsx(wonderBlocksDropdown.OptionItem,{value:"0",disabled:true,label:jsxRuntimeExports.jsx(Renderer,{content:placeholder,strings:strings}),labelAsText:placeholder},"placeholder"),...choices.map((choice,i)=>jsxRuntimeExports.jsx(wonderBlocksDropdown.OptionItem,{value:String(i+1),label:jsxRuntimeExports.jsx(Renderer,{content:choice.content,strings:strings}),labelAsText:choice.content},String(i+1)))];return jsxRuntimeExports.jsxs(wonderBlocksCore.View,{ref:rootRef,onClick:e=>{e.stopPropagation();},onTouchStart:e=>{e.stopPropagation();},children:[visibleLabel&&jsxRuntimeExports.jsx(wonderBlocksTypography.BodyText,{size:"medium",weight:"bold",tag:"label",htmlFor:dropdownId,children:visibleLabel}),jsxRuntimeExports.jsx(wonderBlocksDropdown.SingleSelect,{id:dropdownId,placeholder:"",className:"perseus-dropdown",onChange:value=>handleChange(parseInt(value)),selectedValue:String(userInput.value),disabled:apiOptions.readOnly||isStatic,"aria-label":ariaLabel||visibleLabel||strings.selectAnAnswer,showOpenerLabelAsText:false,children:children})]})});function getUserInputFromSerializedState$c(serializedState){return {value:serializedState.selected}}function getStartUserInput$d(){return {value:0}}function getCorrectUserInput$6(options){return {value:options.choices.findIndex(c=>c.correct)+1}}const WrappedDropdown=withDependencies(Dropdown);var Dropdown$1 = {name:"dropdown",displayName:"Drop down",widget:WrappedDropdown,getStartUserInput: getStartUserInput$d,getCorrectUserInput: getCorrectUserInput$6,getUserInputFromSerializedState: getUserInputFromSerializedState$c};
|
|
1811
1809
|
|
|
1812
1810
|
function sharedInitializeUserInput(widgetOptions,problemNum){const startUserInput={};if(!widgetOptions){return startUserInput}Object.entries(widgetOptions).forEach(([id,widgetInfo])=>{const widgetExports=getWidgetExport(widgetInfo.type);if(widgetInfo.static&&widgetExports?.getCorrectUserInput){startUserInput[id]=widgetExports.getCorrectUserInput(widgetInfo.options);}else if(widgetExports?.getStartUserInput){startUserInput[id]=widgetExports.getStartUserInput(widgetInfo.options,problemNum??0);}});return startUserInput}function deriveUserInputFromSerializedState(serializedState,widgetsMap){const restoredUserInput={};Object.entries(serializedState).forEach(([widgetId,props])=>{const widgetType=getWidgetTypeByWidgetId(widgetId,widgetsMap);const widgetExport=getWidgetExport(widgetType);if(widgetExport?.getUserInputFromSerializedState){const restoreResult=widgetExport.getUserInputFromSerializedState(props,widgetsMap[widgetId].options);restoredUserInput[widgetId]=restoreResult;}});return restoredUserInput}function UserInputManager(props){const[userInput,setUserInput]=React.useState(props.initialUserInput||sharedInitializeUserInput(props.widgets,props.problemNum??0));function handleUserInput(id,nextUserInput,widgetsEmpty){const next={...userInput,[id]:nextUserInput};setUserInput(next);props.handleUserInput?.(next,widgetsEmpty);}function initializeUserInput(widgetOptions,problemNum){setUserInput(props.initialUserInput||sharedInitializeUserInput(widgetOptions,problemNum));}return props.children({userInput,handleUserInput,initializeUserInput})}
|
|
1813
1811
|
|
|
@@ -1857,7 +1855,7 @@ const VisibleIcon=()=>jsxRuntimeExports.jsxs("svg",{width:"24",height:"24",viewB
|
|
|
1857
1855
|
|
|
1858
1856
|
const BASE_ICON_SIZE=10;class Icon extends React__namespace.Component{render(){const{color,pathClassName,className,title,style,alt}=this.props;let{icon,size}=this.props;let units="";if(typeof icon==="string"){icon={path:icon,width:BASE_ICON_SIZE,height:BASE_ICON_SIZE};}if(typeof size!=="number"){size=1;units="em";}const height=size;const width=height/icon.height*icon.width;const xMin=0;const yMin=0;const focusable=!!this.props.focusable;return jsxRuntimeExports.jsxs("svg",{role:"img",alt:alt,"aria-label":title,"aria-hidden":title?null:true,className:className,style:style,focusable:focusable.toString(),width:width+units,height:height+units,viewBox:`${xMin} ${yMin} ${icon.width} ${icon.height}`,children:[!!title&&jsxRuntimeExports.jsx("title",{children:title}),jsxRuntimeExports.jsx("path",{className:pathClassName,fill:color,d:icon.path})]})}}Icon.defaultProps={color:"currentColor"};
|
|
1859
1857
|
|
|
1860
|
-
const InfoTipBase=props=>{return jsxRuntimeExports.jsx(Tooltip__default.default,{content:jsxRuntimeExports.jsx(wonderBlocksTypography.
|
|
1858
|
+
const InfoTipBase=props=>{return jsxRuntimeExports.jsx(Tooltip__default.default,{content:jsxRuntimeExports.jsx(wonderBlocksTypography.BodyText,{style:styles$e.body,children:props.children}),placement:"right",children:jsxRuntimeExports.jsx(wonderBlocksIcon.PhosphorIcon,{size:"small",icon:questionIcon__default.default,style:styles$e.spacingLeft})})};const styles$e=aphrodite.StyleSheet.create({spacingLeft:{marginInlineStart:wonderBlocksTokens.spacing.xxxSmall_4},body:{padding:wonderBlocksTokens.spacing.medium_16}});
|
|
1861
1859
|
|
|
1862
1860
|
class InfoTip extends React__namespace.Component{componentDidMount(){this.setState({didMount:true});}render(){if(this.state.didMount){return jsxRuntimeExports.jsx(InfoTipBase,{...this.props})}return jsxRuntimeExports.jsx("div",{})}constructor(...args){super(...args),this.state={didMount:false};}}
|
|
1863
1861
|
|
|
@@ -1890,7 +1888,7 @@ var components = /*#__PURE__*/Object.freeze({
|
|
|
1890
1888
|
|
|
1891
1889
|
const GifControlsButton=({isPlaying,onToggle})=>{const strings=usePerseusI18n().strings;return jsxRuntimeExports.jsx(Button__default.default,{kind:"secondary",startIcon:isPlaying?pauseIcon__default.default:playIcon__default.default,onClick:onToggle,style:{width:"fit-content"},children:isPlaying?strings.gifPauseButtonLabel:strings.gifPlayButtonLabel})};
|
|
1892
1890
|
|
|
1893
|
-
const MODAL_HEIGHT=568;function ExploreImageModalContent({backgroundImage,scale:contentScale,caption,alt,longDescription,linterContext,apiOptions,box,labels,range,zoomSize,isGifPlaying,setIsGifPlaying}){const context=React__namespace.useContext(PerseusI18nContext);if(!backgroundImage.url){return null}const scaleFF=perseusCore.isFeatureOn({apiOptions},"image-widget-upgrade-scale");const gifControlsFF=perseusCore.isFeatureOn({apiOptions},"image-widget-upgrade-gif-controls");const[zoomWidth,zoomHeight]=zoomSize;const imageIsGif=isGif(backgroundImage.url);const imageIsSvg=isSvg(backgroundImage.url);let scale=1;if(backgroundImage.width&&backgroundImage.height){scale=imageIsSvg?Math.max(contentScale,2):Math.max(contentScale,1);}let height=backgroundImage.height;let width=backgroundImage.width;height=Math.min(MODAL_HEIGHT,zoomHeight);width=zoomWidth/zoomHeight*height;if(scaleFF){if(backgroundImage.height&&backgroundImage.width){height=Math.min(MODAL_HEIGHT/scale,backgroundImage.height);width=backgroundImage.width/backgroundImage.height*height;}}return jsxRuntimeExports.jsxs("div",{className:styles$g.modalPanelContainer,children:[jsxRuntimeExports.jsx("div",{className:styles$g.modalImageContainer,children:jsxRuntimeExports.jsx(context$1.Consumer,{children:({setAssetStatus})=>jsxRuntimeExports.jsx(SvgImage,{src:backgroundImage.url,allowZoom:false,alt:caption===alt?"":alt,width:width,height:height,scale:scaleFF?scale:1,preloader:apiOptions.imagePreloader,extraGraphie:{box:box,range:range,labels:labels??[]},zoomToFullSizeOnMobile:apiOptions.isMobile,constrainHeight:apiOptions.isMobile,allowFullBleed:apiOptions.isMobile,setAssetStatus:setAssetStatus})})}),jsxRuntimeExports.jsxs("div",{className:`perseus-image-modal-description ${styles$g.modalDescriptionContainer}`,children:[gifControlsFF&&imageIsGif&&jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx(GifControlsButton,{isPlaying:isGifPlaying,onToggle:()=>setIsGifPlaying(!isGifPlaying)}),jsxRuntimeExports.jsx("div",{className:styles$g.spacerVertical})]}),caption&&jsxRuntimeExports.jsx("div",{className:styles$g.modalCaptionContainer,children:jsxRuntimeExports.jsx(Renderer,{content:caption,apiOptions:apiOptions,linterContext:linterContext,strings:context.strings})}),jsxRuntimeExports.jsx(wonderBlocksTypography.
|
|
1891
|
+
const MODAL_HEIGHT=568;function ExploreImageModalContent({backgroundImage,scale:contentScale,caption,alt,longDescription,linterContext,apiOptions,box,labels,range,zoomSize,isGifPlaying,setIsGifPlaying}){const context=React__namespace.useContext(PerseusI18nContext);if(!backgroundImage.url){return null}const scaleFF=perseusCore.isFeatureOn({apiOptions},"image-widget-upgrade-scale");const gifControlsFF=perseusCore.isFeatureOn({apiOptions},"image-widget-upgrade-gif-controls");const[zoomWidth,zoomHeight]=zoomSize;const imageIsGif=isGif(backgroundImage.url);const imageIsSvg=isSvg(backgroundImage.url);let scale=1;if(backgroundImage.width&&backgroundImage.height){scale=imageIsSvg?Math.max(contentScale,2):Math.max(contentScale,1);}let height=backgroundImage.height;let width=backgroundImage.width;height=Math.min(MODAL_HEIGHT,zoomHeight);width=zoomWidth/zoomHeight*height;if(scaleFF){if(backgroundImage.height&&backgroundImage.width){height=Math.min(MODAL_HEIGHT/scale,backgroundImage.height);width=backgroundImage.width/backgroundImage.height*height;}}return jsxRuntimeExports.jsxs("div",{className:styles$g.modalPanelContainer,children:[jsxRuntimeExports.jsx("div",{className:styles$g.modalImageContainer,children:jsxRuntimeExports.jsx(context$1.Consumer,{children:({setAssetStatus})=>jsxRuntimeExports.jsx(SvgImage,{src:backgroundImage.url,allowZoom:false,alt:caption===alt?"":alt,width:width,height:height,scale:scaleFF?scale:1,preloader:apiOptions.imagePreloader,extraGraphie:{box:box,range:range,labels:labels??[]},zoomToFullSizeOnMobile:apiOptions.isMobile,constrainHeight:apiOptions.isMobile,allowFullBleed:apiOptions.isMobile,setAssetStatus:setAssetStatus})})}),jsxRuntimeExports.jsxs("div",{className:`perseus-image-modal-description ${styles$g.modalDescriptionContainer}`,children:[gifControlsFF&&imageIsGif&&jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx(GifControlsButton,{isPlaying:isGifPlaying,onToggle:()=>setIsGifPlaying(!isGifPlaying)}),jsxRuntimeExports.jsx("div",{className:styles$g.spacerVertical})]}),caption&&jsxRuntimeExports.jsx("div",{className:styles$g.modalCaptionContainer,children:jsxRuntimeExports.jsx(Renderer,{content:caption,apiOptions:apiOptions,linterContext:linterContext,strings:context.strings})}),jsxRuntimeExports.jsx(wonderBlocksTypography.Heading,{size:"large",tag:"h2",style:wbStyles$1.descriptionHeading,children:context.strings.imageDescriptionLabel}),jsxRuntimeExports.jsx(Renderer,{content:longDescription,apiOptions:apiOptions,linterContext:linterContext,strings:context.strings})]})]})}const wbStyles$1={descriptionHeading:{marginBlockEnd:wonderBlocksTokens.sizing.size_160}};
|
|
1894
1892
|
|
|
1895
1893
|
const ExploreImageModal=props=>{const context=React__namespace.default.useContext(PerseusI18nContext);const titleText=props.title||context.strings.imageAlternativeTitle;const title=jsxRuntimeExports.jsx("h1",{className:`perseus-image-modal-title ${styles$g.modalTitleContainer}`,children:jsxRuntimeExports.jsx(Renderer,{content:titleText,apiOptions:props.apiOptions,linterContext:props.linterContext,strings:context.strings})});return jsxRuntimeExports.jsx("div",{className:`framework-perseus ${styles$g.modalContainer}`,children:jsxRuntimeExports.jsx(wonderBlocksModal.FlexibleDialog,{title:title,content:jsxRuntimeExports.jsx(ExploreImageModalContent,{...props}),styles:{root:wbStyles.root}})})};const wbStyles={root:{borderRadius:wonderBlocksTokens.sizing.size_120,maxWidth:"100%"}};
|
|
1896
1894
|
|
|
@@ -2032,7 +2030,7 @@ function renderTangentGraph(state,dispatch,i18n){return {graph:jsxRuntimeExports
|
|
|
2032
2030
|
|
|
2033
2031
|
const{calculateAngleInDegrees,convertDegreesToRadians}=kmath.angles;const protractorImage="https://cdn.kastatic.org/images/perseus/protractor.svg";const centerToTopLeft=[-195,-190];const centerToRotationHandle=[-201,-15];function Protractor(){const staticUrl=getDependencies().staticUrl;const{range,snapStep}=useGraphConfig();const[[xMin,xMax],[yMin,yMax]]=range;const initialCenter=[lerp(xMin,xMax,.5),lerp(yMin,yMax,.25)];const[center,setCenter]=React.useState(initialCenter);const[rotationHandleOffset,setRotationHandleOffset]=React.useState(centerToRotationHandle);const draggableRef=React.useRef(null);const{dragging}=useDraggable({gestureTarget:draggableRef,onMove:setCenter,point:center,constrainKeyboardMovement:point=>bound$1({snapStep,range,point})});const rotationHandleRef=React.useRef(null);useDraggablePx({gestureTarget:rotationHandleRef,onMove:setRotationHandleOffset,point:rotationHandleOffset,constrain:constrainToCircle});const[centerPx]=useTransformVectorsToPixels(center);const topLeftPx=mafs.vec.add(centerPx,centerToTopLeft);const angle=calculateAngleInDegrees(rotationHandleOffset)-calculateAngleInDegrees(centerToRotationHandle);return jsxRuntimeExports.jsxs("g",{ref:draggableRef,transform:`translate(${topLeftPx[X]}, ${topLeftPx[Y]}), rotate(${angle})`,style:{transformOrigin:`${-centerToTopLeft[X]}px ${-centerToTopLeft[Y]}px`,cursor:dragging?"grabbing":"grab"},children:[jsxRuntimeExports.jsx("image",{href:staticUrl(protractorImage)}),jsxRuntimeExports.jsx("g",{transform:`translate(5, ${-centerToTopLeft[1]})`,ref:rotationHandleRef,children:jsxRuntimeExports.jsx(RotationArrow,{})})]})}function RotationArrow(){const radius=175;const angleDeg=10;const angleRad=convertDegreesToRadians(angleDeg);const endX=radius*(1-Math.cos(angleRad));const endY=radius*-Math.sin(angleRad);const rotationArrow=pathBuilder().move(0,0).circularArc(radius,endX,endY,{sweep:true}).build();const arrowhead=pathBuilder().move(-8,0).line(0,10).line(8,0).build();const targetRadius=TARGET_SIZE/2;return jsxRuntimeExports.jsxs("g",{className:"protractor-rotation-handle",children:[jsxRuntimeExports.jsx("path",{className:"protractor-rotation-handle-arrow-arc",d:rotationArrow}),jsxRuntimeExports.jsx("path",{className:"protractor-rotation-handle-arrowhead",d:arrowhead}),jsxRuntimeExports.jsx("path",{className:"protractor-rotation-handle-arrowhead",d:arrowhead,transform:`translate(${endX}, ${endY}), rotate(${180+angleDeg})`}),jsxRuntimeExports.jsx("ellipse",{cx:"0px",cy:"-15px",rx:targetRadius,ry:targetRadius,fill:"none"})]})}const protractorRadius=mafs.vec.mag(centerToRotationHandle);function constrainToCircle(edgePoint){return mafs.vec.withMag(edgePoint,protractorRadius)}function useDraggablePx(args){const{gestureTarget:target,onMove,point,constrain=p=>p}=args;const pickupPx=React__namespace.useRef([0,0]);react.useDrag(state=>{const{event,first,movement:pixelMovement}=state;event?.stopPropagation();if(first){pickupPx.current=point;}if(mafs.vec.mag(pixelMovement)===0){return}onMove?.(constrain(mafs.vec.add(pickupPx.current,pixelMovement)));},{target,eventOptions:{passive:false}});}
|
|
2034
2032
|
|
|
2035
|
-
const GRAPH_LEFT_MARGIN=20;const MafsGraph=props=>{const{state,dispatch,labels,labelLocation,readOnly,fullGraphAriaLabel,fullGraphAriaDescription,widgetId}=props;const{type}=state;const[width,height]=props.box;const tickStep=props.step;const uniqueId=React__namespace.useId();const descriptionId=`interactive-graph-description-${uniqueId}`;const interactiveElementsDescriptionId=`interactive-graph-interactive-elements-description-${uniqueId}`;const unlimitedGraphKeyboardPromptId=`unlimited-graph-keyboard-prompt-${uniqueId}`;const instructionsId=`instructions-${uniqueId}`;const graphRef=React__namespace.useRef(null);const{analytics}=useDependencies();const{viewboxX,viewboxY}=calculateNestedSVGCoords(state.range,width,height);const viewBox=`${viewboxX} ${viewboxY} ${width} ${height}`;const nestedSVGAttributes={width,height,viewBox,preserveAspectRatio:"xMidYMin",x:viewboxX,y:viewboxY};const i18n=usePerseusI18n();const{strings}=i18n;const interactionPrompt=isUnlimitedGraphState(state)&&state.showKeyboardInteractionInvitation;wonderBlocksCore.useOnMountEffect(()=>{analytics.onAnalyticsEvent({type:"perseus:widget:rendered:ti",payload:{widgetSubType:type,widgetType:"interactive-graph",widgetId:widgetId}});});const{graph,interactiveElementsDescription}=renderGraphElements({state,dispatch,i18n,markings:props.markings});const disableInteraction=readOnly||!!props.static;const graphInfo={range:state.range,width,height};const[xAxisLabelLocation,yAxisLabelLocation]=getLabelPosition(graphInfo,labelLocation,tickStep);const needsExtraMargin=labelLocation==="alongEdge"&&yAxisLabelLocation[0]<-14*fontSizeYAxisLabelMultiplier;const marginLabelDiff=GRAPH_LEFT_MARGIN-fontSize*fontSizeYAxisLabelMultiplier;const marginWithExtraOffset=-1*(yAxisLabelLocation[X]-marginLabelDiff);return jsxRuntimeExports.jsx(GraphConfigContext.Provider,{value:{range:state.range,snapStep:state.snapStep,markings:props.markings,tickStep:tickStep,gridStep:props.gridStep,showTooltips:!!props.showTooltips,showAxisArrows:props.showAxisArrows,graphDimensionsInPixels:props.box,width,height,labels,labelLocation,disableKeyboardInteraction:disableInteraction,interactiveColor:disableInteraction?"var(--static-gray)":"var(--mafs-blue)"},children:jsxRuntimeExports.jsxs(wonderBlocksCore.View,{className:"mafs-graph-container",children:[jsxRuntimeExports.jsxs(wonderBlocksCore.View,{className:"mafs-graph",style:{position:"relative",padding:"25px 25px 0 0",boxSizing:"content-box",marginLeft:needsExtraMargin?`${marginWithExtraOffset}px`:`${GRAPH_LEFT_MARGIN}px`,marginBottom:"30px",pointerEvents:props.static?"none":"auto",userSelect:"none",width,height},onKeyUp:event=>{handleKeyboardEvent(event,state,dispatch);},"aria-label":fullGraphAriaLabel,"aria-describedby":describedByIds(fullGraphAriaDescription&&descriptionId,interactiveElementsDescription&&interactiveElementsDescriptionId,isUnlimitedGraphState(state)&&unlimitedGraphKeyboardPromptId,state.type!=="none"&&!disableInteraction&&instructionsId),ref:graphRef,tabIndex:0,onFocus:event=>{handleFocusEvent(event,state,dispatch);},onBlur:event=>{handleBlurEvent(event,state,dispatch);},children:[fullGraphAriaDescription&&jsxRuntimeExports.jsx(wonderBlocksCore.View,{id:descriptionId,tabIndex:-1,className:"mafs-sr-only",children:fullGraphAriaDescription}),interactiveElementsDescription&&jsxRuntimeExports.jsx(wonderBlocksCore.View,{id:interactiveElementsDescriptionId,tabIndex:-1,className:"mafs-sr-only",children:interactiveElementsDescription}),state.type!=="none"&&jsxRuntimeExports.jsx(wonderBlocksCore.View,{id:instructionsId,tabIndex:-1,className:"mafs-sr-only",children:isUnlimitedGraphState(state)?strings.srUnlimitedGraphInstructions:strings.srGraphInstructions}),jsxRuntimeExports.jsx(LegacyGrid,{box:props.box,backgroundImage:props.backgroundImage}),jsxRuntimeExports.jsxs(wonderBlocksCore.View,{style:{position:"absolute",bottom:0,left:0},children:[(props.markings==="graph"||props.markings==="axes")&&jsxRuntimeExports.jsx(jsxRuntimeExports.Fragment,{children:jsxRuntimeExports.jsx(AxisLabels,{i18n:i18n,xAxisLabelLocation:xAxisLabelLocation,yAxisLabelLocation:yAxisLabelLocation})}),jsxRuntimeExports.jsx(wonderBlocksCore.View,{"aria-hidden":props.lockedFigures.length===0,children:jsxRuntimeExports.jsxs(mafs.Mafs,{preserveAspectRatio:false,viewBox:{x:state.range[X],y:state.range[Y],padding:0},pan:false,zoom:false,width:width,height:height,children:[jsxRuntimeExports.jsx(SvgDefs,{}),jsxRuntimeExports.jsx("svg",{...nestedSVGAttributes,children:jsxRuntimeExports.jsx(Grid,{gridStep:props.gridStep,range:state.range,containerSizeClass:props.containerSizeClass,markings:props.markings,width:width,height:height})}),(props.markings==="graph"||props.markings==="axes")&&jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx(AxisTicks,{}),jsxRuntimeExports.jsx(AxisArrows,{})]}),props.lockedFigures.length>0&&jsxRuntimeExports.jsx("svg",{...nestedSVGAttributes,children:jsxRuntimeExports.jsx(GraphLockedLayer,{lockedFigures:props.lockedFigures,range:state.range})})]})}),jsxRuntimeExports.jsx(GraphLockedLabelsLayer,{lockedFigures:props.lockedFigures}),jsxRuntimeExports.jsx(wonderBlocksCore.View,{style:{position:"absolute"},children:jsxRuntimeExports.jsx(mafs.Mafs,{preserveAspectRatio:false,viewBox:{x:state.range[X],y:state.range[Y],padding:0},pan:false,zoom:false,width:width,height:height,children:jsxRuntimeExports.jsxs("svg",{...nestedSVGAttributes,style:{overflow:type==="point"?"visible":"hidden"},children:[props.showProtractor&&jsxRuntimeExports.jsx(Protractor,{}),graph]})})})]}),interactionPrompt&&jsxRuntimeExports.jsx(wonderBlocksCore.View,{style:{display:interactionPrompt?undefined:"hidden",textAlign:"center",backgroundColor:"white",border:"1px solid #21242C52",padding:"16px 0",boxShadow:"0px 8px 8px 0px #21242C14",top:"50%",transform:"translateY(-50%)"},children:jsxRuntimeExports.jsx(wonderBlocksTypography.LabelMedium,{id:unlimitedGraphKeyboardPromptId,children:strings.graphKeyboardPrompt})})]}),renderGraphControls({state,dispatch,width,perseusStrings:strings})]})})};const renderPointGraphControls=props=>{const{interactionMode,showRemovePointButton,focusedPointIndex}=props.state;const{perseusStrings}=props;const shouldShowRemoveButton=showRemovePointButton&&focusedPointIndex!==null;return jsxRuntimeExports.jsxs(wonderBlocksCore.View,{style:{flexDirection:"row",width:props.width},children:[interactionMode==="keyboard"&&jsxRuntimeExports.jsx(Button__default.default,{kind:"secondary",style:{width:"100%",marginLeft:"20px"},tabIndex:0,onClick:()=>{props.dispatch(actions.pointGraph.addPoint([0,0]));},children:perseusStrings.addPoint}),interactionMode==="mouse"&&jsxRuntimeExports.jsx(Button__default.default,{id:REMOVE_BUTTON_ID,kind:"secondary",actionType:"destructive",tabIndex:-1,style:{width:"100%",marginLeft:"20px",visibility:shouldShowRemoveButton?"visible":"hidden"},onClick:_event=>{props.dispatch(actions.pointGraph.removePoint(props.state.focusedPointIndex));},children:perseusStrings.removePoint})]})};const renderPolygonGraphControls=props=>{const{interactionMode,showRemovePointButton,focusedPointIndex,closedPolygon,coords}=props.state;const{perseusStrings}=props;const shouldShowRemoveButton=showRemovePointButton&&focusedPointIndex!==null;const disableCloseButton=getArrayWithoutDuplicates(coords).length<3;const polygonButton=closedPolygon?jsxRuntimeExports.jsx(Button__default.default,{kind:"secondary",style:{width:"100%",marginLeft:"20px"},tabIndex:0,onClick:()=>{props.dispatch(actions.polygon.openPolygon());},children:perseusStrings.openPolygon}):jsxRuntimeExports.jsx(Button__default.default,{kind:"secondary",disabled:disableCloseButton,style:{width:"100%",marginLeft:"20px"},tabIndex:disableCloseButton?-1:0,onClick:()=>{props.dispatch(actions.polygon.closePolygon());},children:perseusStrings.closePolygon});return jsxRuntimeExports.jsx(jsxRuntimeExports.Fragment,{children:jsxRuntimeExports.jsxs(wonderBlocksCore.View,{style:{flexDirection:"row",width:props.width},children:[interactionMode==="keyboard"&&jsxRuntimeExports.jsx(Button__default.default,{kind:"secondary",style:{width:"100%",marginLeft:"20px"},disabled:closedPolygon,tabIndex:closedPolygon?-1:0,onClick:()=>{props.dispatch(actions.polygon.addPoint([0,0]));},children:perseusStrings.addPoint}),interactionMode==="mouse"&&jsxRuntimeExports.jsx(Button__default.default,{id:REMOVE_BUTTON_ID,kind:"secondary",actionType:"destructive",disabled:closedPolygon||!shouldShowRemoveButton,tabIndex:-1,style:{width:"100%",marginLeft:"20px"},onClick:_event=>{props.dispatch(actions.polygon.removePoint(props.state.focusedPointIndex));},children:perseusStrings.removePoint}),polygonButton]})})};const renderGraphControls=props=>{const{state,dispatch,width,perseusStrings}=props;const{type}=state;switch(type){case "point":if(state.numPoints==="unlimited"){return renderPointGraphControls({state,dispatch,width,perseusStrings})}return null;case "polygon":if(state.numSides==="unlimited"){return renderPolygonGraphControls({state,dispatch,width,perseusStrings})}return null;default:return null}};function handleFocusEvent(event,state,dispatch){if(isUnlimitedGraphState(state)){if(event.target.classList.contains("mafs-graph")&&state.interactionMode==="mouse"){dispatch(actions.global.changeKeyboardInvitationVisibility(true));}}}function handleBlurEvent(_event,state,dispatch){if(isUnlimitedGraphState(state)){dispatch(actions.global.changeKeyboardInvitationVisibility(false));}}function handleKeyboardEvent(event,state,dispatch){if(isUnlimitedGraphState(state)){if(event.key==="Backspace"||event.key==="Delete"){if(document.activeElement?.classList.contains("movable-point__focusable-handle")){if(state.type==="point"||state.type==="polygon"&&!state.closedPolygon){dispatch(actions.global.deleteIntent());}}document.activeElement.blur();}else if(event.shiftKey&&event.key==="Enter"){dispatch(actions.global.changeInteractionMode("keyboard"));}else if(state.interactionMode==="keyboard"&&event.key==="a"){dispatch(actions.pointGraph.addPoint([0,0]));}}}const renderGraphElements=props=>{const{state,dispatch,i18n,markings}=props;const{type}=state;switch(type){case "angle":return renderAngleGraph(state,dispatch,i18n);case "segment":return renderSegmentGraph(state,dispatch,i18n);case "linear-system":return renderLinearSystemGraph(state,dispatch,i18n);case "linear":return renderLinearGraph(state,dispatch,i18n);case "ray":return renderRayGraph(state,dispatch,i18n);case "polygon":return renderPolygonGraph(state,dispatch,i18n,markings);case "point":return renderPointGraph(state,dispatch,i18n);case "circle":return renderCircleGraph(state,dispatch,i18n);case "quadratic":return renderQuadraticGraph(state,dispatch,i18n);case "sinusoid":return renderSinusoidGraph(state,dispatch,i18n);case "exponential":return renderExponentialGraph(state,dispatch,i18n);case "none":return {graph:null,interactiveElementsDescription:null};case "absolute-value":return renderAbsoluteValueGraph(state,dispatch,i18n);case "tangent":return renderTangentGraph(state,dispatch,i18n);default:throw new wonderStuffCore.UnreachableCaseError(type)}};function describedByIds(...args){return args.filter(Boolean).join(" ")||undefined}
|
|
2033
|
+
const GRAPH_LEFT_MARGIN=20;const MafsGraph=props=>{const{state,dispatch,labels,labelLocation,readOnly,fullGraphAriaLabel,fullGraphAriaDescription,widgetId}=props;const{type}=state;const[width,height]=props.box;const tickStep=props.step;const uniqueId=React__namespace.useId();const descriptionId=`interactive-graph-description-${uniqueId}`;const interactiveElementsDescriptionId=`interactive-graph-interactive-elements-description-${uniqueId}`;const unlimitedGraphKeyboardPromptId=`unlimited-graph-keyboard-prompt-${uniqueId}`;const instructionsId=`instructions-${uniqueId}`;const graphRef=React__namespace.useRef(null);const{analytics}=useDependencies();const{viewboxX,viewboxY}=calculateNestedSVGCoords(state.range,width,height);const viewBox=`${viewboxX} ${viewboxY} ${width} ${height}`;const nestedSVGAttributes={width,height,viewBox,preserveAspectRatio:"xMidYMin",x:viewboxX,y:viewboxY};const i18n=usePerseusI18n();const{strings}=i18n;const interactionPrompt=isUnlimitedGraphState(state)&&state.showKeyboardInteractionInvitation;wonderBlocksCore.useOnMountEffect(()=>{analytics.onAnalyticsEvent({type:"perseus:widget:rendered:ti",payload:{widgetSubType:type,widgetType:"interactive-graph",widgetId:widgetId}});});const{graph,interactiveElementsDescription}=renderGraphElements({state,dispatch,i18n,markings:props.markings});const disableInteraction=readOnly||!!props.static;const graphInfo={range:state.range,width,height};const[xAxisLabelLocation,yAxisLabelLocation]=getLabelPosition(graphInfo,labelLocation,tickStep);const needsExtraMargin=labelLocation==="alongEdge"&&yAxisLabelLocation[0]<-14*fontSizeYAxisLabelMultiplier;const marginLabelDiff=GRAPH_LEFT_MARGIN-fontSize*fontSizeYAxisLabelMultiplier;const marginWithExtraOffset=-1*(yAxisLabelLocation[X]-marginLabelDiff);return jsxRuntimeExports.jsx(GraphConfigContext.Provider,{value:{range:state.range,snapStep:state.snapStep,markings:props.markings,tickStep:tickStep,gridStep:props.gridStep,showTooltips:!!props.showTooltips,showAxisArrows:props.showAxisArrows,graphDimensionsInPixels:props.box,width,height,labels,labelLocation,disableKeyboardInteraction:disableInteraction,interactiveColor:disableInteraction?"var(--static-gray)":"var(--mafs-blue)"},children:jsxRuntimeExports.jsxs(wonderBlocksCore.View,{className:"mafs-graph-container",children:[jsxRuntimeExports.jsxs(wonderBlocksCore.View,{className:"mafs-graph",style:{position:"relative",padding:"25px 25px 0 0",boxSizing:"content-box",marginLeft:needsExtraMargin?`${marginWithExtraOffset}px`:`${GRAPH_LEFT_MARGIN}px`,marginBottom:"30px",pointerEvents:props.static?"none":"auto",userSelect:"none",width,height},onKeyUp:event=>{handleKeyboardEvent(event,state,dispatch);},"aria-label":fullGraphAriaLabel,"aria-describedby":describedByIds(fullGraphAriaDescription&&descriptionId,interactiveElementsDescription&&interactiveElementsDescriptionId,isUnlimitedGraphState(state)&&unlimitedGraphKeyboardPromptId,state.type!=="none"&&!disableInteraction&&instructionsId),ref:graphRef,tabIndex:0,onFocus:event=>{handleFocusEvent(event,state,dispatch);},onBlur:event=>{handleBlurEvent(event,state,dispatch);},children:[fullGraphAriaDescription&&jsxRuntimeExports.jsx(wonderBlocksCore.View,{id:descriptionId,tabIndex:-1,className:"mafs-sr-only",children:fullGraphAriaDescription}),interactiveElementsDescription&&jsxRuntimeExports.jsx(wonderBlocksCore.View,{id:interactiveElementsDescriptionId,tabIndex:-1,className:"mafs-sr-only",children:interactiveElementsDescription}),state.type!=="none"&&jsxRuntimeExports.jsx(wonderBlocksCore.View,{id:instructionsId,tabIndex:-1,className:"mafs-sr-only",children:isUnlimitedGraphState(state)?strings.srUnlimitedGraphInstructions:strings.srGraphInstructions}),jsxRuntimeExports.jsx(LegacyGrid,{box:props.box,backgroundImage:props.backgroundImage}),jsxRuntimeExports.jsxs(wonderBlocksCore.View,{style:{position:"absolute",bottom:0,left:0},children:[(props.markings==="graph"||props.markings==="axes")&&jsxRuntimeExports.jsx(jsxRuntimeExports.Fragment,{children:jsxRuntimeExports.jsx(AxisLabels,{i18n:i18n,xAxisLabelLocation:xAxisLabelLocation,yAxisLabelLocation:yAxisLabelLocation})}),jsxRuntimeExports.jsx(wonderBlocksCore.View,{"aria-hidden":props.lockedFigures.length===0,children:jsxRuntimeExports.jsxs(mafs.Mafs,{preserveAspectRatio:false,viewBox:{x:state.range[X],y:state.range[Y],padding:0},pan:false,zoom:false,width:width,height:height,children:[jsxRuntimeExports.jsx(SvgDefs,{}),jsxRuntimeExports.jsx("svg",{...nestedSVGAttributes,children:jsxRuntimeExports.jsx(Grid,{gridStep:props.gridStep,range:state.range,containerSizeClass:props.containerSizeClass,markings:props.markings,width:width,height:height})}),(props.markings==="graph"||props.markings==="axes")&&jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx(AxisTicks,{}),jsxRuntimeExports.jsx(AxisArrows,{})]}),props.lockedFigures.length>0&&jsxRuntimeExports.jsx("svg",{...nestedSVGAttributes,children:jsxRuntimeExports.jsx(GraphLockedLayer,{lockedFigures:props.lockedFigures,range:state.range})})]})}),jsxRuntimeExports.jsx(GraphLockedLabelsLayer,{lockedFigures:props.lockedFigures}),jsxRuntimeExports.jsx(wonderBlocksCore.View,{style:{position:"absolute"},children:jsxRuntimeExports.jsx(mafs.Mafs,{preserveAspectRatio:false,viewBox:{x:state.range[X],y:state.range[Y],padding:0},pan:false,zoom:false,width:width,height:height,children:jsxRuntimeExports.jsxs("svg",{...nestedSVGAttributes,style:{overflow:type==="point"?"visible":"hidden"},children:[props.showProtractor&&jsxRuntimeExports.jsx(Protractor,{}),graph]})})})]}),interactionPrompt&&jsxRuntimeExports.jsx(wonderBlocksCore.View,{style:{display:interactionPrompt?undefined:"hidden",textAlign:"center",backgroundColor:"white",border:"1px solid #21242C52",padding:"16px 0",boxShadow:"0px 8px 8px 0px #21242C14",top:"50%",transform:"translateY(-50%)"},children:jsxRuntimeExports.jsx(wonderBlocksTypography.BodyText,{id:unlimitedGraphKeyboardPromptId,children:strings.graphKeyboardPrompt})})]}),renderGraphControls({state,dispatch,width,perseusStrings:strings})]})})};const renderPointGraphControls=props=>{const{interactionMode,showRemovePointButton,focusedPointIndex}=props.state;const{perseusStrings}=props;const shouldShowRemoveButton=showRemovePointButton&&focusedPointIndex!==null;return jsxRuntimeExports.jsxs(wonderBlocksCore.View,{style:{flexDirection:"row",width:props.width},children:[interactionMode==="keyboard"&&jsxRuntimeExports.jsx(Button__default.default,{kind:"secondary",style:{width:"100%",marginLeft:"20px"},tabIndex:0,onClick:()=>{props.dispatch(actions.pointGraph.addPoint([0,0]));},children:perseusStrings.addPoint}),interactionMode==="mouse"&&jsxRuntimeExports.jsx(Button__default.default,{id:REMOVE_BUTTON_ID,kind:"secondary",actionType:"destructive",tabIndex:-1,style:{width:"100%",marginLeft:"20px",visibility:shouldShowRemoveButton?"visible":"hidden"},onClick:_event=>{props.dispatch(actions.pointGraph.removePoint(props.state.focusedPointIndex));},children:perseusStrings.removePoint})]})};const renderPolygonGraphControls=props=>{const{interactionMode,showRemovePointButton,focusedPointIndex,closedPolygon,coords}=props.state;const{perseusStrings}=props;const shouldShowRemoveButton=showRemovePointButton&&focusedPointIndex!==null;const disableCloseButton=getArrayWithoutDuplicates(coords).length<3;const polygonButton=closedPolygon?jsxRuntimeExports.jsx(Button__default.default,{kind:"secondary",style:{width:"100%",marginLeft:"20px"},tabIndex:0,onClick:()=>{props.dispatch(actions.polygon.openPolygon());},children:perseusStrings.openPolygon}):jsxRuntimeExports.jsx(Button__default.default,{kind:"secondary",disabled:disableCloseButton,style:{width:"100%",marginLeft:"20px"},tabIndex:disableCloseButton?-1:0,onClick:()=>{props.dispatch(actions.polygon.closePolygon());},children:perseusStrings.closePolygon});return jsxRuntimeExports.jsx(jsxRuntimeExports.Fragment,{children:jsxRuntimeExports.jsxs(wonderBlocksCore.View,{style:{flexDirection:"row",width:props.width},children:[interactionMode==="keyboard"&&jsxRuntimeExports.jsx(Button__default.default,{kind:"secondary",style:{width:"100%",marginLeft:"20px"},disabled:closedPolygon,tabIndex:closedPolygon?-1:0,onClick:()=>{props.dispatch(actions.polygon.addPoint([0,0]));},children:perseusStrings.addPoint}),interactionMode==="mouse"&&jsxRuntimeExports.jsx(Button__default.default,{id:REMOVE_BUTTON_ID,kind:"secondary",actionType:"destructive",disabled:closedPolygon||!shouldShowRemoveButton,tabIndex:-1,style:{width:"100%",marginLeft:"20px"},onClick:_event=>{props.dispatch(actions.polygon.removePoint(props.state.focusedPointIndex));},children:perseusStrings.removePoint}),polygonButton]})})};const renderGraphControls=props=>{const{state,dispatch,width,perseusStrings}=props;const{type}=state;switch(type){case "point":if(state.numPoints==="unlimited"){return renderPointGraphControls({state,dispatch,width,perseusStrings})}return null;case "polygon":if(state.numSides==="unlimited"){return renderPolygonGraphControls({state,dispatch,width,perseusStrings})}return null;default:return null}};function handleFocusEvent(event,state,dispatch){if(isUnlimitedGraphState(state)){if(event.target.classList.contains("mafs-graph")&&state.interactionMode==="mouse"){dispatch(actions.global.changeKeyboardInvitationVisibility(true));}}}function handleBlurEvent(_event,state,dispatch){if(isUnlimitedGraphState(state)){dispatch(actions.global.changeKeyboardInvitationVisibility(false));}}function handleKeyboardEvent(event,state,dispatch){if(isUnlimitedGraphState(state)){if(event.key==="Backspace"||event.key==="Delete"){if(document.activeElement?.classList.contains("movable-point__focusable-handle")){if(state.type==="point"||state.type==="polygon"&&!state.closedPolygon){dispatch(actions.global.deleteIntent());}}document.activeElement.blur();}else if(event.shiftKey&&event.key==="Enter"){dispatch(actions.global.changeInteractionMode("keyboard"));}else if(state.interactionMode==="keyboard"&&event.key==="a"){dispatch(actions.pointGraph.addPoint([0,0]));}}}const renderGraphElements=props=>{const{state,dispatch,i18n,markings}=props;const{type}=state;switch(type){case "angle":return renderAngleGraph(state,dispatch,i18n);case "segment":return renderSegmentGraph(state,dispatch,i18n);case "linear-system":return renderLinearSystemGraph(state,dispatch,i18n);case "linear":return renderLinearGraph(state,dispatch,i18n);case "ray":return renderRayGraph(state,dispatch,i18n);case "polygon":return renderPolygonGraph(state,dispatch,i18n,markings);case "point":return renderPointGraph(state,dispatch,i18n);case "circle":return renderCircleGraph(state,dispatch,i18n);case "quadratic":return renderQuadraticGraph(state,dispatch,i18n);case "sinusoid":return renderSinusoidGraph(state,dispatch,i18n);case "exponential":return renderExponentialGraph(state,dispatch,i18n);case "none":return {graph:null,interactiveElementsDescription:null};case "absolute-value":return renderAbsoluteValueGraph(state,dispatch,i18n);case "tangent":return renderTangentGraph(state,dispatch,i18n);default:throw new wonderStuffCore.UnreachableCaseError(type)}};function describedByIds(...args){return args.filter(Boolean).join(" ")||undefined}
|
|
2036
2034
|
|
|
2037
2035
|
function mafsStateToInteractiveGraph(state,originalGraph){switch(state.type){case "angle":invariant__default.default(originalGraph.type==="angle");return {...originalGraph,coords:state.coords};case "quadratic":invariant__default.default(originalGraph.type==="quadratic");return {...originalGraph,coords:state.coords};case "circle":invariant__default.default(originalGraph.type==="circle");return {...originalGraph,center:state.center,radius:getRadius(state)};case "linear":invariant__default.default(originalGraph.type==="linear");return {...originalGraph,coords:state.coords};case "ray":invariant__default.default(originalGraph.type==="ray");return {...originalGraph,coords:state.coords};case "sinusoid":invariant__default.default(originalGraph.type==="sinusoid");return {...originalGraph,coords:state.coords};case "segment":invariant__default.default(originalGraph.type==="segment");return {...originalGraph,coords:state.coords};case "linear-system":invariant__default.default(originalGraph.type==="linear-system");return {...originalGraph,coords:state.coords};case "polygon":invariant__default.default(originalGraph.type==="polygon");return {...originalGraph,coords:state.coords};case "point":invariant__default.default(originalGraph.type==="point");return {...originalGraph,coords:state.coords};case "exponential":invariant__default.default(originalGraph.type==="exponential");return {...originalGraph,coords:state.coords,asymptote:state.asymptote};case "none":invariant__default.default(originalGraph.type==="none");return {...originalGraph};case "absolute-value":invariant__default.default(originalGraph.type==="absolute-value");return {...originalGraph,coords:state.coords};case "tangent":invariant__default.default(originalGraph.type==="tangent");return {...originalGraph,coords:state.coords};default:throw new wonderStuffCore.UnreachableCaseError(state)}}
|
|
2038
2036
|
|
|
@@ -2046,7 +2044,7 @@ const getPromptJSON$a=widgetData=>{const propMarkers=widgetData.markers.map(mark
|
|
|
2046
2044
|
|
|
2047
2045
|
const AnswerChoices=props=>{const{strings}=usePerseusI18n();const onAnswerChange=selected=>{const{choices,onChange}=props;onChange(choices.map(choice=>selected.includes(choice.content)));};const AnswerItems=choices=>choices.map(({content})=>jsxRuntimeExports.jsx(wonderBlocksDropdown.OptionItem,{value:content,label:jsxRuntimeExports.jsx(Renderer,{content:content,strings:strings,inline:true})},content));const selectedValues=props.choices.filter(choice=>choice.checked).map(choice=>choice.content);const{opener,onToggle,disabled}=props;const args={style:{zIndex:"unset"},children:AnswerItems(props.choices),opener,onToggle,disabled};return props.multipleSelect?jsxRuntimeExports.jsx(wonderBlocksDropdown.MultiSelect,{...args,selectedValues:selectedValues,onChange:selected=>onAnswerChange(selected)}):jsxRuntimeExports.jsx(wonderBlocksDropdown.SingleSelect,{...args,selectedValue:selectedValues[0],onChange:selected=>onAnswerChange([selected]),placeholder:props.choices[0].content})};
|
|
2048
2046
|
|
|
2049
|
-
const HideAnswersToggle=props=>{const switchId=React.useId();const labelId=React.useId();const{strings}=usePerseusI18n();return jsxRuntimeExports.jsxs(wonderBlocksCore.View,{style:styles$c.switchWrapper,children:[jsxRuntimeExports.jsx(Switch__default.default,{id:switchId,checked:props.areAnswersHidden,onChange:props.onChange,"aria-labelledby":labelId}),jsxRuntimeExports.jsx(wonderBlocksTypography.
|
|
2047
|
+
const HideAnswersToggle=props=>{const switchId=React.useId();const labelId=React.useId();const{strings}=usePerseusI18n();return jsxRuntimeExports.jsxs(wonderBlocksCore.View,{style:styles$c.switchWrapper,children:[jsxRuntimeExports.jsx(Switch__default.default,{id:switchId,checked:props.areAnswersHidden,onChange:props.onChange,"aria-labelledby":labelId}),jsxRuntimeExports.jsx(wonderBlocksTypography.BodyText,{id:labelId,htmlFor:switchId,tag:"label",children:strings.hideAnswersToggleLabel})]})};const styles$c=aphrodite.StyleSheet.create({switchWrapper:{display:"flex",flexDirection:"row",flexWrap:"wrap-reverse",alignItems:"center",gap:"0.5em",marginTop:"1em"}});
|
|
2050
2048
|
|
|
2051
2049
|
const BringToFront={boxShadow:`0 8px 8px ${wonderBlocksTokens.semanticColor.core.border.neutral.default}`,zIndex:1e3};const AnswerPill=props=>{const{selectedAnswers,showCorrectness,markerRef,side,onClick,style,focused,hovered}=props;const pillId=React.useId();const{strings}=usePerseusI18n();const answerString=selectedAnswers.length>1?strings.answers({num:selectedAnswers.length}):selectedAnswers[0];const correct=showCorrectness==="correct";const incorrect=showCorrectness==="incorrect";return jsxRuntimeExports.jsx(reactPopper.Popper,{placement:side,referenceElement:markerRef,modifiers:[{name:"preventOverflow",options:{rootBoundary:"viewport"}}],children:({ref,style:popperStyle})=>jsxRuntimeExports.jsx(Pill__default.default,{size:"large",kind:"accent",id:pillId,onClick:correct?undefined:onClick,ref:ref,style:[style,popperStyle,styles$b.pill,correct&&styles$b.correct,incorrect&&styles$b.incorrect,(focused||hovered)&&BringToFront],children:jsxRuntimeExports.jsx(Renderer,{content:answerString,strings:strings,inline:true})})})};const styles$b=aphrodite.StyleSheet.create({correct:{backgroundColor:"#00880b"},incorrect:{backgroundColor:wonderBlocksTokens.semanticColor.core.background.neutral.default},pill:{height:"auto"}});
|
|
2052
2050
|
|
|
@@ -2112,7 +2110,7 @@ var extraWidgets = [CSProgram$1,Categorizer$1,Definition$1,DeprecatedStandin$1,D
|
|
|
2112
2110
|
|
|
2113
2111
|
const init=function(){registerWidgets(basicWidgets);registerWidgets(extraWidgets);replaceDeprecatedWidgets();};
|
|
2114
2112
|
|
|
2115
|
-
const libName="@khanacademy/perseus";const libVersion="77.0
|
|
2113
|
+
const libName="@khanacademy/perseus";const libVersion="77.1.0";perseusUtils.addLibraryVersionToPerseusDebug(libName,libVersion);
|
|
2116
2114
|
|
|
2117
2115
|
const apiVersion={major:12,minor:0};
|
|
2118
2116
|
|