UNPKG

@instructure/quiz-interactions

Version:

A React UI component Library for quiz interaction types.

221 lines (204 loc) 7.46 kB
import React, {Component} from 'react' import PropTypes from 'prop-types' import {ScreenReaderContent} from '@instructure/ui-a11y-content' import {Checkbox} from '@instructure/ui-checkbox' import {TextInput} from '@instructure/quiz-common/components/TextInput/index' import {FormFieldGroup} from '@instructure/quiz-common/components/FormFieldGroup/index' import NumberInput from '@instructure/quiz-number-input/components/NumberInput/index' import FileUploadInteractionType from '../../../records/interactions/file_upload' import QuestionContainer from '../../common/edit/components/QuestionContainer' import QuestionSettingsContainer from '../../common/edit/components/QuestionSettingsContainer' import withEditTools from '../../../util/withEditTools' import t from '@instructure/quiz-i18n/format-message' import QuestionSettingsPanel from '../../common/edit/components/QuestionSettingsPanel' import CalculatorOptionWithOqaatAlert from '../../common/edit/components/CalculatorOptionWithOqaatAlert' /** --- category: FileUpload --- File Upload Edit component ```jsx_example function Example (props) { const exampleProps = { itemBody: 'Give two examples of tortoises', interactionData: { restrictCount: true, filesCount: '2' }, overrideEditableForRegrading: false, properties: { restrictTypes: true, allowedTypes: 'media/*' } } return ( <FileUploadEdit {...exampleProps} {...props} /> ) } <SettingsSwitcher locales={LOCALES}> <EditStateProvider> <Example /> </EditStateProvider> </SettingsSwitcher> ``` **/ @withEditTools export default class FileUploadEdit extends Component { static interactionType = FileUploadInteractionType static propTypes = { additionalOptions: PropTypes.array, calculatorType: PropTypes.string, changeItemState: PropTypes.func, enableRichContentEditor: PropTypes.bool, interactionData: PropTypes.shape({ restrictCount: PropTypes.bool.isRequired, filesCount: PropTypes.string.isRequired, }).isRequired, itemBody: PropTypes.string.isRequired, onModalClose: PropTypes.func, onModalOpen: PropTypes.func, oneQuestionAtATime: PropTypes.bool, openImportModal: PropTypes.func, overrideEditableForRegrading: PropTypes.bool, properties: PropTypes.shape({ restrictTypes: PropTypes.bool.isRequired, allowedTypes: PropTypes.string, }).isRequired, setOneQuestionAtATime: PropTypes.func, ...withEditTools.injectedProps, showCalculatorOption: PropTypes.bool, } static defaultProps = { additionalOptions: [], calculatorType: 'none', enableRichContentEditor: true, oneQuestionAtATime: false, overrideEditableForRegrading: false, setOneQuestionAtATime: Function.prototype, changeItemState: void 0, onModalClose: void 0, onModalOpen: void 0, openImportModal: void 0, showCalculatorOption: true, } handleCalculatorTypeChange = (e, value) => { this.props.changeItemState({ calculatorType: value, }) } handleRestrictCountChange = () => this.props.changeItemState({ interactionData: { ...this.props.interactionData, restrictCount: !this.props.interactionData.restrictCount, }, }) handleFilesCountChange = (event, countString, normalizedCountString) => this.props.changeItemState({ interactionData: { ...this.props.interactionData, filesCount: normalizedCountString, }, }) handleRestrictTypesChange = event => this.props.changeItemState({ properties: { ...this.props.properties, restrictTypes: event.target.checked, }, }) handleAllowedTypesChange = event => this.props.changeItemState({ properties: { ...this.props.properties, allowedTypes: event.target.value, }, }) renderOptions() { const {restrictTypes, allowedTypes} = this.props.properties const {restrictCount, filesCount} = this.props.interactionData const allowedTypesDescription = t('File extensions') const filesCountDescription = t('Max number of files') const description = <ScreenReaderContent>{t('File upload options')}</ScreenReaderContent> const fieldGroup = ( <FormFieldGroup rowSpacing="small" description={description}> {this.props.showCalculatorOption && ( <CalculatorOptionWithOqaatAlert disabled={this.props.overrideEditableForRegrading} calculatorValue={this.props.calculatorType} onCalculatorTypeChange={this.handleCalculatorTypeChange} oqaatChecked={this.props.oneQuestionAtATime} onOqaatChange={this.props.setOneQuestionAtATime} /> )} <Checkbox disabled={this.props.overrideEditableForRegrading} checked={restrictCount} label={t('Limit File number')} onChange={this.handleRestrictCountChange} value="restrictCount" data-automation="sdk-limit-file-number-checkbox" /> {restrictCount && ( <NumberInput disabled={this.props.overrideEditableForRegrading} renderLabel={<ScreenReaderContent>{filesCountDescription}</ScreenReaderContent>} messages={this.props.getErrors('interactionData.filesCount')} min={1} onChange={this.handleFilesCountChange} placeholder={filesCountDescription} value={filesCount} data-automation="sdk-limit-file-number-input" /> )} <Checkbox checked={restrictTypes} disabled={this.props.overrideEditableForRegrading} label={t('Restrict File Types')} onChange={this.handleRestrictTypesChange} value="restrictTypes" data-automation="sdk-restrict-file-type-checkbox" /> {restrictTypes && ( <TextInput interaction={this.props.overrideEditableForRegrading ? 'disabled' : 'enabled'} renderLabel={<ScreenReaderContent>{allowedTypesDescription}</ScreenReaderContent>} messages={[ ...this.props.getErrors('properties.allowedTypes'), {text: t('Enter file extensions separated by a comma'), type: 'hint'}, ]} onChange={this.handleAllowedTypesChange} placeholder={allowedTypesDescription} type="text" value={allowedTypes} data-automation="sdk-file-extensions-input" /> )} </FormFieldGroup> ) return ( <QuestionSettingsContainer additionalOptions={this.props.additionalOptions}> <QuestionSettingsPanel label={t('Options')} defaultExpanded> {fieldGroup} </QuestionSettingsPanel> </QuestionSettingsContainer> ) } render() { return ( <div> <QuestionContainer disabled={this.props.overrideEditableForRegrading} enableRichContentEditor={this.props.enableRichContentEditor} itemBody={this.props.itemBody} onDescriptionChange={this.props.onDescriptionChange} onModalClose={this.props.onModalClose} onModalOpen={this.props.onModalOpen} openImportModal={this.props.openImportModal} stemErrors={this.props.getErrors('itemBody')} /> {this.renderOptions()} </div> ) } }