diff --git a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProAtlas.cs b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProAtlas.cs index 0dda533..c9d9d1c 100644 --- a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProAtlas.cs +++ b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProAtlas.cs @@ -36,7 +36,8 @@ namespace MA_TextureAtlasserPro editorWorkRect = new Rect(Vector2.zero - zoomCoordsOrigin, textureAtlasSize); GUI.backgroundColor = new Color(0, 0, 0, 0.1f); - GUI.Box(editorWorkRect, this.name); + GUI.Box(editorWorkRect, ""); + GUI.Box(new Rect(editorWorkRect.x, editorWorkRect.y - 25, editorWorkRect.width, 20), this.name); GUI.backgroundColor = Color.white; MA_Editor.Grid.Grid.DrawZoomableGrid(editorWorkRect, 64, new Color(0, 0, 0, 0.1f), zoomCoordsOrigin); diff --git a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProQuad.cs b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProQuad.cs index 6837d7d..327937c 100644 --- a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProQuad.cs +++ b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProQuad.cs @@ -25,7 +25,6 @@ namespace MA_TextureAtlasserPro public Rect dragRectPos; //Data - public Texture texture; //Replace this with texture groups public List textureGroups; public List meshes; @@ -43,7 +42,7 @@ namespace MA_TextureAtlasserPro //Clamp and snap the guiRect guiRect = new Rect(Mathf.RoundToInt(rect.x / 32) * 32, Mathf.RoundToInt(rect.y / 32) * 32, Mathf.RoundToInt(rect.width / 32) * 32, Mathf.RoundToInt(rect.height / 32) * 32); - //Draw the sqaud background + //Draw the quad background if(showTexture && textureGroups != null && textureGroups.Count > 0 && textureGroups[0].texture != null) GUI.DrawTexture(new Rect(guiRect.x - zoomCoordsOrigin.x, guiRect.y - zoomCoordsOrigin.y, guiRect.width, guiRect.height), textureGroups[0].texture, ScaleMode.StretchToFill); else @@ -54,8 +53,8 @@ namespace MA_TextureAtlasserPro GUILayout.BeginHorizontal(); GUILayout.FlexibleSpace(); var tempColor = GUI.backgroundColor; - GUI.backgroundColor = Color.white; - GUILayout.Label(this.name, GUI.skin.box); + GUI.backgroundColor = new Color(1, 1, 1, 0.7f); + GUILayout.Label(" " + this.name + " ", GUI.skin.box); GUI.backgroundColor = tempColor; GUILayout.FlexibleSpace(); GUILayout.EndHorizontal(); diff --git a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProSettings.cs b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProSettings.cs index 5ce0441..043dff5 100644 --- a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProSettings.cs +++ b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Data/MA_TextureAtlasserProSettings.cs @@ -10,18 +10,31 @@ namespace MA_TextureAtlasserPro [System.Serializable] public class MA_TextureAtlasserProSettings : ScriptableObject { - [Header("Selection")] - public bool autoFocus = false; - - [Header("Duplication:")] - public bool copySelectedQuadData = false; - public string duplicatedQuadNamePrefix = "new "; - [Header("Hotkeys:")] public bool useHotkeys = false; + public EventModifiers modifierKey = EventModifiers.Alt; public KeyCode addQuadHotKey = KeyCode.Q; public KeyCode removeQuadHotKey = KeyCode.R; public KeyCode duplicateHotKey = KeyCode.D; + public KeyCode zoomInHotKey = KeyCode.Equals; + public KeyCode zoomOutHotKey = KeyCode.Minus; + + [Header("Duplication:")] + public bool copySelectedQuadData = true; + public string duplicatedQuadNamePrefix = "new "; + + [Header("Selection")] + public bool autoFocus = true; + + public bool GetHotKey(Event e, KeyCode shortKey) + { + if (e.type == EventType.KeyDown && e.modifiers == modifierKey && e.keyCode == shortKey) + { + return true; + } + + return false; + } } } #endif \ No newline at end of file diff --git a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Utils/MA_TextureAtlasserProUtils.cs b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Utils/MA_TextureAtlasserProUtils.cs index 963bc56..e8ee9c3 100644 --- a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Utils/MA_TextureAtlasserProUtils.cs +++ b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Utils/MA_TextureAtlasserProUtils.cs @@ -8,6 +8,34 @@ using MA_Texture; namespace MA_TextureAtlasserPro { + public enum ExportPreset + { + Custom, + Default, + Sprites, + ReplaceObjMeshes + } + + public enum ModelFormat + { + None, + Obj, + ReplaceObj + } + + public enum TextureFormat + { + None, + Png + } + + public enum TextureType + { + Default, + Sprite, + SpriteSliced + } + public static class MA_TextureAtlasserProUtils { public const string SETTINGSASSETPATH = "Assets/MA_ToolBox/MA_TextureAtlasserPro/Settings/"; @@ -19,7 +47,7 @@ namespace MA_TextureAtlasserPro public static MA_TextureAtlasserProSettings CreateSettings() { - MA_TextureAtlasserProSettings _settings = (MA_TextureAtlasserProSettings)ScriptableObject.CreateInstance(); + MA_TextureAtlasserProSettings _settings = ScriptableObject.CreateInstance(); if(_settings != null) { @@ -49,7 +77,7 @@ namespace MA_TextureAtlasserPro public static MA_TextureAtlasserProAtlas CreateTextureAtlas(string name, Vector2 size) { - MA_TextureAtlasserProAtlas _atlas = (MA_TextureAtlasserProAtlas)ScriptableObject.CreateInstance(); + MA_TextureAtlasserProAtlas _atlas = ScriptableObject.CreateInstance(); if(_atlas != null) { @@ -145,7 +173,7 @@ namespace MA_TextureAtlasserPro } } - public static void CreateTextureQuad(MA_TextureAtlasserProAtlas atlas, string name, Rect rect, bool focus = true) + public static MA_TextureAtlasserProQuad CreateTextureQuad(MA_TextureAtlasserProAtlas atlas, string name, Rect rect, bool focus = true) { if(atlas != null) { @@ -156,7 +184,7 @@ namespace MA_TextureAtlasserPro } //Create new quad - MA_TextureAtlasserProQuad _quad = (MA_TextureAtlasserProQuad)ScriptableObject.CreateInstance("MA_TextureAtlasserProQuad"); + MA_TextureAtlasserProQuad _quad = ScriptableObject.CreateInstance(); //Add quad to asset if(_quad != null) @@ -167,7 +195,7 @@ namespace MA_TextureAtlasserPro SetTextureGroups(atlas, _quad); - atlas.textureQuads.Add((MA_TextureAtlasserProQuad)_quad); + atlas.textureQuads.Add(_quad); AssetDatabase.AddObjectToAsset(_quad, atlas); AssetDatabase.SaveAssets(); @@ -177,6 +205,8 @@ namespace MA_TextureAtlasserPro { atlas.selectedTextureQuad = atlas.textureQuads[atlas.textureQuads.Count - 1]; } + + return _quad; } else { @@ -187,6 +217,8 @@ namespace MA_TextureAtlasserPro { Debug.LogError("CreateTextureQuad Failed: textureAtlas"); } + + return null; } public static void RemoveTextureQuad(MA_TextureAtlasserProAtlas atlas, bool focus = true) @@ -196,7 +228,7 @@ namespace MA_TextureAtlasserPro int _index = atlas.textureQuads.IndexOf(atlas.selectedTextureQuad); atlas.textureQuads.RemoveAt(_index); - GameObject.DestroyImmediate(atlas.selectedTextureQuad, true); + Object.DestroyImmediate(atlas.selectedTextureQuad, true); AssetDatabase.SaveAssets(); AssetDatabase.Refresh(); @@ -212,18 +244,25 @@ namespace MA_TextureAtlasserPro { if(atlas != null && atlas.selectedTextureQuad != null) { - CreateTextureQuad(atlas, namePrefix + atlas.selectedTextureQuad.name, atlas.selectedTextureQuad.rect, false); + MA_TextureAtlasserProQuad q = CreateTextureQuad(atlas, namePrefix + atlas.selectedTextureQuad.name, atlas.selectedTextureQuad.rect, false); - if(copyData) + if (copyData) { - atlas.textureQuads[atlas.textureQuads.Count - 1].meshes = atlas.selectedTextureQuad.meshes; - atlas.textureQuads[atlas.textureQuads.Count - 1].textureGroups = atlas.selectedTextureQuad.textureGroups; + q.meshes = atlas.selectedTextureQuad.meshes; + + for (int i = 0; i < atlas.selectedTextureQuad.textureGroups.Count; i++) + { + q.textureGroups[i].texture = atlas.selectedTextureQuad.textureGroups[i].texture; + } } if(focus) { - atlas.selectedTextureQuad = atlas.textureQuads[atlas.textureQuads.Count - 1]; + atlas.selectedTextureQuad = q; } + + AssetDatabase.SaveAssets(); + AssetDatabase.Refresh(); } } @@ -276,183 +315,6 @@ namespace MA_TextureAtlasserPro curWindow.Close(); } - public static void ExportAtlas(MA_TextureAtlasserProAtlas atlas, string savePath = EXPORTASSETPATH) - { - if(atlas != null && atlas.textureQuads != null) - { - ExportAtlasMeshesObj(atlas); - ExportAtlasTexturesPNG(atlas); - - AssetDatabase.Refresh(); - } - } - - public static void ExportAtlasMeshesObj(MA_TextureAtlasserProAtlas atlas, string savePath = EXPORTASSETPATH) - { - if(atlas != null && atlas.textureQuads != null) - { - foreach (MA_TextureAtlasserProQuad ta in atlas.textureQuads) - { - //Export Mesh - if(ta.meshes != null) - { - for (int m = 0; m < ta.meshes.Count; m++) - { - if(ta.meshes[m] != null) - { - //Create new mesh - Mesh newMesh = new Mesh(); - //Duplicate it from the current one - newMesh = MA_MeshUtils.MA_DuplicateMesh(ta.meshes[m]); - //Remap uvs - newMesh = MA_MeshUtils.MA_UVReMap(newMesh, atlas.textureAtlasSize, ta.guiRect); - //Save it - MA_MeshUtils.MeshToFile(newMesh, "MA_" + ta.name, savePath); - } - } - } - } - } - } - - public static void ModifyMeshes(MA_TextureAtlasserProAtlas atlas) - { - if (atlas == null || atlas.textureQuads == null) return; - var quads = atlas.textureQuads; - for (var index = 0; index < quads.Count; index++) - { - var quad = quads[index]; - if (quad.meshes == null) continue; - var meshes = quad.meshes; - for (var meshIndex = 0; meshIndex < quad.meshes.Count; meshIndex++) - { - if (meshes[meshIndex] == null) continue; - MA_MeshUtils.MA_UVReMap(meshes[meshIndex], atlas.textureAtlasSize, quad.guiRect); - EditorUtility.SetDirty(meshes[meshIndex]); - } - } - AssetDatabase.SaveAssets(); - } - - // public static void ExportAtlasTexturePNG(MA_TextureAtlasserProAtlas atlas, string savePath = EXPORTASSETPATH) - // { - // if(atlas != null && atlas.textureQuads != null) - // { - // //Create new Texture Atlas - // Texture2D newTexture = new Texture2D((int)atlas.textureAtlasSize.x, (int)atlas.textureAtlasSize.y); - // newTexture.name = atlas.name; - - // foreach (MA_TextureAtlasserProQuad ta in atlas.textureQuads) - // { - // //Export Texture Atlas - // //TODO: Replace with texture groups (foreacht ...) - // if(ta.texture != null) - // { - // //Create new texture part - // Texture2D newTexturePart = (Texture2D)MA_Texture.MA_TextureUtils.ConvertToReadableTexture(ta.texture); - // //Scale it - // newTexturePart = newTexturePart.MA_Scale2D((int)ta.guiRect.width, (int)ta.guiRect.height); - // //Add it - // newTexture = newTexture.MA_Combine2D(newTexturePart, (int)ta.guiRect.x, (int)ta.guiRect.y); - // } - // } - - // //Save it - // newTexture.MA_Save2D("MA_" + newTexture.name, savePath); - // //Refresh - // AssetDatabase.Refresh(); - // } - // } - - public static void ExportAtlasTexturesPNG(MA_TextureAtlasserProAtlas atlas, string savePath = EXPORTASSETPATH) - { - if(atlas != null && atlas.textureQuads != null && atlas.textureGroupRegistration != null) - { - //Foreach texture group - for (int i = 0; i < atlas.textureGroupRegistration.Count; i++) - { - //Create new Texture Atlas - Texture2D newTexture = new Texture2D((int)atlas.textureAtlasSize.x, (int)atlas.textureAtlasSize.y); - newTexture.name = atlas.name + "_" + atlas.textureGroupRegistration[i].name; - - foreach (MA_TextureAtlasserProQuad q in atlas.textureQuads) - { - if(q.textureGroups != null && q.textureGroups[i].texture != null) - { - //Create new texture part - Texture2D newTexturePart = (Texture2D)MA_Texture.MA_TextureUtils.ConvertToReadableTexture(q.textureGroups[i].texture); - //Scale it - newTexturePart = newTexturePart.ScaleTexture((int)q.guiRect.width, (int)q.guiRect.height, true); - //Add it - newTexture = newTexture.MA_Combine2D(newTexturePart, (int)q.guiRect.x, (int)q.guiRect.y); - } - } - - //Save it - newTexture.MA_Save2D("MA_" + newTexture.name, savePath); - - TextureImporter textureImporter = (TextureImporter)AssetImporter.GetAtPath(savePath + "MA_" + newTexture.name + ".png"); - textureImporter.textureType = TextureImporterType.Default; - textureImporter.SaveAndReimport(); - } - - //Refresh - AssetDatabase.Refresh(); - } - } - - public static void ExportAtlasSpritesPNG(MA_TextureAtlasserProAtlas atlas, bool sliceSprites = true, string savePath = EXPORTASSETPATH) - { - if (atlas != null && atlas.textureQuads != null && atlas.textureGroupRegistration != null) - { - ExportAtlasTexturesPNG(atlas, savePath); - - //Foreach texture group - for (int i = 0; i < atlas.textureGroupRegistration.Count; i++) - { - //Convert - string textureName = "MA_" + atlas.name + "_" + atlas.textureGroupRegistration[i].name + ".png"; - TextureImporter textureImporter = (TextureImporter)AssetImporter.GetAtPath(savePath + textureName); - textureImporter.textureType = TextureImporterType.Sprite; - textureImporter.alphaIsTransparency = true; - - //Slice sprites. - if (sliceSprites) - { - textureImporter.spriteImportMode = SpriteImportMode.None; //Reset it to update? - textureImporter.spriteImportMode = SpriteImportMode.Multiple; - List spriteMetaData = new List(); - - foreach (MA_TextureAtlasserProQuad q in atlas.textureQuads) - { - if (q.textureGroups != null && q.textureGroups[i].texture != null) - { - //Create new SpriteMetaData. - SpriteMetaData smd = new SpriteMetaData(); - - smd.name = q.name; - smd.rect = new Rect(q.guiRect.x, atlas.textureAtlasSize.y - q.guiRect.y - q.guiRect.height, q.guiRect.width, q.guiRect.height); - - spriteMetaData.Add(smd); - } - } - - textureImporter.spritesheet = spriteMetaData.ToArray(); - } - else - { - textureImporter.spriteImportMode = SpriteImportMode.Single; - } - - - textureImporter.SaveAndReimport(); - } - - //Refresh - AssetDatabase.Refresh(); - } - } - public static bool IsPowerOfTwo(int value) { //While x is even and > 1 @@ -463,6 +325,193 @@ namespace MA_TextureAtlasserPro return (value == 1); } + + #region Export + public static void ExportAtlasModels(MA_TextureAtlasserProAtlas atlas, ModelFormat modelFormat, string savePath = EXPORTASSETPATH) + { + switch (modelFormat) + { + case ModelFormat.None: + break; + case ModelFormat.Obj: + ExportAtlasObj(atlas, savePath); + break; + case ModelFormat.ReplaceObj: + ModifyAtlasObj(atlas); + break; + default: + break; + } + } + + public static void ExportAtlasObj(MA_TextureAtlasserProAtlas atlas, string savePath = EXPORTASSETPATH) + { + if (atlas == null || atlas.textureQuads == null) + return; + + foreach (MA_TextureAtlasserProQuad ta in atlas.textureQuads) + { + //Export Mesh + if(ta.meshes != null) + { + for (int m = 0; m < ta.meshes.Count; m++) + { + if(ta.meshes[m] != null) + { + //Create new mesh + Mesh newMesh = new Mesh(); + //Duplicate it from the current one + newMesh = MA_MeshUtils.MA_DuplicateMesh(ta.meshes[m]); + //Remap UV's + newMesh = MA_MeshUtils.MA_UVReMap(newMesh, atlas.textureAtlasSize, ta.guiRect); + //Save it + string modelName = string.IsNullOrEmpty(ta.name) ? "": ta.name + "-"; + modelName += ta.meshes[m].name; + int n = m + 1; + modelName += "_" + n.ToString("#000"); + + MA_MeshUtils.MeshToFile(newMesh, modelName, savePath); + } + } + } + } + } + + public static void ModifyAtlasObj(MA_TextureAtlasserProAtlas atlas) + { + if (atlas == null || atlas.textureQuads == null) + return; + + var quads = atlas.textureQuads; + + for (var index = 0; index < quads.Count; index++) + { + var quad = quads[index]; + if (quad.meshes == null) + continue; + + var meshes = quad.meshes; + for (var meshIndex = 0; meshIndex < quad.meshes.Count; meshIndex++) + { + if (meshes[meshIndex] == null) + continue; + + MA_MeshUtils.MA_UVReMap(meshes[meshIndex], atlas.textureAtlasSize, quad.guiRect); + EditorUtility.SetDirty(meshes[meshIndex]); + } + } + + AssetDatabase.SaveAssets(); + } + + public static void ExportAtlasTextures(MA_TextureAtlasserProAtlas atlas, TextureFormat textureFormat, TextureType textureType, MA_TextureUtils.TextureScaleMode scaleMode, string savePath = EXPORTASSETPATH) + { + switch (textureFormat) + { + case TextureFormat.None: + break; + case TextureFormat.Png: + ExportAtlasPNG(atlas, textureType, scaleMode, savePath); + break; + default: + break; + } + } + + private static void ExportAtlasPNG(MA_TextureAtlasserProAtlas atlas, TextureType textureType, MA_TextureUtils.TextureScaleMode scaleMode, string savePath = EXPORTASSETPATH) + { + if (atlas == null || atlas.textureQuads == null || atlas.textureGroupRegistration == null) + return; + + //Foreach texture group + for (int i = 0; i < atlas.textureGroupRegistration.Count; i++) + { + //Create new Texture Atlas + Texture2D newTexture = new Texture2D((int)atlas.textureAtlasSize.x, (int)atlas.textureAtlasSize.y); + newTexture.name = atlas.name + "_" + atlas.textureGroupRegistration[i].name; + + foreach (MA_TextureAtlasserProQuad q in atlas.textureQuads) + { + if (q.textureGroups != null && q.textureGroups[i].texture != null) + { + //Create new texture part + Texture2D newTexturePart = (Texture2D)MA_Texture.MA_TextureUtils.ConvertToReadableTexture(q.textureGroups[i].texture); + //Scale it + newTexturePart = newTexturePart.MA_Scale2D((int)q.guiRect.width, (int)q.guiRect.height, scaleMode); + //Add it + newTexture = newTexture.MA_Combine2D(newTexturePart, (int)q.guiRect.x, (int)q.guiRect.y); + } + } + + //Save it + newTexture.MA_Save2D(newTexture.name, savePath); + + TextureImporter textureImporter = (TextureImporter)AssetImporter.GetAtPath(savePath + newTexture.name + ".png"); + textureImporter.textureType = TextureImporterType.Default; + textureImporter.SaveAndReimport(); + } + + switch (textureType) + { + case TextureType.Default: + break; + case TextureType.Sprite: + SetAtlasPNGSpriteSettings(atlas, textureType, savePath); + break; + case TextureType.SpriteSliced: + SetAtlasPNGSpriteSettings(atlas, textureType, savePath); + break; + default: + break; + } + + //Refresh + AssetDatabase.Refresh(); + } + + private static void SetAtlasPNGSpriteSettings(MA_TextureAtlasserProAtlas atlas, TextureType textureType, string savePath = EXPORTASSETPATH) + { + //Foreach texture group + for (int i = 0; i < atlas.textureGroupRegistration.Count; i++) + { + //Convert + string textureName = atlas.name + "_" + atlas.textureGroupRegistration[i].name + ".png"; + TextureImporter textureImporter = (TextureImporter)AssetImporter.GetAtPath(savePath + textureName); + textureImporter.textureType = TextureImporterType.Sprite; + textureImporter.alphaIsTransparency = true; + + //Slice sprites. + if (textureType == TextureType.SpriteSliced) + { + textureImporter.spriteImportMode = SpriteImportMode.None; //Reset it to update? + textureImporter.spriteImportMode = SpriteImportMode.Multiple; + List spriteMetaData = new List(); + + foreach (MA_TextureAtlasserProQuad q in atlas.textureQuads) + { + if (q.textureGroups != null && q.textureGroups[i].texture != null) + { + //Create new SpriteMetaData. + SpriteMetaData smd = new SpriteMetaData(); + + smd.name = q.name; + smd.rect = new Rect(q.guiRect.x, atlas.textureAtlasSize.y - q.guiRect.y - q.guiRect.height, q.guiRect.width, q.guiRect.height); + + spriteMetaData.Add(smd); + } + } + + textureImporter.spritesheet = spriteMetaData.ToArray(); + } + else + { + textureImporter.spriteImportMode = SpriteImportMode.Single; + } + + textureImporter.SaveAndReimport(); + } + } + #endregion } } #endif \ No newline at end of file diff --git a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Views/MA_TextureAtlasserProDebugView.cs b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Views/MA_TextureAtlasserProDebugView.cs index 15cd6fc..f40cd9d 100644 --- a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Views/MA_TextureAtlasserProDebugView.cs +++ b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Views/MA_TextureAtlasserProDebugView.cs @@ -33,7 +33,7 @@ namespace MA_TextureAtlasserPro curWindow.workView.ResetWindow(); } - if(curWindow.textureAtlas != null) + if (curWindow.textureAtlas != null) { GUILayout.FlexibleSpace(); //GUILayout.Label(curWindow.textureAtlas.textureAtlasSize.ToString()); diff --git a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Views/MA_TextureAtlasserProWorkView.cs b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Views/MA_TextureAtlasserProWorkView.cs index cdeb916..ba55221 100644 --- a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Views/MA_TextureAtlasserProWorkView.cs +++ b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Views/MA_TextureAtlasserProWorkView.cs @@ -19,7 +19,7 @@ namespace MA_TextureAtlasserPro private const float kZoomMax = 2.0f; private Rect zoomArea; private float zoom = 1.0f; - public float Zoom { get { return zoom; } } + public float Zoom { get { return zoom; } set { zoom = Mathf.Clamp(value, kZoomMin, kZoomMax); } } private Vector2 zoomCoordsOrigin = Vector2.zero; public override void UpdateView(Event e, Rect editorViewRect) @@ -96,21 +96,32 @@ namespace MA_TextureAtlasserPro { if(curWindow.textureAtlas != null) { - if (e.type == EventType.KeyDown && e.keyCode == curWindow.settings.addQuadHotKey) + if (curWindow.settings.GetHotKey(e, curWindow.settings.addQuadHotKey)) { MA_TextureAtlasserProUtils.CreateTextureQuad(curWindow.textureAtlas, "new Quad", new Rect(0, 0, 128, 128), curWindow.settings.autoFocus); e.Use(); } + if(curWindow.settings.GetHotKey(e, curWindow.settings.zoomInHotKey)) + { + Zoom += 0.25f; + e.Use(); + } + if(curWindow.settings.GetHotKey(e, curWindow.settings.zoomOutHotKey)) + { + Zoom -= 0.25f; + e.Use(); + } + if (curWindow.textureAtlas.selectedTextureQuad != null) { - if (e.type == EventType.KeyDown && e.keyCode == curWindow.settings.removeQuadHotKey) + if (curWindow.settings.GetHotKey(e, curWindow.settings.removeQuadHotKey)) { MA_TextureAtlasserProUtils.RemoveTextureQuad(curWindow.textureAtlas, curWindow.settings.autoFocus); e.Use(); } - if (e.type == EventType.KeyDown && e.keyCode == curWindow.settings.duplicateHotKey) + if (curWindow.settings.GetHotKey(e, curWindow.settings.duplicateHotKey)) { MA_TextureAtlasserProUtils.DuplicateTextureQuad(curWindow.textureAtlas, curWindow.settings.autoFocus, curWindow.settings.copySelectedQuadData, curWindow.settings.duplicatedQuadNamePrefix); e.Use(); diff --git a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Windows/MA_TextureAtlasserProExportWindow.cs b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Windows/MA_TextureAtlasserProExportWindow.cs index 894b55f..4f1f765 100644 --- a/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Windows/MA_TextureAtlasserProExportWindow.cs +++ b/MA_ToolBox/MA_TextureAtlasserPro/Scripts/Editor/Windows/MA_TextureAtlasserProExportWindow.cs @@ -4,21 +4,14 @@ using System.Collections.Generic; using UnityEngine; using UnityEditor; using MA_Editor; +using MA_Texture; namespace MA_TextureAtlasserPro { public class MA_TextureAtlasserProExportWindow : EditorWindow { - private const int WindowHeight = 215; - - private enum ExportMode - { - None, - D3, - D2, - Meshes, - } - + private const int WindowHeight = 235; + //Editor private static MA_TextureAtlasserProExportWindow thisWindow; public static MA_TextureAtlasserProWindow curWindow; @@ -26,14 +19,12 @@ namespace MA_TextureAtlasserPro //Data private static bool isLoaded = false; //Make sure we wait a frame at the start to setup and don't draw. - private ExportMode _selectedExportMode; - private bool _showAdvancedEditor; - - private bool exportObjDefault = false; - private bool _replaceMeshes = false; - private bool exportPngDefault = false; - private bool exportSprite = false; - private bool exportSliceSprite = false; + //Export settings. + private ExportPreset exportPreset = ExportPreset.Default; + private ModelFormat modelFormat = ModelFormat.Obj; + private TextureFormat textureFormat = TextureFormat.Png; + private TextureType textureType = TextureType.Default; + private MA_TextureUtils.TextureScaleMode textureScaleMode = MA_TextureUtils.TextureScaleMode.Bilinear; [MenuItem("MA_ToolKit/MA_TextureAtlasserPro/Export Atlas")] private static void Init() @@ -116,36 +107,42 @@ namespace MA_TextureAtlasserPro //Export GUILayout.BeginVertical(); - DrawExportModeEditor(); - DrawAdvancedEditor(); + DrawExportPresetMenu(); + DrawExportAdvancedOptions(); GUILayout.BeginHorizontal(EditorStyles.helpBox); - GUI.enabled = _selectedExportMode != ExportMode.None; - if (GUILayout.Button("Export", GUILayout.ExpandWidth(true), GUILayout.Height(37))) + switch (exportPreset) { - if(exportObjDefault) - { - MA_TextureAtlasserProUtils.ExportAtlasMeshesObj(curWindow.textureAtlas); - } - - if (_replaceMeshes) - MA_TextureAtlasserProUtils.ModifyMeshes(curWindow.textureAtlas); - - if(exportPngDefault) - { - if(exportSprite) - { - MA_TextureAtlasserProUtils.ExportAtlasSpritesPNG(curWindow.textureAtlas, exportSliceSprite); - } - else - { - MA_TextureAtlasserProUtils.ExportAtlasTexturesPNG(curWindow.textureAtlas); - } - } + case ExportPreset.Custom: + break; + case ExportPreset.Default: + modelFormat = ModelFormat.Obj; + textureFormat = TextureFormat.Png; + textureType = TextureType.Default; + textureScaleMode = MA_TextureUtils.TextureScaleMode.Bilinear; + break; + case ExportPreset.Sprites: + modelFormat = ModelFormat.None; + textureFormat = TextureFormat.Png; + textureType = TextureType.SpriteSliced; + textureScaleMode = MA_TextureUtils.TextureScaleMode.Bilinear; + break; + case ExportPreset.ReplaceObjMeshes: + modelFormat = ModelFormat.ReplaceObj; + textureFormat = TextureFormat.Png; + textureType = TextureType.Default; + textureScaleMode = MA_TextureUtils.TextureScaleMode.Bilinear; + break; + default: + break; } - GUI.enabled = true; + if (GUILayout.Button("Export", GUILayout.ExpandWidth(true), GUILayout.Height(37))) + { + MA_TextureAtlasserProUtils.ExportAtlasModels(curWindow.textureAtlas, modelFormat); + MA_TextureAtlasserProUtils.ExportAtlasTextures(curWindow.textureAtlas, textureFormat, textureType, textureScaleMode); + } GUILayout.EndHorizontal(); GUILayout.EndVertical(); @@ -175,77 +172,41 @@ namespace MA_TextureAtlasserPro isLoaded = true; } - private void DrawExportModeEditor() + private void DrawExportPresetMenu() { GUILayout.BeginHorizontal(EditorStyles.helpBox); - GUILayout.FlexibleSpace(); - var value = GUILayout.Toggle(_selectedExportMode == ExportMode.D3, "3D", EditorStyles.miniButtonLeft, - GUILayout.ExpandWidth(false)); - if (value && _selectedExportMode != ExportMode.D3) - { - _selectedExportMode = ExportMode.D3; - exportObjDefault = true; - _replaceMeshes = false; - exportPngDefault = true; - exportSprite = false; - exportSliceSprite = false; - } - value = GUILayout.Toggle(_selectedExportMode == ExportMode.D2, "2D", EditorStyles.miniButtonMid, - GUILayout.ExpandWidth(false)); - if (value && _selectedExportMode != ExportMode.D2) - { - _selectedExportMode = ExportMode.D2; - exportObjDefault = false; - _replaceMeshes = false; - exportPngDefault = true; - exportSprite = true; - exportSliceSprite = true; - } - value = GUILayout.Toggle(_selectedExportMode == ExportMode.Meshes, "Replace source meshes", EditorStyles.miniButtonRight, - GUILayout.ExpandWidth(false)); - if (value && _selectedExportMode != ExportMode.Meshes) - { - _selectedExportMode = ExportMode.Meshes; - exportObjDefault = false; - _replaceMeshes = true; - exportPngDefault = true; - exportSprite = false; - exportSliceSprite = false; - } - GUILayout.FlexibleSpace(); + + exportPreset = (ExportPreset)EditorGUILayout.EnumPopup("ExportPreset:", exportPreset, GUILayout.ExpandWidth(true)); + GUILayout.EndHorizontal(); } - private void DrawAdvancedEditor() + private void DrawExportAdvancedOptions() { - EditorGUILayout.BeginVertical(EditorStyles.helpBox); - _showAdvancedEditor = EditorGUILayout.Foldout(_showAdvancedEditor, "Advanced editor"); - if (!_showAdvancedEditor) + bool wasEnabled = GUI.enabled; + + if(exportPreset == ExportPreset.Custom) { - EditorGUILayout.EndVertical(); - return; + GUI.enabled = true; + } + else + { + GUI.enabled = false; } - GUILayout.Label("Meshes:", EditorStyles.miniBoldLabel); - EditorGUILayout.BeginHorizontal(); - exportObjDefault = GUILayout.Toggle(exportObjDefault, "OBJ default."); - _replaceMeshes = GUILayout.Toggle(_replaceMeshes, "Replace meshes"); - EditorGUILayout.EndHorizontal(); - + EditorGUILayout.BeginVertical(EditorStyles.helpBox); + + GUILayout.Label("Models:", EditorStyles.miniBoldLabel); + modelFormat = (ModelFormat)EditorGUILayout.EnumPopup("ModelFormat:", modelFormat); + GUILayout.Label("Textures:", EditorStyles.miniBoldLabel); - GUILayout.BeginHorizontal(); - exportPngDefault = GUILayout.Toggle(exportPngDefault, "PNG default."); - if(exportPngDefault) - { - exportSprite = GUILayout.Toggle(exportSprite, "Sprite."); - if (exportSprite) - { - exportSliceSprite = GUILayout.Toggle(exportSliceSprite, "Slice sprites."); - } - } - GUILayout.FlexibleSpace(); - GUILayout.EndHorizontal(); + textureFormat = (TextureFormat)EditorGUILayout.EnumPopup("TextureFormat:", textureFormat); + textureType = (TextureType)EditorGUILayout.EnumPopup("TextureType:", textureType); + textureScaleMode = (MA_TextureUtils.TextureScaleMode)EditorGUILayout.EnumPopup("TextureScaleMode:", textureScaleMode); + EditorGUILayout.EndVertical(); + + GUI.enabled = wasEnabled; } } } diff --git a/MA_ToolBox/MA_Utilities/TextureUtils/MA_TextureUtils.cs b/MA_ToolBox/MA_Utilities/TextureUtils/MA_TextureUtils.cs index 6fad41b..729277c 100644 --- a/MA_ToolBox/MA_Utilities/TextureUtils/MA_TextureUtils.cs +++ b/MA_ToolBox/MA_Utilities/TextureUtils/MA_TextureUtils.cs @@ -5,6 +5,7 @@ //https://forum.unity3d.com/threads/contribution-texture2d-blur-in-c.185694/ //http://orbcreation.com/orbcreation/page.orb?1180 //https://support.unity3d.com/hc/en-us/articles/206486626-How-can-I-get-pixels-from-unreadable-textures- +//https://github.com/maxartz15/MA_TextureAtlasser/commit/9f5240967a51692fa2a17a6b3c8d124dd5dc60f9 #if UNITY_EDITOR using UnityEngine; @@ -12,6 +13,7 @@ using UnityEditor; using System.IO; using System.Collections; using System.Collections.Generic; +using System; namespace MA_Texture { @@ -69,8 +71,6 @@ namespace MA_Texture bw.Close(); fs.Close(); - Debug.Log("Saved texture: " + texture.name); - AssetDatabase.Refresh(); return texture; @@ -86,111 +86,110 @@ namespace MA_Texture return texture; } - #endregion + #endregion - #region Scale - public static Texture2D MA_Scale2D(this Texture2D texture, int newWidth, int newHeight) - { - Texture2D texture2D = new Texture2D(newWidth, newHeight); - float ratioWidth = texture.width / newWidth; - float ratioHeight = texture.height / newHeight; - - for (int x = 0; x < texture.width; x++) - { - for (int y = 0; y < texture.height; y++) - { - Color pixel = texture.GetPixel(x, y); - int posX = Mathf.FloorToInt(x / ratioWidth); - int posY = Mathf.FloorToInt(y / ratioHeight); - texture2D.SetPixel(posX, posY, new Color(pixel.r, pixel.g, pixel.b, pixel.a)); - } - } - texture2D.Apply(); - - return texture2D; - } - - public static Texture MA_Scale(this Texture texture, int newWidth, int newHeight) - { - Texture2D texture2D = (Texture2D)MA_TextureUtils.ConvertToReadableTexture(texture); - - texture2D.MA_Scale2D(newWidth, newHeight); - - texture = texture2D; - - return texture; - } - - public static Texture2D MA_Scale22D(this Texture2D texture, float width, float height) - { - float ratioWidth = width / texture.width; - float ratioHeight = height / texture.height; - - int newWidth = Mathf.RoundToInt(texture.width * ratioWidth); - int newHeight = Mathf.RoundToInt(texture.height * ratioHeight); - - Texture2D newTexture = new Texture2D(newWidth, newHeight); - - for (int x = 0; x < texture.width; x++) - { - for (int y = 0; y < texture.height; y++) - { - Color pixel = texture.GetPixel(x, y); - int posX = Mathf.RoundToInt(x * ratioWidth); - int posY = Mathf.RoundToInt(y * ratioHeight); - newTexture.SetPixel(posX, posY, new Color(pixel.r, pixel.g, pixel.b, pixel.a)); - } - } - - newTexture.name = texture.name; - - newTexture.Apply(); - return newTexture; - } - - public static Texture MA_Scale2(this Texture texture, float newWidth, float newHeight) - { - Texture2D texture2D = (Texture2D)MA_TextureUtils.ConvertToReadableTexture(texture); - - texture = texture2D.MA_Scale22D(newWidth, newHeight); - - return texture; - } - - public static Texture2D MA_Scale32D(this Texture2D texture, int width, int height) + #region Scale + public enum TextureScaleMode { - float ratioWidth = (float)width / texture.width; - float ratioHeight = (float)height / texture.height; + Bilinear, + Point + } - Texture2D newTexture = new Texture2D(width, height); + public static Texture MA_Scale(this Texture texture, int width, int height, TextureScaleMode scaleMode) + { + Texture2D texture2D = (Texture2D)MA_TextureUtils.ConvertToReadableTexture(texture); - for (int x = 0; x < width; x++) + texture2D.MA_Scale2D(width, height, scaleMode); + + texture = texture2D; + + return texture; + } + + public static Texture2D MA_Scale2D(this Texture2D texture, int newWidth, int newHeight, TextureScaleMode scaleMode) + { + Color[] curColors = texture.GetPixels(); + Color[] newColors = new Color[newWidth * newHeight]; + + switch (scaleMode) { - int posX = Mathf.FloorToInt(x / ratioWidth); - for (int y = 0; y < height; y++) + case TextureScaleMode.Bilinear: + newColors = MA_BilinearScale(curColors, texture.width, texture.height, newWidth, newHeight); + break; + case TextureScaleMode.Point: + newColors = MA_PointScale(curColors, texture.width, texture.height, newWidth, newHeight); + break; + + } + + texture.Resize(newWidth, newHeight); + texture.SetPixels(newColors); + texture.Apply(); + + return texture; + } + + private static Color[] MA_BilinearScale(Color[] curColors, int curWidth, int curHeight, int newWidth, int newHeight) + { + Color[] newColors = new Color[newWidth * newHeight]; + + float ratioX = 1.0f / ((float)newWidth / (curWidth - 1)); + float ratioY = 1.0f / ((float)newHeight / (curHeight - 1)); + + for (int y = 0; y < newHeight; y++) + { + int yFloor = Mathf.FloorToInt(y * ratioY); + var y1 = yFloor * curWidth; + var y2 = (yFloor + 1) * curWidth; + var yw = y * newWidth; + + for (int x = 0; x < newWidth; x++) { - int posY = Mathf.FloorToInt(y / ratioHeight); - Color pixel = texture.GetPixel(posX, posY); - newTexture.SetPixel(x, y, new Color(pixel.r, pixel.g, pixel.b, pixel.a)); + int xFloor = Mathf.FloorToInt(x * ratioX); + var xLerp = x * ratioX - xFloor; + + newColors[yw + x] = ColorLerpUnclamped(ColorLerpUnclamped(curColors[y1 + xFloor], curColors[y1 + xFloor + 1], xLerp), + ColorLerpUnclamped(curColors[y2 + xFloor], curColors[y2 + xFloor + 1], xLerp), + y * ratioY - yFloor); } } - newTexture.name = texture.name; - - newTexture.Apply(); - return newTexture; + return newColors; } - public static Texture2D ScaleTexture(this Texture2D texture, int width, int height, bool bilinear) - { - TextureScaler.Scale(texture, width, height, bilinear); - return texture; - } - - #endregion + private static Color[] MA_PointScale(Color[] curColors, int curWidth, int curHeight, int newWidth, int newHeight) + { + Color[] newColors = new Color[newWidth * newHeight]; - #region combine - public static Texture2D MA_Combine2D(this Texture2D texture, Texture2D combineTexture, int offsetX, int offsetY, bool flipY = true) + float ratioX = ((float)curWidth) / newWidth; + float ratioY = ((float)curHeight) / newHeight; + + for (int y = 0; y < newHeight; y++) + { + var thisY = Mathf.RoundToInt((ratioY * y) * curWidth); + var yw = y * newWidth; + + for (int x = 0; x < newWidth; x++) + { + newColors[yw + x] = curColors[Mathf.RoundToInt(thisY + ratioX * x)]; + } + } + + return newColors; + } + + private static Color ColorLerpUnclamped(Color c1, Color c2, float value) + { + return new Color(c1.r + (c2.r - c1.r) * value, + c1.g + (c2.g - c1.g) * value, + c1.b + (c2.b - c1.b) * value, + c1.a + (c2.a - c1.a) * value); + } + + #endregion + + #region combine + public static Texture2D MA_Combine2D(this Texture2D texture, Texture2D combineTexture, int offsetX, int offsetY, bool flipY = true) { for (int x = 0; x < combineTexture.width; x++) { diff --git a/MA_ToolBox/MA_Utilities/TextureUtils/TextureScaler.cs b/MA_ToolBox/MA_Utilities/TextureUtils/TextureScaler.cs deleted file mode 100644 index 698de7e..0000000 --- a/MA_ToolBox/MA_Utilities/TextureUtils/TextureScaler.cs +++ /dev/null @@ -1,103 +0,0 @@ -using System.Threading; -using UnityEngine; - -namespace MA_Texture -{ - public static class TextureScaler - { - public class ThreadData - { - public int start; - public int end; - public ThreadData (int s, int e) { - start = s; - end = e; - } - } - - private static Color[] texColors; - private static Color[] newColors; - private static int w; - private static float ratioX; - private static float ratioY; - private static int w2; - private static int finishCount; - - public static void Scale (Texture2D tex, int newWidth, int newHeight, bool useBilinear) - { - texColors = tex.GetPixels(); - newColors = new Color[newWidth * newHeight]; - if (useBilinear) - { - ratioX = 1.0f / ((float)newWidth / (tex.width-1)); - ratioY = 1.0f / ((float)newHeight / (tex.height-1)); - } - else { - ratioX = ((float)tex.width) / newWidth; - ratioY = ((float)tex.height) / newHeight; - } - w = tex.width; - w2 = newWidth; - finishCount = 0; - if (useBilinear) - { - BilinearScale(0, newHeight); - } - else - { - PointScale(0, newHeight); - } - - - tex.Resize(newWidth, newHeight); - tex.SetPixels(newColors); - tex.Apply(); - - texColors = null; - newColors = null; - } - - public static void BilinearScale (int start, int end) - { - for (var y = start; y < end; y++) - { - int yFloor = (int)Mathf.Floor(y * ratioY); - var y1 = yFloor * w; - var y2 = (yFloor+1) * w; - var yw = y * w2; - - for (var x = 0; x < w2; x++) { - int xFloor = (int)Mathf.Floor(x * ratioX); - var xLerp = x * ratioX-xFloor; - newColors[yw + x] = ColorLerpUnclamped(ColorLerpUnclamped(texColors[y1 + xFloor], texColors[y1 + xFloor+1], xLerp), - ColorLerpUnclamped(texColors[y2 + xFloor], texColors[y2 + xFloor+1], xLerp), - y*ratioY-yFloor); - } - } - - finishCount++; - } - - public static void PointScale (int start, int end) - { - for (var y = start; y < end; y++) - { - var thisY = (int)(ratioY * y) * w; - var yw = y * w2; - for (var x = 0; x < w2; x++) { - newColors[yw + x] = texColors[(int)(thisY + ratioX*x)]; - } - } - - finishCount++; - } - - private static Color ColorLerpUnclamped (Color c1, Color c2, float value) - { - return new Color (c1.r + (c2.r - c1.r)*value, - c1.g + (c2.g - c1.g)*value, - c1.b + (c2.b - c1.b)*value, - c1.a + (c2.a - c1.a)*value); - } - } -} \ No newline at end of file