mirror of
https://github.com/danny-avila/LibreChat.git
synced 2025-12-17 00:40:14 +01:00
🎤 feat: Cumulative Transcription Support for AudioRecorder (#9316)
- Added useRef to maintain existing text during audio recording. - Updated setText to prepend existing text to new transcriptions. - Modified handleStartRecording and handleStopRecording to manage existing text state. - Improved spinner icon styling for better visibility.
This commit is contained in:
parent
ba424666f8
commit
c3e88b97c8
1 changed files with 17 additions and 7 deletions
|
|
@ -1,4 +1,4 @@
|
||||||
import { useCallback } from 'react';
|
import { useCallback, useRef } from 'react';
|
||||||
import { useToastContext, TooltipAnchor, ListeningIcon, Spinner } from '@librechat/client';
|
import { useToastContext, TooltipAnchor, ListeningIcon, Spinner } from '@librechat/client';
|
||||||
import { useLocalize, useSpeechToText } from '~/hooks';
|
import { useLocalize, useSpeechToText } from '~/hooks';
|
||||||
import { useChatFormContext } from '~/Providers';
|
import { useChatFormContext } from '~/Providers';
|
||||||
|
|
@ -18,9 +18,10 @@ export default function AudioRecorder({
|
||||||
textAreaRef: React.RefObject<HTMLTextAreaElement>;
|
textAreaRef: React.RefObject<HTMLTextAreaElement>;
|
||||||
isSubmitting: boolean;
|
isSubmitting: boolean;
|
||||||
}) {
|
}) {
|
||||||
const { setValue, reset } = methods;
|
const { setValue, reset, getValues } = methods;
|
||||||
const localize = useLocalize();
|
const localize = useLocalize();
|
||||||
const { showToast } = useToastContext();
|
const { showToast } = useToastContext();
|
||||||
|
const existingTextRef = useRef<string>('');
|
||||||
|
|
||||||
const onTranscriptionComplete = useCallback(
|
const onTranscriptionComplete = useCallback(
|
||||||
(text: string) => {
|
(text: string) => {
|
||||||
|
|
@ -39,6 +40,7 @@ export default function AudioRecorder({
|
||||||
}
|
}
|
||||||
ask({ text });
|
ask({ text });
|
||||||
reset({ text: '' });
|
reset({ text: '' });
|
||||||
|
existingTextRef.current = '';
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
[ask, reset, showToast, localize, isSubmitting],
|
[ask, reset, showToast, localize, isSubmitting],
|
||||||
|
|
@ -46,7 +48,9 @@ export default function AudioRecorder({
|
||||||
|
|
||||||
const setText = useCallback(
|
const setText = useCallback(
|
||||||
(text: string) => {
|
(text: string) => {
|
||||||
setValue('text', text, {
|
/** The transcript is cumulative, so we only need to prepend the existing text once */
|
||||||
|
const newText = existingTextRef.current ? `${existingTextRef.current} ${text}` : text;
|
||||||
|
setValue('text', newText, {
|
||||||
shouldValidate: true,
|
shouldValidate: true,
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
@ -62,18 +66,24 @@ export default function AudioRecorder({
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
const handleStartRecording = async () => startRecording();
|
const handleStartRecording = async () => {
|
||||||
|
existingTextRef.current = getValues('text') || '';
|
||||||
|
startRecording();
|
||||||
|
};
|
||||||
|
|
||||||
const handleStopRecording = async () => stopRecording();
|
const handleStopRecording = async () => {
|
||||||
|
stopRecording();
|
||||||
|
existingTextRef.current = '';
|
||||||
|
};
|
||||||
|
|
||||||
const renderIcon = () => {
|
const renderIcon = () => {
|
||||||
if (isListening === true) {
|
if (isListening === true) {
|
||||||
return <ListeningIcon className="stroke-red-500" />;
|
return <ListeningIcon className="stroke-red-500" />;
|
||||||
}
|
}
|
||||||
if (isLoading === true) {
|
if (isLoading === true) {
|
||||||
return <Spinner className="stroke-gray-700 dark:stroke-gray-300" />;
|
return <Spinner className="stroke-text-secondary" />;
|
||||||
}
|
}
|
||||||
return <ListeningIcon className="stroke-gray-700 dark:stroke-gray-300" />;
|
return <ListeningIcon className="stroke-text-secondary" />;
|
||||||
};
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue