HTX Frederikshavn & Hjørring

Det har aldrig været sjovere at være nørd

Brugerværktøjer

Webstedsværktøjer


ddu:godot:multiple_levels

Flere Scener (Levels)


SceneManager klasse

Lav et Area2D med en collision shape der fange når en Player er nået i mål og skal skifte scene.

Tilføj nedenstående script:

using Godot;
using System;
 
using Godot;
using System.Threading.Tasks;
 
public partial class SceneManager : CanvasLayer
{
	private ColorRect _fadeRect;
 
	private string _nextScene;
	private string _spawnPoint;
 
	public override void _Ready()
	{
		_fadeRect = GetNode<ColorRect>("ColorRect");
		_fadeRect.Modulate = new Color(0, 0, 0, 0); // transparent
	}
 
public async void ChangeScene(string scenePath, string spawnPoint = "")
{
	// Gem hvilken scene vi vil skifte til
	_nextScene = scenePath;
 
	// Gem hvilket spawn point player skal starte ved i næste scene
	_spawnPoint = spawnPoint;
 
	// Fade skærmen til sort (så spiller ikke ser scene-skift)
	await FadeOut();
 
	// Start async load af scene så vi undgår freeze / hakken)
	await LoadSceneAsync();
 
	// Selve scene-skiftet 	// Den gamle scene fjernes og den nye instanseres
	GetTree().ChangeSceneToFile(_nextScene);
 
	// Vent 1 frame dette  giver Godot tid til at færdiggøre scene-skiftet
	// (ellers findes player/node ikke endnu)
	await ToSignal(GetTree(), SceneTree.SignalName.ProcessFrame);
 
	// Find player + spawn point i den nye scene
	// og sæt player position korrekt
	SetPlayerSpawn();
 
	// Fade tilbage fra sort
	await FadeIn();
}
 
	private async Task FadeOut()
	{
		var tween = CreateTween();
		tween.TweenProperty(_fadeRect, "modulate:a", 1.0f, 0.3f);
		await ToSignal(tween, Tween.SignalName.Finished);
	}
 
	private async Task FadeIn()
	{
		var tween = CreateTween();
		tween.TweenProperty(_fadeRect, "modulate:a", 0.0f, 0.3f);
		await ToSignal(tween, Tween.SignalName.Finished);
	}
 
	private async Task LoadSceneAsync()
	{
		var loader = ResourceLoader.LoadThreadedRequest(_nextScene);
 
		while (ResourceLoader.LoadThreadedGetStatus(_nextScene) == ResourceLoader.ThreadLoadStatus.InProgress)
		{
			await ToSignal(GetTree(), SceneTree.SignalName.ProcessFrame);
		}
	}
 
	private void SetPlayerSpawn()
	{
		if (_spawnPoint == "") return;
 
		var player = GetTree().GetFirstNodeInGroup("player") as Node2D;
		var spawn = GetTree().GetFirstNodeInGroup(_spawnPoint) as Node2D;
 
		if (player != null && spawn != null)
		{
			player.GlobalPosition = spawn.GlobalPosition;
		}
	}
}

Scriptet tilføjes som Autoload i Projekt properties, under navnet 'SceneManager'

ScenePortal

using Godot;
using System;
 
using Godot;
 
public partial class ScenePortal : Area2D
{
	[Export(PropertyHint.File, "*.tscn")]
	public string TargetScene;
	[Export] public string TargetSpawnPoint;
 
	public override void _Ready()
	{
		BodyEntered += OnBodyEntered;
	}
 
	private void OnBodyEntered(Node body)
	{
		if (!body.IsInGroup("player")) return;
		// Vi henviser til vores globale(Autoload) SceneManager
		GetNode<SceneManager>("/root/SceneManager").ChangeScene(TargetScene, TargetSpawnPoint);
	}
}

Obs ! når man skifter fra en scene A til en anden scene B, vil den information der var i scene A blive glemt. Har man information så som score, health og andet bør man ikke gemme dette direkte i scenen. Her kan det være en god ide at gemme værdier i en Global/Autload.


ddu/godot/multiple_levels.txt · Sidst ændret: af 127.0.0.1