HOME / 第 7 部分 · 完整游戏项目实战 / 第 95 课
MODULE 7 · 完整游戏项目实战
第 95 课 · 太空射击完整项目(三):打磨与完成
🎯 本课学习目标
- 实现 HUD、生命与游戏结束
- 接入存档与排行榜
- 完成打磨并发布
太空射击收官:HUD、结算、存档、排行榜,完整可发布的游戏。
📖 详细教学步骤
HUD搭建
- ui.tscn:CanvasLayer + 得分 Label + 生命图标 + 波次 Label
- 实时刷新(读 Globals)
GDSCRIPTextends CanvasLayer
func _process(delta):
$ScoreLabel.text = "得分: %d" % Globals.score
$WaveLabel.text = "波次: %d" % Globals.wave
update_lives(Globals.lives)
玩家死亡与游戏结束代码
飞船被撞/被击中 → 扣命 → 命尽结束:
GDSCRIPTfunc take_damage():
if shield:
shield = false
return
Globals.lives -= 1
GameAudio.hit()
shake()
if Globals.lives <= 0:
game_over()
func game_over():
# 记录最高分
if Globals.score > Globals.best_score:
Globals.best_score = Globals.score
# 判断上榜
if Leaderboard.qualifies(Globals.score):
show_name_input()
else:
show_game_over()
结算界面搭建
- 游戏结束面板:最终得分 + 最高分 + 重玩/主菜单按钮
- 上榜时先输入名字 → 存排行榜 → 显示
存档代码
保存最高分与排行榜(第 62/66 课):
GDSCRIPT# Globals.gd
func save():
var data = {"best_score": best_score}
var file = FileAccess.open("user://save.json", FileAccess.WRITE)
file.store_string(JSON.stringify(data))
file.close()
func load_save():
if FileAccess.file_exists("user://save.json"):
var file = FileAccess.open("user://save.json", FileAccess.READ)
var d = JSON.parse_string(file.get_as_text())
file.close()
if d:
best_score = d.get("best_score", 0)
主菜单整合集成
- 主菜单:开始 / 排行榜 / 设置 / 退出
- 排行榜界面读 Leaderboard 显示前 10(第 66 课)
- 设置界面:音量/全屏(第 65 课)
完整测试清单测试
- ✅ 菜单 → 开始 → 游戏
- ✅ 战斗 → 道具 → 死亡 → 结束
- ✅ 结束 → 上榜 → 输入名字 → 排行榜显示
- ✅ 重玩 → 分数重置
- ✅ 主菜单 → 排行榜/设置正常
- ✅ 重开游戏 → 最高分保留
打磨与发布收尾
- 音效、特效、手感最后过一遍
- 用第 78 课剖析器确认性能
- 用第 96-98 课导出到 Windows / Web
- 让朋友试玩,收集反馈再优化
🎉 《星域猎手》完成!这是你第一个「完整可发布」的原创游戏。
⚠️
重玩后分数没重置?
开始新游戏时调 Globals.reset_game() 清零。
⚠️
排行榜不刷新?
打开排行榜界面时调用 refresh() 重新渲染。
🧪 动手试一试
🏋️ 课后练习
给游戏加「暂停」(Esc)+ 暂停菜单(继续/重开/回菜单),并确保暂停时计时与射击停止。
第 25 课状态机 + get_tree().paused。
💡
发布前用「完整测试清单」逐项过一遍,别凭感觉。
💡
一个游戏从「能玩」到「能发布」差的就是打磨与测试。
🎓 本课小结
太空射击完整版:HUD + 生命 + 结算 + 存档 + 排行榜 + 暂停 + 全流程测试;一个真正「可发布」的完整游戏。