UNPKG

@100mslive/react-native-room-kit

Version:

100ms Room Kit provides simple & easy to use UI components to build Live Streaming & Video Conferencing experiences in your apps.

415 lines (414 loc) 15.6 kB
import * as React from 'react'; import { View, Text, StyleSheet, TouchableOpacity, Platform } from 'react-native'; import { HMSPollQuestionType, HMSPollType } from '@100mslive/react-native-hms'; import { useSelector } from 'react-redux'; import { useHMSRoomStyleSheet } from '../hooks-util'; import { BottomSheet } from './BottomSheet'; import { AddIcon, CheckBoxIcon, ChevronIcon, TrashBinIcon } from '../Icons'; import { HMSTextInput } from './HMSTextInput'; import { HMSBaseButton } from './HMSBaseButton'; import { PressableIcon } from './PressableIcon'; import { RadioInput } from './RadioInput'; const questionTypes = [{ label: getLabelFromPollQuestionType(HMSPollQuestionType.singleChoice), value: HMSPollQuestionType.singleChoice, id: 'single-choice' }, { label: getLabelFromPollQuestionType(HMSPollQuestionType.multipleChoice), value: HMSPollQuestionType.multipleChoice, id: 'multiple-choice' } // { // label: getLabelFromPollQuestionType(HMSPollQuestionType.shortAnswer), // value: HMSPollQuestionType.shortAnswer, // id: 'short-answer', // }, // { // label: getLabelFromPollQuestionType(HMSPollQuestionType.longAnswer), // value: HMSPollQuestionType.longAnswer, // id: 'long-answer', // }, ]; export const PollQuestion = ({ totalQuestions, currentQuestionIndex, pollQuestion, onAddPollQuestionOption, onDeletePollQuestionOption, onEditPollQuestionOption, onSetPollQuestionCorrectOption, onQuestionFieldChange, onDelete }) => { const [questionTypesVisible, setQuestionTypesVisible] = React.useState(false); const launchingPoll = useSelector(state => state.polls.launchingPoll); const pollType = useSelector(state => state.polls.pollConfig.type); const hmsRoomStyles = useHMSRoomStyleSheet((theme, typography) => ({ container: { backgroundColor: theme.palette.surface_default }, regularMediumText: { color: theme.palette.on_surface_medium, fontFamily: `${typography.font_family}-Regular` }, regularHighText: { color: theme.palette.on_surface_high, fontFamily: `${typography.font_family}-Regular` }, semiBoldLowText: { color: theme.palette.on_surface_low, fontFamily: `${typography.font_family}-SemiBold` }, questionType: { backgroundColor: theme.palette.surface_bright }, floatingQuestionContainer: { borderColor: theme.palette.border_default, backgroundColor: theme.palette.surface_bright }, saveButton: { backgroundColor: theme.palette.secondary_default }, saveButtonDisabled: { backgroundColor: theme.palette.secondary_dim }, saveText: { color: theme.palette.on_secondary_high, fontFamily: `${typography.font_family}-SemiBold` }, saveTextDisabled: { color: theme.palette.on_secondary_low, fontFamily: `${typography.font_family}-SemiBold` }, divider: { backgroundColor: theme.palette.border_bright }, dividerV2: { backgroundColor: theme.palette.border_default }, optionText: { backgroundColor: theme.palette.surface_bright, borderColor: theme.palette.surface_bright }, optionDeleteIcon: { tintColor: theme.palette.on_surface_low } })); const saveButtonDisabled = // Disable save button if: !pollQuestion.title || // title is not vaild, OR !pollQuestion.pointWeightage || // pointWeightage is not valid, OR (pollQuestion.type === HMSPollQuestionType.singleChoice || pollQuestion.type === HMSPollQuestionType.multipleChoice) && // If question type is singleChoice or multipleChoice, AND pollQuestion.options && ( // options are defined pollQuestion.options.length <= 1 || // options are less than or equal to 1, OR pollQuestion.options.some(option => !option[1]) || // some options are not valid, OR pollType === HMSPollType.quiz && pollQuestion.options.every(option => !option[0])); // If poll type is quiz, all options are marked as not correct if (pollQuestion.saved) { return /*#__PURE__*/React.createElement(View, { style: [styles.container, hmsRoomStyles.container] }, /*#__PURE__*/React.createElement(Text, { style: [styles.tinyText, styles.questionLabel, hmsRoomStyles.semiBoldLowText] }, "Question ", currentQuestionIndex + 1, " of ", totalQuestions, ":", ' ', getLabelFromPollQuestionType(pollQuestion.type).toUpperCase()), pollQuestion.type === HMSPollQuestionType.singleChoice || pollQuestion.type === HMSPollQuestionType.multipleChoice ? /*#__PURE__*/React.createElement(TouchableOpacity, { activeOpacity: 0.8, onPress: () => setQuestionTypesVisible(prev => !prev), style: { flexDirection: 'row', alignItems: 'center', justifyContent: 'space-between' } }, /*#__PURE__*/React.createElement(Text, { style: [styles.normalText, hmsRoomStyles.regularHighText] }, pollQuestion.title), /*#__PURE__*/React.createElement(ChevronIcon, { direction: questionTypesVisible ? 'top' : 'down' })) : /*#__PURE__*/React.createElement(Text, { style: [styles.normalText, hmsRoomStyles.regularHighText] }, pollQuestion.title), pollType === HMSPollType.quiz ? /*#__PURE__*/React.createElement(Text, { style: [styles.smallerText, hmsRoomStyles.regularMediumText, { marginTop: 4 }] }, pollQuestion.pointWeightage, ' ', parseInt(pollQuestion.pointWeightage) <= 1 ? 'point' : 'points') : null, questionTypesVisible && pollQuestion.options ? /*#__PURE__*/React.createElement(View, { style: { marginTop: 16 } }, pollQuestion.options.map((option, idx) => /*#__PURE__*/React.createElement(Text, { key: idx, style: [styles.smallText, { marginBottom: 8 }, hmsRoomStyles.regularMediumText] }, option[1]))) : null, /*#__PURE__*/React.createElement(View, { style: [styles.saveContainer, { marginTop: 16 }] }, /*#__PURE__*/React.createElement(PressableIcon, { disabled: launchingPoll, style: [styles.deleteIcon, launchingPoll ? { opacity: 0.4 } : null], onPress: () => onDelete(currentQuestionIndex) }, /*#__PURE__*/React.createElement(TrashBinIcon, null)), /*#__PURE__*/React.createElement(HMSBaseButton, { loading: false, disabled: saveButtonDisabled || launchingPoll, onPress: () => { setQuestionTypesVisible(false); onQuestionFieldChange(currentQuestionIndex, 'saved', !pollQuestion.saved); }, title: pollQuestion.saved ? 'Edit' : 'Save', underlayColor: hmsRoomStyles.saveButtonDisabled.backgroundColor, style: saveButtonDisabled || launchingPoll ? hmsRoomStyles.saveButtonDisabled : hmsRoomStyles.saveButton, textStyle: [styles.normalText, saveButtonDisabled || launchingPoll ? hmsRoomStyles.saveTextDisabled : hmsRoomStyles.saveText] }))); } const InputComponent = pollType === HMSPollType.quiz ? pollQuestion.type === HMSPollQuestionType.singleChoice ? RadioInput : pollQuestion.type === HMSPollQuestionType.multipleChoice ? CheckBoxIcon : null : null; return /*#__PURE__*/React.createElement(View, { style: [styles.container, hmsRoomStyles.container] }, /*#__PURE__*/React.createElement(Text, { style: [styles.tinyText, styles.questionLabel, hmsRoomStyles.semiBoldLowText] }, "Question ", currentQuestionIndex + 1, " of ", totalQuestions), /*#__PURE__*/React.createElement(Text, { style: [styles.smallText, styles.bottomSpace, hmsRoomStyles.regularHighText] }, "Question Type"), /*#__PURE__*/React.createElement(View, { style: styles.questionTypeWrapper }, /*#__PURE__*/React.createElement(TouchableOpacity, { activeOpacity: 0.8, onPress: () => setQuestionTypesVisible(prev => !prev), style: [styles.questionType, hmsRoomStyles.questionType] }, /*#__PURE__*/React.createElement(Text, { style: [styles.normalText, hmsRoomStyles.regularHighText] }, getLabelFromPollQuestionType(pollQuestion.type)), /*#__PURE__*/React.createElement(ChevronIcon, { direction: questionTypesVisible ? 'top' : 'down' })), questionTypesVisible ? /*#__PURE__*/React.createElement(View, { collapsable: false, style: [styles.questionTypeOptions, { height: 48 * questionTypes.length + 16 }, hmsRoomStyles.floatingQuestionContainer] }, questionTypes.map((item, idx) => { const isFirst = idx === 0; return /*#__PURE__*/React.createElement(React.Fragment, { key: item.id }, isFirst ? null : /*#__PURE__*/React.createElement(View, { style: [styles.questionTypeDivider, hmsRoomStyles.dividerV2] }), /*#__PURE__*/React.createElement(TouchableOpacity, { key: item.id, onPress: () => { setQuestionTypesVisible(prev => !prev); onQuestionFieldChange(currentQuestionIndex, 'type', item.value); }, style: [styles.questionTypeOption, hmsRoomStyles.questionType] }, /*#__PURE__*/React.createElement(Text, { style: [styles.normalText, hmsRoomStyles.regularHighText] }, item.label))); })) : null), /*#__PURE__*/React.createElement(Text, { style: [styles.smallText, styles.bottomSpace, hmsRoomStyles.regularHighText] }, "Question"), /*#__PURE__*/React.createElement(HMSTextInput, { placeholder: "e.g. Who will win the match?", style: hmsRoomStyles.optionText, value: pollQuestion.title, autoFocus: false, autoCapitalize: "none", autoComplete: "off", onChangeText: value => onQuestionFieldChange(currentQuestionIndex, 'title', value) }), pollQuestion.options ? /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(BottomSheet.Divider, { style: hmsRoomStyles.divider }), /*#__PURE__*/React.createElement(Text, { style: [styles.smallText, styles.bottomSpace, hmsRoomStyles.regularHighText] }, "Options"), /*#__PURE__*/React.createElement(View, { style: styles.optionsWrapper }, pollQuestion.options.map((option, idx) => { const isFirst = idx === 0; return /*#__PURE__*/React.createElement(View, { key: idx, style: [styles.optionContainer, isFirst ? null : styles.topSpace] }, !InputComponent ? null : /*#__PURE__*/React.createElement(View, { style: { marginRight: 8 } }, /*#__PURE__*/React.createElement(InputComponent, { selected: option[0], type: option[0] ? 'checked' : 'unchecked', onChange: data => { onSetPollQuestionCorrectOption(currentQuestionIndex, idx, data === 'checked' ? true : data === 'unchecked' ? false : data); } })), /*#__PURE__*/React.createElement(HMSTextInput, { placeholder: `Option ${idx + 1}`, style: hmsRoomStyles.optionText, value: option[1], autoCapitalize: "none", autoComplete: "off", autoFocus: false, onChangeText: value => onEditPollQuestionOption(currentQuestionIndex, idx, value) }), /*#__PURE__*/React.createElement(PressableIcon, { style: styles.optionDelete, border: false, onPress: () => onDeletePollQuestionOption(currentQuestionIndex, idx) }, /*#__PURE__*/React.createElement(TrashBinIcon, { style: hmsRoomStyles.optionDeleteIcon }))); })), /*#__PURE__*/React.createElement(View, { style: styles.addOptionWrapper }, /*#__PURE__*/React.createElement(TouchableOpacity, { style: styles.addOptionContainer, onPress: () => onAddPollQuestionOption(currentQuestionIndex) }, /*#__PURE__*/React.createElement(View, { style: styles.addOptionIconWrapper }, /*#__PURE__*/React.createElement(AddIcon, { type: "circle" })), /*#__PURE__*/React.createElement(Text, { style: [styles.smallText, hmsRoomStyles.regularMediumText] }, "Add an option")))) : null, /*#__PURE__*/React.createElement(BottomSheet.Divider, { style: hmsRoomStyles.divider }), pollType === HMSPollType.quiz ? /*#__PURE__*/React.createElement(View, { style: { marginBottom: 16, flexDirection: 'row', alignItems: 'center', justifyContent: 'space-between' } }, /*#__PURE__*/React.createElement(Text, { style: [styles.smallText, hmsRoomStyles.regularMediumText] }, "Point Weightage"), /*#__PURE__*/React.createElement(HMSTextInput, { placeholder: "", style: [hmsRoomStyles.optionText, { maxWidth: 88, marginLeft: 12 }], value: pollQuestion.pointWeightage, autoFocus: false, autoCapitalize: "none", autoComplete: "off", keyboardType: Platform.OS === 'android' ? 'numeric' : 'number-pad', onChangeText: value => onQuestionFieldChange(currentQuestionIndex, 'pointWeightage', value) })) : null, /*#__PURE__*/React.createElement(View, { style: styles.saveContainer }, /*#__PURE__*/React.createElement(PressableIcon, { style: styles.deleteIcon, onPress: () => onDelete(currentQuestionIndex) }, /*#__PURE__*/React.createElement(TrashBinIcon, null)), /*#__PURE__*/React.createElement(HMSBaseButton, { loading: false, disabled: saveButtonDisabled, onPress: () => { setQuestionTypesVisible(false); onQuestionFieldChange(currentQuestionIndex, 'saved', !pollQuestion.saved); }, title: pollQuestion.saved ? 'Edit' : 'Save', underlayColor: hmsRoomStyles.saveButtonDisabled.backgroundColor, style: saveButtonDisabled ? hmsRoomStyles.saveButtonDisabled : hmsRoomStyles.saveButton, textStyle: [styles.normalText, saveButtonDisabled ? hmsRoomStyles.saveTextDisabled : hmsRoomStyles.saveText] }))); }; const styles = StyleSheet.create({ container: { padding: 16, borderRadius: 8 }, tinyText: { fontSize: 10, lineHeight: 16, letterSpacing: 1.5 }, smallerText: { fontSize: 12, lineHeight: 16 }, smallText: { fontSize: 14, lineHeight: 20 }, normalText: { fontSize: 16, lineHeight: 24, letterSpacing: 0.5 }, questionLabel: { textTransform: 'uppercase', marginBottom: 16 }, questionTypeWrapper: { position: 'relative', marginBottom: 16, zIndex: 40 }, questionType: { paddingVertical: 12, paddingHorizontal: 16, flexDirection: 'row', alignItems: 'center', justifyContent: 'space-between', borderRadius: 8 }, questionTypeOptions: { width: '100%', paddingVertical: 8, overflow: 'hidden', position: 'absolute', zIndex: 20, top: 48 + 4, borderWidth: 1, borderRadius: 8 }, questionTypeDivider: { height: 1, width: '90%', alignSelf: 'center' }, questionTypeOption: { paddingVertical: 12, paddingHorizontal: 16 }, optionsWrapper: { marginBottom: 16 }, optionContainer: { flexDirection: 'row', alignItems: 'center' }, optionDelete: { alignSelf: 'center', marginLeft: 8 }, topSpace: { marginTop: 8 }, bottomSpace: { marginBottom: 8 }, addOptionWrapper: { alignSelf: 'flex-start' }, addOptionContainer: { flexDirection: 'row', alignItems: 'center' }, addOptionIconWrapper: { marginRight: 8, padding: 8 }, config: { marginBottom: 16 }, saveContainer: { flexDirection: 'row', justifyContent: 'space-between', alignItems: 'center' }, deleteIcon: { marginRight: 16 } }); function getLabelFromPollQuestionType(type) { switch (type) { case HMSPollQuestionType.singleChoice: return 'Single Choice'; case HMSPollQuestionType.multipleChoice: return 'Multiple Choice'; case HMSPollQuestionType.longAnswer: return 'Long Answer'; case HMSPollQuestionType.shortAnswer: return 'Short Answer'; } } //# sourceMappingURL=PollQuestion.js.map