mirror of
https://github.com/pewdiepie-archdaemon/odysseus.git
synced 2026-06-16 09:45:24 -04:00
Cookbook auto-fold: use IntersectionObserver to catch any scroll source
The scroll listener on .cookbook-body never fired — the user is likely scrolling inside the nested .hwfit-list (max-height:52vh) which doesn't bubble to its parent. IntersectionObserver fires whenever the Direct Download header crosses the viewport edge regardless of which container moved. Folds only when boundingClientRect.top < 0 (header pushed up past the top) so modal close / detach doesn't trigger it.
This commit is contained in:
+21
-17
@@ -1416,24 +1416,28 @@ function _wireTabEvents(body) {
|
||||
_setFolded(!folded);
|
||||
});
|
||||
// Auto-fold when the user scrolls past the Direct Download header.
|
||||
// Desktop scroll container is .cookbook-body; mobile is the modal
|
||||
// .modal-content. Walk up via .closest() to find whichever is
|
||||
// actually scrollable. Doesn't auto-unfold — chevron ▸ still
|
||||
// expands manually.
|
||||
const _scrollHost = dlFold.closest('.cookbook-body')
|
||||
|| dlFold.closest('#cookbook-modal .modal-content')
|
||||
|| dlFold.closest('.modal-content')
|
||||
|| document.scrollingElement
|
||||
|| document.body;
|
||||
const _onScroll = () => {
|
||||
if (dlFoldBody.style.display === 'none') return;
|
||||
const r = dlFold.getBoundingClientRect();
|
||||
const top = (_scrollHost && _scrollHost.getBoundingClientRect) ? _scrollHost.getBoundingClientRect().top : 0;
|
||||
if (r.bottom < top + 4) {
|
||||
_setFolded(true, /* persist */ false);
|
||||
// Use IntersectionObserver — fires whenever the header element
|
||||
// crosses the viewport edge, regardless of which scroll container
|
||||
// moved (cookbook-body, modal-content, hwfit-list, viewport, etc).
|
||||
// Doesn't auto-unfold; the chevron ▸ still expands manually.
|
||||
let _ioPrimed = false;
|
||||
const _io = new IntersectionObserver((entries) => {
|
||||
const entry = entries[0];
|
||||
if (!entry) return;
|
||||
// Skip the initial firing where the header is already in view.
|
||||
if (!_ioPrimed) {
|
||||
_ioPrimed = true;
|
||||
if (entry.isIntersecting) return;
|
||||
}
|
||||
};
|
||||
_scrollHost.addEventListener('scroll', _onScroll, { passive: true });
|
||||
if (entry.isIntersecting) return;
|
||||
// Only fold when scrolled ABOVE the viewport (not when the modal
|
||||
// closes / detaches under it). boundingClientRect.top < 0 means
|
||||
// the header was pushed off the top.
|
||||
if (entry.boundingClientRect.top >= 0) return;
|
||||
if (dlFoldBody.style.display === 'none') return;
|
||||
_setFolded(true, /* persist */ false);
|
||||
}, { threshold: 0 });
|
||||
_io.observe(dlFold);
|
||||
}
|
||||
const hfToggle = document.getElementById('cookbook-hf-latest-toggle');
|
||||
const hfArrow = document.getElementById('cookbook-hf-latest-arrow');
|
||||
|
||||
Reference in New Issue
Block a user