@magmamath/students-features 0.9.107-rc.2 → 0.9.107-rc.21
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/commonjs/features/chatbot/components/Chat/Chat.js +29 -18
- package/dist/commonjs/features/chatbot/components/Chat/Chat.js.map +1 -1
- package/dist/commonjs/features/chatbot/components/ChatControls/ChatControls.js +7 -2
- package/dist/commonjs/features/chatbot/components/ChatControls/ChatControls.js.map +1 -1
- package/dist/commonjs/features/chatbot/components/Chatbot.js +14 -3
- package/dist/commonjs/features/chatbot/components/Chatbot.js.map +1 -1
- package/dist/commonjs/features/chatbot/model/ChatBotModel.js +11 -2
- package/dist/commonjs/features/chatbot/model/ChatBotModel.js.map +1 -1
- package/dist/commonjs/features/chatbot/model/ChatsCacheModel.js.map +1 -1
- package/dist/commonjs/features/chatbot/types/model.types.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/components/VoiceRecord.js +25 -17
- package/dist/commonjs/features/voiceRecord/components/VoiceRecord.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/components/VoiceRecordButton.js +22 -8
- package/dist/commonjs/features/voiceRecord/components/VoiceRecordButton.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/components/{VoiceRecordDelete.js → VoiceRecordDeleteButton.js} +9 -6
- package/dist/commonjs/features/voiceRecord/components/VoiceRecordDeleteButton.js.map +1 -0
- package/dist/commonjs/features/voiceRecord/components/VoiceRecordTimer.js +7 -2
- package/dist/commonjs/features/voiceRecord/components/VoiceRecordTimer.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/constants.js +8 -1
- package/dist/commonjs/features/voiceRecord/constants.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/helpers.js +89 -3
- package/dist/commonjs/features/voiceRecord/helpers.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/hooks/useVoiceRecorder.js +45 -33
- package/dist/commonjs/features/voiceRecord/hooks/useVoiceRecorder.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/hooks/useVoiceRecorderAnimation.js +3 -3
- package/dist/commonjs/features/voiceRecord/hooks/useVoiceRecorderAnimation.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/index.js +44 -0
- package/dist/commonjs/features/voiceRecord/index.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/modal/VoiceRecordDeleteModal.js +93 -0
- package/dist/commonjs/features/voiceRecord/modal/VoiceRecordDeleteModal.js.map +1 -0
- package/dist/commonjs/features/voiceRecord/modal/VoiceRecordUndoModal.js +75 -0
- package/dist/commonjs/features/voiceRecord/modal/VoiceRecordUndoModal.js.map +1 -0
- package/dist/commonjs/features/voiceRecord/model/Recorder.model.js +54 -0
- package/dist/commonjs/features/voiceRecord/model/Recorder.model.js.map +1 -0
- package/dist/commonjs/features/voiceRecord/model/VoiceRecord.model.js +162 -21
- package/dist/commonjs/features/voiceRecord/model/VoiceRecord.model.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/model/VoiceRecordApi.js +21 -1
- package/dist/commonjs/features/voiceRecord/model/VoiceRecordApi.js.map +1 -1
- package/dist/commonjs/features/voiceRecord/model/VoiceRecordCollection.js +30 -0
- package/dist/commonjs/features/voiceRecord/model/VoiceRecordCollection.js.map +1 -0
- package/dist/commonjs/features/voiceRecord/types.js +6 -0
- package/dist/commonjs/features/voiceRecord/types.js.map +1 -0
- package/dist/commonjs/lib/components/ConditionalWrapper.js +23 -0
- package/dist/commonjs/lib/components/ConditionalWrapper.js.map +1 -0
- package/dist/commonjs/shared/translation/localization/ca.json +13 -0
- package/dist/commonjs/shared/translation/localization/de.json +13 -0
- package/dist/commonjs/shared/translation/localization/en.json +13 -0
- package/dist/commonjs/shared/translation/localization/gb.json +13 -0
- package/dist/commonjs/shared/translation/localization/sct.json +13 -0
- package/dist/commonjs/shared/translation/localization/sw.json +13 -0
- package/dist/module/features/chatbot/components/Chat/Chat.js +29 -18
- package/dist/module/features/chatbot/components/Chat/Chat.js.map +1 -1
- package/dist/module/features/chatbot/components/ChatControls/ChatControls.js +5 -2
- package/dist/module/features/chatbot/components/ChatControls/ChatControls.js.map +1 -1
- package/dist/module/features/chatbot/components/Chatbot.js +14 -3
- package/dist/module/features/chatbot/components/Chatbot.js.map +1 -1
- package/dist/module/features/chatbot/model/ChatBotModel.js +11 -2
- package/dist/module/features/chatbot/model/ChatBotModel.js.map +1 -1
- package/dist/module/features/chatbot/model/ChatsCacheModel.js.map +1 -1
- package/dist/module/features/chatbot/types/model.types.js.map +1 -1
- package/dist/module/features/voiceRecord/components/VoiceRecord.js +24 -16
- package/dist/module/features/voiceRecord/components/VoiceRecord.js.map +1 -1
- package/dist/module/features/voiceRecord/components/VoiceRecordButton.js +22 -8
- package/dist/module/features/voiceRecord/components/VoiceRecordButton.js.map +1 -1
- package/dist/module/features/voiceRecord/components/{VoiceRecordDelete.js → VoiceRecordDeleteButton.js} +8 -5
- package/dist/module/features/voiceRecord/components/VoiceRecordDeleteButton.js.map +1 -0
- package/dist/module/features/voiceRecord/components/VoiceRecordTimer.js +7 -2
- package/dist/module/features/voiceRecord/components/VoiceRecordTimer.js.map +1 -1
- package/dist/module/features/voiceRecord/constants.js +7 -0
- package/dist/module/features/voiceRecord/constants.js.map +1 -1
- package/dist/module/features/voiceRecord/helpers.js +84 -2
- package/dist/module/features/voiceRecord/helpers.js.map +1 -1
- package/dist/module/features/voiceRecord/hooks/useVoiceRecorder.js +47 -35
- package/dist/module/features/voiceRecord/hooks/useVoiceRecorder.js.map +1 -1
- package/dist/module/features/voiceRecord/hooks/useVoiceRecorderAnimation.js +3 -3
- package/dist/module/features/voiceRecord/hooks/useVoiceRecorderAnimation.js.map +1 -1
- package/dist/module/features/voiceRecord/index.js +4 -0
- package/dist/module/features/voiceRecord/index.js.map +1 -1
- package/dist/module/features/voiceRecord/modal/VoiceRecordDeleteModal.js +86 -0
- package/dist/module/features/voiceRecord/modal/VoiceRecordDeleteModal.js.map +1 -0
- package/dist/module/features/voiceRecord/modal/VoiceRecordUndoModal.js +69 -0
- package/dist/module/features/voiceRecord/modal/VoiceRecordUndoModal.js.map +1 -0
- package/dist/module/features/voiceRecord/model/Recorder.model.js +49 -0
- package/dist/module/features/voiceRecord/model/Recorder.model.js.map +1 -0
- package/dist/module/features/voiceRecord/model/VoiceRecord.model.js +163 -22
- package/dist/module/features/voiceRecord/model/VoiceRecord.model.js.map +1 -1
- package/dist/module/features/voiceRecord/model/VoiceRecordApi.js +21 -1
- package/dist/module/features/voiceRecord/model/VoiceRecordApi.js.map +1 -1
- package/dist/module/features/voiceRecord/model/VoiceRecordCollection.js +25 -0
- package/dist/module/features/voiceRecord/model/VoiceRecordCollection.js.map +1 -0
- package/dist/module/features/voiceRecord/types.js +4 -0
- package/dist/module/features/voiceRecord/types.js.map +1 -0
- package/dist/module/lib/components/ConditionalWrapper.js +17 -0
- package/dist/module/lib/components/ConditionalWrapper.js.map +1 -0
- package/dist/module/shared/translation/localization/ca.json +13 -0
- package/dist/module/shared/translation/localization/de.json +13 -0
- package/dist/module/shared/translation/localization/en.json +13 -0
- package/dist/module/shared/translation/localization/gb.json +13 -0
- package/dist/module/shared/translation/localization/sct.json +13 -0
- package/dist/module/shared/translation/localization/sw.json +13 -0
- package/dist/typescript/commonjs/features/chatbot/components/Chat/Chat.d.ts +4 -2
- package/dist/typescript/commonjs/features/chatbot/components/Chat/Chat.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/chatbot/components/ChatControls/ChatControls.d.ts +2 -1
- package/dist/typescript/commonjs/features/chatbot/components/ChatControls/ChatControls.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/chatbot/components/Chatbot.d.ts +2 -1
- package/dist/typescript/commonjs/features/chatbot/components/Chatbot.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/chatbot/model/ChatBotModel.d.ts +1 -0
- package/dist/typescript/commonjs/features/chatbot/model/ChatBotModel.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/chatbot/model/ChatsCacheModel.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/chatbot/types/api.types.d.ts +1 -0
- package/dist/typescript/commonjs/features/chatbot/types/api.types.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/chatbot/types/model.types.d.ts +1 -0
- package/dist/typescript/commonjs/features/chatbot/types/model.types.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/components/VoiceRecord.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/components/VoiceRecordButton.d.ts +1 -5
- package/dist/typescript/commonjs/features/voiceRecord/components/VoiceRecordButton.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/components/VoiceRecordDeleteButton.d.ts +8 -0
- package/dist/typescript/commonjs/features/voiceRecord/components/VoiceRecordDeleteButton.d.ts.map +1 -0
- package/dist/typescript/commonjs/features/voiceRecord/components/VoiceRecordTimer.d.ts +4 -2
- package/dist/typescript/commonjs/features/voiceRecord/components/VoiceRecordTimer.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/constants.d.ts +6 -0
- package/dist/typescript/commonjs/features/voiceRecord/constants.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/helpers.d.ts +26 -2
- package/dist/typescript/commonjs/features/voiceRecord/helpers.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/hooks/useVoiceRecorder.d.ts +0 -4
- package/dist/typescript/commonjs/features/voiceRecord/hooks/useVoiceRecorder.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/hooks/useVoiceRecorderAnimation.d.ts +1 -2
- package/dist/typescript/commonjs/features/voiceRecord/hooks/useVoiceRecorderAnimation.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/index.d.ts +4 -0
- package/dist/typescript/commonjs/features/voiceRecord/index.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/modal/VoiceRecordDeleteModal.d.ts +13 -0
- package/dist/typescript/commonjs/features/voiceRecord/modal/VoiceRecordDeleteModal.d.ts.map +1 -0
- package/dist/typescript/commonjs/features/voiceRecord/modal/VoiceRecordUndoModal.d.ts +13 -0
- package/dist/typescript/commonjs/features/voiceRecord/modal/VoiceRecordUndoModal.d.ts.map +1 -0
- package/dist/typescript/commonjs/features/voiceRecord/model/Recorder.model.d.ts +20 -0
- package/dist/typescript/commonjs/features/voiceRecord/model/Recorder.model.d.ts.map +1 -0
- package/dist/typescript/commonjs/features/voiceRecord/model/VoiceRecord.model.d.ts +38 -20
- package/dist/typescript/commonjs/features/voiceRecord/model/VoiceRecord.model.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/model/VoiceRecordApi.d.ts +2 -0
- package/dist/typescript/commonjs/features/voiceRecord/model/VoiceRecordApi.d.ts.map +1 -1
- package/dist/typescript/commonjs/features/voiceRecord/model/VoiceRecordCollection.d.ts +10 -0
- package/dist/typescript/commonjs/features/voiceRecord/model/VoiceRecordCollection.d.ts.map +1 -0
- package/dist/typescript/commonjs/features/voiceRecord/types.d.ts +43 -0
- package/dist/typescript/commonjs/features/voiceRecord/types.d.ts.map +1 -0
- package/dist/typescript/commonjs/lib/components/ConditionalWrapper.d.ts +9 -0
- package/dist/typescript/commonjs/lib/components/ConditionalWrapper.d.ts.map +1 -0
- package/dist/typescript/commonjs/shared/translation/constants.d.ts +78 -0
- package/dist/typescript/commonjs/shared/translation/constants.d.ts.map +1 -1
- package/dist/typescript/commonjs/shared/translation/model.d.ts +26 -0
- package/dist/typescript/commonjs/shared/translation/model.d.ts.map +1 -1
- package/dist/typescript/commonjs/types/common.types.d.ts +3 -0
- package/dist/typescript/commonjs/types/common.types.d.ts.map +1 -1
- package/dist/typescript/module/features/chatbot/components/Chat/Chat.d.ts +4 -2
- package/dist/typescript/module/features/chatbot/components/Chat/Chat.d.ts.map +1 -1
- package/dist/typescript/module/features/chatbot/components/ChatControls/ChatControls.d.ts +2 -1
- package/dist/typescript/module/features/chatbot/components/ChatControls/ChatControls.d.ts.map +1 -1
- package/dist/typescript/module/features/chatbot/components/Chatbot.d.ts +2 -1
- package/dist/typescript/module/features/chatbot/components/Chatbot.d.ts.map +1 -1
- package/dist/typescript/module/features/chatbot/model/ChatBotModel.d.ts +1 -0
- package/dist/typescript/module/features/chatbot/model/ChatBotModel.d.ts.map +1 -1
- package/dist/typescript/module/features/chatbot/model/ChatsCacheModel.d.ts.map +1 -1
- package/dist/typescript/module/features/chatbot/types/api.types.d.ts +1 -0
- package/dist/typescript/module/features/chatbot/types/api.types.d.ts.map +1 -1
- package/dist/typescript/module/features/chatbot/types/model.types.d.ts +1 -0
- package/dist/typescript/module/features/chatbot/types/model.types.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/components/VoiceRecord.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/components/VoiceRecordButton.d.ts +1 -5
- package/dist/typescript/module/features/voiceRecord/components/VoiceRecordButton.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/components/VoiceRecordDeleteButton.d.ts +8 -0
- package/dist/typescript/module/features/voiceRecord/components/VoiceRecordDeleteButton.d.ts.map +1 -0
- package/dist/typescript/module/features/voiceRecord/components/VoiceRecordTimer.d.ts +4 -2
- package/dist/typescript/module/features/voiceRecord/components/VoiceRecordTimer.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/constants.d.ts +6 -0
- package/dist/typescript/module/features/voiceRecord/constants.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/helpers.d.ts +26 -2
- package/dist/typescript/module/features/voiceRecord/helpers.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/hooks/useVoiceRecorder.d.ts +0 -4
- package/dist/typescript/module/features/voiceRecord/hooks/useVoiceRecorder.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/hooks/useVoiceRecorderAnimation.d.ts +1 -2
- package/dist/typescript/module/features/voiceRecord/hooks/useVoiceRecorderAnimation.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/index.d.ts +4 -0
- package/dist/typescript/module/features/voiceRecord/index.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/modal/VoiceRecordDeleteModal.d.ts +13 -0
- package/dist/typescript/module/features/voiceRecord/modal/VoiceRecordDeleteModal.d.ts.map +1 -0
- package/dist/typescript/module/features/voiceRecord/modal/VoiceRecordUndoModal.d.ts +13 -0
- package/dist/typescript/module/features/voiceRecord/modal/VoiceRecordUndoModal.d.ts.map +1 -0
- package/dist/typescript/module/features/voiceRecord/model/Recorder.model.d.ts +20 -0
- package/dist/typescript/module/features/voiceRecord/model/Recorder.model.d.ts.map +1 -0
- package/dist/typescript/module/features/voiceRecord/model/VoiceRecord.model.d.ts +38 -20
- package/dist/typescript/module/features/voiceRecord/model/VoiceRecord.model.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/model/VoiceRecordApi.d.ts +2 -0
- package/dist/typescript/module/features/voiceRecord/model/VoiceRecordApi.d.ts.map +1 -1
- package/dist/typescript/module/features/voiceRecord/model/VoiceRecordCollection.d.ts +10 -0
- package/dist/typescript/module/features/voiceRecord/model/VoiceRecordCollection.d.ts.map +1 -0
- package/dist/typescript/module/features/voiceRecord/types.d.ts +43 -0
- package/dist/typescript/module/features/voiceRecord/types.d.ts.map +1 -0
- package/dist/typescript/module/lib/components/ConditionalWrapper.d.ts +9 -0
- package/dist/typescript/module/lib/components/ConditionalWrapper.d.ts.map +1 -0
- package/dist/typescript/module/shared/translation/constants.d.ts +78 -0
- package/dist/typescript/module/shared/translation/constants.d.ts.map +1 -1
- package/dist/typescript/module/shared/translation/model.d.ts +26 -0
- package/dist/typescript/module/shared/translation/model.d.ts.map +1 -1
- package/dist/typescript/module/types/common.types.d.ts +3 -0
- package/dist/typescript/module/types/common.types.d.ts.map +1 -1
- package/package.json +3 -1
- package/src/features/chatbot/components/Chat/Chat.tsx +30 -19
- package/src/features/chatbot/components/ChatControls/ChatControls.tsx +9 -2
- package/src/features/chatbot/components/Chatbot.tsx +15 -2
- package/src/features/chatbot/model/ChatBotModel.ts +12 -3
- package/src/features/chatbot/model/ChatsCacheModel.ts +4 -0
- package/src/features/chatbot/types/api.types.ts +1 -0
- package/src/features/chatbot/types/model.types.ts +1 -0
- package/src/features/voiceRecord/components/VoiceRecord.tsx +29 -18
- package/src/features/voiceRecord/components/VoiceRecordButton.tsx +33 -17
- package/src/features/voiceRecord/components/{VoiceRecordDelete.tsx → VoiceRecordDeleteButton.tsx} +5 -4
- package/src/features/voiceRecord/components/VoiceRecordTimer.tsx +19 -3
- package/src/features/voiceRecord/constants.ts +6 -0
- package/src/features/voiceRecord/helpers.ts +115 -1
- package/src/features/voiceRecord/hooks/useVoiceRecorder.ts +50 -36
- package/src/features/voiceRecord/hooks/useVoiceRecorderAnimation.ts +3 -4
- package/src/features/voiceRecord/index.ts +4 -0
- package/src/features/voiceRecord/modal/VoiceRecordDeleteModal.tsx +105 -0
- package/src/features/voiceRecord/modal/VoiceRecordUndoModal.tsx +82 -0
- package/src/features/voiceRecord/model/Recorder.model.ts +62 -0
- package/src/features/voiceRecord/model/VoiceRecord.model.ts +193 -32
- package/src/features/voiceRecord/model/VoiceRecordApi.ts +25 -1
- package/src/features/voiceRecord/model/VoiceRecordCollection.ts +26 -0
- package/src/features/voiceRecord/types.ts +49 -0
- package/src/lib/components/ConditionalWrapper.tsx +15 -0
- package/src/shared/translation/localization/ca.json +13 -0
- package/src/shared/translation/localization/de.json +13 -0
- package/src/shared/translation/localization/en.json +13 -0
- package/src/shared/translation/localization/gb.json +13 -0
- package/src/shared/translation/localization/sct.json +13 -0
- package/src/shared/translation/localization/sw.json +13 -0
- package/src/types/common.types.ts +1 -0
- package/dist/commonjs/features/voiceRecord/components/VoiceRecordDelete.js.map +0 -1
- package/dist/module/features/voiceRecord/components/VoiceRecordDelete.js.map +0 -1
- package/dist/typescript/commonjs/features/voiceRecord/components/VoiceRecordDelete.d.ts +0 -7
- package/dist/typescript/commonjs/features/voiceRecord/components/VoiceRecordDelete.d.ts.map +0 -1
- package/dist/typescript/module/features/voiceRecord/components/VoiceRecordDelete.d.ts +0 -7
- package/dist/typescript/module/features/voiceRecord/components/VoiceRecordDelete.d.ts.map +0 -1
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
import React, { useEffect } from 'react'
|
|
2
|
+
import {
|
|
3
|
+
BaseModal,
|
|
4
|
+
Button,
|
|
5
|
+
ButtonColor,
|
|
6
|
+
ButtonSize,
|
|
7
|
+
ButtonVariant,
|
|
8
|
+
SPACING,
|
|
9
|
+
} from '@magmamath/react-native-ui'
|
|
10
|
+
import { View, StyleSheet } from 'react-native'
|
|
11
|
+
import { useUnit } from 'effector-react'
|
|
12
|
+
import { VoiceRecordModel } from '../model/VoiceRecord.model'
|
|
13
|
+
import { VoiceRecorderState } from '../constants'
|
|
14
|
+
import { useText } from '../../../shared/translation'
|
|
15
|
+
|
|
16
|
+
type VoiceRecordDeleteModalComponentProps = {
|
|
17
|
+
modal: {
|
|
18
|
+
closeModal: () => void
|
|
19
|
+
params: {
|
|
20
|
+
model: VoiceRecordModel
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
type FooterButtonsProps = {
|
|
26
|
+
onClose: () => void
|
|
27
|
+
onDelete: () => void
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
const FooterButtons = ({ onClose, onDelete }: FooterButtonsProps) => {
|
|
31
|
+
const t = useText()
|
|
32
|
+
|
|
33
|
+
return (
|
|
34
|
+
<View style={styles.footerContainer}>
|
|
35
|
+
<Button variant={ButtonVariant.TERTIARY} size={ButtonSize.LARGE} onPress={onClose}>
|
|
36
|
+
{t('voiceRecorder.cancel')}
|
|
37
|
+
</Button>
|
|
38
|
+
<Button
|
|
39
|
+
colorScheme={ButtonColor.RED}
|
|
40
|
+
variant={ButtonVariant.PRIMARY}
|
|
41
|
+
size={ButtonSize.LARGE}
|
|
42
|
+
onPress={onDelete}
|
|
43
|
+
>
|
|
44
|
+
{t('voiceRecorder.delete')}
|
|
45
|
+
</Button>
|
|
46
|
+
</View>
|
|
47
|
+
)
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
export const VoiceRecordDeleteModal = ({
|
|
51
|
+
modal: { closeModal, params },
|
|
52
|
+
}: VoiceRecordDeleteModalComponentProps) => {
|
|
53
|
+
const t = useText()
|
|
54
|
+
const { model } = params
|
|
55
|
+
|
|
56
|
+
const recorderState = useUnit(model.recorderModel.$voiceRecordState)
|
|
57
|
+
|
|
58
|
+
const handleDelete = async () => {
|
|
59
|
+
if (recorderState === VoiceRecorderState.RECORDING) {
|
|
60
|
+
await model.stopAndDiscard()
|
|
61
|
+
}
|
|
62
|
+
await model.deleteCurrentRecording()
|
|
63
|
+
|
|
64
|
+
closeModal()
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
useEffect(() => {
|
|
68
|
+
if (recorderState === VoiceRecorderState.RECORDING) {
|
|
69
|
+
model.recorderModel.recorder.pause()
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
return () => {
|
|
73
|
+
if (model.recorderModel.$voiceRecordState.getState() === VoiceRecorderState.PAUSED) {
|
|
74
|
+
try {
|
|
75
|
+
model.recorderModel.recorder.record()
|
|
76
|
+
} catch (error) {
|
|
77
|
+
console.error(`Failed to resume recording: ${error}`)
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
}, [])
|
|
82
|
+
|
|
83
|
+
return (
|
|
84
|
+
<BaseModal
|
|
85
|
+
style={{
|
|
86
|
+
container: styles.modalContainer,
|
|
87
|
+
}}
|
|
88
|
+
header={t('voiceRecorder.deleteRecording')}
|
|
89
|
+
content={t('voiceRecorder.youWontBeAbleToRecover')}
|
|
90
|
+
footer={<FooterButtons onClose={closeModal} onDelete={handleDelete} />}
|
|
91
|
+
/>
|
|
92
|
+
)
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
const styles = StyleSheet.create({
|
|
96
|
+
modalContainer: {
|
|
97
|
+
width: 600,
|
|
98
|
+
height: 268,
|
|
99
|
+
},
|
|
100
|
+
footerContainer: {
|
|
101
|
+
flexDirection: 'row',
|
|
102
|
+
alignItems: 'center',
|
|
103
|
+
gap: SPACING[200],
|
|
104
|
+
},
|
|
105
|
+
})
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
import React from 'react'
|
|
2
|
+
import {
|
|
3
|
+
BaseModal,
|
|
4
|
+
Button,
|
|
5
|
+
ButtonColor,
|
|
6
|
+
ButtonSize,
|
|
7
|
+
ButtonVariant,
|
|
8
|
+
SPACING,
|
|
9
|
+
} from '@magmamath/react-native-ui'
|
|
10
|
+
import { StyleSheet, View } from 'react-native'
|
|
11
|
+
import { useText } from '../../../shared/translation'
|
|
12
|
+
import { VoiceRecordModel } from '../model/VoiceRecord.model'
|
|
13
|
+
|
|
14
|
+
type VoiceRecordUndoModalProps = {
|
|
15
|
+
modal: {
|
|
16
|
+
closeModal: () => void
|
|
17
|
+
params: {
|
|
18
|
+
model: VoiceRecordModel
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
type FooterButtonsProps = {
|
|
24
|
+
onClose: () => void
|
|
25
|
+
onRedo: () => void
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
const FooterButtons = ({ onClose, onRedo }: FooterButtonsProps) => {
|
|
29
|
+
const t = useText()
|
|
30
|
+
|
|
31
|
+
return (
|
|
32
|
+
<View style={styles.footerContainer}>
|
|
33
|
+
<Button variant={ButtonVariant.TERTIARY} size={ButtonSize.LARGE} onPress={onClose}>
|
|
34
|
+
{t('voiceRecorder.cancel')}
|
|
35
|
+
</Button>
|
|
36
|
+
<Button
|
|
37
|
+
colorScheme={ButtonColor.BLUE}
|
|
38
|
+
variant={ButtonVariant.PRIMARY}
|
|
39
|
+
size={ButtonSize.LARGE}
|
|
40
|
+
onPress={onRedo}
|
|
41
|
+
>
|
|
42
|
+
{t('voiceRecorder.redo')}
|
|
43
|
+
</Button>
|
|
44
|
+
</View>
|
|
45
|
+
)
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
export const VoiceRecordUndoModal = ({
|
|
49
|
+
modal: { closeModal, params },
|
|
50
|
+
}: VoiceRecordUndoModalProps) => {
|
|
51
|
+
const t = useText()
|
|
52
|
+
const { model } = params
|
|
53
|
+
|
|
54
|
+
const handleRedo = () => {
|
|
55
|
+
model.deleteCurrentRecording({ notification: false })
|
|
56
|
+
closeModal()
|
|
57
|
+
model.initializeRecording()
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
return (
|
|
61
|
+
<BaseModal
|
|
62
|
+
style={{
|
|
63
|
+
container: styles.modalStyle,
|
|
64
|
+
}}
|
|
65
|
+
header={t('voiceRecorder.redoRecording')}
|
|
66
|
+
content={t('voiceRecorder.thisWillRemoveRecording')}
|
|
67
|
+
footer={<FooterButtons onClose={closeModal} onRedo={handleRedo} />}
|
|
68
|
+
/>
|
|
69
|
+
)
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
const styles = StyleSheet.create({
|
|
73
|
+
modalStyle: {
|
|
74
|
+
width: 600,
|
|
75
|
+
height: 268,
|
|
76
|
+
},
|
|
77
|
+
footerContainer: {
|
|
78
|
+
flexDirection: 'row',
|
|
79
|
+
alignItems: 'center',
|
|
80
|
+
gap: SPACING[200],
|
|
81
|
+
},
|
|
82
|
+
})
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
import { createEffect, createEvent, restore } from 'effector'
|
|
2
|
+
import { AudioRecorder, setAudioModeAsync } from 'expo-audio'
|
|
3
|
+
import { VoiceRecorderState } from '../constants'
|
|
4
|
+
import { AvailableAudioInputs, VoiceRecordCollectionItem } from '../types'
|
|
5
|
+
|
|
6
|
+
const AUDIO_MODE_CONFIG = {
|
|
7
|
+
playsInSilentMode: true,
|
|
8
|
+
allowsRecording: true,
|
|
9
|
+
} as const
|
|
10
|
+
|
|
11
|
+
type StopResolver = (item: VoiceRecordCollectionItem) => void
|
|
12
|
+
|
|
13
|
+
export class RecorderModel {
|
|
14
|
+
public recorder!: AudioRecorder
|
|
15
|
+
private stopResolver: StopResolver | null = null
|
|
16
|
+
|
|
17
|
+
public readonly reset = createEvent()
|
|
18
|
+
public readonly setAudioFileDurationMs = createEvent<number>()
|
|
19
|
+
public readonly setVoiceRecordState = createEvent<VoiceRecorderState>()
|
|
20
|
+
public readonly setAvailableInputs = createEvent<AvailableAudioInputs>()
|
|
21
|
+
|
|
22
|
+
public readonly $audioFileDurationMs = restore(this.setAudioFileDurationMs, 0).reset(this.reset)
|
|
23
|
+
public readonly $voiceRecordState = restore(
|
|
24
|
+
this.setVoiceRecordState,
|
|
25
|
+
VoiceRecorderState.IDLE,
|
|
26
|
+
).reset(this.reset)
|
|
27
|
+
public readonly $availableInputs = restore(this.setAvailableInputs, [])
|
|
28
|
+
|
|
29
|
+
public readonly start = createEffect(async () => {
|
|
30
|
+
try {
|
|
31
|
+
await setAudioModeAsync(AUDIO_MODE_CONFIG)
|
|
32
|
+
await this.recorder.prepareToRecordAsync()
|
|
33
|
+
this.recorder.record()
|
|
34
|
+
} catch (error) {
|
|
35
|
+
console.error('Error starting recording:', error)
|
|
36
|
+
throw error
|
|
37
|
+
}
|
|
38
|
+
})
|
|
39
|
+
|
|
40
|
+
public readonly stop = createEffect(() => {
|
|
41
|
+
if (!this.recorder.isRecording) return Promise.resolve()
|
|
42
|
+
return this.recorder.stop()
|
|
43
|
+
})
|
|
44
|
+
|
|
45
|
+
public stopAndGetCollectionItem(): Promise<VoiceRecordCollectionItem> {
|
|
46
|
+
return new Promise((resolve) => {
|
|
47
|
+
this.stopResolver = resolve
|
|
48
|
+
this.recorder.isRecording && this.recorder.stop()
|
|
49
|
+
})
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
public resolveStopWithCollectionItem(item: VoiceRecordCollectionItem): void {
|
|
53
|
+
if (this.stopResolver) {
|
|
54
|
+
this.stopResolver(item)
|
|
55
|
+
this.stopResolver = null
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
public clearStopResolver(): void {
|
|
60
|
+
this.stopResolver = null
|
|
61
|
+
}
|
|
62
|
+
}
|
|
@@ -1,51 +1,212 @@
|
|
|
1
|
-
import { createEffect, createEvent, createStore, restore, sample } from 'effector'
|
|
2
|
-
import {
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
}
|
|
1
|
+
import { attach, createEffect, createEvent, createStore, restore, sample } from 'effector'
|
|
2
|
+
import {
|
|
3
|
+
ensureRecordingPermissions,
|
|
4
|
+
generateAudioFormData,
|
|
5
|
+
getAudioDurationMs,
|
|
6
|
+
getAvailableInputs,
|
|
7
|
+
uploadAudioFileRequestGenerator,
|
|
8
|
+
} from '../helpers'
|
|
9
|
+
import { AudioApi, VoiceRecordNotificationTypes, VoiceRecordCollectionItem } from '../types'
|
|
10
|
+
import { t } from '../../../shared/translation'
|
|
11
|
+
import { RecorderModel } from './Recorder.model'
|
|
12
|
+
import { VoiceRecordsCollection } from './VoiceRecordCollection'
|
|
13
|
+
import { VoiceRecorderState } from '../constants'
|
|
10
14
|
|
|
11
15
|
type VoiceRecordModelParams = {
|
|
12
|
-
|
|
16
|
+
api: AudioApi
|
|
17
|
+
notification: VoiceRecordNotificationTypes
|
|
18
|
+
events: VoiceRecordEvents
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
type UploadParams = {
|
|
22
|
+
uri: string
|
|
23
|
+
currentKey: string
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
type VoiceRecordEvents = {
|
|
27
|
+
deleteRecord: () => void
|
|
28
|
+
undoRecord: () => void
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
type DeleteCurrentRecordingProps = {
|
|
32
|
+
notification?: boolean
|
|
33
|
+
}
|
|
34
|
+
type DeleteCurrentRecordingValues = {
|
|
35
|
+
currentKey: string
|
|
36
|
+
notification?: boolean
|
|
13
37
|
}
|
|
14
38
|
|
|
15
39
|
export class VoiceRecordModel {
|
|
16
|
-
public readonly
|
|
17
|
-
public readonly
|
|
40
|
+
public readonly recorderModel: RecorderModel
|
|
41
|
+
public readonly collection: VoiceRecordsCollection
|
|
42
|
+
public readonly api: AudioApi
|
|
43
|
+
public readonly notification: VoiceRecordNotificationTypes
|
|
44
|
+
public readonly events: VoiceRecordEvents
|
|
45
|
+
private shouldDiscardRecording = false
|
|
46
|
+
|
|
47
|
+
public readonly setCurrentKey = createEvent<string>()
|
|
48
|
+
public readonly setCurrentRecord = createEvent<any>()
|
|
49
|
+
public readonly reset = createEvent()
|
|
50
|
+
public readonly setIsDisabled = createEvent<boolean>()
|
|
51
|
+
public readonly startAudioUpload = createEvent<string>()
|
|
52
|
+
|
|
53
|
+
public readonly $currentKey = restore(this.setCurrentKey, '')
|
|
54
|
+
public readonly $currentRecord = restore(this.setCurrentRecord, null).reset(this.reset)
|
|
18
55
|
|
|
19
|
-
public readonly
|
|
56
|
+
public readonly $isDisabled = restore(this.setIsDisabled, false)
|
|
20
57
|
|
|
21
|
-
public readonly
|
|
22
|
-
|
|
23
|
-
|
|
58
|
+
public readonly deleteCurrentRecording = attach({
|
|
59
|
+
source: this.$currentKey,
|
|
60
|
+
mapParams: (props: DeleteCurrentRecordingProps | void, currentKey) => ({
|
|
61
|
+
notification: true,
|
|
62
|
+
...props,
|
|
63
|
+
currentKey,
|
|
64
|
+
}),
|
|
65
|
+
effect: createEffect(({ currentKey, notification }: DeleteCurrentRecordingValues) => {
|
|
66
|
+
const recordingItem = this.collection.get(currentKey)
|
|
24
67
|
|
|
25
|
-
|
|
68
|
+
this.abortUploadIfInProgress(recordingItem)
|
|
69
|
+
this.resetRecordingState(currentKey)
|
|
26
70
|
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
71
|
+
if (notification) {
|
|
72
|
+
this.notification.info(t('voiceRecorder.recordingDeleted'))
|
|
73
|
+
}
|
|
74
|
+
}),
|
|
75
|
+
})
|
|
30
76
|
|
|
31
|
-
public readonly
|
|
32
|
-
|
|
77
|
+
public readonly initializeRecording = createEffect(async () => {
|
|
78
|
+
this.deleteCurrentRecording({ notification: false })
|
|
33
79
|
|
|
34
|
-
|
|
35
|
-
|
|
80
|
+
const hasPermissions = await ensureRecordingPermissions()
|
|
81
|
+
if (!hasPermissions) {
|
|
82
|
+
this.notification.error(t('voiceRecorder.noMicrophoneAccess'))
|
|
83
|
+
return
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
const inputs = await getAvailableInputs(this.recorderModel.recorder)
|
|
87
|
+
this.recorderModel.setAvailableInputs(inputs)
|
|
88
|
+
|
|
89
|
+
if (inputs.length === 0) {
|
|
90
|
+
this.notification.error(t('voiceRecorder.noMicrophoneFound'))
|
|
91
|
+
return
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
return this.recorderModel.start()
|
|
95
|
+
})
|
|
96
|
+
|
|
97
|
+
public readonly stopAndDiscard = createEffect(async () => {
|
|
98
|
+
this.shouldDiscardRecording = true
|
|
99
|
+
await this.recorderModel.stop()
|
|
100
|
+
this.recorderModel.clearStopResolver()
|
|
101
|
+
this.recorderModel.reset()
|
|
102
|
+
})
|
|
103
|
+
|
|
104
|
+
public readonly recordingStatusUpdate = (status: any) => {
|
|
105
|
+
if (status.error) {
|
|
106
|
+
this.notification.error(`Recorder error: ${status.error}`)
|
|
107
|
+
this.recorderModel.clearStopResolver()
|
|
108
|
+
this.shouldDiscardRecording = false
|
|
109
|
+
return
|
|
110
|
+
}
|
|
111
|
+
if (status.isFinished && status.url) {
|
|
112
|
+
if (!this.shouldDiscardRecording) {
|
|
113
|
+
this.startAudioUpload(status.url)
|
|
114
|
+
}
|
|
115
|
+
this.shouldDiscardRecording = false
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
constructor({ api, notification, events }: VoiceRecordModelParams) {
|
|
120
|
+
this.api = api
|
|
121
|
+
this.notification = notification
|
|
122
|
+
this.events = events
|
|
123
|
+
this.recorderModel = new RecorderModel()
|
|
124
|
+
this.collection = new VoiceRecordsCollection()
|
|
125
|
+
|
|
126
|
+
this.setupUploadHandler()
|
|
127
|
+
this.setupCurrentRecordSync()
|
|
128
|
+
this.setupUriSync()
|
|
129
|
+
}
|
|
36
130
|
|
|
131
|
+
private abortUploadIfInProgress(recordingItem: ReturnType<VoiceRecordsCollection['get']>) {
|
|
132
|
+
if (!recordingItem?.id && recordingItem?.controller) {
|
|
133
|
+
recordingItem.controller.abort()
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
private resetRecordingState(currentKey: string) {
|
|
138
|
+
this.recorderModel.reset()
|
|
139
|
+
this.reset()
|
|
140
|
+
this.collection.delete(currentKey)
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
private async handleAudioUpload({ uri, currentKey }: UploadParams) {
|
|
144
|
+
const durationMs = await getAudioDurationMs(uri)
|
|
145
|
+
const formData = await generateAudioFormData({ audioFileUri: uri, durationMs })
|
|
146
|
+
const { uploadAudio, controller } = uploadAudioFileRequestGenerator(formData, this.api)
|
|
147
|
+
|
|
148
|
+
const audioUploadPromise = uploadAudio()
|
|
149
|
+
.then((data) => {
|
|
150
|
+
// Check if the item still exists (wasn't deleted during upload)
|
|
151
|
+
if (this.collection.get(currentKey)) {
|
|
152
|
+
this.collection.update(currentKey, { id: data.id })
|
|
153
|
+
}
|
|
154
|
+
return data
|
|
155
|
+
})
|
|
156
|
+
.catch((error) => {
|
|
157
|
+
if (error.name === 'CanceledError') return
|
|
158
|
+
this.notification.error(t('voiceRecorder.uploadFailed'))
|
|
159
|
+
})
|
|
160
|
+
|
|
161
|
+
const collectionItem: VoiceRecordCollectionItem = {
|
|
162
|
+
durationMs,
|
|
163
|
+
audioUploadPromise,
|
|
164
|
+
controller,
|
|
165
|
+
uri,
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
this.collection.add(currentKey, collectionItem)
|
|
169
|
+
this.setCurrentRecord(collectionItem)
|
|
170
|
+
this.recorderModel.resolveStopWithCollectionItem(collectionItem)
|
|
171
|
+
|
|
172
|
+
return audioUploadPromise
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
private setupUploadHandler() {
|
|
37
176
|
sample({
|
|
38
|
-
clock: this.
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
})
|
|
177
|
+
clock: this.startAudioUpload,
|
|
178
|
+
source: this.$currentKey,
|
|
179
|
+
filter: (currentKey, uri) => !!uri && !!currentKey,
|
|
180
|
+
fn: (currentKey, uri) => ({ currentKey, uri }),
|
|
181
|
+
target: createEffect(({ uri, currentKey }: UploadParams) =>
|
|
182
|
+
this.handleAudioUpload({ uri, currentKey }),
|
|
183
|
+
),
|
|
43
184
|
})
|
|
185
|
+
}
|
|
44
186
|
|
|
187
|
+
private setupUriSync() {
|
|
45
188
|
sample({
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
189
|
+
source: this.$currentRecord,
|
|
190
|
+
fn: (record) => record?.uri || '',
|
|
191
|
+
target: createStore<string>('').reset(this.reset),
|
|
192
|
+
})
|
|
193
|
+
}
|
|
194
|
+
|
|
195
|
+
private setupCurrentRecordSync() {
|
|
196
|
+
sample({
|
|
197
|
+
source: this.$currentKey,
|
|
198
|
+
fn: (currentKey) => this.collection.get(currentKey),
|
|
199
|
+
target: createEffect((recordingItem?: VoiceRecordCollectionItem) => {
|
|
200
|
+
if (!recordingItem) {
|
|
201
|
+
this.reset()
|
|
202
|
+
return
|
|
203
|
+
}
|
|
204
|
+
|
|
205
|
+
this.setCurrentRecord(recordingItem)
|
|
206
|
+
|
|
207
|
+
if (recordingItem.durationMs) {
|
|
208
|
+
this.recorderModel.setAudioFileDurationMs(recordingItem.durationMs)
|
|
209
|
+
}
|
|
49
210
|
}),
|
|
50
211
|
})
|
|
51
212
|
}
|
|
@@ -1 +1,25 @@
|
|
|
1
|
-
|
|
1
|
+
import { createEffect } from 'effector'
|
|
2
|
+
import { AudioApi } from '../types'
|
|
3
|
+
import { createControllerEffect } from './../../../lib/effector/createControllerEffect'
|
|
4
|
+
|
|
5
|
+
export class VoiceRecordApi {
|
|
6
|
+
// public readonly uploadAudioFileFx
|
|
7
|
+
|
|
8
|
+
// public readonly abortUpload = createEffect(() => {
|
|
9
|
+
// if (this.uploadAudioFileFx.pending.getState()) {
|
|
10
|
+
// this.uploadAudioFileFx.controller.abort()
|
|
11
|
+
// }
|
|
12
|
+
// })
|
|
13
|
+
|
|
14
|
+
constructor(api: AudioApi) {
|
|
15
|
+
// this.uploadAudioFileFx = createControllerEffect((audioFileFormData: FormData, config) =>
|
|
16
|
+
// api.uploadAudioFile(
|
|
17
|
+
// { audioFileFormData },
|
|
18
|
+
// //@ts-ignore
|
|
19
|
+
// {
|
|
20
|
+
// signal: config?.signal,
|
|
21
|
+
// },
|
|
22
|
+
// ),
|
|
23
|
+
// )
|
|
24
|
+
}
|
|
25
|
+
}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { VoiceRecordCollectionItem } from '../types'
|
|
2
|
+
|
|
3
|
+
export class VoiceRecordsCollection {
|
|
4
|
+
public readonly collection: Map<string, VoiceRecordCollectionItem> = new Map()
|
|
5
|
+
|
|
6
|
+
public add(key: string, item: VoiceRecordCollectionItem) {
|
|
7
|
+
this.collection.set(key, item)
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
public update(key: string, item: Partial<VoiceRecordCollectionItem>) {
|
|
11
|
+
const existingItem = this.collection.get(key) || {}
|
|
12
|
+
this.collection.set(key, { ...existingItem, ...item })
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
public delete(key: string) {
|
|
16
|
+
this.collection.delete(key)
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
public get(key: string) {
|
|
20
|
+
return this.collection.get(key)
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
public clear() {
|
|
24
|
+
this.collection.clear()
|
|
25
|
+
}
|
|
26
|
+
}
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import { WithAbortSignal } from 'src/types/common.types'
|
|
2
|
+
import { getAvailableInputs } from './helpers'
|
|
3
|
+
import { VoiceRecordModel } from './model/VoiceRecord.model'
|
|
4
|
+
|
|
5
|
+
export type VoiceRecordNotificationTypes = {
|
|
6
|
+
info: (message: string) => void
|
|
7
|
+
error: (message: string) => void
|
|
8
|
+
warning: (message: string) => void
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
export type UploadAudioPayload = WithAbortSignal<{
|
|
12
|
+
audioFileFormData: FormData
|
|
13
|
+
}>
|
|
14
|
+
|
|
15
|
+
type AudioTranscriptResponse = {
|
|
16
|
+
text: string
|
|
17
|
+
}
|
|
18
|
+
type UploadAudioResponse = {
|
|
19
|
+
id: string
|
|
20
|
+
fileName: string
|
|
21
|
+
fileType: string
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
export type AudioApi = {
|
|
25
|
+
uploadAudioFile: (data: UploadAudioPayload) => Promise<UploadAudioResponse>
|
|
26
|
+
getAudioFileTranscript: (audioFileId: string) => Promise<AudioTranscriptResponse>
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
export type VoiceRecordCollectionItem = {
|
|
30
|
+
solutionId?: string
|
|
31
|
+
id?: string //it exists after upload to server
|
|
32
|
+
durationMs?: number
|
|
33
|
+
uri?: string
|
|
34
|
+
audioUploadPromise?: Promise<void | UploadAudioResponse>
|
|
35
|
+
controller?: AbortController
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
export type VoiceRecordStack = {
|
|
39
|
+
[problemId: string]: VoiceRecordCollectionItem
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
export type AvailableAudioInputs = Awaited<ReturnType<typeof getAvailableInputs>>
|
|
43
|
+
|
|
44
|
+
export type VoiceRecordDeleteModalParams = {
|
|
45
|
+
model: VoiceRecordModel
|
|
46
|
+
}
|
|
47
|
+
export type VoiceRecordUndoModalParams = {
|
|
48
|
+
model: VoiceRecordModel
|
|
49
|
+
}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import React, { ComponentType, PropsWithChildren, ReactNode } from 'react'
|
|
2
|
+
|
|
3
|
+
type ConditionalWrapperProps = {
|
|
4
|
+
children: ReactNode
|
|
5
|
+
withWrapper?: boolean
|
|
6
|
+
Wrapper?: ComponentType<PropsWithChildren>
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
export const ConditionalWrapper = ({ withWrapper, Wrapper, children }: ConditionalWrapperProps) => {
|
|
10
|
+
if (withWrapper && Wrapper) {
|
|
11
|
+
return <Wrapper>{children}</Wrapper>
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
return children
|
|
15
|
+
}
|
|
@@ -39,5 +39,18 @@
|
|
|
39
39
|
"volume": "Volume",
|
|
40
40
|
"weight": "Weight",
|
|
41
41
|
"time": "Time"
|
|
42
|
+
},
|
|
43
|
+
"voiceRecorder": {
|
|
44
|
+
"deleteRecording": "Delete recording?",
|
|
45
|
+
"youWontBeAbleToRecover": "You won't be able to recover this file once it's gone.",
|
|
46
|
+
"recordingDeleted": "Recording successfully deleted",
|
|
47
|
+
"delete": "Delete",
|
|
48
|
+
"cancel": "Cancel",
|
|
49
|
+
"noMicrophoneAccess": "No microphone access",
|
|
50
|
+
"noMicrophoneFound": "No microphone found",
|
|
51
|
+
"uploadFailed": "Upload failed. Please try again.",
|
|
52
|
+
"redoRecording": "Redo recording?",
|
|
53
|
+
"redo": "Redo",
|
|
54
|
+
"thisWillRemoveRecording": "This will remove your previous recording."
|
|
42
55
|
}
|
|
43
56
|
}
|
|
@@ -39,5 +39,18 @@
|
|
|
39
39
|
"volume": "Volumen",
|
|
40
40
|
"weight": "Gewicht",
|
|
41
41
|
"time": "Zeit"
|
|
42
|
+
},
|
|
43
|
+
"voiceRecorder": {
|
|
44
|
+
"deleteRecording": "Aufnahme löschen?",
|
|
45
|
+
"youWontBeAbleToRecover": "Du kannst die Datei nicht wiederherstellen, wenn sie einmal gelöscht ist.",
|
|
46
|
+
"recordingDeleted": "Aufnahme gelöscht.",
|
|
47
|
+
"delete": "Löschen",
|
|
48
|
+
"cancel": "Abbrechen",
|
|
49
|
+
"noMicrophoneAccess": "Kein Mikrofon-Zugriff.",
|
|
50
|
+
"noMicrophoneFound": "Kein Mikrofon gefunden.",
|
|
51
|
+
"uploadFailed": "Hochladen fehlgeschlagen. Bitte versuche es erneut.",
|
|
52
|
+
"redoRecording": "Redo recording?",
|
|
53
|
+
"redo": "Redo",
|
|
54
|
+
"thisWillRemoveRecording": "This will remove your previous recording."
|
|
42
55
|
}
|
|
43
56
|
}
|
|
@@ -39,5 +39,18 @@
|
|
|
39
39
|
"volume": "Volume",
|
|
40
40
|
"weight": "Weight",
|
|
41
41
|
"time": "Time"
|
|
42
|
+
},
|
|
43
|
+
"voiceRecorder": {
|
|
44
|
+
"deleteRecording": "Delete recording?",
|
|
45
|
+
"youWontBeAbleToRecover": "You won't be able to recover this file once it's gone.",
|
|
46
|
+
"recordingDeleted": "Recording successfully deleted",
|
|
47
|
+
"delete": "Delete",
|
|
48
|
+
"cancel": "Cancel",
|
|
49
|
+
"noMicrophoneAccess": "No microphone access",
|
|
50
|
+
"noMicrophoneFound": "No microphone found",
|
|
51
|
+
"uploadFailed": "Upload failed. Please try again.",
|
|
52
|
+
"redoRecording": "Redo recording?",
|
|
53
|
+
"redo": "Redo",
|
|
54
|
+
"thisWillRemoveRecording": "This will remove your previous recording."
|
|
42
55
|
}
|
|
43
56
|
}
|