diff --git a/packages/machines/combobox/src/combobox.connect.ts b/packages/machines/combobox/src/combobox.connect.ts index 54f20ce413..3fc3358f46 100644 --- a/packages/machines/combobox/src/combobox.connect.ts +++ b/packages/machines/combobox/src/combobox.connect.ts @@ -146,6 +146,16 @@ export function connect(state: State, send send(event.altKey ? "ALT_ARROW_UP" : "ARROW_UP") prevent = true }, + Home(event) { + const isCtrlKey = event.ctrlKey || event.metaKey + if (isCtrlKey) return + send({ type: "HOME", preventDefault: () => event.preventDefault() }) + }, + End(event) { + const isCtrlKey = event.ctrlKey || event.metaKey + if (isCtrlKey) return + send({ type: "END", preventDefault: () => event.preventDefault() }) + }, Enter() { send("ENTER") prevent = true diff --git a/packages/machines/combobox/src/combobox.machine.ts b/packages/machines/combobox/src/combobox.machine.ts index 2423bf5ba7..7d2a54ce2b 100644 --- a/packages/machines/combobox/src/combobox.machine.ts +++ b/packages/machines/combobox/src/combobox.machine.ts @@ -58,7 +58,7 @@ export function machine(ctx: UserDefinedContext = {}) { }, onEvent(ctx, evt) { - ctx.isKeyboardEvent = /(ARROW_UP|ARROW_DOWN)/.test(evt.type) + ctx.isKeyboardEvent = /(ARROW_UP|ARROW_DOWN|HOME|END)/.test(evt.type) }, watch: { @@ -185,6 +185,14 @@ export function machine(ctx: UserDefinedContext = {}) { actions: "focusPrevOption", }, ALT_ARROW_UP: "focused", + HOME: { + target: "interacting", + actions: ["focusFirstOption", "preventDefault"], + }, + END: { + target: "interacting", + actions: ["focusLastOption", "preventDefault"], + }, ENTER: [ { guard: and("isOptionFocused", "autoComplete"), @@ -237,6 +245,12 @@ export function machine(ctx: UserDefinedContext = {}) { activities: ["scrollOptionIntoView", "trackPointerDown", "computePlacement", "ariaHideOutside"], entry: "focusMatchingOption", on: { + HOME: { + actions: ["focusFirstOption", "preventDefault"], + }, + END: { + actions: ["focusLastOption", "preventDefault"], + }, ARROW_DOWN: [ { guard: and("autoComplete", "isLastOptionFocused"), @@ -561,6 +575,9 @@ export function machine(ctx: UserDefinedContext = {}) { removeLiveRegion(ctx) { ctx.liveRegion?.destroy() }, + preventDefault(_ctx, evt) { + evt.preventDefault() + }, setSectionLabel(ctx) { const label = dom.getClosestSectionLabel(ctx) if (!label) return