Commit dbc63f3d authored by 董政锦's avatar 董政锦

Merge branch 'fix-修复音乐通用js文件' into 'main'

build: 图片压缩; See merge request !17
parents 00dea6cc 5629f083
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This diff is collapsed.
...@@ -12,21 +12,21 @@ const gameId = 'game4'; ...@@ -12,21 +12,21 @@ const gameId = 'game4';
type GameView = 'loading' | 'playing' | 'score' type GameView = 'loading' | 'playing' | 'score'
const imageUrls = { const imageUrls = {
bg: cssAssetUrl('game4/h5-game4-bg.svg'), bg: cssAssetUrl('game4/h5-game4-bg.webp'),
bg2: cssAssetUrl('game1/bg2.png'), bg2: cssAssetUrl('game1/bg2.png'),
playBg: cssAssetUrl('game4/h5-game4-bg2.svg'), playBg: cssAssetUrl('game4/h5-game4-bg2.webp'),
logo: cssAssetUrl('game4/logo.svg'), logo: cssAssetUrl('game4/logo.webp'),
time: cssAssetUrl('game4/h5-game4-clock.svg'), time: cssAssetUrl('game4/h5-game4-clock.svg'),
title: cssAssetUrl('game4/h5-game4-title1.svg'), title: cssAssetUrl('game4/h5-game4-title1.webp'),
title2: cssAssetUrl('game4/h5-game4-title2.svg'), title2: cssAssetUrl('game4/h5-game4-title2.webp'),
// avatarBg: cssAssetUrl('game4/h5-game4-join.svg'), // avatarBg: cssAssetUrl('game4/h5-game4-join.svg'),
userBg: cssAssetUrl('game4/user-bg.svg'), userBg: cssAssetUrl('game4/user-bg.webpp'),
startBg: cssAssetUrl('game4/start-bg.svg'), startBg: cssAssetUrl('game4/start-bg.webp'),
gift: cssAssetUrl('game4/h5-game4-gift.svg'), gift: cssAssetUrl('game4/h5-game4-gift.webp'),
avatar: cssAssetUrl('game1/avatar.png'), avatar: cssAssetUrl('game1/avatar.png'),
gu: cssAssetUrl('game4/h5-game4-horse.svg'), gu: cssAssetUrl('game4/h5-game4-horse.webp'),
clock: cssAssetUrl('game1/clock.png'), clock: cssAssetUrl('game1/clock.png'),
horse: cssAssetUrl('game4/h5-game4-horse.svg'), horse: cssAssetUrl('game4/h5-game4-horse.webp'),
yaoyiyao: cssAssetUrl('game4/h5-game4-yaoyiyao.svg'), yaoyiyao: cssAssetUrl('game4/h5-game4-yaoyiyao.svg'),
scoreBg: cssAssetUrl('game1/score-bg.png'), scoreBg: cssAssetUrl('game1/score-bg.png'),
back: cssAssetUrl('game4/back.svg'), back: cssAssetUrl('game4/back.svg'),
......
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This diff is collapsed.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
This source diff could not be displayed because it is too large. You can view the blob instead.
...@@ -11,7 +11,7 @@ const password = ref('') ...@@ -11,7 +11,7 @@ const password = ref('')
const imageUrls = { const imageUrls = {
bg1: cssAssetUrl('main-bg1.png'), bg1: cssAssetUrl('main-bg1.png'),
logo: cssAssetUrl('game1/logo.png'), logo: cssAssetUrl('game1/logo.png'),
title1: cssAssetUrl('main-title.png'), title1: cssAssetUrl('main-title.webp'),
} }
async function login() { async function login() {
......
...@@ -8,7 +8,7 @@ import { onMounted, onUnmounted, ref } from 'vue'; ...@@ -8,7 +8,7 @@ import { onMounted, onUnmounted, ref } from 'vue';
const imageUrls = { const imageUrls = {
bg1: cssAssetUrl('main-bg1.png'), bg1: cssAssetUrl('main-bg1.png'),
logo: cssAssetUrl('game1/logo.png'), logo: cssAssetUrl('game1/logo.png'),
title1: cssAssetUrl('main-title.png'), title1: cssAssetUrl('main-title.webp'),
icon1: cssAssetUrl('icon1.png'), icon1: cssAssetUrl('icon1.png'),
icon2: cssAssetUrl('icon2.png'), icon2: cssAssetUrl('icon2.png'),
......
...@@ -42,7 +42,7 @@ const imageUrls = { ...@@ -42,7 +42,7 @@ const imageUrls = {
// ========== 马匹帧配置(只用 ma1/ma2/ma3,不用 ma4) ========== // ========== 马匹帧配置(只用 ma1/ma2/ma3,不用 ma4) ==========
const HORSE_SIZE = 280; const HORSE_SIZE = 280;
const HORSE_START_X = -HORSE_SIZE; const HORSE_START_X = -100;
const HORSE_END_X = 1920; const HORSE_END_X = 1920;
const HORSE_Y_OFFSET = 50; // 马匹整体偏移 const HORSE_Y_OFFSET = 50; // 马匹整体偏移
...@@ -341,7 +341,6 @@ const startIntro = async () => { ...@@ -341,7 +341,6 @@ const startIntro = async () => {
isGameRunning.value = false; isGameRunning.value = false;
horses.value = []; horses.value = [];
horseIdCounter = 0; horseIdCounter = 0;
// 重置加速状态
transientBoosts.value = {}; transientBoosts.value = {};
Object.keys(prevScores).forEach(k => delete prevScores[k]); Object.keys(prevScores).forEach(k => delete prevScores[k]);
preloadHorseFrames(); preloadHorseFrames();
...@@ -349,11 +348,45 @@ const startIntro = async () => { ...@@ -349,11 +348,45 @@ const startIntro = async () => {
const countdownPromise = designStage.value?.startCountdown(3, 60); const countdownPromise = designStage.value?.startCountdown(3, 60);
await new Promise((r) => setTimeout(r, 3500)); await new Promise((r) => setTimeout(r, 3500));
const validCount = list.value.filter(p => getPlayerKey(p).length > 0 && !getPlayerKey(p).startsWith('empty-')).length; console.log('[game3 Rank1View] 倒计时结束,马匹开始奔跑');
console.log('[game3 Rank1View] startIntro: 3.5s 后, list 有效玩家数:', validCount);
gameStarted.value = true; gameStarted.value = true;
isGameRunning.value = true; isGameRunning.value = true;
const validPlayers = list.value.filter(p => {
const key = getPlayerKey(p);
return key && !key.startsWith('empty-') && p.nickname !== '-' && p.nickname !== '虚位以待';
});
if (validPlayers.length > 0) {
updateHorses(list.value); updateHorses(list.value);
} else {
const count = 8 + Math.floor(Math.random() * 3);
const now = performance.now();
const newHorses: Horse[] = [];
for (let i = 0; i < count; i++) {
const type = HORSE_TYPES[i % HORSE_TYPES.length]!;
const lane = i % LANE_TOP_POSITIONS.length;
const delayMs = i * 50 + Math.random() * 50;
const durationMs = (60 + Math.random() * 40) * 1000;
newHorses.push({
id: `horse-${++horseIdCounter}`,
horseType: type,
lane,
frameIndex: Math.floor(Math.random() * (horseFrameCount[type] ?? 12)),
frameTimer: 0,
x: HORSE_START_X,
xPercent: 0,
boost: 0,
nickname: `马匹${i + 1}`,
avatar: '',
playerKey: `auto-${i}`,
});
}
horses.value = newHorses;
console.log('[game3 Rank1View] 生成', count, '匹默认马');
}
startHorseLoop(); startHorseLoop();
await countdownPromise; await countdownPromise;
......
...@@ -14,14 +14,14 @@ const emit = defineEmits<{ ...@@ -14,14 +14,14 @@ const emit = defineEmits<{
}>(); }>();
const imageUrls = { const imageUrls = {
bg: cssAssetUrl("game4/bg.svg"), bg: cssAssetUrl("game4/bg.webp"),
logo: cssAssetUrl("game1/logo.png"), logo: cssAssetUrl("game1/logo.png"),
title1: cssAssetUrl("game4/title1.svg"), title1: cssAssetUrl("game4/title1.webp"),
title2: cssAssetUrl("game4/title2.svg"), title2: cssAssetUrl("game4/title2.svg"),
qrcode: assetUrl("game4/qrcode.png"), qrcode: assetUrl("game4/qrcode.png"),
gift: cssAssetUrl("game4/gift.svg"), gift: cssAssetUrl("game4/gift.webp"),
gu: cssAssetUrl("game4/big-brum.svg"), gu: cssAssetUrl("game4/big-brum.webp"),
smallGu: cssAssetUrl("game4/small-brum.svg"), smallGu: cssAssetUrl("game4/small-brum.webp"),
bottomLayers: cssAssetUrl("game1/bottom-layers.png"), bottomLayers: cssAssetUrl("game1/bottom-layers.png"),
avatarAnimation: cssAssetUrl("avatar_animation.png"), avatarAnimation: cssAssetUrl("avatar_animation.png"),
avatar: cssAssetUrl("avatar.png"), avatar: cssAssetUrl("avatar.png"),
......
...@@ -5,7 +5,7 @@ import type Player from "@/commons/player.ts"; ...@@ -5,7 +5,7 @@ import type Player from "@/commons/player.ts";
import { $is_local_mode } from "@/commons/utils.ts"; import { $is_local_mode } from "@/commons/utils.ts";
import { cssAssetUrl, assetUrl } from "@/commons/assets.ts"; import { cssAssetUrl, assetUrl } from "@/commons/assets.ts";
import { playApplauseMusic, stopApplauseMusic } from "@/commons/music"; import { playApplauseMusic, stopApplauseMusic } from "@/commons/music";
const defaultAvatarUrl = assetUrl("game4/default-avator.svg"); const defaultAvatarUrl = assetUrl("game4/default-avator.webp");
const props = defineProps<{ const props = defineProps<{
rankList: Player[]; rankList: Player[];
...@@ -25,22 +25,22 @@ const imageUrls = { ...@@ -25,22 +25,22 @@ const imageUrls = {
bgTop: cssAssetUrl("game4/bg-top.webp"), bgTop: cssAssetUrl("game4/bg-top.webp"),
bgBottom: cssAssetUrl("game4/bg-bottom.webp"), bgBottom: cssAssetUrl("game4/bg-bottom.webp"),
logo: cssAssetUrl("game1/logo.png"), logo: cssAssetUrl("game1/logo.png"),
titleBg: cssAssetUrl("game4/horse-title-bg.svg"), titleBg: cssAssetUrl("game4/horse-title-bg.webp"),
bigBrum: cssAssetUrl("game4/big-brum.svg"), bigBrum: cssAssetUrl("game4/big-brum.webp"),
username: cssAssetUrl("game4/username.svg"), username: cssAssetUrl("game4/username.svg"),
avatar: cssAssetUrl("game4/default-avator.svg"), avatar: cssAssetUrl("game4/default-avator.webp"),
resultBg: cssAssetUrl("game4/resultBg.svg"), resultBg: cssAssetUrl("game4/resultbg.webp"),
next: cssAssetUrl("game1/next.png"), next: cssAssetUrl("game1/next.png"),
back: cssAssetUrl("game1/back.png"), back: cssAssetUrl("game1/back.png"),
// 结果弹窗 - podium 相关资源(复用 game1) // 结果弹窗 - podium 相关资源(复用 game1)
podium: cssAssetUrl("game4/podium.svg"), podium: cssAssetUrl("game4/podium.webp"),
fireworks: cssAssetUrl("game1/fireworks.png"), fireworks: cssAssetUrl("game1/fireworks.png"),
guan1: cssAssetUrl("game1/guan1.png"), guan1: cssAssetUrl("game1/guan1.png"),
pai1: cssAssetUrl("game4/pai1.svg"), pai1: cssAssetUrl("game4/pai1.webp"),
guan2: cssAssetUrl("game1/guan2.png"), guan2: cssAssetUrl("game1/guan2.png"),
pai2: cssAssetUrl("game4/pai2.svg"), pai2: cssAssetUrl("game4/pai2.webp"),
guan3: cssAssetUrl("game1/guan3.png"), guan3: cssAssetUrl("game1/guan3.png"),
pai3: cssAssetUrl("game4/pai3.svg"), pai3: cssAssetUrl("game4/pai3.webp"),
rankIcon: cssAssetUrl("game1/no-icon.png"), rankIcon: cssAssetUrl("game1/no-icon.png"),
avatarAnimation: cssAssetUrl("avatar_animation.png"), avatarAnimation: cssAssetUrl("avatar_animation.png"),
}; };
...@@ -52,12 +52,12 @@ const TOTAL_DISTANCE_PX = 2160; // -120px ~ 2040px ...@@ -52,12 +52,12 @@ const TOTAL_DISTANCE_PX = 2160; // -120px ~ 2040px
const BASE_DURATION_SEC = 220; const BASE_DURATION_SEC = 220;
const BASE_SPEED_PERCENT_PER_SEC = 100 / BASE_DURATION_SEC; // ≈ 0.455%/s 基准速度 const BASE_SPEED_PERCENT_PER_SEC = 100 / BASE_DURATION_SEC; // ≈ 0.455%/s 基准速度
// 马匹精灵图帧动画(horse.png 共 12 帧,改用 JS 切帧,避免 CSS steps 在部分浏览器不生效) // 马匹精灵图帧动画(horse.webp 共 12 帧,改用 JS 切帧,避免 CSS steps 在部分浏览器不生效)
const HORSE_FRAME_COUNT = 12; const HORSE_FRAME_COUNT = 12;
const HORSE_FRAME_TICK_MS = 48; // ~20fps const HORSE_FRAME_TICK_MS = 48; // ~20fps
const HORSE_SPRITE_OFFSET_X = -17; const HORSE_SPRITE_OFFSET_X = -17;
const HORSE_SPRITE_FRAME_WIDTH = 120; const HORSE_SPRITE_FRAME_WIDTH = 120;
const horseSpriteUrl = assetUrl("game4/horse.png"); const horseSpriteUrl = assetUrl("game4/horse.webp");
// ========== 瞬时加速脉冲机制 ========== // ========== 瞬时加速脉冲机制 ==========
// H5 每次摇一摇发送累计积分,PC 端检测 score 增长 → 触发短暂加速脉冲 → 迅速衰减 // H5 每次摇一摇发送累计积分,PC 端检测 score 增长 → 触发短暂加速脉冲 → 迅速衰减
...@@ -398,25 +398,32 @@ const startIntro = async () => { ...@@ -398,25 +398,32 @@ const startIntro = async () => {
gameStarted.value = false; gameStarted.value = false;
isGameRunning.value = false; isGameRunning.value = false;
stopApplauseMusic(); stopApplauseMusic();
// 重置瞬时加速和积分追踪
transientBoosts.value = {}; transientBoosts.value = {};
Object.keys(prevScores).forEach((k) => delete prevScores[k]); Object.keys(prevScores).forEach((k) => delete prevScores[k]);
// 启动完整倒计时:3s 开场 + 3s 游戏(DesignStage 内部管理两个阶段的 UI)
const countdownPromise = designStage.value?.startCountdown(3, 60); const countdownPromise = designStage.value?.startCountdown(3, 60);
// 等待 3-2-1 开场倒计时结束(~3.5s 后安全触发)
await new Promise((r) => setTimeout(r, 3500)); await new Promise((r) => setTimeout(r, 3500));
// Phase 2: 倒计时结束 → 游戏正式开始,背景动画+马匹启动
gameStarted.value = true; gameStarted.value = true;
isGameRunning.value = true; isGameRunning.value = true;
if (horses.value.length === 0) {
const count = 8 + Math.floor(Math.random() * 3);
const mockPlayers: Player[] = Array.from({ length: count }, (_, i) => ({
userid: `auto-${i}`,
nickname: mockNicknames[i] || `马匹${i + 1}`,
avatar: mockAvatars[i] || '',
score: Math.floor(Math.random() * 60) + 10,
}));
updateHorses(mockPlayers);
console.log('[game4 Rank1View] 生成', count, '匹默认马');
}
startGameLoop(); startGameLoop();
if ($is_local_mode()) { if ($is_local_mode()) {
startMockBoost(); startMockBoost();
} }
// 等待 60s 游戏倒计时完全结束 → 才出现结果页
await countdownPromise; await countdownPromise;
stopGame(); stopGame();
}; };
...@@ -442,7 +449,7 @@ const renderAvatar = (item: any) => { ...@@ -442,7 +449,7 @@ const renderAvatar = (item: any) => {
if (item && item.avatar) { if (item && item.avatar) {
return `background: url('${item.avatar}') center / cover no-repeat;`; return `background: url('${item.avatar}') center / cover no-repeat;`;
} }
// 无头像时用 default-avator.svg 占位(白底 + 居中 cover) // 无头像时用 default-avator 占位(白底 + 居中 cover)
return `background: #fff url('${defaultAvatarUrl}') center / cover no-repeat;`; return `background: #fff url('${defaultAvatarUrl}') center / cover no-repeat;`;
}; };
......
...@@ -14,7 +14,7 @@ const emit = defineEmits<{ ...@@ -14,7 +14,7 @@ const emit = defineEmits<{
const FINAL_RANK_LIMIT = 10; const FINAL_RANK_LIMIT = 10;
const imageUrls = { const imageUrls = {
bg: cssAssetUrl("game4/bg.svg"), bg: cssAssetUrl("game4/bg.webp"),
logo: cssAssetUrl("game1/logo.png"), logo: cssAssetUrl("game1/logo.png"),
title: cssAssetUrl("game1/title3.png"), title: cssAssetUrl("game1/title3.png"),
title2: cssAssetUrl("game1/title4.png"), title2: cssAssetUrl("game1/title4.png"),
......
...@@ -14,7 +14,7 @@ const emit = defineEmits<{ ...@@ -14,7 +14,7 @@ const emit = defineEmits<{
}>(); }>();
const imageUrls = { const imageUrls = {
bg: cssAssetUrl('game5/bg.svg'), bg: cssAssetUrl('game5/bg.webp'),
logo: cssAssetUrl('game1/logo.png'), logo: cssAssetUrl('game1/logo.png'),
title1: cssAssetUrl('game5/title1.webp'), title1: cssAssetUrl('game5/title1.webp'),
// title2: cssAssetUrl('game1/title2.png'), // title2: cssAssetUrl('game1/title2.png'),
......
...@@ -22,7 +22,7 @@ const showResult = ref(false); ...@@ -22,7 +22,7 @@ const showResult = ref(false);
const imageUrls = { const imageUrls = {
runway: cssAssetUrl("game5/paodao.webp"), runway: cssAssetUrl("game5/paodao.webp"),
bg: cssAssetUrl("game5/bg.svg"), bg: cssAssetUrl("game5/bg.webp"),
logo: cssAssetUrl("game1/logo.png"), logo: cssAssetUrl("game1/logo.png"),
title: cssAssetUrl("game5/title3.webp"), title: cssAssetUrl("game5/title3.webp"),
rankNo4: cssAssetUrl("game6/no4.png"), rankNo4: cssAssetUrl("game6/no4.png"),
......
...@@ -15,7 +15,7 @@ const emit = defineEmits<{ ...@@ -15,7 +15,7 @@ const emit = defineEmits<{
const FINAL_RANK_LIMIT = 10; const FINAL_RANK_LIMIT = 10;
const imageUrls = { const imageUrls = {
bg: cssAssetUrl('game5/bg.svg'), bg: cssAssetUrl('game5/bg.webp'),
logo: cssAssetUrl('game1/logo.png'), logo: cssAssetUrl('game1/logo.png'),
title: cssAssetUrl('game5/title.webp'), title: cssAssetUrl('game5/title.webp'),
title2: cssAssetUrl('game5/title2.webp'), title2: cssAssetUrl('game5/title2.webp'),
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment