首页 > 解决方案 > 如何从方法中返回转换或游戏对象列表而不为新游戏对象创建实例?

问题描述

 using UnityEngine;
 using System.Collections;
 using System.Collections.Generic;
 using System.IO;
 using UnityEngine.SceneManagement;

 public static class TransformSaver
 {
     [System.Serializable]
     public class TransformInfo
     {
         public string sceneName;
         public string name;
         public Transform parent;
         public Vector3 pos;
         public Quaternion rot;
         public Vector3 scale;
     }

     //Save Transform
     public static void SaveTransform(Transform[] tranformToSave)
     {
         TransformInfo[] trnfrm = new TransformInfo[tranformToSave.Length];
         for (int i = 0; i < trnfrm.Length; i++)
         {
             trnfrm[i] = new TransformInfo();

             trnfrm[i].sceneName = tranformToSave[i].gameObject.scene.name;
             trnfrm[i].name = tranformToSave[i].name;
             trnfrm[i].parent = tranformToSave[i].parent;
             trnfrm[i].pos = tranformToSave[i].localPosition;
             trnfrm[i].rot = tranformToSave[i].localRotation;
             trnfrm[i].scale = tranformToSave[i].localScale;
         }

         string jsonTransform = JsonHelper.ToJson(trnfrm, true);
         File.WriteAllText(@"d:\json\json.txt", jsonTransform);
     }

     //Load Transform
     public static Transform[] LoadTransform()
     {
         string jsonTransform = File.ReadAllText(@"d:\json\json.txt");
         if (jsonTransform == null)
         {
             return null;
         }

         TransformInfo[] savedTransforms = JsonHelper.FromJson<TransformInfo>(jsonTransform);
         GameObject[] gameObjects = new GameObject[savedTransforms.Length];
         Transform[] loadedTransforms = new Transform[savedTransforms.Length];

         for (int i = 0; i < gameObjects.Length; i++)
         {
             SceneManager.SetActiveScene(SceneManager.GetSceneByName(savedTransforms[i].sceneName));

             gameObjects[i] = new GameObject();
             loadedTransforms[i] = gameObjects[i].transform;
             loadedTransforms[i].name = savedTransforms[i].name;
             loadedTransforms[i].parent = savedTransforms[i].parent;
             loadedTransforms[i].localPosition = savedTransforms[i].pos;
             loadedTransforms[i].localRotation = savedTransforms[i].rot;
             loadedTransforms[i].localScale = savedTransforms[i].scale;
         }
         return loadedTransforms;
     }
 }

问题是 LoadTransform 方法将返回变换数组,但也会在层次结构的编辑器中创建新的游戏对象。

我想要做的是添加类似布尔标志或其他方式的东西,这样我就可以选择 toe 是否返回转换数组,无论是否创建新的游戏对象,所以我尝试了类似的方法:

 //Load Transform
     public static Transform[] LoadTransform(bool returnInfo)
     {
         string jsonTransform = File.ReadAllText(@"d:\json\json.txt");
         if (jsonTransform == null)
         {
             return null;
         }

         TransformInfo[] savedTransforms = JsonHelper.FromJson<TransformInfo>(jsonTransform);
         GameObject[] gameObjects = new GameObject[savedTransforms.Length];
         Transform[] loadedTransforms = new Transform[savedTransforms.Length];

         for (int i = 0; i < gameObjects.Length; i++)
         {
             SceneManager.SetActiveScene(SceneManager.GetSceneByName(savedTransforms[i].sceneName));

             if (returnInfo == true)
             {
                 gameObjects[i] = new GameObject();
                 loadedTransforms[i] = gameObjects[i].transform;
             }
             loadedTransforms[i].name = savedTransforms[i].name;
             loadedTransforms[i].parent = savedTransforms[i].parent;
             loadedTransforms[i].localPosition = savedTransforms[i].pos;
             loadedTransforms[i].localRotation = savedTransforms[i].rot;
             loadedTransforms[i].localScale = savedTransforms[i].scale;
         }
         return loadedTransforms;
     }

我添加了一个布尔标志returnInfo,但现在loadedTransforms 为空。

但主要目标是决定是否返回转换数组,是否为新游戏对象创建实例。

问题是当我使用 Editorwindow 类型脚本并在 OnGUI 内部保存和加载对象时:

  List<GameObject> selections = Selection.objects.OfType<GameObject>().ToList();
          if (selections.Count > 0)
          {
              GUI.enabled = true;
          }
          else
          {
              GUI.enabled = false;
          }
          if (GUILayout.Button("Save selected objects data"))
          {
              if (selections.Count > 0)
              {
                              tempTransformSelection = selections;
                  for (var i = selections.Count - 1; i >= 0; --i)
                  {
                      var selected = selections[i];
                      transformSelection.Add(selected.transform);
                  }

                  TransformSaver.SaveTransform(transformSelection.ToArray());
                  transformSelection = new List<Transform>();
              }
          }

          var file = @"d:\json\json.txt";
          FileInfo fi = new FileInfo(file);

          // By default asume you don't want to show the button
          // it will than only be enabled if the later conditions match
          bool showButton = false;

          // you can check this already here not in the loop
          // if no file -> nothing to do
          if (!File.Exists(@"d:\json\json.txt") || fi.Length <= 0) return;


          // This is only reached if the file exists and is not empty
          // check for null transforms
          for (int i = 0; i < tempTransformSelection.Count(); i++)
          {
              // if not null do nothing
              if (tempTransformSelection[i] != null)
                  continue;

              // otherwise enable the button and leave the loop
              showButton = true;
              break;
          }

          // if not true then button won't be shown
          if (showButton == true)
          {
              GUI.enabled = true;
          }
          else
          {
              GUI.enabled = false;
          }
          if (GUILayout.Button("Instantiate back deleted selected bojects"))
          {
              TransformSaver.LoadTransform(true);
              showButton = false;
          }
      }

      private void OnInspectorUpdate()
      {
          Repaint();
      }

主要目标是在编辑器的层次结构中选择对象。然后单击“保存选定对象数据”以将选定对象保存到 json 文件。

然后,我只想在层次结构中保存到文件的对象之一为空时才这样做,例如,如果我删除了保存文件中的一个或多个对象!只有这样才启用真正的按钮“实例化已删除的选定项目”

然后当单击“实例化返回已删除选定对象”按钮时,将按钮设置回启用 false !

但重要的是根据 json 文件中保存的对象列表检查 null !但是我又一次被 tempTransformSelection 以及如何启用 false/true 按钮所困扰。

标签: c#unity3d

解决方案


推荐阅读