Expose Context for SaveFile/ITrainerInfo

This commit is contained in:
Kurt
2022-06-03 19:08:46 -07:00
parent dde70f4962
commit ab723af640
30 changed files with 65 additions and 40 deletions

View File

@@ -14,7 +14,7 @@ public static List<string> GetMetLocationSuggestionMessage(PKM pkm, int level, i
var suggestion = new List<string> { MsgPKMSuggestionStart };
if (pkm.Format >= 3)
{
var metList = GameInfo.GetLocationList((GameVersion)pkm.Version, pkm.Format, egg: false);
var metList = GameInfo.GetLocationList((GameVersion)pkm.Version, pkm.Context, egg: false);
var locationName = metList.First(loc => loc.Value == location).Text;
suggestion.Add($"{MsgPKMSuggestionMetLocation} {locationName}");
suggestion.Add($"{MsgPKMSuggestionMetLevel} {level}");

View File

@@ -36,6 +36,7 @@ public sealed class FakeSaveFile : SaveFile
protected override PKM GetPKM(byte[] data) => BlankPKM;
protected override byte[] DecryptPKM(byte[] data) => data;
public override PKM BlankPKM => new PK3();
public override EntityContext Context => EntityContext.Gen3;
protected override int SIZE_STORED => 0;
protected override int SIZE_PARTY => 0;
}

View File

@@ -72,12 +72,12 @@ public static string GetLocationName(bool isEggLocation, int location, int forma
/// Gets the location list for a specific version, which can retrieve either met locations or egg locations.
/// </summary>
/// <param name="version">Version to retrieve for</param>
/// <param name="pkmFormat">Generation to retrieve for</param>
/// <param name="context">Current format context</param>
/// <param name="egg">Egg Locations are to be retrieved instead of regular Met Locations</param>
/// <returns>Consumable list of met locations</returns>
public static IReadOnlyList<ComboItem> GetLocationList(GameVersion version, int pkmFormat, bool egg = false)
public static IReadOnlyList<ComboItem> GetLocationList(GameVersion version, EntityContext context, bool egg = false)
{
return Sources.Met.GetLocationList(version, pkmFormat, egg);
return Sources.Met.GetLocationList(version, context, egg);
}
}
}

View File

