fix: 修复 Unity 环境背景和字体问题
- 添加 Environment 对象和 EnvironmentManager 组件到场景 - 重新生成 SourceHanSansSC-Regular SDF 字体资产 - 添加 FixTMPFont 和 RegenerateChineseFont 编辑器工具
This commit is contained in:
101
unity-client/Assets/Editor/FixTMPFont.cs
Normal file
101
unity-client/Assets/Editor/FixTMPFont.cs
Normal file
@@ -0,0 +1,101 @@
|
|||||||
|
using UnityEngine;
|
||||||
|
using UnityEditor;
|
||||||
|
using TMPro;
|
||||||
|
|
||||||
|
public class FixTMPFont : EditorWindow
|
||||||
|
{
|
||||||
|
[MenuItem("Tools/Fix TMP Font Assets")]
|
||||||
|
public static void FixFonts()
|
||||||
|
{
|
||||||
|
// Find all TMP font assets
|
||||||
|
string[] guids = AssetDatabase.FindAssets("t:TMP_FontAsset");
|
||||||
|
int fixedCount = 0;
|
||||||
|
|
||||||
|
foreach (string guid in guids)
|
||||||
|
{
|
||||||
|
string path = AssetDatabase.GUIDToAssetPath(guid);
|
||||||
|
TMP_FontAsset font = AssetDatabase.LoadAssetAtPath<TMP_FontAsset>(path);
|
||||||
|
|
||||||
|
if (font == null) continue;
|
||||||
|
|
||||||
|
bool needsSave = false;
|
||||||
|
|
||||||
|
// Check if material is missing
|
||||||
|
if (font.material == null)
|
||||||
|
{
|
||||||
|
Debug.LogWarning($"[FixTMPFont] Font '{font.name}' has missing material. Attempting to fix...");
|
||||||
|
|
||||||
|
// Try to find a sub-asset material
|
||||||
|
Object[] subAssets = AssetDatabase.LoadAllAssetRepresentationsAtPath(path);
|
||||||
|
foreach (Object subAsset in subAssets)
|
||||||
|
{
|
||||||
|
if (subAsset is Material mat)
|
||||||
|
{
|
||||||
|
Debug.Log($"[FixTMPFont] Found sub-asset material: {mat.name}");
|
||||||
|
font.material = mat;
|
||||||
|
needsSave = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// If still no material, create one
|
||||||
|
if (font.material == null && font.atlasTexture != null)
|
||||||
|
{
|
||||||
|
Debug.Log($"[FixTMPFont] Creating new material for '{font.name}'");
|
||||||
|
Shader shader = Shader.Find("TextMeshPro/Distance Field");
|
||||||
|
if (shader != null)
|
||||||
|
{
|
||||||
|
Material newMat = new Material(shader);
|
||||||
|
newMat.name = font.name + " Atlas Material";
|
||||||
|
newMat.SetTexture("_MainTex", font.atlasTexture);
|
||||||
|
AssetDatabase.AddObjectToAsset(newMat, font);
|
||||||
|
font.material = newMat;
|
||||||
|
needsSave = true;
|
||||||
|
Debug.Log($"[FixTMPFont] Created and assigned new material for '{font.name}'");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Debug.LogError("[FixTMPFont] Could not find TextMeshPro/Distance Field shader!");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Verify atlas texture
|
||||||
|
if (font.atlasTexture == null)
|
||||||
|
{
|
||||||
|
Debug.LogError($"[FixTMPFont] Font '{font.name}' has no atlas texture - needs to be regenerated!");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (needsSave)
|
||||||
|
{
|
||||||
|
EditorUtility.SetDirty(font);
|
||||||
|
fixedCount++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
AssetDatabase.SaveAssets();
|
||||||
|
AssetDatabase.Refresh();
|
||||||
|
|
||||||
|
Debug.Log($"[FixTMPFont] Done! Fixed {fixedCount} font asset(s).");
|
||||||
|
EditorUtility.DisplayDialog("Fix TMP Fonts", $"Fixed {fixedCount} font asset(s). Check console for details.", "OK");
|
||||||
|
}
|
||||||
|
|
||||||
|
[MenuItem("Tools/Regenerate Chinese Font")]
|
||||||
|
public static void RegenerateChinese()
|
||||||
|
{
|
||||||
|
string fontPath = "Assets/Fonts/SourceHanSansSC-Regular.otf";
|
||||||
|
Font sourceFont = AssetDatabase.LoadAssetAtPath<Font>(fontPath);
|
||||||
|
|
||||||
|
if (sourceFont == null)
|
||||||
|
{
|
||||||
|
Debug.LogError($"[FixTMPFont] Could not load font at '{fontPath}'");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Debug.Log($"[FixTMPFont] Source font loaded: {sourceFont.name}");
|
||||||
|
Debug.Log("[FixTMPFont] Please use Window > TextMeshPro > Font Asset Creator to regenerate the font.");
|
||||||
|
|
||||||
|
// Open the Font Asset Creator
|
||||||
|
EditorApplication.ExecuteMenuItem("Window/TextMeshPro/Font Asset Creator");
|
||||||
|
}
|
||||||
|
}
|
||||||
2
unity-client/Assets/Editor/FixTMPFont.cs.meta
Normal file
2
unity-client/Assets/Editor/FixTMPFont.cs.meta
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 6708bf6d0bfc548ce85411093037126b
|
||||||
98
unity-client/Assets/Editor/RegenerateChineseFont.cs
Normal file
98
unity-client/Assets/Editor/RegenerateChineseFont.cs
Normal file
@@ -0,0 +1,98 @@
|
|||||||
|
using UnityEngine;
|
||||||
|
using UnityEditor;
|
||||||
|
using TMPro;
|
||||||
|
using System.IO;
|
||||||
|
|
||||||
|
public class RegenerateChineseFont : EditorWindow
|
||||||
|
{
|
||||||
|
[MenuItem("Tools/Regenerate Chinese Font Asset")]
|
||||||
|
public static void Regenerate()
|
||||||
|
{
|
||||||
|
string sourceFontPath = "Assets/Fonts/SourceHanSansSC-Regular.otf";
|
||||||
|
string outputPath = "Assets/Fonts/SourceHanSansSC-Regular SDF.asset";
|
||||||
|
|
||||||
|
// Load source font
|
||||||
|
Font sourceFont = AssetDatabase.LoadAssetAtPath<Font>(sourceFontPath);
|
||||||
|
if (sourceFont == null)
|
||||||
|
{
|
||||||
|
Debug.LogError($"[RegenerateFont] Source font not found at: {sourceFontPath}");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Debug.Log($"[RegenerateFont] Loaded source font: {sourceFont.name}");
|
||||||
|
|
||||||
|
// Create font asset using TMP's API
|
||||||
|
TMP_FontAsset fontAsset = TMP_FontAsset.CreateFontAsset(sourceFont);
|
||||||
|
|
||||||
|
if (fontAsset == null)
|
||||||
|
{
|
||||||
|
Debug.LogError("[RegenerateFont] Failed to create font asset!");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Configure the font asset for Chinese characters
|
||||||
|
fontAsset.name = "SourceHanSansSC-Regular SDF";
|
||||||
|
|
||||||
|
// Save the asset
|
||||||
|
if (File.Exists(outputPath))
|
||||||
|
{
|
||||||
|
AssetDatabase.DeleteAsset(outputPath);
|
||||||
|
}
|
||||||
|
|
||||||
|
AssetDatabase.CreateAsset(fontAsset, outputPath);
|
||||||
|
|
||||||
|
// Save the atlas texture as a sub-asset
|
||||||
|
if (fontAsset.atlasTexture != null)
|
||||||
|
{
|
||||||
|
fontAsset.atlasTexture.name = "SourceHanSansSC-Regular SDF Atlas";
|
||||||
|
AssetDatabase.AddObjectToAsset(fontAsset.atlasTexture, fontAsset);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Save the material as a sub-asset
|
||||||
|
if (fontAsset.material != null)
|
||||||
|
{
|
||||||
|
fontAsset.material.name = "SourceHanSansSC-Regular SDF Material";
|
||||||
|
AssetDatabase.AddObjectToAsset(fontAsset.material, fontAsset);
|
||||||
|
}
|
||||||
|
|
||||||
|
AssetDatabase.SaveAssets();
|
||||||
|
AssetDatabase.Refresh();
|
||||||
|
|
||||||
|
Debug.Log($"[RegenerateFont] Font asset created successfully at: {outputPath}");
|
||||||
|
|
||||||
|
// Setup as fallback for TMP Settings
|
||||||
|
SetupFallbackFont(fontAsset);
|
||||||
|
|
||||||
|
EditorUtility.DisplayDialog("Regenerate Font",
|
||||||
|
"Chinese font asset regenerated successfully!\n\nNote: For full Chinese character support, use Window > TextMeshPro > Font Asset Creator to generate with a specific character set.",
|
||||||
|
"OK");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void SetupFallbackFont(TMP_FontAsset chineseFont)
|
||||||
|
{
|
||||||
|
// Get TMP Settings
|
||||||
|
string settingsPath = "Assets/TextMesh Pro/Resources/TMP Settings.asset";
|
||||||
|
TMP_Settings settings = AssetDatabase.LoadAssetAtPath<TMP_Settings>(settingsPath);
|
||||||
|
|
||||||
|
if (settings == null)
|
||||||
|
{
|
||||||
|
Debug.LogWarning("[RegenerateFont] TMP Settings not found. Skipping fallback setup.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Add Chinese font as fallback to default font
|
||||||
|
string defaultFontPath = "Assets/TextMesh Pro/Resources/Fonts & Materials/LiberationSans SDF.asset";
|
||||||
|
TMP_FontAsset defaultFont = AssetDatabase.LoadAssetAtPath<TMP_FontAsset>(defaultFontPath);
|
||||||
|
|
||||||
|
if (defaultFont != null && defaultFont.fallbackFontAssetTable != null)
|
||||||
|
{
|
||||||
|
if (!defaultFont.fallbackFontAssetTable.Contains(chineseFont))
|
||||||
|
{
|
||||||
|
defaultFont.fallbackFontAssetTable.Add(chineseFont);
|
||||||
|
EditorUtility.SetDirty(defaultFont);
|
||||||
|
AssetDatabase.SaveAssets();
|
||||||
|
Debug.Log("[RegenerateFont] Added Chinese font as fallback to default font.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
2
unity-client/Assets/Editor/RegenerateChineseFont.cs.meta
Normal file
2
unity-client/Assets/Editor/RegenerateChineseFont.cs.meta
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
fileFormatVersion: 2
|
||||||
|
guid: 5a690ec5d70524b1bbf892548be212bd
|
||||||
File diff suppressed because one or more lines are too long
@@ -7972,6 +7972,11 @@ MonoBehaviour:
|
|||||||
m_ShouldReimportFontFeatures: 0
|
m_ShouldReimportFontFeatures: 0
|
||||||
m_FallbackFontAssetTable:
|
m_FallbackFontAssetTable:
|
||||||
- {fileID: 11400000, guid: 2e498d1c8094910479dc3e1b768306a4, type: 2}
|
- {fileID: 11400000, guid: 2e498d1c8094910479dc3e1b768306a4, type: 2}
|
||||||
|
- {fileID: 0}
|
||||||
|
- {fileID: 0}
|
||||||
|
- {fileID: 0}
|
||||||
|
- {fileID: 0}
|
||||||
|
- {fileID: 0}
|
||||||
- {fileID: 11400000, guid: 05d7311017e2a4618aeb1598563375bc, type: 2}
|
- {fileID: 11400000, guid: 05d7311017e2a4618aeb1598563375bc, type: 2}
|
||||||
m_FontWeightTable:
|
m_FontWeightTable:
|
||||||
- regularTypeface: {fileID: 0}
|
- regularTypeface: {fileID: 0}
|
||||||
|
|||||||
@@ -119,6 +119,73 @@ NavMeshSettings:
|
|||||||
debug:
|
debug:
|
||||||
m_Flags: 0
|
m_Flags: 0
|
||||||
m_NavMeshData: {fileID: 0}
|
m_NavMeshData: {fileID: 0}
|
||||||
|
--- !u!1 &318018866
|
||||||
|
GameObject:
|
||||||
|
m_ObjectHideFlags: 0
|
||||||
|
m_CorrespondingSourceObject: {fileID: 0}
|
||||||
|
m_PrefabInstance: {fileID: 0}
|
||||||
|
m_PrefabAsset: {fileID: 0}
|
||||||
|
serializedVersion: 6
|
||||||
|
m_Component:
|
||||||
|
- component: {fileID: 318018868}
|
||||||
|
- component: {fileID: 318018867}
|
||||||
|
m_Layer: 0
|
||||||
|
m_Name: Environment
|
||||||
|
m_TagString: Untagged
|
||||||
|
m_Icon: {fileID: 0}
|
||||||
|
m_NavMeshLayer: 0
|
||||||
|
m_StaticEditorFlags: 0
|
||||||
|
m_IsActive: 1
|
||||||
|
--- !u!114 &318018867
|
||||||
|
MonoBehaviour:
|
||||||
|
m_ObjectHideFlags: 0
|
||||||
|
m_CorrespondingSourceObject: {fileID: 0}
|
||||||
|
m_PrefabInstance: {fileID: 0}
|
||||||
|
m_PrefabAsset: {fileID: 0}
|
||||||
|
m_GameObject: {fileID: 318018866}
|
||||||
|
m_Enabled: 1
|
||||||
|
m_EditorHideFlags: 0
|
||||||
|
m_Script: {fileID: 11500000, guid: 6aa9102a04d7544619ec0187e065eda9, type: 3}
|
||||||
|
m_Name:
|
||||||
|
m_EditorClassIdentifier: Assembly-CSharp::TheIsland.Visual.EnvironmentManager
|
||||||
|
dawnSkyTop: {r: 0.98, g: 0.65, b: 0.45, a: 1}
|
||||||
|
dawnSkyBottom: {r: 1, g: 0.85, b: 0.6, a: 1}
|
||||||
|
dawnAmbient: {r: 1, g: 0.8, b: 0.6, a: 1}
|
||||||
|
daySkyTop: {r: 0.4, g: 0.7, b: 1, a: 1}
|
||||||
|
daySkyBottom: {r: 0.7, g: 0.9, b: 1, a: 1}
|
||||||
|
dayAmbient: {r: 1, g: 1, b: 0.95, a: 1}
|
||||||
|
duskSkyTop: {r: 0.3, g: 0.2, b: 0.5, a: 1}
|
||||||
|
duskSkyBottom: {r: 1, g: 0.5, b: 0.3, a: 1}
|
||||||
|
duskAmbient: {r: 1, g: 0.6, b: 0.4, a: 1}
|
||||||
|
nightSkyTop: {r: 0.05, g: 0.05, b: 0.15, a: 1}
|
||||||
|
nightSkyBottom: {r: 0.1, g: 0.15, b: 0.3, a: 1}
|
||||||
|
nightAmbient: {r: 0.3, g: 0.35, b: 0.5, a: 1}
|
||||||
|
cloudyTint: {r: 0.7, g: 0.7, b: 0.75, a: 1}
|
||||||
|
rainyTint: {r: 0.5, g: 0.55, b: 0.6, a: 1}
|
||||||
|
stormyTint: {r: 0.35, g: 0.35, b: 0.4, a: 1}
|
||||||
|
foggyTint: {r: 0.8, g: 0.8, b: 0.85, a: 1}
|
||||||
|
hotTint: {r: 1.1, g: 0.95, b: 0.85, a: 1}
|
||||||
|
sandColor: {r: 0.95, g: 0.87, b: 0.7, a: 1}
|
||||||
|
sandDarkColor: {r: 0.8, g: 0.7, b: 0.5, a: 1}
|
||||||
|
waterShallowColor: {r: 0.3, g: 0.8, b: 0.9, a: 0.8}
|
||||||
|
waterDeepColor: {r: 0.1, g: 0.4, b: 0.6, a: 0.9}
|
||||||
|
waveSpeed: 0.5
|
||||||
|
waveAmplitude: 0.1
|
||||||
|
--- !u!4 &318018868
|
||||||
|
Transform:
|
||||||
|
m_ObjectHideFlags: 0
|
||||||
|
m_CorrespondingSourceObject: {fileID: 0}
|
||||||
|
m_PrefabInstance: {fileID: 0}
|
||||||
|
m_PrefabAsset: {fileID: 0}
|
||||||
|
m_GameObject: {fileID: 318018866}
|
||||||
|
serializedVersion: 2
|
||||||
|
m_LocalRotation: {x: 0, y: 0, z: 0, w: 1}
|
||||||
|
m_LocalPosition: {x: 0, y: 0, z: 0}
|
||||||
|
m_LocalScale: {x: 1, y: 1, z: 1}
|
||||||
|
m_ConstrainProportionsScale: 0
|
||||||
|
m_Children: []
|
||||||
|
m_Father: {fileID: 0}
|
||||||
|
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
|
||||||
--- !u!1 &851065943
|
--- !u!1 &851065943
|
||||||
GameObject:
|
GameObject:
|
||||||
m_ObjectHideFlags: 0
|
m_ObjectHideFlags: 0
|
||||||
@@ -429,3 +496,4 @@ SceneRoots:
|
|||||||
- {fileID: 1918023635}
|
- {fileID: 1918023635}
|
||||||
- {fileID: 851065944}
|
- {fileID: 851065944}
|
||||||
- {fileID: 1562380643}
|
- {fileID: 1562380643}
|
||||||
|
- {fileID: 318018868}
|
||||||
|
|||||||
Reference in New Issue
Block a user