2016-09-26 23:15:40 +00:00
|
|
|
|
using System;
|
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
|
|
|
|
using System.Collections.Generic;
|
2016-09-26 23:15:40 +00:00
|
|
|
|
using System.Linq;
|
|
|
|
|
using System.Security.Cryptography;
|
|
|
|
|
|
2017-01-08 07:54:09 +00:00
|
|
|
|
namespace PKHeX.Core
|
2016-09-26 23:15:40 +00:00
|
|
|
|
{
|
2017-10-24 06:12:58 +00:00
|
|
|
|
/// <summary>
|
|
|
|
|
/// Generation 3 <see cref="SaveFile"/> object for Pokémon Colosseum saves.
|
|
|
|
|
/// </summary>
|
2019-02-19 05:59:57 +00:00
|
|
|
|
public sealed class SAV3Colosseum : SaveFile, IDisposable, IGCSaveFile
|
2016-09-26 23:15:40 +00:00
|
|
|
|
{
|
2018-07-30 04:51:45 +00:00
|
|
|
|
protected override string BAKText => $"{OT} ({Version}) - {PlayTimeString}";
|
2019-02-19 05:59:57 +00:00
|
|
|
|
public override string Filter => this.GCFilter();
|
|
|
|
|
public override string Extension => this.GCExtension();
|
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 PersonalTable Personal => PersonalTable.RS;
|
|
|
|
|
public override IReadOnlyList<ushort> HeldItems => Legal.HeldItems_COLO;
|
2019-02-19 05:59:57 +00:00
|
|
|
|
public bool IsMemoryCardSave => MC != null;
|
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
|
|
|
|
private readonly SAV3GCMemoryCard? MC;
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
|
|
|
|
// 3 Save files are stored
|
|
|
|
|
// 0x0000-0x6000 contains memory card data
|
|
|
|
|
// 0x6000-0x60000 contains the 3 save slots
|
|
|
|
|
// 0x5A000 / 3 = 0x1E000 per save slot
|
|
|
|
|
// Checksum is SHA1 over 0-0x1DFD7, stored in the last 20 bytes of the save slot.
|
|
|
|
|
// Another SHA1 hash is 0x1DFD8, for 20 bytes. Unknown purpose.
|
|
|
|
|
// Checksum is used as the crypto key.
|
|
|
|
|
|
|
|
|
|
private const int SLOT_SIZE = 0x1E000;
|
|
|
|
|
private const int SLOT_START = 0x6000;
|
|
|
|
|
private const int SLOT_COUNT = 3;
|
|
|
|
|
|
2019-01-05 23:37:06 +00:00
|
|
|
|
private int SaveCount = -1;
|
|
|
|
|
private int SaveIndex = -1;
|
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
|
|
|
|
private readonly StrategyMemo StrategyMemo;
|
2019-10-26 19:33:58 +00:00
|
|
|
|
public const int MaxShadowID = 0x80; // 128
|
2019-06-09 02:56:11 +00:00
|
|
|
|
private int Memo;
|
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 SAV3Colosseum(byte[] data, SAV3GCMemoryCard MC) : this(data, MC.Data) { this.MC = MC; }
|
|
|
|
|
public SAV3Colosseum(byte[] data) : this(data, (byte[])data.Clone()) { }
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2019-06-09 02:56:11 +00:00
|
|
|
|
public SAV3Colosseum() : base(SaveUtil.SIZE_G3COLO)
|
2016-09-26 23:15:40 +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
|
|
|
|
StrategyMemo = Initialize();
|
2019-06-09 02:56:11 +00:00
|
|
|
|
ClearBoxes();
|
|
|
|
|
}
|
|
|
|
|
|
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
|
|
|
|
private SAV3Colosseum(byte[] data, byte[] bak) : base(data, bak)
|
2019-06-09 02:56:11 +00:00
|
|
|
|
{
|
|
|
|
|
InitializeData();
|
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
|
|
|
|
StrategyMemo = Initialize();
|
2019-06-09 02:56:11 +00:00
|
|
|
|
}
|
2016-09-26 23:15:40 +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
|
|
|
|
private StrategyMemo Initialize()
|
2019-06-09 02:56:11 +00:00
|
|
|
|
{
|
2019-11-28 22:00:55 +00:00
|
|
|
|
// Trainer1 = 0x00078;
|
2016-09-26 23:15:40 +00:00
|
|
|
|
Party = 0x000A8;
|
|
|
|
|
|
|
|
|
|
Box = 0x00B90;
|
2019-10-19 03:42:03 +00:00
|
|
|
|
DaycareOffset = 0x08170;
|
2016-10-01 02:05:35 +00:00
|
|
|
|
Memo = 0x082B0;
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
2016-10-02 04:43:23 +00:00
|
|
|
|
// Since PartyCount is not stored in the save file,
|
|
|
|
|
// Count up how many party slots are active.
|
|
|
|
|
for (int i = 0; i < 6; i++)
|
2018-09-15 05:37:47 +00:00
|
|
|
|
{
|
2019-11-16 01:34:18 +00:00
|
|
|
|
if (GetPartySlot(Data, GetPartyOffset(i)).Species != 0)
|
2016-10-02 04:43:23 +00:00
|
|
|
|
PartyCount++;
|
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
|
|
|
|
|
|
|
|
|
var memo = new StrategyMemo(Data, Memo, xd: false);
|
|
|
|
|
return memo;
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
|
|
|
|
|
2019-01-05 23:37:06 +00:00
|
|
|
|
private void InitializeData()
|
|
|
|
|
{
|
|
|
|
|
// Scan all 3 save slots for the highest counter
|
|
|
|
|
for (int i = 0; i < SLOT_COUNT; i++)
|
|
|
|
|
{
|
|
|
|
|
int slotOffset = SLOT_START + (i * SLOT_SIZE);
|
|
|
|
|
int SaveCounter = BigEndian.ToInt32(Data, slotOffset + 4);
|
|
|
|
|
if (SaveCounter <= SaveCount)
|
|
|
|
|
continue;
|
|
|
|
|
|
|
|
|
|
SaveCount = SaveCounter;
|
|
|
|
|
SaveIndex = i;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Decrypt most recent save slot
|
|
|
|
|
{
|
|
|
|
|
byte[] slot = new byte[SLOT_SIZE];
|
|
|
|
|
int slotOffset = SLOT_START + (SaveIndex * SLOT_SIZE);
|
|
|
|
|
Array.Copy(Data, slotOffset, slot, 0, slot.Length);
|
|
|
|
|
byte[] digest = new byte[20];
|
|
|
|
|
Array.Copy(slot, SLOT_SIZE - 20, digest, 0, digest.Length);
|
|
|
|
|
|
|
|
|
|
// Decrypt Slot
|
|
|
|
|
Data = DecryptColosseum(slot, digest);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2019-02-19 05:59:57 +00:00
|
|
|
|
protected override byte[] GetFinalData()
|
2019-03-08 02:05:55 +00:00
|
|
|
|
{
|
|
|
|
|
var newFile = GetInnerData();
|
|
|
|
|
|
|
|
|
|
// Return the gci if Memory Card is not being exported
|
|
|
|
|
if (!IsMemoryCardSave)
|
|
|
|
|
return newFile;
|
|
|
|
|
|
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
|
|
|
|
MC!.SelectedSaveData = newFile;
|
2019-03-08 02:05:55 +00:00
|
|
|
|
return MC.Data;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private byte[] GetInnerData()
|
2016-09-26 23:15:40 +00:00
|
|
|
|
{
|
2019-10-26 19:58:55 +00:00
|
|
|
|
StrategyMemo.Write().CopyTo(Data, Memo);
|
2017-06-18 01:37:19 +00:00
|
|
|
|
SetChecksums();
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
|
|
|
|
// Get updated save slot data
|
2019-09-23 22:13:22 +00:00
|
|
|
|
byte[] digest = Data.Slice(Data.Length - 20, 20);
|
2016-09-26 23:15:40 +00:00
|
|
|
|
byte[] newSAV = EncryptColosseum(Data, digest);
|
|
|
|
|
|
|
|
|
|
// Put save slot back in original save data
|
2018-02-07 04:33:32 +00:00
|
|
|
|
byte[] newFile = MC != null ? MC.SelectedSaveData : (byte[])BAK.Clone();
|
2018-09-15 05:37:47 +00:00
|
|
|
|
Array.Copy(newSAV, 0, newFile, SLOT_START + (SaveIndex * SLOT_SIZE), newSAV.Length);
|
2019-03-08 02:05:55 +00:00
|
|
|
|
return newFile;
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Configuration
|
2019-03-08 02:05:55 +00:00
|
|
|
|
public override SaveFile Clone()
|
|
|
|
|
{
|
|
|
|
|
var data = GetInnerData();
|
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
|
|
|
|
var sav = IsMemoryCardSave ? new SAV3Colosseum(data, MC!) : new SAV3Colosseum(data);
|
2019-03-08 02:05:55 +00:00
|
|
|
|
sav.Header = (byte[])Header.Clone();
|
|
|
|
|
return sav;
|
|
|
|
|
}
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
2020-01-04 22:48:39 +00:00
|
|
|
|
public override int SIZE_STORED => PokeCrypto.SIZE_3CSTORED;
|
|
|
|
|
protected override int SIZE_PARTY => PokeCrypto.SIZE_3CSTORED; // unused
|
2016-09-26 23:15:40 +00:00
|
|
|
|
public override PKM BlankPKM => new CK3();
|
2016-09-26 23:18:10 +00:00
|
|
|
|
public override Type PKMType => typeof(CK3);
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
2017-12-28 00:36:24 +00:00
|
|
|
|
public override int MaxMoveID => Legal.MaxMoveID_3;
|
2016-10-24 04:59:27 +00:00
|
|
|
|
public override int MaxSpeciesID => Legal.MaxSpeciesID_3;
|
2017-12-28 00:36:24 +00:00
|
|
|
|
public override int MaxAbilityID => Legal.MaxAbilityID_3;
|
|
|
|
|
public override int MaxBallID => Legal.MaxBallID_3;
|
|
|
|
|
public override int MaxItemID => Legal.MaxItemID_3_COLO;
|
|
|
|
|
public override int MaxGameID => Legal.MaxGameID_3;
|
2018-05-12 15:13:39 +00:00
|
|
|
|
|
2016-09-26 23:15:40 +00:00
|
|
|
|
public override int MaxEV => 255;
|
|
|
|
|
public override int Generation => 3;
|
|
|
|
|
protected override int GiftCountMax => 1;
|
2018-10-27 23:06:06 +00:00
|
|
|
|
public override int OTLength => 10; // as evident by Mattle Ho-Oh
|
2016-09-26 23:15:40 +00:00
|
|
|
|
public override int NickLength => 10;
|
|
|
|
|
public override int MaxMoney => 999999;
|
|
|
|
|
|
|
|
|
|
public override int BoxCount => 3;
|
2019-09-03 02:30:58 +00:00
|
|
|
|
public override bool IsPKMPresent(byte[] data, int offset) => PKX.IsPKMPresentGC(data, offset);
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
|
|
|
|
// Checksums
|
|
|
|
|
private readonly SHA1 sha1 = SHA1.Create();
|
2020-04-05 02:30:50 +00:00
|
|
|
|
public void Dispose() => sha1.Dispose();
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2016-09-26 23:15:40 +00:00
|
|
|
|
private byte[] EncryptColosseum(byte[] input, byte[] digest)
|
|
|
|
|
{
|
|
|
|
|
if (input.Length != SLOT_SIZE)
|
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
|
|
|
|
throw new ArgumentException(nameof(input));
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
|
|
|
|
byte[] d = (byte[])input.Clone();
|
|
|
|
|
byte[] k = (byte[])digest.Clone(); // digest
|
|
|
|
|
|
|
|
|
|
// NOT key
|
|
|
|
|
for (int i = 0; i < 20; i++)
|
|
|
|
|
k[i] = (byte)~k[i];
|
|
|
|
|
|
|
|
|
|
for (int i = 0x18; i < 0x1DFD8; i += 20)
|
|
|
|
|
{
|
|
|
|
|
for (int j = 0; j < 20; j++)
|
|
|
|
|
d[i + j] ^= k[j];
|
|
|
|
|
k = sha1.ComputeHash(d, i, 20); // update digest
|
|
|
|
|
}
|
|
|
|
|
return d;
|
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2016-09-26 23:15:40 +00:00
|
|
|
|
private byte[] DecryptColosseum(byte[] input, byte[] digest)
|
|
|
|
|
{
|
|
|
|
|
if (input.Length != SLOT_SIZE)
|
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
|
|
|
|
throw new ArgumentException(nameof(input));
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
|
|
|
|
byte[] d = (byte[])input.Clone();
|
|
|
|
|
byte[] k = (byte[])digest.Clone();
|
|
|
|
|
|
|
|
|
|
// NOT key
|
|
|
|
|
for (int i = 0; i < 20; i++)
|
|
|
|
|
k[i] = (byte)~k[i];
|
|
|
|
|
|
|
|
|
|
for (int i = 0x18; i < 0x1DFD8; i += 20)
|
|
|
|
|
{
|
|
|
|
|
byte[] key = sha1.ComputeHash(d, i, 20); // update digest
|
|
|
|
|
for (int j = 0; j < 20; j++)
|
|
|
|
|
d[i + j] ^= k[j];
|
|
|
|
|
Array.Copy(key, k, 20); // for use in next loop
|
|
|
|
|
}
|
|
|
|
|
return d;
|
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2017-06-18 01:37:19 +00:00
|
|
|
|
protected override void SetChecksums()
|
2016-09-26 23:15:40 +00:00
|
|
|
|
{
|
|
|
|
|
// Clear Header Checksum
|
|
|
|
|
BitConverter.GetBytes(0).CopyTo(Data, 12);
|
|
|
|
|
// Compute checksum of data
|
|
|
|
|
byte[] checksum = sha1.ComputeHash(Data, 0, 0x1DFD8);
|
|
|
|
|
// Set Checksum to end
|
|
|
|
|
Array.Copy(checksum, 0, Data, Data.Length - 20, 20);
|
|
|
|
|
|
|
|
|
|
// Header Integrity
|
|
|
|
|
byte[] H = new byte[8]; Array.Copy(checksum, 0, H, 0, 8);
|
|
|
|
|
byte[] D = new byte[8]; Array.Copy(Data, 0x18, D, 0, 8);
|
|
|
|
|
// Decrypt Checksum
|
|
|
|
|
for (int i = 0; i < 8; i++)
|
|
|
|
|
D[i] ^= (byte)~H[i];
|
|
|
|
|
|
|
|
|
|
// Compute new header checksum
|
|
|
|
|
int newHC = 0;
|
|
|
|
|
for (int i = 0; i < 0x18; i += 4)
|
|
|
|
|
newHC -= BigEndian.ToInt32(Data, i);
|
|
|
|
|
|
|
|
|
|
newHC -= BigEndian.ToInt32(D, 0);
|
|
|
|
|
newHC -= BigEndian.ToInt32(D, 4);
|
|
|
|
|
|
|
|
|
|
// Set Header Checksum
|
|
|
|
|
BigEndian.GetBytes(newHC).CopyTo(Data, 12);
|
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2016-09-26 23:15:40 +00:00
|
|
|
|
public override bool ChecksumsValid => !ChecksumInfo.Contains("Invalid");
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2016-09-26 23:15:40 +00:00
|
|
|
|
public override string ChecksumInfo
|
|
|
|
|
{
|
|
|
|
|
get
|
|
|
|
|
{
|
|
|
|
|
byte[] data = (byte[])Data.Clone();
|
|
|
|
|
int oldHC = BigEndian.ToInt32(data, 12);
|
|
|
|
|
// Clear Header Checksum
|
|
|
|
|
BitConverter.GetBytes(0).CopyTo(data, 12);
|
|
|
|
|
byte[] checksum = sha1.ComputeHash(data, 0, 0x1DFD8);
|
|
|
|
|
// Header Integrity
|
|
|
|
|
byte[] H = new byte[8];
|
|
|
|
|
byte[] D = new byte[8];
|
|
|
|
|
|
|
|
|
|
Array.Copy(checksum, 0, H, 0, H.Length);
|
|
|
|
|
Array.Copy(data, 0x00018, D, 0, D.Length);
|
|
|
|
|
for (int i = 0; i < 8; i++)
|
|
|
|
|
D[i] ^= (byte)~H[i];
|
|
|
|
|
|
|
|
|
|
// Compute new header checksum
|
|
|
|
|
int newHC = 0;
|
|
|
|
|
for (int i = 0; i < 0x18; i += 4)
|
|
|
|
|
newHC -= BigEndian.ToInt32(data, i);
|
|
|
|
|
|
|
|
|
|
newHC -= BigEndian.ToInt32(D, 0);
|
|
|
|
|
newHC -= BigEndian.ToInt32(D, 4);
|
|
|
|
|
|
2019-09-23 22:13:22 +00:00
|
|
|
|
byte[] chk = data.Slice(data.Length - 20, 20);
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
|
|
|
|
bool header = newHC == oldHC;
|
|
|
|
|
bool body = chk.SequenceEqual(checksum);
|
2019-10-08 01:40:09 +00:00
|
|
|
|
static string valid(bool s) => s ? "Valid" : "Invalid";
|
2017-05-13 19:51:33 +00:00
|
|
|
|
return $"Header Checksum {valid(header)}, Body Checksum {valid(body)}alid.";
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Trainer Info
|
2017-05-13 03:32:36 +00:00
|
|
|
|
public override GameVersion Version { get => GameVersion.COLO; protected set { } }
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
|
|
|
|
// Storage
|
2017-06-18 01:37:19 +00:00
|
|
|
|
public override int GetPartyOffset(int slot)
|
2016-09-26 23:15:40 +00:00
|
|
|
|
{
|
2018-09-15 05:37:47 +00:00
|
|
|
|
return Party + (SIZE_STORED * slot);
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2017-06-18 01:37:19 +00:00
|
|
|
|
public override int GetBoxOffset(int box)
|
2016-09-26 23:15:40 +00:00
|
|
|
|
{
|
2018-09-15 05:37:47 +00:00
|
|
|
|
return Box + (((30 * SIZE_STORED) + 0x14)*box) + 0x14;
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2017-06-18 01:37:19 +00:00
|
|
|
|
public override string GetBoxName(int box)
|
2016-09-26 23:15:40 +00:00
|
|
|
|
{
|
2018-09-15 05:37:47 +00:00
|
|
|
|
return GetString(Box + (0x24A4 * box), 16);
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2017-06-18 01:37:19 +00:00
|
|
|
|
public override void SetBoxName(int box, string value)
|
2016-09-26 23:15:40 +00:00
|
|
|
|
{
|
2018-09-15 05:37:47 +00:00
|
|
|
|
SetString(value, 8).CopyTo(Data, Box + (0x24A4 * box));
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2019-03-30 02:43:33 +00:00
|
|
|
|
protected override PKM GetPKM(byte[] data)
|
2016-09-26 23:15:40 +00:00
|
|
|
|
{
|
2019-02-17 18:42:43 +00:00
|
|
|
|
if (data.Length != SIZE_STORED)
|
|
|
|
|
Array.Resize(ref data, SIZE_STORED);
|
|
|
|
|
return new CK3(data);
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2019-03-30 02:43:33 +00:00
|
|
|
|
protected override byte[] DecryptPKM(byte[] data)
|
2016-09-26 23:15:40 +00:00
|
|
|
|
{
|
|
|
|
|
return data;
|
|
|
|
|
}
|
|
|
|
|
|
2017-06-18 01:37:19 +00:00
|
|
|
|
protected override void SetPKM(PKM pkm)
|
2016-12-27 05:26:45 +00:00
|
|
|
|
{
|
2018-05-12 19:28:48 +00:00
|
|
|
|
if (!(pkm is CK3 pk))
|
2016-12-27 05:26:45 +00:00
|
|
|
|
return;
|
|
|
|
|
|
|
|
|
|
if (pk.CurrentRegion == 0)
|
|
|
|
|
pk.CurrentRegion = 2; // NTSC-U
|
|
|
|
|
if (pk.OriginalRegion == 0)
|
|
|
|
|
pk.OriginalRegion = 2; // NTSC-U
|
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2017-06-18 01:37:19 +00:00
|
|
|
|
protected override void SetDex(PKM pkm)
|
2016-10-01 02:05:35 +00:00
|
|
|
|
{
|
|
|
|
|
// Dex Related
|
|
|
|
|
var entry = StrategyMemo.GetEntry(pkm.Species);
|
|
|
|
|
if (entry.IsEmpty) // Populate
|
|
|
|
|
{
|
|
|
|
|
entry.Species = pkm.Species;
|
|
|
|
|
entry.PID = pkm.PID;
|
|
|
|
|
entry.TID = pkm.TID;
|
|
|
|
|
entry.SID = pkm.SID;
|
|
|
|
|
}
|
|
|
|
|
if (entry.Matches(pkm.Species, pkm.PID, pkm.TID, pkm.SID))
|
|
|
|
|
{
|
|
|
|
|
entry.Seen = true;
|
|
|
|
|
entry.Owned = true;
|
|
|
|
|
}
|
|
|
|
|
StrategyMemo.SetEntry(entry);
|
|
|
|
|
}
|
2018-05-12 15:13:39 +00:00
|
|
|
|
|
2016-09-26 23:15:40 +00:00
|
|
|
|
private TimeSpan PlayedSpan
|
|
|
|
|
{
|
2017-05-13 03:32:36 +00:00
|
|
|
|
get => TimeSpan.FromSeconds((double)(BigEndian.ToUInt32(Data, 40) - 0x47000000) / 128);
|
|
|
|
|
set => BigEndian.GetBytes((uint)(value.TotalSeconds * 128) + 0x47000000).CopyTo(Data, 40);
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2016-09-26 23:15:40 +00:00
|
|
|
|
public override int PlayedHours
|
|
|
|
|
{
|
2017-05-13 03:32:36 +00:00
|
|
|
|
get => (ushort)PlayedSpan.Hours;
|
2016-09-26 23:15:40 +00:00
|
|
|
|
set { var time = PlayedSpan; PlayedSpan = time - TimeSpan.FromHours(time.Hours) + TimeSpan.FromHours(value); }
|
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2016-09-26 23:15:40 +00:00
|
|
|
|
public override int PlayedMinutes
|
|
|
|
|
{
|
2017-05-13 03:32:36 +00:00
|
|
|
|
get => (byte)PlayedSpan.Minutes;
|
2016-09-26 23:15:40 +00:00
|
|
|
|
set { var time = PlayedSpan; PlayedSpan = time - TimeSpan.FromMinutes(time.Minutes) + TimeSpan.FromMinutes(value); }
|
|
|
|
|
}
|
2018-09-15 05:37:47 +00:00
|
|
|
|
|
2016-09-26 23:15:40 +00:00
|
|
|
|
public override int PlayedSeconds
|
|
|
|
|
{
|
2017-05-13 03:32:36 +00:00
|
|
|
|
get => (byte)PlayedSpan.Seconds;
|
2016-09-26 23:15:40 +00:00
|
|
|
|
set { var time = PlayedSpan; PlayedSpan = time - TimeSpan.FromSeconds(time.Seconds) + TimeSpan.FromSeconds(value); }
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Trainer Info (offset 0x78, length 0xB18, end @ 0xB90)
|
2017-06-18 01:37:19 +00:00
|
|
|
|
public override string OT { get => GetString(0x78, 20); set { SetString(value, 10).CopyTo(Data, 0x78); OT2 = value; } }
|
|
|
|
|
private string OT2 { get => GetString(0x8C, 20); set => SetString(value, 10).CopyTo(Data, 0x8C); }
|
2018-04-28 18:06:58 +00:00
|
|
|
|
public override int SID { get => BigEndian.ToUInt16(Data, 0xA4); set => BigEndian.GetBytes((ushort)value).CopyTo(Data, 0xA4); }
|
|
|
|
|
public override int TID { get => BigEndian.ToUInt16(Data, 0xA6); set => BigEndian.GetBytes((ushort)value).CopyTo(Data, 0xA6); }
|
2017-05-13 03:32:36 +00:00
|
|
|
|
|
|
|
|
|
public override int Gender { get => Data[0xAF8]; set => Data[0xAF8] = (byte)value; }
|
|
|
|
|
public override uint Money { get => BigEndian.ToUInt32(Data, 0xAFC); set => BigEndian.GetBytes(value).CopyTo(Data, 0xAFC); }
|
|
|
|
|
public uint Coupons { get => BigEndian.ToUInt32(Data, 0xB00); set => BigEndian.GetBytes(value).CopyTo(Data, 0xB00); }
|
2017-06-18 01:37:19 +00:00
|
|
|
|
public string RUI_Name { get => GetString(0xB3A, 20); set => SetString(value, 10).CopyTo(Data, 0xB3A); }
|
2016-09-26 23:15:40 +00:00
|
|
|
|
|
|
|
|
|
public override InventoryPouch[] Inventory
|
|
|
|
|
{
|
|
|
|
|
get
|
|
|
|
|
{
|
|
|
|
|
InventoryPouch[] pouch =
|
|
|
|
|
{
|
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
|
|
|
|
new InventoryPouch3GC(InventoryType.Items, Legal.Pouch_Items_COLO, 999, 0x007F8, 20), // 20 COLO, 30 XD
|
|
|
|
|
new InventoryPouch3GC(InventoryType.KeyItems, Legal.Pouch_Key_COLO, 1, 0x00848, 43),
|
|
|
|
|
new InventoryPouch3GC(InventoryType.Balls, Legal.Pouch_Ball_RS, 999, 0x008F4, 16),
|
|
|
|
|
new InventoryPouch3GC(InventoryType.TMHMs, Legal.Pouch_TM_RS, 999, 0x00934, 64), // no HMs
|
|
|
|
|
new InventoryPouch3GC(InventoryType.Berries, Legal.Pouch_Berries_RS, 999, 0x00A34, 46),
|
|
|
|
|
new InventoryPouch3GC(InventoryType.Medicine, Legal.Pouch_Cologne_COLO, 999, 0x00AEC, 3), // Cologne
|
2016-09-26 23:15:40 +00:00
|
|
|
|
};
|
2019-03-30 23:10:14 +00:00
|
|
|
|
return pouch.LoadAll(Data);
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
2019-03-30 23:10:14 +00:00
|
|
|
|
set => value.SaveAll(Data);
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Daycare Structure:
|
|
|
|
|
// 0x00 -- Occupied
|
|
|
|
|
// 0x01 -- Deposited Level
|
|
|
|
|
// 0x02-0x03 -- unused?
|
|
|
|
|
// 0x04-0x07 -- Initial EXP
|
2019-10-19 03:42:03 +00:00
|
|
|
|
public override int GetDaycareSlotOffset(int loc, int slot) { return DaycareOffset + 8; }
|
2017-06-18 01:37:19 +00:00
|
|
|
|
public override uint? GetDaycareEXP(int loc, int slot) { return null; }
|
|
|
|
|
public override bool? IsDaycareOccupied(int loc, int slot) { return null; }
|
|
|
|
|
public override void SetDaycareEXP(int loc, int slot, uint EXP) { }
|
|
|
|
|
public override void SetDaycareOccupied(int loc, int slot, bool occupied) { }
|
|
|
|
|
|
2019-03-21 04:50:44 +00:00
|
|
|
|
public override string GetString(byte[] data, int offset, int length) => StringConverter3.GetBEString3(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;
|
2019-03-21 04:50:44 +00:00
|
|
|
|
return StringConverter3.SetBEString3(value, maxLength, PadToSize, PadWith);
|
2017-04-09 21:06:50 +00:00
|
|
|
|
}
|
2016-09-26 23:15:40 +00:00
|
|
|
|
}
|
|
|
|
|
}
|