From 1d8e8273743697fe00991b647ade04dd0913de03 Mon Sep 17 00:00:00 2001 From: kkfluous Date: Thu, 2 Apr 2026 00:05:42 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E5=9B=9E=E5=88=B0=E9=A1=B6=E9=83=A8?= =?UTF-8?q?=E6=8C=89=E9=92=AE=E7=94=A8=20IntersectionObserver=20=E6=A3=80?= =?UTF-8?q?=E6=B5=8B+scrollIntoView?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 顶部放哨兵元素,离开视口时显示回到顶部按钮 - 点击用 scrollIntoView 替代 window.scrollTo,兼容各种布局 Co-Authored-By: Claude Opus 4.6 (1M context) --- src/modules/mileage/MonitoringView.tsx | 21 +++++++++++++-------- 1 file changed, 13 insertions(+), 8 deletions(-) diff --git a/src/modules/mileage/MonitoringView.tsx b/src/modules/mileage/MonitoringView.tsx index 8912048..2a8d688 100644 --- a/src/modules/mileage/MonitoringView.tsx +++ b/src/modules/mileage/MonitoringView.tsx @@ -196,18 +196,20 @@ export default function MonitoringView() { return () => observer.disconnect(); }, []); - // 回到顶部按钮 + // 回到顶部按钮:用 IntersectionObserver 检测顶部哨兵是否离开视口 + const topSentinelRef = useRef(null); useEffect(() => { - const handleScroll = () => { - const scrollY = window.scrollY || document.documentElement.scrollTop; - setShowBackToTop(scrollY > 400); - }; - window.addEventListener('scroll', handleScroll, { passive: true }); - return () => window.removeEventListener('scroll', handleScroll); + const el = topSentinelRef.current; + if (!el) return; + const observer = new IntersectionObserver( + ([entry]) => setShowBackToTop(!entry.isIntersecting), + ); + observer.observe(el); + return () => observer.disconnect(); }, []); const scrollToTop = () => { - window.scrollTo({ top: 0, behavior: 'smooth' }); + topSentinelRef.current?.scrollIntoView({ behavior: 'smooth' }); }; const filteredVehicles = vehicles; @@ -228,6 +230,9 @@ export default function MonitoringView() { return ( <> + {/* 顶部哨兵:离开视口时显示回到顶部按钮 */} +
+ {/* Fullscreen Landscape View Overlay */} {isFullscreen && (