public override bool DoesImporterMatchSettings(AssetImporter importer) { AudioImporter audioImporter = importer as AudioImporter; return audioImporter.compressionBitrate == compressionBitrate && audioImporter.forceToMono == forceToMono && audioImporter.format == format && audioImporter.hardware == hardware && audioImporter.loadType == loadType && audioImporter.loopable == loopable && audioImporter.threeD == threeD; }
public static void GenerateAssetBundlesMd5Mapping(string[] allAssets) { string info = "Generate AssetBundles Md5Mapping "; EditorUtility.DisplayProgressBar("GenerateAssetBundlesMd5Mapping", info, 0); string speciallyPath = "Assets/Config/Lan/"; string luaPath = "Assets/Lua/"; AssetImporter import = null; float i = 0; float allLen = allAssets.Length; string name = ""; string nameMd5 = ""; //name mapping StringBuilder nameSb = new StringBuilder(); //asset map StringBuilder sb = new StringBuilder(); sb.AppendLine("return {"); foreach (string path in allAssets) { import = AssetImporter.GetAtPath(path); string line = string.Empty; if (import != null && string.IsNullOrEmpty(import.assetBundleName) == false) { string abName = import.assetBundleName; name = CUtils.GetAssetName(path).ToLower(); if (!string.IsNullOrEmpty(import.assetBundleVariant)) { abName = import.assetBundleName + "." + import.assetBundleVariant; // line = "{\"" + import.assetBundleName + "\" = { size = \"" + name + "\", path = \"" + path + "\"}},"; } line = "[\"" + abName + "\"] = { size = " + GetAssetbundleSize(abName) + ", path = \"" + path + "\"},"; sb.AppendLine(line); nameSb.AppendFormat("{0}={1}\r\n", CUtils.GetRightFileName(name), name); if (name.Contains(" ")) { Debug.LogWarning(name + " contains space"); } } else if (import != null && path.Contains(speciallyPath)) { name = CUtils.GetAssetName(path).ToLower(); string md5name = CUtils.GetRightFileName(name) + Common.CHECK_ASSETBUNDLE_SUFFIX; line = "[\"" + md5name + "\"] = { size = " + GetAssetbundleSize(md5name) + ", path = \"" + path + "\"},"; sb.AppendLine(line); nameSb.AppendFormat("{0}={1}\r\n", md5name, name); } else if (import != null && path.Contains(luaPath)) { string luaname = path.Replace(luaPath, "").Replace("\\", ".").Replace("/", "."); string luacname = luaname.Replace(".lua", "").Replace(".", "+"); string luaMd5Name = CUtils.GetRightFileName(luacname); line = "[\"" + luaMd5Name + "\"] = { size = " + GetAssetbundleSize(luaMd5Name + ".bytes") + ", path = \"" + path + "\"},"; sb.AppendLine(line); nameSb.AppendFormat("{0}={1}\r\n", luaMd5Name, luaname); } EditorUtility.DisplayProgressBar("Generate AssetBundles Md5Mapping", info + "=>" + i.ToString() + "/" + allLen.ToString(), i / allLen); i++; } string[] special = new string[] { CUtils.platform, Common.CONFIG_CSV_NAME, Common.CRC32_FILELIST_NAME, Common.CRC32_VER_FILENAME }; foreach (string p in special) { name = EditorUtils.GetAssetBundleName(p); nameMd5 = CUtils.GetRightFileName(name); string line = "[\"" + nameMd5 + "\"] ={ size = 0, path = \"" + p + "\" },"; sb.AppendLine(line); nameSb.AppendFormat("{0}={1}\r\n", CUtils.GetRightFileName(name), name); } sb.AppendLine("}"); string tmpPath = Path.Combine(Application.dataPath, EditorUtils.TmpPath); EditorUtils.CheckDirectory(tmpPath); EditorUtility.DisplayProgressBar("Generate AssetBundles Md5Mapping", "write file to Assets/" + EditorUtils.TmpPath + "Md5Mapping.txt", 0.99f); string outPath = Path.Combine(tmpPath, "md5_asset_mapping.txt"); Debug.Log("write to path=" + outPath); using (StreamWriter sr = new StreamWriter(outPath, false)) { sr.Write(sb.ToString()); } outPath = Path.Combine(tmpPath, "md5_name_mapping.txt"); Debug.Log("write to path=" + outPath); using (StreamWriter sr = new StreamWriter(outPath, false)) { sr.Write(nameSb.ToString()); } EditorUtility.ClearProgressBar(); Debug.Log(info + " Complete! Assets/" + EditorUtils.TmpPath + "md5_asset_mapping.txt"); }
static void Bake() { var oldScene = UnityEditor.SceneManagement.EditorSceneManager.GetActiveScene().path; var loginSceneName = "Assets/Scenes/FrameworkEx/Login/Login"; var scene = UnityEditor.SceneManagement.EditorSceneManager.OpenScene(loginSceneName + ".unity"); if (!scene.IsValid()) { return; } var oldQualityLevel = QualitySettings.GetQualityLevel(); QualitySettings.SetQualityLevel(5); var oldShadowDistance = QualitySettings.shadowDistance; QualitySettings.shadowDistance = ConfigurationController.Instance._ShadowDistance; var oldIntensity = 0f; var go = GameObject.Find("Login/Directional Light"); Light light = null; if (go != null) { light = go.GetComponent <Light>(); if (light != null) { oldIntensity = light.intensity; light.intensity = ConfigurationController.Instance._BakeIntensity; } } LightmapEditorSettings.maxAtlasWidth = 1024; LightmapEditorSettings.maxAtlasHeight = 1024; Lightmapping.Clear(); Lightmapping.Bake(); if (oldIntensity > 0) { light.intensity = oldIntensity; } string[] filePaths = Directory.GetFiles(loginSceneName, "*.*", SearchOption.AllDirectories); foreach (var filePath in filePaths) { var fileName = Path.GetFileName(filePath); if (fileName.EndsWith(".png") || fileName.EndsWith(".exr")) { AssetImporter ai = AssetImporter.GetAtPath(filePath); if (ai is TextureImporter) { if (fileName.StartsWith("Lightmap")) { var ti = ((TextureImporter)ai); ti.mipmapEnabled = false; // iOS ti.SetPlatformTextureSettings("iPhone", 1024, TextureImporterFormat.PVRTC_RGB4); // Android ti.SetPlatformTextureSettings("Android", 1024, TextureImporterFormat.ETC_RGB4); ti.SaveAndReimport(); } } else { Debug.LogError("Error! " + fileName + " is not an image: " + ai); } } } UnityEditor.SceneManagement.EditorSceneManager.OpenScene(oldScene); QualitySettings.shadowDistance = oldShadowDistance; QualitySettings.SetQualityLevel(oldQualityLevel); }
static internal ReturnCode RunInternal(TaskInput input, out TaskOutput output) { input.EngineHooks = input.EngineHooks != null ? input.EngineHooks : new CalculateAssetDependencyHooks(); output = new TaskOutput(); output.AssetResults = new AssetOutput[input.Assets.Count]; IList <CachedInfo> cachedInfo = null; if (input.BuildCache != null) { IList <CacheEntry> entries = input.Assets.Select(x => input.BuildCache.GetCacheEntry(x, kVersion)).ToList(); input.BuildCache.LoadCachedData(entries, out cachedInfo); } for (int i = 0; i < input.Assets.Count; i++) { AssetOutput assetResult = new AssetOutput(); assetResult.asset = input.Assets[i]; if (cachedInfo != null && cachedInfo[i] != null) { assetResult.assetInfo = cachedInfo[i].Data[0] as AssetLoadInfo; assetResult.usageTags = cachedInfo[i].Data[1] as BuildUsageTagSet; assetResult.spriteData = cachedInfo[i].Data[2] as SpriteImporterData; assetResult.extendedData = cachedInfo[i].Data[3] as ExtendedAssetData; output.AssetResults[i] = assetResult; output.CachedAssetCount++; continue; } GUID asset = input.Assets[i]; string assetPath = AssetDatabase.GUIDToAssetPath(asset.ToString()); if (!input.ProgressTracker.UpdateInfoUnchecked(assetPath)) { return(ReturnCode.Canceled); } assetResult.assetInfo = new AssetLoadInfo(); assetResult.usageTags = new BuildUsageTagSet(); assetResult.assetInfo.asset = asset; var includedObjects = ContentBuildInterface.GetPlayerObjectIdentifiersInAsset(asset, input.Target); assetResult.assetInfo.includedObjects = new List <ObjectIdentifier>(includedObjects); var referencedObjects = ContentBuildInterface.GetPlayerDependenciesForObjects(includedObjects, input.Target, input.TypeDB); assetResult.assetInfo.referencedObjects = new List <ObjectIdentifier>(referencedObjects); var allObjects = new List <ObjectIdentifier>(includedObjects); allObjects.AddRange(referencedObjects); ContentBuildInterface.CalculateBuildUsageTags(allObjects.ToArray(), includedObjects, input.GlobalUsage, assetResult.usageTags, input.DependencyUsageCache); var importer = AssetImporter.GetAtPath(assetPath) as TextureImporter; if (importer != null && importer.textureType == TextureImporterType.Sprite) { assetResult.spriteData = new SpriteImporterData(); assetResult.spriteData.PackedSprite = false; assetResult.spriteData.SourceTexture = includedObjects.First(); if (EditorSettings.spritePackerMode != SpritePackerMode.Disabled) { assetResult.spriteData.PackedSprite = referencedObjects.Length > 0; } #if !UNITY_2020_1_OR_NEWER if (EditorSettings.spritePackerMode == SpritePackerMode.AlwaysOn || EditorSettings.spritePackerMode == SpritePackerMode.BuildTimeOnly) { assetResult.spriteData.PackedSprite = !string.IsNullOrEmpty(importer.spritePackingTag); } #endif } var representations = input.EngineHooks.LoadAllAssetRepresentationsAtPath(assetPath); if (!representations.IsNullOrEmpty()) { assetResult.extendedData = new ExtendedAssetData(); for (int j = 0; j < representations.Length; j++) { if (representations[j] == null) { BuildLogger.LogWarning($"SubAsset {j} inside {assetPath} is null. It will not be included in the build."); continue; } if (AssetDatabase.IsMainAsset(representations[j])) { continue; } string guid; long localId; if (!AssetDatabase.TryGetGUIDAndLocalFileIdentifier(representations[j], out guid, out localId)) { continue; } assetResult.extendedData.Representations.AddRange(includedObjects.Where(x => x.localIdentifierInFile == localId)); } } output.AssetResults[i] = assetResult; } if (input.BuildCache != null) { List <CachedInfo> toCache = new List <CachedInfo>(); for (int i = 0; i < input.Assets.Count; i++) { AssetOutput r = output.AssetResults[i]; if (cachedInfo[i] == null) { toCache.Add(GetCachedInfo(input.BuildCache, input.Assets[i], r.assetInfo, r.usageTags, r.spriteData, r.extendedData)); } } input.BuildCache.SaveCachedData(toCache); } return(ReturnCode.Success); }
public override void OnInspectorGUI() { base.OnInspectorGUI(); var buildData = target as ModPackageBuildPiplineData; EditorGUILayout.HelpBox($"Current Build On:{EditorUserBuildSettings.activeBuildTarget.ToString()} Tip: Press 'Ctrl + Shift + B' to change the current platform.", MessageType.None); if (GUILayout.Button("Build Linked Objects to AssetBundle")) { List <AssetBundleBuild> buildMap = new List <AssetBundleBuild>(); foreach (var o in buildData.linkedObjects) { var assetPath = AssetDatabase.GetAssetPath(o); var importer = AssetImporter.GetAtPath(assetPath); if (importer == null) { EditorUtility.DisplayDialog("Fetal Error", $"Missing Assets", "OK"); return; } var assetBundleName = importer.assetBundleName; var assetBundleVariant = importer.assetBundleVariant; var assetBundleFullName = string.IsNullOrEmpty(assetBundleVariant) ? assetBundleName : assetBundleName + "." + assetBundleVariant; if (string.IsNullOrEmpty(assetBundleName) || string.IsNullOrEmpty(assetBundleVariant)) { EditorUtility.DisplayDialog("Fetal Error", $"Asset:{o.name} has not set the assetbundle name and variant. Index in List: {buildData.linkedObjects.IndexOf(o)}", "OK"); return; } AssetBundleBuild build = new AssetBundleBuild { assetBundleName = assetBundleName, assetBundleVariant = assetBundleVariant, assetNames = AssetDatabase.GetAssetPathsFromAssetBundle(assetBundleFullName) }; buildMap.Add(build); } var buildDir = $"Build/Mod-BuildPipline/{EditorUserBuildSettings.activeBuildTarget}/{buildData.name}/packages/"; var dir = new DirectoryInfo(buildDir); if (!dir.Exists) { dir.Create(); } var manifest = BuildPipeline.BuildAssetBundles(buildDir, buildMap.ToArray(), BuildAssetBundleOptions.ChunkBasedCompression, EditorUserBuildSettings.activeBuildTarget); if (buildData.linkedModPackage != null) { buildData.linkedModPackage.relatedAssets = new List <string>(); } foreach (var file in dir.GetFiles("*")) { if (buildData.linkedModPackage != null) { buildData.linkedModPackage.relatedAssets.Add(MakeRelative(file.FullName, Application.dataPath)); } } EditorUtility.RevealInFinder(buildDir); } if (GUI.changed) { EditorUtility.SetDirty(target); } }
public static void DoImportBitmapFont(string fntPatn) { if (!IsFnt(fntPatn)) { return; } TextAsset fnt = AssetDatabase.LoadMainAssetAtPath(fntPatn) as TextAsset; string text = fnt.text; FntParse parse = FntParse.GetFntParse(ref text); if (parse == null) { return; } string fntName = Path.GetFileNameWithoutExtension(fntPatn); string rootPath = Path.GetDirectoryName(fntPatn); string fontPath = string.Format("{0}/{1}.fontsettings", rootPath, fntName); string texPath = string.Format("{0}/{1}", rootPath, parse.textureName); Texture2D texture = AssetDatabase.LoadMainAssetAtPath(texPath) as Texture2D; if (texture == null) { Debug.LogErrorFormat(fnt, "{0}: not found '{1}'.", typeof(BFImporter), texPath); return; } TextureImporter texImporter = AssetImporter.GetAtPath(texPath) as TextureImporter; texImporter.textureType = TextureImporterType.GUI; texImporter.mipmapEnabled = false; texImporter.SaveAndReimport(); Font font = AssetDatabase.LoadMainAssetAtPath(fontPath) as Font; if (font == null) { font = new Font(); AssetDatabase.CreateAsset(font, fontPath); AssetDatabase.WriteImportSettingsIfDirty(fontPath); AssetDatabase.ImportAsset(fontPath); } Material material = AssetDatabase.LoadAssetAtPath(fontPath, typeof(Material)) as Material; if (material == null) { material = new Material(Shader.Find("UI/Default")); material.name = "Font Material"; AssetDatabase.AddObjectToAsset(material, fontPath); // unity 5.4+ cannot refresh it immediately, must import it AssetDatabase.ImportAsset(fontPath); } font.material = material; material.mainTexture = texture; font.characterInfo = parse.charInfos; SerializedObject so = new SerializedObject(font); so.Update(); so.FindProperty("m_FontSize").floatValue = Mathf.Abs(parse.fontSize); so.FindProperty("m_LineSpacing").floatValue = parse.lineHeight; so.FindProperty("m_Ascent").floatValue = parse.lineBaseHeight; SerializedProperty prop = so.FindProperty("m_Descent"); if (prop != null) { prop.floatValue = parse.lineBaseHeight - parse.lineHeight; } UpdateKernings(so, parse.kernings); so.ApplyModifiedProperties(); so.SetIsDifferentCacheDirty(); AssetDatabase.SaveAssets(); #if UNITY_5_5_OR_NEWER // unity 5.5 can not load custom font ReloadFont(fontPath); #endif }
/// <summary> /// Copy srcaar files to aar files that are excluded from Unity's build process. /// </summary> /// <param name="dependencies">Dependencies to inject.</param> /// <returns>true if successful, false otherwise.</returns> private static bool CopySrcAars(ICollection <Dependency> dependencies) { bool succeeded = true; var aarFiles = new List <KeyValuePair <string, string> >(); // Copy each .srcaar file to .aar while configuring the plugin importer to ignore the // file. foreach (var aar in LocalMavenRepository.FindAarsInLocalRepos(dependencies)) { // Only need to copy for .srcaar if (Path.GetExtension(aar).CompareTo(".srcaar") != 0) { continue; } var aarPath = aar; if (FileUtils.IsUnderPackageDirectory(aar)) { var logicalPackagePath = FileUtils.GetPackageDirectory(aar, FileUtils.PackageDirectoryType.AssetDatabasePath); aarPath = FileUtils.ReplaceBaseAssetsOrPackagesFolder( aar, logicalPackagePath); } var dir = FileUtils.ReplaceBaseAssetsOrPackagesFolder( Path.GetDirectoryName(aar), GooglePlayServices.SettingsDialog.LocalMavenRepoDir); var filename = Path.GetFileNameWithoutExtension(aarPath); var targetFilename = Path.Combine(dir, filename + ".aar"); bool configuredAar = File.Exists(targetFilename); if (!configuredAar) { var error = PlayServicesResolver.CopyAssetAndLabel( aarPath, targetFilename); if (String.IsNullOrEmpty(error)) { try { PluginImporter importer = (PluginImporter)AssetImporter.GetAtPath( targetFilename); importer.SetCompatibleWithAnyPlatform(false); importer.SetCompatibleWithPlatform(BuildTarget.Android, false); configuredAar = true; } catch (Exception ex) { PlayServicesResolver.Log(String.Format( "Failed to disable {0} from being included by Unity's " + "internal build. {0} has been deleted and will not be " + "included in Gradle builds. ({1})", aar, ex), level: LogLevel.Error); } } else { PlayServicesResolver.Log(String.Format( "Unable to copy {0} to {1}. {1} will not be included in Gradle " + "builds. Reason: {2}", aarPath, targetFilename, error), level: LogLevel.Error); } } if (configuredAar) { aarFiles.Add(new KeyValuePair <string, string>(aarPath, targetFilename)); // Some versions of Unity do not mark the asset database as dirty when // plugin importer settings change so reimport the asset to synchronize // the state. AssetDatabase.ImportAsset(targetFilename, ImportAssetOptions.ForceUpdate); } else { if (File.Exists(targetFilename)) { AssetDatabase.DeleteAsset(targetFilename); } succeeded = false; } } foreach (var keyValue in aarFiles) { succeeded &= LocalMavenRepository.PatchPomFile(keyValue.Value, keyValue.Key); } return(succeeded); }
public override bool IsMatch(AssetImporter assetImporter) { return(assetImporter is AudioImporter && assetImporter.assetPath.Contains(audioPath)); }
public void SetAssetBundleNameAndVariant(string assetPath, string bundleName, string variantName) { AssetImporter.GetAtPath(assetPath).SetAssetBundleNameAndVariant(bundleName, variantName); }
/// <summary> /// Imports and configures atlas texture. /// </summary> /// <returns><c>true</c>, if import and configure atlas texture was successful, <c>false</c> otherwise.</returns> /// <param name="targetTexture">Target texture.</param> /// <param name="sourceTexture">Source texture.</param> /// <param name="uvs">Uvs.</param> /// <param name="names">Names.</param> /// <param name="defaultPivot">Default pivot.</param> /// <param name="defaultCustomPivot">Default custom pivot.</param> public static bool ImportAndConfigureAtlasTexture(Texture2D targetTexture, Texture2D sourceTexture, Rect[] uvs, SPSpriteImportData[] spritesImportData) { // Get the asset path string assetPath = SPTools.GetAssetPath(targetTexture); if (string.IsNullOrEmpty(assetPath)) { Debug.LogError("Sprite Packer failed to Import and Configure the atlas texture, reason: Could not resolve asset path."); return(false); } // Clear the read-only flag in texture file attributes if (!SPTools.RemoveReadOnlyFlag(assetPath)) { Debug.LogError("Sprite Packer failed to Import and Configure the atlas texture, reason: Could not remove the readonly flag from the asset."); return(false); } // Write the source texture data to the asset byte[] bytes = sourceTexture.EncodeToPNG(); System.IO.File.WriteAllBytes(assetPath, bytes); bytes = null; // Get the asset texture importer TextureImporter texImporter = AssetImporter.GetAtPath(assetPath) as TextureImporter; if (texImporter == null) { Debug.LogError("Sprite Packer failed to Import and Configure the atlas texture, reason: Could not get the texture importer for the asset."); return(false); } // Get the asset texture importer settings TextureImporterSettings texImporterSettings = new TextureImporterSettings(); // Apply sprite type texImporter.textureType = TextureImporterType.Sprite; texImporter.spriteImportMode = SpriteImportMode.Multiple; // Configure the spritesheet meta data SpriteMetaData[] spritesheetMeta = new SpriteMetaData[uvs.Length]; for (int i = 0; i < uvs.Length; i++) { if (SPTools.HasSpritesheetMeta(texImporter.spritesheet, spritesImportData[i].name)) { SpriteMetaData currentMeta = SPTools.GetSpritesheetMeta(texImporter.spritesheet, spritesImportData[i].name); Rect currentRect = uvs[i]; currentRect.x *= sourceTexture.width; currentRect.width *= sourceTexture.width; currentRect.y *= sourceTexture.height; currentRect.height *= sourceTexture.height; currentMeta.rect = currentRect; spritesheetMeta[i] = currentMeta; } else { SpriteMetaData currentMeta = new SpriteMetaData(); Rect currentRect = uvs[i]; currentRect.x *= sourceTexture.width; currentRect.width *= sourceTexture.width; currentRect.y *= sourceTexture.height; currentRect.height *= sourceTexture.height; currentMeta.rect = currentRect; currentMeta.name = spritesImportData[i].name; currentMeta.alignment = (int)spritesImportData[i].alignment; currentMeta.pivot = spritesImportData[i].pivot; currentMeta.border = spritesImportData[i].border; spritesheetMeta[i] = currentMeta; } } texImporter.spritesheet = spritesheetMeta; // Read the texture importer settings texImporter.ReadTextureSettings(texImporterSettings); // Disable Read/Write texImporterSettings.readable = false; // Re-set the texture importer settings texImporter.SetTextureSettings(texImporterSettings); // Save and Reimport the asset AssetDatabase.SaveAssets(); SPTools.DoAssetReimport(assetPath, ImportAssetOptions.ForceUpdate | ImportAssetOptions.ForceSynchronousImport); // Return success return(true); }
public override void OnInspectorGUI() { GraphData GetGraphData(AssetImporter importer) { var textGraph = File.ReadAllText(importer.assetPath, Encoding.UTF8); var graphObject = CreateInstance <GraphObject>(); graphObject.hideFlags = HideFlags.HideAndDontSave; bool isSubGraph; var extension = Path.GetExtension(importer.assetPath).Replace(".", ""); switch (extension) { case ShaderGraphImporter.Extension: isSubGraph = false; break; case ShaderGraphImporter.LegacyExtension: isSubGraph = false; break; case ShaderSubGraphImporter.Extension: isSubGraph = true; break; default: throw new Exception($"Invalid file extension {extension}"); } var assetGuid = AssetDatabase.AssetPathToGUID(importer.assetPath); graphObject.graph = new GraphData { assetGuid = assetGuid, isSubGraph = isSubGraph, messageManager = null }; MultiJson.Deserialize(graphObject.graph, textGraph); graphObject.graph.OnEnable(); graphObject.graph.ValidateGraph(); return(graphObject.graph); } if (GUILayout.Button("Open Shader Editor")) { AssetImporter importer = target as AssetImporter; Debug.Assert(importer != null, "importer != null"); ShowGraphEditWindow(importer.assetPath); } if (GUILayout.Button("View Generated Shader")) { AssetImporter importer = target as AssetImporter; string assetName = Path.GetFileNameWithoutExtension(importer.assetPath); string path = String.Format("Temp/GeneratedFromGraph-{0}.shader", assetName.Replace(" ", "")); var graphData = GetGraphData(importer); var generator = new Generator(graphData, null, GenerationMode.ForReals, assetName); if (GraphUtil.WriteToFile(path, generator.generatedShader)) { GraphUtil.OpenFile(path); } } if (Unsupported.IsDeveloperMode()) { if (GUILayout.Button("View Preview Shader")) { AssetImporter importer = target as AssetImporter; string assetName = Path.GetFileNameWithoutExtension(importer.assetPath); string path = String.Format("Temp/GeneratedFromGraph-{0}-Preview.shader", assetName.Replace(" ", "")); var graphData = GetGraphData(importer); var generator = new Generator(graphData, null, GenerationMode.Preview, $"{assetName}-Preview"); if (GraphUtil.WriteToFile(path, generator.generatedShader)) { GraphUtil.OpenFile(path); } } } if (GUILayout.Button("Copy Shader")) { AssetImporter importer = target as AssetImporter; string assetName = Path.GetFileNameWithoutExtension(importer.assetPath); var graphData = GetGraphData(importer); var generator = new Generator(graphData, null, GenerationMode.ForReals, assetName); GUIUtility.systemCopyBuffer = generator.generatedShader; } ApplyRevertGUI(); }
public void SaveLUT(LUTResult lutResult) { if (lutResult == null) { ToolSettings.Instance.Message = "Error while reading LUT data."; return; } var assetpath = _texturePath; bool justBrowsed = false; if (string.IsNullOrEmpty(assetpath)) { if (EditorUtility.DisplayDialog("Browse?", "There is no current path to save the file to.", "Browse", "Cancel")) { var path = EditorUtility.SaveFilePanelInProject("Save as", Path.GetFileName(_texturePath), "png", "Please enter a file name to save the texture to"); justBrowsed = true; if (string.IsNullOrEmpty(path)) { return; } _texturePath = path; } else { return; } } if (File.Exists(_texturePath) && !justBrowsed && !_overwrite) { if (!EditorUtility.DisplayDialog("Overwrite?", "File already exists. This action will overwrite the current file. Do you want to continue?", "Overwrite", "Cancel")) { return; } } File.WriteAllBytes(_texturePath, lutResult.Texture.EncodeToPNG()); AssetDatabase.Refresh(); var text = AssetDatabase.LoadAssetAtPath(_texturePath, typeof(Texture2D)) as Texture2D; if (text != null) { text.wrapMode = TextureWrapMode.Clamp; text.filterMode = FilterMode.Bilinear; } TextureImporter tImporter = AssetImporter.GetAtPath(_texturePath) as TextureImporter; if (tImporter != null) { tImporter.mipmapEnabled = false; tImporter.isReadable = false; tImporter.filterMode = FilterMode.Bilinear; tImporter.anisoLevel = 0; #if UNITY_5_6_OR_NEWER tImporter.textureType = TextureImporterType.Default; tImporter.textureCompression = TextureImporterCompression.Uncompressed; tImporter.sRGBTexture = false; #else tImporter.textureType = TextureImporterType.Advanced; tImporter.textureFormat = TextureImporterFormat.AutomaticTruecolor; tImporter.linearTexture = true; #endif tImporter.wrapMode = TextureWrapMode.Clamp; tImporter.maxTextureSize = 1024; AssetDatabase.ImportAsset(_texturePath, ImportAssetOptions.ForceUpdate); } }
void CreateNode(object obj, Vector2 nodePosition) { var texture2D = obj as Texture2D; if (texture2D != null) { graph.owner.RegisterCompleteObjectUndo("Drag Texture"); bool isNormalMap = false; if (EditorUtility.IsPersistent(texture2D) && !string.IsNullOrEmpty(AssetDatabase.GetAssetPath(texture2D))) { var importer = AssetImporter.GetAtPath(AssetDatabase.GetAssetPath(texture2D)) as TextureImporter; if (importer != null) { isNormalMap = importer.textureType == TextureImporterType.NormalMap; } } var node = new SampleTexture2DNode(); var drawState = node.drawState; drawState.position = new Rect(nodePosition, drawState.position.size); node.drawState = drawState; graph.AddNode(node); if (isNormalMap) { node.textureType = TextureType.Normal; } var inputslot = node.FindInputSlot <Texture2DInputMaterialSlot>(SampleTexture2DNode.TextureInputId); if (inputslot != null) { inputslot.texture = texture2D; } } var textureArray = obj as Texture2DArray; if (textureArray != null) { graph.owner.RegisterCompleteObjectUndo("Drag Texture Array"); var property = new Texture2DArrayShaderProperty { displayName = textureArray.name, value = { textureArray = textureArray } }; graph.AddShaderProperty(property); var node = new SampleTexture2DArrayNode(); var drawState = node.drawState; drawState.position = new Rect(nodePosition, drawState.position.size); node.drawState = drawState; graph.AddNode(node); var inputslot = node.FindSlot <Texture2DArrayInputMaterialSlot>(SampleTexture2DArrayNode.TextureInputId); if (inputslot != null) { inputslot.textureArray = textureArray; } } var texture3D = obj as Texture3D; if (texture3D != null) { graph.owner.RegisterCompleteObjectUndo("Drag Texture 3D"); var property = new Texture3DShaderProperty { displayName = texture3D.name, value = { texture = texture3D } }; graph.AddShaderProperty(property); var node = new SampleTexture3DNode(); var drawState = node.drawState; drawState.position = new Rect(nodePosition, drawState.position.size); node.drawState = drawState; graph.AddNode(node); var inputslot = node.FindSlot <Texture3DInputMaterialSlot>(SampleTexture3DNode.TextureInputId); if (inputslot != null) { inputslot.texture = texture3D; } } var cubemap = obj as Cubemap; if (cubemap != null) { graph.owner.RegisterCompleteObjectUndo("Drag Cubemap"); var property = new CubemapShaderProperty { displayName = cubemap.name, value = { cubemap = cubemap } }; graph.AddShaderProperty(property); var node = new SampleCubemapNode(); var drawState = node.drawState; drawState.position = new Rect(nodePosition, drawState.position.size); node.drawState = drawState; graph.AddNode(node); var inputslot = node.FindInputSlot <CubemapInputMaterialSlot>(SampleCubemapNode.CubemapInputId); if (inputslot != null) { inputslot.cubemap = cubemap; } } var subGraphAsset = obj as SubGraphAsset; if (subGraphAsset != null) { graph.owner.RegisterCompleteObjectUndo("Drag Sub-Graph"); var node = new SubGraphNode(); var drawState = node.drawState; drawState.position = new Rect(nodePosition, drawState.position.size); node.drawState = drawState; node.subGraphAsset = subGraphAsset; graph.AddNode(node); } var blackboardField = obj as BlackboardField; if (blackboardField != null) { AbstractShaderProperty property = blackboardField.userData as AbstractShaderProperty; if (property != null) { graph.owner.RegisterCompleteObjectUndo("Drag Property"); var node = new PropertyNode(); var drawState = node.drawState; drawState.position = new Rect(nodePosition, drawState.position.size); node.drawState = drawState; graph.AddNode(node); // Setting the guid requires the graph to be set first. node.propertyGuid = property.guid; } } }
/// <summary> /// 设置AssetBundleName /// </summary> /// <param name="fullpath">Fullpath.</param> public static void setAssetBundleName(string fullPath) { string[] files = System.IO.Directory.GetFiles(fullPath); if (files == null || files.Length == 0) { return; } Debug.Log("Set AssetBundleName Start......"); string dirBundleName = fullPath.Substring(RES_SRC_PATH.Length); dirBundleName = dirBundleName.Replace("/", "@") + ASSET_BUNDLE_SUFFIX; foreach (string file in files) { if (file.EndsWith(".meta")) { continue; } AssetImporter importer = AssetImporter.GetAtPath(file); if (importer != null) { string ext = System.IO.Path.GetExtension(file); string bundleName = dirBundleName; if (null != ext && (ext.Equals(".prefab") || ext.Equals(".unity"))) { // prefab单个文件打包 bundleName = file.Substring(RES_SRC_PATH.Length); bundleName = bundleName.Replace("/", "@"); if (null != ext) { bundleName = bundleName.Replace(ext, ASSET_BUNDLE_SUFFIX); } else { bundleName += ASSET_BUNDLE_SUFFIX; } } bundleName = bundleName.ToLower(); Debug.LogFormat("Set AssetName Succ, File:{0}, AssetName:{1}", file, bundleName); importer.assetBundleName = bundleName; EditorUtility.UnloadUnusedAssetsImmediate(); // 存储bundleInfo AssetBuildBundleInfo info = new AssetBuildBundleInfo(); info.assetName = file; info.fileName = file; info.bundleName = bundleName; if (null != ext) { info.fileName = file.Substring(0, file.IndexOf(ext)); } fileMap.Add(file, info); List <AssetBuildBundleInfo> infoList = null; bundleMap.TryGetValue(info.bundleName, out infoList); if (null == infoList) { infoList = new List <AssetBuildBundleInfo> (); bundleMap.Add(info.bundleName, infoList); } infoList.Add(info); } else { Debug.LogFormat("Set AssetName Fail, File:{0}, Msg:Importer is null", file); } } Debug.Log("Set AssetBundleName End......"); }
public void OnInspectorGUI(AssetImporter referenceImporter, BuildTargetGroup target, Action onValueChanged) { }
public void Save(string assetPath, string assetName, bool createBillboardAsset = false) { var lastSlash = assetPath.LastIndexOf("/", StringComparison.Ordinal); var folder = assetPath.Substring(0, lastSlash); EditorUtility.SetDirty(this); BaseTexture.name = "ImposterBase"; var baseTexPath = WriteTexture(BaseTexture, folder, assetName); PackTexture.name = "ImposterPack"; var normTexPath = WriteTexture(PackTexture, folder, assetName); AssetDatabase.Refresh(); var importer = AssetImporter.GetAtPath(baseTexPath) as TextureImporter; if (importer != null) { importer.textureType = TextureImporterType.Default; importer.maxTextureSize = AtlasResolution; importer.alphaSource = TextureImporterAlphaSource.FromInput; importer.alphaIsTransparency = false; importer.sRGBTexture = false; importer.SaveAndReimport(); BaseTexture = AssetDatabase.LoadAssetAtPath <Texture2D>(baseTexPath); } importer = AssetImporter.GetAtPath(normTexPath) as TextureImporter; if (importer != null) { importer.textureType = TextureImporterType.Default; importer.maxTextureSize = AtlasResolution; importer.alphaSource = TextureImporterAlphaSource.FromInput; importer.alphaIsTransparency = false; importer.sRGBTexture = false; importer.SaveAndReimport(); PackTexture = AssetDatabase.LoadAssetAtPath <Texture2D>(normTexPath); } var shader = Shader.Find("XRA/IMP/Standard (Surface)"); Material = new Material(shader); Material.SetTexture("_ImposterBaseTex", BaseTexture); Material.SetTexture("_ImposterWorldNormalDepthTex", PackTexture); Material.SetFloat("_ImposterFrames", Frames); Material.SetFloat("_ImposterSize", Radius); Material.SetVector("_ImposterOffset", Offset); Material.SetFloat("_ImposterFullSphere", IsHalf ? 0f : 1f); Material.name = assetName; EditorUtility.SetDirty(Material); //create material AssetDatabase.CreateAsset(Material, folder + "/" + assetName + "_Imposter_Mat.mat"); //mesh (not for billboardAsset) Mesh = MeshSetup(); Mesh.name = "ImposterQuad_" + Radius.ToString("F1"); AssetDatabase.AddObjectToAsset(Mesh, assetPath); //create unity billboard asset, for billboard renderer //TODO has issues, but unity terrain is being upgraded so billboard renderer might be going if (createBillboardAsset) { BillboardAsset = CreateUnityBillboardAsset(folder, assetName, assetPath); } AssetDatabase.SaveAssets(); }
bool Load(Texture2D texture) { if (texture == null) { return(true); } var importer = AssetImporter.GetAtPath(AssetDatabase.GetAssetPath(texture)); if (importer != null) { if (importer.userData.StartsWith("texture_combiner")) { //no error check here! //may break with different userData var userDataSplit = importer.userData.Split(' '); var rGuid = userDataSplit[1].Split(':')[1]; var gGuid = userDataSplit[2].Split(':')[1]; var bGuid = userDataSplit[3].Split(':')[1]; var aGuid = userDataSplit[4].Split(':')[1]; textureR = AssetDatabase.LoadAssetAtPath <Texture2D>(AssetDatabase.GUIDToAssetPath(rGuid)); textureG = AssetDatabase.LoadAssetAtPath <Texture2D>(AssetDatabase.GUIDToAssetPath(gGuid)); textureB = AssetDatabase.LoadAssetAtPath <Texture2D>(AssetDatabase.GUIDToAssetPath(bGuid)); textureA = AssetDatabase.LoadAssetAtPath <Texture2D>(AssetDatabase.GUIDToAssetPath(aGuid)); string errorGUID = ""; if (!string.IsNullOrEmpty(rGuid) && textureR == null) { errorGUID += "Red "; } if (!string.IsNullOrEmpty(gGuid) && textureG == null) { errorGUID += "Green "; } if (!string.IsNullOrEmpty(bGuid) && textureB == null) { errorGUID += "Blue "; } if (!string.IsNullOrEmpty(aGuid) && textureA == null) { errorGUID += "Alpha"; } sourceR = (Channel)System.Enum.Parse(typeof(Channel), userDataSplit[5].Split(':')[1]); sourceG = (Channel)System.Enum.Parse(typeof(Channel), userDataSplit[6].Split(':')[1]); sourceB = (Channel)System.Enum.Parse(typeof(Channel), userDataSplit[7].Split(':')[1]); sourceA = (Channel)System.Enum.Parse(typeof(Channel), userDataSplit[8].Split(':')[1]); textureSaved = texture; if (textureCombined != null) { textureCombined.Release(); DestroyImmediate(textureCombined); } if (textureCombinedAlpha != null) { textureCombinedAlpha.Release(); DestroyImmediate(textureCombinedAlpha); } if (!string.IsNullOrEmpty(errorGUID)) { EditorUtility.DisplayDialog("Error", "Source texture(s) couldn't be found in the project:\n\n" + errorGUID + "\n\nMaybe they have been deleted, or they GUID has been updated?", "Ok"); } return(true); } else { ShowNotification(new GUIContent("This texture doesn't seem to have been generated with the Texture Combiner")); } } return(false); }
public override BuildPipelineCodes Convert(AssetInfoMap assetLoadInfo, out AssetInfoMap output) { StartProgressBar("Stripping unused sprite source textures", 3); if (!UpdateProgressBar("Finding sprite source textures")) { output = null; return(BuildPipelineCodes.Canceled); } var spriteRefCount = new Dictionary <ObjectIdentifier, int>(); foreach (var assetInfo in assetLoadInfo) { var path = AssetDatabase.GUIDToAssetPath(assetInfo.Value.asset.ToString()); var importer = AssetImporter.GetAtPath(path) as TextureImporter; if (importer != null && importer.textureType == TextureImporterType.Sprite && !string.IsNullOrEmpty(importer.spritePackingTag)) { spriteRefCount[assetInfo.Value.includedObjects[0]] = 0; } } Hash128 hash = CalculateInputHash(assetLoadInfo, spriteRefCount); if (UseCache && BuildCache.TryLoadCachedResults(hash, out output)) { EndProgressBar(); return(BuildPipelineCodes.SuccessCached); } // Mutating the input, this is the only converter that does this output = assetLoadInfo; if (!UpdateProgressBar("Finding sprite source textures usage")) { EndProgressBar(); return(BuildPipelineCodes.Canceled); } foreach (var assetInfo in output) { if (!string.IsNullOrEmpty(assetInfo.Value.processedScene)) { continue; } foreach (var reference in assetInfo.Value.referencedObjects) { int refCount = 0; if (!spriteRefCount.TryGetValue(reference, out refCount)) { continue; } // Note: Because pass by value spriteRefCount[reference] = ++refCount; } } if (!UpdateProgressBar("Removing unused sprite source textures.")) { EndProgressBar(); return(BuildPipelineCodes.Canceled); } foreach (var source in spriteRefCount) { if (source.Value > 0) { continue; } var assetInfo = output[source.Key.guid]; var includedObjects = assetInfo.includedObjects; includedObjects.Swap(0, includedObjects.Length - 1); Array.Resize(ref includedObjects, includedObjects.Length - 1); // Note: Because pass by value output[source.Key.guid] = assetInfo; } if (UseCache && !BuildCache.SaveCachedResults(hash, output)) { BuildLogger.LogWarning("Unable to cache SpriteSourceProcessor results."); } if (!EndProgressBar()) { return(BuildPipelineCodes.Canceled); } return(BuildPipelineCodes.Success); }
public override void ValidateFeatures(VRC_AvatarDescriptor avatar, Animator anim, AvatarPerformanceStats perfStats) { //Create avatar debug hashset VRCAvatarDescriptor avatarSDK3 = avatar as VRCAvatarDescriptor; if (avatarSDK3 != null) { avatarSDK3.animationHashSet.Clear(); foreach (VRCAvatarDescriptor.CustomAnimLayer animLayer in avatarSDK3.baseAnimationLayers) { AnimatorController controller = animLayer.animatorController as AnimatorController; if (controller != null) { foreach (AnimatorControllerLayer layer in controller.layers) { ProcessStateMachine(layer.stateMachine, ""); void ProcessStateMachine(AnimatorStateMachine stateMachine, string prefix) { //Update prefix prefix = prefix + stateMachine.name + "."; //States foreach (var state in stateMachine.states) { VRCAvatarDescriptor.DebugHash hash = new VRCAvatarDescriptor.DebugHash(); string fullName = prefix + state.state.name; hash.hash = Animator.StringToHash(fullName); hash.name = fullName.Remove(0, layer.stateMachine.name.Length + 1); avatarSDK3.animationHashSet.Add(hash); } //Sub State Machines foreach (var subMachine in stateMachine.stateMachines) { ProcessStateMachine(subMachine.stateMachine, prefix); } } } } } } //Validate Playable Layers if (avatarSDK3 != null && avatarSDK3.customizeAnimationLayers) { VRCAvatarDescriptor.CustomAnimLayer gestureLayer = avatarSDK3.baseAnimationLayers[2]; if (anim != null && anim.isHuman && gestureLayer.animatorController != null && gestureLayer.type == VRCAvatarDescriptor.AnimLayerType.Gesture && !gestureLayer.isDefault) { AnimatorController controller = gestureLayer.animatorController as AnimatorController; if (controller != null && controller.layers[0].avatarMask == null) { _builder.OnGUIError(avatar, "Gesture Layer needs valid mask on first animator layer", delegate { OpenAnimatorControllerWindow(controller); }, null); } } } //Expression menu images if (avatarSDK3 != null) { bool ValidateTexture(Texture2D texture) { string path = AssetDatabase.GetAssetPath(texture); TextureImporter importer = AssetImporter.GetAtPath(path) as TextureImporter; if (importer == null) { return(true); } TextureImporterPlatformSettings settings = importer.GetDefaultPlatformTextureSettings(); //Max texture size if ((texture.width > MAX_ACTION_TEXTURE_SIZE || texture.height > MAX_ACTION_TEXTURE_SIZE) && settings.maxTextureSize > MAX_ACTION_TEXTURE_SIZE) { return(false); } //Compression if (settings.textureCompression == TextureImporterCompression.Uncompressed) { return(false); } //Success return(true); } void FixTexture(Texture2D texture) { string path = AssetDatabase.GetAssetPath(texture); TextureImporter importer = AssetImporter.GetAtPath(path) as TextureImporter; if (importer == null) { return; } TextureImporterPlatformSettings settings = importer.GetDefaultPlatformTextureSettings(); //Max texture size if (texture.width > MAX_ACTION_TEXTURE_SIZE || texture.height > MAX_ACTION_TEXTURE_SIZE) { settings.maxTextureSize = Math.Min(settings.maxTextureSize, MAX_ACTION_TEXTURE_SIZE); } //Compression if (settings.textureCompression == TextureImporterCompression.Uncompressed) { settings.textureCompression = TextureImporterCompression.Compressed; } //Set & Reimport importer.SetPlatformTextureSettings(settings); AssetDatabase.ImportAsset(path); } //Find all textures List <Texture2D> textures = new List <Texture2D>(); List <VRCExpressionsMenu> menuStack = new List <VRCExpressionsMenu>(); FindTextures(avatarSDK3.expressionsMenu); void FindTextures(VRCExpressionsMenu menu) { if (menu == null || menuStack.Contains(menu)) //Prevent recursive menu searching { return; } menuStack.Add(menu); //Check controls foreach (VRCExpressionsMenu.Control control in menu.controls) { AddTexture(control.icon); if (control.labels != null) { foreach (VRCExpressionsMenu.Control.Label label in control.labels) { AddTexture(label.icon); } } if (control.subMenu != null) { FindTextures(control.subMenu); } } void AddTexture(Texture2D texture) { if (texture != null) { textures.Add(texture); } } } //Validate bool isValid = true; foreach (Texture2D texture in textures) { if (!ValidateTexture(texture)) { isValid = false; } } if (!isValid) { _builder.OnGUIError(avatar, "Images used for Actions & Moods are too large.", delegate { Selection.activeObject = avatar.gameObject; }, FixTextures); } //Fix void FixTextures() { foreach (Texture2D texture in textures) { FixTexture(texture); } } } //Expression menu parameters if (avatarSDK3 != null) { //Check for expression menu/parameters object if (avatarSDK3.expressionsMenu != null || avatarSDK3.expressionParameters != null) { //Menu if (avatarSDK3.expressionsMenu == null) { _builder.OnGUIError(avatar, "VRCExpressionsMenu object reference is missing.", delegate { Selection.activeObject = avatarSDK3; }, null); } //Parameters if (avatarSDK3.expressionParameters == null) { _builder.OnGUIError(avatar, "VRCExpressionParameters object reference is missing.", delegate { Selection.activeObject = avatarSDK3; }, null); } } //Check if parameters is valid if (avatarSDK3.expressionParameters != null && avatarSDK3.expressionParameters.CalcTotalCost() > VRCExpressionParameters.MAX_PARAMETER_COST) { _builder.OnGUIError(avatar, "VRCExpressionParameters has too many parameters defined.", delegate { Selection.activeObject = avatarSDK3.expressionParameters; }, null); } //Find all existing parameters if (avatarSDK3.expressionsMenu != null && avatarSDK3.expressionParameters != null) { List <VRCExpressionsMenu> menuStack = new List <VRCExpressionsMenu>(); List <string> parameters = new List <string>(); List <VRCExpressionsMenu> selects = new List <VRCExpressionsMenu>(); FindParameters(avatarSDK3.expressionsMenu); void FindParameters(VRCExpressionsMenu menu) { if (menu == null || menuStack.Contains(menu)) //Prevent recursive menu searching { return; } menuStack.Add(menu); //Check controls foreach (VRCExpressionsMenu.Control control in menu.controls) { AddParameter(control.parameter); if (control.subParameters != null) { foreach (VRCExpressionsMenu.Control.Parameter subParameter in control.subParameters) { AddParameter(subParameter); } } if (control.subMenu != null) { FindParameters(control.subMenu); } } void AddParameter(VRCExpressionsMenu.Control.Parameter parameter) { if (parameter != null) { parameters.Add(parameter.name); selects.Add(menu); } } } //Validate parameters for (int i = 0; i < parameters.Count; i++) { string parameter = parameters[i]; VRCExpressionsMenu select = selects[i]; //Find bool exists = string.IsNullOrEmpty(parameter) || avatarSDK3.expressionParameters.FindParameter(parameter) != null; if (!exists) { _builder.OnGUIError(avatar, "VRCExpressionsMenu uses a parameter that is not defined.\nParameter: " + parameter, delegate { Selection.activeObject = select; }, null); } } //Validate param choices foreach (var menu in menuStack) { foreach (var control in menu.controls) { bool isValid = true; if (control.type == VRCExpressionsMenu.Control.ControlType.FourAxisPuppet) { isValid &= ValidateNonBoolParam(control.subParameters[0].name); isValid &= ValidateNonBoolParam(control.subParameters[1].name); isValid &= ValidateNonBoolParam(control.subParameters[2].name); isValid &= ValidateNonBoolParam(control.subParameters[3].name); } else if (control.type == VRCExpressionsMenu.Control.ControlType.RadialPuppet) { isValid &= ValidateNonBoolParam(control.subParameters[0].name); } else if (control.type == VRCExpressionsMenu.Control.ControlType.TwoAxisPuppet) { isValid &= ValidateNonBoolParam(control.subParameters[0].name); isValid &= ValidateNonBoolParam(control.subParameters[1].name); } if (!isValid) { _builder.OnGUIError(avatar, "VRCExpressionsMenu uses an invalid parameter for a control.\nControl: " + control.name, delegate { Selection.activeObject = menu; }, null); } } bool ValidateNonBoolParam(string name) { VRCExpressionParameters.Parameter param = string.IsNullOrEmpty(name) ? null : avatarSDK3.expressionParameters.FindParameter(name); if (param != null && param.valueType == VRCExpressionParameters.ValueType.Bool) { return(false); } return(true); } } } } List <Component> componentsToRemove = AvatarValidation.FindIllegalComponents(avatar.gameObject).ToList(); // create a list of the PipelineSaver component(s) List <Component> toRemoveSilently = new List <Component>(); foreach (Component c in componentsToRemove) { if (c.GetType().Name == "PipelineSaver") { toRemoveSilently.Add(c); } } // delete PipelineSaver(s) from the list of the Components we will destroy now foreach (Component c in toRemoveSilently) { componentsToRemove.Remove(c); } HashSet <string> componentsToRemoveNames = new HashSet <string>(); List <Component> toRemove = componentsToRemove as List <Component> ?? componentsToRemove; foreach (Component c in toRemove) { if (componentsToRemoveNames.Contains(c.GetType().Name) == false) { componentsToRemoveNames.Add(c.GetType().Name); } } if (componentsToRemoveNames.Count > 0) { _builder.OnGUIError(avatar, "The following component types are found on the Avatar and will be removed by the client: " + string.Join(", ", componentsToRemoveNames.ToArray()), delegate { ShowRestrictedComponents(toRemove); }, delegate { FixRestrictedComponents(toRemove); }); } List <AudioSource> audioSources = avatar.gameObject.GetComponentsInChildren <AudioSource>(true).ToList(); if (audioSources.Count > 0) { _builder.OnGUIWarning(avatar, "Audio sources found on Avatar, they will be adjusted to safe limits, if necessary.", GetAvatarSubSelectAction(avatar, typeof(AudioSource)), null); } List <VRCStation> stations = avatar.gameObject.GetComponentsInChildren <VRCStation>(true).ToList(); if (stations.Count > 0) { _builder.OnGUIWarning(avatar, "Stations found on Avatar, they will be adjusted to safe limits, if necessary.", GetAvatarSubSelectAction(avatar, typeof(VRCStation)), null); } if (VRCSdkControlPanel.HasSubstances(avatar.gameObject)) { _builder.OnGUIWarning(avatar, "This avatar has one or more Substance materials, which is not supported and may break in-game. Please bake your Substances to regular materials.", () => { Selection.objects = VRCSdkControlPanel.GetSubstanceObjects(avatar.gameObject); }, null); } CheckAvatarMeshesForLegacyBlendShapesSetting(avatar); CheckAvatarMeshesForMeshReadWriteSetting(avatar); #if UNITY_ANDROID IEnumerable <Shader> illegalShaders = AvatarValidation.FindIllegalShaders(avatar.gameObject); foreach (Shader s in illegalShaders) { _builder.OnGUIError(avatar, "Avatar uses unsupported shader '" + s.name + "'. You can only use the shaders provided in 'VRChat/Mobile' for Quest avatars.", delegate() { Selection.activeObject = avatar.gameObject; }, null); } #endif foreach (AvatarPerformanceCategory perfCategory in Enum.GetValues(typeof(AvatarPerformanceCategory))) { if (perfCategory == AvatarPerformanceCategory.Overall || perfCategory == AvatarPerformanceCategory.PolyCount || perfCategory == AvatarPerformanceCategory.AABB || perfCategory == AvatarPerformanceCategory.AvatarPerformanceCategoryCount) { continue; } Action show = null; switch (perfCategory) { case AvatarPerformanceCategory.AnimatorCount: show = GetAvatarSubSelectAction(avatar, typeof(Animator)); break; case AvatarPerformanceCategory.AudioSourceCount: show = GetAvatarSubSelectAction(avatar, typeof(AudioSource)); break; case AvatarPerformanceCategory.BoneCount: show = GetAvatarSubSelectAction(avatar, typeof(SkinnedMeshRenderer)); break; case AvatarPerformanceCategory.ClothCount: show = GetAvatarSubSelectAction(avatar, typeof(Cloth)); break; case AvatarPerformanceCategory.ClothMaxVertices: show = GetAvatarSubSelectAction(avatar, typeof(Cloth)); break; case AvatarPerformanceCategory.LightCount: show = GetAvatarSubSelectAction(avatar, typeof(Light)); break; case AvatarPerformanceCategory.LineRendererCount: show = GetAvatarSubSelectAction(avatar, typeof(LineRenderer)); break; case AvatarPerformanceCategory.MaterialCount: show = GetAvatarSubSelectAction(avatar, new[] { typeof(MeshRenderer), typeof(SkinnedMeshRenderer) }); break; case AvatarPerformanceCategory.MeshCount: show = GetAvatarSubSelectAction(avatar, new[] { typeof(MeshRenderer), typeof(SkinnedMeshRenderer) }); break; case AvatarPerformanceCategory.ParticleCollisionEnabled: show = GetAvatarSubSelectAction(avatar, typeof(ParticleSystem)); break; case AvatarPerformanceCategory.ParticleMaxMeshPolyCount: show = GetAvatarSubSelectAction(avatar, typeof(ParticleSystem)); break; case AvatarPerformanceCategory.ParticleSystemCount: show = GetAvatarSubSelectAction(avatar, typeof(ParticleSystem)); break; case AvatarPerformanceCategory.ParticleTotalCount: show = GetAvatarSubSelectAction(avatar, typeof(ParticleSystem)); break; case AvatarPerformanceCategory.ParticleTrailsEnabled: show = GetAvatarSubSelectAction(avatar, typeof(ParticleSystem)); break; case AvatarPerformanceCategory.PhysicsColliderCount: show = GetAvatarSubSelectAction(avatar, typeof(Collider)); break; case AvatarPerformanceCategory.PhysicsRigidbodyCount: show = GetAvatarSubSelectAction(avatar, typeof(Rigidbody)); break; case AvatarPerformanceCategory.PolyCount: show = GetAvatarSubSelectAction(avatar, new[] { typeof(MeshRenderer), typeof(SkinnedMeshRenderer) }); break; case AvatarPerformanceCategory.SkinnedMeshCount: show = GetAvatarSubSelectAction(avatar, typeof(SkinnedMeshRenderer)); break; case AvatarPerformanceCategory.TrailRendererCount: show = GetAvatarSubSelectAction(avatar, typeof(TrailRenderer)); break; } // we can only show these buttons if DynamicBone is installed Type dynamicBoneType = typeof(AvatarValidation).Assembly.GetType("DynamicBone"); Type dynamicBoneColliderType = typeof(AvatarValidation).Assembly.GetType("DynamicBoneCollider"); if ((dynamicBoneType != null) && (dynamicBoneColliderType != null)) { switch (perfCategory) { case AvatarPerformanceCategory.DynamicBoneColliderCount: show = GetAvatarSubSelectAction(avatar, dynamicBoneColliderType); break; case AvatarPerformanceCategory.DynamicBoneCollisionCheckCount: show = GetAvatarSubSelectAction(avatar, dynamicBoneColliderType); break; case AvatarPerformanceCategory.DynamicBoneComponentCount: show = GetAvatarSubSelectAction(avatar, dynamicBoneType); break; case AvatarPerformanceCategory.DynamicBoneSimulatedBoneCount: show = GetAvatarSubSelectAction(avatar, dynamicBoneType); break; } } OnGUIPerformanceInfo(avatar, perfStats, perfCategory, show, null); } _builder.OnGUILink(avatar, "Avatar Optimization Tips", VRCSdkControlPanel.AVATAR_OPTIMIZATION_TIPS_URL); }
private static bool AssetInIgnores(AssetInfo assetInfo, List <string> ignoredScenes) { if (assetInfo.Type == CSReflectionTools.monoScriptType /* && !MaintainerSettings.Cleaner.findUnreferencedScripts*/) { return(true); } if (assetInfo.Type == CSReflectionTools.textAssetType) { return(true); } if (assetInfo.Type == CSReflectionTools.spriteAtlasType) { var atlas = AssetDatabase.LoadAssetAtPath <UnityEngine.U2D.SpriteAtlas>(assetInfo.Path); if (atlas != null) { var so = new SerializedObject(atlas); // source: SpriteAtlasInspector var bindAsDefaultProperty = so.FindProperty("m_EditorData.bindAsDefault"); if (bindAsDefaultProperty != null) { if (bindAsDefaultProperty.boolValue) { return(true); } } else { Debug.LogError(Maintainer.LogPrefix + "Can't parse UnityEngine.U2D.SpriteAtlas, please report to " + Maintainer.SupportEmail); } } else { Debug.LogWarning(Maintainer.LogPrefix + "Couldn't load SpriteAtlas: " + assetInfo.Path); } } if (assetInfo.Type == CSReflectionTools.assemblyDefinitionAssetType) { return(true); } if (assetInfo.Type == CSReflectionTools.defaultAssetType) { var importer = AssetImporter.GetAtPath(assetInfo.Path); if (importer is PluginImporter) { return(true); } if (importer.ToString() == " (UnityEngine.DefaultImporter)") { return(true); } } if (CSFilterTools.IsValueMatchesAnyFilter(assetInfo.Path, MaintainerSettings.Cleaner.MandatoryFilters)) { return(true); } if (CSFilterTools.IsValueMatchesAnyFilter(assetInfo.Path, MaintainerSettings.Cleaner.pathIgnoresFilters)) { return(true); } if (assetInfo.Type == CSReflectionTools.sceneAssetType && ignoredScenes.IndexOf(assetInfo.Path) != -1) { return(true); } foreach (var referencedAtInfo in assetInfo.referencedAtInfoList) { if (referencedAtInfo.assetInfo.SettingsKind != AssetSettingsKind.NotSettings && referencedAtInfo.assetInfo.SettingsKind != AssetSettingsKind.EditorBuildSettings) { return(true); } if (referencedAtInfo.assetInfo.Kind == AssetKind.FromPackage) { return(true); } } var assetBundleName = AssetDatabase.GetImplicitAssetBundleName(assetInfo.Path); if (!string.IsNullOrEmpty(assetBundleName)) { return(true); } #if UNITY_2018_2_OR_NEWER if (assetInfo.Type != null) { var nameSpace = assetInfo.Type.Namespace; if (!string.IsNullOrEmpty(nameSpace)) { if (nameSpace.StartsWith("UnityEditor.AddressableAssets")) { return(true); } } } #endif return(false); }
/// <summary> /// Automatically creates prefab variants for newly imported models /// </summary> /// <param name="importedAssets"></param> /// <param name="deletedAssets"></param> /// <param name="movedAssets"></param> /// <param name="movedFromAssetPaths"></param> public static void OnPostprocessAllAssets(string[] importedAssets, string[] deletedAssets, string[] movedAssets, string[] movedFromAssetPaths) { // Only check imported assets foreach (var path in importedAssets) { // Load the asset from the path var prefab = AssetDatabase.LoadMainAssetAtPath(path); if (prefab == null) { continue; } // Make sure this is a prefab if (PrefabUtility.GetPrefabInstanceStatus(prefab) != PrefabInstanceStatus.Connected) { return; } // Get the type of asset var assetType = PrefabUtility.GetPrefabAssetType(prefab); // If it's not a model, skip if (assetType != PrefabAssetType.Model) { continue; } #if UNITY_VECTOR_GRAPHICS // Skip SVG files if (AssetImporter.GetAtPath(path) is SVGImporter) { return; } #endif #if ODIN_INSPECTOR if (!ModelPostProcessorConfig.Instance.CreatePrefabVariantsForModels) { continue; } #endif var prefabPath = Path.ChangeExtension(path, ".prefab"); if (File.Exists(Path.GetFullPath(prefabPath))) { continue; } // Create a prefab variant var instanceRoot = (GameObject)PrefabUtility.InstantiatePrefab(prefab); if (instanceRoot == null) { Debug.LogError("Failed to instantiate prefab"); continue; } // Save prefab variant next to model PrefabUtility.SaveAsPrefabAsset(instanceRoot, prefabPath); if (Application.isPlaying) { Object.Destroy(instanceRoot); } else { Object.DestroyImmediate(instanceRoot); } } }
public static void CreatePackage(bool isCreateBundle = true) { List <string> NoBundlesFiles = new List <string>(); string path = SceneManager.STREAMINGPATH.Replace("file://", "") + ResConfig.FDESASSETBUNDLE; //正式路径 string tempPath = FEPath.GetDirectoryName(SceneManager.STREAMINGPATH.Replace("file://", "")).Replace("Assets/StreamingAssets", "FPartPack/") + ResConfig.FDESASSETBUNDLE; //打包缓存路径 //删除上次数据 if (FEPath.Exists(path)) { MyEdior.DeletFile(path); } if (File.Exists(path + ResConfig.FZIPNAMEEX)) { File.Delete(path + ResConfig.FZIPNAMEEX); } AssetDatabase.Refresh(); string onlyKey = "[" + PackType.only + "]"; SelectPrefabEditor spe = new SelectPrefabEditor(".", "/" + ResConfig.ASSETBUNDLE + "/", "", true); EditorDay day = new EditorDay(); day.SaveFile(); bool IsSpeedPack = day.IsSpeedPack; //连续打包,不用清空,快速打包模式 day.IsSpeedPack = true; day.SaveFile(); if (!IsSpeedPack) { if (isCreateBundle) { IsSpeedPack = !EditorUtility.DisplayDialog("打包提示", "是否强制清空缓存打包?\n(提示:差异包不建议清空,可能产生Md5码的变化)", "清空", "不清空"); } } if (isCreateBundle && !IsSpeedPack) { if (!ClearAssetBundleName()) { Debug.LogError("强制终止打包"); EditorUtility.ClearProgressBar(); return; } } if (!IsSpeedPack) { if (FEPath.Exists(tempPath)) { MyEdior.DeletFile(tempPath); } } EditorUtility.ClearProgressBar(); FEPath.CreateDirectory(path); FEPath.CreateDirectory(tempPath); BundleManager.BundleConfig bundleConfig = new BundleManager.BundleConfig(); Dictionary <string, Dictionary <string, BundleManager.BundleConfig.BundleFileData> > mBundleFileDatas = new Dictionary <string, Dictionary <string, BundleManager.BundleConfig.BundleFileData> >(); Dictionary <string, int> mBundleEncrypts = new Dictionary <string, int>(); List <EditorScripts.NoPackAsset.PackData> packData = new List <EditorScripts.NoPackAsset.PackData>(); List <AssetImporter> Importers = new List <AssetImporter>(); var pmode = Enum.GetValues(typeof(FPackageEditor.PackType)); Dictionary <string, int> PackTypeDic = new Dictionary <string, int>(); foreach (var fp in pmode) { FPackageEditor.PackType tempType = (FPackageEditor.PackType)fp; PackTypeDic[tempType.ToString()] = (int)tempType; } ScriptsTime.Begin(); //先处理文件夹一下得到打包需要的数据 Dictionary <string, int> HeadPath = new Dictionary <string, int>(); Dictionary <string, ProPathHandle> datas = new Dictionary <string, ProPathHandle>(); Dictionary <string, int> allMushResouress = new Dictionary <string, int>();//所有引用的资源 List <PackFileData> packFiles = new List <PackFileData>(); Dictionary <string, string> WarningFile = new Dictionary <string, string>(); for (int i = 0; i < spe.tempAllStrs.Length; i++) { PackFileData pfd = new PackFileData(); packFiles.Add(pfd); string realName = spe.tempAllStrs[i]; pfd.realFileName = realName; string pathFile = FEPath.GetDirectoryName(realName); ProPathHandle ProHandle = null; if (!datas.TryGetValue(pathFile, out ProHandle)) { ProHandle = new ProPathHandle(); datas[pathFile] = ProHandle; ProHandle.path = pathFile; int headPos = pathFile.IndexOf("/" + ResConfig.ASSETBUNDLE + "/"); string otherFilePath = ""; if (headPos == -1) { //纯路经 otherFilePath = pathFile + "/"; } else { otherFilePath = pathFile.Substring(0, headPos + 1); } string[] tempHeadPaths = otherFilePath.Split('/'); string tString = ""; for (int t = 0; t < tempHeadPaths.Length - 1; t++) { HeadPath[tString + tempHeadPaths[t]] = 1; tString += (tempHeadPaths[t] + "/"); } HeadPath[tString + ResConfig.ASSETBUNDLE] = 0; //文件夹打包类型获取 int packType = 0; if (headPos != -1) { string validPath = pathFile.Substring(headPos + ResConfig.ASSETBUNDLE.Length + 2); var keyEncrypt = FUniversalFunction.GetChunk(validPath, "[", "]"); ProHandle.realPath = keyEncrypt[0].ToLower(); if (ProHandle.realPath != "") { if (WarningFile.ContainsKey(ProHandle.realPath)) { Debug.Log("<color=#660000>存在相同的相对路径打包文件</color>:" + WarningFile[ProHandle.realPath] + "<color=#660000>****</color>" + pathFile); } WarningFile[ProHandle.realPath] = pathFile; } string[] proPaths = validPath.Split('/'); string startFile = pathFile.Substring(0, headPos + ResConfig.ASSETBUNDLE.Length + 1); for (int p = 0; p < proPaths.Length; p++) { startFile = startFile + "/" + proPaths[p]; var parms = PackFileEditor.PackFileConfig.GetPackType(startFile); if (parms != null) { packType |= parms.type; } } for (int p = 1; p < keyEncrypt.Count; p++) { packType |= PackTypeDic[keyEncrypt[p]]; } } ProHandle.packType = packType; } int lastIndex = realName.LastIndexOf("/"); string fileName = realName.Substring(lastIndex + 1).ToLower(); pfd.budleName = string.IsNullOrEmpty(ProHandle.realPath) ? fileName : (ProHandle.realPath + "/" + fileName); pfd.ProHandle = ProHandle; if (!PackFileEditor.IsHaveSameWinType(ProHandle.packType, (int)PackType.only)) { string[] paths = AssetDatabase.GetDependencies(realName); for (int p = 0; p < paths.Length; p++) { allMushResouress[paths[p]] = 1; } } } int AssetsNum = "Assets".Length + 1; for (int i = 0; i < packFiles.Count; i++) { PackFileData pf = packFiles[i]; ProPathHandle pHandle = pf.ProHandle; string spePath = pf.realFileName; string pathName = pHandle.path; if (EditorUtility.DisplayCancelableProgressBar("打包数据资源", "转换进度: " + spePath, (float)i / spe.tempAllStrs.Length)) { EditorUtility.ClearProgressBar(); return; } EditorScripts.NoPackAsset.PackData enp = new EditorScripts.NoPackAsset.PackData(); enp.allName = spePath; AssetImporter ai = AssetImporter.GetAtPath(spePath); int packType = pf.ProHandle.packType;//PackFileEditor.IsHaveSameWinType(ProHandle.packType, (int)PackType.only) if (ai != null) { Importers.Add(ai); string houPro = ""; string budleName = pf.budleName; string encryptFile = budleName; //需要智能排除 if (PackFileEditor.IsHaveSameWinType(packType, (int)PackType.only)) { if (!allMushResouress.ContainsKey(spePath)) { ai.assetBundleName = ""; continue; } } else { packData.Add(enp); } bool isNoBundle = PackFileEditor.IsHaveSameWinType(packType, (int)PackType.nb); int headPos = budleName.LastIndexOf("."); string typeName = BundleManager.PrefabType; if (headPos != -1) { string hou = budleName.Substring(headPos); if (hou != "" && BundleManager.AssetType.IndexOf(hou) != -1) { houPro = hou; } budleName = budleName.Substring(0, headPos); typeName = hou.ToLower(); } string pathFile = ""; headPos = budleName.LastIndexOf("/"); if (headPos != -1) { pathFile += (budleName.Substring(0, headPos)); } Dictionary <string, BundleManager.BundleConfig.BundleFileData> bmbfds = new Dictionary <string, BundleManager.BundleConfig.BundleFileData>(); mBundleEncrypts[pathFile] = packType; if (mBundleFileDatas.ContainsKey(pathFile)) { bmbfds = mBundleFileDatas[pathFile]; } else { if (!isNoBundle) { mBundleFileDatas[pathFile] = bmbfds; } } enp.key = (budleName + houPro).ToLower(); string assetbundleName = budleName + ResConfig.ASSETBUNDLESUFFIXES; //路径打包规则 if (pathFile != "") { string txtName = pathFile.ToLower(); int filePos = pathFile.LastIndexOf("/"); if (filePos != -1) { txtName = txtName.Substring(filePos + 1); } if (!PackFileEditor.IsHaveSameWinType(packType, (int)PackType.part)) { assetbundleName = pathFile + "/" + txtName + ResConfig.ASSETBUNDLESUFFIXES; } } enp.type = packType; if (isNoBundle) { string CopyBunld = encryptFile; string copyPath = tempPath + "/" + encryptFile;//修改 string dir = FEPath.GetDirectoryName(copyPath); if (isCreateBundle) { if (!FEPath.Exists(dir)) { FEPath.CreateDirectory(dir); } if (File.Exists(copyPath)) { File.Copy(spePath, copyPath, true); } else { File.Copy(spePath, copyPath); } NoBundlesFiles.Add(copyPath); } enp.key = CopyBunld.ToLower(); enp.bunldName = enp.key; } else { ai.assetBundleName = assetbundleName.ToLower(); enp.bunldName = ai.assetBundleName; //特殊处理 if (ai is TextureImporter) { TextureImporter ti = ai as TextureImporter; if (ti.textureType == TextureImporterType.Sprite) { typeName = BundleManager.SpriteType; } else { typeName = BundleManager.TextureType; } string tagName = ai.assetBundleName.Replace(ResConfig.ASSETBUNDLESUFFIXES, ".PackTag"); if (PackFileEditor.IsHaveSameWinType(packType, (int)PackType.part)) { tagName = ""; } if (tagName != ti.spritePackingTag) { ti.spritePackingTag = tagName; ti.SaveAndReimport(); } } BundleManager.BundleConfig.BundleFileData fd = new BundleManager.BundleConfig.BundleFileData(); fd.bundleFile = assetbundleName.ToLower(); fd.resFileName = (budleName.Replace(pathFile + "/", "") + houPro).ToLower(); fd.resType = typeName; fd.mIsCache = PackFileEditor.IsHaveSameWinType(packType, (int)PackType.cache); bmbfds[fd.resFileName] = fd; } } } ScriptsTime.Debug("打包资源完成"); //创建免打包配置 EditorScripts.CreateNoPackAsset(packData); //创建文件夹外观表现 PackFileEditor.PackFileConfig.SetHeadFile(HeadPath); ScriptsTime.ShowTime("计算打包配置文件"); if (isCreateBundle) { foreach (var ke in mBundleFileDatas) { var encrypts = mBundleEncrypts[ke.Key]; BundleManager.BundleConfig.PathBundles bbf = new BundleManager.BundleConfig.PathBundles(); bbf.path = ke.Key; bbf.fileBundles = ke.Value; bbf.mIsAsync = PackFileEditor.IsHaveSameWinType(encrypts, (int)PackType.asy); bbf.mIsOnly = !PackFileEditor.IsHaveSameWinType(encrypts, (int)PackType.part); bundleConfig.pathBundles[ke.Key] = bbf; } //按时间设置更新版本 bundleConfig.versionId = MyEdior.GetTimeVersion(); PlayerPrefs.SetInt("versionId", bundleConfig.versionId);//记录版本号 FSaveHandle sd = FSaveHandle.Create(tempPath + "/" + ResConfig.ASSETBUNDLECONFIFILE, FFilePath.FP_Abs, FOpenType.OT_Write); sd.PushObject(bundleConfig); sd.Save(); if (IsSpeedPack) { BuildPipeline.BuildAssetBundles(tempPath, BuildAssetBundleOptions.ChunkBasedCompression, EditorUserBuildSettings.activeBuildTarget); } else { BuildPipeline.BuildAssetBundles(tempPath, BuildAssetBundleOptions.ForceRebuildAssetBundle | BuildAssetBundleOptions.ChunkBasedCompression, EditorUserBuildSettings.activeBuildTarget); } } //拷贝 MyEdior.CopyDirectory(tempPath, path); EditorUtility.ClearProgressBar(); AssetDatabase.Refresh(); CreateStreamingConfig(); //清空配置文件 if (NoBundlesFiles.Count != 0) { for (int i = 0; i < NoBundlesFiles.Count; i++) { File.Delete(NoBundlesFiles[i]); Debug.Log("清空了其他未知文件:" + NoBundlesFiles[i]); } NoBundlesFiles.Clear(); } }
public static T GetAssetImporter <T>(string path) where T : AssetImporter { return(AssetImporter.GetAtPath(path) as T); }
/// <summary> /// 分析资源 /// </summary> /// <param name="paths"></param> /// <param name="target"></param> /// <param name="outpath"></param> private static void AnalyzeResource(string[] paths, BuildTarget target, string outpath) { additionBuildPackageCache = new List <string>(); curManifestConfig = new ManifestConfig(); //加载 ManifestConfig lastManifestConfig = null; if (File.Exists(configPath)) { lastManifestConfig = new ManifestConfig(File.ReadAllText(configPath)); } else { lastManifestConfig = new ManifestConfig(); } // if (File.Exists(cachePath)) { AssetCache = new ManifestConfig(File.ReadAllText(cachePath)); } else { AssetCache = new ManifestConfig(); } /***************************************开始分析资源****************************************/ List <string> changeList = new List <string>(); float curIndex = 0; var allAssetList = paths.ToList(); for (int index = 0; index < allAssetList.Count; index++) { var path = allAssetList[index]; var _path = path.Replace("\\", "/"); EditorUtility.DisplayProgressBar( "分析资源 -" + target, "分析:" + Path.GetFileNameWithoutExtension(_path) + " 进度:" + curIndex + "/" + paths.Length, curIndex / paths.Length); curIndex++; //获取被依赖的路径 var dependsource = "Assets" + _path.Replace(Application.dataPath, ""); var allDependObjectPaths = AssetDatabase.GetDependencies(dependsource).ToList(); dependsource = dependsource.ToLower(); GetCanBuildAssets(ref allDependObjectPaths); //处理依赖资源打包 for (int i = 0; i < allDependObjectPaths.Count; i++) { var dp = allDependObjectPaths[i]; var dependObjPath = Application.dataPath + dp.TrimStart("Assets".ToCharArray()); var uiid = GetMD5HashFromFile(dependObjPath); //判断是否打包 ManifestItem lastItem = null; AssetCache.Manifest.TryGetValue(dp, out lastItem); //已经添加,不用打包 if (lastItem != null && lastItem.UIID == uiid) { //不用打包记录缓存 var _last = lastManifestConfig.Manifest.Values.ToList().Find((item) => item.UIID == lastItem.UIID); curManifestConfig.AddDepend(_last.Name, _last.UIID, _last.Dependencies, _last.PackageName); continue; } changeList.Add(dependsource); // AssetCache.AddDepend(dp, uiid, new List <string>()); //开始设置abname 用以打包 AssetImporter ai = AssetImporter.GetAtPath(dp); string abname = "Assets" + dependObjPath.Replace(Application.dataPath, ""); //判断是否要打在同一个ab包内 string packageName = null; var list = new List <string>(); //嵌套引用prefab if (dp.ToLower() != dependsource && Path.GetExtension(dp).ToLower().Equals(".prefab")) { list = AssetDatabase.GetDependencies(abname).ToList(); GetCanBuildAssets(ref list); //转换成全小写 for (int j = 0; j < list.Count; j++) { list[j] = list[j].ToLower(); } } abname = abname.ToLower(); if (IsMakePackage(abname, ref packageName)) { //增量打包时,如果遇到多包合一时,其中某个变动,剩余的也要一次性打出 if (!additionBuildPackageCache.Contains(packageName)) { var lowPackgeName = packageName.ToLower(); var oldAsset = lastManifestConfig.Manifest.Values.ToList().FindAll((item) => item.PackageName == lowPackgeName); foreach (var oa in oldAsset) { AssetImporter _ai = AssetImporter.GetAtPath(oa.Name); if (_ai == null) { Debug.LogError("资源不存在:" + oa.Name); continue; } _ai.assetBundleName = packageName; _ai.assetBundleVariant = ""; } Debug.LogFormat("<color=yellow>重新打包:{0} , 依赖:{1}</color>", packageName, oldAsset.Count); additionBuildPackageCache.Add(packageName); } // ai.assetBundleName = packageName; ai.assetBundleVariant = ""; //被依赖的文件,不保存其依赖信息 if (abname != dependsource) { curManifestConfig.AddDepend(abname, uiid, list, packageName.ToLower()); } } else { ai.assetBundleName = abname; ai.assetBundleVariant = ""; //被依赖的文件,不保存其依赖信息 if (abname != dependsource) //依赖列表中会包含自己 { curManifestConfig.AddDepend(abname, uiid, list); } } } //保存主文件的依赖 { //获取MD5的UIID var UIID = GetMD5HashFromFile(_path); allDependObjectPaths.Remove(dependsource); for (int i = 0; i < allDependObjectPaths.Count; i++) { allDependObjectPaths[i] = allDependObjectPaths[i].ToLower(); } // string packageName = null; if (IsMakePackage(dependsource, ref packageName)) { //单ab包-多资源模式 curManifestConfig.AddDepend(dependsource, UIID, allDependObjectPaths, packageName.ToLower()); } else { //单ab包-单资源模式 curManifestConfig.AddDepend(dependsource, UIID, allDependObjectPaths); } } } EditorUtility.ClearProgressBar(); Debug.Log("本地需要打包资源:" + changeList.Count); if (changeList.Count < 100) { Debug.Log("本地需要打包资源:" + JsonMapper.ToJson(changeList)); } }
/// <summary> /// 设置assetbundleName /// </summary> /// <param name="s"></param> public static void SetAssetBundleName(Object s, bool replace = false, bool variant = false, string variantName = null) { string abPath = AssetDatabase.GetAssetPath(s); AssetImporter import = AssetImporter.GetAtPath(abPath); string folder = EditorUtils.GetLabelsByPath(abPath); string objName = s.name.ToLower(); if (replace) { objName = HugulaEditorSetting.instance.GetAssetBundleNameByReplaceIgnore(objName); // Debug.LogFormat ("{0} replace {1}", s.name, objName); } bool isScene = abPath.EndsWith(".unity"); string name = CUtils.GetRightFileName(objName); var suffix = Common.CHECK_ASSETBUNDLE_SUFFIX; // if (variant) // variant // { // suffix = ""; // } if (string.IsNullOrEmpty(folder)) { import.assetBundleName = name + suffix; } else { import.assetBundleName = string.Format("{0}/{1}{2}", folder, name, suffix); } if (variant) { string m_variant; if (abPath.IndexOf("_high") == 0) { m_variant = "high"; } else if (abPath.IndexOf("_medium") == 0) { m_variant = "medium"; } else if (abPath.IndexOf("_low") == 0) { m_variant = "low"; } else { DirectoryInfo filePath = new DirectoryInfo(abPath); m_variant = variantName != null ? variantName : filePath.Parent.Name.ToLower(); } import.assetBundleVariant = m_variant; HugulaSetting.instance.AddVariant(m_variant); if (m_variant.Equals(Common.ASSETBUNDLE_SUFFIX)) { Debug.LogWarningFormat("{0} variant folder name Equals {1}", abPath, Common.ASSETBUNDLE_SUFFIX); } if (m_variant == Common.DOT_BYTES.Replace(".", "")) { Debug.LogWarningFormat("{0} variant folder name Equals {1}", abPath, Common.DOT_BYTES); } } if (s.name.Contains(" ")) { Debug.LogWarning(s.name + " contains space"); } Debug.Log(import.assetBundleName + ",variant=" + import.assetBundleVariant); // if (s is GameObject) // { // GameObject tar = s as GameObject; // if (tar.transform.parent == null) // { // ReferenceCount refe = LuaHelper.AddComponent(tar, typeof(ReferenceCount)) as ReferenceCount; // if (refe != null) // { // if (string.IsNullOrEmpty(import.assetBundleVariant)) // refe.assetbundle = import.assetBundleName; // else // refe.assetbundle = import.assetBundleName + "." + import.assetBundleVariant; // EditorUtility.SetDirty(s); // } // } // } // else if (isScene) //如果是场景需要添加引用计数脚本 // { //UnityEngine.SceneAsset // var sce = s; // as SceneAsset; // Debug.Log(sce); // AssetDatabase.OpenAsset(sce); // GameObject gobj = GameObject.Find(sce.name); // if (gobj == null) gobj = new GameObject(sce.name); // ReferenceCount refe = LuaHelper.AddComponent(gobj, typeof(ReferenceCount)) as ReferenceCount; // if (refe != null) // { // if (string.IsNullOrEmpty(import.assetBundleVariant)) // refe.assetbundle = import.assetBundleName; // else // refe.assetbundle = import.assetBundleName + "." + import.assetBundleVariant; // EditorUtility.SetDirty(sce); // } // var refers = GameObject.FindObjectsOfType<ReferenceCount>(); // foreach (var rf in refers) // { // if (rf != refe) // { // Debug.LogWarningFormat("you should not add ReferenceCount in {0}", EditorUtils.GetGameObjectPathInScene(rf.transform, string.Empty)); // } // } // } }
public void Convert(Texture2D temp2DTex) { if (temp2DTex) { int dim = temp2DTex.width * temp2DTex.height; dim = temp2DTex.height; if (!ValidDimensions(temp2DTex)) { Debug.LogWarning("The given 2D texture " + temp2DTex.name + " cannot be used as a 3D LUT."); return; } // if (temp2DTex.GetPixel(5, 5) == null) { Debug.Log("bug"); return; } #if UNITY_EDITOR if (Application.isPlaying != true) { string path = AssetDatabase.GetAssetPath(LutTexture); MemoPath = path; TextureImporter textureImporter = AssetImporter.GetAtPath(path) as TextureImporter; if (!textureImporter.isReadable) { /* * bool doImport = textureImporter.isReadable == false; * if (textureImporter.mipmapEnabled == true) * { * doImport = true; * } * if (textureImporter.textureCompression != TextureImporterCompression.Uncompressed) * { * doImport = true; * }*/ textureImporter.isReadable = true; textureImporter.mipmapEnabled = false; textureImporter.textureCompression = TextureImporterCompression.Uncompressed; AssetDatabase.ImportAsset(path, ImportAssetOptions.ForceUpdate); } } #endif var c = temp2DTex.GetPixels(); var newC = new Color[c.Length]; for (int i = 0; i < dim; i++) { for (int j = 0; j < dim; j++) { for (int k = 0; k < dim; k++) { int j_ = dim - j - 1; newC[i + (j * dim) + (k * dim * dim)] = c[k * dim + i + j_ * dim * dim]; } } } if (converted3DLut) { DestroyImmediate(converted3DLut); } converted3DLut = new Texture3D(dim, dim, dim, TextureFormat.ARGB32, false); converted3DLut.SetPixels(newC); converted3DLut.Apply(); } else { SetIdentityLut(); } }
private static void createCilp(string objName, string objPath, string eventPath, List <animClip> clips) { string path = objPath + ".FBX"; var modelImporter = AssetImporter.GetAtPath(path) as ModelImporter; if (modelImporter == null) { return; } string savePath = getAnimPathByName(objName, "clip"); //帧事件信息 Dictionary <string, animEventTotal> events = new Dictionary <string, animEventTotal>(); getEvent(eventPath, ref events); modelImporter.animationType = ModelImporterAnimationType.Generic; modelImporter.importAnimation = true; modelImporter.generateAnimations = ModelImporterGenerateAnimations.GenerateAnimations; ModelImporterClipAnimation[] animations = new ModelImporterClipAnimation[clips.Count]; for (int i = 0; i < clips.Count; i++) { ModelImporterClipAnimation tempClip = new ModelImporterClipAnimation(); tempClip.name = clips[i].clipName; tempClip.firstFrame = clips[i].startIndex; tempClip.lastFrame = clips[i].endIndex; tempClip.loopTime = clips[i].isLoop; tempClip.wrapMode = clips[i].isLoop ? WrapMode.Loop : WrapMode.Default; tempClip.loopPose = true; if (events.ContainsKey(tempClip.name)) { animEventTotal total = events[tempClip.name]; AnimationEvent[] clipEvents = new AnimationEvent[total.eventLst.Count]; for (int k = 0; k < total.eventLst.Count; k++) { AnimationEvent ae = new AnimationEvent(); ae.functionName = total.eventLst[k].eventName; ae.stringParameter = total.eventLst[k].args; ae.time = total.eventLst[k].frame; clipEvents[k] = ae; } tempClip.events = clipEvents; } animations[i] = tempClip; } modelImporter.clipAnimations = animations; UnityEngine.Object[] objs = AssetDatabase.LoadAllAssetsAtPath(path); for (int i = 0; i < objs.Length; i++) { if (objs[i] is AnimationClip && !objs[i].name.StartsWith("_")) { AnimationClip old = objs[i] as AnimationClip; AnimationClip newClip = new AnimationClip(); EditorUtility.CopySerialized(old, newClip); AssetDatabase.CreateAsset(newClip, Path.Combine(savePath, newClip.name + ".anim")); } } AssetDatabase.ImportAsset(modelImporter.assetPath); AssetDatabase.Refresh(); }
// ** building maps ** void buildMaps(int textureWidth, int textureHeight, string baseFile) { float progress = 0.0f; float progressStep = 1.0f / textureHeight; bool setReadable = false; // check if its readable, if not set it temporarily readable string path = AssetDatabase.GetAssetPath(sourceImage); TextureImporter textureImporter = AssetImporter.GetAtPath(path) as TextureImporter; if (textureImporter.isReadable == false) { textureImporter.isReadable = true; AssetDatabase.ImportAsset(path, ImportAssetOptions.ForceUpdate); setReadable = true; } Texture2D texSource = new Texture2D(textureWidth, textureHeight, TextureFormat.RGB24, false, false); // clone original texture Color[] temp = sourceImage.GetPixels(); texSource.SetPixels(temp); if (specularGroupEnabled) { Texture2D texSpecular = new Texture2D(textureWidth, textureHeight, TextureFormat.RGB24, false, false); Color[] pixels = new Color[textureWidth * textureHeight]; for (int y = 0; y < textureHeight; y++) { for (int x = 0; x < textureWidth; x++) { float bw = sourceImage.GetPixel(x, y).grayscale; // adjust contrast bw *= bw * specularContrast; bw = bw < (specularContrast * specularCutOff)?-1:bw; bw = Mathf.Clamp(bw, -1, 1); bw *= 0.5f; bw += 0.5f; Color c = new Color(bw, bw, bw, 1); pixels[x + y * textureWidth] = c; } // progress bar progress += progressStep; if (EditorUtility.DisplayCancelableProgressBar(appName, "Creating specular map..", progress)) { Debug.Log(appName + ": Specular map creation cancelled by user (strange texture results will occur)"); EditorUtility.ClearProgressBar(); break; } } EditorUtility.ClearProgressBar(); // apply texture texSpecular.SetPixels(pixels); // save texture as png byte[] bytes3 = texSpecular.EncodeToPNG(); File.WriteAllBytes(Path.GetDirectoryName(path) + "/" + baseFile + specularSuffix, bytes3); // cleanup texture UnityEngine.Object.DestroyImmediate(texSpecular); } if (normalGroupEnabled) { progress = 0; if (medianFilterStrength >= 2) // must be atleast 2 for median filter { texSource.SetPixels(filtersMedian(sourceImage, medianFilterStrength)); } Color[] pixels = new Color[textureWidth * textureHeight]; // sobel filter Texture2D texNormal = new Texture2D(textureWidth, textureHeight, TextureFormat.RGB24, false, false); Vector3 vScale = new Vector3(0.3333f, 0.3333f, 0.3333f); for (int y = 0; y < textureHeight; y++) { for (int x = 0; x < textureWidth; x++) { Color tc = texSource.GetPixel(x - 1, y - 1); Vector3 cSampleNegXNegY = new Vector3(tc.r, tc.g, tc.g); tc = texSource.GetPixel(x, y - 1); Vector3 cSampleZerXNegY = new Vector3(tc.r, tc.g, tc.g); tc = texSource.GetPixel(x + 1, y - 1); Vector3 cSamplePosXNegY = new Vector3(tc.r, tc.g, tc.g); tc = texSource.GetPixel(x - 1, y); Vector3 cSampleNegXZerY = new Vector3(tc.r, tc.g, tc.g); tc = texSource.GetPixel(x + 1, y); Vector3 cSamplePosXZerY = new Vector3(tc.r, tc.g, tc.g); tc = texSource.GetPixel(x - 1, y + 1); Vector3 cSampleNegXPosY = new Vector3(tc.r, tc.g, tc.g); tc = texSource.GetPixel(x, y + 1); Vector3 cSampleZerXPosY = new Vector3(tc.r, tc.g, tc.g); tc = texSource.GetPixel(x + 1, y + 1); Vector3 cSamplePosXPosY = new Vector3(tc.r, tc.g, tc.g); float fSampleNegXNegY = Vector3.Dot(cSampleNegXNegY, vScale); float fSampleZerXNegY = Vector3.Dot(cSampleZerXNegY, vScale); float fSamplePosXNegY = Vector3.Dot(cSamplePosXNegY, vScale); float fSampleNegXZerY = Vector3.Dot(cSampleNegXZerY, vScale); float fSamplePosXZerY = Vector3.Dot(cSamplePosXZerY, vScale); float fSampleNegXPosY = Vector3.Dot(cSampleNegXPosY, vScale); float fSampleZerXPosY = Vector3.Dot(cSampleZerXPosY, vScale); float fSamplePosXPosY = Vector3.Dot(cSamplePosXPosY, vScale); float edgeX = (fSampleNegXNegY - fSamplePosXNegY) * 0.25f + (fSampleNegXZerY - fSamplePosXZerY) * 0.5f + (fSampleNegXPosY - fSamplePosXPosY) * 0.25f; float edgeY = (fSampleNegXNegY - fSampleNegXPosY) * 0.25f + (fSampleZerXNegY - fSampleZerXPosY) * 0.5f + (fSamplePosXNegY - fSamplePosXPosY) * 0.25f; Vector2 vEdge = new Vector2(edgeX, edgeY) * normalStrength; Vector3 norm = new Vector3(vEdge.x, vEdge.y, 1.0f).normalized; Color c = new Color(norm.x * 0.5f + 0.5f, norm.y * 0.5f + 0.5f, norm.z * 0.5f + 0.5f, 1); pixels[x + y * textureWidth] = c; } // progress bar progress += progressStep; if (EditorUtility.DisplayCancelableProgressBar(appName, "Creating normal map..", progress)) { Debug.Log(appName + ": Normal map creation cancelled by user (strange texture results will occur)"); EditorUtility.ClearProgressBar(); break; } } // apply texture texNormal.SetPixels(pixels); // save texture as png byte[] bytes2 = texNormal.EncodeToPNG(); File.WriteAllBytes(Path.GetDirectoryName(path) + "/" + baseFile + normalSuffix, bytes2); // remove progressbar EditorUtility.ClearProgressBar(); // cleanup texture UnityEngine.Object.DestroyImmediate(texNormal); } // cleanup texture UnityEngine.Object.DestroyImmediate(texSource); // restore isReadable setting, if we had changed it if (setReadable) { textureImporter.isReadable = false; AssetDatabase.ImportAsset(path, ImportAssetOptions.ForceUpdate); setReadable = false; } AssetDatabase.Refresh(); } // buildMaps()
private static IEnumerator ImportCoroutine(Object psdFile, ImportUserData importSettings, List <int[]> layerIndices, bool doYield = false, Action <int, ImportLayerData> layerCallback = null, Action <List <Sprite> > completeCallback = null) { string filepath = GetPsdFilepath(psdFile); if (string.IsNullOrEmpty(filepath)) { if (completeCallback != null) { completeCallback(null); } yield break; } // No target directory set, use PSD file directory if (string.IsNullOrEmpty(importSettings.TargetDirectory)) { importSettings.TargetDirectory = filepath.Substring(0, filepath.LastIndexOf("/")); } // Get the texture importer for the PSD TextureImporter psdUnitySettings = (TextureImporter)AssetImporter.GetAtPath(filepath); TextureImporterSettings psdUnityImport = new TextureImporterSettings(); psdUnitySettings.ReadTextureSettings(psdUnityImport); int importCurrent = 0; List <Sprite> sprites = new List <Sprite>(); using (PsdDocument psd = PsdDocument.Create(filepath)) { foreach (int[] layerIdx in layerIndices) { ImportLayerData layerSettings = importSettings.GetLayerData(layerIdx); if (layerSettings == null) { continue; } if (layerCallback != null) { layerCallback(importCurrent, layerSettings); } var sprite = ImportLayer(psd, importSettings, layerSettings, psdUnityImport); sprites.Add(sprite); importCurrent++; if (doYield) { yield return(null); } } } if (completeCallback != null) { completeCallback(sprites); } }
public static void CreateAtlasAsset() { var selection = Selection.objects; string path = string.Empty; StringBuilder sb = new StringBuilder(); foreach (Object s in selection) { if (s is DefaultAsset && (path = AssetDatabase.GetAssetPath(s)) != null && Directory.Exists(path)) { // var import = AssetImporter.GetAtPath(path); var ragName = s.name.ToLower() + "_atlas.asset"; string atlas_path = Path.Combine(path, ragName); sb.Append("Crate atlas Asset :"); sb.Append(ragName); sb.Append("\r\n"); var allchildren = EditorUtils.getAllChildFiles(path, @"\.meta$|\.manifest$|\.DS_Store$|\.u$", null, false); int count = 0; List <int> names = new List <int>(); List <Sprite> allSprites = new List <Sprite>(); foreach (var f in allchildren) { count++; TextureImporter ti = AssetImporter.GetAtPath(f) as TextureImporter; if (ti != null) { Object[] objs = AssetDatabase.LoadAllAssetRepresentationsAtPath(f); foreach (var item in objs) { if (item is Sprite) { names.Add(LuaHelper.StringToHash(item.name)); allSprites.Add((Sprite)item); } } EditorUtility.DisplayProgressBar("Processing...", "生成中... (" + count + " / " + allchildren.Count + ")", count / allchildren.Count); } } EditorUtility.ClearProgressBar(); //生成或者替换资源 AtlasAsset atlas = AssetDatabase.LoadAssetAtPath <AtlasAsset>(atlas_path); if (atlas == null) { atlas = AtlasAsset.CreateInstance <AtlasAsset>(); AssetDatabase.CreateAsset(atlas, atlas_path); } atlas.names = names; atlas.sprites = allSprites; EditorUtility.SetDirty(atlas); var import = AssetImporter.GetAtPath(atlas_path); import.assetBundleName = Path.GetFileNameWithoutExtension(ragName) + Common.CHECK_ASSETBUNDLE_SUFFIX; sb.AppendFormat("build {0} success count = {1} ", ragName, names.Count); AssetDatabase.SaveAssets(); } } sb.AppendLine("\r\nall completed"); Debug.Log(sb.ToString()); }
public abstract bool DoesImporterMatchSettings(AssetImporter importer);
void AssignTexture(GameObject selectedObject, Material material, int matIndex, Texture2D texture, string texturePath, string textureExtension) { Color32[] pixelArray = null; bool rgbaSame = false; bool metalSame = false; bool smoothnessSame = false; Color32 rgbaColor; float metallicValue; float smoothnessValue; TextureImporter importer = AssetImporter.GetAtPath(texturePath) as TextureImporter; //Set the maximum texture size. importer.maxTextureSize = maxTextureSize; if (replaceRedundantTextures || processOpacity) { //Set the texture to readable to enable GetPixels. Note that the texture will consume much more memory //because of this. Set it to non-readable when done. importer.isReadable = true; //Apply the texture importer settings. AssetDatabase.WriteImportSettingsIfDirty(texturePath); UnityEditor.AssetDatabase.SaveAssets(); UnityEditor.AssetDatabase.Refresh(); //Convert the texture to an array of colors. pixelArray = texture.GetPixels32(); } switch (textureExtension) { case albedoExtension: if (replaceRedundantTextures == true) { IsRGBASame(out rgbaSame, out rgbaColor, pixelArray); if (rgbaSame) { //Remove texture. material.SetTexture(albedoTextureID, null); //Set a uniform color. material.SetColor(albedoColorID, rgbaColor); redundantTextureAmount++; } } if ((replaceRedundantTextures == false) || ((replaceRedundantTextures == true) && (rgbaSame == false))) { //Assign the texture material.SetTexture(albedoTextureID, texture); //This is important, otherwise the texture will look wrong if a texture is used). material.SetColor(albedoColorID, Color.white); assignedTextureAmount++; } if (processOpacity) { bool alphaPresent = IsAlphaPresent(pixelArray); if (alphaPresent) { SetTransparent(material); } else { SetOpaque(material); } } break; case metallicExtension: if (replaceRedundantTextures == true) { //The metallic texture contains both a metallic and smoothness value. IsMetallicSame(out metalSame, out metallicValue, pixelArray); IsSmoothnessSame(out smoothnessSame, out smoothnessValue, pixelArray); if (metalSame && smoothnessSame) { //Remove texture. material.SetTexture(metallicTextureID, null); //Set the metal HeightSlider. material.SetFloat(metallicSliderID, metallicValue); //Set the smoothness HeightSlider. material.SetFloat(smoothnessSliderID, smoothnessValue); material.DisableKeyword(metallicKeyword); redundantTextureAmount++; } } if ((replaceRedundantTextures == false) || ((replaceRedundantTextures == true) && !(metalSame && smoothnessSame))) { material.EnableKeyword(metallicKeyword); material.SetTexture(metallicTextureID, texture); assignedTextureAmount++; } break; case specularExtension: if (replaceRedundantTextures == true) { //The specular texture contains both a specular and smoothness value. IsRGBASame(out rgbaSame, out rgbaColor, pixelArray); IsSmoothnessSame(out smoothnessSame, out smoothnessValue, pixelArray); if (rgbaSame && smoothnessSame) { //Remove texture. material.SetTexture(specularTextureID, null); //Set the specular color. material.SetColor(specularColorID, rgbaColor); //Set the smoothness HeightSlider. material.SetFloat(smoothnessSliderID, smoothnessValue); material.DisableKeyword(specularKeyword); redundantTextureAmount++; } } if ((replaceRedundantTextures == false) || ((replaceRedundantTextures == true) && !(rgbaSame && smoothnessSame))) { material.EnableKeyword(specularKeyword); material.SetTexture(specularTextureID, texture); assignedTextureAmount++; } break; case normalExtension: if (replaceRedundantTextures == true) { IsRGBASame(out rgbaSame, out rgbaColor, pixelArray); if (rgbaSame) { //Remove texture. material.SetTexture(normalTextureID, null); material.DisableKeyword(normalKeyword); redundantTextureAmount++; } } if ((replaceRedundantTextures == false) || ((replaceRedundantTextures == true) && (rgbaSame == false))) { material.EnableKeyword(normalKeyword); //A normal map should be marked as a normal map. importer.textureType = TextureImporterType.NormalMap; AssetDatabase.WriteImportSettingsIfDirty(texturePath); material.SetTexture(normalTextureID, texture); assignedTextureAmount++; UnityEditor.AssetDatabase.SaveAssets(); UnityEditor.AssetDatabase.Refresh(); } break; case heightExtension: if (replaceRedundantTextures == true) { IsRGBASame(out rgbaSame, out rgbaColor, pixelArray); if (rgbaSame) { //Remove texture. material.SetTexture(heightTextureID, null); material.DisableKeyword(heightKeyword); redundantTextureAmount++; } } if ((replaceRedundantTextures == false) || ((replaceRedundantTextures == true) && (rgbaSame == false))) { material.EnableKeyword(heightKeyword); material.SetTexture(heightTextureID, texture); assignedTextureAmount++; } break; case occlusionExtension: if (replaceRedundantTextures == true) { IsRGBASame(out rgbaSame, out rgbaColor, pixelArray); if (rgbaSame) { //Remove texture. material.SetTexture(occlusionTextureID, null); redundantTextureAmount++; } } if ((replaceRedundantTextures == false) || ((replaceRedundantTextures == true) && (rgbaSame == false))) { material.SetTexture(occlusionTextureID, texture); assignedTextureAmount++; } break; case emissionExtension: if (replaceRedundantTextures == true) { IsRGBASame(out rgbaSame, out rgbaColor, pixelArray); if (rgbaSame) { //The emission shader keyword has to be enabled even if no texture is used, //otherwise the shader won't refresh. material.EnableKeyword(emissionKeyword); //Remove texture. material.SetTexture(emissionTextureID, null); material.SetColor(emissionColorID, rgbaColor); redundantTextureAmount++; } } if ((replaceRedundantTextures == false) || ((replaceRedundantTextures == true) && (rgbaSame == false))) { material.EnableKeyword(emissionKeyword); material.SetTexture(emissionTextureID, texture); assignedTextureAmount++; //This is important, otherwise the texture will look wrong if a texture is used). material.SetColor(emissionColorID, Color.white); } break; default: break; } selectedObject.GetComponent <Renderer>().sharedMaterials[matIndex] = material; if (replaceRedundantTextures || processOpacity) { //Set the texture to non-readable again, to free up memory. importer.isReadable = false; AssetDatabase.WriteImportSettingsIfDirty(texturePath); UnityEditor.AssetDatabase.SaveAssets(); UnityEditor.AssetDatabase.Refresh(); } }