From 92948885ff2e98cf9a6f9d754da75c321d2d126c Mon Sep 17 00:00:00 2001 From: Kurt Date: Wed, 8 Feb 2017 15:51:18 -0800 Subject: [PATCH] Simplify money/coin getset Binary Coded Decimal Closes #836 --- PKHeX/Saves/SAV1.cs | 11 ++++++----- PKHeX/Saves/SAV2.cs | 11 ++++++----- PKHeX/Util/BigEndian.cs | 35 +++++++++++++++++++++++++++++++++++ 3 files changed, 47 insertions(+), 10 deletions(-) diff --git a/PKHeX/Saves/SAV1.cs b/PKHeX/Saves/SAV1.cs index 7a053bfca..431bdab30 100644 --- a/PKHeX/Saves/SAV1.cs +++ b/PKHeX/Saves/SAV1.cs @@ -318,22 +318,23 @@ public int TextSpeed } public override uint Money { - get { return uint.Parse((BigEndian.ToUInt32(Data, Japanese ? 0x25EE : 0x25F3) >> 8).ToString("X6")); } + get { return (uint)BigEndian.BCDToInt32(Data, Japanese ? 0x25EE : 0x25F3, 3); } set { - BigEndian.GetBytes(Convert.ToUInt32(value.ToString("000000"), 16)).Skip(1).ToArray().CopyTo(Data, Japanese ? 0x25EE : 0x25F3); + value = (uint)Math.Min(value, MaxMoney); + BigEndian.Int32ToBCD((int)value, 3).CopyTo(Data, Japanese ? 0x25EE : 0x25F3); } } public uint Coin { get { - return uint.Parse(BigEndian.ToUInt16(Data, Japanese ? 0x2846 : 0x2850).ToString("X4")); + return (uint)BigEndian.BCDToInt32(Data, Japanese ? 0x2846 : 0x2850, 2); } set { - ushort val = (ushort)Math.Min(value, MaxCoins); - BigEndian.GetBytes(val).CopyTo(Data, Japanese ? 0x2846 : 0x2850); + value = (ushort)Math.Min(value, MaxCoins); + BigEndian.Int32ToBCD((int)value, 2).CopyTo(Data, Japanese ? 0x2846 : 0x2850); } } diff --git a/PKHeX/Saves/SAV2.cs b/PKHeX/Saves/SAV2.cs index 7133091cc..f435ae81c 100644 --- a/PKHeX/Saves/SAV2.cs +++ b/PKHeX/Saves/SAV2.cs @@ -448,22 +448,23 @@ public int TextSpeed } public override uint Money { - get { return BigEndian.ToUInt32(Data, MoneyOffset) >> 8; } + get { return (uint)BigEndian.BCDToInt32(Data, MoneyOffset, 3); } set { - BigEndian.GetBytes(value > 999999 ? 999999 : value).Skip(1).ToArray().CopyTo(Data, MoneyOffset); + value = (uint)Math.Min(value, MaxMoney); + BigEndian.Int32ToBCD((int)value, 3).CopyTo(Data, MoneyOffset); } } public uint Coin { get { - return BigEndian.ToUInt16(Data, MoneyOffset + 7); + return (uint)BigEndian.BCDToInt32(Data, MoneyOffset + 7, 2); } set { - ushort val = (ushort)Math.Min(value, MaxCoins); - BigEndian.GetBytes(val).CopyTo(Data, MoneyOffset + 7); + value = (ushort)Math.Min(value, MaxCoins); + BigEndian.Int32ToBCD((int)value, 2).CopyTo(Data, MoneyOffset + 7); } } diff --git a/PKHeX/Util/BigEndian.cs b/PKHeX/Util/BigEndian.cs index 70b4555ae..c8ff24a30 100644 --- a/PKHeX/Util/BigEndian.cs +++ b/PKHeX/Util/BigEndian.cs @@ -63,5 +63,40 @@ private static byte[] Invert(byte[] data) result[--i] = data[o++]; return result; } + + /// + /// Returns a 32-bit signed integer converted from bytes in a Binary Coded Decimal format byte array. + /// + /// Input byte array to read from. + /// Offset to start reading at. + /// Length of array to read. + public static int BCDToInt32(byte[] input, int offset, int length) + { + int result = 0; + for (int i = offset; i < offset + length; i++) + { + byte p = input[i]; + result *= 100; + result += 10 * (p >> 4); + result += p & 0xf; + } + return result; + } + /// + /// Returns the specified 32-bit signed integer value as an array of Binary Coded Decimal format bytes. + /// + /// 32-bit signed integer to convert. + /// Desired size of returned array. + public static byte[] Int32ToBCD(int input, int size) + { + byte[] result = new byte[size]; + for (int i = 0; i < size; i++) + { + int p = input%100; + input /= 100; + result[size - i - 1] = (byte)(p/10 << 4 | p%10); + } + return result; + } } }