public void UpdateMagearnaConstant() { var flag = GetEventFlag(3100); ulong value = flag ? MagearnaConst : 0ul; WriteUInt64LittleEndian(Data.AsSpan(Blocks.BlockInfo[35].Offset + 0x168), value); }
protected override void SetBoxMetadata(int box) { var bdata = GetBoxOffset(box); // Set box count int count = 0; for (int s = 0; s < BoxSlotCount; s++) { var rel = bdata + (SIZE_STORED * s); if (Data[rel] != 0) // Species present { count++; } } var boxOfs = bdata - ListHeaderSizeBox; if (Data[boxOfs] == 0) { Data[boxOfs] = 1; Data[boxOfs + 1] = (byte)count; Data[boxOfs + 4] = StringConverter12.G1TerminatorCode; StringConverter12.SetString(Data.AsSpan(boxOfs + 0x10, 4), "1234".AsSpan(), 4, Japanese, StringConverterOption.None); } else { Data[boxOfs + 1] = (byte)count; } }
public PersonalInfoXY(byte[] data) : base(data) { // Unpack TMHM & Tutors TMHM = GetBits(Data.AsSpan(0x28, 0x10)); TypeTutors = GetBits(Data.AsSpan(0x38, 0x4)); // 0x3C-0x40 unknown }
public override byte[] Write() { SetBits(TMHM, Data.AsSpan(0x28)); SetBits(TypeTutors, Data.AsSpan(0x38)); SetBits(SpecialTutors[0], Data.AsSpan(0x3C)); return(Data); }
public override void SetRecord(int recordID, int value) { if ((uint)recordID >= RecordCount) { throw new ArgumentOutOfRangeException(nameof(recordID)); } int ofs = GetRecordOffset(recordID); int max = GetRecordMax(recordID); if (value > max) { value = max; } switch (recordID) { case < 100: WriteInt32LittleEndian(Data.AsSpan(ofs), value); break; case < 200: WriteUInt16LittleEndian(Data.AsSpan(ofs), (ushort)value); break; default: Trace.Fail(nameof(recordID)); break; } }
protected override void SetBoxChecksum(int box) { var boxOfs = GetBoxOffset(box) - ListHeaderSize; const int size = BoxSizeJ - 2; var chk = Checksums.CheckSum16(new ReadOnlySpan <byte>(Data, boxOfs, size)); WriteUInt16BigEndian(Data.AsSpan(boxOfs + size), chk); }
public override string GetDaycareRNGSeed(int loc) { int ofs = DaycareOffset; var data = Data.AsSpan(ofs + 0x1E8, DaycareSeedSize / 2).ToArray(); Array.Reverse(data); return(BitConverter.ToString(data).Replace("-", string.Empty)); }
protected override bool GetIsBoxChecksumValid(int box) { var boxOfs = GetBoxOffset(box) - ListHeaderSize; const int size = BoxSizeJ - 2; var chk = Checksums.CheckSum16(new ReadOnlySpan <byte>(Data, boxOfs, size)); var actual = ReadUInt16BigEndian(Data.AsSpan(boxOfs + size)); return(chk == actual); }
public void SaveBattleTeams() { var span = Data.AsSpan(Offset); for (int i = 0; i < TeamCount * 6; i++) { int index = TeamSlots[i]; if (index < 0) { WriteInt16LittleEndian(span[(i * 2)..], (short)index);
public PersonalInfoSM(byte[] data) : base(data) { TMHM = GetBits(Data.AsSpan(0x28, 0x10)); // 36-39 TypeTutors = GetBits(Data.AsSpan(0x38, 0x4)); // 40 SpecialTutors = new[] { GetBits(Data.AsSpan(0x3C, 0x0A)), }; }
private ushort CalculateChecksum() { ushort chk = 0; for (int i = 8; i < PokeCrypto.SIZE_8STORED; i += 2) { chk += ReadUInt16LittleEndian(Data.AsSpan(i)); } return(chk); }
public override void SetMessage(string line1, string line2) { if (US) { StringConverter12.SetString(Data.AsSpan(0x11, 0x10), line2.AsSpan(), 0x10, false, StringConverterOption.Clear50); bool hasLine2 = Data[0x11] != StringConverter12.G1TerminatorCode; var padChar = !hasLine2 ? StringConverterOption.Clear50 : StringConverterOption.Clear7F; // space StringConverter12.SetString(Data.AsSpan(0, 0x10), line1.AsSpan(), 0x10, false, padChar); Data[0x10] = 0x4E; } }
public PersonalInfoB2W2(byte[] data) : base(data) { // Unpack TMHM & Tutors TMHM = GetBits(Data.AsSpan(0x28, 0x10)); TypeTutors = GetBits(Data.AsSpan(0x38, 0x4)); SpecialTutors = new[] { GetBits(Data.AsSpan(0x3C, 0x04)), GetBits(Data.AsSpan(0x40, 0x04)), GetBits(Data.AsSpan(0x44, 0x04)), GetBits(Data.AsSpan(0x48, 0x04)), }; }
protected override void SetChecksums() { // ensure the final data is written if the user screws stuff up WriteInt32BigEndian(Data.AsSpan(FinalCountOffset), FinalCount); var goodlen = (FinalCountOffset + 4); Array.Clear(Data, goodlen, Data.Length - goodlen); // 20 byte SHA checksum at the top of the file, which covers all data that follows. using var hash = SHA1.Create(); var result = hash.ComputeHash(Data, 20, Data.Length - 20); SetData(result, 0); }
public string GetTeamName(int team) { var name = $"{((Stadium2TeamType) (team / TeamCountType)).ToString().Replace('_', ' ')} {(team % 10) + 1}"; var ofs = GetTeamOffset(team); var str = GetString(ofs + 4, 7); if (string.IsNullOrWhiteSpace(str)) { return(name); } var id = ReadUInt16BigEndian(Data.AsSpan(ofs + 2)); return($"{name} [{id:D5}:{str}]"); }
public static int GetTeamOffset(int team) => 0 + (team * 2 * TeamSizeJ); // backups are after each team public string GetTeamName(int team) { var name = $"Team {team + 1}"; var ofs = GetTeamOffset(team); var str = GetString(ofs + 2, 5); if (string.IsNullOrWhiteSpace(str)) { return(name); } var id = ReadUInt16BigEndian(Data.AsSpan(ofs + 8)); return($"{name} [{id:D5}:{str}]"); }
public override int GetRecord(int recordID) { int ofs = Records.GetOffset(Offset, recordID); switch (recordID) { case < 100: return(ReadInt32LittleEndian(Data.AsSpan(ofs))); case < 200: return(ReadInt16LittleEndian(Data.AsSpan(ofs))); default: Trace.Fail(nameof(recordID)); return(0); } }
private void InitializeData(ReadOnlySpan <byte> data) { Data = DecryptPBRSaveData(data); // Detect active save var first = ReadUInt32BigEndian(Data.AsSpan(0x00004C)); var second = ReadUInt32BigEndian(Data.AsSpan(0x1C004C)); SaveCount = Math.Max(second, first); if (second > first) { // swap halves byte[] tempData = new byte[0x1C0000]; Array.Copy(Data, 0, tempData, 0, 0x1C0000); Array.Copy(Data, 0x1C0000, Data, 0, 0x1C0000); tempData.CopyTo(Data, 0x1C0000); } var names = (string[])SaveNames; for (int i = 0; i < SAVE_COUNT; i++) { var name = GetOTName(i); if (string.IsNullOrWhiteSpace(name)) { name = $"Empty {i + 1}"; } else if (_currentSlot == -1) { _currentSlot = i; } names[i] = name; } if (_currentSlot == -1) { _currentSlot = 0; } CurrentSlot = _currentSlot; }
public SAV4Ranch(byte[] data) : base(data, typeof(PK4), 0) { Version = Data.Length == SaveUtil.SIZE_G4RANCH_PLAT ? GameVersion.Pt : GameVersion.DP; OT = GetString(0x770, 0x12); // 0x18 starts the header table // Block 00, Offset = ??? // Block 01, Offset = Mii Data // Block 02, Offset = Mii Link Data // Block 03, Offset = Pokemon Data // Block 04, Offset = ?? // Unpack the binary a little: // size, count, Mii data[count] // size, count, Mii Link data[count] // size, count, Pokemon (PK4 + metadata)[count] // size, count, ??? /* ====Metadata==== * uint8_t poke_type;// 01 trainer, 04 hayley, 05 traded * uint8_t tradeable;// 02 is tradeable, normal 00 * uint16_t tid; * uint16_t sid; * uint32_t name1; * uint32_t name2; * uint32_t name3; * uint32_t name4; */ var pkCountOffset = ReadInt32BigEndian(Data.AsSpan(0x34)) + 4; SlotCount = ReadInt32BigEndian(Data.AsSpan(pkCountOffset)); BoxCount = (int)Math.Ceiling((decimal)SlotCount / SlotsPerBox); Box = pkCountOffset + 4; FinalCountOffset = ReadInt32BigEndian(Data.AsSpan(0x3C)); FinalCount = ReadInt32BigEndian(Data.AsSpan(FinalCountOffset)); }
public void LoadBattleTeams() { if (!SAV.State.Exportable) { ClearBattleTeams(); return; } for (int i = 0; i < TeamCount * 6; i++) { short val = ReadInt16LittleEndian(Data.AsSpan(Offset + (i * 2))); if (val < 0) { TeamSlots[i] = NONE_SELECTED; continue; } int box = val >> 8; int slot = val & 0xFF; int index = (SAV.BoxSlotCount * box) + slot; TeamSlots[i] = index & 0xFFFF; } }
public void SetArrayNew(int region, bool[] value) => ArrayUtil.SetBitFlagArray(Data.AsSpan((region + REGIONS) * SIZE_ENTRY), value);
public int GetWork(int index) => ReadInt32LittleEndian(Data.AsSpan(Offset + (index * WorkSize)));
private Span <byte> GetBoxNameSpan(int box) => Data.AsSpan(GetBoxNameOffset(box), SAV6.LongStringLength);
public override string GetMessage(bool isLastLine) => US?StringConverter12.GetString(Data.AsSpan(isLastLine ? 0x11 : 0, 0x10), false) : string.Empty;
public void SetWork(int index, int value) => WriteInt32LittleEndian(Data.AsSpan(Offset + (index * WorkSize)), value);
public bool[] GetArrayOwned(int region) => ArrayUtil.GitBitFlagArray(Data.AsSpan(region * SIZE_ENTRY), SIZE_ENTRY * 8);
public bool[] GetArrayNew(int region) => ArrayUtil.GitBitFlagArray(Data.AsSpan((region + REGIONS) * SIZE_ENTRY), SIZE_ENTRY * 8);
public void SetArrayOwned(int region, bool[] value) => ArrayUtil.SetBitFlagArray(Data.AsSpan(region * SIZE_ENTRY), value);
public PersonalInfoGG(byte[] data) : base(data) { TMHM = GetBits(Data.AsSpan(0x28, 8)); // only 60 TMs used TypeTutors = GetBits(Data.AsSpan(0x38, 1)); // at most 8 flags used }
public PersonalInfoBW(byte[] data) : base(data) { // Unpack TMHM & Tutors TMHM = GetBits(Data.AsSpan(0x28, 0x10)); TypeTutors = GetBits(Data.AsSpan(0x38, 0x4)); }