private static TextureAtlasMapper CreateTextureAtlasMapper(Vector2[] unityUvs, Vector2[] unityUvs2, Vector2[] unityUvs3, double[] uvs, int[] uvMap) { const int infoEntrySize = 8; var count = uvMap == null ? 0 : uvMap.Length; List <TextureAtlasInfo> infos = new List <TextureAtlasInfo>(count / infoEntrySize); for (int i = 0; i < count;) { var info = new TextureAtlasInfo(); info.UvIndexRange = new Range <int>(!infos.Any() ? 0 : infos.Last().UvIndexRange.Maximum, uvMap[i++]); info.TextureIndex = uvMap[i++]; int atlasWidth = uvMap[i++]; int atlasHeight = uvMap[i++]; float x = uvMap[i++]; float y = uvMap[i++]; float width = uvMap[i++]; float height = uvMap[i++]; bool isEmpty = atlasWidth == 0 || atlasHeight == 0; info.TextureSize = new Vector2(isEmpty ? 0 : width / atlasWidth, isEmpty ? 0 : height / atlasHeight); info.TextureOffset = new Vector2(isEmpty ? 0 : x / atlasWidth, isEmpty ? 0 : y / atlasHeight); infos.Add(info); } return(new TextureAtlasMapper(unityUvs, unityUvs2, unityUvs3, uvs, infos)); }
public void Regenerate(TextureAtlasInfo tai) { this.m_src = tai.srcDirectory; var path = AssetDatabase.GetAssetPath(tai); this.m_dst = path.Substring(0, path.LastIndexOf('/')); PreparePaths(); ProcessAndSave(tai.atlas, tai, tai.material, false); }
public void RefreshDependentObjects(TextureAtlasInfo tai) { // Check sprites Sprite[] s = GameObject.FindObjectsOfTypeIncludingAssets(typeof(Sprite)) as Sprite[]; for(int i = 0; i < s.Length; i++) { if(s[i].atlas.Equals(tai)) { s[i].HandleStaticSpriteChange(); } } }
void ProcessAndSave(Texture2D atlas, TextureAtlasInfo tai, Material material, bool isNew) { LoadAssets(); Rect[] results = atlas.PackTextures(m_srcTextures.ToArray(), 0, 1024); atlas.Apply(); byte[] bytes = atlas.EncodeToPNG(); File.WriteAllBytes(m_outputFile, bytes); if(isNew) { AssetDatabase.ImportAsset(m_outputFile.Substring(m_outputFile.IndexOf("Assets"))); } else { EditorUtility.SetDirty(atlas); } var a = AssetDatabase.LoadAssetAtPath(m_outputFile.Substring(m_outputFile.IndexOf("Assets")), typeof(Texture2D)) as Texture2D; material.mainTexture = a; if(isNew) { AssetDatabase.CreateAsset(material, m_materialOutputFile); } else { EditorUtility.SetDirty(material); } AssetDatabase.ImportAsset(m_materialOutputFile); material = AssetDatabase.LoadAssetAtPath(m_materialOutputFile, typeof(Material)) as Material; tai.SetInitialData(m_src, m_files, results, a, material); if(isNew) { AssetDatabase.CreateAsset(tai, m_atlasInfoOutputFile); } else { EditorUtility.SetDirty(tai); } UnloadAssets(); }
void OnGUI() { m_scrollPosition = EditorGUILayout.BeginScrollView(m_scrollPosition); Rect verticalLayoutRect = EditorGUILayout.BeginVertical(); EditorGUILayout.LabelField("Select the parent object that is to be combined."); EditorGUI.BeginChangeCheck(); m_parentObject = (GameObject)EditorGUILayout.ObjectField("Parent Object Of Meshes To Be Combined", m_parentObject, typeof(GameObject), true); if(EditorGUI.EndChangeCheck()) { m_textureAtlasInfo = new TextureAtlasInfo(); m_texPropArraySize = m_textureAtlasInfo.shaderPropertiesToLookFor.Length; m_shaderFoldoutBools = new bool[m_texPropArraySize]; } if(m_parentObject != null) { m_textureAtlasInfo.compressTexturesInMemory = false;//EditorGUILayout.Toggle("Compress Texture", m_textureAtlasInfo.compressTexturesInMemory); EditorGUI.BeginChangeCheck(); m_texPropArraySize = EditorGUILayout.IntSlider("# Of Shader Properties", m_texPropArraySize, 0, 20); if(EditorGUI.EndChangeCheck()) { if(m_texPropArraySize > m_textureAtlasInfo.shaderPropertiesToLookFor.Length) { ShaderProperties[] temp = new ShaderProperties[m_texPropArraySize]; for(int i = 0; i < m_texPropArraySize; i++) { if(i < m_textureAtlasInfo.shaderPropertiesToLookFor.Length) { temp[i] = m_textureAtlasInfo.shaderPropertiesToLookFor[i]; } else { temp[i] = new ShaderProperties(false, ""); } } m_textureAtlasInfo.shaderPropertiesToLookFor = temp; } else if(m_texPropArraySize < m_textureAtlasInfo.shaderPropertiesToLookFor.Length) { ShaderProperties[] temp = new ShaderProperties[m_texPropArraySize]; for(int i = 0; i < m_texPropArraySize; i++) { temp[i] = m_textureAtlasInfo.shaderPropertiesToLookFor[i]; } m_textureAtlasInfo.shaderPropertiesToLookFor = temp; } m_shaderFoldoutBools = new bool[m_texPropArraySize]; } m_showShaderProperties = EditorGUILayout.Foldout(m_showShaderProperties, "Shader Properties To Watch For"); if(m_showShaderProperties) { for(int i = 0; i < m_texPropArraySize; i++) { m_shaderFoldoutBools[i] = EditorGUILayout.Foldout(m_shaderFoldoutBools[i], "Shader Properties Element " + i); if(m_shaderFoldoutBools[i] == true) { m_textureAtlasInfo.shaderPropertiesToLookFor[i].markAsNormal = EditorGUILayout.Toggle("Mark As Normal Map", m_textureAtlasInfo.shaderPropertiesToLookFor[i].markAsNormal); m_textureAtlasInfo.shaderPropertiesToLookFor[i].propertyName = EditorGUILayout.TextField("Shader Property Name", m_textureAtlasInfo.shaderPropertiesToLookFor[i].propertyName); } } } GUILayout.Space(m_window.position.height * 0.05f); EditorGUI.BeginChangeCheck(); m_folderPath = EditorGUILayout.TextField("Combined Asset Path", m_folderPath); if(EditorGUI.EndChangeCheck()) { m_pathToAssets = Application.dataPath + "/" + m_folderPath + "/"; } GUILayout.Space(m_window.position.height * 0.05f); m_showModelSettings = EditorGUILayout.Foldout(m_showModelSettings, "Model Settings"); if(m_showModelSettings == true) { GUILayout.Label("Meshes", "BoldLabel"); EditorGUILayout.LabelField("Meshes"); m_modelImportSettings.globalScale = EditorGUILayout.FloatField("Global Scale", m_modelImportSettings.globalScale); m_modelImportSettings.meshCompression = (ModelImporterMeshCompression)EditorGUILayout.EnumPopup("Mesh Compression", m_modelImportSettings.meshCompression); m_modelImportSettings.optimizeMesh = EditorGUILayout.Toggle("Optimize Mesh", m_modelImportSettings.optimizeMesh); m_modelImportSettings.addCollider = EditorGUILayout.Toggle("Generate Colliders", m_modelImportSettings.addCollider); m_modelImportSettings.swapUVChannels = EditorGUILayout.Toggle("Swap UVs", m_modelImportSettings.swapUVChannels); m_modelImportSettings.generateSecondaryUV = EditorGUILayout.Toggle("Generate Lightmap UVs", m_modelImportSettings.generateSecondaryUV); GUILayout.Label("Normals & Tangents", "BoldLabel"); m_modelImportSettings.normalImportMode = (ModelImporterTangentSpaceMode)EditorGUILayout.EnumPopup("Normals", m_modelImportSettings.normalImportMode); m_modelImportSettings.tangentImportMode = (ModelImporterTangentSpaceMode)EditorGUILayout.EnumPopup("Tangents", m_modelImportSettings.tangentImportMode); if((m_modelImportSettings.normalImportMode == ModelImporterTangentSpaceMode.Calculate) && !(m_modelImportSettings.tangentImportMode == ModelImporterTangentSpaceMode.None)) { m_modelImportSettings.tangentImportMode = ModelImporterTangentSpaceMode.Calculate; } EditorGUI.BeginDisabledGroup(!(m_modelImportSettings.normalImportMode == ModelImporterTangentSpaceMode.Calculate)); m_modelImportSettings.normalSmoothingAngle = EditorGUILayout.IntSlider("Normal Smoothing Angle", (int)m_modelImportSettings.normalSmoothingAngle, 0, 180); EditorGUI.EndDisabledGroup(); EditorGUI.BeginDisabledGroup(!(m_modelImportSettings.tangentImportMode == ModelImporterTangentSpaceMode.Calculate)); m_modelImportSettings.splitTangentsAcrossSeams = EditorGUILayout.Toggle("Split Tangents", m_modelImportSettings.splitTangentsAcrossSeams); EditorGUI.EndDisabledGroup(); } m_showTextureSettings = EditorGUILayout.Foldout(m_showTextureSettings, "Texture Settings"); if(m_showTextureSettings == true) { m_textureImportSettings.textureType = (TextureImporterType)EditorGUILayout.EnumPopup("", m_textureImportSettings.textureType); switch(m_textureImportSettings.textureType) { case TextureImporterType.Bump: //m_textureImportSettings.convertToNormalmap = EditorGUILayout.Toggle("", m_textureImportSettings.convertToNormalmap); m_textureImportSettings.heightmapScale = EditorGUILayout.Slider(m_textureImportSettings.heightmapScale, 0.0f, 0.3f); m_textureImportSettings.normalmapFilter = (TextureImporterNormalFilter)EditorGUILayout.EnumPopup("Normal Map Filter", m_textureImportSettings.normalmapFilter); m_textureImportSettings.wrapMode = (TextureWrapMode)EditorGUILayout.EnumPopup("Texture Wrap Mode", m_textureImportSettings.wrapMode); m_textureImportSettings.filterMode = (FilterMode)EditorGUILayout.EnumPopup("Texture Filter Mode", m_textureImportSettings.filterMode); m_textureImportSettings.anisoLevel = EditorGUILayout.IntSlider("Aniso Level", m_textureImportSettings.anisoLevel, 0, 10); break; case TextureImporterType.Lightmap: m_textureImportSettings.filterMode = (FilterMode)EditorGUILayout.EnumPopup("Texture Filter Mode", m_textureImportSettings.filterMode); m_textureImportSettings.anisoLevel = EditorGUILayout.IntSlider("Aniso Level", m_textureImportSettings.anisoLevel, 0, 10); break; case TextureImporterType.Reflection: m_textureImportSettings.grayscaleToAlpha = EditorGUILayout.Toggle("Alpha From Grayscale", m_textureImportSettings.grayscaleToAlpha); m_textureImportSettings.filterMode = (FilterMode)EditorGUILayout.EnumPopup("Texture Filter Mode", m_textureImportSettings.filterMode); m_textureImportSettings.anisoLevel = EditorGUILayout.IntSlider("Aniso Level", m_textureImportSettings.anisoLevel, 0, 10); break; case TextureImporterType.Image: default: m_textureImportSettings.textureType = TextureImporterType.Image; m_textureImportSettings.grayscaleToAlpha = EditorGUILayout.Toggle("Alpha From Grayscale", m_textureImportSettings.grayscaleToAlpha); m_textureImportSettings.wrapMode = (TextureWrapMode)EditorGUILayout.EnumPopup("Texture Wrap Mode", m_textureImportSettings.wrapMode); m_textureImportSettings.filterMode = (FilterMode)EditorGUILayout.EnumPopup("Texture Filter Mode", m_textureImportSettings.filterMode); m_textureImportSettings.anisoLevel = EditorGUILayout.IntSlider("Aniso Level", m_textureImportSettings.anisoLevel, 0, 10); break; } m_textureImportSettings.maxTextureSize = (int)(object)EditorGUILayout.EnumPopup((TextureSize)m_textureImportSettings.maxTextureSize); m_textureImportSettings.textureFormat = (TextureImporterFormat)EditorGUILayout.EnumPopup(m_textureImportSettings.textureFormat); /*mip map stuff*/ } EditorGUILayout.Toggle("Export Assets ", exportAssets); GUILayout.Space(m_window.position.height * 0.05f); EditorGUILayout.EndVertical(); EditorGUILayout.BeginHorizontal(); if(GUILayout.Button("Combine Mesh", GUILayout.Height(m_window.position.height * 0.1f))) { combineMesh(exportAssets); } EditorGUILayout.EndHorizontal(); } EditorGUILayout.EndScrollView(); }
void OnGUI() { m_scrollPosition = EditorGUILayout.BeginScrollView(m_scrollPosition); Rect verticalLayoutRect = EditorGUILayout.BeginVertical(); EditorGUILayout.LabelField("Select the parent object that is to be combined."); EditorGUI.BeginChangeCheck(); m_parentObject = (GameObject)EditorGUILayout.ObjectField("Parent Object Of Meshes To Be Combined", m_parentObject, typeof(GameObject), true); if (EditorGUI.EndChangeCheck()) { m_textureAtlasInfo = new TextureAtlasInfo(); m_texPropArraySize = m_textureAtlasInfo.shaderPropertiesToLookFor.Length; m_shaderFoldoutBools = new bool[m_texPropArraySize]; } if (m_parentObject != null) { m_textureAtlasInfo.compressTexturesInMemory = false; //EditorGUILayout.Toggle("Compress Texture", m_textureAtlasInfo.compressTexturesInMemory); EditorGUI.BeginChangeCheck(); m_texPropArraySize = EditorGUILayout.IntSlider("# Of Shader Properties", m_texPropArraySize, 0, 20); if (EditorGUI.EndChangeCheck()) { if (m_texPropArraySize > m_textureAtlasInfo.shaderPropertiesToLookFor.Length) { ShaderProperties[] temp = new ShaderProperties[m_texPropArraySize]; for (int i = 0; i < m_texPropArraySize; i++) { if (i < m_textureAtlasInfo.shaderPropertiesToLookFor.Length) { temp[i] = m_textureAtlasInfo.shaderPropertiesToLookFor[i]; } else { temp[i] = new ShaderProperties(false, ""); } } m_textureAtlasInfo.shaderPropertiesToLookFor = temp; } else if (m_texPropArraySize < m_textureAtlasInfo.shaderPropertiesToLookFor.Length) { ShaderProperties[] temp = new ShaderProperties[m_texPropArraySize]; for (int i = 0; i < m_texPropArraySize; i++) { temp[i] = m_textureAtlasInfo.shaderPropertiesToLookFor[i]; } m_textureAtlasInfo.shaderPropertiesToLookFor = temp; } m_shaderFoldoutBools = new bool[m_texPropArraySize]; } m_showShaderProperties = EditorGUILayout.Foldout(m_showShaderProperties, "Shader Properties To Watch For"); if (m_showShaderProperties) { for (int i = 0; i < m_texPropArraySize; i++) { m_shaderFoldoutBools[i] = EditorGUILayout.Foldout(m_shaderFoldoutBools[i], "Shader Properties Element " + i); if (m_shaderFoldoutBools[i] == true) { m_textureAtlasInfo.shaderPropertiesToLookFor[i].markAsNormal = EditorGUILayout.Toggle("Mark As Normal Map", m_textureAtlasInfo.shaderPropertiesToLookFor[i].markAsNormal); m_textureAtlasInfo.shaderPropertiesToLookFor[i].propertyName = EditorGUILayout.TextField("Shader Property Name", m_textureAtlasInfo.shaderPropertiesToLookFor[i].propertyName); } } } GUILayout.Space(m_window.position.height * 0.05f); EditorGUI.BeginChangeCheck(); m_folderPath = EditorGUILayout.TextField("Combined Asset Path", m_folderPath); if (EditorGUI.EndChangeCheck()) { m_pathToAssets = Application.dataPath + "/" + m_folderPath + "/"; } GUILayout.Space(m_window.position.height * 0.05f); m_showModelSettings = EditorGUILayout.Foldout(m_showModelSettings, "Model Settings"); if (m_showModelSettings == true) { GUILayout.Label("Meshes", "BoldLabel"); EditorGUILayout.LabelField("Meshes"); m_modelImportSettings.globalScale = EditorGUILayout.FloatField("Global Scale", m_modelImportSettings.globalScale); m_modelImportSettings.meshCompression = (ModelImporterMeshCompression)EditorGUILayout.EnumPopup("Mesh Compression", m_modelImportSettings.meshCompression); m_modelImportSettings.optimizeMesh = EditorGUILayout.Toggle("Optimize Mesh", m_modelImportSettings.optimizeMesh); m_modelImportSettings.addCollider = EditorGUILayout.Toggle("Generate Colliders", m_modelImportSettings.addCollider); m_modelImportSettings.swapUVChannels = EditorGUILayout.Toggle("Swap UVs", m_modelImportSettings.swapUVChannels); m_modelImportSettings.generateSecondaryUV = EditorGUILayout.Toggle("Generate Lightmap UVs", m_modelImportSettings.generateSecondaryUV); GUILayout.Label("Normals & Tangents", "BoldLabel"); m_modelImportSettings.normalImportMode = (ModelImporterTangentSpaceMode)EditorGUILayout.EnumPopup("Normals", m_modelImportSettings.normalImportMode); m_modelImportSettings.tangentImportMode = (ModelImporterTangentSpaceMode)EditorGUILayout.EnumPopup("Tangents", m_modelImportSettings.tangentImportMode); if ((m_modelImportSettings.normalImportMode == ModelImporterTangentSpaceMode.Calculate) && !(m_modelImportSettings.tangentImportMode == ModelImporterTangentSpaceMode.None)) { m_modelImportSettings.tangentImportMode = ModelImporterTangentSpaceMode.Calculate; } EditorGUI.BeginDisabledGroup(!(m_modelImportSettings.normalImportMode == ModelImporterTangentSpaceMode.Calculate)); m_modelImportSettings.normalSmoothingAngle = EditorGUILayout.IntSlider("Normal Smoothing Angle", (int)m_modelImportSettings.normalSmoothingAngle, 0, 180); EditorGUI.EndDisabledGroup(); EditorGUI.BeginDisabledGroup(!(m_modelImportSettings.tangentImportMode == ModelImporterTangentSpaceMode.Calculate)); m_modelImportSettings.splitTangentsAcrossSeams = EditorGUILayout.Toggle("Split Tangents", m_modelImportSettings.splitTangentsAcrossSeams); EditorGUI.EndDisabledGroup(); } m_showTextureSettings = EditorGUILayout.Foldout(m_showTextureSettings, "Texture Settings"); if (m_showTextureSettings == true) { m_textureImportSettings.textureType = (TextureImporterType)EditorGUILayout.EnumPopup("", m_textureImportSettings.textureType); switch (m_textureImportSettings.textureType) { case TextureImporterType.Bump: //m_textureImportSettings.convertToNormalmap = EditorGUILayout.Toggle("", m_textureImportSettings.convertToNormalmap); m_textureImportSettings.heightmapScale = EditorGUILayout.Slider(m_textureImportSettings.heightmapScale, 0.0f, 0.3f); m_textureImportSettings.normalmapFilter = (TextureImporterNormalFilter)EditorGUILayout.EnumPopup("Normal Map Filter", m_textureImportSettings.normalmapFilter); m_textureImportSettings.wrapMode = (TextureWrapMode)EditorGUILayout.EnumPopup("Texture Wrap Mode", m_textureImportSettings.wrapMode); m_textureImportSettings.filterMode = (FilterMode)EditorGUILayout.EnumPopup("Texture Filter Mode", m_textureImportSettings.filterMode); m_textureImportSettings.anisoLevel = EditorGUILayout.IntSlider("Aniso Level", m_textureImportSettings.anisoLevel, 0, 10); break; case TextureImporterType.Lightmap: m_textureImportSettings.filterMode = (FilterMode)EditorGUILayout.EnumPopup("Texture Filter Mode", m_textureImportSettings.filterMode); m_textureImportSettings.anisoLevel = EditorGUILayout.IntSlider("Aniso Level", m_textureImportSettings.anisoLevel, 0, 10); break; case TextureImporterType.Reflection: m_textureImportSettings.grayscaleToAlpha = EditorGUILayout.Toggle("Alpha From Grayscale", m_textureImportSettings.grayscaleToAlpha); m_textureImportSettings.filterMode = (FilterMode)EditorGUILayout.EnumPopup("Texture Filter Mode", m_textureImportSettings.filterMode); m_textureImportSettings.anisoLevel = EditorGUILayout.IntSlider("Aniso Level", m_textureImportSettings.anisoLevel, 0, 10); break; case TextureImporterType.Image: default: m_textureImportSettings.textureType = TextureImporterType.Image; m_textureImportSettings.grayscaleToAlpha = EditorGUILayout.Toggle("Alpha From Grayscale", m_textureImportSettings.grayscaleToAlpha); m_textureImportSettings.wrapMode = (TextureWrapMode)EditorGUILayout.EnumPopup("Texture Wrap Mode", m_textureImportSettings.wrapMode); m_textureImportSettings.filterMode = (FilterMode)EditorGUILayout.EnumPopup("Texture Filter Mode", m_textureImportSettings.filterMode); m_textureImportSettings.anisoLevel = EditorGUILayout.IntSlider("Aniso Level", m_textureImportSettings.anisoLevel, 0, 10); break; } m_textureImportSettings.maxTextureSize = (int)(object)EditorGUILayout.EnumPopup((TextureSize)m_textureImportSettings.maxTextureSize); m_textureImportSettings.textureFormat = (TextureImporterFormat)EditorGUILayout.EnumPopup(m_textureImportSettings.textureFormat); /*mip map stuff*/ } EditorGUILayout.Toggle("Export Assets ", exportAssets); GUILayout.Space(m_window.position.height * 0.05f); EditorGUILayout.EndVertical(); EditorGUILayout.BeginHorizontal(); if (GUILayout.Button("Combine Mesh", GUILayout.Height(m_window.position.height * 0.1f))) { combineMesh(exportAssets); } EditorGUILayout.EndHorizontal(); } EditorGUILayout.EndScrollView(); }
/** * This function returns two variables: -> The tecture atlas -> An array of the old textures and their new positions. (Used for UV modification) */ public static Material combine(Material[] combines, out TexturePosition[] texturePositions, TextureAtlasInfo atlasInfo) { if(atlasInfo == null) { Debug.LogError("atlasInfo is null. Try removing and reattaching combine children component"); texturePositions = null; return null; } if(atlasInfo.shaderPropertiesToLookFor.Length <= 0) { Debug.LogError("You need to enter some shader properties to look for into Atlas Info. Cannot combine with 0 properties"); texturePositions = null; return null; } List<ShaderProperties> properties = new List<ShaderProperties>(); for(int i = 0; i < atlasInfo.shaderPropertiesToLookFor.Length; i++) { if(combines[0].HasProperty(atlasInfo.shaderPropertiesToLookFor[i].propertyName) == true) { properties.Add(atlasInfo.shaderPropertiesToLookFor[i]); } } texturePositions = new TexturePosition[combines.Length]; for(int i = 0; i < combines.Length; i++) { TexturePosition tempTexturePosition = new TexturePosition(); tempTexturePosition.textures = new Texture2D[properties.Count]; for(int j = 0; j < properties.Count; j++) { //Debug.Log((combines[i].GetTexture(properties[j].propertyName) == null) + ", " + properties[j].propertyName + ", " + combines[i].name); if(combines[i].GetTexture(properties[j].propertyName) == null) { Debug.LogError("Cannot combine textures when using Unity's default material texture"); texturePositions = null; return null; } tempTexturePosition.textures[j] = GameObject.Instantiate(combines[i].GetTexture(properties[j].propertyName)) as Texture2D; tempTexturePosition.textures[j].name = tempTexturePosition.textures[j].name.Remove(tempTexturePosition.textures[j].name.IndexOf("(Clone)")); } texturePositions[i] = tempTexturePosition; } textureQuickSort(texturePositions, 0, texturePositions.Length - 1); for(int i = 0; i < texturePositions.Length; i++) { for(int j = 1; j < texturePositions[i].textures.Length; j++) { texturePositions[i].textures[j] = scaleTexture(texturePositions[i].textures[j], texturePositions[i].textures[0].width, texturePositions[i].textures[0].height); } } texturePositions[0].position.x = texturePositions[0].position.y = 0; texturePositions[0].position.width = texturePositions[0].textures[0].width; texturePositions[0].position.height = texturePositions[0].textures[0].height; int height = texturePositions[0].textures[0].height; int width = texturePositions[0].textures[0].width; int widthIndex = width; int heightIndex = 0; bool useHeightAsReference = true; for(int i = 1; i < texturePositions.Length; i++) { texturePositions[i].position.x = widthIndex; texturePositions[i].position.y = heightIndex; texturePositions[i].position.width = texturePositions[i].textures[0].width; texturePositions[i].position.height = texturePositions[i].textures[0].height; if(useHeightAsReference) { if(widthIndex + texturePositions[i].textures[0].width > width) { width = widthIndex + texturePositions[i].textures[0].width; } heightIndex += texturePositions[i].textures[0].height; if(heightIndex >= height) { useHeightAsReference = false; height = heightIndex; heightIndex = height; widthIndex = 0; } } else { if(heightIndex + texturePositions[i].textures[0].height > height) { height = heightIndex + texturePositions[i].textures[0].height; } widthIndex += texturePositions[i].textures[0].width; if(widthIndex >= width) { useHeightAsReference = true; width = widthIndex; widthIndex = width; heightIndex = 0; } } } if(height > width) { width = height; } else { height = width; } float textureSizeFactor = 1.0f / height; Material newMaterial = new Material(combines[0]); for(int i = 0; i < properties.Count; i++) { Texture2D combinesTextures = new Texture2D(width, height, (atlasInfo.ignoreAlpha && !properties[i].markAsNormal) ? TextureFormat.RGB24 : TextureFormat.ARGB32, true); combinesTextures.anisoLevel = atlasInfo.anisoLevel; combinesTextures.filterMode = atlasInfo.filterMode; combinesTextures.wrapMode = atlasInfo.wrapMode; for(int j = 0; j < texturePositions.Length; j++) { combinesTextures.SetPixels((int)texturePositions[j].position.x, (int)texturePositions[j].position.y, texturePositions[j].textures[i].width, texturePositions[j].textures[i].height, texturePositions[j].textures[i].GetPixels()); } combinesTextures.Apply(); if(atlasInfo.compressTexturesInMemory == true) { combinesTextures.Compress(true); } newMaterial.SetTexture(properties[i].propertyName, combinesTextures); } for(int i = 0; i < texturePositions.Length; i++) { texturePositions[i].position.x = texturePositions[i].position.x * textureSizeFactor; texturePositions[i].position.y = texturePositions[i].position.y * textureSizeFactor; texturePositions[i].position.width = texturePositions[i].position.width * textureSizeFactor; texturePositions[i].position.height = texturePositions[i].position.height * textureSizeFactor; } return newMaterial; }
/** * This function returns two variables: * -> The tecture atlas * -> An array of the old textures and their new positions. (Used for UV modification) */ public static Material combine(Material[] combines, out TexturePosition[] texturePositions, TextureAtlasInfo atlasInfo) { if (atlasInfo == null) { Debug.LogError("atlasInfo is null. Try removing and reattaching combine children component"); texturePositions = null; return(null); } if (atlasInfo.shaderPropertiesToLookFor.Length <= 0) { Debug.LogError("You need to enter some shader properties to look for into Atlas Info. Cannot combine with 0 properties"); texturePositions = null; return(null); } List <ShaderProperties> properties = new List <ShaderProperties>(); for (int i = 0; i < atlasInfo.shaderPropertiesToLookFor.Length; i++) { if (combines[0].HasProperty(atlasInfo.shaderPropertiesToLookFor[i].propertyName) == true) { properties.Add(atlasInfo.shaderPropertiesToLookFor[i]); } } texturePositions = new TexturePosition[combines.Length]; for (int i = 0; i < combines.Length; i++) { TexturePosition tempTexturePosition = new TexturePosition(); tempTexturePosition.textures = new Texture2D[properties.Count]; for (int j = 0; j < properties.Count; j++) { //Debug.Log((combines[i].GetTexture(properties[j].propertyName) == null) + ", " + properties[j].propertyName + ", " + combines[i].name); if (combines[i].GetTexture(properties[j].propertyName) == null) { Debug.LogError("Cannot combine textures when using Unity's default material texture"); texturePositions = null; return(null); } tempTexturePosition.textures[j] = GameObject.Instantiate(combines[i].GetTexture(properties[j].propertyName)) as Texture2D; tempTexturePosition.textures[j].name = tempTexturePosition.textures[j].name.Remove(tempTexturePosition.textures[j].name.IndexOf("(Clone)")); } texturePositions[i] = tempTexturePosition; } textureQuickSort(texturePositions, 0, texturePositions.Length - 1); for (int i = 0; i < texturePositions.Length; i++) { for (int j = 1; j < texturePositions[i].textures.Length; j++) { texturePositions[i].textures[j] = scaleTexture(texturePositions[i].textures[j], texturePositions[i].textures[0].width, texturePositions[i].textures[0].height); } } texturePositions[0].position.x = texturePositions[0].position.y = 0; texturePositions[0].position.width = texturePositions[0].textures[0].width; texturePositions[0].position.height = texturePositions[0].textures[0].height; int height = texturePositions[0].textures[0].height; int width = texturePositions[0].textures[0].width; int widthIndex = width; int heightIndex = 0; bool useHeightAsReference = true; for (int i = 1; i < texturePositions.Length; i++) { texturePositions[i].position.x = widthIndex; texturePositions[i].position.y = heightIndex; texturePositions[i].position.width = texturePositions[i].textures[0].width; texturePositions[i].position.height = texturePositions[i].textures[0].height; if (useHeightAsReference) { if (widthIndex + texturePositions[i].textures[0].width > width) { width = widthIndex + texturePositions[i].textures[0].width; } heightIndex += texturePositions[i].textures[0].height; if (heightIndex >= height) { useHeightAsReference = false; height = heightIndex; heightIndex = height; widthIndex = 0; } } else { if (heightIndex + texturePositions[i].textures[0].height > height) { height = heightIndex + texturePositions[i].textures[0].height; } widthIndex += texturePositions[i].textures[0].width; if (widthIndex >= width) { useHeightAsReference = true; width = widthIndex; widthIndex = width; heightIndex = 0; } } } if (height > width) { width = height; } else { height = width; } float textureSizeFactor = 1.0f / height; Material newMaterial = new Material(combines[0]); for (int i = 0; i < properties.Count; i++) { Texture2D combinesTextures = new Texture2D(width, height, (atlasInfo.ignoreAlpha && !properties[i].markAsNormal) ? TextureFormat.RGB24 : TextureFormat.ARGB32, true); combinesTextures.anisoLevel = atlasInfo.anisoLevel; combinesTextures.filterMode = atlasInfo.filterMode; combinesTextures.wrapMode = atlasInfo.wrapMode; for (int j = 0; j < texturePositions.Length; j++) { combinesTextures.SetPixels((int)texturePositions[j].position.x, (int)texturePositions[j].position.y, texturePositions[j].textures[i].width, texturePositions[j].textures[i].height, texturePositions[j].textures[i].GetPixels()); } combinesTextures.Apply(); if (atlasInfo.compressTexturesInMemory == true) { combinesTextures.Compress(true); } newMaterial.SetTexture(properties[i].propertyName, combinesTextures); } for (int i = 0; i < texturePositions.Length; i++) { texturePositions[i].position.x = texturePositions[i].position.x * textureSizeFactor; texturePositions[i].position.y = texturePositions[i].position.y * textureSizeFactor; texturePositions[i].position.width = texturePositions[i].position.width * textureSizeFactor; texturePositions[i].position.height = texturePositions[i].position.height * textureSizeFactor; } // Debug.Log("TexCU : " + newMaterial.GetTexture(properties[0].propertyName).name + " combines[0] :"+combines[0].name); return(newMaterial); }