yanghao 1 ヶ月 前
コミット
a7e2d65f01
3 ファイル変更50 行追加76 行削除
  1. 2 2
      src/components/layout/AppFooter.vue
  2. 1 1
      src/views/ContactView.vue
  3. 47 73
      src/views/SolutionsView.vue

+ 2 - 2
src/components/layout/AppFooter.vue

@@ -75,12 +75,12 @@ const links = {
       <div class="muted" style="display: flex; gap: 15px">
         <div style="display: flex; align-items: center; gap: 6px">
           <Icon icon="ri:phone-fill" width="20" height="20" />
-          <span>400-000-0000</span>
+          <span>0546-608-1888</span>
         </div>
 
         <div style="display: flex; align-items: center; gap: 6px">
           <Icon icon="ri:mail-fill" width="20" height="20" />
-          <span>kerui@deepOil.com</span>
+          <span>wubj@keruigroup.com</span>
         </div>
       </div>
     </div>

+ 1 - 1
src/views/ContactView.vue

@@ -28,7 +28,7 @@ function submit() {
       <div class="container grid contactGrid">
         <div class="card card-pad">
           <div class="blockTitle">联系方式</div>
-          <div class="muted">热线:400-000-0000</div>
+          <div class="muted">热线:0546-608-1888</div>
           <div class="muted">邮箱:wubj@keruigroup.com</div>
           <div class="muted">地址:山东省东营市东营区南二路233号</div>
           <div class="divider blockDivider"></div>

+ 47 - 73
src/views/SolutionsView.vue

@@ -5,7 +5,6 @@ import { onBeforeUnmount, onMounted, ref } from "vue";
 import platformCover from "../assets/images/pbg.png?url";
 import equipmentCover from "../assets/images/case2.png?url";
 import productionCover from "../assets/images/sence2.jpg?url";
-import qhseCover from "../assets/images/sence3.png?url";
 
 const activeTab = ref("platform");
 const tabBarRef = ref(null);
@@ -131,7 +130,37 @@ function scrollToTab(key) {
   });
 }
 
-let observer = null;
+let scrollRafId = 0;
+let isScrollListenerBound = false;
+
+function updateActiveTabFromScroll() {
+  const offset = headerOffsetPx();
+  let bestKey = pillars[0]?.key || activeTab.value;
+  let bestTop = Number.NEGATIVE_INFINITY;
+
+  for (const p of pillars) {
+    const el = document.getElementById(`product-${p.key}`);
+    if (!el) continue;
+
+    const top = el.getBoundingClientRect().top - offset;
+
+    // Pick the last section whose top has crossed the sticky header+tab bar.
+    if (top <= 1 && top > bestTop) {
+      bestTop = top;
+      bestKey = p.key;
+    }
+  }
+
+  if (bestKey && activeTab.value !== bestKey) activeTab.value = bestKey;
+}
+
+function onWindowScrollOrResize() {
+  if (scrollRafId) return;
+  scrollRafId = window.requestAnimationFrame(() => {
+    scrollRafId = 0;
+    updateActiveTabFromScroll();
+  });
+}
 
 const currentImageIndex = ref({
   platform: 0,
@@ -183,75 +212,37 @@ const goToImageSlide = (key, index, totalItems) => {
   startImageCarousel(key, totalItems);
 };
 
-function updateActiveTab() {
-  const sections = pillars
-    .map((p) => document.getElementById(`product-${p.key}`))
-    .filter(Boolean);
-  const offset = headerOffsetPx();
-
-  const scrollPos = window.scrollY + offset;
-
-  let currentSection = null;
-  for (const section of sections) {
-    const rect = section.getBoundingClientRect();
-    if (rect.top <= 100) {
-      currentSection = section;
-    } else {
-      break;
-    }
-  }
-
-  if (currentSection) {
-    const key = currentSection.id.replace("product-", "");
-    if (activeTab.value !== key) {
-      activeTab.value = key;
-    }
-  }
-}
-
 onMounted(() => {
-  const offset = headerOffsetPx();
-  observer = new IntersectionObserver(
-    (entries) => {
-      const visible = entries
-        .filter((e) => e.isIntersecting)
-        .sort(
-          (a, b) => (b.intersectionRatio || 0) - (a.intersectionRatio || 0),
-        )[0];
-      if (visible?.target?.id)
-        activeTab.value = visible.target.id.replace("product-", "");
-    },
-    {
-      root: null,
-      threshold: [0.3, 0.5, 0.7],
-      rootMargin: `-${offset}px 0px -40% 0px`,
-    },
-  );
-
-  for (const p of pillars) {
-    const el = document.getElementById(`product-${p.key}`);
-    if (el) observer.observe(el);
+  if (!isScrollListenerBound) {
+    window.addEventListener("scroll", onWindowScrollOrResize, { passive: true });
+    window.addEventListener("resize", onWindowScrollOrResize, { passive: true });
+    isScrollListenerBound = true;
   }
 
+  // Ensure initial highlight is correct even before the first scroll event.
+  updateActiveTabFromScroll();
+
   for (const p of pillars) {
     if (currentImageIndex.value[p.key] === undefined)
       currentImageIndex.value[p.key] = 0;
     startImageCarousel(p.key, p.items?.length || 0);
   }
-
-  window.addEventListener("scroll", updateActiveTab, { passive: true });
-  updateActiveTab();
 });
 
 onBeforeUnmount(() => {
-  observer?.disconnect?.();
-  observer = null;
+  if (isScrollListenerBound) {
+    window.removeEventListener("scroll", onWindowScrollOrResize);
+    window.removeEventListener("resize", onWindowScrollOrResize);
+    isScrollListenerBound = false;
+  }
+  if (scrollRafId) {
+    window.cancelAnimationFrame(scrollRafId);
+    scrollRafId = 0;
+  }
 
   for (const key of Object.keys(imageTimers.value || {})) {
     stopImageCarousel(key);
   }
-
-  window.removeEventListener("scroll", updateActiveTab);
 });
 </script>
 
@@ -1051,23 +1042,6 @@ onBeforeUnmount(() => {
   }
 }
 
-@media (prefers-reduced-motion: reduce) {
-  .tabBtn {
-    transition: none !important;
-    transform: none !important;
-  }
-
-  .tabText {
-    transition: none !important;
-  }
-
-  .platformFeature,
-  .tabFeatureRow {
-    transition: none !important;
-    transform: none !important;
-  }
-}
-
 .imageCarouselWrapper {
   position: relative;
   display: flex;