All checks were successful
Build Docker Image / build (push) Successful in 4m41s
- Dynamic top positioning based on scrollY - Chevron inside SearchBar for expand/collapse - All layers position:fixed with calculated offsets
68 lines
1.8 KiB
TypeScript
68 lines
1.8 KiB
TypeScript
/**
|
|
* Composable for smooth header collapse on scroll
|
|
* Returns pixel positions for all fixed layers
|
|
*/
|
|
export const useScrollCollapse = (headerHeight = 112, searchBarHeight = 48) => {
|
|
const scrollY = ref(0)
|
|
|
|
// Layer positions in pixels
|
|
// Layers 1+2 (MainNav + SubNav): slide up as user scrolls
|
|
const headerOffset = computed(() => -Math.min(scrollY.value, headerHeight))
|
|
|
|
// Layer 3 (SearchBar): slides down to top:0
|
|
const searchBarTop = computed(() => Math.max(0, headerHeight - scrollY.value))
|
|
|
|
// Layer 4 (Map): follows SearchBar, minimum is searchBarHeight
|
|
const mapTop = computed(() => Math.max(searchBarHeight, headerHeight + searchBarHeight - scrollY.value))
|
|
|
|
// Content padding-top
|
|
const contentPaddingTop = computed(() => Math.max(searchBarHeight, headerHeight + searchBarHeight - scrollY.value))
|
|
|
|
// Is header fully collapsed?
|
|
const isCollapsed = computed(() => scrollY.value >= headerHeight)
|
|
|
|
// Expand - scroll to top
|
|
const expand = () => {
|
|
if (import.meta.client) {
|
|
window.scrollTo({ top: 0, behavior: 'smooth' })
|
|
}
|
|
}
|
|
|
|
// Collapse - scroll down to hide header
|
|
const collapse = () => {
|
|
if (import.meta.client) {
|
|
window.scrollTo({ top: headerHeight, behavior: 'smooth' })
|
|
}
|
|
}
|
|
|
|
const onScroll = () => {
|
|
if (import.meta.client) {
|
|
scrollY.value = window.scrollY
|
|
}
|
|
}
|
|
|
|
onMounted(() => {
|
|
if (import.meta.client) {
|
|
window.addEventListener('scroll', onScroll, { passive: true })
|
|
onScroll() // Initial value
|
|
}
|
|
})
|
|
|
|
onUnmounted(() => {
|
|
if (import.meta.client) {
|
|
window.removeEventListener('scroll', onScroll)
|
|
}
|
|
})
|
|
|
|
return {
|
|
scrollY: readonly(scrollY),
|
|
headerOffset,
|
|
searchBarTop,
|
|
mapTop,
|
|
contentPaddingTop,
|
|
isCollapsed,
|
|
expand,
|
|
collapse
|
|
}
|
|
}
|