Skip to content

Commit 3703780

Browse files
feat: add AssessmentContext component
1 parent 66f232f commit 3703780

File tree

1 file changed

+94
-0
lines changed

1 file changed

+94
-0
lines changed
Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,94 @@
1+
import { createContext, useMemo } from 'react';
2+
import PropTypes from 'prop-types';
3+
4+
import { StrictDict, useKeyedState } from '@edx/react-unit-test-utils';
5+
6+
import { useEmptyRubric } from 'data/services/lms/hooks/selectors';
7+
8+
export const AssessmentContext = createContext({
9+
selectedOptions: {},
10+
criterionFeedback: {},
11+
overallFeedback: '',
12+
});
13+
14+
export const stateKeys = StrictDict({
15+
selectedOptions: 'selectedOptions',
16+
criterionFeedback: 'criterionFeedback',
17+
overallFeedback: 'overallFeedback',
18+
});
19+
20+
export const AssessmentContextProvider = ({
21+
children,
22+
}) => {
23+
const emptyRubric = useEmptyRubric();
24+
const [selectedOptions, setSelectedOptions] = useKeyedState(
25+
stateKeys.selectedOptions,
26+
emptyRubric.selectedOptions,
27+
);
28+
const [criterionFeedback, setCriterionFeedback] = useKeyedState(
29+
stateKeys.criterionFeedback,
30+
emptyRubric.criterionFeedback,
31+
);
32+
const [overallFeedback, setOverallFeedback] = useKeyedState(
33+
stateKeys.overallFeedback,
34+
'',
35+
);
36+
37+
const genCriterionData = (name) => ({
38+
options: {
39+
value: selectedOptions[name],
40+
onChange: (e) => {
41+
setSelectedOptions({ ...selectedOptions, [name]: e.target.value });
42+
},
43+
isInvalid: selectedOptions[name] === '',
44+
},
45+
feedback: {
46+
value: criterionFeedback[name],
47+
onChange: (e) => {
48+
setCriterionFeedback({ ...criterionFeedback, [name]: e.target.value });
49+
},
50+
isInvalid: criterionFeedback[name] === '',
51+
isDisabled: false, // TODO: check config logic
52+
},
53+
});
54+
55+
const criteriaData = Object.keys(selectedOptions).reduce(
56+
({ obj, name }) => ({ ...obj, [name]: genCriterionData(name) }),
57+
{},
58+
);
59+
60+
const overallFeedbackData = useMemo(() => ({
61+
value: overallFeedback,
62+
onChange: (e) => {
63+
setOverallFeedback(e.target.value);
64+
},
65+
isInvalid: false,
66+
isDisabled: false, // TODO: check config logic
67+
}), [overallFeedback, setOverallFeedback]);
68+
69+
const currentValue = useMemo(() => ({
70+
selectedOptions,
71+
criterionFeedback,
72+
overallFeedback,
73+
}), [selectedOptions, criterionFeedback, overallFeedback]);
74+
75+
const value = useMemo(
76+
() => ({
77+
formFields: { criteria: criteriaData, overallFeedback: overallFeedbackData },
78+
currentValue,
79+
}),
80+
[
81+
criteriaData,
82+
overallFeedbackData,
83+
currentValue,
84+
],
85+
);
86+
return (
87+
<AssessmentContext.Provider value={value}>
88+
{children}
89+
</AssessmentContext.Provider>
90+
);
91+
};
92+
AssessmentContextProvider.propTypes = {
93+
children: PropTypes.node.isRequired,
94+
};

0 commit comments

Comments
 (0)