@@ -196,21 +196,22 @@ private static List<ComboItem> CreateGen8b(GameStrings s)
/// Fetches a Met Location list for a <see cref="version"/> that has been transferred away from and overwritten.
/// </summary>
/// <param name="version">Origin version</param>
/// <param name="currentGen">Current save file generation</param>
/// <param name="context">Current format context</param>
/// <param name="egg">True if an egg location list, false if a regular met location list</param>
/// <returns>Met location list</returns>
public IReadOnlyList<ComboItem> GetLocationList(GameVersion version, int currentGen, bool egg = false)
public IReadOnlyList<ComboItem> GetLocationList(GameVersion version, EntityContext context, bool egg = false)
{
if (currentGen == 2)
if (context == EntityContext.Gen2)
return MetGen2;
if (egg && version < W && currentGen >= 5)
return MetGen4;
var result = GetLocationListInternal(version, currentGen);
IReadOnlyList<ComboItem> result;
if (egg && version < W && context.Generation() >= 5)
result = MetGen4;
else
result = GetLocationListInternal(version, context);
// Insert the BDSP none location if the format requires it.
if (currentGen == 8 && !BDSP.Contains(version))
if (context is EntityContext.Gen8b && !BDSP.Contains(version))
{
var list = new List<ComboItem>(result.Count + 1);
list.AddRange(result);
@@ -221,17 +222,17 @@ public IReadOnlyList<ComboItem> GetLocationList(GameVersion version, int current
return result;
}
private IReadOnlyList<ComboItem> GetLocationListInternal(GameVersion version, int currentGen)
private IReadOnlyList<ComboItem> GetLocationListInternal(GameVersion version, EntityContext context)
{
return version switch
{
CXD when currentGen == 3 => MetGen3CXD,
R or S when currentGen == 3 => Partition1(MetGen3, z => z <= 87), // Ferry
E when currentGen == 3 => Partition1(MetGen3, z => z is <= 87 or >= 197 and <= 212), // Trainer Hill
FR or LG when currentGen == 3 => Partition1(MetGen3, z => z is > 87 and < 197), // Celadon Dept.
D or P when currentGen == 4 => Partition2(MetGen4, z => z <= 111, 4), // Battle Park
Pt when currentGen == 4 => Partition2(MetGen4, z => z <= 125, 4), // Rock Peak Ruins
HG or SS when currentGen == 4 => Partition2(MetGen4, z => z is > 125 and < 234, 4), // Celadon Dept.
CXD when context == EntityContext.Gen3 => MetGen3CXD,
R or S when context == EntityContext.Gen3 => Partition1(MetGen3, z => z <= 87), // Ferry
E when context == EntityContext.Gen3 => Partition1(MetGen3, z => z is <= 87 or >= 197 and <= 212), // Trainer Hill
FR or LG when context == EntityContext.Gen3 => Partition1(MetGen3, z => z is > 87 and < 197), // Celadon Dept.
D or P when context == EntityContext.Gen4 => Partition2(MetGen4, z => z <= 111, 4), // Battle Park
Pt when context == EntityContext.Gen4 => Partition2(MetGen4, z => z <= 125, 4), // Rock Peak Ruins
HG or SS when context == EntityContext.Gen4 => Partition2(MetGen4, z => z is > 125 and < 234, 4), // Celadon Dept.
B or W => MetGen5,
B2 or W2 => Partition2(MetGen5, z => z <= 116), // Abyssal Ruins
@@ -245,7 +246,7 @@ private IReadOnlyList<ComboItem> GetLocationListInternal(GameVersion version, in
SW or SH => Partition2(MetGen8, z => z < 400),
BD or SP => Partition2(MetGen8b, z => z < 628),
PLA => Partition2(MetGen8a, z => z < 512),
_ => new List<ComboItem>(GetLocationListModified(version, currentGen)),
_ => new List<ComboItem>(GetLocationListModified(version, context)),
};
static IReadOnlyList<ComboItem> Partition1(IReadOnlyList<ComboItem> list, Func<int, bool> criteria)
@@ -288,12 +289,12 @@ static IReadOnlyList<ComboItem> Partition1(IReadOnlyList<ComboItem> list, Func<i
/// Fetches a Met Location list for a <see cref="version"/> that has been transferred away from and overwritten.
/// </summary>
/// <param name="version">Origin version</param>
/// <param name="currentGen">Current save file generation</param>
/// <param name="context">Current format context</param>
/// <returns>Met location list</returns>
private IReadOnlyList<ComboItem> GetLocationListModified(GameVersion version, int currentGen) => version switch
private IReadOnlyList<ComboItem> GetLocationListModified(GameVersion version, EntityContext context) => version switch
{
<= CXD when currentGen == 4 => MetGen4Transfer ??= CreateGen4Transfer(),
< X when currentGen >= 5 => MetGen5Transfer ??= CreateGen5Transfer(),
<= CXD when context == EntityContext.Gen4 => MetGen4Transfer ??= CreateGen4Transfer(),
< X when context.Generation() >= 5 => MetGen5Transfer ??= CreateGen5Transfer(),
_ => Array.Empty<ComboItem>(),
};
}

View File

@@ -11,6 +11,7 @@ public interface ITrainerInfo : ITrainerID
int Language { get; }
int Generation { get; }
EntityContext Context { get; }
}
public static partial class Extensions

View File

@@ -15,6 +15,7 @@ public sealed record SimpleTrainerInfo : ITrainerInfo, IRegionOrigin
public int Game { get; }
public int Generation { get; set; } = PKX.Generation;
public EntityContext Context { get; set; } = PKX.Context;
public SimpleTrainerInfo(GameVersion game = GameVersion.SW)
{

View File

@@ -9,6 +9,7 @@ public static class PKX
{
internal static readonly PersonalTable Personal = PersonalTable.LA;
public const int Generation = 8;
public const EntityContext Context = EntityContext.Gen8a;
/// <summary>
/// Reorders (in place) the input array of stats to have the Speed value last rather than before the SpA/SpD stats.

View File

@@ -226,6 +226,7 @@ private int GetBoxRawDataOffset(int box)
public override int MaxEV => 65535;
public override int MaxIV => 15;
public override int Generation => 1;
public override EntityContext Context => EntityContext.Gen1;
protected override int GiftCountMax => 0;
public override int OTLength => Japanese ? 5 : 7;
public override int NickLength => Japanese ? 5 : 10;

View File

@@ -20,6 +20,7 @@ public sealed class SAV1Stadium : SAV_STADIUM
protected override SaveFile CloneInternal() => new SAV1Stadium((byte[])Data.Clone(), Japanese);
public override int Generation => 1;
public override EntityContext Context => EntityContext.Gen1;
private int StringLength => Japanese ? StringLengthJ : StringLengthU;
private const int StringLengthJ = 6;
private const int StringLengthU = 11;

View File

@@ -21,6 +21,7 @@ public sealed class SAV1StadiumJ : SAV_STADIUM
protected override SaveFile CloneInternal() => new SAV1StadiumJ((byte[])Data.Clone());
public override int Generation => 1;
public override EntityContext Context => EntityContext.Gen1;
private const int StringLength = 6; // Japanese Only
public override int OTLength => StringLength;
public override int NickLength => StringLength;

View File

@@ -280,6 +280,7 @@ protected override byte[] GetFinalData()
public override int MaxEV => 65535;
public override int MaxIV => 15;
public override int Generation => 2;
public override EntityContext Context => EntityContext.Gen2;
protected override int GiftCountMax => 0;
public override int OTLength => Japanese || Korean ? 5 : 7;
public override int NickLength => Japanese || Korean ? 5 : 10;

View File

@@ -20,6 +20,7 @@ public sealed class SAV2Stadium : SAV_STADIUM
protected override SaveFile CloneInternal() => new SAV2Stadium((byte[])Data.Clone(), Japanese);
public override int Generation => 2;
public override EntityContext Context => EntityContext.Gen2;
private const int StringLength = 12;
public override int OTLength => StringLength;
public override int NickLength => StringLength;

View File

@@ -171,6 +171,7 @@ protected sealed override byte[] GetFinalData()
public sealed override int BoxCount => 14;
public sealed override int MaxEV => 255;
public sealed override int Generation => 3;
public sealed override EntityContext Context => EntityContext.Gen3;
protected sealed override int GiftCountMax => 1;
public sealed override int OTLength => 7;
public sealed override int NickLength => 10;

View File

@@ -147,6 +147,7 @@ protected override SaveFile CloneInternal()
public override int MaxEV => 255;
public override int Generation => 3;
public override EntityContext Context => EntityContext.Gen3;
protected override int GiftCountMax => 1;
public override int OTLength => 10; // as evident by Mattle Ho-Oh
public override int NickLength => 10;

View File

@@ -116,6 +116,7 @@ protected override SaveFile CloneInternal()
public override int MaxEV => 255;
public override int Generation => 3;
public override EntityContext Context => EntityContext.Gen3;
protected override int GiftCountMax => 1;
public override int OTLength => 7;
public override int NickLength => 10;

View File

@@ -180,6 +180,7 @@ protected override SaveFile CloneInternal()
public override int MaxEV => 255;
public override int Generation => 3;
public override EntityContext Context => EntityContext.Gen3;
protected override int GiftCountMax => 1;
public override int OTLength => 7;
public override int NickLength => 10;

View File

@@ -79,6 +79,7 @@ public sealed override void CopyChangesFrom(SaveFile sav)
public sealed override int BoxCount => 18;
public sealed override int MaxEV => 255;
public sealed override int Generation => 4;
public override EntityContext Context => EntityContext.Gen4;
public int EventFlagCount => 0xB60; // 2912
public int EventWorkCount => (EventFlag - EventWork) >> 1;
protected sealed override int GiftCountMax => 11;

View File

@@ -106,6 +106,7 @@ public int CurrentSlot
public override int MaxEV => 255;
public override int Generation => 4;
public override EntityContext Context => EntityContext.Gen4;
protected override int GiftCountMax => 1;
public override int OTLength => 7;
public override int NickLength => 10;

View File

@@ -24,6 +24,7 @@ public abstract class SAV5 : SaveFile, ISaveBlock5BW, IEventFlag37
public override int BoxCount => 24;
public override int MaxEV => 255;
public override int Generation => 5;
public override EntityContext Context => EntityContext.Gen5;
public override int OTLength => 7;
public override int NickLength => 10;
protected override int GiftCountMax => 12;

View File

@@ -25,6 +25,7 @@ public abstract class SAV6 : SAV_BEEF, ITrainerStatRecord, ISaveBlock6Core, IReg
public override int BoxCount => 31;
public override int MaxEV => 252;
public override int Generation => 6;
public override EntityContext Context => EntityContext.Gen6;
protected override int GiftCountMax => 24;
protected override int GiftFlagMax => 0x100 * 8;
public int EventFlagCount => 8 * 0x1A0;

View File

@@ -73,6 +73,7 @@ protected void ReloadBattleTeams()
public override int BoxCount => 32;
public override int MaxEV => 252;
public override int Generation => 7;
public override EntityContext Context => EntityContext.Gen7;
protected override int GiftCountMax => 48;
protected override int GiftFlagMax => 0x100 * 8;
public abstract int EventFlagCount { get; }

View File

@@ -65,6 +65,7 @@ private void Initialize()
// Feature Overrides
public override int Generation => 7;
public override EntityContext Context => EntityContext.Gen7b;
public override int MaxMoveID => Legal.MaxMoveID_7b;
public override int MaxSpeciesID => Legal.MaxSpeciesID_7b;
public override int MaxItemID => Legal.MaxItemID_7b;

View File

@@ -109,6 +109,7 @@ private void Initialize()
public override int MaxEV => 252;
public override int Generation => 8;
public override EntityContext Context => EntityContext.Gen8b;
public override PersonalTable Personal => PersonalTable.BDSP;
public override int OTLength => 12;
public override int NickLength => 12;

View File

@@ -62,6 +62,7 @@ public override void CopyChangesFrom(SaveFile sav)
public override Type PKMType => typeof(PA8);
public override int MaxEV => 252;
public override int Generation => 8;
public override EntityContext Context => EntityContext.Gen8a;
public override int OTLength => 12;
public override int NickLength => 12;

View File

@@ -148,6 +148,7 @@ private void Initialize()
public override int BoxCount => BoxLayout8.BoxCount;
public override int MaxEV => 252;
public override int Generation => 8;
public override EntityContext Context => EntityContext.Gen8;
public override int OTLength => 12;
public override int NickLength => 12;
protected override PKM GetPKM(byte[] data) => new PK8(data);

View File

@@ -63,6 +63,7 @@ protected virtual byte[] GetFinalData()
public abstract bool ChecksumsValid { get; }
public abstract string ChecksumInfo { get; }
public abstract int Generation { get; }
public abstract EntityContext Context { get; }
#endregion
#region Savedata Container Handling

View File

@@ -35,6 +35,7 @@ protected BulkStorage(byte[] data, Type t, int start, int slotsPerBox = 30) : ba
protected override int SIZE_PARTY => blank.SIZE_PARTY;
public sealed override int MaxEV => blank.MaxEV;
public sealed override int Generation => blank.Format;
public sealed override EntityContext Context => blank.Context;
public sealed override int MaxMoveID => blank.MaxMoveID;
public sealed override int MaxSpeciesID => blank.MaxSpeciesID;
public sealed override int MaxAbilityID => blank.MaxAbilityID;

View File

@@ -146,7 +146,7 @@ public bool HideSecretValues
/// </summary>
private GameVersion origintrack;
private int originFormat = -1;
private EntityContext originFormat = EntityContext.Invalid;
/// <summary>
/// Action to perform when loading a PKM to the editor GUI.
@@ -1146,7 +1146,7 @@ private void UpdateOriginGame(object sender, EventArgs e)
GameVersion version = (GameVersion)WinFormsUtil.GetIndex(CB_GameOrigin);
if (version.IsValidSavedVersion())
{
CheckMetLocationChange(version, Entity.Format);
CheckMetLocationChange(version, Entity.Context);
if (FieldsLoaded)
Entity.Version = (int)version;
}
@@ -1168,23 +1168,23 @@ private void UpdateOriginGame(object sender, EventArgs e)
UpdateLegality();
}
private void CheckMetLocationChange(GameVersion version, int format)
private void CheckMetLocationChange(GameVersion version, EntityContext context)
{
// Does the list of locations need to be changed to another group?
var group = GameUtil.GetMetLocationVersionGroup(version);
if (group != origintrack || format != originFormat)
ReloadMetLocations(version, format);
if (group != origintrack || context != originFormat)
ReloadMetLocations(version, context);
origintrack = group;
originFormat = format;
originFormat = context;
}
private void ReloadMetLocations(GameVersion version, int format)
private void ReloadMetLocations(GameVersion version, EntityContext context)
{
var metList = GameInfo.GetLocationList(version, format, egg: false);
var metList = GameInfo.GetLocationList(version, context, egg: false);
CB_MetLocation.DataSource = new BindingSource(metList, null);
CB_MetLocation.DropDownWidth = GetWidth(metList, CB_MetLocation.Font);
var eggList = GameInfo.GetLocationList(version, format, egg: true);
var eggList = GameInfo.GetLocationList(version, context, egg: true);
CB_EggLocation.DataSource = new BindingSource(eggList, null);
CB_EggLocation.DropDownWidth = GetWidth(eggList, CB_EggLocation.Font);
@@ -1197,7 +1197,7 @@ private void ReloadMetLocations(GameVersion version, int format)
SetMarkings(); // Set/Remove the Nativity marking when gamegroup changes too
int metLoc = EncounterSuggestion.GetSuggestedTransferLocation(Entity);
int eggLoc = CHK_AsEgg.Checked
? EncounterSuggestion.GetSuggestedEncounterEggLocationEgg(format, version)
? EncounterSuggestion.GetSuggestedEncounterEggLocationEgg(Entity, true)
: LocationEdits.GetNoneLocation(Entity);
CB_MetLocation.SelectedValue = Math.Max(0, metLoc);
@@ -1908,7 +1908,7 @@ private bool FinalizeInterface(SaveFile sav)
// pk2 save files do not have an Origin Game stored. Prompt the met location list to update.
if (Entity.Format == 2)
CheckMetLocationChange(GameVersion.C, Entity.Format);
CheckMetLocationChange(GameVersion.C, Entity.Context);
return TranslationRequired;
}
@@ -2015,7 +2015,7 @@ private void PopulateFilteredDataSources(ITrainerInfo sav, bool force = false)
var game = (GameVersion) sav.Game;
if (game <= 0)
game = Entity.Context.GetSingleGameVersion();
CheckMetLocationChange(game, sav.Generation);
CheckMetLocationChange(game, sav.Context);
SetIfDifferentCount(source.Items, CB_HeldItem, force);
}

View File

@@ -116,12 +116,12 @@ private void ReadMain()
switch (SAV)
{
case SAV4Sinnoh:
metLocationList = GameInfo.GetLocationList(GameVersion.Pt, 4, false);
metLocationList = GameInfo.GetLocationList(GameVersion.Pt, EntityContext.Gen4, false);
FlyDestD = new[] { 001, 002, 006, 008, 003, 009, 010, 004, 012, 011, 005, 007, 014, 013, 054, 015, 081, 082, 083, 055 };
FlyDestC = new[] { 000, 001, 007, 009, 002, 010, 011, 003, 013, 012, 004, 008, 015, 014, 016, 068, 017, 005, 006, 067 };
break;
case SAV4HGSS:
metLocationList = GameInfo.GetLocationList(GameVersion.HG, 4, false);
metLocationList = GameInfo.GetLocationList(GameVersion.HG, EntityContext.Gen4, false);
FlyDestD = new[] { 126, 127, 128, 129, 131, 133, 132, 130, 134, 135, 136, 227, 229, 137, 221, 147, 138, 139, 140, 141, 143, 142, 144, 148, 145, 146, 225 };
FlyDestC = new[] { 011, 012, 013, 014, 016, 018, 017, 015, 019, 020, 021, 030, 027, 022, 033, 009, 000, 001, 002, 003, 005, 004, 006, 010, 007, 008, 035 };
break;

View File

@@ -230,7 +230,7 @@ private void LoadThrowTypeLists()
private void LoadMapFlyToData()
{
var metLocationList = GameInfo.GetLocationList(GameVersion.US, 7, false);
var metLocationList = GameInfo.GetLocationList(GameVersion.US, EntityContext.Gen7, false);
int[] FlyDestNameIndex = {
-1,24,34,8,20,38,12,46,40,30,//Melemele
70,68,78,86,74,104,82,58,90,72,76,92,62,//Akala