feat: 数据mock
This commit is contained in:
@@ -37,61 +37,47 @@
|
||||
</template>
|
||||
|
||||
<script setup lang="ts">
|
||||
import { ref, computed } from 'vue'
|
||||
import { ref, computed, onMounted } from 'vue'
|
||||
import { useBaseLayoutStore } from '@/stores'
|
||||
import { storeToRefs } from 'pinia'
|
||||
import { getGameList, type GameItem } from '@/api/modules/game'
|
||||
|
||||
/** 游戏数据接口 */
|
||||
interface GameInfo {
|
||||
id: string
|
||||
/** 图标(emoji 或文字占位) */
|
||||
icon: string
|
||||
name: string
|
||||
description: string
|
||||
gameplay: string
|
||||
/** 游戏列表 */
|
||||
const games = ref<GameItem[]>([])
|
||||
/** 加载状态 */
|
||||
const loading = ref<boolean>(false)
|
||||
|
||||
/** 获取游戏列表 */
|
||||
async function fetchGameList() {
|
||||
loading.value = true
|
||||
try {
|
||||
const res = await getGameList()
|
||||
games.value = res.data.list
|
||||
// 默认选中第一个游戏
|
||||
if (games.value.length > 0 && !activeGameId.value) {
|
||||
const first = games.value[0]
|
||||
if (first) {
|
||||
baseLayoutStore.setActiveGame(first.id, first.icon, first.name)
|
||||
}
|
||||
}
|
||||
} finally {
|
||||
loading.value = false
|
||||
}
|
||||
}
|
||||
|
||||
/** 游戏列表数据 */
|
||||
const games: GameInfo[] = [
|
||||
{
|
||||
id: 'snake',
|
||||
icon: '🐍',
|
||||
name: '贪吃蛇',
|
||||
description: '经典贪吃蛇竞技,在狭小空间内争夺生存权',
|
||||
gameplay: '方向键控制蛇的移动,吃到食物变长。撞墙或其他蛇的身体即死亡,最后存活的玩家获胜。'
|
||||
},
|
||||
{
|
||||
id: 'tetris',
|
||||
icon: '🧊',
|
||||
name: '俄罗斯方块',
|
||||
description: '经典下落消除,与对手一较高下',
|
||||
gameplay: '方向键移动和旋转方块,填满横排即可消除。同时向对手发送干扰行,坚持到最后的玩家获胜。'
|
||||
},
|
||||
{
|
||||
id: 'gomoku',
|
||||
icon: '⚫',
|
||||
name: '五子棋',
|
||||
description: '黑白对弈,先连成五子者胜',
|
||||
gameplay: '鼠标点击落子,黑白双方轮流在棋盘上放置棋子。先在横、竖、斜任意方向连成五子的一方获胜。'
|
||||
},
|
||||
{
|
||||
id: 'guess-number',
|
||||
icon: '🔢',
|
||||
name: '猜数字',
|
||||
description: '逻辑推理对战,猜中对方的秘密数字',
|
||||
gameplay: '每轮输入猜测的数字组合,系统会提示位置和数字正确的数量。率先猜中对手数字组合的玩家获胜。'
|
||||
}
|
||||
]
|
||||
onMounted(() => {
|
||||
fetchGameList()
|
||||
})
|
||||
|
||||
const baseLayoutStore = useBaseLayoutStore()
|
||||
const { activeGameId } = storeToRefs(baseLayoutStore)
|
||||
|
||||
/** 当前选中的游戏对象 */
|
||||
const activeGame = computed(() => games.find((g) => g.id === activeGameId.value) ?? null)
|
||||
const activeGame = computed(() => games.value.find((g) => g.id === activeGameId.value) ?? null)
|
||||
|
||||
/** 选择游戏 */
|
||||
function selectGame(id: string) {
|
||||
const game = games.find((g) => g.id === id)
|
||||
const game = games.value.find((g) => g.id === id)
|
||||
if (game) {
|
||||
baseLayoutStore.setActiveGame(game.id, game.icon, game.name)
|
||||
}
|
||||
|
||||
@@ -43,9 +43,10 @@
|
||||
<script setup lang="ts">
|
||||
import { ref, computed, watch } from 'vue'
|
||||
import TableCard from './TableCard.vue'
|
||||
import type { Room } from './TableCard.vue'
|
||||
import type { RoomItem } from '@/api/modules/game'
|
||||
import { useBaseLayoutStore } from '@/stores'
|
||||
import { storeToRefs } from 'pinia'
|
||||
import { getRoomList } from '@/api/modules/game'
|
||||
|
||||
/** 状态筛选选项 */
|
||||
const statusFilters = [
|
||||
@@ -58,336 +59,30 @@ const activeFilter = ref('all')
|
||||
const baseLayoutStore = useBaseLayoutStore()
|
||||
const { activeGameId } = storeToRefs(baseLayoutStore)
|
||||
|
||||
/** 切换游戏时重置筛选 */
|
||||
/** 房间列表 */
|
||||
const rooms = ref<RoomItem[]>([])
|
||||
/** 加载状态 */
|
||||
const loading = ref<boolean>(false)
|
||||
|
||||
/** 获取房间列表 */
|
||||
async function fetchRoomList() {
|
||||
loading.value = true
|
||||
try {
|
||||
const res = await getRoomList({ gameId: activeGameId.value })
|
||||
rooms.value = res.data.list
|
||||
} finally {
|
||||
loading.value = false
|
||||
}
|
||||
}
|
||||
|
||||
/** 切换游戏时重新获取房间列表并重置筛选 */
|
||||
watch(activeGameId, () => {
|
||||
activeFilter.value = 'all'
|
||||
fetchRoomList()
|
||||
})
|
||||
|
||||
/** 根据名字生成头像 URL */
|
||||
function avatarUrl(name: string): string {
|
||||
return `https://api.dicebear.com/7.x/bottts-neutral/svg?seed=${encodeURIComponent(name)}`
|
||||
}
|
||||
|
||||
/**
|
||||
* 各游戏的模拟房间数据
|
||||
* key 对应 GameList 中的 gameId
|
||||
*/
|
||||
const ALL_ROOMS: Record<string, Room[]> = {
|
||||
/* ---- 贪吃蛇 ---- */
|
||||
snake: [
|
||||
{
|
||||
id: 'snake-001',
|
||||
name: '桌 01',
|
||||
gameIcon: '🐍',
|
||||
gameId: 'snake',
|
||||
maxPlayers: 4,
|
||||
players: [
|
||||
{ avatar: avatarUrl('小龙'), nickname: '小龙' },
|
||||
{ avatar: avatarUrl('阿蟒'), nickname: '阿蟒' }
|
||||
],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 300,
|
||||
mode: '经典模式',
|
||||
creatorName: '小龙'
|
||||
},
|
||||
{
|
||||
id: 'snake-002',
|
||||
name: '桌 02',
|
||||
gameIcon: '🐍',
|
||||
gameId: 'snake',
|
||||
maxPlayers: 4,
|
||||
players: [
|
||||
{ avatar: avatarUrl('闪电'), nickname: '闪电' },
|
||||
{ avatar: avatarUrl('疾风'), nickname: '疾风' },
|
||||
{ avatar: avatarUrl('游侠'), nickname: '游侠' },
|
||||
{ avatar: avatarUrl('幻影'), nickname: '幻影' }
|
||||
],
|
||||
status: 'playing',
|
||||
statusText: '进行中',
|
||||
stakes: 500,
|
||||
mode: '道具模式',
|
||||
creatorName: '闪电'
|
||||
},
|
||||
{
|
||||
id: 'snake-003',
|
||||
name: '桌 03',
|
||||
gameIcon: '🐍',
|
||||
gameId: 'snake',
|
||||
maxPlayers: 4,
|
||||
players: [{ avatar: avatarUrl('青蛇'), nickname: '青蛇' }],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 200,
|
||||
mode: '加速模式',
|
||||
creatorName: '青蛇'
|
||||
},
|
||||
{
|
||||
id: 'snake-004',
|
||||
name: '桌 04',
|
||||
gameIcon: '🐍',
|
||||
gameId: 'snake',
|
||||
maxPlayers: 4,
|
||||
players: [],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 100,
|
||||
mode: '经典模式',
|
||||
creatorName: '毒牙'
|
||||
},
|
||||
{
|
||||
id: 'snake-005',
|
||||
name: '桌 05',
|
||||
gameIcon: '🐍',
|
||||
gameId: 'snake',
|
||||
maxPlayers: 4,
|
||||
players: [
|
||||
{ avatar: avatarUrl('巨蟒'), nickname: '巨蟒' },
|
||||
{ avatar: avatarUrl('灵蛇'), nickname: '灵蛇' },
|
||||
{ avatar: avatarUrl('毒牙'), nickname: '毒牙' }
|
||||
],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 400,
|
||||
mode: '道具模式',
|
||||
creatorName: '巨蟒'
|
||||
}
|
||||
],
|
||||
|
||||
/* ---- 俄罗斯方块 ---- */
|
||||
tetris: [
|
||||
{
|
||||
id: 'tetris-001',
|
||||
name: '桌 01',
|
||||
gameIcon: '🧊',
|
||||
gameId: 'tetris',
|
||||
maxPlayers: 2,
|
||||
players: [{ avatar: avatarUrl('方块大师'), nickname: '方块大师' }],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 300,
|
||||
mode: '1v1 对战',
|
||||
creatorName: '方块大师'
|
||||
},
|
||||
{
|
||||
id: 'tetris-002',
|
||||
name: '桌 02',
|
||||
gameIcon: '🧊',
|
||||
gameId: 'tetris',
|
||||
maxPlayers: 2,
|
||||
players: [
|
||||
{ avatar: avatarUrl('极速下落'), nickname: '极速下落' },
|
||||
{ avatar: avatarUrl('消行高手'), nickname: '消行高手' }
|
||||
],
|
||||
status: 'playing',
|
||||
statusText: '进行中',
|
||||
stakes: 500,
|
||||
mode: '竞速模式',
|
||||
creatorName: '极速下落'
|
||||
},
|
||||
{
|
||||
id: 'tetris-003',
|
||||
name: '桌 03',
|
||||
gameIcon: '🧊',
|
||||
gameId: 'tetris',
|
||||
maxPlayers: 2,
|
||||
players: [],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 150,
|
||||
mode: '1v1 对战',
|
||||
creatorName: '堆叠王者'
|
||||
},
|
||||
{
|
||||
id: 'tetris-004',
|
||||
name: '桌 04',
|
||||
gameIcon: '🧊',
|
||||
gameId: 'tetris',
|
||||
maxPlayers: 2,
|
||||
players: [{ avatar: avatarUrl('T旋大师'), nickname: 'T旋大师' }],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 200,
|
||||
mode: '1v1 对战',
|
||||
creatorName: 'T旋大师'
|
||||
},
|
||||
{
|
||||
id: 'tetris-005',
|
||||
name: '桌 05',
|
||||
gameIcon: '🧊',
|
||||
gameId: 'tetris',
|
||||
maxPlayers: 2,
|
||||
players: [
|
||||
{ avatar: avatarUrl('连击王'), nickname: '连击王' },
|
||||
{ avatar: avatarUrl('消除者'), nickname: '消除者' }
|
||||
],
|
||||
status: 'playing',
|
||||
statusText: '进行中',
|
||||
stakes: 400,
|
||||
mode: '竞速模式',
|
||||
creatorName: '连击王'
|
||||
}
|
||||
],
|
||||
|
||||
/* ---- 五子棋 ---- */
|
||||
gomoku: [
|
||||
{
|
||||
id: 'gomoku-001',
|
||||
name: '桌 01',
|
||||
gameIcon: '⚫',
|
||||
gameId: 'gomoku',
|
||||
maxPlayers: 2,
|
||||
players: [{ avatar: avatarUrl('棋圣'), nickname: '棋圣' }],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 200,
|
||||
mode: '无禁手',
|
||||
creatorName: '棋圣'
|
||||
},
|
||||
{
|
||||
id: 'gomoku-002',
|
||||
name: '桌 02',
|
||||
gameIcon: '⚫',
|
||||
gameId: 'gomoku',
|
||||
maxPlayers: 2,
|
||||
players: [
|
||||
{ avatar: avatarUrl('黑白子'), nickname: '黑白子' },
|
||||
{ avatar: avatarUrl('五连珠'), nickname: '五连珠' }
|
||||
],
|
||||
status: 'playing',
|
||||
statusText: '进行中',
|
||||
stakes: 400,
|
||||
mode: '有禁手',
|
||||
creatorName: '黑白子'
|
||||
},
|
||||
{
|
||||
id: 'gomoku-003',
|
||||
name: '桌 03',
|
||||
gameIcon: '⚫',
|
||||
gameId: 'gomoku',
|
||||
maxPlayers: 2,
|
||||
players: [],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 100,
|
||||
mode: '无禁手',
|
||||
creatorName: '落子无悔'
|
||||
},
|
||||
{
|
||||
id: 'gomoku-004',
|
||||
name: '桌 04',
|
||||
gameIcon: '⚫',
|
||||
gameId: 'gomoku',
|
||||
maxPlayers: 2,
|
||||
players: [{ avatar: avatarUrl('天元'), nickname: '天元' }],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 300,
|
||||
mode: '有禁手',
|
||||
creatorName: '天元'
|
||||
},
|
||||
{
|
||||
id: 'gomoku-005',
|
||||
name: '桌 05',
|
||||
gameIcon: '⚫',
|
||||
gameId: 'gomoku',
|
||||
maxPlayers: 2,
|
||||
players: [
|
||||
{ avatar: avatarUrl('先手必胜'), nickname: '先手必胜' },
|
||||
{ avatar: avatarUrl('后手无敌'), nickname: '后手无敌' }
|
||||
],
|
||||
status: 'playing',
|
||||
statusText: '进行中',
|
||||
stakes: 500,
|
||||
mode: '有禁手',
|
||||
creatorName: '先手必胜'
|
||||
}
|
||||
],
|
||||
|
||||
/* ---- 猜数字 ---- */
|
||||
'guess-number': [
|
||||
{
|
||||
id: 'guess-001',
|
||||
name: '桌 01',
|
||||
gameIcon: '🔢',
|
||||
gameId: 'guess-number',
|
||||
maxPlayers: 4,
|
||||
players: [
|
||||
{ avatar: avatarUrl('逻辑怪'), nickname: '逻辑怪' },
|
||||
{ avatar: avatarUrl('推理王'), nickname: '推理王' }
|
||||
],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 200,
|
||||
mode: '经典模式',
|
||||
creatorName: '逻辑怪'
|
||||
},
|
||||
{
|
||||
id: 'guess-002',
|
||||
name: '桌 02',
|
||||
gameIcon: '🔢',
|
||||
gameId: 'guess-number',
|
||||
maxPlayers: 4,
|
||||
players: [
|
||||
{ avatar: avatarUrl('秒猜'), nickname: '秒猜' },
|
||||
{ avatar: avatarUrl('心算'), nickname: '心算' },
|
||||
{ avatar: avatarUrl('直觉'), nickname: '直觉' }
|
||||
],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 300,
|
||||
mode: '限时模式',
|
||||
creatorName: '秒猜'
|
||||
},
|
||||
{
|
||||
id: 'guess-003',
|
||||
name: '桌 03',
|
||||
gameIcon: '🔢',
|
||||
gameId: 'guess-number',
|
||||
maxPlayers: 4,
|
||||
players: [{ avatar: avatarUrl('数字猎人'), nickname: '数字猎人' }],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 150,
|
||||
mode: '经典模式',
|
||||
creatorName: '数字猎人'
|
||||
},
|
||||
{
|
||||
id: 'guess-004',
|
||||
name: '桌 04',
|
||||
gameIcon: '🔢',
|
||||
gameId: 'guess-number',
|
||||
maxPlayers: 4,
|
||||
players: [
|
||||
{ avatar: avatarUrl('密码破解'), nickname: '密码破解' },
|
||||
{ avatar: avatarUrl('枚举大师'), nickname: '枚举大师' },
|
||||
{ avatar: avatarUrl('二分法'), nickname: '二分法' },
|
||||
{ avatar: avatarUrl('穷举王'), nickname: '穷举王' }
|
||||
],
|
||||
status: 'playing',
|
||||
statusText: '进行中',
|
||||
stakes: 500,
|
||||
mode: '限时模式',
|
||||
creatorName: '密码破解'
|
||||
},
|
||||
{
|
||||
id: 'guess-005',
|
||||
name: '桌 05',
|
||||
gameIcon: '🔢',
|
||||
gameId: 'guess-number',
|
||||
maxPlayers: 4,
|
||||
players: [],
|
||||
status: 'waiting',
|
||||
statusText: '等待中',
|
||||
stakes: 100,
|
||||
mode: '经典模式',
|
||||
creatorName: '神秘数字'
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
/** 当前游戏的房间列表 */
|
||||
const rooms = computed(() => ALL_ROOMS[activeGameId.value] ?? [])
|
||||
/** 首次加载 */
|
||||
fetchRoomList()
|
||||
|
||||
/** 筛选后的房间列表 */
|
||||
const filteredRooms = computed(() => {
|
||||
|
||||
@@ -72,40 +72,10 @@
|
||||
|
||||
<script setup lang="ts">
|
||||
import { computed } from 'vue'
|
||||
|
||||
/** 房间内玩家 */
|
||||
interface RoomPlayer {
|
||||
avatar: string
|
||||
nickname: string
|
||||
}
|
||||
|
||||
/** 房间数据 */
|
||||
export interface Room {
|
||||
id: string
|
||||
/** 桌号显示名,如 "桌 01" */
|
||||
name: string
|
||||
/** 游戏图标 emoji */
|
||||
gameIcon: string
|
||||
/** 游戏 ID */
|
||||
gameId: string
|
||||
/** 最大玩家数 */
|
||||
maxPlayers: number
|
||||
/** 已入座玩家列表 */
|
||||
players: RoomPlayer[]
|
||||
/** 房间状态 */
|
||||
status: 'waiting' | 'playing' | 'finished'
|
||||
/** 状态展示文字 */
|
||||
statusText: string
|
||||
/** 底注金额 */
|
||||
stakes: number
|
||||
/** 玩法模式标签 */
|
||||
mode: string
|
||||
/** 房主昵称 */
|
||||
creatorName: string
|
||||
}
|
||||
import type { RoomItem, RoomPlayer, RoomStatus } from '@/api/modules/game'
|
||||
|
||||
const props = defineProps<{
|
||||
room: Room
|
||||
room: RoomItem
|
||||
}>()
|
||||
|
||||
const emit = defineEmits<{
|
||||
|
||||
Reference in New Issue
Block a user