using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEditor;
namespace SFramework.Editor
{
public static class SAssetsBundleHelper
{
static string ResourcesBuildDir
{
get
{
var dir = "Assets/" + SFrameworkDef.ResourceDir + "/";
return dir;
}
}
///
/// Unity 5新AssetBundle系统,需要为打包的AssetBundle配置名称
///
/// 直接将KEngine配置的BundleResources目录整个自动配置名称,因为这个目录本来就是整个导出
///
[MenuItem("SFramework/AssetBundle/Auto Set Names To [BundleResources]")]
public static void AutoSetAssetBundleNames()
{
var dir = ResourcesBuildDir;
// Check marked asset bundle whether real
foreach (var assetGuid in AssetDatabase.FindAssets(""))
{
var assetPath = AssetDatabase.GUIDToAssetPath(assetGuid);
var assetImporter = AssetImporter.GetAtPath(assetPath);
var bundleName = assetImporter.assetBundleName;
if (string.IsNullOrEmpty(bundleName))
{
continue;
}
if (!assetPath.StartsWith(dir))
{
assetImporter.assetBundleName = null;
}
}
// set BundleResources's all bundle name
foreach (var filepath in System.IO.Directory.GetFiles(dir, "*.*", System.IO.SearchOption.AllDirectories))
{
if (filepath.EndsWith(".meta")) continue;
var importer = AssetImporter.GetAtPath(filepath);
if (importer == null)
{
Debug.LogError(string.Format("Not found: {0}", filepath));
continue;
}
var bundleName = filepath.Substring(dir.Length, filepath.Length - dir.Length);
importer.assetBundleName = bundleName + SFrameworkDef.AssetsBundleExtName;
}
Debug.Log("Make all asset name success!");
}
///
/// 清理冗余,即无此资源,却存在AssetBundle的文件, Unity 5 only
///
[MenuItem("SFramework/AssetBundle/Clean Redundancies")]
public static void CleanAssetBundlesRedundancies()
{
var platformName = SPlatformInfo.GetBuildPlatformName();
var outputPath = GetExportPath(EditorUserBuildSettings.activeBuildTarget);
var srcList = new List(System.IO.Directory.GetFiles(ResourcesBuildDir, "*.*", System.IO.SearchOption.AllDirectories));
for (var i = srcList.Count - 1; i >= 0; i--)
{
if (srcList[i].EndsWith(".meta"))
srcList.RemoveAt(i);
else
srcList[i] = srcList[i].Replace(ResourcesBuildDir, "").ToLower();
}
var toListMap = new Dictionary();
var toList = new List(System.IO.Directory.GetFiles(outputPath, "*.*", System.IO.SearchOption.AllDirectories));
for (var i = toList.Count - 1; i >= 0; i--)
{
var filePath = toList[i];
if (toList[i].EndsWith((".meta")) || toList[i].EndsWith(".manifest"))
{
toList.RemoveAt(i);
}
else
{
var rName = toList[i].Replace(outputPath, "");
if (rName == platformName || // 排除AB 平台总索引文件,
rName == (platformName + ".manifest") ||
rName == (platformName + ".meta") ||
rName == (platformName + ".manifest.meta"))
{
toList.RemoveAt(i);
}
else
{
// 去掉扩展名,因为AssetBundle额外扩展名
toList[i] = System.IO.Path.ChangeExtension(rName, "");// 会留下最后句点
toList[i] = toList[i].Substring(0, toList[i].Length - 1); // 去掉句点
toListMap[toList[i]] = filePath;
}
}
}
// 删文件和manifest
for (var i = 0; i < toList.Count; i++)
{
if (!srcList.Contains(toList[i]))
{
var filePath = toListMap[toList[i]];
var manifestPath = filePath + ".manifest";
System.IO.File.Delete(filePath);
Debug.LogWarning("Delete... " + filePath);
if (System.IO.File.Exists(manifestPath))
{
System.IO.File.Delete(manifestPath);
Debug.LogWarning("Delete... " + manifestPath);
}
}
}
}
[MenuItem("SFramework/AssetBundle/Create Version File")]
public static void CreateVersionFile()
{
AssetBundle.UnloadAllAssetBundles(true);
var platformName = SPlatformInfo.GetBuildPlatformName();
var outputPath = GetExportPath(EditorUserBuildSettings.activeBuildTarget);
Debug.Log(string.Format("CreateVersionFile -> platformName:{0} outputPath:{1}", platformName, outputPath));
// Load manifestAB
string manifestABPath = Application.dataPath + "/../Product/Bundles/" + platformName + "/" + platformName;
Debug.Log("manifestABPath -> " + manifestABPath);
byte[] byManifest = System.IO.File.ReadAllBytes(manifestABPath);
AssetBundle manifestAB = AssetBundle.LoadFromMemory(byManifest);
if (manifestAB == null)
{
Debug.LogError("CreateVersionFile -> Get ManifestAB Failed. Path:" + manifestABPath);
return;
}
AssetBundleManifest manifest = manifestAB.LoadAsset("AssetBundleManifest") as AssetBundleManifest;
if (manifest == null)
{
Debug.LogError("CreateVersionFile -> Get Manifest From AssetBundle Failed.");
return;
}
SVersionInfo curVersionInfo = new SVersionInfo();
curVersionInfo.version = 0;
curVersionInfo.fileInfo = new List();
// Add Manifest File
string manifestFileName = platformName;
SFileInfo manifestFileInfo = SToolFunction.CreateFileInfo(manifestFileName, outputPath + manifestFileName);
curVersionInfo.fileInfo.Add(manifestFileInfo);
// Add Manifest Ext File(platform.manifest)
string manifestExtFileName = platformName + ".manifest";
SFileInfo manifestExtFileInfo = SToolFunction.CreateFileInfo(manifestExtFileName, outputPath + manifestExtFileName);
curVersionInfo.fileInfo.Add(manifestExtFileInfo);
// Add files in manifest.
string[] allABName = manifest.GetAllAssetBundles();
curVersionInfo.fileCount = allABName.Length;
foreach (string abName in allABName)
{
string oneABFullPathWithName = outputPath + abName;
SFileInfo curFileInfo = SToolFunction.CreateFileInfo(abName, oneABFullPathWithName);
curFileInfo.hashInfo = manifest.GetAssetBundleHash(abName).ToString();
curVersionInfo.fileInfo.Add(curFileInfo);
// Debug.Log(string.Format("oneAB:{0} Size:{1}", abName, oneABFileInfo.Length));
Debug.Log(string.Format("abName: {0} FileSize:{1} HashCode: {2}",
curFileInfo.fileName, curFileInfo.fileSize, curFileInfo.hashInfo));
}
string jsonString = LitJson.JsonMapper.ToJson(curVersionInfo);
Debug.Log("jsonString -> " + jsonString);
string jsonPath = Application.dataPath + "/../Product/Bundles/" + platformName + "/" + SFrameworkDef.VersionFileName;
System.IO.StreamWriter build_info = new System.IO.StreamWriter(jsonPath);
build_info.Write(jsonString);
build_info.Close();
build_info.Dispose();
manifestAB.Unload(true);
Debug.Log("CreateVersionFile Success!");
}
//[MenuItem("SFramework/AssetBundle/Build All to All Platforms")]
//public static void BuildAllAssetBundlesToAllPlatforms()
//{
// var platforms = new List()
// {
// BuildTarget.iOS,
// BuildTarget.Android,
// BuildTarget.StandaloneWindows,
// BuildTarget.StandaloneOSX,
// };
// // Build all support platforms asset bundle
// var currentBuildTarget = EditorUserBuildSettings.activeBuildTarget;
// platforms.Remove(currentBuildTarget);
// BuildAllAssetBundles();
// foreach (var platform in platforms)
// {
// if (EditorUserBuildSettings.SwitchActiveBuildTarget(platform))
// BuildAllAssetBundles();
// }
// // revert platform
// EditorUserBuildSettings.SwitchActiveBuildTarget(currentBuildTarget);
//}
[MenuItem("SFramework/AssetBundle/ReBuild All")]
public static void ReBuildAllAssetBundles()
{
var outputPath = GetExportPath(EditorUserBuildSettings.activeBuildTarget);
System.IO.Directory.Delete(outputPath, true);
Debug.Log("Delete folder: " + outputPath);
BuildAllAssetBundles();
}
[MenuItem("SFramework/AssetBundle/Build All %&b")]
public static void BuildAllAssetBundles()
{
if (EditorApplication.isPlaying)
{
Debug.LogError("Cannot build in playing mode! Please stop!");
return;
}
AutoSetAssetBundleNames();
var outputPath = GetExportPath(EditorUserBuildSettings.activeBuildTarget);
Debug.Log(string.Format("Asset bundle start build to: {0}", outputPath));
BuildPipeline.BuildAssetBundles(outputPath, BuildAssetBundleOptions.DeterministicAssetBundle, EditorUserBuildSettings.activeBuildTarget);
//BuildPipeline.BuildAssetBundles(outputPath, BuildAssetBundleOptions.DeterministicAssetBundle | BuildAssetBundleOptions.AppendHashToAssetBundleName, EditorUserBuildSettings.activeBuildTarget);
CreateVersionFile();
}
///
/// Extra Flag -> ex: Android/ AndroidSD/ AndroidHD/
///
///
///
public static string GetExportPath(BuildTarget platfrom)
{
//string basePath =
// System.IO.Path.GetFullPath(KEngine.AppEngine.GetConfig(KEngineDefaultConfigs.AssetBundleBuildRelPath));
string basePath = SFrameworkDef.AssetsBundleProductDir;
if (System.IO.File.Exists(basePath))
{
SAssetsBundleHelper.ShowDialog("路径配置错误: " + basePath);
throw new System.Exception("路径配置错误");
}
if (!System.IO.Directory.Exists(basePath))
{
System.IO.Directory.CreateDirectory(basePath);
}
string path = null;
var platformName = SPlatformInfo.GetBuildPlatformName();
path = basePath + "/" + platformName + "/";
if (!System.IO.Directory.Exists(path))
{
System.IO.Directory.CreateDirectory(path);
}
return path;
}
public static void ClearConsole()
{
System.Reflection.Assembly assembly = System.Reflection.Assembly.GetAssembly(typeof(SceneView));
System.Type type = assembly.GetType("UnityEditorInternal.LogEntries");
System.Reflection.MethodInfo method = type.GetMethod("Clear");
method.Invoke(null, null);
}
public static bool ShowDialog(string msg, string title = "提示", string button = "确定")
{
return EditorUtility.DisplayDialog(title, msg, button);
}
public static void ShowDialogSelection(string msg, System.Action yesCallback)
{
if (EditorUtility.DisplayDialog("确定吗", msg, "是!", "不!"))
{
yesCallback();
}
}
}
}