天天看點

Unity SceneManager場景管理Chinar詳解API12345其他

Unity 場景API詳解

本文提供全圖文流程,中文翻譯。

Chinar 堅持将簡單的生活方式,帶給世人!

(擁有更好的閱讀體驗 —— 高分辨率使用者請根據需求調整網頁縮放比例)

Chinar —— 心分享、心創新!

助力快速了解 Unity 場景管理的 API 諸多用法

給新手節省寶貴的時間,避免采坑!

Chinar 教程效果:

Unity SceneManager場景管理Chinar詳解API12345其他
全文高清圖檔,點選即可放大觀看 (很多人竟然不知道)

1

SceneManager —— 場景管理

我們在遊戲開發中,經常用到關卡切換、場景切換、加載場景等諸多功能性操作

Unity 為我們提供了場景管理類,可以很友善的對場景進行各類操作

下邊我們就來逐一的看一下,API中的函數具體用法

另附——

官方API連結 其他
Unity SceneManager場景管理Chinar詳解API12345其他
Unity SceneManager場景管理Chinar詳解API12345其他

2

API —— API(建立/擷取/加載)

直接給大家貼上中文注釋,便于初學者學習

其他易出錯的函數, Chinar 也用了簡單例子做了說明,避免初學者踩坑!

提示:

其中 0 号場景為: SampleScene

其中 1 号場景為: Chinar

Unity SceneManager場景管理Chinar詳解API12345其他
using System.Collections;
using UnityEngine;
using UnityEngine.SceneManagement;


/// <summary>
/// 場景管理測試類
/// </summary>
public class ChinarSceneManager1 : MonoBehaviour
{
    /// <summary> 
    /// 初始化函數
    /// </summary>
    void Start()
    {
        SceneManager.CreateScene("Chinar");                             //使用給定名稱在運作時建立一個空的新場景
        SceneManager.GetActiveScene();                                  //擷取目前活動的場景
        SceneManager.GetSceneAt(0);                                     //在SceneManager的已加載場景清單中擷取索引處的場景
        SceneManager.GetSceneByBuildIndex(0);                           //從建構Build Setting中索引擷取Scene結構
        SceneManager.GetSceneByName("Chinar");                          //搜尋給定名稱的場景
        SceneManager.GetSceneByPath("Assets/Scenes/SampleScene.unity"); //搜尋給定路徑的場景
        SceneManager.LoadScene(1);                                      //根據“Build Setting”中索引加載場景
        SceneManager.LoadScene("Chinar");                               //根據“Build Setting”中名稱加載場景
        SceneManager.LoadScene(1,        LoadSceneMode.Additive);       //加載場景,加載方式:保留目前場景,附加指定場景
        SceneManager.LoadScene("Chinar", LoadSceneMode.Single);         //加載場景,加載方式:關閉所有目前加載的場景并加載場景
        SceneManager.LoadSceneAsync(1);                                 //根據下标,在背景異步加載場景
        SceneManager.LoadSceneAsync("Chinar");                          //根據名稱,在背景異步加載場景
        SceneManager.LoadSceneAsync(1, LoadSceneMode.Additive);         //異步加載,方式:附加
        SceneManager.LoadSceneAsync(1);                                 //異步加載,方式:單一
        SceneManager.UnloadSceneAsync("Chinar");                        //銷毀與給定場景關聯的所有GameObject,并從SceneManager中移除場景。
    }
}           

3

API (Merge) —— 常用API(合并/移動對象/設定活動)

有時我們需要将場景合并

或者将目前場景的遊戲對象,移動到其他場景中 / 設定活躍場景

進行這三類操作,都需要先将目标場景加載後,才可保證函數正确執行

這裡為了便于初學者了解,我用了協成加載的方式,來做說明

Unity SceneManager場景管理Chinar詳解API12345其他
using System.Collections;
using UnityEngine;
using UnityEngine.SceneManagement;


