Files
tuono/packages/router/src/components/Link.tsx
T

42 lines
1.0 KiB
TypeScript
Raw Normal View History

2024-06-16 11:23:02 +02:00
import * as React from 'react'
2024-07-11 21:43:38 +02:00
import { useRouter } from '../hooks/useRouter'
2024-05-11 15:08:49 +02:00
import type { AnchorHTMLAttributes, MouseEvent } from 'react'
import useRoute from '../hooks/useRoute'
import { useInView } from 'react-intersection-observer'
interface TuonoLinkProps {
preload?: boolean
}
2024-05-11 15:08:49 +02:00
export default function Link(
componentProps: AnchorHTMLAttributes<HTMLAnchorElement> & TuonoLinkProps,
2024-05-11 15:08:49 +02:00
): JSX.Element {
const { preload = true, ...props } = componentProps
2024-07-11 21:43:38 +02:00
const router = useRouter()
const route = useRoute(props.href)
const { ref } = useInView({
onChange(inView) {
if (inView && preload) route?.component.preload()
},
triggerOnce: true,
})
2024-07-11 21:43:38 +02:00
2024-05-11 15:08:49 +02:00
const handleTransition = (e: MouseEvent<HTMLAnchorElement>): void => {
e.preventDefault()
props.onClick?.(e)
2024-08-16 11:21:18 +02:00
if (props.href?.startsWith('#')) {
window.location.hash = props.href
return
}
2024-07-11 21:43:38 +02:00
router.push(props.href || '')
2024-05-11 15:08:49 +02:00
}
2024-07-11 21:43:38 +02:00
2024-05-11 15:08:49 +02:00
return (
<a {...props} ref={ref} onClick={handleTransition}>
2024-05-11 15:08:49 +02:00
{props.children}
</a>
)
}