Как я могу исправить MissingReferenceException, который говорит мне, что игровой объект уничтожен, если я его не уничтожил? - PullRequest
0 голосов
/ 20 ноября 2018

У меня есть код, который выглядит следующим образом.

public static Dictionary<int, Action> functionsMap;
void Function()
{
    if (!isDictionaryInitialized)
    {
        functionsMap = new Dictionary<int, Action>();

        functionsMap.Add(1, () => StartCoroutine(Function1()));
        functionsMap.Add(1, () => StartCoroutine(Function2()));
    }
 }

void CheckForFunction()
{
    var r = currentFunctionNumber;

    if (functionsMap.TryGetValue(r, out currentAction)) { currentAction(); }
}

Код работает нормально, когда я запускаю свою программу.Однако, если я перехожу в другую сцену и затем возвращаюсь к ней, я получаю эту ошибку.

"MissingReferenceException: объект типа 'ScriptName' был уничтожен, но вы все еще пытаетесь получить к нему доступ.сценарий должен либо проверить, является ли он нулевым, либо вы не должны уничтожать объект. "

Проблема в том, что я никогда не уничтожал объект.Изначально у меня не было bool isDictionaryInitialized, и я определил новый Dictionary вне функции, потому что я думал, что ошибка связана с моей программой, пытающейся получить доступ к Dictionary, который был удален после закрытия сцены.У меня возникает та же проблема с или без bool, и независимо от того, где я определяю Dictionary.

Что является причиной этого и какова причина, чтобы я мог избежать одной и той же ошибки?

Редактировать: Этот вопрос был помечен как дубликат, но ссылка, на которую я не верю, относится к моей ситуации, или, если это так, я не понимаю, как.В нем говорится, что статические объекты не перезагружаются при смене сцены, а Словарь определяется как статический объект.Я также попытался изменить его на нестатический, и результат тот же.

У меня есть десятки игровых объектов в моем коде, и у меня нет этой проблемы с любым другим объектом, поэтому я предполагаю, что проблема связана скак определяется объект словаря.Есть ли способ предотвратить разрушение объекта Dictionary при смене сцены?У меня его нет как игрового объекта на сцене, он просто определен в самом коде как публичный статический словарь.Может кто-нибудь сказать мне, что мне нужно сделать по-другому, пожалуйста, и спасибо?

Ответы [ 2 ]

0 голосов
/ 21 ноября 2018

Сначала вы добавляете два Action s в свой словарь, но оба с одним и тем же key.

functionsMap.Add(1, () => StartCoroutine(Function1()));
functionsMap.Add(1, () => StartCoroutine(Function2()));

не перезапишет ли это первую запись?


Чем ваша общая проблема:

В то время как functionsMap равен static два добавленных вами действия / одно действие не являются статичными (StartCoroutine всегда требует для запуска экземпляр MonoBehaviour) ипоэтому доступно только для соответствующего компонента!(Вы говорили о методе обновления, так что это должен быть MonoBehaviour, прикрепленный к GameObject в вашей первой сцене.)

Теперь, если вы измените сцену, GameObject, содержащий этот компонент, вероятно, будет уничтожен, если выне используется DontDestroyOnLoad

В результате ваш static словарь остается неизменным и заполненным, то есть запись с key = 1 все еще существует , но the Valueа именно добавленный нестатический Action больше не доступен.

Во избежание этого вы должны добавить

DontDestroyOnLoad(this.gameObject);

либо в Awake, либо в Start, чтобы предотвратить GameObjectудерживая компонент и тем самым удерживая Action, который принадлежит ссылке (ям) в записи в вашем Словаре.

0 голосов
/ 20 ноября 2018

Проблема может быть вызвана сменой сцен, потому что простая загрузка другой сцены уничтожит все игровые объекты в текущей сцене.

Согласно Object.DontDestroyOnLoad .

Загрузка новой сцены уничтожает все текущие объекты сцены.

Чтобы решить эту проблему, вы можете использовать функцию DontDestroyOnLoad, чтобы отметить объект, который вы хотите сохранить, перед загрузкой другой сцены, илииспользуя другой способ загрузки, например LoadSceneMode.Additive без разрушения текущей сцены.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...