예제 #1
0
        public override void Read(AssetReader reader)
        {
            base.Read(reader);

            if (IsReadPreloadTable(reader.Version))
            {
                m_preloadTable = reader.ReadAssetArray <PPtr <Object> >();
            }

            m_container = reader.ReadKVPStringTArray <AssetBundles.AssetInfo>();
            MainAsset.Read(reader);

            if (IsReadScriptCampatibility(reader.Version))
            {
                m_scriptCampatibility = reader.ReadAssetArray <AssetBundleScriptInfo>();
            }
            if (IsReadClassCampatibility(reader.Version))
            {
                m_classCampatibility = reader.ReadKVPInt32UInt32Array();
            }

            if (IsReadClassVersionMap(reader.Version))
            {
                m_classVersionMap = new Dictionary <int, int>();
                m_classVersionMap.Read(reader);
            }

            if (IsReadRuntimeCompatibility(reader.Version))
            {
                RuntimeCompatibility = reader.ReadUInt32();
            }

            if (IsReadAssetBundleName(reader.Version))
            {
                AssetBundleName = reader.ReadString();
                m_dependencies  = reader.ReadStringArray();
            }
            if (IsReadIsStreamedSceneAssetBundle(reader.Version))
            {
                IsStreamedSceneAssetBundle = reader.ReadBoolean();
                reader.AlignStream(AlignType.Align4);
            }
            if (IsReadExplicitDataLayout(reader.Version))
            {
                ExplicitDataLayout = reader.ReadInt32();
            }
            if (IsReadPathFlags(reader.Version))
            {
                PathFlags = reader.ReadInt32();
            }

            if (IsReadSceneHashes(reader.Version))
            {
                m_sceneHashes = new Dictionary <string, string>();
                m_sceneHashes.Read(reader);
            }
        }
예제 #2
0
        public override void Read(AssetStream stream)
        {
            base.Read(stream);

            if (IsReadPreloadTable(stream.Version))
            {
                m_preloadTable = stream.ReadArray <PPtr <Object> >();
            }

            m_container = stream.ReadStringKVPArray <AssetBundles.AssetInfo>();
            MainAsset.Read(stream);

            if (IsReadScriptCampatibility(stream.Version))
            {
                m_scriptCampatibility = stream.ReadArray <AssetBundleScriptInfo>();
            }
            if (IsReadClassCampatibility(stream.Version))
            {
                m_classCampatibility = stream.ReadInt32KVPUInt32Array();
            }

            if (IsReadClassVersionMap(stream.Version))
            {
                m_classVersionMap = new Dictionary <int, int>();
                m_classVersionMap.Read(stream);
            }

            if (IsReadRuntimeCompatibility(stream.Version))
            {
                RuntimeCompatibility = stream.ReadUInt32();
            }

            if (IsReadAssetBundleName(stream.Version))
            {
                AssetBundleName = stream.ReadStringAligned();
                m_dependencies  = stream.ReadStringArray();
            }
            if (IsReadIsStreamedSceneAssetBundle(stream.Version))
            {
                IsStreamedSceneAssetBundle = stream.ReadBoolean();
                stream.AlignStream(AlignType.Align4);
            }

            if (IsReadPathFlags(stream.Version))
            {
                PathFlags = stream.ReadInt32();
            }
        }
예제 #3
0
 protected override void WriteBase(AssetsWriter writer)
 {
     base.WriteBase(writer);
     writer.Write(Name);
     writer.WriteArrayOf(PreloadTable, (x, y) => x.WritePtr(y));
     writer.WriteArrayOf(Container, (x, y) => x.Write(y));
     MainAsset.Write(writer);
     writer.Write(RuntimeCompatibility);
     writer.Write(AssetBundleName);
     writer.WriteArrayOf(Dependencies, (x, y) => x.WritePtr(y));
     writer.Write(IsStreamedSceneAssetBundle);
     writer.AlignTo(4);
     writer.Write(ExplicitDataLayout);
     writer.Write(PathFlags);
     writer.WriteArrayOf(SceneHashes, (x, y) => x.Write(y));
 }
