Don't select <Input/> text when focus is due to window focus

Closes https://feedback.yaak.app/p/url-input-auto-selects-all-text-when-regaining-focus-after
This commit is contained in:
Gregory Schier
2025-05-12 22:19:16 -07:00
parent 81e78ef24c
commit 417a02744b
2 changed files with 28 additions and 14 deletions
+19 -3
View File
@@ -13,6 +13,7 @@ import {
} from 'react'; } from 'react';
import { useIsEncryptionEnabled } from '../../hooks/useIsEncryptionEnabled'; import { useIsEncryptionEnabled } from '../../hooks/useIsEncryptionEnabled';
import { useStateWithDeps } from '../../hooks/useStateWithDeps'; import { useStateWithDeps } from '../../hooks/useStateWithDeps';
import { copyToClipboard } from '../../lib/copy';
import { import {
analyzeTemplate, analyzeTemplate,
convertTemplateToInsecure, convertTemplateToInsecure,
@@ -30,7 +31,6 @@ import { Icon } from './Icon';
import { IconButton } from './IconButton'; import { IconButton } from './IconButton';
import { Label } from './Label'; import { Label } from './Label';
import { HStack } from './Stacks'; import { HStack } from './Stacks';
import { copyToClipboard } from '../../lib/copy';
export type InputProps = Pick< export type InputProps = Pick<
EditorProps, EditorProps,
@@ -127,13 +127,29 @@ const BaseInput = forwardRef<EditorView, InputProps>(function InputBase(
useImperativeHandle<EditorView | null, EditorView | null>(ref, () => editorRef.current); useImperativeHandle<EditorView | null, EditorView | null>(ref, () => editorRef.current);
const lastWindowFocus = useRef<number>(0);
useEffect(() => {
const fn = () => (lastWindowFocus.current = Date.now());
window.addEventListener('focus', fn);
return () => {
window.removeEventListener('focus', fn);
};
}, []);
const handleFocus = useCallback(() => { const handleFocus = useCallback(() => {
if (readOnly) return; if (readOnly) return;
setFocused(true);
// Select all text on focus // Select all text of input when it's focused to match standard browser behavior.
// This should not, however, select when the input is focused due to a window focus event, so
// we handle that case as well.
const windowJustFocused = Date.now() - lastWindowFocus.current < 200;
if (!windowJustFocused) {
editorRef.current?.dispatch({ editorRef.current?.dispatch({
selection: { anchor: 0, head: editorRef.current.state.doc.length }, selection: { anchor: 0, head: editorRef.current.state.doc.length },
}); });
}
setFocused(true);
onFocus?.(); onFocus?.();
}, [onFocus, readOnly]); }, [onFocus, readOnly]);
+5 -7
View File
@@ -5,15 +5,13 @@ export function useWindowFocus() {
const [visible, setVisible] = useState(true); const [visible, setVisible] = useState(true);
useEffect(() => { useEffect(() => {
let unsub: undefined | (() => void) = undefined; const unlisten = getCurrentWebviewWindow().onFocusChanged((e) => {
getCurrentWebviewWindow()
.onFocusChanged((e) => {
setVisible(e.payload); setVisible(e.payload);
})
.then((fn) => {
unsub = fn;
}); });
return () => unsub?.();
return () => {
unlisten.then((fn) => fn());
};
}, []); }, []);
return visible; return visible;