/// <summary>
/// 場景管理測試類
/// </summary>
public class ChinarSceneManager1 : MonoBehaviour
{
    /// <summary> 
    /// 初始化函數
    /// </summary>
    void Start()
    {
        StartCoroutine(MergeMethodEnumerator());           //合并場景
        StartCoroutine(MoveGameObjectToSceneEnumerator()); //移動遊戲對象到目标場景
        StartCoroutine(SetActiveSceneEnumerator());        //設定場景為活動場景
    }


    /// <summary>
    /// 合并場景
    /// 必須要保證:要合并的場景被加載後,才可以正确合并
    /// 如果物體名稱相同,并不會合并,互相獨立
    /// </summary>
    IEnumerator MergeMethodEnumerator()
    {
        yield return SceneManager.LoadSceneAsync(1, LoadSceneMode.Additive);                           //等待場景加載完畢後,再向下執行
        SceneManager.MergeScenes(SceneManager.GetSceneByBuildIndex(1), SceneManager.GetActiveScene()); //源場景 1,目标場景:目前 —— 将源場景合并到目标場景中
    }


    /// <summary>
    /// 移動遊戲對象到新場景
    /// 必須要保證:目标場景被加載後,遊戲對象才能被正确移動到目标場景中
    /// 如果物體名稱相同,并不會合并,互相獨立
    /// </summary>
    IEnumerator MoveGameObjectToSceneEnumerator()
    {
        yield return SceneManager.LoadSceneAsync(1, LoadSceneMode.Additive);                                //等待場景加載完畢後,再向下執行
        SceneManager.MoveGameObjectToScene(GameObject.Find("Cube"), SceneManager.GetSceneByName("Chinar")); //将目前場景中的 Cube,移動到目标場景中
        SceneManager.UnloadSceneAsync(SceneManager.GetActiveScene());                                       //解除安裝掉目前場景
        //如果要加載單個場景,請確定在要移動到新場景的GameObject上使用DontDestroyOnLoad,否則Unity會在加載新場景時删除它。
    }


    /// <summary>
    /// 設定場景為活動場景
    /// 必須要保證:目标場景被加載後,才可以正确設定活動狀态
    /// </summary>
    IEnumerator SetActiveSceneEnumerator()
    {
        yield return SceneManager.LoadSceneAsync(1, LoadSceneMode.Additive); //等待場景加載完畢後,再向下執行
        SceneManager.SetActiveScene(SceneManager.GetSceneAt(1));             //設定場景為活動場景
        //print(SceneManager.GetSceneAt(1).IsValid());
    }
}           

4

Scene (Events) —— 場景事件

有時我們需要場景記載/解除安裝/變更時,進行一系列操作

這時我們需要用事件來完成通知

Unity SceneManager場景管理Chinar詳解API12345其他
using System.Collections;
using UnityEngine;
using UnityEngine.SceneManagement;


/// <summary>
/// 場景管理測試類
/// </summary>
public class ChinarSceneManager1 : MonoBehaviour
{
    /// <summary> 
    /// 初始化函數
    /// </summary>
    void Start()
    {
        SceneManager.activeSceneChanged += SceneManager_activeSceneChanged; //訂閱此事件可在活動場景發生更改時收到通知。
        StartCoroutine(SetActiveSceneEnumerator());                         //活動場景切換時,會收到通知,列印輸出"活動場景變更了"
        SceneManager.sceneLoaded += SceneManager_sceneLoaded;               //委托 —— 加載場景時收到通知
        SceneManager.LoadSceneAsync(1);                                     //異步加載,加載方式:單一
        SceneManager.sceneUnloaded += SceneManager_sceneUnloaded;           //委托 —— 解除安裝Scene時收到通知
    }


