feat(hydration): allow fine tuning of lazy hydration strategy triggers (#11530)

This commit is contained in:
Michael Brevard 2024-08-07 07:06:15 +03:00 committed by GitHub
parent 63689ed776
commit 261c8b111d
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
2 changed files with 23 additions and 26 deletions

View File

@ -15,35 +15,32 @@ export type HydrationStrategy = (
forEachElement: (cb: (el: Element) => any) => void,
) => (() => void) | void
export type HydrationStrategyFactory<Options = any> = (
export type HydrationStrategyFactory<Options> = (
options?: Options,
) => HydrationStrategy
export const hydrateOnIdle: HydrationStrategyFactory = () => hydrate => {
const id = requestIdleCallback(hydrate)
return () => cancelIdleCallback(id)
}
export const hydrateOnVisible: HydrationStrategyFactory<string | number> =
(margin = 0) =>
(hydrate, forEach) => {
const ob = new IntersectionObserver(
entries => {
for (const e of entries) {
if (!e.isIntersecting) continue
ob.disconnect()
hydrate()
break
}
},
{
rootMargin: isString(margin) ? margin : margin + 'px',
},
)
forEach(el => ob.observe(el))
return () => ob.disconnect()
export const hydrateOnIdle: HydrationStrategyFactory<number> =
(timeout = 10000) =>
hydrate => {
const id = requestIdleCallback(hydrate, { timeout })
return () => cancelIdleCallback(id)
}
export const hydrateOnVisible: HydrationStrategyFactory<
IntersectionObserverInit
> = opts => (hydrate, forEach) => {
const ob = new IntersectionObserver(entries => {
for (const e of entries) {
if (!e.isIntersecting) continue
ob.disconnect()
hydrate()
break
}
}, opts)
forEach(el => ob.observe(el))
return () => ob.disconnect()
}
export const hydrateOnMediaQuery: HydrationStrategyFactory<string> =
query => hydrate => {
if (query) {
@ -58,7 +55,7 @@ export const hydrateOnMediaQuery: HydrationStrategyFactory<string> =
}
export const hydrateOnInteraction: HydrationStrategyFactory<
string | string[]
keyof HTMLElementEventMap | Array<keyof HTMLElementEventMap>
> =
(interactions = []) =>
(hydrate, forEach) => {

View File

@ -35,7 +35,7 @@
const AsyncComp = defineAsyncComponent({
loader: () => Promise.resolve(Comp),
hydrate: hydrateOnVisible(rootMargin + 'px')
hydrate: hydrateOnVisible({rootMargin: rootMargin + 'px'})
})
createSSRApp({