diff --git a/.gitea/workflows/deploy.yaml b/.gitea/workflows/deploy.yaml index c72996b..26b55e7 100644 --- a/.gitea/workflows/deploy.yaml +++ b/.gitea/workflows/deploy.yaml @@ -3,7 +3,7 @@ run-name: ${{ gitea.actor }} is testing out Gitea Actions 🚀 on: push: branches: - - 'dev' + - 'demo-t*' env: BUILD: staging diff --git a/server.js b/server.js index 68de804..ca263df 100644 --- a/server.js +++ b/server.js @@ -88,7 +88,7 @@ const connectedClients = new Map(); // 视频映射配置 const videoMapping = { // 'say-6s-m-e': '1-m.mp4', - 'default': 'chane.mp4', + 'default': 'chang.mp4', // 'say-5s-amplitude': '2.mp4', // 'say-5s-m-e': '4.mp4', // 'say-5s-m-sw': 'd-0.mp4', diff --git a/src/audio_processor.js b/src/audio_processor.js index e8b4cb4..e651a2d 100644 --- a/src/audio_processor.js +++ b/src/audio_processor.js @@ -362,8 +362,23 @@ class AudioProcessor { // 停止录音 stopRecording() { + console.log('开始停止录音...'); + + // 停止所有音频轨道 + if (this.stream) { + this.stream.getTracks().forEach(track => { + track.stop(); + console.log(`停止音频轨道: ${track.label}`); + }); + this.stream = null; + } + if (this.audioContext) { - this.audioContext.close(); + this.audioContext.close().then(() => { + console.log('AudioContext已关闭'); + }).catch(err => { + console.error('关闭AudioContext时出错:', err); + }); this.audioContext = null; } @@ -377,12 +392,16 @@ class AudioProcessor { this.handleSpeechEnd(); } + // 重置所有状态 this.isRecording = false; this.isSpeaking = false; this.audioBuffer = []; + this.audioChunks = []; + this.consecutiveFramesCount = 0; + this.frameBuffer = []; - this.onStatusUpdate('录音已停止', 'stopped'); - console.log('录音已停止'); + this.onStatusUpdate('录音已完全停止', 'stopped'); + console.log('录音已完全停止,所有资源已释放'); } // 获取录音状态 diff --git a/src/config.js b/src/config.js index e4e1d01..0433660 100644 --- a/src/config.js +++ b/src/config.js @@ -3,7 +3,7 @@ export const config = { // LLM API配置 llm: { apiKey: 'd012651b-a65b-4b13-8ff3-cc4ff3a29783', // 请替换为实际的API密钥 - model: 'bot-20250720193048-84fkp', + model: 'bot-20250724150616-xqpz8', }, // Minimaxi API配置 diff --git a/src/index.html b/src/index.html index f43765b..49d0af3 100644 --- a/src/index.html +++ b/src/index.html @@ -194,37 +194,40 @@ } #startButton { + width: 60px; + height: 60px; + border-radius: 50%; + background: rgba(34, 197, 94, 0.9); + backdrop-filter: blur(10px); + border: none; + cursor: pointer; + display: flex; + align-items: center; + justify-content: center; + transition: all 0.3s ease; + box-shadow: 0 4px 15px rgba(34, 197, 94, 0.3); + min-width: auto; padding: 15px 30px; font-size: 1.1rem; border-radius: 25px; min-width: 200px; - background: rgba(0, 123, 255, 0.9); - backdrop-filter: blur(10px); } - #stopButton { - width: 60px; - height: 60px; - border-radius: 50%; - background: rgba(220, 53, 69, 0.9); - backdrop-filter: blur(10px); - border: none; - cursor: pointer; - display: none; - align-items: center; - justify-content: center; - transition: all 0.3s ease; - box-shadow: 0 4px 15px rgba(220, 53, 69, 0.3); - } - - #stopButton.show { - display: flex; - } - - #stopButton:hover:not(:disabled) { - background: rgba(200, 35, 51, 0.95); + #startButton:hover:not(:disabled) { + background: rgba(22, 163, 74, 0.95); transform: scale(1.1); - box-shadow: 0 6px 20px rgba(220, 53, 69, 0.5); + box-shadow: 0 6px 20px rgba(34, 197, 94, 0.5); + } + + #startButton svg { + width: 24px; + height: 24px; + fill: white; + } + + #startButton:disabled { + opacity: 0.5; + cursor: not-allowed; } #stopButton svg { @@ -284,12 +287,14 @@
- + diff --git a/src/index.js b/src/index.js index c280051..6f82154 100644 --- a/src/index.js +++ b/src/index.js @@ -837,8 +837,16 @@ class WebRTCChat { } stopCall() { + // 停止音频处理器 + if (this.audioProcessor) { + this.audioProcessor.stopRecording(); + } + if (this.localStream) { - this.localStream.getTracks().forEach(track => track.stop()); + this.localStream.getTracks().forEach(track => { + track.stop(); + console.log(`停止轨道: ${track.kind}`); + }); this.localStream = null; } @@ -855,7 +863,6 @@ class WebRTCChat { this.recordedVideo.srcObject = null; this.currentVideo = null; - this.currentVideoName.textContent = '未选择视频'; this.startButton.disabled = false; this.stopButton.disabled = true; @@ -863,11 +870,8 @@ class WebRTCChat { // 隐藏结束通话按钮 this.stopButton.classList.remove('show'); - this.stopVoiceRecording() this.updateAudioStatus('未连接', 'disconnected'); - this.logMessage('音频通话已结束', 'info'); - - + this.logMessage('音频通话已结束,所有资源已释放', 'info'); } async createPeerConnection() { diff --git a/src/llm_stream.js b/src/llm_stream.js index 884abd7..608f8e8 100644 --- a/src/llm_stream.js +++ b/src/llm_stream.js @@ -29,7 +29,7 @@ async function requestLLMStream({ apiKey, model, messages, onSegment }) { let pendingText = ''; // 待处理的文本片段 // 分段分隔符 - const segmentDelimiters = /[,。:;!?,.:;!?]/; + const segmentDelimiters = /[,。:;!?,.:;!?]|\.{3,}/; while (!done) { const { value, done: doneReading } = await reader.read();