2016-06-20 04:22:43 +00:00
|
|
|
|
using System;
|
2019-02-02 07:08:03 +00:00
|
|
|
|
using System.Collections.Generic;
|
2016-06-20 04:22:43 +00:00
|
|
|
|
|
2017-01-08 07:54:09 +00:00
|
|
|
|
namespace PKHeX.Core
|
2016-06-20 04:22:43 +00:00
|
|
|
|
{
|
2017-10-24 06:12:58 +00:00
|
|
|
|
/// <summary>
|
|
|
|
|
/// Generation 5 <see cref="SaveFile"/> object.
|
|
|
|
|
/// </summary>
|
PKHeX.Core Nullable cleanup (#2401)
* Handle some nullable cases
Refactor MysteryGift into a second abstract class (backed by a byte array, or fake data)
Make some classes have explicit constructors instead of { } initialization
* Handle bits more obviously without null
* Make SaveFile.BAK explicitly readonly again
* merge constructor methods to have readonly fields
* Inline some properties
* More nullable handling
* Rearrange box actions
define straightforward classes to not have any null properties
* Make extrabyte reference array immutable
* Move tooltip creation to designer
* Rearrange some logic to reduce nesting
* Cache generated fonts
* Split mystery gift album purpose
* Handle more tooltips
* Disallow null setters
* Don't capture RNG object, only type enum
* Unify learnset objects
Now have readonly properties which are never null
don't new() empty learnsets (>800 Learnset objects no longer created,
total of 2400 objects since we also new() a move & level array)
optimize g1/2 reader for early abort case
* Access rewrite
Initialize blocks in a separate object, and get via that object
removes a couple hundred "might be null" warnings since blocks are now readonly getters
some block references have been relocated, but interfaces should expose all that's needed
put HoF6 controls in a groupbox, and disable
* Readonly personal data
* IVs non nullable for mystery gift
* Explicitly initialize forced encounter moves
* Make shadow objects readonly & non-null
Put murkrow fix in binary data resource, instead of on startup
* Assign dex form fetch on constructor
Fixes legality parsing edge cases
also handle cxd parse for valid; exit before exception is thrown in FrameGenerator
* Remove unnecessary null checks
* Keep empty value until init
SetPouch sets the value to an actual one during load, but whatever
* Readonly team lock data
* Readonly locks
Put locked encounters at bottom (favor unlocked)
* Mail readonly data / offset
Rearrange some call flow and pass defaults
Add fake classes for SaveDataEditor mocking
Always party size, no need to check twice in stat editor
use a fake save file as initial data for savedata editor, and for
gamedata (wow i found a usage)
constrain eventwork editor to struct variable types (uint, int, etc),
thus preventing null assignment errors
2019-10-17 01:47:31 +00:00
|
|
|
|
public abstract class SAV5 : SaveFile, ISaveBlock5BW
|
2016-06-20 04:22:43 +00:00
|
|
|
|
{
|
2019-06-09 02:56:11 +00:00
|
|
|
|
protected override PKM GetPKM(byte[] data) => new PK5(data);
|
2020-01-04 22:48:39 +00:00
|
|
|
|
protected override byte[] DecryptPKM(byte[] data) => PokeCrypto.DecryptArray45(data);
|
2019-06-09 02:56:11 +00:00
|
|
|
|
|
2020-12-05 13:36:23 +00:00
|
|
|
|
protected internal override string ShortSummary => $"{OT} ({(GameVersion)Game}) - {PlayTimeString}";
|
2016-06-20 05:11:53 +00:00
|
|
|
|
public override string Extension => ".sav";
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
PKHeX.Core Nullable cleanup (#2401)
* Handle some nullable cases
Refactor MysteryGift into a second abstract class (backed by a byte array, or fake data)
Make some classes have explicit constructors instead of { } initialization
* Handle bits more obviously without null
* Make SaveFile.BAK explicitly readonly again
* merge constructor methods to have readonly fields
* Inline some properties
* More nullable handling
* Rearrange box actions
define straightforward classes to not have any null properties
* Make extrabyte reference array immutable
* Move tooltip creation to designer
* Rearrange some logic to reduce nesting
* Cache generated fonts
* Split mystery gift album purpose
* Handle more tooltips
* Disallow null setters
* Don't capture RNG object, only type enum
* Unify learnset objects
Now have readonly properties which are never null
don't new() empty learnsets (>800 Learnset objects no longer created,
total of 2400 objects since we also new() a move & level array)
optimize g1/2 reader for early abort case
* Access rewrite
Initialize blocks in a separate object, and get via that object
removes a couple hundred "might be null" warnings since blocks are now readonly getters
some block references have been relocated, but interfaces should expose all that's needed
put HoF6 controls in a groupbox, and disable
* Readonly personal data
* IVs non nullable for mystery gift
* Explicitly initialize forced encounter moves
* Make shadow objects readonly & non-null
Put murkrow fix in binary data resource, instead of on startup
* Assign dex form fetch on constructor
Fixes legality parsing edge cases
also handle cxd parse for valid; exit before exception is thrown in FrameGenerator
* Remove unnecessary null checks
* Keep empty value until init
SetPouch sets the value to an actual one during load, but whatever
* Readonly team lock data
* Readonly locks
Put locked encounters at bottom (favor unlocked)
* Mail readonly data / offset
Rearrange some call flow and pass defaults
Add fake classes for SaveDataEditor mocking
Always party size, no need to check twice in stat editor
use a fake save file as initial data for savedata editor, and for
gamedata (wow i found a usage)
constrain eventwork editor to struct variable types (uint, int, etc),
thus preventing null assignment errors
2019-10-17 01:47:31 +00:00
|
|
|
|
public override IReadOnlyList<ushort> HeldItems => Legal.HeldItems_BW;
|
2020-08-07 23:16:10 +00:00
|
|
|
|
protected override int SIZE_STORED => PokeCrypto.SIZE_5STORED;
|
2020-01-04 22:48:39 +00:00
|
|
|
|
protected override int SIZE_PARTY => PokeCrypto.SIZE_5PARTY;
|
2016-06-20 04:22:43 +00:00
|
|
|
|
public override PKM BlankPKM => new PK5();
|
2016-09-26 23:14:11 +00:00
|
|
|
|
public override Type PKMType => typeof(PK5);
|
2016-06-20 04:22:43 +00:00
|
|
|
|
|
|
|
|
|
public override int BoxCount => 24;
|
|
|
|
|
public override int MaxEV => 255;
|
|
|
|
|
public override int Generation => 5;
|
2017-04-10 04:53:53 +00:00
|
|
|
|
public override int OTLength => 7;
|
2016-06-20 04:22:43 +00:00
|
|
|
|
public override int NickLength => 10;
|
|
|
|
|
protected override int GiftCountMax => 12;
|
|
|
|
|
|
2017-01-27 03:18:20 +00:00
|
|
|
|
public override int MaxMoveID => Legal.MaxMoveID_5;
|
2016-10-24 04:59:27 +00:00
|
|
|
|
public override int MaxSpeciesID => Legal.MaxSpeciesID_5;
|
2017-01-27 03:18:20 +00:00
|
|
|
|
public override int MaxAbilityID => Legal.MaxAbilityID_5;
|
|
|
|
|
public override int MaxBallID => Legal.MaxBallID_5;
|
|
|
|
|
public override int MaxGameID => Legal.MaxGameID_5; // B2
|
2016-06-21 01:58:06 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
protected SAV5(int size) : base(size)
|
2016-06-20 04:22:43 +00:00
|
|
|
|
{
|
2019-06-09 02:56:11 +00:00
|
|
|
|
Initialize();
|
|
|
|
|
ClearBoxes();
|
2016-06-20 04:22:43 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
protected SAV5(byte[] data) : base(data)
|
2016-06-20 04:22:43 +00:00
|
|
|
|
{
|
2019-06-09 02:56:11 +00:00
|
|
|
|
Initialize();
|
2016-06-20 04:22:43 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
public override GameVersion Version
|
2016-06-20 04:22:43 +00:00
|
|
|
|
{
|
2019-06-09 02:56:11 +00:00
|
|
|
|
get => (GameVersion)Game;
|
|
|
|
|
protected set => Game = (int)value;
|
2016-06-20 04:22:43 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
private void Initialize()
|
2016-06-20 04:22:43 +00:00
|
|
|
|
{
|
2019-06-09 02:56:11 +00:00
|
|
|
|
Box = 0x400;
|
|
|
|
|
Party = 0x18E00;
|
|
|
|
|
AdventureInfo = 0x1D900;
|
2016-06-20 04:22:43 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
// Blocks & Offsets
|
PKHeX.Core Nullable cleanup (#2401)
* Handle some nullable cases
Refactor MysteryGift into a second abstract class (backed by a byte array, or fake data)
Make some classes have explicit constructors instead of { } initialization
* Handle bits more obviously without null
* Make SaveFile.BAK explicitly readonly again
* merge constructor methods to have readonly fields
* Inline some properties
* More nullable handling
* Rearrange box actions
define straightforward classes to not have any null properties
* Make extrabyte reference array immutable
* Move tooltip creation to designer
* Rearrange some logic to reduce nesting
* Cache generated fonts
* Split mystery gift album purpose
* Handle more tooltips
* Disallow null setters
* Don't capture RNG object, only type enum
* Unify learnset objects
Now have readonly properties which are never null
don't new() empty learnsets (>800 Learnset objects no longer created,
total of 2400 objects since we also new() a move & level array)
optimize g1/2 reader for early abort case
* Access rewrite
Initialize blocks in a separate object, and get via that object
removes a couple hundred "might be null" warnings since blocks are now readonly getters
some block references have been relocated, but interfaces should expose all that's needed
put HoF6 controls in a groupbox, and disable
* Readonly personal data
* IVs non nullable for mystery gift
* Explicitly initialize forced encounter moves
* Make shadow objects readonly & non-null
Put murkrow fix in binary data resource, instead of on startup
* Assign dex form fetch on constructor
Fixes legality parsing edge cases
also handle cxd parse for valid; exit before exception is thrown in FrameGenerator
* Remove unnecessary null checks
* Keep empty value until init
SetPouch sets the value to an actual one during load, but whatever
* Readonly team lock data
* Readonly locks
Put locked encounters at bottom (favor unlocked)
* Mail readonly data / offset
Rearrange some call flow and pass defaults
Add fake classes for SaveDataEditor mocking
Always party size, no need to check twice in stat editor
use a fake save file as initial data for savedata editor, and for
gamedata (wow i found a usage)
constrain eventwork editor to struct variable types (uint, int, etc),
thus preventing null assignment errors
2019-10-17 01:47:31 +00:00
|
|
|
|
protected override void SetChecksums() => AllBlocks.SetChecksums(Data);
|
|
|
|
|
public override bool ChecksumsValid => AllBlocks.GetChecksumsValid(Data);
|
|
|
|
|
public override string ChecksumInfo => AllBlocks.GetChecksumInfo(Data);
|
2019-06-09 02:56:11 +00:00
|
|
|
|
|
|
|
|
|
protected int CGearInfoOffset;
|
|
|
|
|
protected int CGearDataOffset;
|
|
|
|
|
protected int EntreeForestOffset;
|
|
|
|
|
private int AdventureInfo;
|
2021-07-25 00:23:58 +00:00
|
|
|
|
public abstract int GTS { get; }
|
|
|
|
|
public abstract int Fused { get; }
|
2021-08-16 18:54:03 +00:00
|
|
|
|
public int PGL => AllBlocks[35].Offset + 8; // Dream World Upload
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
// Daycare
|
|
|
|
|
public override int DaycareSeedSize => Daycare5.DaycareSeedSize;
|
2019-10-19 03:42:03 +00:00
|
|
|
|
public override bool? IsDaycareOccupied(int loc, int slot) => Daycare.IsOccupied(slot);
|
|
|
|
|
public override int GetDaycareSlotOffset(int loc, int slot) => Daycare.GetPKMOffset(slot);
|
|
|
|
|
public override uint? GetDaycareEXP(int loc, int slot) => Daycare.GetEXP(slot);
|
|
|
|
|
public override string GetDaycareRNGSeed(int loc) => Daycare.GetSeed()?.ToString("X16") ?? string.Empty;
|
|
|
|
|
public override void SetDaycareEXP(int loc, int slot, uint EXP) => Daycare.SetEXP(slot, EXP);
|
|
|
|
|
public override void SetDaycareOccupied(int loc, int slot, bool occupied) => Daycare.SetOccupied(slot, occupied);
|
|
|
|
|
public override void SetDaycareRNGSeed(int loc, string seed) => Daycare.SetSeed(seed);
|
2016-06-20 04:22:43 +00:00
|
|
|
|
|
|
|
|
|
// Storage
|
|
|
|
|
public override int PartyCount
|
|
|
|
|
{
|
2017-05-13 03:32:36 +00:00
|
|
|
|
get => Data[Party + 4];
|
|
|
|
|
protected set => Data[Party + 4] = (byte)value;
|
2016-06-20 04:22:43 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
public override int GetBoxOffset(int box) => Box + (SIZE_STORED * box * 30) + (box * 0x10);
|
|
|
|
|
public override int GetPartyOffset(int slot) => Party + 8 + (SIZE_PARTY * slot);
|
2019-04-30 00:21:19 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
protected override int GetBoxWallpaperOffset(int box) => BoxLayout.GetBoxWallpaperOffset(box);
|
|
|
|
|
public override int GetBoxWallpaper(int box) => BoxLayout.GetBoxWallpaper(box);
|
|
|
|
|
public override void SetBoxWallpaper(int box, int value) => BoxLayout.SetBoxWallpaper(box, value);
|
|
|
|
|
public override string GetBoxName(int box) => BoxLayout[box];
|
|
|
|
|
public override void SetBoxName(int box, string value) => BoxLayout[box] = value;
|
|
|
|
|
public override int CurrentBox { get => BoxLayout.CurrentBox; set => BoxLayout.CurrentBox = value; }
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2019-11-16 01:34:18 +00:00
|
|
|
|
protected int BattleBoxOffset;
|
2019-11-26 18:45:36 +00:00
|
|
|
|
|
2019-11-16 01:34:18 +00:00
|
|
|
|
public bool BattleBoxLocked
|
2016-06-20 04:22:43 +00:00
|
|
|
|
{
|
2019-10-19 03:42:03 +00:00
|
|
|
|
get => Data[BattleBoxOffset + 0x358] != 0; // wifi/live
|
2021-03-29 07:14:44 +00:00
|
|
|
|
set => Data[BattleBoxOffset + 0x358] = value ? (byte)1 : (byte)0;
|
2016-06-20 04:22:43 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2021-02-09 04:26:53 +00:00
|
|
|
|
protected override void SetPKM(PKM pkm, bool isParty = false)
|
2018-03-22 04:10:23 +00:00
|
|
|
|
{
|
|
|
|
|
var pk5 = (PK5)pkm;
|
|
|
|
|
// Apply to this Save File
|
|
|
|
|
DateTime Date = DateTime.Now;
|
|
|
|
|
if (pk5.Trade(OT, TID, SID, Gender, Date.Day, Date.Month, Date.Year))
|
|
|
|
|
pkm.RefreshChecksum();
|
|
|
|
|
}
|
2018-05-12 15:13:39 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
// Player Data
|
|
|
|
|
public override string OT { get => PlayerData.OT; set => PlayerData.OT = value; }
|
|
|
|
|
public override int TID { get => PlayerData.TID; set => PlayerData.TID = value; }
|
|
|
|
|
public override int SID { get => PlayerData.SID; set => PlayerData.SID = value; }
|
|
|
|
|
public override int Language { get => PlayerData.Language; set => PlayerData.Language = value; }
|
|
|
|
|
public override int Game { get => PlayerData.Game; set => PlayerData.Game = value; }
|
|
|
|
|
public override int Gender { get => PlayerData.Gender; set => PlayerData.Gender = value; }
|
|
|
|
|
public override int PlayedHours { get => PlayerData.PlayedHours; set => PlayerData.PlayedHours = value; }
|
|
|
|
|
public override int PlayedMinutes { get => PlayerData.PlayedMinutes; set => PlayerData.PlayedMinutes = value; }
|
|
|
|
|
public override int PlayedSeconds { get => PlayerData.PlayedSeconds; set => PlayerData.PlayedSeconds = value; }
|
2019-10-19 03:42:03 +00:00
|
|
|
|
public override uint Money { get => Misc.Money; set => Misc.Money = value; }
|
2019-03-05 23:55:26 +00:00
|
|
|
|
public override uint SecondsToStart { get => BitConverter.ToUInt32(Data, AdventureInfo + 0x34); set => BitConverter.GetBytes(value).CopyTo(Data, AdventureInfo + 0x34); }
|
|
|
|
|
public override uint SecondsToFame { get => BitConverter.ToUInt32(Data, AdventureInfo + 0x3C); set => BitConverter.GetBytes(value).CopyTo(Data, AdventureInfo + 0x3C); }
|
2019-10-19 03:42:03 +00:00
|
|
|
|
public override MysteryGiftAlbum GiftAlbum { get => Mystery.GiftAlbum; set => Mystery.GiftAlbum = (EncryptedMysteryGiftAlbum)value; }
|
2020-12-05 14:09:33 +00:00
|
|
|
|
public override IReadOnlyList<InventoryPouch> Inventory { get => Items.Inventory; set => Items.Inventory = value; }
|
2016-07-04 18:56:30 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
protected override void SetDex(PKM pkm) => Zukan.SetDex(pkm);
|
|
|
|
|
public override bool GetCaught(int species) => Zukan.GetCaught(species);
|
|
|
|
|
public override bool GetSeen(int species) => Zukan.GetSeen(species);
|
2017-04-09 21:06:50 +00:00
|
|
|
|
|
2018-12-05 06:00:57 +00:00
|
|
|
|
public override string GetString(byte[] data, int offset, int length) => StringConverter.GetString5(data, offset, length);
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2017-06-18 01:37:19 +00:00
|
|
|
|
public override byte[] SetString(string value, int maxLength, int PadToSize = 0, ushort PadWith = 0)
|
2017-04-09 21:06:50 +00:00
|
|
|
|
{
|
|
|
|
|
if (PadToSize == 0)
|
|
|
|
|
PadToSize = maxLength + 1;
|
2017-08-01 06:03:51 +00:00
|
|
|
|
return StringConverter.SetString5(value, maxLength, PadToSize, PadWith);
|
2017-04-09 21:06:50 +00:00
|
|
|
|
}
|
2018-01-14 00:32:57 +00:00
|
|
|
|
|
|
|
|
|
// DLC
|
2019-07-14 22:06:45 +00:00
|
|
|
|
private int CGearSkinInfoOffset => CGearInfoOffset + (this is SAV5B2W2 ? 0x10 : 0) + 0x24;
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2018-01-14 00:32:57 +00:00
|
|
|
|
private bool CGearSkinPresent
|
|
|
|
|
{
|
|
|
|
|
get => Data[CGearSkinInfoOffset + 2] == 1;
|
2021-03-29 07:14:44 +00:00
|
|
|
|
set => Data[CGearSkinInfoOffset + 2] = Data[PlayerData.Offset + (this is SAV5B2W2 ? 0x6C : 0x54)] = value ? (byte)1 : (byte)0;
|
2018-01-14 00:32:57 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2018-01-14 00:32:57 +00:00
|
|
|
|
public byte[] CGearSkinData
|
|
|
|
|
{
|
|
|
|
|
get
|
|
|
|
|
{
|
2019-06-09 02:56:11 +00:00
|
|
|
|
byte[] data = new byte[CGearBackground.SIZE_CGB];
|
2018-01-14 00:32:57 +00:00
|
|
|
|
if (CGearSkinPresent)
|
|
|
|
|
Array.Copy(Data, CGearDataOffset, data, 0, data.Length);
|
|
|
|
|
return data;
|
|
|
|
|
}
|
|
|
|
|
set
|
|
|
|
|
{
|
|
|
|
|
byte[] dlcfooter = { 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x14, 0x27, 0x00, 0x00, 0x27, 0x35, 0x05, 0x31, 0x00, 0x00 };
|
|
|
|
|
|
|
|
|
|
byte[] bgdata = value;
|
|
|
|
|
SetData(bgdata, CGearDataOffset);
|
|
|
|
|
|
2019-03-16 19:01:21 +00:00
|
|
|
|
ushort chk = Checksums.CRC16_CCITT(bgdata);
|
2018-01-14 00:32:57 +00:00
|
|
|
|
var chkbytes = BitConverter.GetBytes(chk);
|
|
|
|
|
int footer = CGearDataOffset + bgdata.Length;
|
|
|
|
|
|
|
|
|
|
BitConverter.GetBytes((ushort)1).CopyTo(Data, footer); // block updated once
|
|
|
|
|
chkbytes.CopyTo(Data, footer + 2); // checksum
|
|
|
|
|
chkbytes.CopyTo(Data, footer + 0x100); // second checksum
|
|
|
|
|
dlcfooter.CopyTo(Data, footer + 0x102);
|
2021-05-14 19:30:40 +00:00
|
|
|
|
ushort skinchkval = Checksums.CRC16_CCITT(new ReadOnlySpan<byte>(Data, footer + 0x100, 4));
|
2018-01-14 00:32:57 +00:00
|
|
|
|
BitConverter.GetBytes(skinchkval).CopyTo(Data, footer + 0x112);
|
|
|
|
|
|
|
|
|
|
// Indicate in the save file that data is present
|
|
|
|
|
BitConverter.GetBytes((ushort)0xC21E).CopyTo(Data, 0x19438);
|
|
|
|
|
|
|
|
|
|
chkbytes.CopyTo(Data, CGearSkinInfoOffset);
|
|
|
|
|
CGearSkinPresent = true;
|
|
|
|
|
|
2020-12-05 13:36:23 +00:00
|
|
|
|
State.Edited = true;
|
2018-01-14 00:32:57 +00:00
|
|
|
|
}
|
|
|
|
|
}
|
2018-05-28 15:26:52 +00:00
|
|
|
|
|
|
|
|
|
public EntreeForest EntreeData
|
|
|
|
|
{
|
2020-12-22 01:17:56 +00:00
|
|
|
|
get => new(GetData(EntreeForestOffset, 0x850));
|
2018-05-28 15:26:52 +00:00
|
|
|
|
set => SetData(value.Write(), EntreeForestOffset);
|
|
|
|
|
}
|
PKHeX.Core Nullable cleanup (#2401)
* Handle some nullable cases
Refactor MysteryGift into a second abstract class (backed by a byte array, or fake data)
Make some classes have explicit constructors instead of { } initialization
* Handle bits more obviously without null
* Make SaveFile.BAK explicitly readonly again
* merge constructor methods to have readonly fields
* Inline some properties
* More nullable handling
* Rearrange box actions
define straightforward classes to not have any null properties
* Make extrabyte reference array immutable
* Move tooltip creation to designer
* Rearrange some logic to reduce nesting
* Cache generated fonts
* Split mystery gift album purpose
* Handle more tooltips
* Disallow null setters
* Don't capture RNG object, only type enum
* Unify learnset objects
Now have readonly properties which are never null
don't new() empty learnsets (>800 Learnset objects no longer created,
total of 2400 objects since we also new() a move & level array)
optimize g1/2 reader for early abort case
* Access rewrite
Initialize blocks in a separate object, and get via that object
removes a couple hundred "might be null" warnings since blocks are now readonly getters
some block references have been relocated, but interfaces should expose all that's needed
put HoF6 controls in a groupbox, and disable
* Readonly personal data
* IVs non nullable for mystery gift
* Explicitly initialize forced encounter moves
* Make shadow objects readonly & non-null
Put murkrow fix in binary data resource, instead of on startup
* Assign dex form fetch on constructor
Fixes legality parsing edge cases
also handle cxd parse for valid; exit before exception is thrown in FrameGenerator
* Remove unnecessary null checks
* Keep empty value until init
SetPouch sets the value to an actual one during load, but whatever
* Readonly team lock data
* Readonly locks
Put locked encounters at bottom (favor unlocked)
* Mail readonly data / offset
Rearrange some call flow and pass defaults
Add fake classes for SaveDataEditor mocking
Always party size, no need to check twice in stat editor
use a fake save file as initial data for savedata editor, and for
gamedata (wow i found a usage)
constrain eventwork editor to struct variable types (uint, int, etc),
thus preventing null assignment errors
2019-10-17 01:47:31 +00:00
|
|
|
|
|
|
|
|
|
public abstract IReadOnlyList<BlockInfo> AllBlocks { get; }
|
|
|
|
|
public abstract MyItem Items { get; }
|
|
|
|
|
public abstract Zukan5 Zukan { get; }
|
2019-10-19 03:42:03 +00:00
|
|
|
|
public abstract Misc5 Misc { get; }
|
|
|
|
|
public abstract MysteryBlock5 Mystery { get; }
|
|
|
|
|
public abstract Daycare5 Daycare { get; }
|
PKHeX.Core Nullable cleanup (#2401)
* Handle some nullable cases
Refactor MysteryGift into a second abstract class (backed by a byte array, or fake data)
Make some classes have explicit constructors instead of { } initialization
* Handle bits more obviously without null
* Make SaveFile.BAK explicitly readonly again
* merge constructor methods to have readonly fields
* Inline some properties
* More nullable handling
* Rearrange box actions
define straightforward classes to not have any null properties
* Make extrabyte reference array immutable
* Move tooltip creation to designer
* Rearrange some logic to reduce nesting
* Cache generated fonts
* Split mystery gift album purpose
* Handle more tooltips
* Disallow null setters
* Don't capture RNG object, only type enum
* Unify learnset objects
Now have readonly properties which are never null
don't new() empty learnsets (>800 Learnset objects no longer created,
total of 2400 objects since we also new() a move & level array)
optimize g1/2 reader for early abort case
* Access rewrite
Initialize blocks in a separate object, and get via that object
removes a couple hundred "might be null" warnings since blocks are now readonly getters
some block references have been relocated, but interfaces should expose all that's needed
put HoF6 controls in a groupbox, and disable
* Readonly personal data
* IVs non nullable for mystery gift
* Explicitly initialize forced encounter moves
* Make shadow objects readonly & non-null
Put murkrow fix in binary data resource, instead of on startup
* Assign dex form fetch on constructor
Fixes legality parsing edge cases
also handle cxd parse for valid; exit before exception is thrown in FrameGenerator
* Remove unnecessary null checks
* Keep empty value until init
SetPouch sets the value to an actual one during load, but whatever
* Readonly team lock data
* Readonly locks
Put locked encounters at bottom (favor unlocked)
* Mail readonly data / offset
Rearrange some call flow and pass defaults
Add fake classes for SaveDataEditor mocking
Always party size, no need to check twice in stat editor
use a fake save file as initial data for savedata editor, and for
gamedata (wow i found a usage)
constrain eventwork editor to struct variable types (uint, int, etc),
thus preventing null assignment errors
2019-10-17 01:47:31 +00:00
|
|
|
|
public abstract BoxLayout5 BoxLayout { get; }
|
|
|
|
|
public abstract PlayerData5 PlayerData { get; }
|
2019-10-19 03:42:03 +00:00
|
|
|
|
public abstract BattleSubway5 BattleSubway { get; }
|
2021-07-26 06:44:03 +00:00
|
|
|
|
public abstract Entralink5 Entralink { get; }
|
|
|
|
|
public abstract Musical5 Musical { get; }
|
PKHeX.Core Nullable cleanup (#2401)
* Handle some nullable cases
Refactor MysteryGift into a second abstract class (backed by a byte array, or fake data)
Make some classes have explicit constructors instead of { } initialization
* Handle bits more obviously without null
* Make SaveFile.BAK explicitly readonly again
* merge constructor methods to have readonly fields
* Inline some properties
* More nullable handling
* Rearrange box actions
define straightforward classes to not have any null properties
* Make extrabyte reference array immutable
* Move tooltip creation to designer
* Rearrange some logic to reduce nesting
* Cache generated fonts
* Split mystery gift album purpose
* Handle more tooltips
* Disallow null setters
* Don't capture RNG object, only type enum
* Unify learnset objects
Now have readonly properties which are never null
don't new() empty learnsets (>800 Learnset objects no longer created,
total of 2400 objects since we also new() a move & level array)
optimize g1/2 reader for early abort case
* Access rewrite
Initialize blocks in a separate object, and get via that object
removes a couple hundred "might be null" warnings since blocks are now readonly getters
some block references have been relocated, but interfaces should expose all that's needed
put HoF6 controls in a groupbox, and disable
* Readonly personal data
* IVs non nullable for mystery gift
* Explicitly initialize forced encounter moves
* Make shadow objects readonly & non-null
Put murkrow fix in binary data resource, instead of on startup
* Assign dex form fetch on constructor
Fixes legality parsing edge cases
also handle cxd parse for valid; exit before exception is thrown in FrameGenerator
* Remove unnecessary null checks
* Keep empty value until init
SetPouch sets the value to an actual one during load, but whatever
* Readonly team lock data
* Readonly locks
Put locked encounters at bottom (favor unlocked)
* Mail readonly data / offset
Rearrange some call flow and pass defaults
Add fake classes for SaveDataEditor mocking
Always party size, no need to check twice in stat editor
use a fake save file as initial data for savedata editor, and for
gamedata (wow i found a usage)
constrain eventwork editor to struct variable types (uint, int, etc),
thus preventing null assignment errors
2019-10-17 01:47:31 +00:00
|
|
|
|
|
2019-10-26 19:58:55 +00:00
|
|
|
|
public static int GetMailOffset(int index) => (index * Mail5.SIZE) + 0x1DD00;
|
PKHeX.Core Nullable cleanup (#2401)
* Handle some nullable cases
Refactor MysteryGift into a second abstract class (backed by a byte array, or fake data)
Make some classes have explicit constructors instead of { } initialization
* Handle bits more obviously without null
* Make SaveFile.BAK explicitly readonly again
* merge constructor methods to have readonly fields
* Inline some properties
* More nullable handling
* Rearrange box actions
define straightforward classes to not have any null properties
* Make extrabyte reference array immutable
* Move tooltip creation to designer
* Rearrange some logic to reduce nesting
* Cache generated fonts
* Split mystery gift album purpose
* Handle more tooltips
* Disallow null setters
* Don't capture RNG object, only type enum
* Unify learnset objects
Now have readonly properties which are never null
don't new() empty learnsets (>800 Learnset objects no longer created,
total of 2400 objects since we also new() a move & level array)
optimize g1/2 reader for early abort case
* Access rewrite
Initialize blocks in a separate object, and get via that object
removes a couple hundred "might be null" warnings since blocks are now readonly getters
some block references have been relocated, but interfaces should expose all that's needed
put HoF6 controls in a groupbox, and disable
* Readonly personal data
* IVs non nullable for mystery gift
* Explicitly initialize forced encounter moves
* Make shadow objects readonly & non-null
Put murkrow fix in binary data resource, instead of on startup
* Assign dex form fetch on constructor
Fixes legality parsing edge cases
also handle cxd parse for valid; exit before exception is thrown in FrameGenerator
* Remove unnecessary null checks
* Keep empty value until init
SetPouch sets the value to an actual one during load, but whatever
* Readonly team lock data
* Readonly locks
Put locked encounters at bottom (favor unlocked)
* Mail readonly data / offset
Rearrange some call flow and pass defaults
Add fake classes for SaveDataEditor mocking
Always party size, no need to check twice in stat editor
use a fake save file as initial data for savedata editor, and for
gamedata (wow i found a usage)
constrain eventwork editor to struct variable types (uint, int, etc),
thus preventing null assignment errors
2019-10-17 01:47:31 +00:00
|
|
|
|
public byte[] GetMailData(int offset) => GetData(offset, Mail5.SIZE);
|
2019-11-16 01:34:18 +00:00
|
|
|
|
public int GetBattleBoxSlot(int slot) => BattleBoxOffset + (slot * SIZE_STORED);
|
2021-05-22 16:28:04 +00:00
|
|
|
|
|
2021-08-06 03:33:25 +00:00
|
|
|
|
public Mail GetMail(int mailIndex)
|
2021-05-22 16:28:04 +00:00
|
|
|
|
{
|
2021-08-06 03:33:25 +00:00
|
|
|
|
int ofs = GetMailOffset(mailIndex);
|
2021-05-22 16:28:04 +00:00
|
|
|
|
var data = GetMailData(ofs);
|
|
|
|
|
return new Mail5(data, ofs);
|
|
|
|
|
}
|
2016-06-20 04:22:43 +00:00
|
|
|
|
}
|
|
|
|
|
}
|