zoukankan      html  css  js  c++  java
  • Unity3D 游戏引擎之将场景导出XML或JSON或二进制并且解析还原场景

    导出unity场景的所有游戏对象信息,一种是XML一种是JSON。本篇文章我们把游戏场景中游戏对象的、旋转、缩放、平移与Prefab的名称导出在XML与JSON中。然后解析刚刚导出的XML或JSON通过脚本把导出的游戏场景还原。在Unity官网上下载随便下载一个demo Project,如下图所示这是我刚刚在官网上下载的一个范例程序。

    接着将层次视图中的所有游戏对象都封装成Prefab保存在资源路径中,这里注意一下如果你的Prefab绑定的脚本中有public Object 的话 ,需要在代码中改一下。。用 Find() FindTag()这类方法在脚本中Awake()方法中来拿,不然Prefab动态加载的时候无法赋值的,如下图所示,我把封装的Prefab对象都放在了Resources/Prefab文件夹下。

    OK,现在我们就需要编写我们的导出工具、在Project视图中创建Editor文件夹,接着创建脚本MyEditor 。如下图所示。

    因为编辑的游戏场景数量比较多,导出的时候我们需要遍历所有的游戏场景,一个一个的读取场景信息。然后取得游戏场景中所有游戏对象的Prefab的 名称 旋转 缩放 平移。有关XML的使用请大家看我的上一篇文章: unity3d研究院之使用 C#合成解析XML与JSON(四十一) 代码中我只注释重点的部分,嘿嘿。

      1 using UnityEngine;
      2  
      3   using System.Collections;
      4  
      5   using UnityEditor;
      6  
      7   using System.Collections.Generic;
      8  
      9   using System.Xml;
     10  
     11   using System.IO;
     12  
     13   using System.Text;
     14  
     15   using LitJson;
     16  
     17   public class MyEditor : Editor
     18  
     19   {
     20  
     21   //将所有游戏场景导出为XML格式
     22  
     23   [MenuItem (“GameObject/ExportXML”)]
     24  
     25   static void ExportXML ()
     26  
     27   {
     28  
     29   string filepath = Application.dataPath + @“/StreamingAssets/my.xml”;
     30  
     31   if(!File.Exists (filepath))
     32  
     33   {
     34  
     35   File.Delete(filepath);
     36  
     37   }
     38  
     39   XmlDocument xmlDoc = new XmlDocument();
     40  
     41   XmlElement root = xmlDoc.CreateElement(“gameObjects”);
     42  
     43   //遍历所有的游戏场景
     44  
     45   foreach (UnityEditor.EditorBuildSettingsScene S in UnityEditor.EditorBuildSettings.scenes)
     46  
     47   {
     48  
     49   //当关卡启用
     50  
     51   if (S.enabled)
     52  
     53   {
     54  
     55   //得到关卡的名称
     56  
     57   string name = S.path;
     58  
     59   //打开这个关卡
     60  
     61   EditorApplication.OpenScene(name);
     62  
     63   XmlElement scenes = xmlDoc.CreateElement(“scenes”);
     64  
     65   scenes.SetAttribute(“name”,name);
     66  
     67   foreach (GameObject obj in Object.FindObjectsOfType(typeof(GameObject)))
     68  
     69   {
     70  
     71   if (obj.transform.parent == null)
     72  
     73   {
     74  
     75   XmlElement gameObject = xmlDoc.CreateElement(“gameObjects”);
     76  
     77   gameObject.SetAttribute(“name”,obj.name);
     78  
     79   gameObject.SetAttribute(“asset”,obj.name + “.prefab”);
     80  
     81   XmlElement transform = xmlDoc.CreateElement(“transform”);
     82  
     83   XmlElement position = xmlDoc.CreateElement(“position”);
     84  
     85   XmlElement position_x = xmlDoc.CreateElement(“x”);
     86  
     87   position_x.InnerText = obj.transform.position.x+“”;
     88  
     89   XmlElement position_y = xmlDoc.CreateElement(“y”);
     90  
     91   position_y.InnerText = obj.transform.position.y+“”;
     92  
     93   XmlElement position_z = xmlDoc.CreateElement(“z”);
     94  
     95   position_z.InnerText = obj.transform.position.z+“”;
     96  
     97   position.AppendChild(position_x);
     98  
     99   position.AppendChild(position_y);
    100  
    101   position.AppendChild(position_z);
    102  
    103   XmlElement rotation = xmlDoc.CreateElement(“rotation”);
    104  
    105   XmlElement rotation_x = xmlDoc.CreateElement(“x”);
    106  
    107   rotation_x.InnerText = obj.transform.rotation.eulerAngles.x+“”;
    108  
    109   XmlElement rotation_y = xmlDoc.CreateElement(“y”);
    110  
    111   rotation_y.InnerText = obj.transform.rotation.eulerAngles.y+“”;
    112  
    113   XmlElement rotation_z = xmlDoc.CreateElement(“z”);
    114  
    115   rotation_z.InnerText = obj.transform.rotation.eulerAngles.z+“”;
    116  
    117   rotation.AppendChild(rotation_x);
    118  
    119   rotation.AppendChild(rotation_y);
    120  
    121   rotation.AppendChild(rotation_z);
    122  
    123   XmlElement scale = xmlDoc.CreateElement(“scale”);
    124  
    125   XmlElement scale_x = xmlDoc.CreateElement(“x”);
    126  
    127   scale_x.InnerText = obj.transform.localScale.x+“”;
    128  
    129   XmlElement scale_y = xmlDoc.CreateElement(“y”);
    130  
    131   scale_y.InnerText = obj.transform.localScale.y+“”;
    132  
    133   XmlElement scale_z = xmlDoc.CreateElement(“z”);
    134  
    135   scale_z.InnerText = obj.transform.localScale.z+“”;
    136  
    137   scale.AppendChild(scale_x);
    138  
    139   scale.AppendChild(scale_y);
    140  
    141   scale.AppendChild(scale_z);
    142  
    143   transform.AppendChild(position);
    144  
    145   transform.AppendChild(rotation);
    146  
    147   transform.AppendChild(scale);
    148  
    149   gameObject.AppendChild(transform);
    150  
    151   scenes.AppendChild(gameObject);
    152  
    153   root.AppendChild(scenes);
    154  
    155   xmlDoc.AppendChild(root);
    156  
    157   xmlDoc.Save(filepath);
    158  
    159   }
    160  
    161   }
    162  
    163   }
    164  
    165   }
    166  
    167   //刷新Project视图, 不然需要手动刷新哦
    168  
    169   AssetDatabase.Refresh();
    170  
    171   }
    172  
    173   //将所有游戏场景导出为JSON格式
    174  
    175   [MenuItem (“GameObject/ExportJSON”)]
    176  
    177   static void ExportJSON ()
    178  
    179   {
    180  
    181   string filepath = Application.dataPath + @“/StreamingAssets/json.txt”;
    182  
    183   FileInfo t = new FileInfo(filepath);
    184  
    185   if(!File.Exists (filepath))
    186  
    187   {
    188  
    189   File.Delete(filepath);
    190  
    191   }
    192  
    193   StreamWriter sw = t.CreateText();
    194  
    195   StringBuilder sb = new StringBuilder ();
    196  
    197   JsonWriter writer = new JsonWriter (sb);
    198  
    199   writer.WriteObjectStart ();
    200  
    201   writer.WritePropertyName (“GameObjects”);
    202  
    203   writer.WriteArrayStart ();
    204  
    205   foreach (UnityEditor.EditorBuildSettingsScene S in UnityEditor.EditorBuildSettings.scenes)
    206  
    207   {
    208  
    209   if (S.enabled)
    210  
    211   {
    212  
    213   string name = S.path;
    214  
    215   EditorApplication.OpenScene(name);
    216  
    217   writer.WriteObjectStart();
    218  
    219   writer.WritePropertyName(“scenes”);
    220  
    221   writer.WriteArrayStart ();
    222  
    223   writer.WriteObjectStart();
    224  
    225   writer.WritePropertyName(“name”);
    226  
    227   writer.Write(name);
    228  
    229   writer.WritePropertyName(“gameObject”);
    230  
    231   writer.WriteArrayStart ();
    232  
    233   foreach (GameObject obj in Object.FindObjectsOfType(typeof(GameObject)))
    234  
    235   {
    236  
    237   if (obj.transform.parent == null)
    238  
    239   {
    240  
    241   writer.WriteObjectStart();
    242  
    243   writer.WritePropertyName(“name”);
    244  
    245   writer.Write(obj.name);
    246  
    247   writer.WritePropertyName(“position”);
    248  
    249   writer.WriteArrayStart ();
    250  
    251   writer.WriteObjectStart();
    252  
    253   writer.WritePropertyName(“x”);
    254  
    255   writer.Write(obj.transform.position.x.ToString(“F5”));
    256  
    257   writer.WritePropertyName(“y”);
    258  
    259   writer.Write(obj.transform.position.y.ToString(“F5”));
    260  
    261   writer.WritePropertyName(“z”);
    262  
    263   writer.Write(obj.transform.position.z.ToString(“F5”));
    264  
    265   writer.WriteObjectEnd();
    266  
    267   writer.WriteArrayEnd();
    268  
    269   writer.WritePropertyName(“rotation”);
    270  
    271   writer.WriteArrayStart ();
    272  
    273   writer.WriteObjectStart();
    274  
    275   writer.WritePropertyName(“x”);
    276  
    277   writer.Write(obj.transform.rotation.eulerAngles.x.ToString(“F5”));
    278  
    279   writer.WritePropertyName(“y”);
    280  
    281   writer.Write(obj.transform.rotation.eulerAngles.y.ToString(“F5”));
    282  
    283   writer.WritePropertyName(“z”);
    284  
    285   writer.Write(obj.transform.rotation.eulerAngles.z.ToString(“F5”));
    286  
    287   writer.WriteObjectEnd();
    288  
    289   writer.WriteArrayEnd();
    290  
    291   writer.WritePropertyName(“scale”);
    292  
    293   writer.WriteArrayStart ();
    294  
    295   writer.WriteObjectStart();
    296  
    297   writer.WritePropertyName(“x”);
    298  
    299   writer.Write(obj.transform.localScale.x.ToString(“F5”));
    300  
    301   writer.WritePropertyName(“y”);
    302  
    303   writer.Write(obj.transform.localScale.y.ToString(“F5”));
    304  
    305   writer.WritePropertyName(“z”);
    306  
    307   writer.Write(obj.transform.localScale.z.ToString(“F5”));
    308  
    309   writer.WriteObjectEnd();
    310  
    311   writer.WriteArrayEnd();
    312  
    313   writer.WriteObjectEnd();
    314  
    315   }
    316  
    317   }
    318  
    319   writer.WriteArrayEnd();
    320  
    321   writer.WriteObjectEnd();
    322  
    323   writer.WriteArrayEnd();
    324  
    325   writer.WriteObjectEnd();
    326  
    327   }
    328  
    329   }
    330  
    331   writer.WriteArrayEnd();
    332  
    333   writer.WriteObjectEnd ();
    334  
    335   sw.WriteLine(sb.ToString());
    336  
    337   sw.Close();
    338  
    339   sw.Dispose();
    340  
    341   AssetDatabase.Refresh();
    342  
    343   }
    344  
    345   }

    原文链接:http://www.unitymanual.com/thread-36576-1-1.html?_dsign=ad7267e6

  • 相关阅读:
    《android开发艺术探索》读书笔记(八)--WindowManager
    《android开发艺术探索》读书笔记(七)--动画
    《android开发艺术探索》读书笔记(六)--Drawable
    《android开发艺术探索》读书笔记(五)--RemoteViews
    PendingIntent
    桌面小部件开发
    《android开发艺术探索》读书笔记(四)--View工作原理
    Quartz.NET开源作业调度框架系列
    多线程下C#如何保证线程安全?
    图解.NET Stack和Heap的本质区别
  • 原文地址:https://www.cnblogs.com/atong/p/4252412.html
Copyright © 2011-2022 走看看