From 00757da2f3a4e7795ce1ddf9b6656b25c7f826df Mon Sep 17 00:00:00 2001 From: Neil <4138956+nwparker@users.noreply.github.com> Date: Sat, 30 May 2026 01:54:34 -0700 Subject: [PATCH] perf: guard voice pane permission state without effect --- src/renderer/src/components/settings/VoicePane.tsx | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/src/renderer/src/components/settings/VoicePane.tsx b/src/renderer/src/components/settings/VoicePane.tsx index dd057108c8e..1dd5dc5f0b1 100644 --- a/src/renderer/src/components/settings/VoicePane.tsx +++ b/src/renderer/src/components/settings/VoicePane.tsx @@ -1,4 +1,4 @@ -import { useEffect, useRef, useState } from 'react' +import { useCallback, useEffect, useRef, useState } from 'react' import type { GlobalSettings } from '../../../../shared/types' import { getDefaultVoiceSettings } from '../../../../shared/constants' import type { SpeechModelManifest, SpeechModelState } from '../../../../shared/speech-types' @@ -34,11 +34,10 @@ export function VoicePane({ settings, updateSettings }: VoicePaneProps): React.J const [permissionPending, setPermissionPending] = useState(false) const mountedRef = useRef(true) - useEffect(() => { - mountedRef.current = true - return () => { - mountedRef.current = false - } + const handlePaneRef = useCallback((node: HTMLDivElement | null): void => { + // Why: the microphone permission prompt can resolve after Settings closes; + // the pane ref gives that completion a stale-write guard without an Effect. + mountedRef.current = node !== null }, []) useEffect(() => { @@ -116,7 +115,7 @@ export function VoicePane({ settings, updateSettings }: VoicePaneProps): React.J const selectedIsReady = selectedModelState?.status === 'ready' return ( -
+