예제 #4
0
        public override void Read(EndianStream stream)
        {
            base.Read(stream);

            m_preloadTable = stream.ReadArray(() => new PPtr <Object>(AssetsFile));
            m_container    = stream.ReadStringKVPArray(() => new AssetBundles.AssetInfo(AssetsFile));
            MainAsset.Read(stream);
            if (IsReadScriptCampatibility)
            {
                m_scriptCampatibility = stream.ReadArray <AssetBundleScriptInfo>();
                m_classCampatibility  = stream.ReadInt32KVPUInt32Array();
            }
            RuntimeCompatibility = stream.ReadUInt32();
            if (IsReadAssetBundleName)
            {
                AssetBundleName            = stream.ReadStringAligned();
                m_dependencies             = stream.ReadStringArray();
                IsStreamedSceneAssetBundle = stream.ReadBoolean();
                stream.AlignStream(AlignType.Align4);

                PathFlags = stream.ReadInt32();
            }
        }
예제 #5
0
    public void LoadAsset <T>(string assetName, string assetType, Action <T> cb, bool cache) where T : Object
    {
        if (string.IsNullOrEmpty(assetName))
        {
            UnityEngine.Debug.LogError("LoadAsset<> failed - assetName is null!");
            return;
        }

#if COLLECTION_PERFORMANCE
        Stopwatch timer = new Stopwatch();
        timer.Start();
#endif
        if (_prefabCache.ContainsKey(assetName))
        {
            T asset = _prefabCache[assetName] as T;
            if (asset != null && cb != null)
            {
                cb(asset);
            }
        }
        else
        {
#if USE_E//使用在editor下的不打包文件
            T asset = null;
            switch (assetType)
            {
            case ResourceUI:
                asset = UnityEditor.AssetDatabase.LoadMainAssetAtPath(string.Format("Assets/Game/__Load/ui/{0}.prefab", assetName)) as T;
                break;

            case ResourceCharacter:
                asset = UnityEditor.AssetDatabase.LoadMainAssetAtPath(string.Format("Assets/Game/__Load/character/{0}.prefab", assetName)) as T;
                break;

            case ResourceMap:
                asset = UnityEditor.AssetDatabase.LoadMainAssetAtPath(string.Format("Assets/Game/__Load/map/{0}.prefab", assetName)) as T;
                break;

            case ResourceItem:
                asset = UnityEditor.AssetDatabase.LoadMainAssetAtPath(string.Format("Assets/Game/__Load/item/{0}.prefab", assetName)) as T;
                break;

            case ResourceEffect:
                asset = UnityEditor.AssetDatabase.LoadMainAssetAtPath(string.Format("Assets/Game/__Load/effect/{0}.prefab", assetName)) as T;
                break;

            case ResourceSound:
                asset = UnityEditor.AssetDatabase.LoadMainAssetAtPath(string.Format("Assets/Game/__Load/sound/{0}.ogg", assetName)) as T;
                break;

            case ResourceImage:
                asset = UnityEditor.AssetDatabase.LoadMainAssetAtPath(string.Format("Assets/Game/__Load/Image/{0}.png", assetName)) as T;
                break;

            case ResourceMaterial:
                asset = UnityEditor.AssetDatabase.LoadMainAssetAtPath(string.Format("Assets/Game/__Load/material/{0}.mat", assetName)) as T;
                break;
            }
            if (asset != null)
            {
                if (cache && !_prefabCache.ContainsKey(assetName))
                {
                    _prefabCache.Add(assetName, asset);
                }

                if (cb != null)
                {
                    cb(asset);
                }
            }
            else
            {
                UnityEngine.Debug.LogErrorFormat("LoadAsset() - Failed: assetType is {0}, assetName is {1}", assetType, assetName);
            }
#else
            MainAsset mainAsset = null;
            if (_assetCache.ContainsKey(assetName))
            {
                mainAsset = _assetCache[assetName];
            }
            else
            {
                mainAsset = new MainAsset(assetName, assetType);
                _assetCache.Add(assetName, mainAsset);
            }

            if (mainAsset.IsLoaded())
            {
                T asset = mainAsset.asset.download.ab.mainAsset as T;
                if (asset != null)
                {
                    if (cache && !_prefabCache.ContainsKey(assetName))
                    {
                        _prefabCache.Add(assetName, asset);
                    }

                    if (cb != null)
                    {
                        cb(asset);
                    }
                }
            }
            else
            {
                if (!mainAsset.isLoading)
                {
                    if (!mainAsset.IsLoaded())
                    {
                        mainAsset.Load();
                    }
                    mainAsset.isLoading = true;
                }

                mainAsset.onLoadCompletedEvent += (DownloadItem item) =>
                {
                    T asset = item.ab.mainAsset as T;
                    if (!Object.ReferenceEquals(asset, null))
                    {
                        if (cache && !_prefabCache.ContainsKey(assetName))
                        {
                            _prefabCache.Add(assetName, asset);
                        }

#if COLLECTION_PERFORMANCE
                        timer.Stop();
                        long Elapsed = timer.ElapsedMilliseconds;
                        timer.Reset();
                        timer.Start();
#endif
                        if (cb != null)
                        {
                            cb(asset);
                        }
#if COLLECTION_PERFORMANCE
                        timer.Stop();
                        CollectionPerformance.FileAppend(CollectionPerformance.TimesRecord, string.Format("{0}\t{1}\t{2}\n", assetName, Elapsed, timer.ElapsedMilliseconds));
#endif
                    }
                };
            }
#endif
        }
    }
