UNPKG

@instructure/quiz-grading

Version:

The Quiz React SDK by Instructure Inc.

140 lines (123 loc) 4.75 kB
/** @jsx jsx */ import {Component} from 'react' import PropTypes from 'prop-types' import partial from 'lodash/partial' import ImmutablePropTypes from 'react-immutable-proptypes' import {jsx} from '@instructure/emotion' import {View} from '@instructure/ui-view' import {IconArrowOpenEndLine} from '@instructure/ui-icons' import {ResultStimulus} from '@instructure/quiz-core/common/components/resources/sessionItemResult/ResultStimulus/index' import {generateDisplayPositions} from '@instructure/quiz-core/common/util/generateDisplayPositions' import {Flex} from '@instructure/quiz-common/components/Flex/index' import {GRADE_BY_QUESTION_NEXT} from '@instructure/quiz-common/constants' import {withStyleOverrides} from '@instructure/quiz-common/util/withStyleOverrides' import SessionItemResultWrapper from '../SessionItemResultWrapper' import generateStyle from './styles' import t from '@instructure/quiz-i18n/format-message' class BaseSessionItemResultList extends Component { static displayName = 'SessionItemResultList' static componentId = `Quizzes${this.displayName}` static propTypes = { activeItemId: PropTypes.string, gradeByQuestionEnabled: PropTypes.bool, handleChangePoints: PropTypes.func.isRequired, handleChangeFeedback: PropTypes.func.isRequired, handleChangeGradeStatus: PropTypes.func.isRequired, postToParent: PropTypes.func.isRequired, quizSessionId: PropTypes.string.isRequired, regradingIdentifier: PropTypes.string.isRequired, renderUpdateButton: PropTypes.func.isRequired, scrollToItem: PropTypes.func.isRequired, sessionItems: ImmutablePropTypes.list.isRequired, withConfirm: PropTypes.func.isRequired, styles: PropTypes.object, } static defaultProps = { activeItemId: null, gradeByQuestionEnabled: false, } componentDidMount() { this.scrollToActiveItem() } componentDidUpdate(prevProps) { if (prevProps.quizSessionId !== this.props.quizSessionId) { this.scrollToActiveItem() } } scrollToActiveItem() { const {activeItemId, gradeByQuestionEnabled, sessionItems} = this.props if (gradeByQuestionEnabled && activeItemId) { const sessionItem = sessionItems.find(si => si.itemRecord.id === activeItemId) if (sessionItem) { this.props.scrollToItem(sessionItem.id) } else { const continueText = ( <Flex alignItems="center"> <View margin="0 x-small 0 0">{t('Next Student')}</View> <IconArrowOpenEndLine /> </Flex> ) this.props.withConfirm(this.nextStudent, { continueText, text: t( 'The active student does not have this question. Please use the Next Student button to proceed.', ), title: t('Question Not Available'), }) } } } nextStudent = () => { this.props.postToParent({subject: GRADE_BY_QUESTION_NEXT}) } renderSessionItemResultWrapper = (sessionItem, shouldRenderTopBorder) => { const { handleChangePoints, handleChangeFeedback, handleChangeGradeStatus, quizSessionId, regradingIdentifier, renderUpdateButton, } = this.props const result = sessionItem.sessionItemResult const item = sessionItem.getItem() return ( <SessionItemResultWrapper handleChangeFeedback={handleChangeFeedback} handleChangeGradeStatus={partial(handleChangeGradeStatus, result.id, item.id)} handleChangePoints={partial(handleChangePoints, result.id, item.id)} item={item} key={sessionItem.id} quizSessionId={quizSessionId} isRegrading={sessionItem.id === regradingIdentifier} regradingKey={sessionItem.id} renderUpdateButton={renderUpdateButton} sessionItem={sessionItem} shouldRenderTopBorder={shouldRenderTopBorder} /> ) } renderItem(sessionItem) { if (sessionItem.stimulus) { return ( <ResultStimulus key={sessionItem.id} stimulus={sessionItem.stimulusRecord} renderItem={this.renderSessionItemResultWrapper} sessionItem={sessionItem} // This prop is necessary to rerender the child items when we enter regrading mode regradingIdentifier={this.props.regradingIdentifier} /> ) } return this.renderSessionItemResultWrapper(sessionItem, true) } renderItems() { return generateDisplayPositions(this.props.sessionItems).map(si => this.renderItem(si.record)) } render() { return <div css={this.props.styles.root}>{this.renderItems()}</div> } } export const SessionItemResultList = withStyleOverrides(generateStyle)(BaseSessionItemResultList) export default SessionItemResultList