Skip to content

Commit 80d6667

Browse files
committed
feat: add keyboard shortcuts for nav sections
1 parent 94f6d65 commit 80d6667

File tree

3 files changed

+27
-3
lines changed

3 files changed

+27
-3
lines changed

src/components/Nav/Menu/index.tsx

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
1-
import { AnimatePresence, motion } from "framer-motion"
1+
import { motion } from "framer-motion"
22
import { Box, type BoxProps, Flex, Text } from "@chakra-ui/react"
33
import * as NavigationMenu from "@radix-ui/react-navigation-menu"
44

55
import { Button } from "@/components/Buttons"
66

7-
import { SECTION_LABELS } from "@/lib/constants"
7+
import { MAIN_NAV_ID, SECTION_LABELS } from "@/lib/constants"
88

99
import type { NavSections } from "../types"
1010

@@ -35,7 +35,7 @@ const Menu = ({ sections, ...props }: NavMenuProps) => {
3535
onValueChange={handleSectionChange}
3636
>
3737
<NavigationMenu.List asChild>
38-
<Flex as="ul" listStyleType="none">
38+
<Flex id={MAIN_NAV_ID} as="ul" listStyleType="none">
3939
{SECTION_LABELS.map((sectionKey) => {
4040
const { label, items } = sections[sectionKey]
4141
const isActive = activeSection === sectionKey

src/components/Nav/Menu/useNavMenu.ts

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
import { useState } from "react"
22
import type { MotionProps } from "framer-motion"
3+
import { useEventListener } from "@chakra-ui/react"
4+
5+
import { MAIN_NAV_ID, SECTION_LABELS } from "@/lib/constants"
36

47
import type { NavSectionKey, NavSections } from "../types"
58

@@ -11,6 +14,25 @@ export const useNavMenu = (sections: NavSections) => {
1114
const menuColors = useNavMenuColors()
1215
const [activeSection, setActiveSection] = useState<NavSectionKey | null>(null)
1316

17+
// Focus corresponding nav section when number keys pressed
18+
useEventListener("keydown", (event) => {
19+
if (!document || !event.key.match(/[1-9]/)) return
20+
if (event.target instanceof HTMLInputElement) return
21+
if (event.target instanceof HTMLTextAreaElement) return
22+
if (event.target instanceof HTMLSelectElement) return
23+
24+
const sectionIdx = parseInt(event.key) - 1
25+
if (sectionIdx >= SECTION_LABELS.length) return
26+
27+
const button = document.querySelector(
28+
`#${MAIN_NAV_ID} li:nth-of-type(${sectionIdx + 1}) button`
29+
)
30+
if (!button) return
31+
32+
event.preventDefault()
33+
;(button as HTMLButtonElement).focus()
34+
})
35+
1436
const getEnglishSectionName = (
1537
activeSection: string
1638
): NavSectionKey | null => {

src/lib/constants.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,3 +85,5 @@ export const SECTION_LABELS: NavSectionKey[] = [
8585
"participate",
8686
"research",
8787
]
88+
89+
export const MAIN_NAV_ID = "main-navigation"

0 commit comments

Comments
 (0)