diff --git a/main/xiaozhi-server/test/css/test_page.css b/main/xiaozhi-server/test/css/test_page.css index 57332d0c..1bfc3bd7 100644 --- a/main/xiaozhi-server/test/css/test_page.css +++ b/main/xiaozhi-server/test/css/test_page.css @@ -904,17 +904,6 @@ body { .mcp-tools-panel { padding: 20px; - transition: max-height 0.3s ease; - overflow: hidden; -} - -.mcp-tools-panel.expanded { - max-height: 500px; -} - -.mcp-tools-panel:not(.expanded) { - max-height: 0; - padding: 0 20px; } .mcp-tools-list { diff --git a/main/xiaozhi-server/test/js/app.js b/main/xiaozhi-server/test/js/app.js index 6984fce9..bca7e3a7 100644 --- a/main/xiaozhi-server/test/js/app.js +++ b/main/xiaozhi-server/test/js/app.js @@ -1,10 +1,10 @@ // 主应用入口 -import { checkOpusLoaded, initOpusEncoder } from './core/audio/opus-codec.js?v=0127'; -import { getAudioPlayer } from './core/audio/player.js?v=0127'; -import { checkMicrophoneAvailability, isHttpNonLocalhost } from './core/audio/recorder.js?v=0127'; -import { initMcpTools } from './core/mcp/tools.js?v=0127'; -import { uiController } from './ui/controller.js?v=0127'; -import { log } from './utils/logger.js?v=0127'; +import { checkOpusLoaded, initOpusEncoder } from './core/audio/opus-codec.js?v=0205'; +import { getAudioPlayer } from './core/audio/player.js?v=0205'; +import { checkMicrophoneAvailability, isHttpNonLocalhost } from './core/audio/recorder.js?v=0205'; +import { initMcpTools } from './core/mcp/tools.js?v=0205'; +import { uiController } from './ui/controller.js?v=0205'; +import { log } from './utils/logger.js?v=0205'; // 辅助函数:将Base64数据转换为Blob function dataURItoBlob(dataURI) { @@ -254,7 +254,7 @@ class App { if (!url || !token) { throw new Error('视觉分析失败:配置缺少接口地址(url)或令牌(token)'); } - + log(`正在发送图片到视觉分析接口: ${url}`, 'info'); const deviceId = document.getElementById('deviceMac')?.value || ''; diff --git a/main/xiaozhi-server/test/js/core/audio/opus-codec.js b/main/xiaozhi-server/test/js/core/audio/opus-codec.js index 8bca8bb8..52ee12e6 100644 --- a/main/xiaozhi-server/test/js/core/audio/opus-codec.js +++ b/main/xiaozhi-server/test/js/core/audio/opus-codec.js @@ -1,4 +1,4 @@ -import { log } from '../../utils/logger.js?v=0127'; +import { log } from '../../utils/logger.js?v=0205'; // 检查Opus库是否已加载 diff --git a/main/xiaozhi-server/test/js/core/audio/player.js b/main/xiaozhi-server/test/js/core/audio/player.js index 191a1981..70b37fa5 100644 --- a/main/xiaozhi-server/test/js/core/audio/player.js +++ b/main/xiaozhi-server/test/js/core/audio/player.js @@ -1,7 +1,7 @@ // 音频播放模块 -import BlockingQueue from '../../utils/blocking-queue.js?v=0127'; -import { log } from '../../utils/logger.js?v=0127'; -import { createStreamingContext } from './stream-context.js?v=0127'; +import BlockingQueue from '../../utils/blocking-queue.js?v=0205'; +import { log } from '../../utils/logger.js?v=0205'; +import { createStreamingContext } from './stream-context.js?v=0205'; // 音频播放器类 export class AudioPlayer { diff --git a/main/xiaozhi-server/test/js/core/audio/recorder.js b/main/xiaozhi-server/test/js/core/audio/recorder.js index 8ac14655..bb24a723 100644 --- a/main/xiaozhi-server/test/js/core/audio/recorder.js +++ b/main/xiaozhi-server/test/js/core/audio/recorder.js @@ -1,7 +1,7 @@ // Audio recording module -import { log } from '../../utils/logger.js?v=0127'; -import { initOpusEncoder } from './opus-codec.js?v=0127'; -import { getAudioPlayer } from './player.js?v=0127'; +import { log } from '../../utils/logger.js?v=0205'; +import { initOpusEncoder } from './opus-codec.js?v=0205'; +import { getAudioPlayer } from './player.js?v=0205'; // Audio recorder class export class AudioRecorder { @@ -204,7 +204,7 @@ export class AudioRecorder { if (this.isRecording) return false; try { // Check if WebSocketHandler instance exists - const { getWebSocketHandler } = await import('../network/websocket.js?v=0127'); + const { getWebSocketHandler } = await import('../network/websocket.js?v=0205'); const wsHandler = getWebSocketHandler(); // If machine is speaking, send abort message if (wsHandler && wsHandler.isRemoteSpeaking && wsHandler.currentSessionId) { diff --git a/main/xiaozhi-server/test/js/core/audio/stream-context.js b/main/xiaozhi-server/test/js/core/audio/stream-context.js index eef6dce9..db56ebad 100644 --- a/main/xiaozhi-server/test/js/core/audio/stream-context.js +++ b/main/xiaozhi-server/test/js/core/audio/stream-context.js @@ -1,5 +1,5 @@ -import BlockingQueue from '../../utils/blocking-queue.js?v=0127'; -import { log } from '../../utils/logger.js?v=0127'; +import BlockingQueue from '../../utils/blocking-queue.js?v=0205'; +import { log } from '../../utils/logger.js?v=0205'; // 音频流播放上下文类 export class StreamingContext { diff --git a/main/xiaozhi-server/test/js/core/mcp/tools.js b/main/xiaozhi-server/test/js/core/mcp/tools.js index 0d9f0976..7cfa8971 100644 --- a/main/xiaozhi-server/test/js/core/mcp/tools.js +++ b/main/xiaozhi-server/test/js/core/mcp/tools.js @@ -1,4 +1,4 @@ -import { log } from '../../utils/logger.js?v=0127'; +import { log } from '../../utils/logger.js?v=0205'; // ========================================== // MCP 工具管理逻辑 @@ -45,10 +45,7 @@ export async function initMcpTools() { mcpTools = [...defaultMcpTools]; } renderMcpTools(); - // Only setup event listeners if DOM elements exist - if (document.getElementById('toggleMcpTools')) { - setupMcpEventListeners(); - } + setupMcpEventListeners(); } /** @@ -280,7 +277,6 @@ function deleteMcpProperty(index) { * 设置事件监听 */ function setupMcpEventListeners() { - const toggleBtn = document.getElementById('toggleMcpTools'); const panel = document.getElementById('mcpToolsPanel'); const addBtn = document.getElementById('addMcpToolBtn'); const modal = document.getElementById('mcpToolModal'); @@ -297,32 +293,19 @@ function setupMcpEventListeners() { const propertyTypeSelect = document.getElementById('mcpPropertyType'); // Return early if required elements don't exist (e.g., in test environment) - if (!toggleBtn || !panel || !addBtn || !modal || !closeBtn || !cancelBtn || !form || !addPropertyBtn) { + if (!panel || !addBtn || !modal || !closeBtn || !cancelBtn || !form || !addPropertyBtn) { return; } - toggleBtn.addEventListener('click', () => { - const isExpanded = panel.classList.contains('expanded'); - panel.classList.toggle('expanded'); - toggleBtn.textContent = isExpanded ? '收起' : '展开'; - }); - // 确保面板默认展开 - panel.classList.add('expanded'); addBtn.addEventListener('click', () => openMcpModal()); closeBtn.addEventListener('click', closeMcpModal); cancelBtn.addEventListener('click', closeMcpModal); addPropertyBtn.addEventListener('click', addMcpProperty); - modal.addEventListener('click', (e) => { - if (e.target === modal) closeMcpModal(); - }); form.addEventListener('submit', handleMcpSubmit); // 参数编辑模态框事件 if (propertyModal && closePropertyBtn && cancelPropertyBtn && propertyForm && propertyTypeSelect) { closePropertyBtn.addEventListener('click', closePropertyModal); cancelPropertyBtn.addEventListener('click', closePropertyModal); - propertyModal.addEventListener('click', (e) => { - if (e.target === propertyModal) closePropertyModal(); - }); propertyForm.addEventListener('submit', handlePropertySubmit); propertyTypeSelect.addEventListener('change', updatePropertyRangeVisibility); } diff --git a/main/xiaozhi-server/test/js/core/network/ota-connector.js b/main/xiaozhi-server/test/js/core/network/ota-connector.js index 1b6fd134..9780f878 100644 --- a/main/xiaozhi-server/test/js/core/network/ota-connector.js +++ b/main/xiaozhi-server/test/js/core/network/ota-connector.js @@ -1,4 +1,4 @@ -import { log } from '../../utils/logger.js?v=0127'; +import { log } from '../../utils/logger.js?v=0205'; // WebSocket 连接 export async function webSocketConnect(otaUrl, config) { diff --git a/main/xiaozhi-server/test/js/core/network/websocket.js b/main/xiaozhi-server/test/js/core/network/websocket.js index 25134583..d0fffd78 100644 --- a/main/xiaozhi-server/test/js/core/network/websocket.js +++ b/main/xiaozhi-server/test/js/core/network/websocket.js @@ -1,11 +1,11 @@ // WebSocket消息处理模块 -import { getConfig, saveConnectionUrls } from '../../config/manager.js?v=0127'; -import { uiController } from '../../ui/controller.js?v=0127'; -import { log } from '../../utils/logger.js?v=0127'; -import { getAudioPlayer } from '../audio/player.js?v=0127'; -import { getAudioRecorder } from '../audio/recorder.js?v=0127'; -import { executeMcpTool, getMcpTools, setWebSocket as setMcpWebSocket } from '../mcp/tools.js?v=0127'; -import { webSocketConnect } from './ota-connector.js?v=0127'; +import { getConfig, saveConnectionUrls } from '../../config/manager.js?v=0205'; +import { uiController } from '../../ui/controller.js?v=0205'; +import { log } from '../../utils/logger.js?v=0205'; +import { getAudioPlayer } from '../audio/player.js?v=0205'; +import { getAudioRecorder } from '../audio/recorder.js?v=0205'; +import { executeMcpTool, getMcpTools, setWebSocket as setMcpWebSocket } from '../mcp/tools.js?v=0205'; +import { webSocketConnect } from './ota-connector.js?v=0205'; // WebSocket处理器类 export class WebSocketHandler { diff --git a/main/xiaozhi-server/test/js/ui/controller.js b/main/xiaozhi-server/test/js/ui/controller.js index 9f79f6b0..bc23f298 100644 --- a/main/xiaozhi-server/test/js/ui/controller.js +++ b/main/xiaozhi-server/test/js/ui/controller.js @@ -1,8 +1,8 @@ // UI controller module -import { loadConfig, saveConfig } from '../config/manager.js?v=0127'; -import { getAudioPlayer } from '../core/audio/player.js?v=0127'; -import { getAudioRecorder } from '../core/audio/recorder.js?v=0127'; -import { getWebSocketHandler } from '../core/network/websocket.js?v=0127'; +import { loadConfig, saveConfig } from '../config/manager.js?v=0205'; +import { getAudioPlayer } from '../core/audio/player.js?v=0205'; +import { getAudioRecorder } from '../core/audio/recorder.js?v=0205'; +import { getWebSocketHandler } from '../core/network/websocket.js?v=0205'; // UI controller class class UIController { @@ -248,13 +248,15 @@ class UIController { }); }); - // Click modal background to close + // 点击模态框背景关闭(仅对特定模态框禁用此功能) const modals = document.querySelectorAll('.modal'); modals.forEach(modal => { modal.addEventListener('click', (e) => { if (e.target === modal) { - if (modal.id === 'settingsModal') { - saveConfig(); + // settingsModal、mcpToolModal、mcpPropertyModal 只能通过点击X关闭 + const nonClosableModals = ['settingsModal', 'mcpToolModal', 'mcpPropertyModal']; + if (nonClosableModals.includes(modal.id)) { + return; // 禁止点击背景关闭 } this.hideModal(modal.id); } @@ -604,7 +606,7 @@ class UIController { if (isConnected) { // Check microphone availability (check again after connection) - const { checkMicrophoneAvailability } = await import('../core/audio/recorder.js?v=0127'); + const { checkMicrophoneAvailability } = await import('../core/audio/recorder.js?v=0205'); const micAvailable = await checkMicrophoneAvailability(); if (!micAvailable) { diff --git a/main/xiaozhi-server/test/test_page.html b/main/xiaozhi-server/test/test_page.html index 8515c30c..22d4b0f6 100644 --- a/main/xiaozhi-server/test/test_page.html +++ b/main/xiaozhi-server/test/test_page.html @@ -5,7 +5,7 @@