예제 #6
0
    public static void Deploy()
    {
        string[] resConfigs = new string[] {
            "Other/Config/Resource/Audio.txt",
            "Other/Config/Resource/TextAsset.txt",
            "Other/Config/Resource/Model.txt",
            "Other/Config/Resource/Effect.txt",
            "Other/Config/Resource/Scene.txt",
            "Other/Config/Resource/UIAtlas.txt",
            "Other/Config/Resource/UIPanel.txt",
            "Other/Config/Resource/Material.txt",
            "Other/Config/Resource/Cursor.txt",
        };

        // 生成MainAsset的List, 并验证配置文件是否合理
        bool             isMissFile = false;
        int              MissCount  = 0;
        List <MainAsset> mainAssets = new List <MainAsset>();

        for (int i = 0; i < resConfigs.Length; i++)
        {
            TextAsset textAsset = AssetDatabase.LoadMainAssetAtPath("Assets/" + resConfigs[i]) as TextAsset;
            if (null == textAsset)
            {
                Log.Write(LogLevel.WARN, "config is null {0}", resConfigs[i]);
                return;
            }

            string  strAssetType = Path.GetFileNameWithoutExtension(resConfigs[i]);
            TabFile tabFile      = new TabFile(textAsset.name, textAsset.text);
            while (tabFile.Next())
            {
                int    nId         = tabFile.Get <int>("id");
                string strFilePath = tabFile.Get <string>("FilePath");
                for (int j = 0; j < mainAssets.Count; j++)
                {
                    MainAsset mainAsset = mainAssets[j];
                    if (mainAsset.m_strFilePath == strFilePath)
                    {
                        Log.Write(LogLevel.WARN, "exist two same path {0} {1}, {2}", strFilePath, mainAsset.m_strAssetType, strAssetType);
                        return;
                    }
                    if (mainAsset.m_strAssetType == strAssetType && mainAsset.m_nId == nId)
                    {
                        Log.Write(LogLevel.WARN, "{0} repleat id {1}", strAssetType, nId);
                        return;
                    }
                }
                UnityEngine.Object fileObj = AssetDatabase.LoadMainAssetAtPath("Assets/" + strFilePath);
                if (null == fileObj)
                {
                    isMissFile = true;
                    Log.Write(LogLevel.WARN, "null id:{0} name:{1}", nId, strFilePath);
                    MissCount++;
                    continue;
                }

                //UnityEngine.Object[] dependObjects = EditorUtility.CollectDependencies(new UnityEngine.Object[] { fileObj });

                string    fileName = Path.GetFileNameWithoutExtension(strFilePath);
                MainAsset asset    = new MainAsset(strAssetType, nId, strFilePath, fileObj, fileName);
                mainAssets.Add(asset);
            }
        }

        if (isMissFile)
        {
            Log.Write(LogLevel.WARN, "has Miss File Count {0}", MissCount);
        }

        // 分析依赖关系
        SortedList <UnityEngine.Object, List <MainAsset> > depends = new SortedList <UnityEngine.Object, List <MainAsset> >(new objectCompare());

        for (int i = 0; i < mainAssets.Count; i++)
        {
            MainAsset            mainAsset     = mainAssets[i];
            UnityEngine.Object[] dependObjects = EditorUtility.CollectDependencies(new UnityEngine.Object[] { mainAsset.m_obj });
            for (int j = 0; j < dependObjects.Length; j++)
            {
                UnityEngine.Object dependObj = dependObjects[j];
                if (!depends.ContainsKey(dependObj))
                {
                    depends.Add(dependObj, new List <MainAsset>());
                }
                depends[dependObj].Add(mainAsset);
            }
        }

        // 根据依赖关系, 分包
        SortedList <List <MainAsset>, List <UnityEngine.Object> > assets = new SortedList <List <MainAsset>, List <UnityEngine.Object> >(new assetListCompare());

        foreach (KeyValuePair <UnityEngine.Object, List <MainAsset> > kvp in depends)
        {
            List <UnityEngine.Object> list = null;
            if (!assets.ContainsKey(kvp.Value))
            {
                list = new List <UnityEngine.Object>();
                assets.Add(kvp.Value, list);
            }
            if (null == list)
            {
                list = assets[kvp.Value];
            }
            list.Add(kvp.Key);
        }

        // 准备XML配置文件
        string      strXmlFile = "Other/Config/Resource/wwwResource.xml";
        XmlDocument xmlDoc     = new XmlDocument();

        xmlDoc.Load(Application.dataPath + "/" + strXmlFile);
        xmlDoc.RemoveAll();
        XmlElement root = xmlDoc.CreateElement("AssetList");

        xmlDoc.AppendChild((XmlNode)root);
        root.SetAttribute("TotalSize", "0");

        SortedList <string, XmlElement> typeXmlEle = new SortedList <string, XmlElement>();

        for (int i = 0; i < mainAssets.Count; i++)
        {
            MainAsset mainAsset = mainAssets[i];
            if (!typeXmlEle.ContainsKey(mainAsset.m_strAssetType))
            {
                XmlElement typeEle = xmlDoc.CreateElement(mainAsset.m_strAssetType);
                typeEle.SetAttribute("TotalSize", "0");
                root.AppendChild(typeEle);
                typeXmlEle.Add(mainAsset.m_strAssetType, typeEle);
            }
            mainAsset.m_xmlParentEle = typeXmlEle[mainAsset.m_strAssetType];
            mainAsset.m_xmlSelfEle   = xmlDoc.CreateElement("Asset");
            mainAsset.m_xmlSelfEle.SetAttribute("Id", "0");
            mainAsset.m_xmlSelfEle.SetAttribute("Version", mainAsset.m_Version.ToString());
            mainAsset.m_xmlSelfEle.SetAttribute("TotalSize", "0");
            mainAsset.m_xmlParentEle.AppendChild(mainAsset.m_xmlSelfEle);
        }

        //----------------------------------------------------------------------打包
        BuildPipeline.PushAssetDependencies();
        // 打包客户端
//		string errorHead = BuildPipeline.BuildPlayer(new string[]{"Assets/Scene/JueSe.unity"}, buildDir, BuildTarget.WebPlayer, BuildOptions.None);
//		if(!string.IsNullOrEmpty(errorHead))
//		{
//			Log.Write(LogLevel.ERROR,"{0}",errorHead);
//			return ;
//		}

        // 打包Shared
        int k = 0;

        foreach (KeyValuePair <List <MainAsset>, List <UnityEngine.Object> > kvp in assets)
        {
            List <MainAsset> listMainAsset = kvp.Key;
            if (listMainAsset.Count <= 1)
            {
                //MainAsset te1 = listMainAsset[0];
                //Log.Write(LogLevel.INFO,"objectName is {0}",te1.m_Name);
                continue;
            }

            List <UnityEngine.Object> listObject = kvp.Value;
            int    version    = MainAsset.GenVersion();
            string strTgtPath = "Shared/Shared" + (++k) + '_' + version.ToString() + ".asset";
            bool   isSucess   = BuildPipeline.BuildAssetBundle(null, listObject.ToArray(), buildDir + "/" + strTgtPath,
                                                               BuildAssetBundleOptions.CollectDependencies | BuildAssetBundleOptions.CompleteAssets, EditorUserBuildSettings.activeBuildTarget);

            if (!isSucess)
            {
                Log.Write(LogLevel.DEBUG, "build {0} failed", strTgtPath);
                continue;
            }

            // 设置大小观察信息
            FileInfo fileInfo = new FileInfo(buildDir + "/" + strTgtPath);
            double   fileSize = fileInfo.Length / 1024f;
            root.SetAttribute("TotalSize", (fileSize + Convert.ToDouble(root.GetAttribute("TotalSize"))).ToString("0.00"));

            for (int j = 0; j < listMainAsset.Count; j++)
            {
                MainAsset  mainAsset = listMainAsset[j];
                XmlElement ele       = xmlDoc.CreateElement("Depend");
                ele.SetAttribute("Id", "" + k);
                ele.SetAttribute("Version", version.ToString());
                ele.SetAttribute("Size", fileSize.ToString("0.00"));
                mainAsset.m_xmlSelfEle.AppendChild(ele);
                mainAsset.m_xmlSelfEle.SetAttribute("TotalSize", (fileSize + Convert.ToDouble(mainAsset.m_xmlSelfEle.GetAttribute("TotalSize"))).ToString("0.00"));
            }
        }

        //打包共享
//		UnityEngine.Object temp1 = AssetDatabase.LoadMainAssetAtPath("Assets/UIResources/Atlases/Common/CommonAtlas.prefab");
//		BuildPipeline.BuildAssetBundle(temp1,null,buildDir + "/Shared/" + "CommonAtlas.asset",BuildAssetBundleOptions.CollectDependencies | BuildAssetBundleOptions.CompleteAssets);
//
//		UnityEngine.Object temp4 = AssetDatabase.LoadMainAssetAtPath("Assets/UIResources/Font/DySongTi/songti12.prefab");
//		BuildPipeline.BuildAssetBundle(temp4,null,buildDir + "/Shared/" + "Font12.asset",BuildAssetBundleOptions.CollectDependencies | BuildAssetBundleOptions.CompleteAssets);
//
//		UnityEngine.Object temp5 = AssetDatabase.LoadMainAssetAtPath("Assets/UIResources/Font/DySongTi/songti14.prefab");
//		BuildPipeline.BuildAssetBundle(temp5,null,buildDir + "/Shared/" + "Font14.asset",BuildAssetBundleOptions.CollectDependencies | BuildAssetBundleOptions.CompleteAssets);
//
//		UnityEngine.Object temp6 = AssetDatabase.LoadMainAssetAtPath("Assets/UIResources/Font/DySongTi/songti16.prefab");
//		BuildPipeline.BuildAssetBundle(temp6,null,buildDir + "/Shared/" + "Font16.asset",BuildAssetBundleOptions.CollectDependencies | BuildAssetBundleOptions.CompleteAssets);
//

        // 打包mainAsset
        for (int i = 0; i < mainAssets.Count; i++)
        {
            MainAsset mainAsset = mainAssets[i];
            // todo: 是否会出现mainAsset.m_strFilePath不一样但是strTgtPath一样的情况?

            string strTgtName = "" + mainAsset.m_nId + '_' + mainAsset.m_Version.ToString() + ".asset";
            string strTgtPath = mainAsset.m_strAssetType + "/" + strTgtName;
            if ("Scene" == mainAsset.m_strAssetType)
            {
                BuildPipeline.PushAssetDependencies();
                //string errorScene = BuildPipeline.BuildPlayer(new string[]{ "Assets/" + mainAsset.m_strFilePath }, buildDir  + "/" +  strTgtPath,
                //			EditorUserBuildSettings.activeBuildTarget, BuildOptions.BuildAdditionalStreamedScenes);
                BuildPipeline.PopAssetDependencies();

                //if(!string.IsNullOrEmpty(errorScene))
                //{
                //	Log.Write(LogLevel.ERROR,"{0}",errorScene);
                //	return ;
                //}
            }
            else
            {
                BuildPipeline.PushAssetDependencies();
                bool isSuccess = BuildPipeline.BuildAssetBundle(mainAsset.m_obj, null, buildDir + "/" + strTgtPath,
                                                                BuildAssetBundleOptions.CollectDependencies | BuildAssetBundleOptions.CompleteAssets, EditorUserBuildSettings.activeBuildTarget);
                BuildPipeline.PopAssetDependencies();

                if (!isSuccess)
                {
                    Log.Write(LogLevel.DEBUG, "build {0} failed", strTgtPath);
                    continue;
                }
            }

            // 设置大小观察信息
            FileInfo fileInfo = new FileInfo(buildDir + "/" + strTgtPath);
            double   fileSize = fileInfo.Length / 1024f;
            root.SetAttribute("TotalSize", (fileSize + Convert.ToDouble(root.GetAttribute("TotalSize"))).ToString("0.00"));
            mainAsset.m_xmlSelfEle.SetAttribute("Id", "" + mainAsset.m_nId);
            mainAsset.m_xmlSelfEle.SetAttribute("Size", fileSize.ToString("0.00"));
            mainAsset.m_xmlSelfEle.SetAttribute("Name", mainAsset.OrignalName);

            mainAsset.m_xmlSelfEle.SetAttribute("TotalSize", (fileSize + Convert.ToDouble(mainAsset.m_xmlSelfEle.GetAttribute("TotalSize"))).ToString("0.00"));
            mainAsset.m_xmlParentEle.SetAttribute("TotalSize", (Convert.ToDouble(mainAsset.m_xmlParentEle.GetAttribute("TotalSize"))
                                                                + Convert.ToDouble(mainAsset.m_xmlSelfEle.GetAttribute("TotalSize"))).ToString("0.00"));
        }
        BuildPipeline.PopAssetDependencies();
        //----------------------------------------------------------------------

        xmlDoc.Save(Application.dataPath + "/" + strXmlFile);
        Log.Write(LogLevel.INFO, "pack end");
    }
