TexturePacker 图集生成工具

Posted 天涯过客TYGK

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了TexturePacker 图集生成工具相关的知识,希望对你有一定的参考价值。

TexturePacker 可以通过命令行方式,批量生成图集,TexturePacker相关命令可以参考 https://blog.csdn.net/u014065445/article/details/54289787

unity中使用的方式是,通过C#中的Process类,创建一个独立进程,执行命令行脚本,完成图集生成和切分

Mac平台的shell脚本


./TexturePacker \\
--sheet $3/$1_n.png \\
--data $3/$1_n.txt $2 \\
--format unity \\
--trim-sprite-names \\
--basic-sort-by Name \\
--basic-order Descending \\
--max-size $4 \\
--size-constraints POT \\
--force-squared \\
--border-padding 1 \\
--shape-padding 2 \\
--disable-rotation \\
--trim-mode None \\
--disable-auto-alias \\
--multipack

Windows平台的bat脚本

@echo off
start TexturePacker.exe %2 --sheet %3/%1_n.png --data %3/%1_n.txt %2 ^
--format unity --trim-sprite-names --basic-sort-by Name --basic-order Descending ^
--max-size %4 --size-constraints POT --force-squared --border-padding 1 --shape-padding 2 ^
--disable-rotation --trim-mode None --disable-auto-alias --multipack --extrude 0

unity编辑器脚本


using System.Collections.Generic;
using UnityEngine;
using UnityEditor;
using System.IO;
using System.Diagnostics;
using System;
using System.Text;
using LitJson;
​
public class BuildAtlasToolEditor  
​
  public static string spriteFolder = "Assets/AssetBundleData/Image";
  public static string atlasFolder = "Assets/AssetBundleData/UI/Atlas";
​
​
  [MenuItem("Assets/Build Atlas/Build For Folder")]
  static void BuildForSelectedFolder()
  
    string assetPath = AssetDatabase.GetAssetPath(Selection.activeObject);
    BuildForFolder(assetPath);
  
  [MenuItem("Assets/Build Atlas/Build For Folder", true)]
  static bool ValidateBuildForSelectedFolder()
  
    string assetPath = AssetDatabase.GetAssetPath(Selection.activeObject);
    string[] tempList = assetPath.Split('/');
    if(assetPath.Contains(spriteFolder) &&
       tempList.Length > 1)
    
      return true;
    
    return false;
  
  private static void BuildForFolder(string assetPath)
  
    //将路径切割
    string[] tempList = assetPath.Split('/');
    string atlasName = tempList[tempList.Length - 1];
    string spritePath = Path.Combine(Application.dataPath, assetPath.Replace("Assets/", ""));
    string atlasPath = Path.Combine(Application.dataPath, atlasFolder.Replace("Assets/", ""));
    int size = 1024;
    
    Process process = new Process();
    ProcessStartInfo psi = new ProcessStartInfo();
    psi.UseShellExecute = false;
    psi.RedirectStandardOutput = true;
        psi.RedirectStandardError = true;
        psi.RedirectStandardInput = true;
​
#if UNITY_EDITOR_OSX
    psi.FileName = "/bin/sh";
        psi.WorkingDirectory = Path.Combine(Application.dataPath, "../../Tools/TexturePacker/mac/TexturePacker.app/Contents/MacOS");
    psi.Arguments = Path.Combine(Application.dataPath, "Editor/SpriteEditor/PackTexture.sh")
              + " " + atlasName
            + " " + spritePath
            + " " + atlasPath
            + " " + size;
#elif UNITY_STANDALONE_WIN
        psi.FileName = "PackTexture.bat";
        psi.WorkingDirectory = Path.Combine(Application.dataPath, "../../Tools/TexturePacker/wins/bin");
        psi.Arguments = Path.Combine(Application.dataPath, "Editor/SpriteEditor/PackTexture.bat")
                  + " " + atlasName
                  + " " + spritePath
                  + " " + atlasPath
                  + " " + size;
#endif
        process.StartInfo = psi;
        try
    
            if (process.Start())
      
        string strOutput = process.StandardOutput.ReadToEnd();
                string errorInfo = process.StandardError.ReadToEnd();
        process.WaitForExit();
        process.Close();
                if (!string.IsNullOrEmpty(strOutput)) 
                    Debug.Log("Console outPut: " + strOutput);
                
                if (!string.IsNullOrEmpty(errorInfo))
                
                    Debug.LogError("Console errorInfo: " + errorInfo);
                
            
    
    catch (Exception e)
    
      process.Close();
      UnityEngine.Debug.LogError("========Fail to batch " + atlasName + ":" +e.ToString());
      return;
    
    AssetDatabase.Refresh();
        SplitAtlasSprites(atlasName);
  
