c# - 公共(public)静态 Dictionary<String,GameObject> 中的游戏对象在 Unity 中的场景更改时被销毁

标签 c# dictionary unity3d singleton gameobject

第一次正式声明: 编程语言:Unity 中的 C#(MonoBehavior) 我的技能水平:有点菜鸟(不到半年的 C# 经验)。

我正在制作一款打砖 block 游戏 (Arkanoid) 并制作一个成就系统。游戏是一次性的,当您关闭网络构建时,所有内容都会被删除(没有缓存,没有文件保存,没有可序列化的类)。

成就系统包含: “成就”类:很多变量和一些跟踪进度的方法。它附加到具有相同名称的空游戏对象的脚本。普通类。

“管理器”类。初始化一堆“成就”类副本的类,给它们单独的值并将它们添加到下面提到的字典中。辛格尔顿级。

“AcheivementDictionary”类:只包含私有(private)静态字典和访问方法。也是一个单例类

问题:

成就是在第一个场景的“开始”时制作和添加的。添加后,我检索游戏对象并测试它们的标签是否有效,一切正常。然后从我的“levelManager”类中,我从下一个场景调用相同的方法,并收到一条消息,表明游戏对象已被销毁。如果我测试它们,它们也会返回 null。

所以...我真正的问题是:

如何使 Acheivement 游戏对象的实例化副本在 Unity 中的所有场景变化中持续存在?

代码引用:

我不认为“成就”是有任何问题的类,如果您需要该类的代码,请大声疾呼。

“经理”

public class Amanager : MonoBehaviour {

    public static Amanager acheivementManager = null;
public GameObject myAchObject;

void Awake () {
        if (acheivementManager != null) { 
        Destroy(gameObject);
        } else {
            acheivementManager = this;
            GameObject.DontDestroyOnLoad(gameObject);
        }
    }

void Start () {

    myAchObject.AddComponent<Acheivement>();


    initAcheivements ("completeLevelThree", "Level 3", "Complete level 3","Level", 3,5);
    initAcheivements ("completeLevelOne", "Level 1", "Complete level 1","Level", 1,5);
    }

private void initAcheivements(string inAch, string inNavn, string inHow, string inCountType, int goalVal, int Reward) {


            Vector3 loc = new Vector3 (0f, 0f,0f);
            GameObject testAch;
            testAch = Instantiate(myAchObject, loc, Quaternion.identity) as GameObject; 
            //testLives.SetActive (true);
            //testLives.gameObject.tag = "clone";

        testAch.GetComponent<Acheivement>().setName(inNavn);
        testAch.GetComponent<Acheivement>().setHowToGet(inHow);
        testAch.GetComponent<Acheivement>().setCountType(inCountType);
        testAch.GetComponent<Acheivement>().setGoalVal(goalVal);
        testAch.GetComponent<Acheivement>().setReward(Reward);
        testAch.tag = inCountType;
        Debug.Log ("InitiAch did run");
        AcheivementDictionary._Instance.achRegAdder(inNavn,testAch);
}

成就词典代码:

public class AcheivementDictionary : MonoBehaviour {
public static AcheivementDictionary _Instance;

    private static Dictionary<string,GameObject> AchReg = new Dictionary<string,GameObject>();

void Awake () {
        if (_Instance != null) { 
            Destroy(gameObject);
        } else {
            _Instance = this;
            GameObject.DontDestroyOnLoad(gameObject);
    }
    }

    public void achRegAdder (string inName, GameObject theAch) {
    AchReg.Add(inName,theAch);
    Debug.Log ("achRegAdded did run");
    readThisString = inName;
    tryRead = true;
    }

    private void readIt() {
    Debug.Log ("readItRan"); 
    GameObject testShit; 
    AchReg.TryGetValue("Level 1",out testShit);
    Debug.Log("if it works level should stand there ---> " + testShit.tag);
    tryRead = false;
    }

    public void achRegReader () {
        readIt ();
    }

运行时,控制台中会出现以下消息:

initAch did run

achRegAdded did run

initAch did run

achRegAdded did run

readItRan

if it works level should stand there ---> Level

readitRan

MissingReferenceException: The object of type "GameObject" has been destroyed but you are still trying to access it. Your script should either check if it is null or you should not destroy the obejct.

(此错误在尝试访问存储对象的标签时出现,并发生在以下方法调用中:Debug.Log("if it works level should stand there ---> "+ testShit.tag);)

这是用于在失败时调用 achRegReader 的代码行(来自另一个类): AcheivementDictionary._Instance.achRegReader();

此外:如果我计算字典中对象的数量,它会返回 2。它们只是被销毁了,我真的不明白为什么。我的程序中没有任何代码可以破坏这些。

我的猜测是这样的:

关于在 Singelton 类中放置静态字典,我不理解一些问题。 Acheivements 的实例化副本不会在场景中持续存在,因为它们不是 dontDestroyOnLoad,即使处理它们的两个类都是。 无论哪种方式,我在最后6个小时的斗争中都没有设法隔离或解决问题,请帮助!

最佳答案

在 initAcheivements 函数中,要么

testAch.transform.setParent(transform);

DontDestroyOnLoad(testAch);

您的问题是由于 testAch 不是不会被销毁的对象的子对象,或者 testAch 本身不是不会被销毁的对象。

为了回应您的评论,我快速编写了这段代码,它没有给我带来任何问题,我是不是漏掉了什么?

Vector3 loc = new Vector3(0f, 0f, 0f);
var testAch = Instantiate(myAchObject, loc, Quaternion.identity) as GameObject;
DontDestroyOnLoad(testAch);

关于c# - 公共(public)静态 Dictionary<String,GameObject> 中的游戏对象在 Unity 中的场景更改时被销毁,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42069848/

相关文章:

haskell - 在一元上下文中使用 Data.Map

android - 如何在谷歌地图中获取解析 url 以获取有关 android 中位置和邻域的详细信息

c# - 如何在 Unity 3D 中包含 SWIG 封装的 C++?

c# - XAML UWP 浮出控件定位

c# - C# 和 sql 中的负日期

c# - 使用特定数据跟踪数据库插入

c# - VS Code 有 Autos 和 Locals 调试功能吗?

ios - Swift 4 按第一个值排序字典

ios - 如何在 swift 中调用 UnitySendMessage 方法?

c# - Unity - 从阵列中获取随机天空盒