    /// <summary>
    /// 設定場景為活動場景
    /// 必須要保證:目标場景被加載後,才可以正确設定活動狀态
    /// </summary>
    IEnumerator SetActiveSceneEnumerator()
    {
        yield return SceneManager.LoadSceneAsync(1, LoadSceneMode.Additive); //等待場景加載完畢後,再向下執行
        SceneManager.SetActiveScene(SceneManager.GetSceneAt(1));             //設定場景為活動場景
    }


    /// <summary>
    /// 活動場景變動時被調用
    /// </summary>
    private void SceneManager_activeSceneChanged(Scene arg0, Scene arg1)
    {
        print("活動場景變更了");
    }


    /// <summary>
    /// 場景被加載後,被調用
    /// </summary>
    private void SceneManager_sceneLoaded(Scene arg0, LoadSceneMode arg1)
    {
        print("場景被加載了");
    }


    /// <summary>
    /// 場景被解除安裝時,被調用
    /// </summary>
    private void SceneManager_sceneUnloaded(Scene arg0)
    {
        print("場景被解除安裝了");
    }
}           

5

Scene —— 場景自身的一些屬性

Scene 類自身具備一些屬性和字段,便于我們對場景的狀态進行了解/操作

Unity SceneManager場景管理Chinar詳解API12345其他
using System.Collections;
using UnityEngine;
using UnityEngine.SceneManagement;


/// <summary>
/// 場景管理測試類
/// </summary>
public class ChinarSceneManager1 : MonoBehaviour
{
    /// <summary> 
    /// 初始化函數
    /// </summary>
    void Start()
    {
        print(SceneManager.GetActiveScene().buildIndex);           //傳回“Build Setting”中場景的索引。如果場景是通過AssetBundle加載的,則始終傳回-1。
        print(SceneManager.GetActiveScene().isDirty);              //如果場景被修改,則傳回true。
        print(SceneManager.GetActiveScene().isLoaded);             //如果加載場景,則傳回true。
        print(SceneManager.GetActiveScene().name);                 //傳回場景的名稱。
        print(SceneManager.GetActiveScene().path);                 //傳回場景的相對路徑。喜歡:“Assets/Scenes/SampleScene.unity”。
        print(SceneManager.GetActiveScene().rootCount);            //傳回場景的遊戲對象個數
        print(SceneManager.GetActiveScene().GetHashCode());        //傳回場景的哈希值
        print(SceneManager.GetActiveScene().GetRootGameObjects()); //傳回場景中所有遊戲對象,是一個GameObject[] 數組
        foreach (var a in SceneManager.GetActiveScene().GetRootGameObjects())
        {
            print(a.name);
        }
        StartCoroutine(SetActiveSceneEnumerator());  //設定場景為活動場景
        print(SceneManager.GetSceneAt(1).IsValid()); //判斷場景是否有效,如果場景未被加載/或是不存在,則場景可能無效
    }


    /// <summary>
    /// 設定場景為活動場景
    /// 必須要保證:目标場景被加載後,才可以正确設定活動狀态
    /// </summary>
    IEnumerator SetActiveSceneEnumerator()
    {
        yield return SceneManager.LoadSceneAsync(1, LoadSceneMode.Additive); //等待場景加載完畢後,再向下執行
        SceneManager.SetActiveScene(SceneManager.GetSceneAt(1));             //設定場景為活動場景
    }
}           

May Be —— 搞開發,總有一天要做的事!

擁有自己的伺服器,無需再找攻略!

Chinar 提供一站式教程,閉眼式建立!

為新手節省寶貴時間,避免采坑!

伺服器、建站、備案、網站配置等(伺服器相關教程大全)

END

本部落格為非營利性個人原創,除部分有明确署名的作品外,所刊登的所有作品的著作權均為本人所擁有,本人保留所有法定權利。違者必究

對于需要複制、轉載、連結和傳播部落格文章或内容的,請及時和本部落客進行聯系,留言,Email: [email protected]

對于經本部落客明确授權和許可使用文章及内容的,使用時請注明文章或内容出處并注明網址

繼續閱讀