using System; using System.Collections.Generic; using System.IO; using System.Linq; #if HotUpdate using HybridCLR.Editor; using HybridCLR.Editor.Settings; #endif using Sirenix.OdinInspector; using Sirenix.OdinInspector.Editor; using Stary.Evo.InformationSave; using UnityEditor; using UnityEditorInternal; using UnityEngine; namespace Stary.Evo.Editor { public class CreatAssetWindow : OdinEditorWindow { [MenuItem("Evo/创建Domain作用域")] static void Init() { // Get existing open window or if none, make a new one: CreatAssetWindow window = (CreatAssetWindow)EditorWindow.GetWindow(typeof(CreatAssetWindow)); window.Show(); } [TitleGroup("创建Domain作用域")] public string domain; [TitleGroup("创建Domain作用域")] [Button("创建Domain", ButtonSizes.Large)] public async void CreatDomain() { // if (GetCreatDomainAll().Count>0) // { // EditorUtility.DisplayDialog("错误!", "Domain仅可以创建一个,请在下方删除存在的Domain", "确定"); // return; // } if (string.IsNullOrEmpty(domain)) { EditorUtility.DisplayDialog("错误!", "请输入将要创建Domain的编号", "确定"); return; } string artDomainPath = $"{Application.dataPath}/Art/{domain}"; if (!Directory.Exists(artDomainPath)) { Directory.CreateDirectory(artDomainPath); if (!Directory.Exists(artDomainPath)) //创建Animation文件夹 CreatDirectory(artDomainPath + "/Animation"); //创建Effects文件夹 CreatDirectory(artDomainPath + "/Effects"); //创建Fbx文件夹 CreatDirectory(artDomainPath + "/Fbx"); //创建Font文件夹 CreatDirectory(artDomainPath + "/Font"); //创建Materials文件夹 CreatDirectory(artDomainPath + "/Materials"); //创建Prefabs文件夹 CreatDirectory(artDomainPath + "/Prefabs"); //创建Scenes文件夹 CreatDirectory(artDomainPath + "/Scenes"); //创建/Scenes/Test文件夹 CreatDirectory(artDomainPath + "/Scenes/Test"); //创建Shader文件夹 CreatDirectory(artDomainPath + "/Shader"); //创建Textures文件夹 CreatDirectory(artDomainPath + "/Textures"); File.WriteAllTextAsync( $"{artDomainPath}/这里放所有美术的资源,因涉及打包依赖等原因,不建议在上一层节点新增文件夹,如涉及文件夹规范等问题请@张铮.hint", ""); } string domainPath = $"{Application.dataPath}/Domain/{domain}"; if (Directory.Exists(domainPath + "/AddressableRes/Config/DomainConfig.asset")) { EditorUtility.DisplayDialog("错误!", $"\"{domain}\"已经存在,无法创建", "确定"); return; } CreatDirectory(domainPath); //程序资源存放文件夹 string resPath = $"{domainPath}/AddressableRes"; CreatDirectory(resPath); //创建音频文件夹 CreatDirectory(resPath + "/Audios"); //创建Config文件夹 CreatDirectory(resPath + "/Config"); //创建Dll文件夹 CreatDirectory(resPath + "/Dll"); //创建Prefabs文件夹 CreatDirectory(resPath + "/Prefabs"); //创建Scenes文件夹 CreatDirectory(resPath + "/Scenes"); //创建SpriteAtlas文件夹 CreatDirectory(resPath + "/SpriteAtlas"); //创建Sprites文件夹 CreatDirectory(resPath + "/Sprites"); //创建Video文件夹 CreatDirectory(resPath + "/Video"); File.WriteAllTextAsync($"{resPath}/这里放所有参与热更的资源.hint", ""); //主入口预制件 GameObject gameObj = new GameObject(domain); gameObj.transform.position = Vector3.zero; gameObj.transform.rotation = Quaternion.identity; gameObj.name = domain; //创建位置层级 GameObject transformInfo = new GameObject("TransformInfo"); transformInfo.transform.SetParent(gameObj.transform); transformInfo.transform.position = Vector3.zero; transformInfo.transform.rotation = Quaternion.identity; transformInfo.AddComponent(); CreatDirectory($"{resPath}/Prefabs"); string rootPfbFilePath = $"Assets/Domain/{domain}/AddressableRes/Prefabs/{domain}.prefab"; var localPath = AssetDatabase.GenerateUniqueAssetPath(rootPfbFilePath); PrefabUtility.SaveAsPrefabAsset(gameObj, localPath); //存放脚本文件夹 string scriptsPath = $"{domainPath}/HotUpdate"; CreatDirectory(scriptsPath); File.WriteAllTextAsync($"{scriptsPath}/这里放所有参与热更的脚本文件.hint", "该文件夹中的程序集定义文件,请勿删除,非常重要。"); //创建配置文件夹 string confPath = $"{domainPath}/Conf"; CreatDirectory(confPath); //程序集配置资源 string hotfixDomain = $"HotUpdate_{domain}"; string hotfixDomainAsmdef = $"{scriptsPath}/{hotfixDomain}.asmdef"; await using (var writer = new StreamWriter(hotfixDomainAsmdef)) { string body = Resources.Load("AssemblyDefinitionTemplate").text; body = body.Replace("MODULE_IDENT", hotfixDomain); body = body.Replace("ROOT_NAMESPACE", hotfixDomain); await writer.WriteAsync(body); } //模块化脚本生成配置 string domainClassName = $"{domain}Domain"; string architectureClassName = $"{domain}Architecture"; #if HotUpdate //模块配置资源 DomainConfig moduleConfig = CreateInstance(); moduleConfig.domain = domain; moduleConfig.className = domainClassName; moduleConfig.mainPrefab = "Prefabs_" + gameObj.name; moduleConfig.@namespace = domain; AssetDatabase.CreateAsset(moduleConfig, $"Assets/Domain/{domain}/AddressableRes/Config/DomainConfig.asset"); // //编辑器配置资源 BuildAssetDataSetting buildAssetDataSetting = CreateInstance(); buildAssetDataSetting.packageName = domain; AssetDatabase.CreateAsset(buildAssetDataSetting, $"Assets/Domain/{domain}/Conf/BuildAssetDataSetting.asset"); AssetDatabase.Refresh(); string configPath = $"Assets/Domain/{domain}/HotUpdate/{hotfixDomain}.asmdef"; AssemblyDefinitionAsset assemblyDefinitionAsset = AssetDatabase.LoadAssetAtPath(configPath); if (domain != "Main") { // 将程序集定义添加到 HybridCLR 热更列表 var settings = SettingsUtil.HybridCLRSettings; if (!settings.hotUpdateAssemblyDefinitions.Contains(assemblyDefinitionAsset)) { var assemblyList = settings.hotUpdateAssemblyDefinitions.ToList(); assemblyList.Add(assemblyDefinitionAsset); SettingsUtil.HybridCLRSettings.hotUpdateAssemblyDefinitions = assemblyList.ToArray(); } List assemblies = new List(); for (int i = 0; i < settings.hotUpdateAssemblyDefinitions.Length; i++) { if (settings.hotUpdateAssemblyDefinitions[i] != null) { assemblies.Add(settings.hotUpdateAssemblyDefinitions[i]); } } HybridCLRSettings.Instance.hotUpdateAssemblyDefinitions = assemblies.ToArray(); HybridCLRSettings.Save(); } #endif AssetDatabase.SaveAssets(); string domainClassPath = $"{scriptsPath}/{domainClassName}.cs"; //await File.WriteAllTextAsync($"{scriptsPath}/{domainClassName}.cs", domainTemplate); await using (var writer = new StreamWriter(domainClassPath)) { string domainTemplate = Resources.Load("DomainTemplate").text; domainTemplate = domainTemplate.Replace("ClassNameXX", domainClassName) .Replace("ReturnArchitecture", architectureClassName) .Replace("ArchitectureX", architectureClassName) .Replace("NamespaceX", domain) .Replace("DomainNameXX", domain); await writer.WriteAsync(domainTemplate); } } [TitleGroup("预览Domain作用域")] public List domainList; protected override void Initialize() { base.Initialize(); domainList = GetCreatDomainAll(); } /// /// 获取全部作用域 /// public static string[] GetCreatDomainAllName() { string domainPath = $"{Application.dataPath}/Domain"; string[] domains; // 新增目录获取代码 if (Directory.Exists(domainPath)) { var dirInfo = new DirectoryInfo(domainPath); // 获取直接子目录(不递归) domains = dirInfo.GetDirectories("*", SearchOption.TopDirectoryOnly) .Select(d => d.Name) .ToArray(); } else { domains = Array.Empty(); } return domains; } /// /// 获取全部作用域 /// public static List GetCreatDomainAll() { string domainPath = $"{Application.dataPath}/Domain"; string[] domains; // 新增目录获取代码 if (Directory.Exists(domainPath)) { var dirInfo = new DirectoryInfo(domainPath); // 获取直接子目录(不递归) domains = dirInfo.GetDirectories("*", SearchOption.TopDirectoryOnly) .Select(d => d.Name) .ToArray(); } else { domains = Array.Empty(); } List domainList = new List(); foreach (var item in domains) { if (File.Exists($"{domainPath}/{item}/AddressableRes/Config/DomainConfig.asset")) { CreatDomainEntity domainEntity = new CreatDomainEntity(domainList) { DomainName = item, domainPath = $"{domainPath}/{item}" }; domainList.Add(domainEntity); } } return domainList; } private static void CreatDirectory(string artDomainPath) { if (!Directory.Exists(artDomainPath)) { //创建Animation文件夹 Directory.CreateDirectory(artDomainPath); } } public static void CreateDomainDirectory(string domain) { string artDomainPath = $"{Application.dataPath}/Art/{domain}"; //创建Animation文件夹 CreatDirectory(artDomainPath + "/Animation"); //创建Effects文件夹 CreatDirectory(artDomainPath + "/Effects"); //创建Fbx文件夹 CreatDirectory(artDomainPath + "/Fbx"); //创建Font文件夹 CreatDirectory(artDomainPath + "/Font"); //创建Materials文件夹 CreatDirectory(artDomainPath + "/Materials"); //创建Prefabs文件夹 CreatDirectory(artDomainPath + "/Prefabs"); //创建Scenes文件夹 CreatDirectory(artDomainPath + "/Scenes"); //创建/Scenes/Test文件夹 CreatDirectory(artDomainPath + "/Scenes/Test"); //创建Shader文件夹 CreatDirectory(artDomainPath + "/Shader"); //创建Textures文件夹 CreatDirectory(artDomainPath + "/Textures"); string domainPath = $"{Application.dataPath}/Domain/{domain}"; //程序资源存放文件夹 string resPath = $"{domainPath}/AddressableRes"; CreatDirectory(resPath); //创建音频文件夹 CreatDirectory(resPath + "/Audios"); //创建Config文件夹 CreatDirectory(resPath + "/Config"); //创建Dll文件夹 CreatDirectory(resPath + "/Dll"); //创建Prefabs文件夹 CreatDirectory(resPath + "/Prefabs"); //创建Scenes文件夹 CreatDirectory(resPath + "/Scenes"); //创建SpriteAtlas文件夹 CreatDirectory(resPath + "/SpriteAtlas"); //创建Sprites文件夹 CreatDirectory(resPath + "/Sprites"); //创建Video文件夹 CreatDirectory(resPath + "/Video"); AssetDatabase.Refresh(); } } }