@chat-lab/ui 0.1.0-beta.20 → 0.1.0-beta.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.
|
@@ -67,9 +67,9 @@ const VoiceInput = () => {
|
|
|
67
67
|
setIsListening(false);
|
|
68
68
|
ref.current?.setInput(transcript);
|
|
69
69
|
};
|
|
70
|
-
return (jsxRuntime.jsx(tooltip.TooltipProvider, { children: jsxRuntime.jsxs(tooltip.Tooltip, { children: [jsxRuntime.jsx(tooltip.TooltipTrigger, { asChild: true, children: jsxRuntime.jsx(button.Button, { variant: isListening ? "destructive" : "ghost", size: "icon", onClick: isListening ? stopListening : startListening, disabled: !!error, className: `w-10 h-10 transition-all duration-200
|
|
70
|
+
return (jsxRuntime.jsx(tooltip.TooltipProvider, { children: jsxRuntime.jsxs(tooltip.Tooltip, { children: [jsxRuntime.jsx(tooltip.TooltipTrigger, { asChild: true, children: jsxRuntime.jsx(button.Button, { variant: isListening ? "destructive" : "ghost", size: "icon", onClick: isListening ? stopListening : startListening, disabled: !!error, className: `w-10 h-10 transition-all duration-200 ${isListening
|
|
71
71
|
? "bg-red-500 hover:bg-red-600 text-white animate-pulse w-8 h-8"
|
|
72
|
-
: ""}`, children: isListening ? (jsxRuntime.jsx(micOff.default, { className: "h-[18px] w-[18px]" })) : (jsxRuntime.jsx(mic.default, { className: "h-[18px] w-[18px]" })) }) }), jsxRuntime.jsx(tooltip.TooltipContent, { children: jsxRuntime.jsx("p", { children: isListening ? "停止录音" : "语音输入" }) })] }) }));
|
|
72
|
+
: ""} h-[18px] w-[18px]`, children: isListening ? (jsxRuntime.jsx(micOff.default, { className: "h-[18px] w-[18px]" })) : (jsxRuntime.jsx(mic.default, { className: "h-[18px] w-[18px]" })) }) }), jsxRuntime.jsx(tooltip.TooltipContent, { children: jsxRuntime.jsx("p", { children: isListening ? "停止录音" : "语音输入" }) })] }) }));
|
|
73
73
|
};
|
|
74
74
|
|
|
75
75
|
module.exports = VoiceInput;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.cjs","sources":["../../../src/components/VoiceInput/index.tsx"],"sourcesContent":["import React, { useState, useRef, useEffect } from \"react\";\nimport { Button } from \"@/components/ui/button\";\nimport { Mic, MicOff } from \"lucide-react\";\nimport {\n Tooltip,\n TooltipContent,\n TooltipProvider,\n TooltipTrigger,\n} from \"@/components/ui/tooltip\";\nimport { useChatkitRef } from \"@/contexts/ChatkitContext\";\n\n// 定义语音识别相关类型\ninterface SpeechRecognitionEvent extends Event {\n results: SpeechRecognitionResultList;\n}\n\ninterface SpeechRecognitionResultList {\n [index: number]: SpeechRecognitionResult;\n length: number;\n}\n\ninterface SpeechRecognitionResult {\n [index: number]: SpeechRecognitionAlternative;\n isFinal: boolean;\n length: number;\n}\n\ninterface SpeechRecognitionAlternative {\n transcript: string;\n confidence: number;\n}\n\ninterface SpeechRecognition extends EventTarget {\n lang: string;\n interimResults: boolean;\n continuous: boolean;\n onresult: ((event: SpeechRecognitionEvent) => void) | null;\n onend: (() => void) | null;\n start: () => void;\n stop: () => void;\n}\n\nconst VoiceInput: React.FC = () => {\n const [transcript, setTranscript] = useState<string>(\"\");\n const [isListening, setIsListening] = useState<boolean>(false);\n const [error, setError] = useState<string | null>(null);\n const recognitionRef = useRef<SpeechRecognition | null>(null);\n const ref = useChatkitRef();\n useEffect(() => {\n // 检查浏览器支持\n const SpeechRecognition =\n (window as any).SpeechRecognition ||\n (window as any).webkitSpeechRecognition;\n\n if (!SpeechRecognition) {\n setError(\"您的浏览器不支持语音识别功能,请使用最新版 Chrome 浏览器\");\n return;\n }\n\n // 初始化识别实例\n const recognition = new SpeechRecognition() as SpeechRecognition;\n recognition.lang = \"zh-CN\"; // 设置为中文识别\n recognition.interimResults = true; // 实时返回结果\n recognition.continuous = false; // 单次识别模式\n\n // 处理识别结果\n recognition.onresult = (event: SpeechRecognitionEvent) => {\n if (event.results.length > 0) {\n const currentResult = event.results[0][0].transcript;\n setTranscript(currentResult);\n ref.current?.setInput(currentResult);\n }\n };\n\n // 识别结束时重置状态\n recognition.onend = () => {\n setIsListening(false);\n };\n\n recognitionRef.current = recognition;\n\n // 清理函数\n return () => {\n recognition.stop();\n };\n }, []);\n\n const startListening = () => {\n if (!recognitionRef.current || isListening) return;\n\n try {\n setIsListening(true);\n setTranscript(\"\");\n recognitionRef.current.start();\n } catch (err) {\n setError(\"启动语音识别失败,请稍后重试\");\n setIsListening(false);\n console.error(\"语音识别启动错误:\", err);\n }\n };\n const stopListening = async () => {\n if (!recognitionRef.current || !isListening) return;\n await new Promise((resolve) => setTimeout(resolve, 1000));\n\n recognitionRef.current.stop();\n setIsListening(false);\n ref.current?.setInput(transcript);\n };\n\n return (\n <TooltipProvider>\n <Tooltip>\n <TooltipTrigger asChild>\n <Button\n variant={isListening ? \"destructive\" : \"ghost\"}\n size=\"icon\"\n onClick={isListening ? stopListening : startListening}\n disabled={!!error}\n className={`w-10 h-10 transition-all duration-200
|
|
1
|
+
{"version":3,"file":"index.cjs","sources":["../../../src/components/VoiceInput/index.tsx"],"sourcesContent":["import React, { useState, useRef, useEffect } from \"react\";\nimport { Button } from \"@/components/ui/button\";\nimport { Mic, MicOff } from \"lucide-react\";\nimport {\n Tooltip,\n TooltipContent,\n TooltipProvider,\n TooltipTrigger,\n} from \"@/components/ui/tooltip\";\nimport { useChatkitRef } from \"@/contexts/ChatkitContext\";\n\n// 定义语音识别相关类型\ninterface SpeechRecognitionEvent extends Event {\n results: SpeechRecognitionResultList;\n}\n\ninterface SpeechRecognitionResultList {\n [index: number]: SpeechRecognitionResult;\n length: number;\n}\n\ninterface SpeechRecognitionResult {\n [index: number]: SpeechRecognitionAlternative;\n isFinal: boolean;\n length: number;\n}\n\ninterface SpeechRecognitionAlternative {\n transcript: string;\n confidence: number;\n}\n\ninterface SpeechRecognition extends EventTarget {\n lang: string;\n interimResults: boolean;\n continuous: boolean;\n onresult: ((event: SpeechRecognitionEvent) => void) | null;\n onend: (() => void) | null;\n start: () => void;\n stop: () => void;\n}\n\nconst VoiceInput: React.FC = () => {\n const [transcript, setTranscript] = useState<string>(\"\");\n const [isListening, setIsListening] = useState<boolean>(false);\n const [error, setError] = useState<string | null>(null);\n const recognitionRef = useRef<SpeechRecognition | null>(null);\n const ref = useChatkitRef();\n useEffect(() => {\n // 检查浏览器支持\n const SpeechRecognition =\n (window as any).SpeechRecognition ||\n (window as any).webkitSpeechRecognition;\n\n if (!SpeechRecognition) {\n setError(\"您的浏览器不支持语音识别功能,请使用最新版 Chrome 浏览器\");\n return;\n }\n\n // 初始化识别实例\n const recognition = new SpeechRecognition() as SpeechRecognition;\n recognition.lang = \"zh-CN\"; // 设置为中文识别\n recognition.interimResults = true; // 实时返回结果\n recognition.continuous = false; // 单次识别模式\n\n // 处理识别结果\n recognition.onresult = (event: SpeechRecognitionEvent) => {\n if (event.results.length > 0) {\n const currentResult = event.results[0][0].transcript;\n setTranscript(currentResult);\n ref.current?.setInput(currentResult);\n }\n };\n\n // 识别结束时重置状态\n recognition.onend = () => {\n setIsListening(false);\n };\n\n recognitionRef.current = recognition;\n\n // 清理函数\n return () => {\n recognition.stop();\n };\n }, []);\n\n const startListening = () => {\n if (!recognitionRef.current || isListening) return;\n\n try {\n setIsListening(true);\n setTranscript(\"\");\n recognitionRef.current.start();\n } catch (err) {\n setError(\"启动语音识别失败,请稍后重试\");\n setIsListening(false);\n console.error(\"语音识别启动错误:\", err);\n }\n };\n const stopListening = async () => {\n if (!recognitionRef.current || !isListening) return;\n await new Promise((resolve) => setTimeout(resolve, 1000));\n\n recognitionRef.current.stop();\n setIsListening(false);\n ref.current?.setInput(transcript);\n };\n\n return (\n <TooltipProvider>\n <Tooltip>\n <TooltipTrigger asChild>\n <Button\n variant={isListening ? \"destructive\" : \"ghost\"}\n size=\"icon\"\n onClick={isListening ? stopListening : startListening}\n disabled={!!error}\n className={`w-10 h-10 transition-all duration-200 ${\n isListening\n ? \"bg-red-500 hover:bg-red-600 text-white animate-pulse w-8 h-8\"\n : \"\"\n } h-[18px] w-[18px]`}\n >\n {isListening ? (\n <MicOff className=\"h-[18px] w-[18px]\" />\n ) : (\n <Mic className=\"h-[18px] w-[18px]\" />\n )}\n </Button>\n </TooltipTrigger>\n <TooltipContent>\n <p>{isListening ? \"停止录音\" : \"语音输入\"}</p>\n </TooltipContent>\n </Tooltip>\n </TooltipProvider>\n );\n};\n\nexport default VoiceInput;\n"],"names":["useState","useRef","useChatkitRef","useEffect","_jsx","TooltipProvider","_jsxs","Tooltip","TooltipTrigger","Button","MicOff","Mic","TooltipContent"],"mappings":";;;;;;;;;;AA0CM,MAAA,UAAU,GAAa,MAAK;IAChC,MAAM,CAAC,UAAU,EAAE,aAAa,CAAC,GAAGA,cAAQ,CAAS,EAAE,CAAC,CAAC;IACzD,MAAM,CAAC,WAAW,EAAE,cAAc,CAAC,GAAGA,cAAQ,CAAU,KAAK,CAAC,CAAC;IAC/D,MAAM,CAAC,KAAK,EAAE,QAAQ,CAAC,GAAGA,cAAQ,CAAgB,IAAI,CAAC,CAAC;AACxD,IAAA,MAAM,cAAc,GAAGC,YAAM,CAA2B,IAAI,CAAC,CAAC;AAC9D,IAAA,MAAM,GAAG,GAAGC,4BAAa,EAAE,CAAC;IAC5BC,eAAS,CAAC,MAAK;;AAEb,QAAA,MAAM,iBAAiB,GACpB,MAAc,CAAC,iBAAiB;YAChC,MAAc,CAAC,uBAAuB,CAAC;QAE1C,IAAI,CAAC,iBAAiB,EAAE;YACtB,QAAQ,CAAC,kCAAkC,CAAC,CAAC;YAC7C,OAAO;SACR;;AAGD,QAAA,MAAM,WAAW,GAAG,IAAI,iBAAiB,EAAuB,CAAC;AACjE,QAAA,WAAW,CAAC,IAAI,GAAG,OAAO,CAAC;AAC3B,QAAA,WAAW,CAAC,cAAc,GAAG,IAAI,CAAC;AAClC,QAAA,WAAW,CAAC,UAAU,GAAG,KAAK,CAAC;;AAG/B,QAAA,WAAW,CAAC,QAAQ,GAAG,CAAC,KAA6B,KAAI;YACvD,IAAI,KAAK,CAAC,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE;AAC5B,gBAAA,MAAM,aAAa,GAAG,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,UAAU,CAAC;gBACrD,aAAa,CAAC,aAAa,CAAC,CAAC;AAC7B,gBAAA,GAAG,CAAC,OAAO,EAAE,QAAQ,CAAC,aAAa,CAAC,CAAC;aACtC;AACH,SAAC,CAAC;;AAGF,QAAA,WAAW,CAAC,KAAK,GAAG,MAAK;YACvB,cAAc,CAAC,KAAK,CAAC,CAAC;AACxB,SAAC,CAAC;AAEF,QAAA,cAAc,CAAC,OAAO,GAAG,WAAW,CAAC;;AAGrC,QAAA,OAAO,MAAK;YACV,WAAW,CAAC,IAAI,EAAE,CAAC;AACrB,SAAC,CAAC;KACH,EAAE,EAAE,CAAC,CAAC;IAEP,MAAM,cAAc,GAAG,MAAK;AAC1B,QAAA,IAAI,CAAC,cAAc,CAAC,OAAO,IAAI,WAAW;YAAE,OAAO;AAEnD,QAAA,IAAI;YACF,cAAc,CAAC,IAAI,CAAC,CAAC;YACrB,aAAa,CAAC,EAAE,CAAC,CAAC;AAClB,YAAA,cAAc,CAAC,OAAO,CAAC,KAAK,EAAE,CAAC;SAChC;QAAC,OAAO,GAAG,EAAE;YACZ,QAAQ,CAAC,gBAAgB,CAAC,CAAC;YAC3B,cAAc,CAAC,KAAK,CAAC,CAAC;AACtB,YAAA,OAAO,CAAC,KAAK,CAAC,WAAW,EAAE,GAAG,CAAC,CAAC;SACjC;AACH,KAAC,CAAC;AACF,IAAA,MAAM,aAAa,GAAG,YAAW;AAC/B,QAAA,IAAI,CAAC,cAAc,CAAC,OAAO,IAAI,CAAC,WAAW;YAAE,OAAO;AACpD,QAAA,MAAM,IAAI,OAAO,CAAC,CAAC,OAAO,KAAK,UAAU,CAAC,OAAO,EAAE,IAAI,CAAC,CAAC,CAAC;AAE1D,QAAA,cAAc,CAAC,OAAO,CAAC,IAAI,EAAE,CAAC;QAC9B,cAAc,CAAC,KAAK,CAAC,CAAC;AACtB,QAAA,GAAG,CAAC,OAAO,EAAE,QAAQ,CAAC,UAAU,CAAC,CAAC;AACpC,KAAC,CAAC;IAEF,QACEC,cAAC,CAAAC,uBAAe,EACd,EAAA,QAAA,EAAAC,eAAA,CAACC,eAAO,EACN,EAAA,QAAA,EAAA,CAAAH,cAAA,CAACI,sBAAc,EAAA,EAAC,OAAO,EAAA,IAAA,EAAA,QAAA,EACrBJ,eAACK,aAAM,EAAA,EACL,OAAO,EAAE,WAAW,GAAG,aAAa,GAAG,OAAO,EAC9C,IAAI,EAAC,MAAM,EACX,OAAO,EAAE,WAAW,GAAG,aAAa,GAAG,cAAc,EACrD,QAAQ,EAAE,CAAC,CAAC,KAAK,EACjB,SAAS,EAAE,CAAA,uCAAA,EACT,WAAW;AACT,8BAAE,8DAA8D;8BAC9D,EACN,CAAoB,kBAAA,CAAA,EAAA,QAAA,EAEnB,WAAW,IACVL,cAAC,CAAAM,cAAM,IAAC,SAAS,EAAC,mBAAmB,EAAA,CAAG,KAExCN,cAAC,CAAAO,WAAG,EAAC,EAAA,SAAS,EAAC,mBAAmB,EAAA,CAAG,CACtC,EACM,CAAA,EAAA,CACM,EACjBP,cAAC,CAAAQ,sBAAc,EACb,EAAA,QAAA,EAAAR,cAAA,CAAA,GAAA,EAAA,EAAA,QAAA,EAAI,WAAW,GAAG,MAAM,GAAG,MAAM,GAAK,EACvB,CAAA,CAAA,EAAA,CACT,EACM,CAAA,EAClB;AACJ;;;;"}
|
|
@@ -65,9 +65,9 @@ const VoiceInput = () => {
|
|
|
65
65
|
setIsListening(false);
|
|
66
66
|
ref.current?.setInput(transcript);
|
|
67
67
|
};
|
|
68
|
-
return (jsx(TooltipProvider, { children: jsxs(Tooltip, { children: [jsx(TooltipTrigger, { asChild: true, children: jsx(Button, { variant: isListening ? "destructive" : "ghost", size: "icon", onClick: isListening ? stopListening : startListening, disabled: !!error, className: `w-10 h-10 transition-all duration-200
|
|
68
|
+
return (jsx(TooltipProvider, { children: jsxs(Tooltip, { children: [jsx(TooltipTrigger, { asChild: true, children: jsx(Button, { variant: isListening ? "destructive" : "ghost", size: "icon", onClick: isListening ? stopListening : startListening, disabled: !!error, className: `w-10 h-10 transition-all duration-200 ${isListening
|
|
69
69
|
? "bg-red-500 hover:bg-red-600 text-white animate-pulse w-8 h-8"
|
|
70
|
-
: ""}`, children: isListening ? (jsx(MicOff, { className: "h-[18px] w-[18px]" })) : (jsx(Mic, { className: "h-[18px] w-[18px]" })) }) }), jsx(TooltipContent, { children: jsx("p", { children: isListening ? "停止录音" : "语音输入" }) })] }) }));
|
|
70
|
+
: ""} h-[18px] w-[18px]`, children: isListening ? (jsx(MicOff, { className: "h-[18px] w-[18px]" })) : (jsx(Mic, { className: "h-[18px] w-[18px]" })) }) }), jsx(TooltipContent, { children: jsx("p", { children: isListening ? "停止录音" : "语音输入" }) })] }) }));
|
|
71
71
|
};
|
|
72
72
|
|
|
73
73
|
export { VoiceInput as default };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sources":["../../../src/components/VoiceInput/index.tsx"],"sourcesContent":["import React, { useState, useRef, useEffect } from \"react\";\nimport { Button } from \"@/components/ui/button\";\nimport { Mic, MicOff } from \"lucide-react\";\nimport {\n Tooltip,\n TooltipContent,\n TooltipProvider,\n TooltipTrigger,\n} from \"@/components/ui/tooltip\";\nimport { useChatkitRef } from \"@/contexts/ChatkitContext\";\n\n// 定义语音识别相关类型\ninterface SpeechRecognitionEvent extends Event {\n results: SpeechRecognitionResultList;\n}\n\ninterface SpeechRecognitionResultList {\n [index: number]: SpeechRecognitionResult;\n length: number;\n}\n\ninterface SpeechRecognitionResult {\n [index: number]: SpeechRecognitionAlternative;\n isFinal: boolean;\n length: number;\n}\n\ninterface SpeechRecognitionAlternative {\n transcript: string;\n confidence: number;\n}\n\ninterface SpeechRecognition extends EventTarget {\n lang: string;\n interimResults: boolean;\n continuous: boolean;\n onresult: ((event: SpeechRecognitionEvent) => void) | null;\n onend: (() => void) | null;\n start: () => void;\n stop: () => void;\n}\n\nconst VoiceInput: React.FC = () => {\n const [transcript, setTranscript] = useState<string>(\"\");\n const [isListening, setIsListening] = useState<boolean>(false);\n const [error, setError] = useState<string | null>(null);\n const recognitionRef = useRef<SpeechRecognition | null>(null);\n const ref = useChatkitRef();\n useEffect(() => {\n // 检查浏览器支持\n const SpeechRecognition =\n (window as any).SpeechRecognition ||\n (window as any).webkitSpeechRecognition;\n\n if (!SpeechRecognition) {\n setError(\"您的浏览器不支持语音识别功能,请使用最新版 Chrome 浏览器\");\n return;\n }\n\n // 初始化识别实例\n const recognition = new SpeechRecognition() as SpeechRecognition;\n recognition.lang = \"zh-CN\"; // 设置为中文识别\n recognition.interimResults = true; // 实时返回结果\n recognition.continuous = false; // 单次识别模式\n\n // 处理识别结果\n recognition.onresult = (event: SpeechRecognitionEvent) => {\n if (event.results.length > 0) {\n const currentResult = event.results[0][0].transcript;\n setTranscript(currentResult);\n ref.current?.setInput(currentResult);\n }\n };\n\n // 识别结束时重置状态\n recognition.onend = () => {\n setIsListening(false);\n };\n\n recognitionRef.current = recognition;\n\n // 清理函数\n return () => {\n recognition.stop();\n };\n }, []);\n\n const startListening = () => {\n if (!recognitionRef.current || isListening) return;\n\n try {\n setIsListening(true);\n setTranscript(\"\");\n recognitionRef.current.start();\n } catch (err) {\n setError(\"启动语音识别失败,请稍后重试\");\n setIsListening(false);\n console.error(\"语音识别启动错误:\", err);\n }\n };\n const stopListening = async () => {\n if (!recognitionRef.current || !isListening) return;\n await new Promise((resolve) => setTimeout(resolve, 1000));\n\n recognitionRef.current.stop();\n setIsListening(false);\n ref.current?.setInput(transcript);\n };\n\n return (\n <TooltipProvider>\n <Tooltip>\n <TooltipTrigger asChild>\n <Button\n variant={isListening ? \"destructive\" : \"ghost\"}\n size=\"icon\"\n onClick={isListening ? stopListening : startListening}\n disabled={!!error}\n className={`w-10 h-10 transition-all duration-200
|
|
1
|
+
{"version":3,"file":"index.js","sources":["../../../src/components/VoiceInput/index.tsx"],"sourcesContent":["import React, { useState, useRef, useEffect } from \"react\";\nimport { Button } from \"@/components/ui/button\";\nimport { Mic, MicOff } from \"lucide-react\";\nimport {\n Tooltip,\n TooltipContent,\n TooltipProvider,\n TooltipTrigger,\n} from \"@/components/ui/tooltip\";\nimport { useChatkitRef } from \"@/contexts/ChatkitContext\";\n\n// 定义语音识别相关类型\ninterface SpeechRecognitionEvent extends Event {\n results: SpeechRecognitionResultList;\n}\n\ninterface SpeechRecognitionResultList {\n [index: number]: SpeechRecognitionResult;\n length: number;\n}\n\ninterface SpeechRecognitionResult {\n [index: number]: SpeechRecognitionAlternative;\n isFinal: boolean;\n length: number;\n}\n\ninterface SpeechRecognitionAlternative {\n transcript: string;\n confidence: number;\n}\n\ninterface SpeechRecognition extends EventTarget {\n lang: string;\n interimResults: boolean;\n continuous: boolean;\n onresult: ((event: SpeechRecognitionEvent) => void) | null;\n onend: (() => void) | null;\n start: () => void;\n stop: () => void;\n}\n\nconst VoiceInput: React.FC = () => {\n const [transcript, setTranscript] = useState<string>(\"\");\n const [isListening, setIsListening] = useState<boolean>(false);\n const [error, setError] = useState<string | null>(null);\n const recognitionRef = useRef<SpeechRecognition | null>(null);\n const ref = useChatkitRef();\n useEffect(() => {\n // 检查浏览器支持\n const SpeechRecognition =\n (window as any).SpeechRecognition ||\n (window as any).webkitSpeechRecognition;\n\n if (!SpeechRecognition) {\n setError(\"您的浏览器不支持语音识别功能,请使用最新版 Chrome 浏览器\");\n return;\n }\n\n // 初始化识别实例\n const recognition = new SpeechRecognition() as SpeechRecognition;\n recognition.lang = \"zh-CN\"; // 设置为中文识别\n recognition.interimResults = true; // 实时返回结果\n recognition.continuous = false; // 单次识别模式\n\n // 处理识别结果\n recognition.onresult = (event: SpeechRecognitionEvent) => {\n if (event.results.length > 0) {\n const currentResult = event.results[0][0].transcript;\n setTranscript(currentResult);\n ref.current?.setInput(currentResult);\n }\n };\n\n // 识别结束时重置状态\n recognition.onend = () => {\n setIsListening(false);\n };\n\n recognitionRef.current = recognition;\n\n // 清理函数\n return () => {\n recognition.stop();\n };\n }, []);\n\n const startListening = () => {\n if (!recognitionRef.current || isListening) return;\n\n try {\n setIsListening(true);\n setTranscript(\"\");\n recognitionRef.current.start();\n } catch (err) {\n setError(\"启动语音识别失败,请稍后重试\");\n setIsListening(false);\n console.error(\"语音识别启动错误:\", err);\n }\n };\n const stopListening = async () => {\n if (!recognitionRef.current || !isListening) return;\n await new Promise((resolve) => setTimeout(resolve, 1000));\n\n recognitionRef.current.stop();\n setIsListening(false);\n ref.current?.setInput(transcript);\n };\n\n return (\n <TooltipProvider>\n <Tooltip>\n <TooltipTrigger asChild>\n <Button\n variant={isListening ? \"destructive\" : \"ghost\"}\n size=\"icon\"\n onClick={isListening ? stopListening : startListening}\n disabled={!!error}\n className={`w-10 h-10 transition-all duration-200 ${\n isListening\n ? \"bg-red-500 hover:bg-red-600 text-white animate-pulse w-8 h-8\"\n : \"\"\n } h-[18px] w-[18px]`}\n >\n {isListening ? (\n <MicOff className=\"h-[18px] w-[18px]\" />\n ) : (\n <Mic className=\"h-[18px] w-[18px]\" />\n )}\n </Button>\n </TooltipTrigger>\n <TooltipContent>\n <p>{isListening ? \"停止录音\" : \"语音输入\"}</p>\n </TooltipContent>\n </Tooltip>\n </TooltipProvider>\n );\n};\n\nexport default VoiceInput;\n"],"names":["_jsx","_jsxs"],"mappings":"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"}
|