2024-10-22 17:38:59 +08:00
|
|
|
|
using UnityEngine;
|
|
|
|
|
using UnityEditor;
|
|
|
|
|
using UnityEngine.TextCore;
|
|
|
|
|
|
|
|
|
|
using TMPro;
|
|
|
|
|
using zbitmapfont;
|
|
|
|
|
using UnityEngine.TextCore.LowLevel;
|
|
|
|
|
using System.Drawing;
|
|
|
|
|
using System.Runtime.InteropServices;
|
|
|
|
|
using zbitmapfont;
|
|
|
|
|
|
|
|
|
|
namespace zbitmapfont
|
|
|
|
|
{
|
|
|
|
|
public static class BitmapFont2TMPro
|
|
|
|
|
{
|
|
|
|
|
static void PatchGlyph(RawCharacterInfo character, int textureHeight, int textureWidth, ref Glyph g)
|
|
|
|
|
{
|
|
|
|
|
var scaleH = textureWidth / textureHeight > 1 ? textureWidth / textureHeight : 1;
|
|
|
|
|
var scaleW = textureHeight / textureWidth > 1 ? textureHeight / textureWidth : 1;
|
|
|
|
|
g.glyphRect = new GlyphRect(
|
|
|
|
|
character.X * scaleW,
|
|
|
|
|
(textureHeight - character.Y - character.Height) * scaleH,
|
|
|
|
|
character.Width * scaleW,
|
|
|
|
|
character.Height * scaleH
|
|
|
|
|
);
|
|
|
|
|
g.metrics = new GlyphMetrics(
|
|
|
|
|
character.Width,
|
|
|
|
|
character.Height,
|
|
|
|
|
character.Xoffset,
|
|
|
|
|
-character.Yoffset,
|
|
|
|
|
character.Xadvance
|
|
|
|
|
);
|
|
|
|
|
}
|
|
|
|
|
|
2024-10-22 18:47:04 +08:00
|
|
|
|
[MenuItem("Assets/zbitmapfont/创建TMP字体")]
|
2024-10-22 17:38:59 +08:00
|
|
|
|
public static void CreateTMP_FontAsset()
|
|
|
|
|
{
|
|
|
|
|
foreach (var a in Selection.assetGUIDs)
|
|
|
|
|
{
|
|
|
|
|
var p = AssetDatabase.GUIDToAssetPath(a);
|
2024-10-22 18:47:04 +08:00
|
|
|
|
|
2024-10-22 17:38:59 +08:00
|
|
|
|
if (System.IO.Directory.Exists(p))
|
|
|
|
|
{
|
|
|
|
|
string destPath = p;
|
|
|
|
|
if (!BitmapFontTool.CreateBitmapFont(p, destPath))
|
|
|
|
|
{
|
|
|
|
|
throw new System.Exception("CreateBitmapFont failed: " + p);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
p += ".fnt";
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (!p.EndsWith(".fnt"))
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (!System.IO.File.Exists(p))
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
Create(p);
|
|
|
|
|
}
|
2024-10-22 18:47:04 +08:00
|
|
|
|
|
2024-10-22 17:38:59 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static void Create(string fntFilePath)
|
|
|
|
|
{
|
|
|
|
|
var pngPath = System.IO.Path.GetDirectoryName(fntFilePath) + "/" + System.IO.Path.GetFileNameWithoutExtension(fntFilePath) + "_0.png";
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
Texture2D m_FontAtlasTexture = AssetDatabase.LoadAssetAtPath<Texture2D>(pngPath);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
var assetPath = System.IO.Path.GetDirectoryName(fntFilePath) + "/" + System.IO.Path.GetFileNameWithoutExtension(fntFilePath) + ".asset";
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
var tex_FileName = System.IO.Path.GetFileNameWithoutExtension(assetPath);
|
|
|
|
|
|
|
|
|
|
//Debug.Log("Creating TextMeshPro font asset!");
|
|
|
|
|
|
|
|
|
|
var fontAsset = AssetDatabase.LoadAssetAtPath<TMP_FontAsset>(assetPath);
|
|
|
|
|
if (fontAsset == null)
|
|
|
|
|
{
|
|
|
|
|
fontAsset = ScriptableObject.CreateInstance<TMP_FontAsset>(); // Create new TextMeshPro Font Asset.
|
|
|
|
|
AssetDatabase.CreateAsset(fontAsset, assetPath);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Set version number of font asset
|
|
|
|
|
//fontAsset.version = "1.1.0";
|
|
|
|
|
|
|
|
|
|
//Set Font Asset Type
|
|
|
|
|
//fontAsset.atlasRenderMode = GlyphRenderMode.RASTER;
|
|
|
|
|
|
|
|
|
|
// Reference to the source font file GUID.
|
|
|
|
|
//fontAsset.m_SourceFontFile_EditorRef = m_DestinationFontFile.sourceFontFile;
|
|
|
|
|
//fontAsset.m_SourceFontFileGUID = AssetDatabase.AssetPathToGUID(AssetDatabase.GetAssetPath(m_DestinationFontFile.sourceFontFile));
|
|
|
|
|
|
|
|
|
|
// Add FaceInfo to Font Asset
|
|
|
|
|
//fontAsset.faceInfo = m_FaceInfo;
|
|
|
|
|
|
|
|
|
|
//// Add GlyphInfo[] to Font Asset
|
|
|
|
|
//fontAsset.glyphTable = m_FontGlyphTable;
|
|
|
|
|
|
|
|
|
|
//// Add CharacterTable[] to font asset.
|
|
|
|
|
//fontAsset.characterTable = m_FontCharacterTable;
|
|
|
|
|
|
|
|
|
|
//// Sort glyph and character tables.
|
|
|
|
|
//fontAsset.SortAllTables();
|
|
|
|
|
|
|
|
|
|
//// Get and Add Kerning Pairs to Font Asset
|
|
|
|
|
//if (m_IncludeFontFeatures)
|
|
|
|
|
// fontAsset.fontFeatureTable = GetKerningTable();
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Add Font Atlas as Sub-Asset
|
|
|
|
|
fontAsset.atlasTextures = new Texture2D[] { m_FontAtlasTexture };
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//fontAsset.atlasWidth = m_FontAtlasTexture.width;
|
|
|
|
|
//fontAsset.atlasHeight = m_FontAtlasTexture.height;
|
|
|
|
|
//fontAsset.atlasPadding = m_Padding;
|
|
|
|
|
|
|
|
|
|
//AssetDatabase.AddObjectToAsset(m_FontAtlasTexture, fontAsset);
|
|
|
|
|
|
|
|
|
|
// Create new Material and Add it as Sub-Asset
|
|
|
|
|
Shader default_Shader = Shader.Find("TextMeshPro/Bitmap Custom Atlas"); // m_shaderSelection;
|
|
|
|
|
Material tmp_material = AssetDatabase.LoadAssetAtPath<Material>(assetPath);
|
|
|
|
|
if (tmp_material == null)
|
|
|
|
|
{
|
|
|
|
|
tmp_material = new Material(default_Shader);
|
|
|
|
|
tmp_material.name = tex_FileName + " Material";
|
|
|
|
|
fontAsset.material = tmp_material;
|
|
|
|
|
AssetDatabase.AddObjectToAsset(tmp_material, fontAsset);
|
|
|
|
|
}
|
|
|
|
|
tmp_material.SetTexture(ShaderUtilities.ID_MainTex, m_FontAtlasTexture);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
fontAsset.GetType().GetProperty("version").SetValue(fontAsset, "1.1.0");
|
|
|
|
|
|
|
|
|
|
fontAsset.GetType().GetProperty("atlasRenderMode").SetValue(fontAsset, (int)GlyphRenderMode.RASTER);
|
|
|
|
|
|
|
|
|
|
//fontAsset.GetType().GetProperty("faceInfo").SetValue(fontAsset, m_DestinationFontFile.faceInfo);
|
|
|
|
|
|
|
|
|
|
fontAsset.GetType().GetProperty("atlasWidth").SetValue(fontAsset, m_FontAtlasTexture.width);
|
|
|
|
|
fontAsset.GetType().GetProperty("atlasHeight").SetValue(fontAsset, m_FontAtlasTexture.height);
|
|
|
|
|
fontAsset.GetType().GetProperty("atlasPadding").SetValue(fontAsset, 1);
|
|
|
|
|
|
|
|
|
|
//fontAsset.GetType().GetField("m_SourceFontFile_EditorRef", System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.NonPublic).SetValue(fontAsset, m_DestinationFontFile.sourceFontFile);
|
|
|
|
|
|
|
|
|
|
//fontAsset.GetType().GetField("m_SourceFontFileGUID", System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.NonPublic).SetValue(fontAsset, AssetDatabase.AssetPathToGUID(AssetDatabase.GetAssetPath(m_DestinationFontFile.sourceFontFile)));
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
var fontFile = fontAsset;
|
|
|
|
|
var fnt = FntParse.GetFntParse(System.IO.File.ReadAllText(fntFilePath));
|
|
|
|
|
fontFile.characterTable.Clear();
|
|
|
|
|
//fontFile.characterLookupTable.Clear();
|
|
|
|
|
fontFile.glyphTable.Clear();
|
|
|
|
|
//fontFile.glyphLookupTable.Clear();
|
|
|
|
|
for (uint j = 0; j < fnt.charInfos.Length; j++)
|
|
|
|
|
{
|
|
|
|
|
var c = fnt.charInfos[j];
|
|
|
|
|
var a = new TMP_Character();
|
|
|
|
|
a.unicode = (uint)c.index;
|
|
|
|
|
a.glyphIndex = j;
|
|
|
|
|
|
|
|
|
|
a.textAsset = fontFile;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
var glyph = new Glyph();
|
|
|
|
|
PatchGlyph(fnt.rawCharInfos[j],
|
|
|
|
|
fnt.textureHeight,
|
|
|
|
|
fnt.textureWidth,
|
|
|
|
|
ref glyph);
|
|
|
|
|
|
|
|
|
|
glyph.index = j;
|
|
|
|
|
glyph.atlasIndex = 0;
|
|
|
|
|
|
|
|
|
|
a.glyph = glyph;
|
|
|
|
|
|
|
|
|
|
fontFile.characterTable.Add(a);
|
|
|
|
|
//fontFile.characterLookupTable.Add(a.unicode, a);
|
|
|
|
|
|
|
|
|
|
fontFile.glyphTable.Add(glyph);
|
|
|
|
|
//fontFile.glyphLookupTable.Add(j, glyph);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
fontAsset.GetType().GetMethod("SortAllTables", System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.NonPublic).Invoke(fontAsset, null);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
var maxHeight = 0;
|
|
|
|
|
for (int j = 0; j < fnt.charInfos.Length; j++)
|
|
|
|
|
{
|
|
|
|
|
maxHeight = Mathf.Max(maxHeight, Mathf.Abs(fnt.charInfos[j].minY - fnt.charInfos[j].maxY));
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
var newFaceInfo = fontFile.faceInfo;
|
|
|
|
|
//newFaceInfo.baseline = fnt.lineBaseHeight;
|
|
|
|
|
//newFaceInfo.lineHeight = fnt.lineHeight;
|
|
|
|
|
//newFaceInfo.ascentLine = fnt.lineHeight;
|
|
|
|
|
|
|
|
|
|
newFaceInfo.baseline = 0;
|
|
|
|
|
newFaceInfo.lineHeight = maxHeight;
|
|
|
|
|
newFaceInfo.ascentLine = 0;
|
|
|
|
|
newFaceInfo.pointSize = fnt.fontSize;
|
|
|
|
|
|
|
|
|
|
newFaceInfo.descentLine = -maxHeight;
|
|
|
|
|
|
|
|
|
|
var fontType = typeof(TMP_FontAsset);
|
|
|
|
|
var faceInfoProperty = fontType.GetProperty("faceInfo");
|
|
|
|
|
faceInfoProperty.SetValue(fontFile, newFaceInfo);
|
|
|
|
|
|
|
|
|
|
AssetDatabase.Refresh();
|
|
|
|
|
AssetDatabase.ImportAsset(assetPath, ImportAssetOptions.ForceUpdate);
|
|
|
|
|
AssetDatabase.SaveAssets();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|