This commit is contained in:
@@ -30,14 +30,13 @@
|
|||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
(function (doc, win)
|
(function (doc, win)
|
||||||
{
|
{
|
||||||
|
|
||||||
var docEl = doc.documentElement;
|
var docEl = doc.documentElement;
|
||||||
var resizeEvt = 'orientationchange' in window ? 'orientationchange' : 'resize';
|
var resizeEvt = 'orientationchange' in window ? 'orientationchange' : 'resize';
|
||||||
var designWidth = 2560;
|
var designWidth = 2560;
|
||||||
var designRemPx = 100;
|
var designRemPx = 100;
|
||||||
function setRootFontSize ()
|
function setRootFontSize ()
|
||||||
{
|
{
|
||||||
console.log('触发')
|
|
||||||
var clientWidth = docEl.clientWidth;
|
var clientWidth = docEl.clientWidth;
|
||||||
if (!clientWidth) return;
|
if (!clientWidth) return;
|
||||||
var fontSize = (clientWidth / designWidth) * designRemPx;
|
var fontSize = (clientWidth / designWidth) * designRemPx;
|
||||||
@@ -55,32 +54,26 @@
|
|||||||
{block name="main"}
|
{block name="main"}
|
||||||
{notempty name="data.top_focus_images"}
|
{notempty name="data.top_focus_images"}
|
||||||
<div class="swiper-container auto-swiper-container" style="margin-top:60px;">
|
<div class="swiper-container auto-swiper-container" style="margin-top:60px;">
|
||||||
{eq name=":cookie('think_lang')" value="en-us"}
|
<div class="swiper-wrapper">
|
||||||
<div class="swiper-wrapper">
|
{volist name="data.top_focus_images" id="tfi"}
|
||||||
{volist name="data.top_focus_images" id="tfi"}
|
<div class="swiper-slide auto-swiper-slide">
|
||||||
<a class="swiper-slide auto-swiper-slide" href="{$tfi.link}">
|
<div class="swiper-container-texts" style="color:#fff">
|
||||||
<img src="{$tfi.image}" alt="{$tfi.title}" />
|
<div class="swiper-container-texts-t">{$tfi.title}</div>
|
||||||
</a>
|
<div class="swiper-container-texts-p">{$tfi.desc||raw|htmlspecialchars_decode}</div>
|
||||||
{/volist}
|
<div class="swiper-container-texts-img">
|
||||||
</div>
|
<a href="{$tfi.link}">
|
||||||
{else/}
|
{eq name=":cookie('think_lang')" value="en-us"}
|
||||||
<div class="swiper-wrapper">
|
<img src="__IMAGES__/topic_laptop/eljgd.png" alt="" >
|
||||||
{volist name="data.top_focus_images" id="tfi"}
|
{else/}
|
||||||
<div class="swiper-slide auto-swiper-slide">
|
<img src="__IMAGES__/topic_laptop/ljgd.png" alt="" >
|
||||||
<div class="swiper-container-texts" style="color:#fff">
|
{/eq}
|
||||||
<div class="swiper-container-texts-t">{$tfi.title}</div>
|
</a>
|
||||||
<div class="swiper-container-texts-p">{$tfi.desc||raw|htmlspecialchars_decode}</div>
|
|
||||||
<div class="swiper-container-texts-img">
|
|
||||||
<a href="{$tfi.link}">
|
|
||||||
<img src="__IMAGES__/topic_laptop/ljgd.png" alt="" loading="lazy" >
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
<img src="{$tfi.image}" alt="{$tfi.title}" loading="lazy" />
|
|
||||||
</div>
|
</div>
|
||||||
{/volist}
|
<img src="{$tfi.image}" alt="{$tfi.title}" />
|
||||||
</div>
|
</div>
|
||||||
{/eq}
|
{/volist}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{/notempty}
|
{/notempty}
|
||||||
{notempty name="data.perf"}
|
{notempty name="data.perf"}
|
||||||
@@ -214,7 +207,6 @@
|
|||||||
<img src="{$gpu_first_section.extra_image|default=''}" alt="" loading="lazy" >
|
<img src="{$gpu_first_section.extra_image|default=''}" alt="" loading="lazy" >
|
||||||
</div>
|
</div>
|
||||||
{/eq}
|
{/eq}
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
<div class="readon-img-box opacity0" data-order="11">
|
<div class="readon-img-box opacity0" data-order="11">
|
||||||
{volist name="data.gpu" id="go"}
|
{volist name="data.gpu" id="go"}
|
||||||
@@ -275,7 +267,6 @@
|
|||||||
</div>
|
</div>
|
||||||
{notempty name="data.ram"}
|
{notempty name="data.ram"}
|
||||||
<div class="wift" >
|
<div class="wift" >
|
||||||
|
|
||||||
<div class="wift-bg" style="background: url('{$data.ram.image}');background-size:100% auto;">
|
<div class="wift-bg" style="background: url('{$data.ram.image}');background-size:100% auto;">
|
||||||
<div class="wift-test">
|
<div class="wift-test">
|
||||||
<div class="wift-t opacity0" data-order="12">{$data.ram.title|raw}</div>
|
<div class="wift-t opacity0" data-order="12">{$data.ram.title|raw}</div>
|
||||||
@@ -290,7 +281,6 @@
|
|||||||
<div class="wift-bg-img opacity0" data-order="14">
|
<div class="wift-bg-img opacity0" data-order="14">
|
||||||
{$data.ram.desc|raw}
|
{$data.ram.desc|raw}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{/notempty}
|
{/notempty}
|
||||||
@@ -299,19 +289,18 @@
|
|||||||
{assign name="hard_drive_first" value=":array_shift($data.hard_drive)"/}
|
{assign name="hard_drive_first" value=":array_shift($data.hard_drive)"/}
|
||||||
<div class="m2-bg" style="background: url('{$hard_drive_first.image|default=\'\'}');background-size:100% auto">
|
<div class="m2-bg" style="background: url('{$hard_drive_first.image|default=\'\'}');background-size:100% auto">
|
||||||
{eq name=":cookie('think_lang')" value="en-us"}
|
{eq name=":cookie('think_lang')" value="en-us"}
|
||||||
<div class="m2-bg-t1 opacity0" data-order="15">{$hard_drive_first.title|default=''|raw}</div>
|
<div class="m2-bg-t1 opacity0" data-order="15">{$hard_drive_first.title|default=''|raw}</div>
|
||||||
{else/}
|
{else/}
|
||||||
<div class="m2-bg-t opacity0" data-order="15">{$hard_drive_first.title|default=''|raw}</div>
|
<div class="m2-bg-t opacity0" data-order="15">{$hard_drive_first.title|default=''|raw}</div>
|
||||||
{/eq}
|
{/eq}
|
||||||
<div class="m2-img-box opacity0" data-order="16">
|
<div class="m2-img-box opacity0" data-order="16">
|
||||||
{volist name="data.hard_drive" id="ho"}
|
{volist name="data.hard_drive" id="ho"}
|
||||||
<img src="{$ho.image}" alt="" loading="lazy" >
|
<img src="{$ho.image}" alt="" loading="lazy" >
|
||||||
{/volist}
|
{/volist}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{/notempty}
|
{/notempty}
|
||||||
|
|
||||||
<div class="fs">
|
<div class="fs">
|
||||||
{notempty name="data.cooling_system"}
|
{notempty name="data.cooling_system"}
|
||||||
{notempty name="$data.cooling_system.0"}
|
{notempty name="$data.cooling_system.0"}
|
||||||
@@ -332,13 +321,13 @@
|
|||||||
</video>
|
</video>
|
||||||
<div class="fs-ts">{$data.cooling_system.0.desc|raw}</div>
|
<div class="fs-ts">{$data.cooling_system.0.desc|raw}</div>
|
||||||
{/notempty}
|
{/notempty}
|
||||||
<div class="fs-box-img opacity0" data-order="18">
|
<div class="fs-box-img" >
|
||||||
<div class="fs-h-img">
|
<div class="fs-h-img">
|
||||||
{notempty name="data.cooling_system.1"}<img src="{$data.cooling_system.1.image}" alt="" loading="lazy" >{/notempty}
|
{notempty name="data.cooling_system.1"}<img src="{$data.cooling_system.1.image}" alt="" >{/notempty}
|
||||||
{notempty name="data.cooling_system.2"}<img src="{$data.cooling_system.2.image}" alt="" loading="lazy" >{/notempty}
|
{notempty name="data.cooling_system.2"}<img src="{$data.cooling_system.2.image}" alt="" >{/notempty}
|
||||||
</div>
|
</div>
|
||||||
<div class="fs-b-img" style="min-height: 20px;">
|
<div class="fs-b-img" style="min-height: 20px;">
|
||||||
{notempty name="data.cooling_system.3"}<img src="{$data.cooling_system.3.image}" alt="" loading="lazy" >{/notempty}
|
{notempty name="data.cooling_system.3"}<img src="{$data.cooling_system.3.image}" alt="" >{/notempty}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -346,10 +335,10 @@
|
|||||||
{/notempty}
|
{/notempty}
|
||||||
{notempty name="data.apps"}
|
{notempty name="data.apps"}
|
||||||
<div class="xn">
|
<div class="xn">
|
||||||
<div class="xn-t opacity0" data-order="19">{$data.apps.title|default=''}</div>
|
<div class="xn-t" >{$data.apps.title|default=''}</div>
|
||||||
<div class="xn-container">
|
<div class="xn-container">
|
||||||
<div class="xn-image-section">
|
<div class="xn-image-section">
|
||||||
<img src="{$data.apps.image|default=''}" alt="" class="zoom-image first-image" loading="lazy">
|
<img src="{$data.apps.image|default=''}" alt="" class="zoom-image first-image" >
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="xn-p">{$data.apps.desc|default=''|raw}</div>
|
<div class="xn-p">{$data.apps.desc|default=''|raw}</div>
|
||||||
@@ -363,23 +352,19 @@
|
|||||||
<div class="ips-t">{$soft_light_first.title|raw}</div>
|
<div class="ips-t">{$soft_light_first.title|raw}</div>
|
||||||
<div class="ips-p">{$soft_light_first.short_title|raw}</div>
|
<div class="ips-p">{$soft_light_first.short_title|raw}</div>
|
||||||
{/notempty}
|
{/notempty}
|
||||||
|
|
||||||
|
|
||||||
{eq name=":cookie('think_lang')" value="en-us"}
|
{eq name=":cookie('think_lang')" value="en-us"}
|
||||||
<div class="ips-img1 opacity0" data-order="21">
|
<div class="ips-img1 opacity0" data-order="21">
|
||||||
{volist name="data.screen_soft_light" id="so"}
|
{volist name="data.screen_soft_light" id="so"}
|
||||||
<img src="{$so.image}" alt="" loading="lazy" >
|
<img src="{$so.image}" alt="" loading="lazy" >
|
||||||
{/volist}
|
{/volist}
|
||||||
</div>
|
</div>
|
||||||
{else/}
|
{else/}
|
||||||
<div class="ips-img opacity0" data-order="21">
|
<div class="ips-img opacity0" data-order="21">
|
||||||
{volist name="data.screen_soft_light" id="so"}
|
{volist name="data.screen_soft_light" id="so"}
|
||||||
<img src="{$so.image}" alt="" loading="lazy" >
|
<img src="{$so.image}" alt="" loading="lazy" >
|
||||||
{/volist}
|
{/volist}
|
||||||
</div>
|
</div>
|
||||||
{/eq}
|
{/eq}
|
||||||
|
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{/notempty}
|
{/notempty}
|
||||||
@@ -506,11 +491,11 @@
|
|||||||
{volist name="data.scene_focus_images" id="so"}
|
{volist name="data.scene_focus_images" id="so"}
|
||||||
<div class="carousel-text {if $key == 0}active{/if}" data-index="{$key}" loading="lazy" >
|
<div class="carousel-text {if $key == 0}active{/if}" data-index="{$key}" loading="lazy" >
|
||||||
{eq name=":cookie('think_lang')" value="en-us"}
|
{eq name=":cookie('think_lang')" value="en-us"}
|
||||||
<div class="carousel-text-t1">{$so.title}</div>
|
<div class="carousel-text-t1">{$so.title}</div>
|
||||||
<div class="carousel-text-p1">{$so.short_title}</div>
|
<div class="carousel-text-p1">{$so.short_title}</div>
|
||||||
{else/}
|
{else/}
|
||||||
<div class="carousel-text-t">{$so.title}</div>
|
<div class="carousel-text-t">{$so.title}</div>
|
||||||
<div class="carousel-text-p">{$so.short_title}</div>
|
<div class="carousel-text-p">{$so.short_title}</div>
|
||||||
{/eq}
|
{/eq}
|
||||||
</div>
|
</div>
|
||||||
{/volist}
|
{/volist}
|
||||||
@@ -1260,7 +1245,6 @@
|
|||||||
const tabT = document.querySelectorAll('.tab-t');
|
const tabT = document.querySelectorAll('.tab-t');
|
||||||
const indicator = document.querySelector('.tab-indicator');
|
const indicator = document.querySelector('.tab-indicator');
|
||||||
const securityVideo = document.getElementById('securityVideo');
|
const securityVideo = document.getElementById('securityVideo');
|
||||||
console.log(tabT,'=========tabT=============')
|
|
||||||
let prevIndex = 0;
|
let prevIndex = 0;
|
||||||
const tabRects = [];
|
const tabRects = [];
|
||||||
|
|
||||||
@@ -1355,265 +1339,162 @@
|
|||||||
resetVideo();
|
resetVideo();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
document.addEventListener('DOMContentLoaded', () => {
|
||||||
|
// 1. 获取元素
|
||||||
|
const carouselImgs = document.querySelector('.carousel-imgs');
|
||||||
|
const imgItems = document.querySelectorAll('.carousel-img');
|
||||||
|
const leftArrow = document.querySelector('.arrow-left');
|
||||||
|
const rightArrow = document.querySelector('.arrow-right');
|
||||||
|
const textItems = document.querySelectorAll('.carousel-text');
|
||||||
|
const carouselContainer = document.querySelector('.carousel-container');
|
||||||
|
|
||||||
// document.addEventListener('DOMContentLoaded', () => {
|
// 容错处理
|
||||||
// // 1. 获取元素(匹配你的结构)
|
if (!carouselImgs || imgItems.length === 0) {
|
||||||
// const carouselImgs = document.querySelector('.carousel-imgs');
|
console.warn('轮播图片为空,初始化终止');
|
||||||
// const imgItems = document.querySelectorAll('.carousel-img');
|
return;
|
||||||
// const leftArrow = document.querySelector('.arrow-left');
|
|
||||||
// const rightArrow = document.querySelector('.arrow-right');
|
|
||||||
// const textItems = document.querySelectorAll('.carousel-text');
|
|
||||||
// const carouselContainer = document.querySelector('.carousel-container');
|
|
||||||
|
|
||||||
// // 容错处理
|
|
||||||
// if (!carouselImgs || imgItems.length === 0) {
|
|
||||||
// console.warn('轮播图片为空,初始化终止');
|
|
||||||
// return;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// // 2. 核心变量(仅索引,无尺寸计算)
|
|
||||||
// const imgCount = imgItems.length;
|
|
||||||
// let currentIndex = 0;
|
|
||||||
// let autoPlayTimer = null;
|
|
||||||
// let isResizing = false; // 缩放锁,避免重复触发
|
|
||||||
|
|
||||||
// // 3. 切换到指定索引(核心:百分比偏移,无尺寸计算)
|
|
||||||
// const goToIndex = (index) => {
|
|
||||||
// // 边界处理
|
|
||||||
// if (index < 0) index = imgCount - 1;
|
|
||||||
// if (index >= imgCount) index = 0;
|
|
||||||
|
|
||||||
// // 关键:用百分比偏移,彻底避开rem/px计算误差
|
|
||||||
// carouselImgs.style.transform = `translateX(-${index * 100}%)`;
|
|
||||||
// currentIndex = index;
|
|
||||||
|
|
||||||
// // 更新文字激活态
|
|
||||||
// textItems.forEach((item, idx) => {
|
|
||||||
// item.classList.toggle('active', idx === currentIndex);
|
|
||||||
// });
|
|
||||||
// };
|
|
||||||
|
|
||||||
// // 4. 左右切换逻辑
|
|
||||||
// const slideNext = () => goToIndex(currentIndex + 1);
|
|
||||||
// const slidePrev = () => goToIndex(currentIndex - 1);
|
|
||||||
|
|
||||||
// // 5. 自动播放逻辑
|
|
||||||
// const autoPlay = () => {
|
|
||||||
// clearInterval(autoPlayTimer);
|
|
||||||
// autoPlayTimer = setInterval(slideNext, 3000); // 3秒切换,可改
|
|
||||||
// };
|
|
||||||
|
|
||||||
// // 6. 绑定事件
|
|
||||||
// // 箭头点击
|
|
||||||
// leftArrow?.addEventListener('click', () => {
|
|
||||||
// slidePrev();
|
|
||||||
// autoPlay(); // 点击后重启自动播放
|
|
||||||
// });
|
|
||||||
// rightArrow?.addEventListener('click', () => {
|
|
||||||
// slideNext();
|
|
||||||
// autoPlay();
|
|
||||||
// });
|
|
||||||
|
|
||||||
// // 文字指示器点击
|
|
||||||
// textItems.forEach((item, idx) => {
|
|
||||||
// item.addEventListener('click', () => {
|
|
||||||
// goToIndex(idx);
|
|
||||||
// autoPlay();
|
|
||||||
// });
|
|
||||||
// });
|
|
||||||
|
|
||||||
// // 鼠标悬停暂停
|
|
||||||
// carouselContainer?.addEventListener('mouseenter', () => {
|
|
||||||
// clearInterval(autoPlayTimer);
|
|
||||||
// });
|
|
||||||
// carouselContainer?.addEventListener('mouseleave', autoPlay);
|
|
||||||
|
|
||||||
// // 7. 窗口缩放响应(核心:仅重新定位,无计算)
|
|
||||||
// const handleResize = () => {
|
|
||||||
// if (isResizing) return;
|
|
||||||
// isResizing = true;
|
|
||||||
|
|
||||||
// // 缩放时直接重新定位当前索引(百分比偏移无需计算)
|
|
||||||
// goToIndex(currentIndex);
|
|
||||||
|
|
||||||
// // 解锁
|
|
||||||
// setTimeout(() => {
|
|
||||||
// isResizing = false;
|
|
||||||
// }, 100);
|
|
||||||
// };
|
|
||||||
|
|
||||||
// // 防抖监听窗口缩放
|
|
||||||
// let resizeTimer;
|
|
||||||
// window.addEventListener('resize', () => {
|
|
||||||
// clearTimeout(resizeTimer);
|
|
||||||
// resizeTimer = setTimeout(handleResize, 150);
|
|
||||||
// });
|
|
||||||
|
|
||||||
// // 8. 初始化
|
|
||||||
// goToIndex(0); // 初始定位到第一张
|
|
||||||
// autoPlay(); // 启动自动播放
|
|
||||||
|
|
||||||
// // 9. 页面卸载清理定时器
|
|
||||||
// window.addEventListener('beforeunload', () => {
|
|
||||||
// clearInterval(autoPlayTimer);
|
|
||||||
// });
|
|
||||||
// });
|
|
||||||
document.addEventListener('DOMContentLoaded', () => {
|
|
||||||
// 1. 获取元素
|
|
||||||
const carouselImgs = document.querySelector('.carousel-imgs');
|
|
||||||
const imgItems = document.querySelectorAll('.carousel-img');
|
|
||||||
const leftArrow = document.querySelector('.arrow-left');
|
|
||||||
const rightArrow = document.querySelector('.arrow-right');
|
|
||||||
const textItems = document.querySelectorAll('.carousel-text');
|
|
||||||
const carouselContainer = document.querySelector('.carousel-container');
|
|
||||||
|
|
||||||
// 容错处理
|
|
||||||
if (!carouselImgs || imgItems.length === 0) {
|
|
||||||
console.warn('轮播图片为空,初始化终止');
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// 2. 核心配置
|
|
||||||
const imgCount = imgItems.length; // 真实图片数量(如3张:1/2/3)
|
|
||||||
let currentRealIndex = 0; // 真实图片索引(0=1, 1=2, 2=3)
|
|
||||||
let isTransitioning = false; // 过渡锁,防止动画冲突
|
|
||||||
const transitionDuration = 500; // 过渡时长(ms),需与CSS一致
|
|
||||||
let autoPlayTimer = null;
|
|
||||||
|
|
||||||
// 3. 初始化无缝DOM:仅复制第一张到末尾(适配3→1右侧滑入)
|
|
||||||
const initSeamless = () => {
|
|
||||||
// 复制第一张图片(1)到轮播容器末尾
|
|
||||||
const firstImgCopy = imgItems[0].cloneNode(true);
|
|
||||||
carouselImgs.appendChild(firstImgCopy);
|
|
||||||
// 初始定位:无过渡,显示真实第一张
|
|
||||||
carouselImgs.style.transition = 'none';
|
|
||||||
carouselImgs.style.transform = `translateX(0%)`;
|
|
||||||
void carouselImgs.offsetWidth; // 强制重绘
|
|
||||||
// 开启过渡
|
|
||||||
carouselImgs.style.transition = `transform ${transitionDuration}ms ease`;
|
|
||||||
};
|
|
||||||
initSeamless();
|
|
||||||
|
|
||||||
// 4. 核心切换函数(保证3→1时1从右侧滑入)
|
|
||||||
const slideToNext = () => {
|
|
||||||
if (isTransitioning) return;
|
|
||||||
isTransitioning = true;
|
|
||||||
|
|
||||||
// 步骤1:计算目标偏移,执行滑动动画
|
|
||||||
const targetTranslateX = -(currentRealIndex + 1) * 100;
|
|
||||||
carouselImgs.style.transform = `translateX(${targetTranslateX}%)`;
|
|
||||||
|
|
||||||
// 步骤2:监听过渡结束,处理无缝逻辑
|
|
||||||
const handleEnd = () => {
|
|
||||||
carouselImgs.removeEventListener('transitionend', handleEnd);
|
|
||||||
isTransitioning = false;
|
|
||||||
|
|
||||||
// 如果滑到了复制的第一张(3→1的视觉终点)
|
|
||||||
if (currentRealIndex === imgCount - 1) {
|
|
||||||
// 瞬间切回真实第一张(无过渡,用户无感知)
|
|
||||||
carouselImgs.style.transition = 'none';
|
|
||||||
carouselImgs.style.transform = `translateX(0%)`;
|
|
||||||
void carouselImgs.offsetWidth;
|
|
||||||
carouselImgs.style.transition = `transform ${transitionDuration}ms ease`;
|
|
||||||
currentRealIndex = 0; // 重置为真实第一张
|
|
||||||
} else {
|
|
||||||
currentRealIndex += 1; // 正常切换,索引+1
|
|
||||||
}
|
|
||||||
|
|
||||||
// 更新文字指示器激活态
|
|
||||||
textItems.forEach((item, idx) => {
|
|
||||||
item.classList.toggle('active', idx === currentRealIndex);
|
|
||||||
});
|
|
||||||
};
|
|
||||||
carouselImgs.addEventListener('transitionend', handleEnd);
|
|
||||||
};
|
|
||||||
|
|
||||||
// 5. 反向切换(1→3,可选保留)
|
|
||||||
const slideToPrev = () => {
|
|
||||||
if (isTransitioning) return;
|
|
||||||
isTransitioning = true;
|
|
||||||
|
|
||||||
// 1→3时,先瞬间切到复制的3位置,再滑入
|
|
||||||
if (currentRealIndex === 0) {
|
|
||||||
carouselImgs.style.transition = 'none';
|
|
||||||
carouselImgs.style.transform = `translateX(-${imgCount * 100}%)`;
|
|
||||||
void carouselImgs.offsetWidth;
|
|
||||||
carouselImgs.style.transition = `transform ${transitionDuration}ms ease`;
|
|
||||||
currentRealIndex = imgCount - 1;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const targetTranslateX = -currentRealIndex * 100;
|
// 2. 核心配置
|
||||||
carouselImgs.style.transform = `translateX(${targetTranslateX}%)`;
|
const imgCount = imgItems.length; // 真实图片数量(如3张:1/2/3)
|
||||||
|
let currentRealIndex = 0; // 真实图片索引(0=1, 1=2, 2=3)
|
||||||
|
let isTransitioning = false; // 过渡锁,防止动画冲突
|
||||||
|
const transitionDuration = 500; // 过渡时长(ms),需与CSS一致
|
||||||
|
let autoPlayTimer = null;
|
||||||
|
|
||||||
const handleEnd = () => {
|
// 3. 初始化无缝DOM:仅复制第一张到末尾(适配3→1右侧滑入)
|
||||||
carouselImgs.removeEventListener('transitionend', handleEnd);
|
const initSeamless = () => {
|
||||||
isTransitioning = false;
|
// 复制第一张图片(1)到轮播容器末尾
|
||||||
// 更新文字指示器
|
const firstImgCopy = imgItems[0].cloneNode(true);
|
||||||
textItems.forEach((item, idx) => {
|
carouselImgs.appendChild(firstImgCopy);
|
||||||
item.classList.toggle('active', idx === currentRealIndex);
|
// 初始定位:无过渡,显示真实第一张
|
||||||
});
|
carouselImgs.style.transition = 'none';
|
||||||
|
carouselImgs.style.transform = `translateX(0%)`;
|
||||||
|
void carouselImgs.offsetWidth; // 强制重绘
|
||||||
|
// 开启过渡
|
||||||
|
carouselImgs.style.transition = `transform ${transitionDuration}ms ease`;
|
||||||
};
|
};
|
||||||
carouselImgs.addEventListener('transitionend', handleEnd);
|
initSeamless();
|
||||||
};
|
|
||||||
|
|
||||||
// 6. 自动播放:严格1→2→3→1循环
|
// 4. 核心切换函数(保证3→1时1从右侧滑入)
|
||||||
const autoPlay = () => {
|
const slideToNext = () => {
|
||||||
clearInterval(autoPlayTimer);
|
if (isTransitioning) return;
|
||||||
autoPlayTimer = setInterval(() => {
|
|
||||||
if (!isTransitioning) slideToNext();
|
|
||||||
}, 3000); // 3秒切换一次,可调整
|
|
||||||
};
|
|
||||||
|
|
||||||
// 7. 事件绑定
|
|
||||||
// 右箭头:下一张(核心,保证3→1右侧滑入)
|
|
||||||
rightArrow?.addEventListener('click', () => {
|
|
||||||
slideToNext();
|
|
||||||
autoPlay(); // 点击后重启自动播放
|
|
||||||
});
|
|
||||||
// 左箭头:上一张(可选,如需取消可注释)
|
|
||||||
leftArrow?.addEventListener('click', () => {
|
|
||||||
slideToPrev();
|
|
||||||
autoPlay();
|
|
||||||
});
|
|
||||||
|
|
||||||
// 文字指示器点击
|
|
||||||
textItems.forEach((item, idx) => {
|
|
||||||
item.addEventListener('click', () => {
|
|
||||||
if (isTransitioning || currentRealIndex === idx) return;
|
|
||||||
isTransitioning = true;
|
isTransitioning = true;
|
||||||
|
|
||||||
// 直接滑到目标图片
|
|
||||||
carouselImgs.style.transform = `translateX(-${idx * 100}%)`;
|
|
||||||
currentRealIndex = idx;
|
|
||||||
|
|
||||||
// 过渡结束解锁
|
// 步骤1:计算目标偏移,执行滑动动画
|
||||||
|
const targetTranslateX = -(currentRealIndex + 1) * 100;
|
||||||
|
carouselImgs.style.transform = `translateX(${targetTranslateX}%)`;
|
||||||
|
|
||||||
|
// 步骤2:监听过渡结束,处理无缝逻辑
|
||||||
const handleEnd = () => {
|
const handleEnd = () => {
|
||||||
carouselImgs.removeEventListener('transitionend', handleEnd);
|
carouselImgs.removeEventListener('transitionend', handleEnd);
|
||||||
isTransitioning = false;
|
isTransitioning = false;
|
||||||
|
|
||||||
|
// 如果滑到了复制的第一张(3→1的视觉终点)
|
||||||
|
if (currentRealIndex === imgCount - 1) {
|
||||||
|
// 瞬间切回真实第一张(无过渡,用户无感知)
|
||||||
|
carouselImgs.style.transition = 'none';
|
||||||
|
carouselImgs.style.transform = `translateX(0%)`;
|
||||||
|
void carouselImgs.offsetWidth;
|
||||||
|
carouselImgs.style.transition = `transform ${transitionDuration}ms ease`;
|
||||||
|
currentRealIndex = 0; // 重置为真实第一张
|
||||||
|
} else {
|
||||||
|
currentRealIndex += 1; // 正常切换,索引+1
|
||||||
|
}
|
||||||
|
|
||||||
|
// 更新文字指示器激活态
|
||||||
|
textItems.forEach((item, idx) => {
|
||||||
|
item.classList.toggle('active', idx === currentRealIndex);
|
||||||
|
});
|
||||||
};
|
};
|
||||||
carouselImgs.addEventListener('transitionend', handleEnd);
|
carouselImgs.addEventListener('transitionend', handleEnd);
|
||||||
|
};
|
||||||
|
|
||||||
|
// 5. 反向切换(1→3,可选保留)
|
||||||
|
const slideToPrev = () => {
|
||||||
|
if (isTransitioning) return;
|
||||||
|
isTransitioning = true;
|
||||||
|
|
||||||
|
// 1→3时,先瞬间切到复制的3位置,再滑入
|
||||||
|
if (currentRealIndex === 0) {
|
||||||
|
carouselImgs.style.transition = 'none';
|
||||||
|
carouselImgs.style.transform = `translateX(-${imgCount * 100}%)`;
|
||||||
|
void carouselImgs.offsetWidth;
|
||||||
|
carouselImgs.style.transition = `transform ${transitionDuration}ms ease`;
|
||||||
|
currentRealIndex = imgCount - 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
const targetTranslateX = -currentRealIndex * 100;
|
||||||
|
carouselImgs.style.transform = `translateX(${targetTranslateX}%)`;
|
||||||
|
|
||||||
|
const handleEnd = () => {
|
||||||
|
carouselImgs.removeEventListener('transitionend', handleEnd);
|
||||||
|
isTransitioning = false;
|
||||||
|
// 更新文字指示器
|
||||||
|
textItems.forEach((item, idx) => {
|
||||||
|
item.classList.toggle('active', idx === currentRealIndex);
|
||||||
|
});
|
||||||
|
};
|
||||||
|
carouselImgs.addEventListener('transitionend', handleEnd);
|
||||||
|
};
|
||||||
|
|
||||||
|
// 6. 自动播放:严格1→2→3→1循环
|
||||||
|
const autoPlay = () => {
|
||||||
|
clearInterval(autoPlayTimer);
|
||||||
|
autoPlayTimer = setInterval(() => {
|
||||||
|
if (!isTransitioning) slideToNext();
|
||||||
|
}, 3000); // 3秒切换一次,可调整
|
||||||
|
};
|
||||||
|
|
||||||
|
// 7. 事件绑定
|
||||||
|
// 右箭头:下一张(核心,保证3→1右侧滑入)
|
||||||
|
rightArrow?.addEventListener('click', () => {
|
||||||
|
slideToNext();
|
||||||
|
autoPlay(); // 点击后重启自动播放
|
||||||
|
});
|
||||||
|
// 左箭头:上一张(可选,如需取消可注释)
|
||||||
|
leftArrow?.addEventListener('click', () => {
|
||||||
|
slideToPrev();
|
||||||
autoPlay();
|
autoPlay();
|
||||||
});
|
});
|
||||||
});
|
|
||||||
|
|
||||||
// 鼠标悬停暂停/恢复
|
// 文字指示器点击
|
||||||
carouselContainer?.addEventListener('mouseenter', () => {
|
textItems.forEach((item, idx) => {
|
||||||
clearInterval(autoPlayTimer);
|
item.addEventListener('click', () => {
|
||||||
});
|
if (isTransitioning || currentRealIndex === idx) return;
|
||||||
carouselContainer?.addEventListener('mouseleave', autoPlay);
|
isTransitioning = true;
|
||||||
|
|
||||||
// 8. 初始化
|
// 直接滑到目标图片
|
||||||
// 激活第一个文字指示器
|
carouselImgs.style.transform = `translateX(-${idx * 100}%)`;
|
||||||
textItems.forEach((item, idx) => {
|
currentRealIndex = idx;
|
||||||
item.classList.toggle('active', idx === 0);
|
|
||||||
});
|
|
||||||
autoPlay(); // 启动自动播放
|
|
||||||
|
|
||||||
// 9. 页面卸载清理定时器
|
// 过渡结束解锁
|
||||||
window.addEventListener('beforeunload', () => {
|
const handleEnd = () => {
|
||||||
clearInterval(autoPlayTimer);
|
carouselImgs.removeEventListener('transitionend', handleEnd);
|
||||||
|
isTransitioning = false;
|
||||||
|
};
|
||||||
|
carouselImgs.addEventListener('transitionend', handleEnd);
|
||||||
|
|
||||||
|
autoPlay();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
// 鼠标悬停暂停/恢复
|
||||||
|
carouselContainer?.addEventListener('mouseenter', () => {
|
||||||
|
clearInterval(autoPlayTimer);
|
||||||
|
});
|
||||||
|
carouselContainer?.addEventListener('mouseleave', autoPlay);
|
||||||
|
|
||||||
|
// 8. 初始化
|
||||||
|
// 激活第一个文字指示器
|
||||||
|
textItems.forEach((item, idx) => {
|
||||||
|
item.classList.toggle('active', idx === 0);
|
||||||
|
});
|
||||||
|
autoPlay(); // 启动自动播放
|
||||||
|
|
||||||
|
// 9. 页面卸载清理定时器
|
||||||
|
window.addEventListener('beforeunload', () => {
|
||||||
|
clearInterval(autoPlayTimer);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
});
|
|
||||||
</script>
|
</script>
|
||||||
{/block}
|
{/block}
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -43,8 +43,3 @@ body {
|
|||||||
/* [data-order="19"] {
|
/* [data-order="19"] {
|
||||||
transition: all 0.3s ease-out 0.2s !important;
|
transition: all 0.3s ease-out 0.2s !important;
|
||||||
} */
|
} */
|
||||||
[data-order], .annotation, .progress-fill, .zoom-image, .float-card {
|
|
||||||
transform: translateZ(0); /* 开启硬件加速,将元素交给 GPU 渲染 */
|
|
||||||
will-change: opacity, transform; /* 告诉浏览器提前优化这个元素 */
|
|
||||||
backface-visibility: hidden; /* 防止元素翻转时的闪烁 */
|
|
||||||
}
|
|
||||||
@@ -189,14 +189,14 @@
|
|||||||
.progress-p {
|
.progress-p {
|
||||||
color: #cbcfd8;
|
color: #cbcfd8;
|
||||||
font-size: clamp(16px, 1vw, 0.22rem);
|
font-size: clamp(16px, 1vw, 0.22rem);
|
||||||
margin-top: 1.23rem;
|
margin-top: 1.56rem;
|
||||||
margin-bottom: 5.04rem;
|
margin-bottom: 2rem;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
}
|
}
|
||||||
.progress-p1 {
|
.progress-p1 {
|
||||||
color: #cbcfd8;
|
color: #cbcfd8;
|
||||||
font-size: clamp(16px, 1vw, 0.22rem);
|
font-size: clamp(16px, 1vw, 0.22rem);
|
||||||
margin-top: 1.56rem;
|
margin-top: 1.56rem;
|
||||||
/* margin-bottom: 2.3rem; */
|
/* margin-bottom: 1.66rem; */
|
||||||
text-align: center;
|
text-align: center;
|
||||||
}
|
}
|
||||||
@@ -39,7 +39,7 @@
|
|||||||
color: #cbcfd8;
|
color: #cbcfd8;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
padding-top: 0.39rem;
|
padding-top: 0.43rem;
|
||||||
line-height: 1.8;
|
line-height: 1.8;
|
||||||
font-family: "HarmonyOS-Light";
|
font-family: "HarmonyOS-Light";
|
||||||
}
|
}
|
||||||
|
|||||||
BIN
public/static/index/pc/images/topic_laptop/eljgd.png
Normal file
BIN
public/static/index/pc/images/topic_laptop/eljgd.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 2.4 KiB |
Reference in New Issue
Block a user