Godot 4中Checkpoint加载异常问题排查
核心错误原因
报错Invalid get index ‘global_position’ (on base: ‘Nil’)来自globals.gd的load_checkpoint()函数:
func load_checkpoint(): if load_checkpoint_from_file(): return { "position": current_checkpoint.global_position, # 此处current_checkpoint为null "scene": current_checkpoint_scene } else: return null
游戏重启后,current_checkpoint变量并未被赋值——加载存档时仅读取了场景路径和位置到current_checkpoint_scene和current_checkpoint_position,未关联任何Checkpoint节点,因此访问current_checkpoint.global_position触发空引用错误,导致load_checkpoint()返回null,最终走title_screen.gd的else分支加载初始场景。
分步修复
1. 修正load_checkpoint()函数逻辑
无需依赖current_checkpoint节点,直接返回已加载的current_checkpoint_position:
func load_checkpoint(): if load_checkpoint_from_file(): return { "position": current_checkpoint_position, # 改用已保存的位置变量 "scene": current_checkpoint_scene } else: return null
2. 调整场景跳转与玩家位置设置顺序
title_screen.gd中先设置玩家位置再切换场景是错误的——此时玩家仍在标题场景,切换场景后原玩家节点会被销毁,新场景的玩家是场景自带的,位置不会同步。需先切换场景,再设置玩家位置:
func _on_start_btn_pressed(): var checkpoint_data = Globals.load_checkpoint() if checkpoint_data != null: # 先切换到目标场景 get_tree().change_scene_to_file(checkpoint_data.scene) # 等待场景切换完成后设置玩家位置 await get_tree().idle_frame Globals.player.position = checkpoint_data.position else: get_tree().change_scene_to_file("res://levels/world_01.tscn")
3. 确保场景加载时玩家全局变量正确赋值
你的world.gd已在_ready()中完成Globals.player = player的赋值,需确保所有world场景都挂载了该脚本,保证场景切换后Globals.player能指向当前场景的玩家节点。
4. 清理冗余逻辑
globals.gd中respawn_player()函数已能通过current_checkpoint_position正常设置玩家位置,无需再依赖current_checkpoint节点,保持代码简洁即可。
验证修复效果
重启游戏点击开始按钮后:
- 会正确读取存档中的场景路径和位置
- 先切换到目标场景(如world_02)
- 再将玩家位置设置为存档的Checkpoint坐标
- 不再触发空引用错误,玩家从存档的场景和位置开始游戏
内容的提问来源于stack exchange,提问作者Neitan

