Unity引擎2D游戏开发,场景加载后的执行逻辑

非强专业性文章,本文仅供学习与交流使用

判断场景是否加载完毕

加载新场景的返回值中,有一个Completed事件方法。可以创建一个方法去注册这个事件方法,即可在加载完毕后进行一系列的操作

c# 复制代码
private void LoadNewScene()
{
    // 加载新场景
    var loadingOperation = targetSceneToGo.assetReference.LoadSceneAsync(LoadSceneMode.Additive, true);
    loadingOperation.Completed += OnLoadComplete;
}

将首次转换的目的场景复制到当前场景,并将目的地坐标赋予给玩家的坐标位置

c# 复制代码
// 玩家坐标
public Transform playerTrans;

private void OnLoadComplete(AsyncOperationHandle<SceneInstance> handle)
{
    currentLoadScene = targetSceneToGo;

    playerTrans.position = targetPositionToGo;

    if (fadeScreen)
    {
        // TODO:淡出
    }
}

将Player拖入到PlayerTrans中,获取玩家坐标

防止传送过程中,反复点击反复加载

添加一个全局变量,用于标识是否在加载中

c# 复制代码
private bool isLoading;

OnLoadRequestEvent()方法中,添加几行代码用于判断是否正在加载

c# 复制代码
private void OnLoadRequestEvent(GameSceneSO sceneToGo, Vector3 positionToGo, bool fadeScreen)
{
    // 如果正在加载,则不执行加载过程中的任何操作
    if (isLoading)
    {
        return;
    }
    isLoading = true;
    targetSceneToGo = sceneToGo;
    targetPositionToGo = positionToGo;
    this.fadeScreen = fadeScreen;
    // 卸载当前场景,装载下一个场景
    StartCoroutine(UnloadPreviousScene());
}

在UnloadPreviousScene()方法中,关闭人物

c# 复制代码
private IEnumerator UnloadPreviousScene()
{
    if (fadeScreen)
    {
        // TODO:实现淡入
    }
    // 等待淡入淡出的指定时间
    yield return new WaitForSeconds(fadeTime);
    // 非空判断
    yield return currentLoadScene.assetReference.UnLoadScene();
    // 关闭人物
    playerTrans.gameObject.SetActive(false);

    LoadNewScene();
}

OnLoadComplete()方法的末尾,将标识置为false,并启动人物

c# 复制代码
private void OnLoadComplete(AsyncOperationHandle<SceneInstance> handle)
{
    currentLoadScene = targetSceneToGo;

    playerTrans.position = targetPositionToGo;
    // 启动人物
    playerTrans.gameObject.SetActive(true);

    if (fadeScreen)
    {
        // TODO:淡出
    }
    // 加载完毕,则把标识置为false
    isLoading = false;
}

解决传送后,头顶仍旧有按键提示的问题

在ButtonSign中,添加OnDisable()方法,将触发标识置为false

c# 复制代码
private void OnDisable()
{
    canPress = false;
}

传送回第一个场景

在第二个场景中,添加Empty Object,并绑定上Teleport Point脚本,注意调整传送点的坐标

添加Box Collider 2D,调整碰撞体边界,并调整Tag为Interactable

解决摄像机边界的问题

在CameraControl中的Start()方法内,需要做一些场景切换后的工作。需要创建一个事件,作为场景加载后需要执行的事件,来通知所有注册的方法

在Events文件夹中,新建一个VoidEventSO

SceneLoader脚本中,添加一个广播,用于发出传送后的处理事件

c# 复制代码
[Header("广播")]
public VoidEventSO afterSceneLoadedEvent;

OnLoadComplete()方法的末尾处,添加一行代码,用于唤起事件

c# 复制代码
// 场景加载完成后的事件
afterSceneLoadedEvent.RaiseEvent();

在CameraControl脚本中,添加一个监听

c# 复制代码
[Header("事件监听")]
public VoidEventSO afterSceneLoadedEvent;

进行注册和销毁

c# 复制代码
private void OnEnable()
{
    cameraShakeEvent.OnEventRaised += OnCameraShakeEvent;
    afterSceneLoadedEvent.OnEventRaised += OnAfterSceneLoadedEvent;
}

private void OnDisable()
{
    cameraShakeEvent.OnEventRaised -= OnCameraShakeEvent;
    afterSceneLoadedEvent.OnEventRaised -= OnAfterSceneLoadedEvent;
}

OnAfterSceneLoadedEvent()方法中,调用获取摄像机边界的方法

c# 复制代码
private void OnAfterSceneLoadedEvent()
{
    GetNewCameraBounds();
}

/// <summary>
/// 切换场景时,获取新的摄像机边界
/// </summary>
private void GetNewCameraBounds()
{
    var obj = GameObject.FindGameObjectWithTag("Bounds");
    if (null == obj)
    {
        return;
    }
    confiner2D.m_BoundingShape2D = obj.GetComponent<Collider2D>();
    // 清除边界缓存
    confiner2D.InvalidateCache();
}

解决刚开始没有摄像机边界的问题

在目前的代码内,加载场景并没有触发创建摄像机边界的事件,只有在创建场景结束后才触发

创建NewGame()方法,新建人物初始化坐标变量。在方法内调用OnLoadRequestEvent()场景加载事件请求方法,将目标场景和人物的初始化坐标变量传入进去即可解决

c# 复制代码
public Vector3 firstPosition;

private void NewGame()
{
    targetSceneToGo = firstLoadScene;
    OnLoadRequestEvent(targetSceneToGo, firstPosition, true);
}
相关推荐
技术小甜甜1 天前
【Blender Texture】【游戏开发】高质感 Blender 4K 材质资源推荐合集 —— 提升场景真实感与美术表现力
blender·游戏开发·材质·texture
Thomas游戏开发1 天前
Unity3D TextMeshPro终极使用指南
前端·unity3d·游戏开发
Thomas游戏开发3 天前
Unity3D 逻辑代码性能优化策略
前端框架·unity3d·游戏开发
Thomas游戏开发4 天前
Unity3D HUD高性能优化方案
前端框架·unity3d·游戏开发
陈哥聊测试4 天前
游戏公司如何同时管好上百个游戏项目?
游戏·程序员·游戏开发
一名用户5 天前
unity随机生成未知符号教程
c#·unity3d·游戏开发
Be_Somebody10 天前
计算机图形学——Games101深度解析_第二章
游戏开发·计算机图形学·games101
GameTomato11 天前
【IOS】【OC】【应用内打印功能的实现】如何在APP内实现打印功能,连接本地打印机,把想要打印的界面打印成图片
macos·ios·objective-c·xcode·游戏开发·cocos2d
Be_Somebody11 天前
计算机图形学——Games101深度解析_第一章
游戏开发·计算机图形学·games101
Thomas_YXQ17 天前
Unity3D HUD UI性能优化方案
开发语言·ui·搜索引擎·性能优化·全文检索·unity3d