feat(语言切换): 添加语言切换功能面板及实现逻辑

- 在工具栏添加语言切换按钮
- 新增语言选择浮动面板及样式
- 实现语言列表加载和切换功能
- 添加相关事件监听和处理逻辑
This commit is contained in:
2026-05-07 08:36:50 +08:00
parent c87ea397e7
commit 7c01dc5f2e
3 changed files with 107 additions and 2 deletions

View File

@@ -25,6 +25,9 @@
<button id="toggleCaptionBtn" class="toolbar-btn" title="字幕样式"> <button id="toggleCaptionBtn" class="toolbar-btn" title="字幕样式">
📝 📝
</button> </button>
<button id="toggleLanguageBtn" class="toolbar-btn" title="语言切换">
🌐
</button>
<button id="toggleLogBtn" class="toolbar-btn" title="事件日志"> <button id="toggleLogBtn" class="toolbar-btn" title="事件日志">
📜 📜
</button> </button>
@@ -272,6 +275,24 @@
</div> </div>
</div> </div>
<!-- 浮动面板:语言切换 -->
<div id="languagePanel" class="floating-panel language-panel">
<div class="panel-header">
<h2>🌐 语言设置</h2>
<button class="panel-close" data-panel="languagePanel">×</button>
</div>
<div class="panel-content">
<div class="config-section">
<h3>当前语言</h3>
<div class="form-group">
<select id="languageSelect" style="width: 100%; padding: 8px; border-radius: 4px; border: 1px solid #ddd;">
<option value="">加载中...</option>
</select>
</div>
</div>
</div>
</div>
<!-- 浮动面板:事件日志 --> <!-- 浮动面板:事件日志 -->
<div id="logPanel" class="floating-panel log-panel"> <div id="logPanel" class="floating-panel log-panel">
<div class="panel-header"> <div class="panel-header">

View File

