diff --git a/openless-all/app/src/components/Onboarding.tsx b/openless-all/app/src/components/Onboarding.tsx index b1466f4c..249f1ba6 100644 --- a/openless-all/app/src/components/Onboarding.tsx +++ b/openless-all/app/src/components/Onboarding.tsx @@ -220,12 +220,14 @@ function AndroidMicrophoneStep() { useEffect(() => { void refresh(); - const id = window.setInterval(refresh, 3000); + // issue #470:纯事件驱动,去掉高频轮询。窗口重新聚焦或重新可见时刷新(授权必经系统设置再切回)。 const onFocus = () => { void refresh(); }; + const onVisibility = () => { if (document.visibilityState === 'visible') void refresh(); }; window.addEventListener('focus', onFocus); + document.addEventListener('visibilitychange', onVisibility); return () => { - window.clearInterval(id); window.removeEventListener('focus', onFocus); + document.removeEventListener('visibilitychange', onVisibility); }; }, []); @@ -299,13 +301,15 @@ function DesktopOnboarding({ }; useEffect(() => { - refresh(); - const id = window.setInterval(refresh, 1000); - const onFocus = () => refresh(); + void refresh(); + // issue #470:纯事件驱动,去掉每秒轮询。授权必经系统设置 App,切回 OpenLess 必触发 focus/visibilitychange。 + const onFocus = () => { void refresh(); }; + const onVisibility = () => { if (document.visibilityState === 'visible') void refresh(); }; window.addEventListener('focus', onFocus); + document.addEventListener('visibilitychange', onVisibility); return () => { - window.clearInterval(id); window.removeEventListener('focus', onFocus); + document.removeEventListener('visibilitychange', onVisibility); if (refreshTimeoutRef.current) clearTimeout(refreshTimeoutRef.current); }; }, [requiresAccessibility]); @@ -318,6 +322,10 @@ function DesktopOnboarding({ } finally { setBusy(false); } + // issue #470:与麦克风路径对称——授权动作返回后立即刷新,并挂一次 800ms 兜底覆盖 app 内按钮发起的授予。 + void refresh(); + if (refreshTimeoutRef.current) clearTimeout(refreshTimeoutRef.current); + refreshTimeoutRef.current = window.setTimeout(refresh, 800); }; const onRequestMicrophone = async () => { diff --git a/openless-all/app/src/pages/settings/PermissionsSection.tsx b/openless-all/app/src/pages/settings/PermissionsSection.tsx index d59e2e14..dfc0a463 100644 --- a/openless-all/app/src/pages/settings/PermissionsSection.tsx +++ b/openless-all/app/src/pages/settings/PermissionsSection.tsx @@ -80,13 +80,11 @@ export function PermissionsSection() { refreshWindowsIme(); } refreshNetwork(); - const hotkeyId = platformCaps?.supportsDesktopHotkey === true - ? window.setInterval(refreshHotkey, 1000) - : undefined; + // issue #470:热键状态改为纯事件驱动,去掉每秒轮询,靠下方 focus/visibilitychange 刷新。 // 麦克风检查会短暂打开输入流,避免每秒探测导致隐私指示器频繁闪烁。 const permissionId = window.setInterval(refreshPermissions, 10000); const networkId = window.setInterval(refreshNetwork, 30000); - const onFocus = () => { + const refreshAll = () => { refreshPermissions(); if (platformCaps?.supportsDesktopHotkey === true) { refreshHotkey(); @@ -96,12 +94,15 @@ export function PermissionsSection() { } refreshNetwork(); }; + const onFocus = () => refreshAll(); + const onVisibility = () => { if (document.visibilityState === 'visible') refreshAll(); }; window.addEventListener('focus', onFocus); + document.addEventListener('visibilitychange', onVisibility); return () => { - if (hotkeyId !== undefined) window.clearInterval(hotkeyId); window.clearInterval(permissionId); window.clearInterval(networkId); window.removeEventListener('focus', onFocus); + document.removeEventListener('visibilitychange', onVisibility); }; }, [platformCaps?.platform, platformCaps?.supportsDesktopHotkey]);