mirror of
https://github.com/kwsch/PKHeX
synced 2024-11-22 20:13:06 +00:00
Add IStringConverter, impl on PKM & SaveFile
use in trash editor to translate strings, from PKM instead of SAV. Closes #4222
This commit is contained in:
parent
394f5ed707
commit
093264bc24
45 changed files with 257 additions and 121 deletions
|
@ -12,6 +12,7 @@ public sealed class FakeSaveFile : SaveFile
|
|||
public override string ChecksumInfo => string.Empty;
|
||||
public override byte Generation => 3;
|
||||
public override string GetString(ReadOnlySpan<byte> data) => string.Empty;
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer) => 0;
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option) => 0;
|
||||
public override PersonalTable3 Personal => PersonalTable.RS;
|
||||
public override int MaxEV => 0;
|
||||
|
|
|
@ -301,4 +301,11 @@ public sealed class BK4 : G4PKM
|
|||
pk4.RefreshChecksum();
|
||||
return pk4;
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter4.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter4.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter4.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -228,4 +228,11 @@ public sealed class CK3(byte[] Data) : G3PKM(Data), IShadowCapture
|
|||
pk.RefreshChecksum();
|
||||
return pk;
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter3GC.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter3GC.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter3GC.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -423,4 +423,11 @@ public sealed class PKH : PKM, IHandlerLanguage, IFormArgument, IHomeTrack, IBat
|
|||
WeightScalar = PokeSizeUtil.GetRandomScalar(rnd);
|
||||
}
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -582,7 +582,6 @@ public sealed class PA8 : PKM, ISanityChecksum,
|
|||
return tr.OT == OriginalTrainerName;
|
||||
}
|
||||
|
||||
|
||||
public void UpdateHandler(ITrainerInfo tr)
|
||||
{
|
||||
// Process to the HT if the OT of the Pokémon does not match the SAV's OT info.
|
||||
|
@ -734,4 +733,11 @@ public sealed class PA8 : PKM, ISanityChecksum,
|
|||
if (permit.IsRecordPermitted(flagIndex))
|
||||
SetMasteredRecordFlag(flagIndex, true);
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -6,7 +6,7 @@ namespace PKHeX.Core;
|
|||
|
||||
/// <summary> Generation 7 <see cref="PKM"/> format used for <see cref="GameVersion.GG"/>. </summary>
|
||||
public sealed class PB7 : G6PKM, IHyperTrain, IAwakened, IScaledSizeValue, ICombatPower, IFavorite,
|
||||
IFormArgument, IAppliedMarkings7, IHandlerUpdate
|
||||
IFormArgument, IAppliedMarkings7
|
||||
{
|
||||
public override ReadOnlySpan<ushort> ExtraBytes =>
|
||||
[
|
||||
|
@ -581,4 +581,11 @@ public sealed class PB7 : G6PKM, IHyperTrain, IAwakened, IScaledSizeValue, IComb
|
|||
5 => 4,
|
||||
_ => throw new ArgumentOutOfRangeException(nameof(characterIndex)), // never happens, characteristic is always 0-29
|
||||
};
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -146,4 +146,11 @@ public sealed class PB8 : G8PKM
|
|||
public override bool WasEgg => IsEgg || EggDay != 0;
|
||||
|
||||
public override bool HasOriginalMetLocation => base.HasOriginalMetLocation && !(LA && MetLocation == LocationsHOME.SWLA);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -248,16 +248,12 @@ public sealed class PK1 : GBPKML, IPersonalType
|
|||
return StringConverter12Transporter.GetString(OriginalTrainerTrash, Japanese);
|
||||
}
|
||||
|
||||
protected override string GetString(ReadOnlySpan<byte> data)
|
||||
{
|
||||
return StringConverter1.GetString(data, Japanese);
|
||||
}
|
||||
|
||||
protected override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength,
|
||||
StringConverterOption option = StringConverterOption.None)
|
||||
{
|
||||
return StringConverter1.SetString(destBuffer, value, maxLength, Japanese, option);
|
||||
}
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter1.GetString(data, Japanese);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter1.LoadString(data, destBuffer, Japanese);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option = StringConverterOption.None)
|
||||
=> StringConverter1.SetString(destBuffer, value, maxLength, Japanese, option);
|
||||
|
||||
/// <summary>
|
||||
/// Gets a checksum over all the entity's data using a single list to wrap all components.
|
||||
|
|
|
@ -259,15 +259,21 @@ public sealed class PK2 : GBPKML, ICaughtData2
|
|||
OriginalTrainerName = OriginalTrainerName,
|
||||
};
|
||||
|
||||
protected override string GetString(ReadOnlySpan<byte> data)
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
{
|
||||
if (Korean)
|
||||
return StringConverter2KOR.GetString(data);
|
||||
return StringConverter2.GetString(data, Language);
|
||||
}
|
||||
|
||||
protected override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength,
|
||||
StringConverterOption option = StringConverterOption.None)
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
{
|
||||
if (Korean)
|
||||
return StringConverter2KOR.LoadString(data, destBuffer);
|
||||
return StringConverter2.LoadString(data, destBuffer, Language);
|
||||
}
|
||||
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
if (Korean)
|
||||
return StringConverter2KOR.SetString(destBuffer, value, maxLength, option);
|
||||
|
|
|
@ -353,4 +353,11 @@ public sealed class PK3 : G3PKM, ISanityChecksum
|
|||
pk.ResetPartyStats();
|
||||
return pk;
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter3.GetString(data, Language);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter3.LoadString(data, destBuffer, Language);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter3.SetString(destBuffer, value, maxLength, Language, option);
|
||||
}
|
||||
|
|
|
@ -383,4 +383,11 @@ public sealed class PK4 : G4PKM
|
|||
StringConverter345.TransferGlyphs45(temp[..len]);
|
||||
StringConverter5.SetString(dest, temp[..len], len);
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter4.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter4.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter4.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -552,4 +552,11 @@ public sealed class PK5 : PKM, ISanityChecksum,
|
|||
_ => Locations.Transfer4,
|
||||
};
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter5.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter5.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter5.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -523,4 +523,11 @@ public sealed class PK6 : G6PKM, IRibbonSetEvent3, IRibbonSetEvent4, IRibbonSetC
|
|||
|
||||
return pk7; // Done!
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter6.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter6.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter6.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -547,6 +547,13 @@ public sealed class PK7 : G6PKM, IRibbonSetEvent3, IRibbonSetEvent4, IRibbonSetC
|
|||
break;
|
||||
}
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter7.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter7.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter7.SetString(destBuffer, value, maxLength, Language);
|
||||
}
|
||||
|
||||
public enum ResortEventState : byte
|
||||
|
|
|
@ -129,4 +129,11 @@ public sealed class PK8 : G8PKM, IHandlerUpdate
|
|||
public override bool BDSP => MetLocation is LocationsHOME.SWBD or LocationsHOME.SHSP;
|
||||
public override bool LA => MetLocation is LocationsHOME.SWLA;
|
||||
public override bool HasOriginalMetLocation => base.HasOriginalMetLocation && !(BDSP || LA);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -681,4 +681,11 @@ public sealed class PK9 : PKM, ISanityChecksum, ITeraType, ITechRecord, IObedien
|
|||
public override int MaxItemID => Legal.MaxItemID_9;
|
||||
public override int MaxBallID => Legal.MaxBallID_9;
|
||||
public override GameVersion MaxGameID => Legal.MaxGameID_HOME;
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -11,7 +11,7 @@ namespace PKHeX.Core;
|
|||
/// Object representing a <see cref="PKM"/>'s data and derived properties.
|
||||
/// </summary>
|
||||
[DynamicallyAccessedMembers(PublicProperties | NonPublicProperties | PublicParameterlessConstructor)]
|
||||
public abstract class PKM : ISpeciesForm, ITrainerID32, IGeneration, IShiny, ILangNick, IGameValueLimit, INature, IFatefulEncounter
|
||||
public abstract class PKM : ISpeciesForm, ITrainerID32, IGeneration, IShiny, ILangNick, IGameValueLimit, INature, IFatefulEncounter, IStringConverter
|
||||
{
|
||||
/// <summary>
|
||||
/// Valid file extensions that represent <see cref="PKM"/> data, without the leading '.'
|
||||
|
@ -148,6 +148,10 @@ public abstract class PKM : ISpeciesForm, ITrainerID32, IGeneration, IShiny, ILa
|
|||
public virtual byte Fullness { get => 0; set { } }
|
||||
public virtual int AbilityNumber { get => 0; set { } }
|
||||
|
||||
public abstract string GetString(ReadOnlySpan<byte> data);
|
||||
public abstract int LoadString(ReadOnlySpan<byte> data, Span<char> text);
|
||||
public abstract int SetString(Span<byte> data, ReadOnlySpan<char> text, int length, StringConverterOption option);
|
||||
|
||||
/// <summary>
|
||||
/// The date the Pokémon was met.
|
||||
/// </summary>
|
||||
|
|
|
@ -345,4 +345,11 @@ public sealed class RK4 : G4PKM
|
|||
pk4.RefreshChecksum();
|
||||
return pk4;
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter4.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter4.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter4.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -212,4 +212,11 @@ public sealed class SK2 : GBPKM, ICaughtData2
|
|||
|
||||
public bool IsPossible(bool japanese) => japanese ? IsJapanese(Data) : IsEnglish(Data);
|
||||
public void SwapLanguage() => IsEncodingJapanese ^= true;
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter2.GetString(data, Language);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter2.LoadString(data, destBuffer, Language);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter2.SetString(destBuffer, value, maxLength, Language, option);
|
||||
}
|
||||
|
|
|
@ -61,11 +61,6 @@ public abstract class GBPKML : GBPKM
|
|||
}
|
||||
}
|
||||
|
||||
protected abstract string GetString(ReadOnlySpan<byte> data);
|
||||
|
||||
protected abstract int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength,
|
||||
StringConverterOption option = StringConverterOption.None);
|
||||
|
||||
public sealed override string Nickname
|
||||
{
|
||||
get => GetString(NicknameTrash);
|
||||
|
|
10
PKHeX.Core/PKM/Strings/IStringConverter.cs
Normal file
10
PKHeX.Core/PKM/Strings/IStringConverter.cs
Normal file
|
@ -0,0 +1,10 @@
|
|||
using System;
|
||||
|
||||
namespace PKHeX.Core;
|
||||
|
||||
public interface IStringConverter
|
||||
{
|
||||
string GetString(ReadOnlySpan<byte> data);
|
||||
int LoadString(ReadOnlySpan<byte> data, Span<char> text);
|
||||
int SetString(Span<byte> data, ReadOnlySpan<char> text, int length, StringConverterOption option);
|
||||
}
|
|
@ -232,4 +232,11 @@ public sealed class XK3 : G3PKM, IShadowCapture
|
|||
90 or 91 or 92 => true, // Pokespot: Rock / Oasis / Cave
|
||||
_ => false,
|
||||
};
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter3GC.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter3GC.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter3GC.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -547,10 +547,10 @@ public sealed class SAV1 : SaveFile, ILangDeviantSave, IEventFlagArray, IEventWo
|
|||
}
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter1.GetString(data, Japanese);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter1.GetString(data, Japanese);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter1.LoadString(data, destBuffer, Japanese);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter1.SetString(destBuffer, value, maxLength, Japanese, option);
|
||||
}
|
||||
=> StringConverter1.SetString(destBuffer, value, maxLength, Japanese, option);
|
||||
}
|
||||
|
|
|
@ -580,15 +580,8 @@ public sealed class SAV2 : SaveFile, ILangDeviantSave, IEventFlagArray, IEventWo
|
|||
get => Data[Offsets.Party]; protected set => Data[Offsets.Party] = (byte)value;
|
||||
}
|
||||
|
||||
public override int GetBoxOffset(int box)
|
||||
{
|
||||
return (box * SIZE_BOX_AS_SINGLES);
|
||||
}
|
||||
|
||||
public override int GetPartyOffset(int slot)
|
||||
{
|
||||
return (BoxCount * SIZE_BOX_AS_SINGLES) + (slot * SIZE_STORED);
|
||||
}
|
||||
public override int GetBoxOffset(int box) => box * SIZE_BOX_AS_SINGLES;
|
||||
public override int GetPartyOffset(int slot) => (BoxCount * SIZE_BOX_AS_SINGLES) + (slot * SIZE_STORED);
|
||||
|
||||
public override int CurrentBox
|
||||
{
|
||||
|
@ -801,6 +794,13 @@ public sealed class SAV2 : SaveFile, ILangDeviantSave, IEventFlagArray, IEventWo
|
|||
return StringConverter2.GetString(data, Language);
|
||||
}
|
||||
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> text)
|
||||
{
|
||||
if (Korean)
|
||||
return StringConverter2KOR.LoadString(data, text);
|
||||
return StringConverter2.LoadString(data, text, Language);
|
||||
}
|
||||
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
if (Korean)
|
||||
|
|
|
@ -600,12 +600,12 @@ public abstract class SAV3 : SaveFile, ILangDeviantSave, IEventFlag37, IBoxDetai
|
|||
public abstract bool NationalDex { get; set; }
|
||||
#endregion
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data) => StringConverter3.GetString(data, Japanese);
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter3.GetString(data, Japanese);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter3.LoadString(data, destBuffer, Japanese);
|
||||
public sealed override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter3.SetString(destBuffer, value, maxLength, Japanese, option);
|
||||
}
|
||||
=> StringConverter3.SetString(destBuffer, value, maxLength, Japanese, option);
|
||||
|
||||
protected abstract int MailOffset { get; }
|
||||
public int GetMailOffset(int index) => (index * Mail3.SIZE) + MailOffset;
|
||||
|
|
|
@ -288,10 +288,10 @@ public sealed class SAV3Colosseum : SaveFile, IGCSaveFile, IBoxDetailName, IDayc
|
|||
public void SetDaycareEXP(int index, uint value) => WriteUInt32BigEndian(Data[(DaycareOffset + 4)..], value);
|
||||
public Memory<byte> GetDaycareSlot(int slot) => Raw.Slice(DaycareOffset + 8, PokeCrypto.SIZE_3CSTORED);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter3GC.GetString(data);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter3GC.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter3GC.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter3GC.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
=> StringConverter3GC.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -207,10 +207,10 @@ public sealed class SAV3RSBox : SaveFile, IGCSaveFile, IBoxDetailName, IBoxDetai
|
|||
WriteUInt16LittleEndian(data[(PokeCrypto.SIZE_3STORED + 2)..], pk.SID16);
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter3.GetString(data, Japanese);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter3.GetString(data, Japanese);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter3.LoadString(data, destBuffer, Japanese);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter3.SetString(destBuffer, value, maxLength, Japanese, option);
|
||||
}
|
||||
=> StringConverter3.SetString(destBuffer, value, maxLength, Japanese, option);
|
||||
}
|
||||
|
|
|
@ -452,10 +452,10 @@ public sealed class SAV3XD : SaveFile, IGCSaveFile, IBoxDetailName, IDaycareStor
|
|||
public void SetDaycareEXP(int index, uint value) => WriteUInt32BigEndian(Data.AsSpan(DaycareOffset + 4), value);
|
||||
public Memory<byte> GetDaycareSlot(int slot) => Data.AsMemory(DaycareOffset + 8, PokeCrypto.SIZE_3XSTORED);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter3GC.GetString(data);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter3GC.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter3GC.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter3GC.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
=> StringConverter3GC.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -478,12 +478,12 @@ public abstract class SAV4 : SaveFile, IEventFlag37, IDaycareStorage, IDaycareRa
|
|||
}
|
||||
}
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data) => StringConverter4.GetString(data);
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter4.GetString(data);
|
||||
public sealed override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter4.LoadString(data, destBuffer);
|
||||
public sealed override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter4.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
=> StringConverter4.SetString(destBuffer, value, maxLength, option);
|
||||
|
||||
#region Event Flag/Event Work
|
||||
public bool GetEventFlag(int flagNumber)
|
||||
|
|
|
@ -367,7 +367,10 @@ public sealed class SAV4BR : SaveFile, IBoxDetailName
|
|||
}
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter4GC.GetStringUnicode(data);
|
||||
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option) => StringConverter4GC.SetStringUnicode(value, destBuffer, maxLength, option);
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter4GC.GetStringUnicode(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter4GC.LoadStringUnicode(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter4GC.SetStringUnicode(value, destBuffer, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -117,12 +117,12 @@ public abstract class SAV5 : SaveFile, ISaveBlock5BW, IEventFlagProvider37, IBox
|
|||
public override bool GetCaught(ushort species) => Zukan.GetCaught(species);
|
||||
public override bool GetSeen(ushort species) => Zukan.GetSeen(species);
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data) => StringConverter5.GetString(data);
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter5.GetString(data);
|
||||
public sealed override int LoadString(ReadOnlySpan<byte> data, Span<char> result)
|
||||
=> StringConverter5.LoadString(data, result);
|
||||
public sealed override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter5.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
=> StringConverter5.SetString(destBuffer, value, maxLength, option);
|
||||
|
||||
// DLC
|
||||
private int CGearSkinInfoOffset => CGearInfoOffset + (this is SAV5B2W2 ? 0x10 : 0) + 0x24;
|
||||
|
|
|
@ -138,12 +138,12 @@ public abstract class SAV6 : SAV_BEEF, ITrainerStatRecord, ISaveBlock6Core, IReg
|
|||
protected set => Data[Party + (6 * SIZE_PARTY)] = (byte)value;
|
||||
}
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data) => StringConverter6.GetString(data);
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter6.GetString(data);
|
||||
public sealed override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter6.LoadString(data, destBuffer);
|
||||
public sealed override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter6.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
=> StringConverter6.SetString(destBuffer, value, maxLength, option);
|
||||
|
||||
public int GetRecord(int recordID) => Records.GetRecord(recordID);
|
||||
public int GetRecordOffset(int recordID) => Records.GetRecordOffset(recordID);
|
||||
|
|
|
@ -109,12 +109,12 @@ public abstract class SAV7 : SAV_BEEF, ITrainerStatRecord, ISaveBlock7Main, IReg
|
|||
public override bool IsVersionValid() =>
|
||||
Version is GameVersion.SN or GameVersion.MN or GameVersion.US or GameVersion.UM;
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data) => StringConverter7.GetString(data);
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter7.GetString(data);
|
||||
public sealed override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter7.LoadString(data, destBuffer);
|
||||
public sealed override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter7.SetString(destBuffer, value, maxLength, Language, option);
|
||||
}
|
||||
=> StringConverter7.SetString(destBuffer, value, maxLength, Language, option);
|
||||
|
||||
// Player Information
|
||||
public override uint ID32 { get => MyStatus.ID32; set => MyStatus.ID32 = value; }
|
||||
|
|
|
@ -124,12 +124,12 @@ public sealed class SAV7b : SAV_BEEF, ISaveBlock7b, IGameSync, IMysteryGiftStora
|
|||
return result;
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter8.GetString(data);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter8.SetString(destBuffer, value, maxLength);
|
||||
}
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength);
|
||||
|
||||
public override bool IsVersionValid() => Version is GameVersion.GP or GameVersion.GE;
|
||||
|
||||
|
|
|
@ -244,12 +244,12 @@ public sealed class SAV8BS : SaveFile, ISaveFileRevision, ITrainerStatRecord, IE
|
|||
|
||||
public override bool IsVersionValid() => Version is GameVersion.BD or GameVersion.SP;
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter8.GetString(data);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
}
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
|
||||
// Player Information
|
||||
public override uint ID32 { get => MyStatus.ID32; set => MyStatus.ID32 = value; }
|
||||
|
|
|
@ -38,8 +38,12 @@ public sealed class SAV8LA : SaveFile, ISaveBlock8LA, ISCBlockArray, ISaveFileRe
|
|||
_ => throw new ArgumentOutOfRangeException(nameof(SaveRevision)),
|
||||
};
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter8.GetString(data);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option) => StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
|
||||
public override void CopyChangesFrom(SaveFile sav)
|
||||
{
|
||||
|
|
|
@ -158,7 +158,10 @@ public sealed class SAV8SWSH : SaveFile, ISaveBlock8SWSH, ITrainerStatRecord, IS
|
|||
|
||||
public override bool IsVersionValid() => Version is GameVersion.SW or GameVersion.SH;
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter8.GetString(data);
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
|
||||
|
|
|
@ -164,7 +164,10 @@ public sealed class SAV9SV : SaveFile, ISaveBlock9Main, ISCBlockArray, ISaveFile
|
|||
|
||||
public override bool IsVersionValid() => Version is GameVersion.SL or GameVersion.VL;
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter8.GetString(data);
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter8.GetString(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter8.LoadString(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter8.SetString(destBuffer, value, maxLength, option);
|
||||
|
||||
|
|
|
@ -93,12 +93,12 @@ public abstract class SAV_STADIUM : SaveFile, ILangDeviantSave
|
|||
return result;
|
||||
}
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data) => StringConverter1.GetString(data, Japanese);
|
||||
|
||||
public sealed override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter1.GetString(data, Japanese);
|
||||
public sealed override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter1.LoadString(data, destBuffer, Japanese);
|
||||
public sealed override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter1.SetString(destBuffer, value, maxLength, Japanese, option);
|
||||
}
|
||||
=> StringConverter1.SetString(destBuffer, value, maxLength, Japanese, option);
|
||||
|
||||
/// <summary>
|
||||
/// Some emulators emit with system architecture endianness (Little Endian) instead of the original Big Endian ordering.
|
||||
|
|
|
@ -8,7 +8,7 @@ namespace PKHeX.Core;
|
|||
/// <summary>
|
||||
/// Base Class for Save Files
|
||||
/// </summary>
|
||||
public abstract class SaveFile : ITrainerInfo, IGameValueLimit, IGeneration, IVersion
|
||||
public abstract class SaveFile : ITrainerInfo, IGameValueLimit, IGeneration, IVersion, IStringConverter
|
||||
{
|
||||
// General Object Properties
|
||||
public byte[] Data;
|
||||
|
@ -78,6 +78,7 @@ public abstract class SaveFile : ITrainerInfo, IGameValueLimit, IGeneration, IVe
|
|||
}
|
||||
|
||||
public abstract string GetString(ReadOnlySpan<byte> data);
|
||||
public abstract int LoadString(ReadOnlySpan<byte> data, Span<char> text);
|
||||
public abstract int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option);
|
||||
#endregion
|
||||
|
||||
|
|
|
@ -54,7 +54,8 @@ public abstract class BulkStorage : SaveFile
|
|||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter.GetString(data, Generation, blank.Japanese, IsBigEndian, Language);
|
||||
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter.LoadString(data, destBuffer, Generation, blank.Japanese, IsBigEndian, Language);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
=> StringConverter.SetString(destBuffer, value, maxLength, option: option, generation: Generation, jp: blank.Japanese, isBigEndian: IsBigEndian, language: Language);
|
||||
}
|
||||
|
|
|
@ -45,7 +45,6 @@ public sealed class SAV4Ranch : BulkStorage, ISaveFileRevision
|
|||
protected override bool IsSlotSwapProtected(int box, int slot) => IsSlotOverwriteProtected(box, slot);
|
||||
public override bool IsPKMPresent(ReadOnlySpan<byte> data) => EntityDetection.IsPresentSAV4Ranch(data);
|
||||
|
||||
|
||||
private readonly GameVersion _version;
|
||||
public override GameVersion Version { get => _version; set { } }
|
||||
public SAV4Ranch(byte[] data) : base(data, typeof(RK4), 0)
|
||||
|
@ -251,10 +250,10 @@ public sealed class SAV4Ranch : BulkStorage, ISaveFileRevision
|
|||
set { var time = PlayedSpan; PlayedSpan = time - TimeSpan.FromSeconds(time.Seconds) + TimeSpan.FromSeconds(value); }
|
||||
}
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data) => StringConverter4GC.GetStringUnicode(data);
|
||||
|
||||
public override string GetString(ReadOnlySpan<byte> data)
|
||||
=> StringConverter4GC.GetStringUnicode(data);
|
||||
public override int LoadString(ReadOnlySpan<byte> data, Span<char> destBuffer)
|
||||
=> StringConverter4GC.LoadStringUnicode(data, destBuffer);
|
||||
public override int SetString(Span<byte> destBuffer, ReadOnlySpan<char> value, int maxLength, StringConverterOption option)
|
||||
{
|
||||
return StringConverter4GC.SetStringUnicode(value, destBuffer, maxLength, option);
|
||||
}
|
||||
=> StringConverter4GC.SetStringUnicode(value, destBuffer, maxLength, option);
|
||||
}
|
||||
|
|
|
@ -1408,8 +1408,7 @@ public sealed partial class PKMEditor : UserControl, IMainEditor
|
|||
return;
|
||||
}
|
||||
|
||||
var sav = RequestSaveFile;
|
||||
using var d = new TrashEditor(tb, trash, sav);
|
||||
using var d = new TrashEditor(tb, trash, Entity, Entity.Format);
|
||||
d.ShowDialog();
|
||||
tb.Text = d.FinalString;
|
||||
d.FinalBytes.CopyTo(trash);
|
||||
|
|
|
@ -9,15 +9,15 @@ namespace PKHeX.WinForms;
|
|||
|
||||
public partial class TrashEditor : Form
|
||||
{
|
||||
private readonly SaveFile SAV;
|
||||
private readonly IStringConverter Converter;
|
||||
|
||||
public TrashEditor(TextBoxBase TB_NN, SaveFile sav) : this(TB_NN, [], sav) { }
|
||||
public TrashEditor(TextBoxBase TB_NN, SaveFile sav) : this(TB_NN, [], sav, sav.Generation) { }
|
||||
|
||||
public TrashEditor(TextBoxBase TB_NN, Span<byte> raw, SaveFile sav)
|
||||
public TrashEditor(TextBoxBase TB_NN, Span<byte> raw, IStringConverter converter, byte generation)
|
||||
{
|
||||
InitializeComponent();
|
||||
WinFormsUtil.TranslateInterface(this, Main.CurrentLanguage);
|
||||
SAV = sav;
|
||||
Converter = converter;
|
||||
|
||||
FinalString = TB_NN.Text;
|
||||
|
||||
|
@ -25,7 +25,7 @@ public partial class TrashEditor : Form
|
|||
if (raw.Length != 0)
|
||||
{
|
||||
Raw = FinalBytes = raw.ToArray();
|
||||
AddTrashEditing(raw.Length);
|
||||
AddTrashEditing(raw.Length, generation);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -33,7 +33,7 @@ public partial class TrashEditor : Form
|
|||
}
|
||||
|
||||
var f = FontUtil.GetPKXFont();
|
||||
AddCharEditing(f);
|
||||
AddCharEditing(f, generation);
|
||||
TB_Text.MaxLength = TB_NN.MaxLength;
|
||||
TB_Text.Text = TB_NN.Text;
|
||||
TB_Text.Font = f;
|
||||
|
@ -76,9 +76,9 @@ public partial class TrashEditor : Form
|
|||
Close();
|
||||
}
|
||||
|
||||
private void AddCharEditing(Font f)
|
||||
private void AddCharEditing(Font f, byte generation)
|
||||
{
|
||||
var chars = GetChars(SAV.Generation);
|
||||
var chars = GetChars(generation);
|
||||
if (chars.Length == 0)
|
||||
return;
|
||||
|
||||
|
@ -94,11 +94,11 @@ public partial class TrashEditor : Form
|
|||
}
|
||||
}
|
||||
|
||||
private void AddTrashEditing(int count)
|
||||
private void AddTrashEditing(int count, byte generation)
|
||||
{
|
||||
FLP_Hex.Visible = true;
|
||||
GB_Trash.Visible = true;
|
||||
NUD_Generation.Value = SAV.Generation;
|
||||
NUD_Generation.Value = generation;
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
var l = GetLabel($"${i:X2}");
|
||||
|
@ -127,7 +127,7 @@ public partial class TrashEditor : Form
|
|||
CB_Species.DataSource = new BindingSource(GameInfo.SpeciesDataSource, null);
|
||||
|
||||
CB_Language.InitializeBinding();
|
||||
CB_Language.DataSource = GameInfo.LanguageDataSource(SAV.Generation);
|
||||
CB_Language.DataSource = GameInfo.LanguageDataSource(generation);
|
||||
}
|
||||
|
||||
private void UpdateNUD(object sender, EventArgs e)
|
||||
|
@ -200,11 +200,11 @@ public partial class TrashEditor : Form
|
|||
private byte[] SetString(ReadOnlySpan<char> text)
|
||||
{
|
||||
Span<byte> temp = stackalloc byte[Raw.Length];
|
||||
var written = SAV.SetString(temp, text, text.Length, StringConverterOption.None);
|
||||
var written = Converter.SetString(temp, text, text.Length, StringConverterOption.None);
|
||||
return temp[..written].ToArray();
|
||||
}
|
||||
|
||||
private string GetString() => SAV.GetString(Raw);
|
||||
private string GetString() => Converter.GetString(Raw);
|
||||
|
||||
// Helpers
|
||||
private static Label GetLabel(string str) => new() { Text = str, AutoSize = false, Size = new Size(40, 24), TextAlign = ContentAlignment.MiddleRight };
|
||||
|
|
|
@ -399,7 +399,7 @@ public partial class SAV_HallOfFame : Form
|
|||
var nicktrash = Data.Slice(0x18 + offset, 26);
|
||||
var text = tb.Text;
|
||||
SAV.SetString(nicktrash, text, 12, StringConverterOption.ClearZero);
|
||||
var d = new TrashEditor(tb, nicktrash, SAV);
|
||||
var d = new TrashEditor(tb, nicktrash, SAV, SAV.Generation);
|
||||
d.ShowDialog();
|
||||
tb.Text = d.FinalString;
|
||||
d.FinalBytes.CopyTo(nicktrash);
|
||||
|
|
Loading…
Reference in a new issue