@@ -33,7 +33,8 @@ const ConfigKey = {
ENABLE_DEVICE_SETTING: 'enableDeviceSetting', ENABLE_DEVICE_SETTING: 'enableDeviceSetting',
ENABLE_NETWORK_CHECK: 'enableNetworkCheck', ENABLE_NETWORK_CHECK: 'enableNetworkCheck',
AUTO_PLAY_REMOTE_VIDEO: 'autoPlayRemoteVideo', AUTO_PLAY_REMOTE_VIDEO: 'autoPlayRemoteVideo',
DEFAULT_MUTE_REMOTE_AUDIO: 'defaultMuteRemoteAudio' DEFAULT_MUTE_REMOTE_AUDIO: 'defaultMuteRemoteAudio',
ENABLE_LOCAL_WAKEUP: 'enableLocalWakeup'
}; };
const state = { const state = {
@@ -57,8 +58,10 @@ const elements = {
fullscreenBtn: document.getElementById('fullscreenBtn'), fullscreenBtn: document.getElementById('fullscreenBtn'),
toggleConfigBtn: document.getElementById('toggleConfigBtn'), toggleConfigBtn: document.getElementById('toggleConfigBtn'),
toggleCaptionBtn: document.getElementById('toggleCaptionBtn'), toggleCaptionBtn: document.getElementById('toggleCaptionBtn'),
toggleLanguageBtn: document.getElementById('toggleLanguageBtn'),
toggleLogBtn: document.getElementById('toggleLogBtn'), toggleLogBtn: document.getElementById('toggleLogBtn'),
applyCaptionStyleBtn: document.getElementById('applyCaptionStyleBtn'), applyCaptionStyleBtn: document.getElementById('applyCaptionStyleBtn'),
languageSelect: document.getElementById('languageSelect'),
containerBgColor: document.getElementById('containerBgColor'), containerBgColor: document.getElementById('containerBgColor'),
containerBgOpacity: document.getElementById('containerBgOpacity'), containerBgOpacity: document.getElementById('containerBgOpacity'),
@@ -189,6 +192,7 @@ const eventListeners = {
[ICSEventKey.LANGUAGE_INFO_CHANGE]: (langInfo) => { [ICSEventKey.LANGUAGE_INFO_CHANGE]: (langInfo) => {
logger.info('语言信息变更', langInfo); logger.info('语言信息变更', langInfo);
updateLanguageSelect(langInfo);
}, },
[ICSEventKey.JOB_END_MENTION]: (data) => { [ICSEventKey.JOB_END_MENTION]: (data) => {
@@ -246,6 +250,7 @@ function togglePanel(panelId) {
const btnMap = { const btnMap = {
configPanel: 'toggleConfigBtn', configPanel: 'toggleConfigBtn',
captionPanel: 'toggleCaptionBtn', captionPanel: 'toggleCaptionBtn',
languagePanel: 'toggleLanguageBtn',
logPanel: 'toggleLogBtn' logPanel: 'toggleLogBtn'
}; };
@@ -256,6 +261,70 @@ function togglePanel(panelId) {
} }
} }
async function loadLanguageOptions() {
if (!state.isInitialized) {
elements.languageSelect.innerHTML = '<option value="">SDK 未初始化</option>';
return;
}
try {
const langInfo = await HwICSUiSdk.getLanguageInfo();
logger.info('获取语言信息成功', langInfo);
if (langInfo.languageList && langInfo.languageList.length > 0) {
elements.languageSelect.innerHTML = '';
langInfo.languageList.forEach(item => {
const option = document.createElement('option');
option.value = item.language;
option.textContent = item.language_desc;
elements.languageSelect.appendChild(option);
});
if (langInfo.currentLanguage) {
elements.languageSelect.value = langInfo.currentLanguage;
}
} else {
elements.languageSelect.innerHTML = '<option value="">无可用语言</option>';
}
} catch (error) {
logger.error('获取语言信息失败', error);
elements.languageSelect.innerHTML = '<option value="">加载失败</option>';
}
}
function updateLanguageSelect(langInfo) {
if (!langInfo) return;
if (langInfo.languageList && langInfo.languageList.length > 0) {
elements.languageSelect.innerHTML = '';
langInfo.languageList.forEach(item => {
const option = document.createElement('option');
option.value = item.language;
option.textContent = item.language_desc;
elements.languageSelect.appendChild(option);
});
}
if (langInfo.currentLanguage) {
elements.languageSelect.value = langInfo.currentLanguage;
}
}
async function changeLanguage(langCode) {
if (!state.isInitialized) {
logger.error('SDK 未初始化,无法切换语言');
return;
}
try {
logger.info('正在切换语言...', langCode);
await HwICSUiSdk.changeLanguage({ langCode });
logger.info('语言切换成功', langCode);
} catch (error) {
logger.error('语言切换失败', error);
}
}
async function initializeSDK() { async function initializeSDK() {
try { try {
const serverAddress = elements.serverAddress.value.trim(); const serverAddress = elements.serverAddress.value.trim();
@@ -305,7 +374,8 @@ async function initializeSDK() {
[ConfigKey.ENABLE_DEVICE_SETTING]: false, [ConfigKey.ENABLE_DEVICE_SETTING]: false,
[ConfigKey.ENABLE_NETWORK_CHECK]: false, [ConfigKey.ENABLE_NETWORK_CHECK]: false,
[ConfigKey.AUTO_PLAY_REMOTE_VIDEO]: true, [ConfigKey.AUTO_PLAY_REMOTE_VIDEO]: true,
[ConfigKey.DEFAULT_MUTE_REMOTE_AUDIO]: false [ConfigKey.DEFAULT_MUTE_REMOTE_AUDIO]: false,
[ConfigKey.ENABLE_LOCAL_WAKEUP]: true
}, },
logLevel logLevel
}; };
@@ -1140,6 +1210,13 @@ function bindEvents() {
} }
}); });
elements.toggleLogBtn.addEventListener('click', () => togglePanel('logPanel')); elements.toggleLogBtn.addEventListener('click', () => togglePanel('logPanel'));
elements.toggleLanguageBtn.addEventListener('click', () => {
togglePanel('languagePanel');
loadLanguageOptions();
});
elements.languageSelect.addEventListener('change', (e) => {
changeLanguage(e.target.value);
});
elements.fullscreenBtn.addEventListener('click', toggleFullscreen); elements.fullscreenBtn.addEventListener('click', toggleFullscreen);
document.querySelectorAll('.panel-close').forEach(btn => { document.querySelectorAll('.panel-close').forEach(btn => {

View File

@@ -362,6 +362,13 @@ body {
margin-bottom: var(--spacing-sm); margin-bottom: var(--spacing-sm);
} }
/* ===== 语言切换面板 ===== */
.language-panel {
bottom: calc(var(--spacing-xl) + 60px);
right: var(--spacing-xl);
width: 280px;
}
.caption-style-section .form-group label { .caption-style-section .form-group label {
font-size: 0.85rem; font-size: 0.85rem;
color: var(--text-muted); color: var(--text-muted);