XML設定寫入和讀取地圖
阿新 • • 發佈:2021-09-01
using System.Collections; using System.Collections.Generic; using System.IO; using System.Xml; using UnityEditor; using UnityEditor.SceneManagement; using UnityEngine; public class Menu : MonoBehaviour { private static int j = 1; private static int k = 1; /// <summary> 新增選單欄(寫入、儲存) </summary> [MenuItem("GetTransform/獲得所有角色的位置設定XML &8")] public static void SetSelectedObjPos() { //獲得選中的Transfrom元件 Transform[] objs = Selection.transforms; SaveName save = new SaveName(); for (int i = 0; i < objs.Length; i++) { SaveByXml(objs[i]); //RecursiveSave(objs[i], save); Debug.Log("儲存完成"); } } /// <summary> 新增選單欄(讀取) </summary> [MenuItem("GetTransform/從XML取得角色位置 &9")] public static void GetSelectedObjPos() { //獲得選中的Transfrom元件 Transform[] objs = Selection.transforms; //地址 string filePath = Application.dataPath + "/byXML.txt"; //檢視是否有檔案 //TODO:還需檢查是否名字和層級相同 //TODO:還需要檢查檢視是否一樣 if (File.Exists(filePath)) { //載入 XML 文件 XmlDocument xmlDoc = new XmlDocument(); //指定URL載入文件 xmlDoc.Load(filePath); //選擇XmlNode匹配(獲得第一個節點) XmlNode root = xmlDoc.SelectSingleNode("saveTransform "); //獲得root節點的所有子節點(所有第一層GameObject) XmlNodeList nodeList = root.ChildNodes; for (int i = 0; i < objs.Length; i++) { for (int j = 0; j < nodeList.Count; j++) { //將第一層的資料帶入 //LoadByXml(nodeList[j], objs[i].GetChild(j)); LoadByXml(nodeList[j], objs[i]); } Debug.Log("載入遊戲"); } } } /// <summary> 建立Xml </summary> public static void SaveByXml(Transform parent) { //建立 XML 檔案的儲存路徑 string filePath = Application.dataPath + "/byXML.txt"; //如果XML檔案已經存在,就刪除 if (File.Exists(filePath)) { File.Delete(filePath); } //建立 XML 文件 XmlDocument xmlDoc = new XmlDocument(); //建立跟節點,即最上層的節點 XmlElement root = xmlDoc.CreateElement("saveTransform"); //設定該節點的一個屬性 root.SetAttribute("場景名稱", EditorSceneManager.GetActiveScene().name); XmlElement parentObject = xmlDoc.CreateElement("GameObject層級0"); XmlElement transformXml = xmlDoc.CreateElement("Transform"); //將Xml加入 TransformXml(parent, transformXml, xmlDoc); parentObject.AppendChild(transformXml); RecursiveAllObjs(parent, parentObject, xmlDoc); root.AppendChild(parentObject); xmlDoc.AppendChild(root); xmlDoc.Save(filePath); } /// <summary> 獲得節點 </summary> private static void RecursiveAllObjs(Transform parent, XmlElement parentObject, XmlDocument xmlDoc) { for (int i = 0; i < parent.childCount; i++) //childCount的數量包括不顯示的物體 { //獲得子物體的 Transform 位置 var temp = parent.GetChild(i); //建立節點遊戲物體 XmlElement gameObjectXml = xmlDoc.CreateElement("GameObject" + "層級" + j); gameObjectXml.SetAttribute("名稱", temp.name); XmlElement transformXml = xmlDoc.CreateElement("Transform"); TransformXml(temp, transformXml, xmlDoc); gameObjectXml.AppendChild(transformXml); //將transformXml設定父節點為 root parentObject.AppendChild(gameObjectXml); //再次查詢子類中的Transform。 if (temp.childCount > 0) { j++; //迭代傳入引數 RecursiveAllObjs(temp, gameObjectXml, xmlDoc); j = 1; } } } /// <summary> 將Transform元件內容加入子類XML </summary> private static void TransformXml(Transform parent, XmlElement transformXml, XmlDocument xmlDoc) { //建立節點position XmlElement localPosition = xmlDoc.CreateElement("LocalPosition"); XmlElement localPositionX = xmlDoc.CreateElement("LocalPositionX"); XmlElement localPositionY = xmlDoc.CreateElement("LocalPositionY"); XmlElement localPositionZ = xmlDoc.CreateElement("LocalPositionZ"); localPositionX.InnerText = parent.localPosition.x.ToString(); localPositionY.InnerText = parent.localPosition.y.ToString(); localPositionZ.InnerText = parent.localPosition.z.ToString(); localPosition.AppendChild(localPositionX); localPosition.AppendChild(localPositionY); localPosition.AppendChild(localPositionZ); //建立節點rotation XmlElement localEulerAngles = xmlDoc.CreateElement("LocalEulerAngles"); XmlElement localEulerAnglesX = xmlDoc.CreateElement("LocalEulerAnglesX"); XmlElement localEulerAnglesY = xmlDoc.CreateElement("LocalEulerAnglesY"); XmlElement localEulerAnglesZ = xmlDoc.CreateElement("LocalEulerAnglesZ"); localEulerAnglesX.InnerText = parent.localEulerAngles.x.ToString(); localEulerAnglesY.InnerText = parent.localEulerAngles.y.ToString(); localEulerAnglesZ.InnerText = parent.localEulerAngles.z.ToString(); localEulerAngles.AppendChild(localEulerAnglesX); localEulerAngles.AppendChild(localEulerAnglesY); localEulerAngles.AppendChild(localEulerAnglesZ); //建立節點scale XmlElement localScale = xmlDoc.CreateElement("LocalScale"); XmlElement localScaleX = xmlDoc.CreateElement("LocalScale"); XmlElement localScaleY = xmlDoc.CreateElement("LocalScale"); XmlElement localScaleZ = xmlDoc.CreateElement("LocalScale"); localScaleX.InnerText = parent.localScale.x.ToString(); localScaleY.InnerText = parent.localScale.y.ToString(); localScaleZ.InnerText = parent.localScale.z.ToString(); localScale.AppendChild(localScaleX); localScale.AppendChild(localScaleY); localScale.AppendChild(localScaleZ); //設定父節點transformXml transformXml.AppendChild(localPosition); transformXml.AppendChild(localEulerAngles); transformXml.AppendChild(localScale); } /// <summary> 載入節點 </summary> public static void LoadByXml(XmlNode noteData, Transform parent) { int j = 1; XmlNodeList notes = noteData.ChildNodes; //獲得子物體的零號位都是Transform 位置 XmlNodeList transformData = notes[0].ChildNodes; #region 初始化物體的Transfrom //獲得Transform的零號位都是Position XmlNodeList LocalPositionData = transformData[0].ChildNodes; parent.localPosition = new Vector3(float.Parse(LocalPositionData[0].InnerText), float.Parse(LocalPositionData[1].InnerText), float.Parse(LocalPositionData[2].InnerText)); //獲得Transform的一號位都是Rotation XmlNodeList LocalEulerAnglesData = transformData[1].ChildNodes; parent.localEulerAngles = new Vector3(float.Parse(LocalEulerAnglesData[0].InnerText), float.Parse(LocalEulerAnglesData[1].InnerText), float.Parse(LocalEulerAnglesData[2].InnerText)); //獲得Transform的二號位都是Rotation XmlNodeList LocalScaleData = transformData[2].ChildNodes; parent.localScale = new Vector3(float.Parse(LocalScaleData[0].InnerText), float.Parse(LocalScaleData[1].InnerText), float.Parse(LocalScaleData[2].InnerText)); #endregion //判斷物體是否還有子物體 if (notes.Count > 1) { //排除第一個Transform節點後開始迴圈每一個 for (int i = 1; i < notes.Count; i++) { j++; var temp = parent.GetChild(i-1); //獲得的是GameObject LoadByXml(notes[i], temp); } } } }