​
    static void SplitAtlasSprites(string atlasName)
    
        for (int i = 0; ; i++)
        
            string texturePath = Path.Combine(atlasFolder, atlasName + "_" + i + ".png");
            string textureFullPath = Path.Combine(Application.dataPath, texturePath.Replace("Assets/", ""));
            if (!File.Exists(textureFullPath))
            
                break;
            
            TextureImporter ti = AssetImporter.GetAtPath(texturePath) as TextureImporter;
            ti.textureType = TextureImporterType.Sprite;
            ti.spriteImportMode = SpriteImportMode.Multiple;
            ti.mipmapEnabled = false;
​
            TextureImporterSettings tis = new TextureImporterSettings();
            ti.ReadTextureSettings(tis);
            tis.spriteMeshType = SpriteMeshType.Tight;
            tis.spriteExtrude = 0;
            //tis.alphaSource = TextureImporterAlphaSource.None;  
            ti.SetTextureSettings(tis);
​
            string jsonPath = Path.Combine(atlasFolder, atlasName + "_" + i + ".txt");
            string jsonFullPath = Path.Combine(Application.dataPath, jsonPath.Replace("Assets/", ""));
            string configJson = File.ReadAllText(jsonFullPath, Encoding.UTF8);
            JsonData configJsonData = JsonMapper.ToObject(configJson);
            int textureHeight = int.Parse(configJsonData["meta"]["size"]["h"].ToString());
            JsonData tempJsonData = configJsonData["frames"];
            List<SpriteMetaData> metas = new List<SpriteMetaData>();
            foreach (string name in tempJsonData.Keys)
            
                JsonData frameData = tempJsonData[name]["frame"];
                int x = int.Parse(frameData["x"].ToString());
                int y = int.Parse(frameData["y"].ToString());
                int w = int.Parse(frameData["w"].ToString());
                int h = int.Parse(frameData["h"].ToString());
                SpriteMetaData meta = new SpriteMetaData();
                string subSpritePath = string.Format("Assets/AssetBundleData/UI/0/1.png", atlasName, name);
                Sprite sprite = AssetDatabase.LoadAssetAtPath<Sprite>(subSpritePath);
                if (sprite != null && sprite.border != null)
                
                    UnityEngine.Debug.Log(sprite.border);
                    // meta.border = new Vector4(sprite.border.x, sprite.border.y, sprite.border.w, sprite.border.z);
                    meta.border = sprite.border;
                
                meta.pivot = new Vector2(0.5f, 0.5f);
                meta.alignment = (int)SpriteAlignment.Center;
                meta.rect = new Rect(x, textureHeight - y - h, w, h);
                meta.name = name;
                metas.Add(meta);
            
            ti.spritesheet = metas.ToArray();
            ti.SaveAndReimport();
            AssetDatabase.DeleteAsset(jsonPath);
            //AssetDatabase.Refresh();
        
        //AssetDatabase.Refresh();
    


为了防止误操作,这里对可打图集的资源目录做了限制

	[MenuItem("Assets/Build Atlas/Build For Folder", true)]
	static bool ValidateBuildForSelectedFolder()
	
		string assetPath = AssetDatabase.GetAssetPath(Selection.activeObject);
		string[] tempList = assetPath.Split('/');
		if(assetPath.Contains(spriteFolder) &&
		   tempList.Length > 1)
		
			return true;
		
		return false;
	

以上是关于TexturePacker 图集生成工具的主要内容,如果未能解决你的问题,请参考以下文章

游戏开发小技TexturePacker生成的图集逆向切分成精灵小图(json | python | PIL | TextureUnPacker | 逆向 | 切图)

游戏开发小技TexturePacker生成的图集逆向切分成精灵小图(json | python | PIL | TextureUnPacker | 逆向 | 切图)

游戏开发小技TexturePacker生成的图集逆向切分成精灵小图(json | python | PIL | TextureUnPacker | 逆向 | 切图)

Unity3D-UGUI图集打包与动态使用(TexturePacker)

LibGDX - TexturePacker2不生成/打包图像

unity 图集资源引用查找