Attention: Here be dragons
This is the latest
(unstable) version of this documentation, which may document features
not available in or compatible with released stable versions of Godot.
Checking the stable version of the documentation...
手動切換場景
有時候你會需要更細緻地控制場景的切換方式。Viewport 的子節點會算繪到它所產生的影像中,即使這些節點並不屬於「目前」場景也一樣。自動載入(Autoload)的節點屬於這一類,同時在執行時動態實例化並加入樹狀結構的場景也是:
var simultaneous_scene = preload("res://levels/level2.tscn").instantiate()
func _add_a_scene_manually():
# This is like autoloading the scene, only
# it happens after already loading the main scene.
get_tree().root.add_child(simultaneous_scene)
public Node simultaneousScene;
public MyClass()
{
simultaneousScene = ResourceLoader.Load<PackedScene>("res://levels/level2.tscn").Instantiate();
}
public void _AddASceneManually()
{
// This is like autoloading the scene, only
// it happens after already loading the main scene.
GetTree().Root.AddChild(simultaneousScene);
}
要完成流程,將新場景與舊場景交換時,你有多種選擇。從 Viewport 視圖中移除場景的方法有很多,這些方法在操作速度、記憶體消耗,以及資料存取與完整性等方面都各有取捨。
刪除現有場景。 SceneTree.change_scene_to_file() 與 SceneTree.change_scene_to_packed() 會立即刪除目前場景。你也可以手動刪除主場景,假設根節點名稱為「Main」,可以執行
get_node("/root/Main").free()來刪除整個場景。釋放記憶體。
優點:記憶體不再被佔用。
缺點:若要再次回到該場景,必須重新載入到記憶體,這會消耗更多時間與記憶體。如果不需要很快切回原場景,這通常不是問題。
缺點:無法再存取該場景的資料。如果短期內不需要用到這些資料,問題不大。
注意:如果需要保留即將被刪除場景中的資料,可以將其中一個或多個節點重新掛載到其他場景,甚至直接掛載到 SceneTree 上。
處理停止。
優點:沒有節點就沒有運算、物理運算或輸入處理,CPU 可專注處理新場景內容。
缺點:這些節點的運算與輸入處理都不再進行。如果不需要即時的資料更新,問題不大。
Hide the existing scene. By changing the visibility or collision detection of the nodes, you can hide the entire node sub-tree from the player's perspective. Use CanvasItem.hide() to hide a scene and CanvasItem.show() to show it again.
記憶體仍被佔用。
優點:如有需要,仍可存取資料。
優點:不必再移動任何節點即可保留資料。
缺點:更多資料會繼續佔用記憶體,對於像網頁或手機這種對記憶體敏感的平台可能會造成問題。
仍然持續處理。
優點:資料會持續接收處理更新,因此場景內依賴 delta time 或影格資料的內容會持續更新。
優點:節點仍然會是群組的成員(因為群組屬於 SceneTree)。
缺點:CPU 的運算量會分散到多個場景,如果負載過大可能導致畫面更新率降低。建議隨時測試效能,確保目標平台能承受這種負載。
Remove the existing scene from the tree. Assign a variable to the existing scene's root node. Then use Node.remove_child(Node) to detach the entire scene from the tree. To attach it later, use Node.add_child(Node).
記憶體仍被佔用(優缺點與隱藏場景方式相似)。
停止處理(優缺點與完全刪除場景相似)。
優點:這種「隱藏」變體更容易顯示/隱藏場景,只需呼叫 add_child 或 remove_child 方法,而不必追蹤場景的多次變動。這類似於其他引擎裡的遊戲物件啟用/停用功能。
缺點:與單純隱藏場景不同,如果場景內的資料依賴 delta time、輸入、群組或其他來自 SceneTree 的資料,這些內容會變得過時。
有時你可能需要同時存在多個場景,例如在執行時新增自訂單例,或在切換場景時保留資料(將場景加到根節點下)。
get_tree().root.add_child(scene)
GetTree().Root.AddChild(scene);
另一種情境是使用 SubViewportContainers 同時顯示多個場景。這非常適合在螢幕不同區域算繪不同內容(如小地圖或分割畫面的多人遊戲)。
每種選項都有其最合適的應用時機,因此你必須評估每種方式的效果,選擇最適合自己專案需求的做法。