暗夜幸存者 — 设计文档
1. 概述
类 Vampire Survivors 的俯视角幸存者游戏。单机版,玩家只控制移动,武器自动攻击敌人。核心循环:击杀敌人 → 捡经验宝石 → 升级选强化 → 变强继续撑。
2. 技术栈
| 层面 | 技术 |
|---|---|
| 框架 | Vue 3 Composition API + <script setup> |
| 渲染 | HTML5 Canvas(纯几何图形,无需素材图) |
| 音频 | Web Audio API(复用 game/vue/audio.ts) |
| 输入 | 键盘 WASD + VJoystick 摇杆组件 |
| 存储 | localStorage 持久化最高分 |
| 模块位置 | game/vue/vampire/ (引擎/渲染分离) |
3. 文件结构
game/vue/
├── vampire.vue # 主视图层:Canvas + HUD + 升级选单
├── vampire/
│ ├── constants.ts # 配置常量、武器/敌人/技能定义表
│ ├── engine.ts # 主循环、实体管理、碰撞、生成、升级逻辑
│ └── renderer.ts # Canvas 绘制所有视觉元素遵循坦克/飞机/2048 已有的 engine/renderer 分离模式。
4. 核心系统
4.1 玩家
- 移动:WASD / 摇杆控制方向,恒定速度
- 生命:初始 100 HP,被敌人碰到掉血,归零游戏结束
- 自动攻击:持有武器自动锁定最近的敌人攻击
- 经验值:拾取宝石积累,攒满升级
4.2 敌人
| 敌人 | 颜色 | 特性 | 经验值 |
|---|---|---|---|
| 蝙蝠 | 紫色 | 血少、快、数量多 | 2 |
| 骷髅兵 | 灰色 | 中型、匀速、普通 | 5 |
| 恶狼 | 橙色 | 矩形、冲撞式移动 | 8 |
| BOSS | 红色 | 高血量、大体积、偶尔出现 | 50 |
- 从屏幕四边波次生成
- 越往后数量越多、速度越快、BOSS 出现频率越高
- 击杀后有概率掉落绿色经验宝石
4.3 武器
| 武器 | 效果 |
|---|---|
| 魔法飞刀 | 朝最近敌人发射穿透飞刀 |
| 烈焰光环 | 角色周围持续燃烧范围伤害 |
| 闪电链 | 间隔随机闪电劈中敌人并传导 |
| 回旋镖 | 角色周围旋转的飞行物 |
升级规则:
- 初始 1 把武器
- 每次升级随机 3 个选项(现有武器升级 / 新武器 / 回血)
- 同武器可重复选,每次提升伤害/频率/范围
4.4 难度曲线
- 时间驱动:每 30 秒进入下一"波次"
- 波次递增:生成间隔缩短、敌人数增加、BOSS 概率提升
- 目标:撑过 20 分钟即为胜利
5. UI 设计
5.1 HUD(Canvas 上层 DOM 覆盖)
┌────────────────────────────────────────────┐
│ 生命 [███████████░░░] 73/100 等级 5 │
│ 04:32 击杀 147 │
│ 经验 [█████████░░░░░░] 245/550 │
├────────────────────────────────────────────┤
│ │
│ [Canvas 游戏画面] │
│ │
├────────────────────────────────────────────┤
│ ← 返回大厅 暂停 │
└────────────────────────────────────────────┘5.2 升级选单(Canvas 上层 Vue overlay)
弹出三层选卡:
- 左侧:已有武器升级(如 魔法飞刀 Lv.3 → Lv.4)
- 中间:新武器解锁(如 获得烈焰光环)
- 右侧:立即回血 40 HP
5.3 Game Over
Canvas 半透明遮罩 + 居中文字:
- 存活时间
- 击杀总数
- 到达等级
- "再来一次" 按钮
6. 架构设计
6.1 Engine 核心
class Engine {
player: Player
enemies: Enemy[]
projectiles: Projectile[]
xpGems: XpGem[]
weapons: Weapon[]
wave: number
elapsed: number
update(dt: number): void {
- 移动玩家
- 每把武器检测最近敌人 → 发射弹道
- 弹道碰撞检测 → 扣血 → 击杀掉落
- 敌人碰撞玩家 → 扣血
- 玩家拾取 XP → 经验累计
- 升级判断 → 触发升级事件
- 波次计时 → 生成新敌人
}
}6.2 Renderer 核心
class Renderer {
render(ctx, engine, viewport): void {
- 绘制地面网格
- 绘制敌人(不同颜色/形状)
- 绘制 XP 宝石(菱形 + 浮动动画)
- 绘制弹道
- 绘制玩家(圆形 + 发光)
- 绘制武器特效
- 绘制受击/击杀特效
}
}6.3 视口系统
- 世界坐标 vs 屏幕坐标映射
- 玩家始终居中
- 敌人超出屏幕一定距离后移除
6.4 对象池
- 敌人和弹道使用对象池复用
- 避免频繁 GC,维持百级实体数的性能
7. 复用现有模块
| 模块 | 用途 |
|---|---|
VJoystick.vue | 手机端摇杆控制移动 |
audio.ts | 程序化音效(攻击/受击/升级/死亡) |
useFullscreen.ts | 全屏按钮 |
useMuted.ts | 静音切换 |
game-router.vue | Hash 路由注册新游戏 |
game-hall.vue | 大厅卡片入口 |
8. 非目标(明确不做)
- 无联网/多人功能
- 无内购/广告
- 无成就系统
- 无剧情/对话
- 无地图编辑器
- 无进化合成系统(首批不做)
9. 估算规模
| # | 文件 | 估行 |
|---|---|---|
| 1 | vampire.vue | ~300 行 |
| 2 | vampire/constants.ts | ~100 行 |
| 3 | vampire/engine.ts | ~400 行 |
| 4 | vampire/renderer.ts | ~300 行 |
| 合计 | ~1100 行 |
10. 实现顺序
constants.ts— 武器/敌人/波次配置定义engine.ts— 玩家移动、自动攻击、敌人 AI、碰撞、升级renderer.ts— Canvas 绘制全流程vampire.vue— Vue 胶水层 + HUD + 升级选单 + Game Over- 注册路由 + 大厅卡片
