From 2f502767386320d84192cc6acd2971d17931e31a Mon Sep 17 00:00:00 2001 From: Infi Date: Tue, 19 Nov 2024 02:29:53 +0100 Subject: [PATCH] Switch PlayerPayload Encode/Decode to using Lumina (#2107) * Switch PlayerPayload Encode/Decode to using Lumina - This also fixes a bug that PlayerPayload would encode worldIds as byte (they are ushort) * Remove comment --- .../Payloads/PlayerPayload.cs | 59 +++++++------------ 1 file changed, 22 insertions(+), 37 deletions(-) diff --git a/Dalamud/Game/Text/SeStringHandling/Payloads/PlayerPayload.cs b/Dalamud/Game/Text/SeStringHandling/Payloads/PlayerPayload.cs index 07a13e5a3..55697782e 100644 --- a/Dalamud/Game/Text/SeStringHandling/Payloads/PlayerPayload.cs +++ b/Dalamud/Game/Text/SeStringHandling/Payloads/PlayerPayload.cs @@ -6,6 +6,9 @@ using Dalamud.Data; using Lumina.Excel; using Lumina.Excel.Sheets; +using Lumina.Text.Payloads; +using Lumina.Text.ReadOnly; + using Newtonsoft.Json; namespace Dalamud.Game.Text.SeStringHandling.Payloads; @@ -84,50 +87,32 @@ public class PlayerPayload : Payload /// protected override byte[] EncodeImpl() { - var chunkLen = this.playerName.Length + 7; - var bytes = new List() - { - START_BYTE, - (byte)SeStringChunkType.Interactable, (byte)chunkLen, (byte)EmbeddedInfoType.PlayerName, - /* unk */ 0x01, - (byte)(this.serverId + 1), // I didn't want to deal with single-byte values in MakeInteger, so we have to do the +1 manually - /* unk */ 0x01, - /* unk */ 0xFF, // these sometimes vary but are frequently this - (byte)(this.playerName.Length + 1), - }; - - bytes.AddRange(Encoding.UTF8.GetBytes(this.playerName)); - bytes.Add(END_BYTE); - - // TODO: should these really be here? additional payloads should come in separately already... - - // encoded names are followed by the name in plain text again - // use the payload parsing for consistency, as this is technically a new chunk - bytes.AddRange(new TextPayload(this.playerName).Encode()); - - // unsure about this entire packet, but it seems to always follow a name - bytes.AddRange(new byte[] - { - START_BYTE, (byte)SeStringChunkType.Interactable, 0x07, (byte)EmbeddedInfoType.LinkTerminator, - 0x01, 0x01, 0x01, 0xFF, 0x01, - END_BYTE, - }); - - return bytes.ToArray(); + var ssb = Lumina.Text.SeStringBuilder.SharedPool.Get(); + var res = ssb + .PushLinkCharacter(this.playerName, this.serverId) + .Append(this.playerName) + .PopLink() + .ToArray(); + Lumina.Text.SeStringBuilder.SharedPool.Return(ssb); + return res; } /// protected override void DecodeImpl(BinaryReader reader, long endOfStream) { - // unk - reader.ReadByte(); + var body = reader.ReadBytes((int)(endOfStream - reader.BaseStream.Position)); + var rosps = new ReadOnlySePayloadSpan(ReadOnlySePayloadType.Macro, MacroCode.Link, body.AsSpan()); - this.serverId = GetInteger(reader); + if (!rosps.TryGetExpression(out _, out var worldIdExpression, out _, out var characterNameExpression)) + return; - // unk - reader.ReadBytes(2); + if (!worldIdExpression.TryGetUInt(out var worldId)) + return; - var nameLen = (int)GetInteger(reader); - this.playerName = Encoding.UTF8.GetString(reader.ReadBytes(nameLen)); + if (!characterNameExpression.TryGetString(out var characterName)) + return; + + this.serverId = worldId; + this.playerName = characterName.ExtractText(); } }