This commit is contained in:
2025-09-08 08:41:56 +08:00
parent b982c63873
commit 7dbf7289a4

View File

@@ -40,15 +40,11 @@
height: 30px; height: 30px;
background: url("hongqi.jpg") no-repeat center/contain; background: url("hongqi.jpg") no-repeat center/contain;
position: absolute; position: absolute;
offset-path: path('M100,350 C150,340 200,320 250,300 300,280 350,260 400,240 450,220 500,200 550,180 600,160 650,140 700,100'); transform: translate(-50%, -50%); /* 使红旗中心对准路径 */
offset-distance: 0%; z-index: 10;
animation: move 20s linear paused; /* 添加备用背景样式,以防图片加载失败 */
} background-color: red;
border-radius: 50% 0;
@keyframes move {
to {
offset-distance: 100%;
}
} }
#subtitle { #subtitle {
@@ -98,6 +94,8 @@
<script> <script>
const flag = document.getElementById("redFlag"); const flag = document.getElementById("redFlag");
const subtitle = document.getElementById("subtitle"); const subtitle = document.getElementById("subtitle");
const route = document.getElementById("route");
const map = document.getElementById("map");
const timeline = [ const timeline = [
{ p: 0, text: "1934年10月 从江西瑞金出发" }, { p: 0, text: "1934年10月 从江西瑞金出发" },
@@ -110,30 +108,92 @@
{ p: 95, text: "1935年10月 到达吴起镇" } { p: 95, text: "1935年10月 到达吴起镇" }
]; ];
let interval; let animationId;
let startTime;
let pausedTime = 0;
let isPlaying = false;
const duration = 20000; // 20秒
// 获取SVG路径的总长度
const pathLength = route.getTotalLength();
// 计算SVG坐标系到页面坐标系的转换比例
function getScaleFactor() {
const viewBox = route.viewBox.baseVal;
const svgRect = route.closest('svg').getBoundingClientRect();
return {
x: svgRect.width / viewBox.width,
y: svgRect.height / viewBox.height
};
}
// 根据进度百分比获取路径上的点
function getPointOnPath(percent) {
const distance = percent * pathLength / 100;
const point = route.getPointAtLength(distance);
const scale = getScaleFactor();
// 获取SVG元素相对于页面的位置
const svgRect = route.closest('svg').getBoundingClientRect();
const mapRect = map.getBoundingClientRect();
// 计算红旗在页面上的位置
return {
x: svgRect.left - mapRect.left + point.x * scale.x,
y: svgRect.top - mapRect.top + point.y * scale.y
};
}
// 更新红旗位置
function updateFlagPosition(percent) {
const point = getPointOnPath(percent);
flag.style.left = `${point.x}px`;
flag.style.top = `${point.y}px`;
}
// 动画循环
function animate(timestamp) {
if (!startTime) startTime = timestamp;
const elapsed = timestamp - startTime + pausedTime;
const progress = Math.min(elapsed / duration, 1) * 100;
updateFlagPosition(progress);
updateSubtitle(progress);
if (progress < 100) {
animationId = requestAnimationFrame(animate);
} else {
isPlaying = false;
}
}
function play() { function play() {
flag.style.animationPlayState = "running"; if (!isPlaying) {
interval = setInterval(updateSubtitle, 200); isPlaying = true;
startTime = null;
animationId = requestAnimationFrame(animate);
}
} }
function pause() { function pause() {
flag.style.animationPlayState = "paused"; if (isPlaying) {
clearInterval(interval); isPlaying = false;
cancelAnimationFrame(animationId);
if (startTime) {
pausedTime += performance.now() - startTime;
}
}
} }
function reset() { function reset() {
flag.style.animation = "none"; pause();
flag.offsetHeight; // 触发重排 pausedTime = 0;
flag.style.animation = "move 20s linear paused"; updateFlagPosition(0);
subtitle.textContent = timeline[0].text; subtitle.textContent = timeline[0].text;
clearInterval(interval);
} }
function updateSubtitle() { function updateSubtitle(percent) {
const computed = window.getComputedStyle(flag);
const distance = computed.offsetDistance;
const percent = parseFloat(distance);
for (let i = timeline.length - 1; i >= 0; i--) { for (let i = timeline.length - 1; i >= 0; i--) {
if (percent >= timeline[i].p) { if (percent >= timeline[i].p) {
subtitle.textContent = timeline[i].text; subtitle.textContent = timeline[i].text;
@@ -141,7 +201,27 @@
} }
} }
} }
</script>
// 页面加载完成后初始化红旗位置
window.addEventListener('load', function() {
// 确保红旗在初始位置可见
updateFlagPosition(0);
// 检查红旗图片是否加载成功
const img = new Image();
img.onload = function() {
// 图片加载成功,使用图片作为背景
flag.style.backgroundImage = 'url("hongqi.jpg")';
flag.style.backgroundColor = 'transparent';
};
img.onerror = function() {
// 图片加载失败,使用备用样式
console.warn('红旗图片加载失败,使用备用样式');
flag.style.backgroundImage = 'none';
flag.style.backgroundColor = 'red';
};
img.src = 'hongqi.jpg';
});
</script>
</body> </body>
</html> </html>