예제 #7
0
    public static void PackDBConfig()
    {
        string[] resConfigs = new string[] {
            "Other/Config/Resource/TextAsset.txt",
        };

        // 生成MainAsset的List, 并验证配置文件是否合理
        bool             isMissFile = false;
        int              MissCount  = 0;
        List <MainAsset> mainAssets = new List <MainAsset>();

        for (int i = 0; i < resConfigs.Length; i++)
        {
            TextAsset textAsset = AssetDatabase.LoadMainAssetAtPath("Assets/" + resConfigs[i]) as TextAsset;
            if (null == textAsset)
            {
                Log.Write(LogLevel.WARN, "config is null {0}", resConfigs[i]);
                return;
            }

            string  strAssetType = Path.GetFileNameWithoutExtension(resConfigs[i]);
            TabFile tabFile      = new TabFile(textAsset.name, textAsset.text);
            while (tabFile.Next())
            {
                int    nId         = tabFile.Get <int>("id");
                string strFilePath = tabFile.Get <string>("FilePath");
                for (int j = 0; j < mainAssets.Count; j++)
                {
                    MainAsset mainAsset = mainAssets[j];
                    if (mainAsset.m_strFilePath == strFilePath)
                    {
                        Log.Write(LogLevel.WARN, "{0} 同时出现在{1}, {2} 这两个配置中, 放弃本次发布", strFilePath, mainAsset.m_strAssetType, strAssetType);
                        return;
                    }
                    if (mainAsset.m_strAssetType == strAssetType && mainAsset.m_nId == nId)
                    {
                        Log.Write(LogLevel.WARN, "{0} 配置出现了Id重复 {1}, 放弃本次发布", strAssetType, nId);
                        return;
                    }
                }
                UnityEngine.Object fileObj = AssetDatabase.LoadMainAssetAtPath("Assets/" + strFilePath);
                if (null == fileObj)
                {
                    isMissFile = true;
                    Log.Write(LogLevel.WARN, "资源为空: {0}, 放弃本次发布", strFilePath);
                    MissCount++;
                    continue;
                }

                string    fileName = Path.GetFileNameWithoutExtension(strFilePath);
                MainAsset asset    = new MainAsset(strAssetType, nId, strFilePath, fileObj, fileName);
                mainAssets.Add(asset);
            }
        }

        if (isMissFile)
        {
            Log.Write(LogLevel.WARN, "资源为空文件数目{0}, 放弃本次发布", MissCount);
        }

        // 准备XML配置文件
        string      strXmlFile = "Other/Config/Resource/wwwResource.xml";
        XmlDocument xmlDoc     = new XmlDocument();

        xmlDoc.Load(Application.dataPath + "/" + strXmlFile);
        xmlDoc.RemoveAll();
        XmlElement root = xmlDoc.CreateElement("AssetList");

        xmlDoc.AppendChild((XmlNode)root);
        root.SetAttribute("TotalSize", "0");

        SortedList <string, XmlElement> typeXmlEle = new SortedList <string, XmlElement>();

        for (int i = 0; i < mainAssets.Count; i++)
        {
            MainAsset mainAsset = mainAssets[i];
            if (!typeXmlEle.ContainsKey(mainAsset.m_strAssetType))
            {
                XmlElement typeEle = xmlDoc.CreateElement(mainAsset.m_strAssetType);
                typeEle.SetAttribute("TotalSize", "0");
                root.AppendChild(typeEle);
                typeXmlEle.Add(mainAsset.m_strAssetType, typeEle);
            }
            mainAsset.m_xmlParentEle = typeXmlEle[mainAsset.m_strAssetType];
            mainAsset.m_xmlSelfEle   = xmlDoc.CreateElement("Asset");
            mainAsset.m_xmlSelfEle.SetAttribute("Id", "0");
            mainAsset.m_xmlSelfEle.SetAttribute("TotalSize", "0");
            mainAsset.m_xmlParentEle.AppendChild(mainAsset.m_xmlSelfEle);
        }

        BuildPipeline.PushAssetDependencies();

        // 打包mainAsset
        for (int i = 0; i < mainAssets.Count; i++)
        {
            MainAsset mainAsset = mainAssets[i];
            // todo: 是否会出现mainAsset.m_strFilePath不一样但是strTgtPath一样的情况?
            string strTgtName = "" + mainAsset.m_Name + ".asset";
            //string strTgtName = "" + mainAsset.m_nId + ".asset";
            string strTgtPath = mainAsset.m_strAssetType + "/" + strTgtName;
            if ("Scene" == mainAsset.m_strAssetType)
            {
                //string errorScene = BuildPipeline.BuildPlayer(new string[]{ "Assets/" + mainAsset.m_strFilePath }, buildDir  + "/" +  strTgtPath,
                //			EditorUserBuildSettings.activeBuildTarget, BuildOptions.BuildAdditionalStreamedScenes);

                //if(!string.IsNullOrEmpty(errorScene))
                //{
                //	Log.Write(LogLevel.ERROR,"{0}",errorScene);
                //	return ;
                //}
            }
            else
            {
                BuildPipeline.BuildAssetBundle(mainAsset.m_obj, null, buildDir + "/" + strTgtPath,
                                               BuildAssetBundleOptions.CollectDependencies | BuildAssetBundleOptions.CompleteAssets, EditorUserBuildSettings.activeBuildTarget);
            }

            // 设置大小观察信息
            FileInfo fileInfo = new FileInfo(buildDir + "/" + strTgtPath);
            double   fileSize = fileInfo.Length / 1024f;
            root.SetAttribute("TotalSize", (fileSize + Convert.ToDouble(root.GetAttribute("TotalSize"))).ToString("0.00"));
            mainAsset.m_xmlSelfEle.SetAttribute("Id", "" + mainAsset.m_nId);
            mainAsset.m_xmlSelfEle.SetAttribute("TotalSize", (fileSize + Convert.ToDouble(mainAsset.m_xmlSelfEle.GetAttribute("TotalSize"))).ToString("0.00"));
            mainAsset.m_xmlParentEle.SetAttribute("TotalSize", (Convert.ToDouble(mainAsset.m_xmlParentEle.GetAttribute("TotalSize"))
                                                                + Convert.ToDouble(mainAsset.m_xmlSelfEle.GetAttribute("TotalSize"))).ToString("0.00"));
        }
        BuildPipeline.PopAssetDependencies();
        //----------------------------------------------------------------------

        xmlDoc.Save(Application.dataPath + "/" + strXmlFile);
    }