(feat): add hotkeys
Some checks failed
/ build-web (push) Successful in 7m53s
/ build-desktop (linux) (push) Successful in 12m24s
/ release (push) Has been cancelled
/ build-mobile (push) Has been cancelled

This commit is contained in:
Alois 2026-08-02 01:10:05 +02:00
commit 85633a1c81
Signed by: alois
SSH key fingerprint: SHA256:GBzT2DXvAuGV9XIV5W3WrzVpjU54FThmxHXdbz95J24
27 changed files with 1014 additions and 33 deletions

View file

@ -52,6 +52,12 @@ import Emoji, {
export const MAX_RENDERED_EMOJI_OPTIONS = 100;
export type InputController = {
focus: () => void;
hasFocus: () => boolean;
insertText: (text: string) => void;
};
export type InputProps = {
ref?: HTMLDivElement;
placeholder?: string;
@ -66,6 +72,8 @@ export type InputProps = {
className?: string;
emojiFrequencies?: Readonly<Record<string, number>>;
onEmojiSelect?: (shortcode: string) => void;
autoFocus?: boolean;
onControllerChange?: (controller: InputController | null) => void;
};
type InputStyle = CSSProperties & {
@ -353,8 +361,23 @@ export default function Input(props: InputProps) {
state,
parent: elementRef.current,
});
props.onControllerChange?.({
focus: () => viewRef.current?.contentDOM.focus({ preventScroll: true }),
hasFocus: () => viewRef.current?.hasFocus ?? false,
insertText: (text) => {
const editor = viewRef.current;
if (!editor) return;
editor.dispatch({
...editor.state.replaceSelection(text),
annotations: Transaction.userEvent.of("input.type"),
scrollIntoView: true,
});
},
});
if (props.autoFocus) viewRef.current.focus();
return () => {
props.onControllerChange?.(null);
viewRef.current?.destroy();
viewRef.current = undefined;
};