Merge branch 'develop' of ssh://git.pthub.vn:3222/Unity/perfect-world-unity into fix-ui

This commit is contained in:
Chomper9981
2026-04-06 15:41:17 +07:00
85 changed files with 79046 additions and 141 deletions
@@ -9743,6 +9743,7 @@ MonoBehaviour:
currentTargetNPCID: 0
dialogResouce: {fileID: 11400000, guid: 540bc8e61556ba4479407a2d68e17580, type: 2}
canvasDlg: {fileID: 7894129013412138377}
_emotionLibrarySpriteMap: {fileID: 11400000, guid: f634ecf63ca3d004f82af9b17c966fc9, type: 2}
btnSecondClick: {fileID: 1330222957695115484}
m_pDlgQuickBar1: {fileID: 8338623026378970694}
ChangeSkillShortcutButton: {fileID: 335905991743982376}
+2 -2
View File
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:7245ad76b42e0f3f97f2cc7990d79ff171b5f78e64bad057b5acae21bed80395
size 321521
oid sha256:543e09f5571b2d48dd57646eee06f8efbc71e6aaa62d6e8a98a529dec44b7364
size 322591
@@ -37,7 +37,7 @@ MonoBehaviour:
prefix:
- channel: 1
iconName:
icon: {fileID: 0}
icon: {fileID: 21300000, guid: 4c42fa6e60df2184fa1a7d606bdbac8c, type: 3}
prefix: '!@'
- channel: 7
iconName:
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 3011939e4e9c0ce4e83bc03a748fcf96
NativeFormatImporter:
externalObjects: {}
mainObjectFileID: 11400000
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,18 @@
%YAML 1.1
%TAG !u! tag:unity3d.com,2011:
--- !u!114 &11400000
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 0}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: af2fa24fb63c4aa45bb99a711c857114, type: 3}
m_Name: EmotionLibrarySpriteMap
m_EditorClassIdentifier:
Library: {fileID: 11400000, guid: 3011939e4e9c0ce4e83bc03a748fcf96, type: 2}
TmpSpriteAsset: {fileID: 11400000, guid: c41005c129ba4d66911b75229fd70b45, type: 2}
PreferSpriteNameTag: 1
DefaultAnimFps: 10
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: f634ecf63ca3d004f82af9b17c966fc9
NativeFormatImporter:
externalObjects: {}
mainObjectFileID: 11400000
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,49 @@
using CSNetwork;
namespace BrewMonster.Scripts.Chat
{
/// <summary>
/// Chat 表情与内联富文本 — Emotion set + TMP conversion for chat (ported from CECGameUIMan::AddChatMessage).
/// Keeps channel emotion filtering and Unmarshal/Convert-to-TMP in one place.
/// </summary>
public sealed class ChatEmotionDisplayPipeline
{
private IEmotionSpriteMap _spriteMap = new StubEmotionSpriteMap();
public ChatEmotionDisplayPipeline(IEmotionSpriteMap spriteMap = null)
{
if (spriteMap != null)
_spriteMap = spriteMap;
}
public void SetSpriteMap(IEmotionSpriteMap spriteMap)
{
_spriteMap = spriteMap ?? new StubEmotionSpriteMap();
}
/// <summary>C++: FilterEmotionSet — map inline emotion codes to the correct set for this channel.</summary>
public string ApplyChannelEmotionFilter(string pszMsg, int cEmotion)
{
return AUICommon.FilterEmotionSet(pszMsg, cEmotion);
}
/// <summary>
/// TMP: Unmarshal edit-box item codes and convert emotion / coord / inventory links to TMP rich text.
/// Call after <see cref="CECUIManager.FilterBadWords"/> when the message is from a player channel.
/// </summary>
public string ConvertInlineItemsToTmp(string pszMsgAfterBadWordFilter)
{
EditBoxItemsSet itemsSet = new EditBoxItemsSet();
string displayText = AUICommon.UnmarshalEditBoxText(pszMsgAfterBadWordFilter, itemsSet);
if (itemsSet.GetItemCount() <= 0)
return pszMsgAfterBadWordFilter;
string tmpText = displayText;
tmpText = AUICommon.ConvertEmotionsToTMP(tmpText, itemsSet, _spriteMap);
tmpText = AUICommon.ConvertCoordsToTMP(tmpText, itemsSet);
tmpText = AUICommon.ConvertIvtrItemsToTMP(tmpText, itemsSet);
tmpText = AUICommon.StripRemainingItemCodes(tmpText);
return tmpText;
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 017020ee87cf87d40abfd39726e185c0
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: b434da58bb8623f439f5cbf37342f155
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,32 @@
using System;
using UnityEngine;
namespace BrewMonster.Scripts.Chat.EmotionData
{
/// <summary>
/// Một dòng định nghĩa emotion trong Emotions{N}.txt (port từ AUITEXTAREA_EMOTION).
/// One emotion definition line from Emotions{N}.txt (ported from AUITEXTAREA_EMOTION).
/// </summary>
[Serializable]
public class EmotionEntryData
{
[Tooltip("Chỉ số ô bắt đầu trong lưới cell (nStartPos) — Starting cell index in the atlas grid.")]
public int StartPos;
[Tooltip("Số frame animation (nNumFrames), tối đa 20 như C++.")]
public int NumFrames;
[Tooltip("Tooltip / hint text từ file txt.")]
public string Hint = "";
/// <summary>
/// Thời điểm tick cho từng frame (nFrameTick[i]), độ dài = NumFrames.
/// </summary>
public int[] FrameTicks = Array.Empty<int>();
/// <summary>
/// Sprite đã cắt cho từng frame (gán bởi tool), độ dài = NumFrames khi đã convert.
/// </summary>
public Sprite[] FrameSprites = Array.Empty<Sprite>();
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: a0e42b4b83e3a6f40a2a7737f584fdc6
@@ -0,0 +1,44 @@
using System;
using System.Collections.Generic;
using UnityEngine;
namespace BrewMonster.Scripts.Chat.EmotionData
{
/// <summary>
/// Snapshot một bộ Emotions{N} (dùng embed trong EmotionLibrarySO hoặc copy sang EmotionSetDataSO).
/// One Emotions{N} snapshot (embedded in EmotionLibrarySO or copied to EmotionSetDataSO).
/// </summary>
[Serializable]
public class EmotionSetSnapshot
{
public int EmotionSetIndex;
public int CellWidth = 32;
public int CellHeight = 32;
public Texture2D SourceAtlas;
public string SourceTxtAssetPath = "";
public List<EmotionEntryData> Entries = new List<EmotionEntryData>();
}
/// <summary>
/// Một ScriptableObject chứa nhiều bộ emotion (vd. emotions0emotions7).
/// Single SO holding multiple emotion sets (e.g. all 8 atlases).
/// </summary>
[CreateAssetMenu(fileName = "EmotionLibrary", menuName = "Perfect World/Chat/Emotion Library (All Sets)", order = 1)]
public class EmotionLibrarySO : ScriptableObject
{
[Tooltip("Danh sách các bộ theo EmotionSetIndex (0,1,2,…).")]
public List<EmotionSetSnapshot> Sets = new List<EmotionSetSnapshot>();
public EmotionSetSnapshot GetSetOrNull(int emotionSetIndex)
{
if (Sets == null) return null;
foreach (var s in Sets)
{
if (s != null && s.EmotionSetIndex == emotionSetIndex)
return s;
}
return null;
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 3805edc4ea793a54eabafdd3e7e48581
@@ -0,0 +1,123 @@
using System;
using TMPro;
using UnityEngine;
namespace BrewMonster.Scripts.Chat.EmotionData
{
/// <summary>
/// Ánh xạ (emotionSet, emotionIndex) từ <see cref="EmotionLibrarySO"/> sang tag TMP.
/// Gán asset này vào <see cref="CECUIManager"/> (field emotion) — <see cref="BrewMonster.UI.CECGameUIMan"/> không phải MonoBehaviour nên không kéo SO trên Inspector được.
///
/// Cách dùng:
/// 1) Tạo <see cref="EmotionLibrarySO"/> bằng Emotion Atlas Converter.
/// 2) Tạo <see cref="TMP_SpriteAsset"/> từ cùng atlas (Window → TextMeshPro → Sprite Importer),
/// đảm bảo tên sub-sprite khớp (vd. cell_0000) với atlas Multiple từ tool.
/// 3) Gán TMP_SpriteAsset vào ô chat <see cref="TMPro.TextMeshProUGUI"/> (Sprite Asset / Additional).
/// 4) Kéo SO này vào field trên GameObject có <see cref="CECUIManager"/> (Awake gọi SetEmotionSpriteMap).
/// </summary>
[CreateAssetMenu(fileName = "EmotionLibrarySpriteMap", menuName = "Perfect World/Chat/Emotion Library Sprite Map", order = 2)]
public class EmotionLibrarySpriteMap : ScriptableObject, IEmotionSpriteMap
{
[Tooltip("Dữ liệu emotion đã convert (Entries + FrameSprites).")]
public EmotionLibrarySO Library;
[Tooltip("Sprite Asset dùng cho chat TMP — cùng tên sub-sprite với atlas (cell_XXXX). Bắt buộc cho emoji động (anim) hoặc khi không dùng name tag.")]
public TMP_SpriteAsset TmpSpriteAsset;
[Tooltip("Nếu true và chỉ 1 frame: thử <sprite name=\"...\"> (không cần tra index). Động (nhiều frame) vẫn cần TmpSpriteAsset để tra index.")]
public bool PreferSpriteNameTag = true;
[Tooltip("FPS mặc định cho <sprite anim> khi không suy ra được từ FrameTicks.")]
public int DefaultAnimFps = 10;
public bool TryGetSprite(int emotionSet, int emotionIndex, out EmotionSpriteInfo info)
{
info = default;
if (Library == null)
return false;
EmotionSetSnapshot set = Library.GetSetOrNull(emotionSet);
if (set == null || emotionIndex < 0 || emotionIndex >= set.Entries.Count)
return false;
EmotionEntryData entry = set.Entries[emotionIndex];
Sprite[] frames = entry.FrameSprites;
if (frames == null || frames.Length == 0)
return false;
if (frames.Length == 1)
{
Sprite s0 = frames[0];
if (s0 == null)
return false;
if (PreferSpriteNameTag && !string.IsNullOrEmpty(s0.name))
{
info = new EmotionSpriteInfo
{
UseSpriteName = true,
SpriteName = s0.name,
IsAnimated = false
};
return true;
}
int idx = FindSpriteIndexInTmpAsset(s0.name);
if (idx < 0)
return false;
info = new EmotionSpriteInfo { SpriteIndex = idx, IsAnimated = false };
return true;
}
if (TmpSpriteAsset == null)
return false;
int start = FindSpriteIndexInTmpAsset(frames[0]?.name);
int end = FindSpriteIndexInTmpAsset(frames[frames.Length - 1]?.name);
if (start < 0 || end < 0)
return false;
int fps = EstimateFps(entry.FrameTicks, frames.Length);
info = new EmotionSpriteInfo
{
SpriteIndex = start,
IsAnimated = true,
AnimEndFrame = end,
AnimFPS = fps > 0 ? fps : DefaultAnimFps
};
return true;
}
private int FindSpriteIndexInTmpAsset(string spriteName)
{
if (TmpSpriteAsset == null || string.IsNullOrEmpty(spriteName))
return -1;
if (TmpSpriteAsset.spriteInfoList != null)
{
for (int i = 0; i < TmpSpriteAsset.spriteInfoList.Count; i++)
{
var s = TmpSpriteAsset.spriteInfoList[i];
if (s != null && s.name == spriteName)
return i;
}
}
return -1;
}
private static int EstimateFps(int[] frameTicks, int numFrames)
{
if (frameTicks == null || numFrames < 2 || frameTicks.Length < numFrames)
return 0;
int last = frameTicks[numFrames - 1];
int first = frameTicks[0];
int span = last - first;
if (span <= 0)
return 0;
return Mathf.Max(1, Mathf.RoundToInt((numFrames - 1) * 60f / span));
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: af2fa24fb63c4aa45bb99a711c857114
@@ -0,0 +1,46 @@
using System.Collections.Generic;
using UnityEngine;
namespace BrewMonster.Scripts.Chat.EmotionData
{
/// <summary>
/// Dữ liệu một bộ emotion (tương ứng Emotions{N}.dds + Emotions{N}.txt).
/// Data for one emotion group (matches Emotions{N}.dds + Emotions{N}.txt).
/// </summary>
[CreateAssetMenu(fileName = "EmotionSetData", menuName = "Perfect World/Chat/Emotion Set Data", order = 0)]
public class EmotionSetDataSO : ScriptableObject
{
[Tooltip("N trong Emotions{N} (0..31 như AUIMANAGER_MAX_EMOTIONGROUPS).")]
public int EmotionSetIndex;
[Tooltip("Kích thước ô lưới giống C++ (mặc định 32x32).")]
public int CellWidth = 32;
[Tooltip("Kích thước ô lưới giống C++ (mặc định 32x32).")]
public int CellHeight = 32;
[Tooltip("Texture nguồn (atlas PNG/DDS import) dùng khi convert.")]
public Texture2D SourceAtlas;
[Tooltip("Đường dẫn asset của file txt nguồn (optional, để trace).")]
public string SourceTxtAssetPath;
public List<EmotionEntryData> Entries = new List<EmotionEntryData>();
/// <summary>
/// Số ô theo chiều ngang trong atlas (texture width / CellWidth).
/// </summary>
public int GridCellsX => SourceAtlas != null && CellWidth > 0
? SourceAtlas.width / CellWidth
: 0;
/// <summary>
/// Số ô theo chiều dọc.
/// </summary>
public int GridCellsY => SourceAtlas != null && CellHeight > 0
? SourceAtlas.height / CellHeight
: 0;
public int TotalCells => GridCellsX * GridCellsY;
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 2143882ad81a4ac4ea7e23512f481104
@@ -0,0 +1,147 @@
using System;
using System.Collections.Generic;
using System.Globalization;
using System.Text;
namespace BrewMonster.Scripts.Chat.EmotionData
{
/// <summary>
/// Parser token giống thứ tự đọc trong AUIManager.cpp (Emotions{N}.txt).
/// Token order matches AUIManager.cpp when loading Emotions{N}.txt.
/// </summary>
public static class EmotionTxtParser
{
public const int MaxFrames = 20; // AUITEXTAREA_EMOTHION_MAXFRAME
public readonly struct ParseResult
{
public readonly List<EmotionEntryData> Entries;
public readonly string ErrorMessage;
public bool Success => string.IsNullOrEmpty(ErrorMessage);
public ParseResult(List<EmotionEntryData> entries, string error)
{
Entries = entries;
ErrorMessage = error ?? "";
}
}
/// <summary>
/// Đọc toàn bộ nội dung file txt; token tách bằng whitespace (giống GetNextToken cơ bản).
/// Reads full txt; tokens split by whitespace (basic GetNextToken behavior).
/// </summary>
public static ParseResult Parse(string text)
{
if (string.IsNullOrWhiteSpace(text))
return new ParseResult(new List<EmotionEntryData>(), "Empty text.");
var tokens = Tokenize(text);
var entries = new List<EmotionEntryData>();
int t = 0;
while (t < tokens.Count)
{
if (!TryParseInt(tokens[t], out int startPos))
return new ParseResult(null, $"Invalid nStartPos at token index {t}: '{tokens[t]}'");
t++;
if (t >= tokens.Count)
return new ParseResult(null, "Unexpected EOF after nStartPos.");
if (!TryParseInt(tokens[t], out int numFramesRaw))
return new ParseResult(null, $"Invalid nNumFrames at token index {t}.");
int numFrames = Math.Min(Math.Max(0, numFramesRaw), MaxFrames);
t++;
if (t >= tokens.Count)
return new ParseResult(null, "Unexpected EOF after nNumFrames (missing hint).");
string hint = tokens[t];
t++;
var frameTicks = new int[numFrames];
for (int i = 0; i < numFrames; i++)
{
if (t >= tokens.Count)
return new ParseResult(null,
$"Unexpected EOF: need {numFrames} frame tick values for entry starting at StartPos={startPos}.");
if (!TryParseInt(tokens[t], out frameTicks[i]))
return new ParseResult(null, $"Invalid nFrameTick[{i}] at token index {t}.");
t++;
}
entries.Add(new EmotionEntryData
{
StartPos = startPos,
NumFrames = numFrames,
Hint = hint,
FrameTicks = frameTicks
});
}
return new ParseResult(entries, null);
}
private static bool TryParseInt(string s, out int v)
{
return int.TryParse(s, NumberStyles.Integer, CultureInfo.InvariantCulture, out v);
}
/// <summary>
/// Tách token: khoảng trắng; hỗ trợ chuỗi trong dấu ngoặc kép cho hint nếu sau này cần.
/// </summary>
private static List<string> Tokenize(string text)
{
var list = new List<string>();
var sb = new StringBuilder();
bool inQuotes = false;
for (int i = 0; i < text.Length; i++)
{
char c = text[i];
if (inQuotes)
{
if (c == '"')
inQuotes = false;
else
sb.Append(c);
continue;
}
if (c == '"')
{
if (sb.Length > 0)
{
list.Add(sb.ToString());
sb.Clear();
}
inQuotes = true;
continue;
}
if (char.IsWhiteSpace(c))
{
if (sb.Length > 0)
{
list.Add(sb.ToString());
sb.Clear();
}
continue;
}
sb.Append(c);
}
if (sb.Length > 0)
list.Add(sb.ToString());
return list;
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 656924d32be0e3c469b409078941188e
@@ -0,0 +1,29 @@
/// <summary>
/// Stub实现 — 在没有真实TMP_SpriteAsset(emotion atlas)时使用的占位映射。
/// Stub implementation used when no real TMP_SpriteAsset (emotion atlas) is available yet.
///
/// 当准备好atlas后,创建一个新的IEmotionSpriteMap实现,替换掉这个stub。
/// When atlas is ready, create a real IEmotionSpriteMap implementation and swap it in
/// ChatEmotionDisplayPipeline / CECGameUIMan emotion pipeline.
/// </summary>
public class StubEmotionSpriteMap : IEmotionSpriteMap
{
private const int EMOTIONS_PER_SET = 50;
private const int FRAMES_PER_EMOTION = 4;
private const int DEFAULT_FPS = 10;
public bool TryGetSprite(int emotionSet, int emotionIndex, out EmotionSpriteInfo info)
{
int startFrame = (emotionSet * EMOTIONS_PER_SET + emotionIndex) * FRAMES_PER_EMOTION;
info = new EmotionSpriteInfo
{
SpriteIndex = startFrame,
IsAnimated = true,
AnimEndFrame = startFrame + FRAMES_PER_EMOTION - 1,
AnimFPS = DEFAULT_FPS
};
return true;
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 8b0342124b298f0428adfc94c9d6d972
+8
View File
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 63ad32ae8f64ef1449e51fe4460570a8
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,348 @@
using System.Collections.Generic;
using System.IO;
using System.Linq;
using BrewMonster.Scripts.Chat.EmotionData;
using UnityEditor;
using UnityEngine;
namespace BrewMonster.Scripts.Editor
{
/// <summary>
/// Convert một bộ: ghi atlas (hoặc slice tại chỗ) + TextureImporter Sprite Multiple full lưới,
/// gán FrameSprites theo tên cell_XXXX khớp C++ (row-major, hàng trên = row 0).
/// </summary>
public static class EmotionAtlasConverterCore
{
public const string CellSpriteNamePrefix = "cell_";
public static string CellSpriteName(int cellIndex) => $"{CellSpriteNamePrefix}{cellIndex:D4}";
/// <param name="sliceInPlace">true = chỉnh importer trên asset atlas hiện tại (ghi đè import settings). false = copy PNG vào thư mục output rồi slice (an toàn hơn).</param>
public static bool ConvertOneSet(
Texture2D sourceAtlas,
TextAsset txtAsset,
int emotionSetIndex,
int cellW,
int cellH,
string outputRootFolder,
bool sliceInPlace,
out EmotionSetSnapshot snapshot,
out string error)
{
snapshot = null;
error = null;
if (sourceAtlas == null)
{
error = "Atlas null.";
return false;
}
if (txtAsset == null)
{
error = "TextAsset null.";
return false;
}
string sourceAtlasPath = AssetDatabase.GetAssetPath(sourceAtlas);
if (string.IsNullOrEmpty(sourceAtlasPath))
{
error = "Atlas không phải asset trong project.";
return false;
}
var parseResult = EmotionTxtParser.Parse(txtAsset.text);
if (!parseResult.Success)
{
error = parseResult.ErrorMessage;
return false;
}
if (cellW <= 0 || cellH <= 0)
{
error = "Cell size phải > 0.";
return false;
}
Texture2D readable = GetReadableTexture(sourceAtlas);
if (readable == null)
{
error = "Không đọc được pixel từ atlas.";
return false;
}
try
{
int texW = readable.width;
int texH = readable.height;
if (texW % cellW != 0 || texH % cellH != 0)
{
error = $"Texture ({texW}x{texH}) không chia hết cho cell ({cellW}x{cellH}).";
return false;
}
int nNumX = texW / cellW;
int nNumY = texH / cellH;
int totalCells = nNumX * nNumY;
foreach (var e in parseResult.Entries)
{
if (e.NumFrames > 0 && e.StartPos + e.NumFrames - 1 >= totalCells)
{
error = $"Set {emotionSetIndex}: StartPos={e.StartPos}, NumFrames={e.NumFrames} vượt lưới ({totalCells} ô).";
return false;
}
}
EnsureFolder(outputRootFolder);
string setFolder = $"{outputRootFolder}/Emotions{emotionSetIndex}";
if (!AssetDatabase.IsValidFolder(setFolder))
AssetDatabase.CreateFolder(outputRootFolder, $"Emotions{emotionSetIndex}");
string atlasAssetPath;
Texture2D atlasForSo;
if (sliceInPlace)
{
atlasAssetPath = sourceAtlasPath;
if (!ApplyMultipleSpriteSheet(atlasAssetPath, texW, texH, cellW, cellH, nNumX, nNumY, out error))
return false;
atlasForSo = AssetDatabase.LoadAssetAtPath<Texture2D>(atlasAssetPath);
if (atlasForSo == null)
{
error = "Không load lại Texture2D sau slice.";
return false;
}
}
else
{
string fileName = $"Emotions{emotionSetIndex}_atlas.png";
atlasAssetPath = $"{setFolder}/{fileName}";
byte[] png = readable.EncodeToPNG();
File.WriteAllBytes(atlasAssetPath, png);
AssetDatabase.Refresh();
if (!ApplyMultipleSpriteSheet(atlasAssetPath, texW, texH, cellW, cellH, nNumX, nNumY, out error))
return false;
atlasForSo = AssetDatabase.LoadAssetAtPath<Texture2D>(atlasAssetPath);
if (atlasForSo == null)
{
error = $"Không load texture tại {atlasAssetPath}";
return false;
}
}
var spriteByName = LoadSpritesByName(atlasAssetPath);
if (spriteByName.Count < totalCells)
{
error = $"Chỉ tìm thấy {spriteByName.Count}/{totalCells} sprite sau import.";
return false;
}
snapshot = new EmotionSetSnapshot
{
EmotionSetIndex = emotionSetIndex,
CellWidth = cellW,
CellHeight = cellH,
SourceAtlas = atlasForSo,
SourceTxtAssetPath = AssetDatabase.GetAssetPath(txtAsset),
Entries = new List<EmotionEntryData>()
};
foreach (var src in parseResult.Entries)
{
var copy = new EmotionEntryData
{
StartPos = src.StartPos,
NumFrames = src.NumFrames,
Hint = src.Hint,
FrameTicks = (int[])src.FrameTicks.Clone(),
FrameSprites = new Sprite[src.NumFrames]
};
for (int f = 0; f < src.NumFrames; f++)
{
int cellIndex = src.StartPos + f;
string key = CellSpriteName(cellIndex);
if (!spriteByName.TryGetValue(key, out var spr) || spr == null)
{
error = $"Thiếu sprite '{key}' trong atlas.";
return false;
}
copy.FrameSprites[f] = spr;
}
snapshot.Entries.Add(copy);
}
return true;
}
finally
{
if (readable != null && readable != sourceAtlas)
Object.DestroyImmediate(readable);
}
}
private static bool ApplyMultipleSpriteSheet(
string assetPath,
int texW,
int texH,
int cellW,
int cellH,
int nNumX,
int nNumY,
out string error)
{
error = null;
var importer = AssetImporter.GetAtPath(assetPath) as TextureImporter;
if (importer == null)
{
error = $"Không mở TextureImporter: {assetPath}";
return false;
}
importer.textureType = TextureImporterType.Sprite;
importer.spriteImportMode = SpriteImportMode.Multiple;
importer.spritePixelsPerUnit = 100;
importer.mipmapEnabled = false;
importer.alphaIsTransparency = true;
importer.maxTextureSize = Mathf.Max(importer.maxTextureSize, Mathf.Max(texW, texH));
importer.spritesheet = BuildSpriteMetaData(texW, texH, cellW, cellH, nNumX, nNumY);
importer.SetPlatformTextureSettings(new TextureImporterPlatformSettings
{
name = "Default",
overridden = false
});
importer.SaveAndReimport();
return true;
}
private static SpriteMetaData[] BuildSpriteMetaData(int texW, int texH, int cellW, int cellH, int nNumX, int nNumY)
{
var list = new List<SpriteMetaData>(nNumX * nNumY);
for (int row = 0; row < nNumY; row++)
{
for (int col = 0; col < nNumX; col++)
{
int cellIndex = row * nNumX + col;
float x = col * cellW;
float y = texH - (row + 1) * cellH;
list.Add(new SpriteMetaData
{
name = CellSpriteName(cellIndex),
rect = new Rect(x, y, cellW, cellH),
pivot = new Vector2(0.5f, 0.5f),
alignment = (int)SpriteAlignment.Center,
border = Vector4.zero
});
}
}
return list.ToArray();
}
private static Dictionary<string, Sprite> LoadSpritesByName(string atlasAssetPath)
{
var map = new Dictionary<string, Sprite>();
foreach (var o in AssetDatabase.LoadAllAssetsAtPath(atlasAssetPath))
{
if (o is Sprite sp && !string.IsNullOrEmpty(sp.name))
map[sp.name] = sp;
}
return map;
}
public static void EnsureFolder(string folder)
{
if (AssetDatabase.IsValidFolder(folder))
return;
string parent = "Assets";
foreach (var part in folder.Replace('\\', '/').Split('/'))
{
if (string.IsNullOrEmpty(part) || part == "Assets")
continue;
string newPath = parent + "/" + part;
if (!AssetDatabase.IsValidFolder(newPath))
AssetDatabase.CreateFolder(parent, part);
parent = newPath;
}
}
public static void ApplySnapshotToSetSO(EmotionSetDataSO so, EmotionSetSnapshot snap)
{
if (so == null || snap == null) return;
so.EmotionSetIndex = snap.EmotionSetIndex;
so.CellWidth = snap.CellWidth;
so.CellHeight = snap.CellHeight;
so.SourceAtlas = snap.SourceAtlas;
so.SourceTxtAssetPath = snap.SourceTxtAssetPath;
so.Entries.Clear();
foreach (var e in snap.Entries)
so.Entries.Add(e);
}
/// <summary>
/// Kiểm tra trùng EmotionSetIndex giữa các slot đang có đủ Atlas+Txt.
/// </summary>
public static bool TryValidateBatchIndices(IReadOnlyList<EmotionBatchSlot> slots, out string error)
{
error = null;
var used = new HashSet<int>();
foreach (var s in slots)
{
if (s?.Atlas == null && s?.Txt == null)
continue;
if (s.Atlas == null || s.Txt == null)
continue;
if (!used.Add(s.EmotionSetIndex))
{
error = $"Trùng Emotion set index: {s.EmotionSetIndex}";
return false;
}
}
return true;
}
private static Texture2D GetReadableTexture(Texture2D atlas)
{
try
{
var dup = new Texture2D(atlas.width, atlas.height, TextureFormat.RGBA32, false);
var prev = RenderTexture.active;
var rt = RenderTexture.GetTemporary(atlas.width, atlas.height, 0, RenderTextureFormat.ARGB32);
Graphics.Blit(atlas, rt);
RenderTexture.active = rt;
dup.ReadPixels(new Rect(0, 0, atlas.width, atlas.height), 0, 0);
dup.Apply(false, false);
RenderTexture.active = prev;
RenderTexture.ReleaseTemporary(rt);
return dup;
}
catch
{
return null;
}
}
}
/// <summary>
/// Một dòng batch: index bộ (N) + atlas + txt — có thể thêm/bớt trong cửa sổ tool.
/// </summary>
[System.Serializable]
public class EmotionBatchSlot
{
[Tooltip("N trong Emotions{N} (thư mục output & tên file atlas copy).")]
public int EmotionSetIndex;
public Texture2D Atlas;
public TextAsset Txt;
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 38dfc1555b7238a4c99647d8d8dcb7e4
@@ -0,0 +1,229 @@
using System.Collections.Generic;
using BrewMonster.Scripts.Chat.EmotionData;
using UnityEditor;
using UnityEngine;
namespace BrewMonster.Scripts.Editor
{
/// <summary>
/// Tool: atlas + txt → Sprite Mode Multiple (một PNG/bộ) + SO; batch linh hoạt số slot.
/// </summary>
public class EmotionAtlasConverterWindow : EditorWindow
{
private Texture2D _sourceAtlas;
private TextAsset _txtAsset;
private int _emotionSetIndex;
private int _cellW = 32;
private int _cellH = 32;
private string _outputFolder = "Assets/PerfectWorld/UI/Chat/GeneratedEmotions";
private bool _sliceInPlace;
private List<EmotionBatchSlot> _batchSlots = new List<EmotionBatchSlot>();
private Vector2 _batchScroll;
private string _libraryAssetPath = "Assets/PerfectWorld/UI/Chat/GeneratedEmotions/EmotionLibrary.asset";
[MenuItem("Tools/Perfect World/ChatSystem/Emotion Atlas Converter…")]
public static void Open()
{
GetWindow<EmotionAtlasConverterWindow>(true, "Emotion Atlas Converter", true);
}
private void OnEnable()
{
if (_batchSlots == null)
_batchSlots = new List<EmotionBatchSlot>();
if (_batchSlots.Count == 0)
{
for (int i = 0; i < 8; i++)
_batchSlots.Add(new EmotionBatchSlot { EmotionSetIndex = i });
}
}
private void OnGUI()
{
EditorGUILayout.LabelField("Chung / Shared", EditorStyles.boldLabel);
_cellW = EditorGUILayout.IntField("Cell width (W)", _cellW);
_cellH = EditorGUILayout.IntField("Cell height (H)", _cellH);
_outputFolder = EditorGUILayout.TextField("Output folder", _outputFolder);
_sliceInPlace = EditorGUILayout.ToggleLeft(
"Slice tại asset nguồn (ghi đè import Multiple lên atlas đang chọn) — Slice in-place on source asset",
_sliceInPlace);
if (_sliceInPlace)
{
EditorGUILayout.HelpBox(
"Cảnh báo: Unity sẽ đổi import của file atlas gốc thành Sprite Multiple full lưới.\n" +
"Warning: overwrites source texture import settings.",
MessageType.Warning);
}
else
{
EditorGUILayout.HelpBox(
"Mặc định: copy atlas vào Output/Emotions{N}/Emotions{N}_atlas.png rồi Multiple slice (giữ nguyên file nguồn).\n" +
"Default: copy atlas to output folder then slice (source unchanged).",
MessageType.None);
}
EditorGUILayout.Space(8f);
EditorGUILayout.LabelField("Một bộ / Single set", EditorStyles.boldLabel);
_sourceAtlas = (Texture2D)EditorGUILayout.ObjectField("Atlas", _sourceAtlas, typeof(Texture2D), false);
_txtAsset = (TextAsset)EditorGUILayout.ObjectField("EmotionsN.txt", _txtAsset, typeof(TextAsset), false);
_emotionSetIndex = EditorGUILayout.IntField("Emotion set index (N)", _emotionSetIndex);
EditorGUILayout.Space();
if (GUILayout.Button("Convert → EmotionSetData + Atlas (Multiple)"))
{
RunConvertSingle();
}
EditorGUILayout.Space(12f);
EditorGUILayout.LabelField("Batch → EmotionLibrary", EditorStyles.boldLabel);
EditorGUILayout.BeginHorizontal();
if (GUILayout.Button("+ Thêm slot", GUILayout.Width(100)))
_batchSlots.Add(new EmotionBatchSlot { EmotionSetIndex = NextSuggestedSetIndex() });
if (GUILayout.Button(" Xóa slot cuối", GUILayout.Width(120)) && _batchSlots.Count > 0)
_batchSlots.RemoveAt(_batchSlots.Count - 1);
EditorGUILayout.LabelField($"Số slot: {_batchSlots.Count}");
EditorGUILayout.EndHorizontal();
_batchScroll = EditorGUILayout.BeginScrollView(_batchScroll, GUILayout.MinHeight(160f));
for (int i = 0; i < _batchSlots.Count; i++)
{
var slot = _batchSlots[i];
EditorGUILayout.BeginVertical(EditorStyles.helpBox);
EditorGUILayout.BeginHorizontal();
EditorGUILayout.LabelField($"#{i}", GUILayout.Width(24));
slot.EmotionSetIndex = EditorGUILayout.IntField("Set N", slot.EmotionSetIndex, GUILayout.Width(120));
slot.Atlas = (Texture2D)EditorGUILayout.ObjectField(slot.Atlas, typeof(Texture2D), false);
slot.Txt = (TextAsset)EditorGUILayout.ObjectField(slot.Txt, typeof(TextAsset), false);
if (GUILayout.Button("×", GUILayout.Width(22)))
{
_batchSlots.RemoveAt(i);
i--;
EditorGUILayout.EndHorizontal();
EditorGUILayout.EndVertical();
continue;
}
EditorGUILayout.EndHorizontal();
EditorGUILayout.EndVertical();
}
EditorGUILayout.EndScrollView();
_libraryAssetPath = EditorGUILayout.TextField("Library .asset path", _libraryAssetPath);
EditorGUILayout.Space();
if (GUILayout.Button("Convert batch → EmotionLibrary.asset"))
{
RunConvertLibrary();
}
EditorGUILayout.Space(8f);
EditorGUILayout.HelpBox(
"Mỗi bộ: một texture **Sprite Multiple**, tên sub-sprite `cell_0000` … theo chỉ số ô (giống C++).\n" +
"Each set: one **Sprite Multiple** texture; sub-sprite names `cell_0000` … by cell index.",
MessageType.Info);
}
private int NextSuggestedSetIndex()
{
int max = -1;
foreach (var s in _batchSlots)
{
if (s.EmotionSetIndex > max)
max = s.EmotionSetIndex;
}
return max + 1;
}
private void RunConvertSingle()
{
if (!EmotionAtlasConverterCore.ConvertOneSet(
_sourceAtlas, _txtAsset, _emotionSetIndex, _cellW, _cellH, _outputFolder, _sliceInPlace,
out var snapshot, out string err))
{
EditorUtility.DisplayDialog("Error", err, "OK");
return;
}
var so = ScriptableObject.CreateInstance<EmotionSetDataSO>();
EmotionAtlasConverterCore.ApplySnapshotToSetSO(so, snapshot);
string setFolder = $"{_outputFolder}/Emotions{_emotionSetIndex}";
string soPath = $"{setFolder}/EmotionSetData_{_emotionSetIndex}.asset";
AssetDatabase.CreateAsset(so, soPath);
AssetDatabase.SaveAssets();
EditorUtility.DisplayDialog("Done", $"Đã tạo:\n{soPath}\nAtlas (Multiple) trong thư mục set (hoặc đã slice tại nguồn).", "OK");
EditorGUIUtility.PingObject(so);
}
private void RunConvertLibrary()
{
if (!EmotionAtlasConverterCore.TryValidateBatchIndices(_batchSlots, out string dupErr))
{
EditorUtility.DisplayDialog("Error", dupErr, "OK");
return;
}
var library = ScriptableObject.CreateInstance<EmotionLibrarySO>();
library.Sets.Clear();
int ok = 0;
int total = _batchSlots.Count;
for (int i = 0; i < total; i++)
{
var slot = _batchSlots[i];
if (slot.Atlas == null && slot.Txt == null)
continue;
if (slot.Atlas == null || slot.Txt == null)
{
EditorUtility.DisplayDialog("Error",
$"Slot #{i} (Set N={slot.EmotionSetIndex}): cần cả Atlas và TXT.",
"OK");
Object.DestroyImmediate(library);
return;
}
EditorUtility.DisplayProgressBar("Emotion Library", $"Set {slot.EmotionSetIndex}…", (float)i / Mathf.Max(1, total));
if (!EmotionAtlasConverterCore.ConvertOneSet(
slot.Atlas, slot.Txt, slot.EmotionSetIndex, _cellW, _cellH, _outputFolder, _sliceInPlace,
out var snapshot, out string err))
{
EditorUtility.ClearProgressBar();
EditorUtility.DisplayDialog("Error", $"Set {slot.EmotionSetIndex}: {err}", "OK");
Object.DestroyImmediate(library);
return;
}
library.Sets.Add(snapshot);
ok++;
}
EditorUtility.ClearProgressBar();
if (ok == 0)
{
EditorUtility.DisplayDialog("Error", "Không có cặp Atlas+TXT hợp lệ.", "OK");
Object.DestroyImmediate(library);
return;
}
string dir = System.IO.Path.GetDirectoryName(_libraryAssetPath)?.Replace('\\', '/') ?? _outputFolder;
if (!string.IsNullOrEmpty(dir))
EmotionAtlasConverterCore.EnsureFolder(dir);
AssetDatabase.CreateAsset(library, _libraryAssetPath);
AssetDatabase.SaveAssets();
EditorUtility.DisplayDialog("Done",
$"EmotionLibrary: {ok} bộ.\n{_libraryAssetPath}",
"OK");
EditorGUIUtility.PingObject(library);
}
}
}
@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: bd89b10678fe79046af39970b5c83b4c
@@ -448,6 +448,177 @@ namespace CSNetwork
}
return sb.ToString();
}
// =====================================================================
// TMP Rich Text Converters — 将内部item格式转换为TextMeshPro标签
// Pipeline: displayText + EditBoxItemsSet
// → ConvertEmotionsToTMP (表情 → <sprite>)
// → ConvertCoordsToTMP (坐标 → <link>)
// → ConvertIvtrItemsToTMP (物品 → <link>)
// → StripRemainingItemCodes(清理残留)
// =====================================================================
/// <summary>
/// [TMP] 将表情item替换为TMP sprite标签 — Replace emotion items with TMP animated sprite tags.
/// Input: displayText từ UnmarshalEditBoxText (chứa PUA placeholder chars).
/// Các item không phải Emotion được giữ nguyên cho converter tiếp theo xử lý.
/// </summary>
public static string ConvertEmotionsToTMP(string displayText, EditBoxItemsSet itemsSet, IEmotionSpriteMap spriteMap)
{
if (string.IsNullOrEmpty(displayText) || spriteMap == null)
return displayText ?? "";
var sb = new StringBuilder(displayText.Length);
for (int i = 0; i < displayText.Length; i++)
{
char ch = displayText[i];
if (IsEditboxItemCode(ch))
{
var item = itemsSet.GetItemByChar(ch);
if (item != null && item.GetType() == EditboxItemType.enumEIEmotion)
{
int nSet = 0, nIndex = 0;
UnmarshalEmotionInfo(item.GetInfo(), ref nSet, ref nIndex);
if (spriteMap.TryGetSprite(nSet, nIndex, out var info))
{
if (info.UseSpriteName && !string.IsNullOrEmpty(info.SpriteName))
sb.AppendFormat("<sprite name=\"{0}\">", info.SpriteName);
else if (info.IsAnimated)
sb.AppendFormat("<sprite anim=\"{0},{1},{2}\">",
info.SpriteIndex, info.AnimEndFrame, info.AnimFPS);
else
sb.AppendFormat("<sprite index={0}>", info.SpriteIndex);
}
}
else
{
sb.Append(ch);
}
}
else
{
sb.Append(ch);
}
}
return sb.ToString();
}
/// <summary>
/// [TMP] 将坐标item替换为TMP可点击link标签 — Replace coord items with TMP link tags.
/// Output: &lt;link="coord:info"&gt;&lt;color=#RRGGBB&gt;name&lt;/color&gt;&lt;/link&gt;
/// </summary>
public static string ConvertCoordsToTMP(string displayText, EditBoxItemsSet itemsSet)
{
if (string.IsNullOrEmpty(displayText))
return displayText ?? "";
var sb = new StringBuilder(displayText.Length);
for (int i = 0; i < displayText.Length; i++)
{
char ch = displayText[i];
if (IsEditboxItemCode(ch))
{
var item = itemsSet.GetItemByChar(ch);
if (item != null && item.GetType() == EditboxItemType.enumEICoord)
{
string colorHex = A3DColorToHex(item.GetColor());
string name = item.GetName() ?? "";
string info = item.GetInfo() ?? "";
sb.AppendFormat("<link=\"coord:{0}\"><color=#{1}>{2}</color></link>",
info, colorHex, name);
}
else
{
sb.Append(ch);
}
}
else
{
sb.Append(ch);
}
}
return sb.ToString();
}
/// <summary>
/// [TMP] 将物品item替换为TMP可点击link标签 — Replace inventory item links with TMP link tags.
/// Output: &lt;link="item:info"&gt;&lt;color=#RRGGBB&gt;&lt;u&gt;name&lt;/u&gt;&lt;/color&gt;&lt;/link&gt;
/// </summary>
public static string ConvertIvtrItemsToTMP(string displayText, EditBoxItemsSet itemsSet)
{
if (string.IsNullOrEmpty(displayText))
return displayText ?? "";
var sb = new StringBuilder(displayText.Length);
for (int i = 0; i < displayText.Length; i++)
{
char ch = displayText[i];
if (IsEditboxItemCode(ch))
{
var item = itemsSet.GetItemByChar(ch);
if (item != null && item.GetType() == EditboxItemType.enumEIIvtrlItem)
{
string colorHex = A3DColorToHex(item.GetColor());
string name = item.GetName() ?? "";
string info = item.GetInfo() ?? "";
sb.AppendFormat("<link=\"item:{0}\"><color=#{1}><u>{2}</u></color></link>",
info, colorHex, name);
}
else
{
sb.Append(ch);
}
}
else
{
sb.Append(ch);
}
}
return sb.ToString();
}
/// <summary>
/// [TMP] 移除剩余的PUA item code字符 — Safety net: strip any remaining PUA item codes
/// not handled by the above converters (e.g. enumEIScriptItem, enumEIImage, custom types).
/// </summary>
public static string StripRemainingItemCodes(string displayText)
{
if (string.IsNullOrEmpty(displayText))
return displayText ?? "";
var sb = new StringBuilder(displayText.Length);
for (int i = 0; i < displayText.Length; i++)
{
if (!IsEditboxItemCode(displayText[i]))
sb.Append(displayText[i]);
}
return sb.ToString();
}
/// <summary>
/// A3DCOLOR (uint, ARGB format) → "RRGGBB" hex string cho TMP color tag.
/// </summary>
public static string A3DColorToHex(uint color)
{
byte r = (byte)((color >> 16) & 0xFF);
byte g = (byte)((color >> 8) & 0xFF);
byte b = (byte)(color & 0xFF);
return $"{r:X2}{g:X2}{b:X2}";
}
}
}
@@ -932,3 +1103,62 @@ public class EditboxScriptItem
return Data?.Length ?? 0;
}
}
/// <summary>
/// 表情sprite信息 — Describes how one emotion maps to a TMP_SpriteAsset sprite (or animation).
/// </summary>
public struct EmotionSpriteInfo
{
/// <summary>TMP sprite index (frame đầu tiên nếu có animation).</summary>
public int SpriteIndex;
/// <summary>True nếu emotion này là icon động (nhiều frame).</summary>
public bool IsAnimated;
/// <summary>Index frame cuối (inclusive). Chỉ dùng khi IsAnimated = true.</summary>
public int AnimEndFrame;
/// <summary>Frames per second. Chỉ dùng khi IsAnimated = true.</summary>
public int AnimFPS;
/// <summary>
/// Nếu true: dùng &lt;sprite name="SpriteName"&gt; (sprite phải có trong Sprite Asset gán trên TMP).
/// If true: emit &lt;sprite name="SpriteName"&gt; (sprite must exist on the TextMeshPro sprite asset).
/// </summary>
public bool UseSpriteName;
/// <summary>Tên sub-sprite Unity (vd. cell_0012) — khớp TMP Sprite Asset.</summary>
public string SpriteName;
}
/// <summary>
/// Interface ánh xạ (emotionSet, emotionIndex) → TMP sprite info.
/// Implement interface này khi đã có TMP_SpriteAsset (atlas emotion icons).
///
/// Ví dụ sử dụng:
/// <code>
/// public class MyEmotionMap : IEmotionSpriteMap
/// {
/// public bool TryGetSprite(int set, int index, out EmotionSpriteInfo info)
/// {
/// int spriteStart = set * 30 + index * 4; // 30 emotions/set, 4 frames mỗi emotion
/// info = new EmotionSpriteInfo
/// {
/// SpriteIndex = spriteStart,
/// IsAnimated = true,
/// AnimEndFrame = spriteStart + 3,
/// AnimFPS = 10
/// };
/// return true;
/// }
/// }
/// </code>
/// </summary>
public interface IEmotionSpriteMap
{
/// <summary>
/// Tra bảng (emotionSet, emotionIndex) → EmotionSpriteInfo.
/// Trả về false nếu không tìm thấy (emotion sẽ bị bỏ qua khi render).
/// </summary>
bool TryGetSprite(int emotionSet, int emotionIndex, out EmotionSpriteInfo info);
}
@@ -2033,6 +2033,11 @@ namespace CSNetwork
{
worldchat p = (worldchat)pProtocol;
// Tránh trùng với echo local trong SendChatData: server vẫn có thể broadcast
// worldchat về đúng người gửi; khi đó đã hiển thị ở SendChatData rồi.
if (p.Roleid == m_iCharID)
return true;
CECGameUIMan pGameUI = EC_Game.GetGameRun().GetUIManager().GetInGameUIMan();
CECStringTab pStrTab = EC_Game.GetFixedMsgs();
@@ -13,6 +13,7 @@ using CSNetwork.GPDataType;
using PerfectWorld.UI.MiniMap;
using UnityEngine;
using BrewMonster.PerfectWorld.Scripts.UI;
using BrewMonster.Scripts.Chat;
namespace BrewMonster.UI
{
@@ -33,6 +34,17 @@ namespace BrewMonster.UI
public CDlgMiniMap m_pDlgMiniMap;
private readonly ChatEmotionDisplayPipeline _chatEmotionPipeline = new ChatEmotionDisplayPipeline();
/// <summary>
/// Gọi từ <see cref="CECUIManager"/> (MonoBehaviour) trước <see cref="Init"/> — CECGameUIMan không phải component nên không kéo SO trên Inspector được.
/// Called from CECUIManager before Init; plain class cannot use Inspector SerializeField.
/// </summary>
public void SetEmotionSpriteMap(IEmotionSpriteMap map)
{
_chatEmotionPipeline.SetSpriteMap(map);
}
// Layout/settings flags for GetUserLayout (saved to server)
// 布局/设置标志,用于 GetUserLayout(保存到服务器)
private bool m_bAutoReply;
@@ -336,6 +348,7 @@ namespace BrewMonster.UI
public override void Init()
{
base.Init();
m_IconMap = new Dictionary<byte, (string, Sprite[])>();
m_pDlgTask = GetDialog(CECUIHelper.DlgTaskName).GetComponent<DlgTask>();
m_pDlgTask.Show(false);
@@ -431,7 +444,8 @@ namespace BrewMonster.UI
}
// C++: ACString strModified = FilterEmotionSet(pszMsg, cEmotion);
string strModified = pszMsg;
// 修正表情 — Correct emotion set for this channel
string strModified = _chatEmotionPipeline.ApplyChannelEmotionFilter(pszMsg, cEmotion);
// C++: 修正给GM的额外信息 (Fix extra info for GM)
// (Skipped in Unity for now)
@@ -474,6 +488,10 @@ namespace BrewMonster.UI
CECUIManager.Instance.FilterBadWords(ref pszMsg);
}
// TMP Conversion: 将内部item格式转换为TMP rich text标签
// Unmarshal inline items (emotion/coord/ivtritem) and convert to TMP tags
pszMsg = _chatEmotionPipeline.ConvertInlineItemsToTmp(pszMsg);
// C++: Booth Message check (cChannel == GP_CHAT_WHISPER && pszMsg ends with "!#")
// (Skipped)
+8
View File
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 74be13e484f282140a6795b465cc3ac2
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: fc7f2e18c19aa5346a706caec5f4ec59
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: dc188c86ecb92594ca08313d5e14f9a6
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.

After

Width:  |  Height:  |  Size: 170 KiB

File diff suppressed because it is too large Load Diff
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 218eac237a6113a49a3e2f5455459c12
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.

After

Width:  |  Height:  |  Size: 157 KiB

File diff suppressed because it is too large Load Diff
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 2eb1325f8b2c40c43bc9de0d1277aae6
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.

After

Width:  |  Height:  |  Size: 360 KiB

File diff suppressed because it is too large Load Diff
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 386959475b960de449e8749b3a011f38
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.

After

Width:  |  Height:  |  Size: 319 KiB

File diff suppressed because it is too large Load Diff
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: c0f9ced5aa63eb94ebb4da17a30d465e
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.

After

Width:  |  Height:  |  Size: 170 KiB

File diff suppressed because it is too large Load Diff
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: f7f6fa101b4147941bf81b649b2041ee
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.

After

Width:  |  Height:  |  Size: 218 KiB

File diff suppressed because it is too large Load Diff
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 2ef2d60aa57075b4bbcc898417b05f01
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.

After

Width:  |  Height:  |  Size: 252 KiB

File diff suppressed because it is too large Load Diff
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: f67e0a5d950e9b34f9241a688d674050
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.

After

Width:  |  Height:  |  Size: 477 KiB

File diff suppressed because it is too large Load Diff
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 76b92f453e51f46438cb914bb0c9e6cc
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

@@ -0,0 +1,537 @@
fileFormatVersion: 2
guid: 84e9c440264236f45adfb529204b91f9
TextureImporter:
internalIDToNameTable: []
externalObjects: {}
serializedVersion: 13
mipmaps:
mipMapMode: 0
enableMipMap: 0
sRGBTexture: 1
linearTexture: 0
fadeOut: 0
borderMipMap: 0
mipMapsPreserveCoverage: 0
alphaTestReferenceValue: 0.5
mipMapFadeDistanceStart: 1
mipMapFadeDistanceEnd: 3
bumpmap:
convertToNormalMap: 0
externalNormalMap: 0
heightScale: 0.25
normalMapFilter: 0
flipGreenChannel: 0
isReadable: 0
streamingMipmaps: 0
streamingMipmapsPriority: 0
vTOnly: 0
ignoreMipmapLimit: 0
grayScaleToAlpha: 0
generateCubemap: 6
cubemapConvolution: 0
seamlessCubemap: 0
textureFormat: 1
maxTextureSize: 2048
textureSettings:
serializedVersion: 2
filterMode: 1
aniso: 1
mipBias: 0
wrapU: 1
wrapV: 1
wrapW: 1
nPOTScale: 0
lightmap: 0
compressionQuality: 50
spriteMode: 2
spriteExtrude: 1
spriteMeshType: 1
alignment: 0
spritePivot: {x: 0.5, y: 0.5}
spritePixelsToUnits: 100
spriteBorder: {x: 0, y: 0, z: 0, w: 0}
spriteGenerateFallbackPhysicsShape: 1
alphaUsage: 1
alphaIsTransparency: 1
spriteTessellationDetail: -1
textureType: 8
textureShape: 1
singleChannelComponent: 0
flipbookRows: 1
flipbookColumns: 1
maxTextureSizeSet: 0
compressionQualitySet: 0
textureFormatSet: 0
ignorePngGamma: 0
applyGammaDecoding: 0
swizzle: 50462976
cookieLightType: 0
platformSettings:
- serializedVersion: 4
buildTarget: DefaultTexturePlatform
maxTextureSize: 2048
resizeAlgorithm: 0
textureFormat: -1
textureCompression: 1
compressionQuality: 50
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
forceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 4
buildTarget: Standalone
maxTextureSize: 2048
resizeAlgorithm: 0
textureFormat: -1
textureCompression: 1
compressionQuality: 50
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
forceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 4
buildTarget: Android
maxTextureSize: 2048
resizeAlgorithm: 0
textureFormat: -1
textureCompression: 1
compressionQuality: 50
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
forceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 4
buildTarget: WebGL
maxTextureSize: 2048
resizeAlgorithm: 0
textureFormat: -1
textureCompression: 1
compressionQuality: 50
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
forceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 4
buildTarget: iOS
maxTextureSize: 2048
resizeAlgorithm: 0
textureFormat: -1
textureCompression: 1
compressionQuality: 50
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
forceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 4
buildTarget: Default
maxTextureSize: 2048
resizeAlgorithm: 0
textureFormat: -1
textureCompression: 1
compressionQuality: 50
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
forceMaximumCompressionQuality_BC6H_BC7: 0
spriteSheet:
serializedVersion: 2
sprites:
- serializedVersion: 2
name: cell_0000
rect:
serializedVersion: 2
x: 0
y: 96
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: 6f5b9663c6b977210800000000000000
internalID: 1330703103982941686
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0001
rect:
serializedVersion: 2
x: 32
y: 96
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: e76cb594529ae32f0800000000000000
internalID: -991168890365294978
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0002
rect:
serializedVersion: 2
x: 64
y: 96
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: 05aa950660ebf5ae0800000000000000
internalID: -1558318011451332016
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0003
rect:
serializedVersion: 2
x: 96
y: 96
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: 027b202b8a95f5a00800000000000000
internalID: 747414644242691872
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0004
rect:
serializedVersion: 2
x: 0
y: 64
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: 00ce46140c373a730800000000000000
internalID: 4009175362857921536
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0005
rect:
serializedVersion: 2
x: 32
y: 64
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: 9a7727b32a2812150800000000000000
internalID: 5846097424597284777
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0006
rect:
serializedVersion: 2
x: 64
y: 64
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: a509edc41b42fe1b0800000000000000
internalID: -5625237065644994470
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0007
rect:
serializedVersion: 2
x: 96
y: 64
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: bc304e17e64179b30800000000000000
internalID: 4293923234310783947
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0008
rect:
serializedVersion: 2
x: 0
y: 32
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: b96277280a806c780800000000000000
internalID: -8663227347723934053
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0009
rect:
serializedVersion: 2
x: 32
y: 32
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: 225da9d6df3668020800000000000000
internalID: 2343670596209661218
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0010
rect:
serializedVersion: 2
x: 64
y: 32
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: cf055f55525b181f0800000000000000
internalID: -1044354466612686596
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0011
rect:
serializedVersion: 2
x: 96
y: 32
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: 4cd04bbe4dfdc37b0800000000000000
internalID: -5243069760585593404
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0012
rect:
serializedVersion: 2
x: 0
y: 0
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: 84d522e2e4defebb0800000000000000
internalID: -4904440549145944760
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0013
rect:
serializedVersion: 2
x: 32
y: 0
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: b63dbb5feb60d68f0800000000000000
internalID: -545772562605681813
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0014
rect:
serializedVersion: 2
x: 64
y: 0
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: bc2840338ad13a5e0800000000000000
internalID: -1899642009572572469
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: cell_0015
rect:
serializedVersion: 2
x: 96
y: 0
width: 32
height: 32
alignment: 0
pivot: {x: 0.5, y: 0.5}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: -1
bones: []
spriteID: ccc4192bfb7190d40800000000000000
internalID: 5550994127812906188
vertices: []
indices:
edges: []
weights: []
outline: []
customData:
physicsShape: []
bones: []
spriteID:
internalID: 0
vertices: []
indices:
edges: []
weights: []
secondaryTextures: []
spriteCustomMetadata:
entries: []
nameFileIdTable:
cell_0000: 1330703103982941686
cell_0001: -991168890365294978
cell_0002: -1558318011451332016
cell_0003: 747414644242691872
cell_0004: 4009175362857921536
cell_0005: 5846097424597284777
cell_0006: -5625237065644994470
cell_0007: 4293923234310783947
cell_0008: -8663227347723934053
cell_0009: 2343670596209661218
cell_0010: -1044354466612686596
cell_0011: -5243069760585593404
cell_0012: -4904440549145944760
cell_0013: -545772562605681813
cell_0014: -1899642009572572469
cell_0015: 5550994127812906188
mipmapLimitGroupName:
pSDRemoveMatte: 0
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 54fa2be7bb2a6a240b9419fd76bc7e2f
TextScriptImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 66461fb8e39c4f74089e1686884ab67c
TextScriptImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 86c918a5757b94246b6da14f5c48f4d6
TextScriptImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 30a52c2c4af94d5499ec3be1f9f84a34
TextScriptImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 479b1ad7206a497468cda9f257b74eeb
TextScriptImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 729dff8dbf27d394cb419e04a4af69a2
TextScriptImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 8c28dea2d06bff24fbbb25a4713d885e
TextScriptImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 49e01270b39230f45b8cf3bd2bf2d4b0
TextScriptImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: d4001a7c27db5394a993c7a395cb072c
TextScriptImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
Binary file not shown.
@@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: a96c3c9fdcd05684db33d441d62f0583
TextScriptImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -6,7 +6,7 @@ TextureImporter:
serializedVersion: 13
mipmaps:
mipMapMode: 0
enableMipMap: 1
enableMipMap: 0
sRGBTexture: 1
linearTexture: 0
fadeOut: 0
@@ -37,13 +37,13 @@ TextureImporter:
filterMode: 1
aniso: 1
mipBias: 0
wrapU: 0
wrapV: 0
wrapU: 1
wrapV: 1
wrapW: 0
nPOTScale: 1
nPOTScale: 0
lightmap: 0
compressionQuality: 50
spriteMode: 0
spriteMode: 2
spriteExtrude: 1
spriteMeshType: 1
alignment: 0
@@ -52,9 +52,9 @@ TextureImporter:
spriteBorder: {x: 0, y: 0, z: 0, w: 0}
spriteGenerateFallbackPhysicsShape: 1
alphaUsage: 1
alphaIsTransparency: 0
alphaIsTransparency: 1
spriteTessellationDetail: -1
textureType: 0
textureType: 8
textureShape: 1
singleChannelComponent: 0
flipbookRows: 1
@@ -132,6 +132,19 @@ TextureImporter:
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
forceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 4
buildTarget: WebGL
maxTextureSize: 2048
resizeAlgorithm: 0
textureFormat: -1
textureCompression: 1
compressionQuality: 50
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
forceMaximumCompressionQuality_BC6H_BC7: 0
spriteSheet:
serializedVersion: 2
sprites: []
@@ -298,6 +298,8 @@ MonoBehaviour:
button: {fileID: 1690303811971402318}
- channel: 8
button: {fileID: 5620031369785857446}
- channel: 1
button: {fileID: 8966563982496817389}
--- !u!114 &806784442167936328
MonoBehaviour:
m_ObjectHideFlags: 0
@@ -1329,6 +1331,142 @@ MonoBehaviour:
m_hasFontAssetChanged: 0
m_baseMaterial: {fileID: 0}
m_maskOffset: {x: 0, y: 0, z: 0, w: 0}
--- !u!1 &4462775877009399025
GameObject:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
serializedVersion: 6
m_Component:
- component: {fileID: 7795282280205679886}
- component: {fileID: 653827421901241620}
- component: {fileID: 7303489182730371871}
m_Layer: 5
m_Name: Text (TMP)
m_TagString: Untagged
m_Icon: {fileID: 0}
m_NavMeshLayer: 0
m_StaticEditorFlags: 0
m_IsActive: 1
--- !u!224 &7795282280205679886
RectTransform:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4462775877009399025}
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: 1847659348073965440}
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
m_AnchorMin: {x: 0, y: 0}
m_AnchorMax: {x: 1, y: 1}
m_AnchoredPosition: {x: -0.1000061, y: 1.6449986}
m_SizeDelta: {x: -10.600004, y: -13.610002}
m_Pivot: {x: 0.5, y: 0.5}
--- !u!222 &653827421901241620
CanvasRenderer:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4462775877009399025}
m_CullTransparentMesh: 1
--- !u!114 &7303489182730371871
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4462775877009399025}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: f4688fdb7df04437aeb418b961361dc5, type: 3}
m_Name:
m_EditorClassIdentifier:
m_Material: {fileID: 0}
m_Color: {r: 1, g: 1, b: 1, a: 1}
m_RaycastTarget: 1
m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0}
m_Maskable: 1
m_OnCullStateChanged:
m_PersistentCalls:
m_Calls: []
m_text: "Th\u1EBF gi\u1EDBi"
m_isRightToLeft: 0
m_fontAsset: {fileID: 11400000, guid: 369c2e14814cc9a4b8e3ad4e37769134, type: 2}
m_sharedMaterial: {fileID: 9092487103257209053, guid: 369c2e14814cc9a4b8e3ad4e37769134, type: 2}
m_fontSharedMaterials: []
m_fontMaterial: {fileID: 0}
m_fontMaterials: []
m_fontColor32:
serializedVersion: 2
rgba: 4294967295
m_fontColor: {r: 1, g: 1, b: 1, a: 1}
m_enableVertexGradient: 0
m_colorMode: 3
m_fontColorGradient:
topLeft: {r: 1, g: 1, b: 1, a: 1}
topRight: {r: 1, g: 1, b: 1, a: 1}
bottomLeft: {r: 1, g: 1, b: 1, a: 1}
bottomRight: {r: 1, g: 1, b: 1, a: 1}
m_fontColorGradientPreset: {fileID: 0}
m_spriteAsset: {fileID: 0}
m_tintAllSprites: 0
m_StyleSheet: {fileID: 0}
m_TextStyleHashCode: -1183493901
m_overrideHtmlColors: 0
m_faceColor:
serializedVersion: 2
rgba: 4294967295
m_fontSize: 24
m_fontSizeBase: 24
m_fontWeight: 400
m_enableAutoSizing: 0
m_fontSizeMin: 18
m_fontSizeMax: 72
m_fontStyle: 0
m_HorizontalAlignment: 2
m_VerticalAlignment: 512
m_textAlignment: 65535
m_characterSpacing: 0
m_wordSpacing: 0
m_lineSpacing: 0
m_lineSpacingMax: 0
m_paragraphSpacing: 0
m_charWidthMaxAdj: 0
m_TextWrappingMode: 1
m_wordWrappingRatios: 0.4
m_overflowMode: 0
m_linkedTextComponent: {fileID: 0}
parentLinkedComponent: {fileID: 0}
m_enableKerning: 0
m_ActiveFontFeatures: 6e72656b
m_enableExtraPadding: 0
checkPaddingRequired: 0
m_isRichText: 1
m_EmojiFallbackSupport: 1
m_parseCtrlCharacters: 1
m_isOrthographic: 1
m_isCullingEnabled: 0
m_horizontalMapping: 0
m_verticalMapping: 0
m_uvLineOffset: 0
m_geometrySortingOrder: 0
m_IsTextObjectScaleStatic: 0
m_VertexBufferAutoSizeReduction: 0
m_useMaxVisibleDescender: 1
m_pageToDisplay: 1
m_margin: {x: 0, y: 0, z: 0, w: 0}
m_isUsingLegacyAnimationComponent: 0
m_isVolumetricText: 0
m_hasFontAssetChanged: 0
m_baseMaterial: {fileID: 0}
m_maskOffset: {x: 0, y: 0, z: 0, w: 0}
--- !u!1 &4662784239972087670
GameObject:
m_ObjectHideFlags: 0
@@ -2682,6 +2820,7 @@ RectTransform:
- {fileID: 2818704151482351807}
- {fileID: 7768785220414438176}
- {fileID: 9191482712609232228}
- {fileID: 1847659348073965440}
m_Father: {fileID: 7512115805537874560}
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
m_AnchorMin: {x: 0, y: 1}
@@ -2753,6 +2892,127 @@ MonoBehaviour:
m_ChildScaleWidth: 1
m_ChildScaleHeight: 1
m_ReverseArrangement: 0
--- !u!1 &7995398686206608668
GameObject:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
serializedVersion: 6
m_Component:
- component: {fileID: 1847659348073965440}
- component: {fileID: 519132139347130033}
- component: {fileID: 2123756557947707806}
- component: {fileID: 8966563982496817389}
m_Layer: 5
m_Name: Button (5)
m_TagString: Untagged
m_Icon: {fileID: 0}
m_NavMeshLayer: 0
m_StaticEditorFlags: 0
m_IsActive: 1
--- !u!224 &1847659348073965440
RectTransform:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 7995398686206608668}
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:
- {fileID: 7795282280205679886}
m_Father: {fileID: 5764262791542584507}
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
m_AnchorMin: {x: 0, y: 0}
m_AnchorMax: {x: 0, y: 0}
m_AnchoredPosition: {x: 0, y: 0}
m_SizeDelta: {x: 0, y: 0}
m_Pivot: {x: 0.5, y: 0.5}
--- !u!222 &519132139347130033
CanvasRenderer:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 7995398686206608668}
m_CullTransparentMesh: 1
--- !u!114 &2123756557947707806
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 7995398686206608668}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: fe87c0e1cc204ed48ad3b37840f39efc, type: 3}
m_Name:
m_EditorClassIdentifier:
m_Material: {fileID: 0}
m_Color: {r: 1, g: 1, b: 1, a: 1}
m_RaycastTarget: 1
m_RaycastPadding: {x: 0, y: 0, z: 0, w: 0}
m_Maskable: 1
m_OnCullStateChanged:
m_PersistentCalls:
m_Calls: []
m_Sprite: {fileID: 21300000, guid: 3b5dda180f088234f97e05dd0bf05463, type: 3}
m_Type: 0
m_PreserveAspect: 0
m_FillCenter: 1
m_FillMethod: 4
m_FillAmount: 1
m_FillClockwise: 1
m_FillOrigin: 0
m_UseSpriteMesh: 0
m_PixelsPerUnitMultiplier: 1
--- !u!114 &8966563982496817389
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 7995398686206608668}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 4e29b1a8efbd4b44bb3f3716e73f07ff, type: 3}
m_Name:
m_EditorClassIdentifier:
m_Navigation:
m_Mode: 3
m_WrapAround: 0
m_SelectOnUp: {fileID: 0}
m_SelectOnDown: {fileID: 0}
m_SelectOnLeft: {fileID: 0}
m_SelectOnRight: {fileID: 0}
m_Transition: 1
m_Colors:
m_NormalColor: {r: 1, g: 1, b: 1, a: 1}
m_HighlightedColor: {r: 0.9607843, g: 0.9607843, b: 0.9607843, a: 1}
m_PressedColor: {r: 0.78431374, g: 0.78431374, b: 0.78431374, a: 1}
m_SelectedColor: {r: 0.9607843, g: 0.9607843, b: 0.9607843, a: 1}
m_DisabledColor: {r: 0.78431374, g: 0.78431374, b: 0.78431374, a: 0.5019608}
m_ColorMultiplier: 1
m_FadeDuration: 0.1
m_SpriteState:
m_HighlightedSprite: {fileID: 0}
m_PressedSprite: {fileID: 0}
m_SelectedSprite: {fileID: 0}
m_DisabledSprite: {fileID: 0}
m_AnimationTriggers:
m_NormalTrigger: Normal
m_HighlightedTrigger: Highlighted
m_PressedTrigger: Pressed
m_SelectedTrigger: Selected
m_DisabledTrigger: Disabled
m_Interactable: 1
m_TargetGraphic: {fileID: 2123756557947707806}
m_OnClick:
m_PersistentCalls:
m_Calls: []
--- !u!1 &8338334069910121121
GameObject:
m_ObjectHideFlags: 0
+7
View File
@@ -4,6 +4,7 @@ using BrewMonster.UI;
using System;
using System.Collections.Generic;
using BrewMonster.PerfectWorld.Scripts.Utility.ChatFilter;
using BrewMonster.Scripts.Chat.EmotionData;
using BrewMonster.Scripts.Managers;
using UnityEngine;
using TMPro;
@@ -31,6 +32,10 @@ public class CECUIManager : MonoSingleton<CECUIManager>
[SerializeField] private DialogScriptTableObject dialogResouce;
[SerializeField] private Canvas canvasDlg;
[SerializeField]
[Tooltip("Chat TMP: EmotionLibrarySpriteMap (SO). CECGameUIMan is not a MonoBehaviour — assign here on CECUIManager.")]
private EmotionLibrarySpriteMap _emotionLibrarySpriteMap;
[SerializeField] private UnityEngine.UI.Button btnSecondClick;
[SerializeField] CDlgQuickBar m_pDlgQuickBar1;
[SerializeField] GameObject ChangeSkillShortcutButton;
@@ -55,6 +60,7 @@ public class CECUIManager : MonoSingleton<CECUIManager>
gameUI = new CECGameUIMan();
gameUI.SetDependency(dialogResouce, canvasDlg);
gameUI.SetEmotionSpriteMap(_emotionLibrarySpriteMap);
gameUI.Init();
m_pDlgSkillAction = GetComponent<CDlgSkillAction>();
// Wire up second-click button / 连接第二次点击按钮
@@ -655,6 +661,7 @@ public class CECUIManager : MonoSingleton<CECUIManager>
{
gameUI = new CECGameUIMan();
gameUI.SetDependency(dialogResouce, canvasDlg);
gameUI.SetEmotionSpriteMap(_emotionLibrarySpriteMap);
gameUI.Init();
}
+22 -2
View File
@@ -3,9 +3,12 @@ using UnityEngine;
using TMPro;
using CSNetwork.GPDataType;
using System.Collections.Generic;
using BrewMonster;
using BrewMonster.Network;
using BrewMonster.Scripts.Managers;
using BrewMonster.UI;
using CSNetwork;
using PerfectWorld.Scripts.Managers;
namespace BrewMonster.Scripts.ChatUI
{
@@ -233,6 +236,11 @@ namespace BrewMonster.Scripts.ChatUI
ChatChannel resolvedChannel = ParseAndSendMessage(strText, nPack, nSlot);
if (resolvedChannel == ChatChannel.GP_CHAT_FARCRY && strText.StartsWith("!@"))
m_dwTickFarCry = now;
if (resolvedChannel == ChatChannel.GP_CHAT_SUPERFARCRY && strText.StartsWith("!#"))
m_dwTickFarCry2 = now;
SaveHistory(resolvedChannel, strText, nPack, nSlot, now);
ClearTextInInputField();
@@ -601,7 +609,19 @@ namespace BrewMonster.Scripts.ChatUI
inputField.ActivateInputField();
}
private int GetPlayerItemCount(int id) => 0;
private int GetPlayerLevel() => 10;
/// <summary>
/// C++: GetHostPlayer()->GetPack()->GetItemTotalNum(id) — đếm túi chính.
/// </summary>
private int GetPlayerItemCount(int templateId)
{
var host = EC_Game.GetGameRun()?.GetHostPlayer();
EC_Inventory pack = host?.GetPack();
return pack?.GetItemTotalNum(templateId) ?? 0;
}
private int GetPlayerLevel()
{
return EC_Game.GetGameRun()?.GetHostPlayer()?.GetBasicProps().iLevel ?? 0;
}
}
}
@@ -2,27 +2,33 @@
%TAG !u! tag:unity3d.com,2011:
--- !u!21 &2103686
Material:
serializedVersion: 6
serializedVersion: 8
m_ObjectHideFlags: 1
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_Name: TextMeshPro/Sprite
m_Shader: {fileID: 4800000, guid: cf81c85f95fe47e1a27f6ae460cf182c, type: 3}
m_ShaderKeywords: UNITY_UI_CLIP_RECT
m_Parent: {fileID: 0}
m_ModifiedSerializedProperties: 0
m_ValidKeywords:
- UNITY_UI_CLIP_RECT
m_InvalidKeywords: []
m_LightmapFlags: 5
m_EnableInstancingVariants: 0
m_DoubleSidedGI: 0
m_CustomRenderQueue: -1
stringTagMap: {}
disabledShaderPasses: []
m_LockedProperties:
m_SavedProperties:
serializedVersion: 3
m_TexEnvs:
- _MainTex:
m_Texture: {fileID: 2800000, guid: dffef66376be4fa480fb02b19edbe903, type: 3}
m_Texture: {fileID: 2800000, guid: e1a057e1756274235a7c676d3d0a761a, type: 3}
m_Scale: {x: 1, y: 1}
m_Offset: {x: 0, y: 0}
m_Ints: []
m_Floats:
- _ColorMask: 15
- _CullMode: 0
@@ -35,6 +41,8 @@ Material:
m_Colors:
- _ClipRect: {r: -32767, g: -32767, b: 32767, a: 32767}
- _Color: {r: 1, g: 1, b: 1, a: 1}
m_BuildTextureStacks: []
m_AllowLocking: 1
--- !u!114 &11400000
MonoBehaviour:
m_ObjectHideFlags: 0
@@ -47,15 +55,14 @@ MonoBehaviour:
m_Script: {fileID: 11500000, guid: 84a92b25f83d49b9bc132d206b370281, type: 3}
m_Name: EmojiOne
m_EditorClassIdentifier:
hashCode: -1836805472
material: {fileID: 2103686}
materialHashCode: 0
m_Version: 1.1.0
m_FaceInfo:
m_FaceIndex: 0
m_FamilyName:
m_StyleName:
m_PointSize: 0
m_Scale: 0
m_UnitsPerEM: 0
m_LineHeight: 0
m_AscentLine: 0
m_CapLine: 0
@@ -71,105 +78,90 @@ MonoBehaviour:
m_StrikethroughOffset: 0
m_StrikethroughThickness: 0
m_TabWidth: 0
spriteSheet: {fileID: 2800000, guid: dffef66376be4fa480fb02b19edbe903, type: 3}
m_Material: {fileID: 2103686}
spriteSheet: {fileID: 2800000, guid: e1a057e1756274235a7c676d3d0a761a, type: 3}
m_SpriteCharacterTable:
- m_ElementType: 2
m_Unicode: 128522
m_GlyphIndex: 0
m_Scale: 1
m_Name: Smiling face with smiling eyes
m_HashCode: -1318250903
- m_ElementType: 2
m_Unicode: 128523
m_GlyphIndex: 1
m_Scale: 1
m_Name: 1f60b
m_HashCode: 57188339
- m_ElementType: 2
m_Unicode: 128525
m_GlyphIndex: 2
m_Scale: 1
m_Name: 1f60d
m_HashCode: 57188341
- m_ElementType: 2
m_Unicode: 128526
m_GlyphIndex: 3
m_Scale: 1
m_Name: 1f60e
m_HashCode: 57188340
- m_ElementType: 2
m_Unicode: 128512
m_GlyphIndex: 4
m_Scale: 1
m_Name: Grinning face
m_HashCode: -95541379
- m_ElementType: 2
m_Unicode: 128513
m_GlyphIndex: 5
m_Scale: 1
m_Name: 1f601
m_HashCode: 57188256
- m_ElementType: 2
m_Unicode: 128514
m_GlyphIndex: 6
m_Scale: 1
m_Name: Face with tears of joy
m_HashCode: 239522663
- m_ElementType: 2
m_Unicode: 128515
m_GlyphIndex: 7
m_Scale: 1
m_Name: 1f603
m_HashCode: 57188258
- m_ElementType: 2
m_Unicode: 128516
m_GlyphIndex: 8
m_Scale: 1
m_Name: 1f604
m_HashCode: 57188261
- m_ElementType: 2
m_Unicode: 128517
m_GlyphIndex: 9
m_Scale: 1
m_Name: 1f605
m_HashCode: 57188260
- m_ElementType: 2
m_Unicode: 128518
m_GlyphIndex: 10
m_Scale: 1
m_Name: 1f606
m_HashCode: 57188263
- m_ElementType: 2
m_Unicode: 128521
m_GlyphIndex: 11
m_Scale: 1
m_Name: 1f609
m_HashCode: 57188264
- m_ElementType: 2
m_Unicode: 0
m_GlyphIndex: 12
m_Scale: 1
m_Name: .notdef
m_HashCode: -600915428
- m_ElementType: 2
m_Unicode: 129315
m_GlyphIndex: 13
m_Scale: 1
m_Name: 1f923
m_HashCode: 57200239
- m_ElementType: 2
m_Unicode: 9786
m_GlyphIndex: 14
m_Scale: 1
m_Name: 263a
m_HashCode: 1748406
- m_ElementType: 2
m_Unicode: 9785
m_GlyphIndex: 15
m_Scale: 1
m_Name: 2639
m_HashCode: 1748462
m_SpriteGlyphTable:
m_GlyphTable:
- m_Index: 0
m_Metrics:
m_Width: 128
@@ -184,6 +176,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 1
m_Metrics:
@@ -199,6 +192,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 2
m_Metrics:
@@ -214,6 +208,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 3
m_Metrics:
@@ -229,6 +224,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 4
m_Metrics:
@@ -244,6 +240,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 5
m_Metrics:
@@ -259,6 +256,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 6
m_Metrics:
@@ -274,6 +272,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 7
m_Metrics:
@@ -289,6 +288,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 8
m_Metrics:
@@ -304,6 +304,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 9
m_Metrics:
@@ -319,6 +320,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 10
m_Metrics:
@@ -334,6 +336,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 11
m_Metrics:
@@ -349,6 +352,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 12
m_Metrics:
@@ -364,6 +368,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 13
m_Metrics:
@@ -379,6 +384,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 14
m_Metrics:
@@ -394,6 +400,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
- m_Index: 15
m_Metrics:
@@ -409,6 +416,7 @@ MonoBehaviour:
m_Height: 128
m_Scale: 1
m_AtlasIndex: 0
m_ClassDefinitionType: 0
sprite: {fileID: 0}
spriteInfoList:
- id: 0
@@ -638,22 +646,29 @@ MonoBehaviour:
fallbackSpriteAssets: []
--- !u!21 &1369835458
Material:
serializedVersion: 6
serializedVersion: 8
m_ObjectHideFlags: 1
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_Name: TextMeshPro/Sprite
m_Shader: {fileID: 4800000, guid: cf81c85f95fe47e1a27f6ae460cf182c, type: 3}
m_ShaderKeywords:
m_Parent: {fileID: 0}
m_ModifiedSerializedProperties: 0
m_ValidKeywords: []
m_InvalidKeywords: []
m_LightmapFlags: 5
m_EnableInstancingVariants: 0
m_DoubleSidedGI: 0
m_CustomRenderQueue: -1
stringTagMap: {}
disabledShaderPasses: []
m_LockedProperties:
m_SavedProperties:
serializedVersion: 3
m_TexEnvs: []
m_Ints: []
m_Floats: []
m_Colors: []
m_BuildTextureStacks: []
m_AllowLocking: 1
+240 -102
View File
@@ -1,27 +1,57 @@
fileFormatVersion: 2
guid: dffef66376be4fa480fb02b19edbe903
TextureImporter:
fileIDToRecycleName:
21300000: EmojiOne_0
21300002: EmojiOne_1
21300004: EmojiOne_2
21300006: EmojiOne_3
21300008: EmojiOne_4
21300010: EmojiOne_6
21300012: EmojiOne_7
21300014: EmojiOne_8
21300016: EmojiOne_9
21300018: EmojiOne_10
21300020: EmojiOne_11
21300022: EmojiOne_12
21300024: EmojiOne_13
21300026: EmojiOne_5
21300028: EmojiOne_14
internalIDToNameTable:
- first:
213: 21300000
second: EmojiOne_0
- first:
213: 21300002
second: EmojiOne_1
- first:
213: 21300004
second: EmojiOne_2
- first:
213: 21300006
second: EmojiOne_3
- first:
213: 21300008
second: EmojiOne_4
- first:
213: 21300010
second: EmojiOne_6
- first:
213: 21300012
second: EmojiOne_7
- first:
213: 21300014
second: EmojiOne_8
- first:
213: 21300016
second: EmojiOne_9
- first:
213: 21300018
second: EmojiOne_10
- first:
213: 21300020
second: EmojiOne_11
- first:
213: 21300022
second: EmojiOne_12
- first:
213: 21300024
second: EmojiOne_13
- first:
213: 21300026
second: EmojiOne_5
- first:
213: 21300028
second: EmojiOne_14
externalObjects: {}
serializedVersion: 5
serializedVersion: 13
mipmaps:
mipMapMode: 0
enableMipMap: 1
enableMipMap: 0
sRGBTexture: 1
linearTexture: 0
fadeOut: 0
@@ -35,7 +65,12 @@ TextureImporter:
externalNormalMap: 0
heightScale: 0.25
normalMapFilter: 0
flipGreenChannel: 0
isReadable: 0
streamingMipmaps: 0
streamingMipmapsPriority: 0
vTOnly: 0
ignoreMipmapLimit: 0
grayScaleToAlpha: 0
generateCubemap: 6
cubemapConvolution: 0
@@ -44,9 +79,9 @@ TextureImporter:
maxTextureSize: 2048
textureSettings:
serializedVersion: 2
filterMode: -1
aniso: -1
mipBias: -1
filterMode: 1
aniso: 1
mipBias: 0
wrapU: 1
wrapV: 1
wrapW: 1
@@ -58,19 +93,26 @@ TextureImporter:
spriteMeshType: 1
alignment: 0
spritePivot: {x: 0.5, y: 0.5}
spriteBorder: {x: 0, y: 0, z: 0, w: 0}
spritePixelsToUnits: 100
spriteBorder: {x: 0, y: 0, z: 0, w: 0}
spriteGenerateFallbackPhysicsShape: 1
alphaUsage: 1
alphaIsTransparency: 1
spriteTessellationDetail: -1
textureType: 0
textureType: 8
textureShape: 1
singleChannelComponent: 0
flipbookRows: 1
flipbookColumns: 1
maxTextureSizeSet: 0
compressionQualitySet: 0
textureFormatSet: 0
ignorePngGamma: 0
applyGammaDecoding: 1
swizzle: 50462976
cookieLightType: 1
platformSettings:
- serializedVersion: 2
- serializedVersion: 4
buildTarget: DefaultTexturePlatform
maxTextureSize: 512
resizeAlgorithm: 0
@@ -80,8 +122,10 @@ TextureImporter:
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
- serializedVersion: 2
forceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 4
buildTarget: Standalone
maxTextureSize: 512
resizeAlgorithm: 0
@@ -91,9 +135,11 @@ TextureImporter:
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
- serializedVersion: 2
buildTarget: iPhone
forceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 4
buildTarget: iOS
maxTextureSize: 512
resizeAlgorithm: 0
textureFormat: -1
@@ -102,8 +148,10 @@ TextureImporter:
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
- serializedVersion: 2
forceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 4
buildTarget: Android
maxTextureSize: 512
resizeAlgorithm: 0
@@ -113,7 +161,22 @@ TextureImporter:
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
forceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 4
buildTarget: WebGL
maxTextureSize: 512
resizeAlgorithm: 0
textureFormat: -1
textureCompression: 1
compressionQuality: 50
crunchedCompression: 0
allowsAlphaSplitting: 0
overridden: 0
ignorePlatformSupport: 0
androidETC2FallbackOverride: 0
forceMaximumCompressionQuality_BC6H_BC7: 0
spriteSheet:
serializedVersion: 2
sprites:
@@ -121,18 +184,20 @@ TextureImporter:
name: EmojiOne_0
rect:
serializedVersion: 2
x: 0
y: 384
width: 128
height: 128
x: 4
y: 388
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: 4bcc36da2108f2c4ba3de5c921d25c3c
internalID: 21300000
vertices: []
indices:
edges: []
@@ -141,18 +206,20 @@ TextureImporter:
name: EmojiOne_1
rect:
serializedVersion: 2
x: 128
y: 384
width: 128
height: 128
x: 132
y: 388
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: e9eea8093eaeaee4d901c4553f572c22
internalID: 21300002
vertices: []
indices:
edges: []
@@ -161,18 +228,20 @@ TextureImporter:
name: EmojiOne_2
rect:
serializedVersion: 2
x: 256
y: 384
width: 128
height: 128
x: 260
y: 388
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: 49451da35411dcc42a3692e39b0fde70
internalID: 21300004
vertices: []
indices:
edges: []
@@ -181,18 +250,20 @@ TextureImporter:
name: EmojiOne_3
rect:
serializedVersion: 2
x: 384
y: 384
width: 128
height: 128
x: 388
y: 388
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: f65709664b924904790c850a50ca82bc
internalID: 21300006
vertices: []
indices:
edges: []
@@ -201,18 +272,20 @@ TextureImporter:
name: EmojiOne_4
rect:
serializedVersion: 2
x: 0
y: 256
width: 128
height: 128
x: 4
y: 260
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: 5b92c568a5ec9ad4b9ed90e271f1c9a8
internalID: 21300008
vertices: []
indices:
edges: []
@@ -221,18 +294,20 @@ TextureImporter:
name: EmojiOne_6
rect:
serializedVersion: 2
x: 256
y: 256
width: 128
height: 128
x: 260
y: 260
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: b10f2b48b7281594bb8a24a6511a35af
internalID: 21300010
vertices: []
indices:
edges: []
@@ -241,18 +316,20 @@ TextureImporter:
name: EmojiOne_7
rect:
serializedVersion: 2
x: 384
y: 256
width: 128
height: 128
x: 388
y: 260
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: 10a600f9329dc2246a897e89f4d283cd
internalID: 21300012
vertices: []
indices:
edges: []
@@ -261,18 +338,20 @@ TextureImporter:
name: EmojiOne_8
rect:
serializedVersion: 2
x: 0
y: 128
width: 128
height: 128
x: 4
y: 132
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: 66cffa363b90ab14787d8a5b90cf4502
internalID: 21300014
vertices: []
indices:
edges: []
@@ -281,18 +360,20 @@ TextureImporter:
name: EmojiOne_9
rect:
serializedVersion: 2
x: 128
y: 128
width: 128
height: 128
x: 132
y: 132
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: 55cf3d409c9b89349b1e1bdc1cc224ad
internalID: 21300016
vertices: []
indices:
edges: []
@@ -301,18 +382,20 @@ TextureImporter:
name: EmojiOne_10
rect:
serializedVersion: 2
x: 256
y: 128
width: 128
height: 128
x: 260
y: 132
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: 2a9e58eaf96feef42bcefa1cf257193f
internalID: 21300018
vertices: []
indices:
edges: []
@@ -321,18 +404,20 @@ TextureImporter:
name: EmojiOne_11
rect:
serializedVersion: 2
x: 384
y: 128
width: 128
height: 128
x: 388
y: 132
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: 2489120affc155840ae6a7be2e93ce19
internalID: 21300020
vertices: []
indices:
edges: []
@@ -341,18 +426,20 @@ TextureImporter:
name: EmojiOne_12
rect:
serializedVersion: 2
x: 0
y: 0
width: 128
height: 128
x: 4
y: 4
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: 412349a150598d14da4d7140df5c0286
internalID: 21300022
vertices: []
indices:
edges: []
@@ -361,18 +448,20 @@ TextureImporter:
name: EmojiOne_13
rect:
serializedVersion: 2
x: 128
y: 0
width: 128
height: 128
x: 132
y: 4
width: 120
height: 120
alignment: 0
pivot: {x: 0.5, y: 0.5}
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: a937464b42bb3634782dea34c6becb6c
internalID: 21300024
vertices: []
indices:
edges: []
@@ -381,18 +470,20 @@ TextureImporter:
name: EmojiOne_5
rect:
serializedVersion: 2
x: 256
y: 0
width: 128
height: 128
x: 132
y: 260
width: 120
height: 120
alignment: 0
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: b0f933b217682124dbfc5e6b89abe3d0
internalID: 21300026
vertices: []
indices:
edges: []
@@ -401,31 +492,78 @@ TextureImporter:
name: EmojiOne_14
rect:
serializedVersion: 2
x: 128
y: 256
width: 128
height: 128
x: 260
y: 4
width: 120
height: 120
alignment: 0
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: f7235c763afe4434e8bb666750a41096
internalID: 21300028
vertices: []
indices:
edges: []
weights: []
- serializedVersion: 2
name: EmojiOne_15
rect:
serializedVersion: 2
x: 388
y: 4
width: 120
height: 120
alignment: 0
pivot: {x: 0, y: 0}
border: {x: 0, y: 0, z: 0, w: 0}
customData:
outline: []
physicsShape: []
tessellationDetail: 0
bones: []
spriteID: fb60fe2758c4c5942906da1f2074306d
internalID: -514145858
vertices: []
indices:
edges: []
weights: []
outline: []
customData:
physicsShape: []
bones: []
spriteID: 3e32d8f5477abfc43b19066e8ad5032e
internalID: 0
vertices: []
indices:
edges: []
weights: []
spritePackingTag:
secondaryTextures: []
spriteCustomMetadata:
entries: []
nameFileIdTable:
EmojiOne_0: 21300000
EmojiOne_1: 21300002
EmojiOne_10: 21300018
EmojiOne_11: 21300020
EmojiOne_12: 21300022
EmojiOne_13: 21300024
EmojiOne_14: 21300028
EmojiOne_15: -514145858
EmojiOne_2: 21300004
EmojiOne_3: 21300006
EmojiOne_4: 21300008
EmojiOne_5: 21300026
EmojiOne_6: 21300010
EmojiOne_7: 21300012
EmojiOne_8: 21300014
EmojiOne_9: 21300016
mipmapLimitGroupName:
pSDRemoveMatte: 0
userData:
assetBundleName:
assetBundleVariant: