mirror of
https://github.com/dmolony/DiskBrowser.git
synced 2025-02-06 04:29:56 +00:00
found bug in Wizardry exp points calculation
This commit is contained in:
parent
91846d8563
commit
ff7c6fd126
@ -38,8 +38,7 @@ class MazeGridV5 extends AbstractFile
|
||||
for (int col = 0; col < 8; col++)
|
||||
grid[row][col] = getLayout (i, row, col);
|
||||
|
||||
MazeGrid mazeGrid =
|
||||
new MazeGrid (grid, buffer[528 + i] & 0xFF, buffer[512 + i] & 0xFF);
|
||||
MazeGrid mazeGrid = new MazeGrid (grid, buffer[528 + i] & 0xFF, buffer[512 + i] & 0xFF);
|
||||
grids.add (mazeGrid);
|
||||
|
||||
minX = Math.min (minX, mazeGrid.xOffset);
|
||||
@ -60,11 +59,10 @@ class MazeGridV5 extends AbstractFile
|
||||
int gridWidth = (maxX - minX + 8) * cellSize.width;
|
||||
int gridHeight = (maxY - minY + 7) * cellSize.height;
|
||||
|
||||
image = new BufferedImage (gridWidth + 1, gridHeight + fudge,
|
||||
BufferedImage.TYPE_USHORT_555_RGB);
|
||||
image =
|
||||
new BufferedImage (gridWidth + 1, gridHeight + fudge, BufferedImage.TYPE_USHORT_555_RGB);
|
||||
Graphics2D g = image.createGraphics ();
|
||||
g.setRenderingHint (RenderingHints.KEY_ANTIALIASING,
|
||||
RenderingHints.VALUE_ANTIALIAS_ON);
|
||||
g.setRenderingHint (RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
|
||||
|
||||
g.setColor (Color.LIGHT_GRAY);
|
||||
g.fillRect (0, 0, gridWidth + 1, gridHeight + fudge);
|
||||
@ -183,8 +181,7 @@ class MazeGridV5 extends AbstractFile
|
||||
{
|
||||
List<String> messages = messageBlock.getMessageLines (msg);
|
||||
if (messages.size () > 0)
|
||||
text.append (
|
||||
String.format ("%n%4d %02X %04X %s%n", i, i, msg, messages.get (0)));
|
||||
text.append (String.format ("%n%4d %02X %04X %s%n", i, i, msg, messages.get (0)));
|
||||
else
|
||||
text.append (String.format ("Message not found: %04X%n", msg));
|
||||
|
||||
|
@ -247,6 +247,7 @@ public class MazeLevel extends AbstractFile
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
text.append ("\n\n");
|
||||
int savePtr = ptr;
|
||||
|
||||
text.append (String.format ("MINENEMY %04X %04X %04X%n", Utility.getShort (buffer, ptr),
|
||||
Utility.getShort (buffer, ptr + 10), Utility.getShort (buffer, ptr + 20)));
|
||||
@ -262,6 +263,28 @@ public class MazeLevel extends AbstractFile
|
||||
ptr += 2;
|
||||
text.append (String.format ("PERCWORS %04X %04X %04X%n", Utility.getShort (buffer, ptr),
|
||||
Utility.getShort (buffer, ptr + 10), Utility.getShort (buffer, ptr + 20)));
|
||||
|
||||
ptr = savePtr;
|
||||
for (int i = 0; i < 3; i++)
|
||||
{
|
||||
String pct = i == 0 ? "75" : i == 1 ? "18.75" : "6.25";
|
||||
text.append (String.format ("%nEnemy #%d %s%%%n%n", (i + 1), pct));
|
||||
int minenemy = Utility.getShort (buffer, ptr);
|
||||
int multwors = Utility.getShort (buffer, ptr + 2);
|
||||
int worse01 = Utility.getShort (buffer, ptr + 4);
|
||||
int range0n = Utility.getShort (buffer, ptr + 6);
|
||||
int percwors = Utility.getShort (buffer, ptr + 8);
|
||||
ptr += 10;
|
||||
|
||||
int max = multwors * worse01;
|
||||
|
||||
for (int id = minenemy; id < minenemy + range0n + max; id++)
|
||||
{
|
||||
if (id == minenemy + range0n)
|
||||
text.append ("\n");
|
||||
text.append (String.format ("%3d %-16s %n", id, monsters.get (id)));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
|
@ -23,12 +23,14 @@ class Monster extends AbstractFile
|
||||
public final int imageID;
|
||||
int rewardTable1;
|
||||
int rewardTable2;
|
||||
|
||||
public final int partnerID;
|
||||
public final int partnerOdds;
|
||||
public final int armourClass;
|
||||
public final int recsn;
|
||||
public final int mageSpellLevel;
|
||||
public final int priestSpellLevel;
|
||||
|
||||
int levelDrain;
|
||||
int healPts;
|
||||
int breathe;
|
||||
@ -40,14 +42,24 @@ class Monster extends AbstractFile
|
||||
List<Dice> damage = new ArrayList<> ();
|
||||
|
||||
static int counter = 0;
|
||||
static boolean debug = true;
|
||||
static int[] pwr = { 0, 1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 0, 0, 0, 0, 0 };
|
||||
static int[] weight1 = { 0, 1, 2, 4, 8, 16, 32, 64, 253, 506, 0 };
|
||||
static int[] weight2 = { 0, 60, 120, 180, 300, 540, 1020, 0 };
|
||||
|
||||
public static String[] monsterClass = { "Fighter", "Mage", "Priest", "Thief", "Midget", "Giant",
|
||||
"Mythical", "Dragon", "Animal", "Were", "Undead", "Demon", "Insect", "Enchanted" };
|
||||
|
||||
private static int[] experience = { //
|
||||
55, 235, 415, 230, 380, 620, 840, 520, 550, 350, // 00-09
|
||||
475, 515, 920, 600, 735, 520, 795, 780, 990, 795, // 10-19
|
||||
1360, 1320, 1275, 680, 960, 600, 755, 1120, 2075, 870, // 20-29
|
||||
960, 600, 1120, 2435, 1080, 2280, 975, 875, 1135, 1200, // 30-39
|
||||
620, 740, 1460, 1245, 960, 1405, 1040, 1220, 1520, 1000, // 40-49
|
||||
960, 2340, 2160, 2395, 790, 1140, 1235, 1790, 1720, 2240, // 50-59
|
||||
1475, 1540, 1720, 1900, 1240, 1220, 1020, 20435, 5100, 3515, // 60-69
|
||||
2115, 2920, 2060, 2140, 1400, 1640, 1280, 4450, 42840, 3300, // 70-79
|
||||
40875, 5000, 3300, 2395, 1935, 1600, 3330, 44090, 40840, 5200, // 80-89
|
||||
4155, 3000, 9200, 3160, 7460, 7320, 15880, 1600, 2200, 1000, // 90-99
|
||||
1900 // 100
|
||||
};
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
Monster (String name, byte[] buffer, List<Reward> rewards, List<Monster> monsters)
|
||||
// ---------------------------------------------------------------------------------//
|
||||
@ -134,8 +146,8 @@ class Monster extends AbstractFile
|
||||
text.append ("\nBreathe ......... " + breathe);
|
||||
text.append ("\nUnaffect ........ " + unaffect);
|
||||
|
||||
text.append ("\n\nResistance ...... " + String.format ("%02X", resistance));
|
||||
text.append ("\nAbilities ....... " + String.format ("%02X", abilities));
|
||||
text.append ("\n\nResistance ...... " + String.format ("%3d %<02X", resistance));
|
||||
text.append ("\nAbilities ....... " + String.format ("%3d %<02X", abilities));
|
||||
|
||||
text.append (String.format ("%n%nExperience ...... %-,7d", totalExperience));
|
||||
|
||||
@ -157,21 +169,20 @@ class Monster extends AbstractFile
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
int expHitPoints = hitPoints.qty * hitPoints.sides * (breathe == 0 ? 20 : 40);
|
||||
int expAc = 40 * (11 - armourClass);
|
||||
|
||||
int expMage = getBonus (35, mageSpellLevel);
|
||||
int expPriest = getBonus (35, priestSpellLevel);
|
||||
int expDrain = getBonus (200, levelDrain);
|
||||
int expHeal = getBonus (90, healPts);
|
||||
|
||||
int expAc = 40 * (11 - armourClass);
|
||||
|
||||
int expDamage = recsn <= 1 ? 0 : getBonus (30, recsn);
|
||||
int expUnaffect = unaffect == 0 ? 0 : getBonus (40, (unaffect / 10 + 1));
|
||||
|
||||
int expFlags1 = getBonus (35, Integer.bitCount (resistance & 0x7E));
|
||||
int expFlags2 = getBonus (40, Integer.bitCount (abilities & 0x7F));
|
||||
|
||||
return expHitPoints + expMage + expPriest + expDrain + expHeal + expAc + expDamage + expUnaffect
|
||||
return expHitPoints + expAc + expMage + expPriest + expDrain + expHeal + expDamage + expUnaffect
|
||||
+ expFlags1 + expFlags2;
|
||||
}
|
||||
|
||||
@ -183,10 +194,13 @@ class Monster extends AbstractFile
|
||||
return 0;
|
||||
|
||||
int total = base;
|
||||
for (int i = 1; i < multiplier; i++)
|
||||
total *= 2;
|
||||
while (multiplier > 1)
|
||||
{
|
||||
multiplier--;
|
||||
total += total; // double the value
|
||||
}
|
||||
|
||||
return total + total / 10000 * 10000;
|
||||
return total + total / 10000 * 10000; // mimics the Wizardry bug
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
@ -231,17 +245,21 @@ class Monster extends AbstractFile
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
StringBuilder line = new StringBuilder (String.format ("%3d %-16s", monsterID, realName));
|
||||
|
||||
int lo = block == 0 ? 64 : block == 1 ? 88 : block == 2 ? 112 : 136;
|
||||
int hi = lo + 24;
|
||||
if (hi > buffer.length)
|
||||
hi = buffer.length;
|
||||
|
||||
for (int i = lo; i < hi; i++)
|
||||
line.append (String.format ("%02X ", buffer[i]));
|
||||
|
||||
if (block == 3)
|
||||
{
|
||||
int exp = getExperience ();
|
||||
line.append (String.format (" %,6d", exp));
|
||||
line.append (String.format (" %,6d %,6d", exp, exp - experience[monsterID]));
|
||||
}
|
||||
|
||||
return line.toString ();
|
||||
}
|
||||
|
||||
|
295
src/com/bytezone/diskbrowser/wizardry/WizLong.java
Normal file
295
src/com/bytezone/diskbrowser/wizardry/WizLong.java
Normal file
@ -0,0 +1,295 @@
|
||||
package com.bytezone.diskbrowser.wizardry;
|
||||
|
||||
// -----------------------------------------------------------------------------------//
|
||||
public class WizLong
|
||||
// -----------------------------------------------------------------------------------//
|
||||
{
|
||||
private static final int MAX = 10000;
|
||||
|
||||
int high; // 4 digits per component
|
||||
int mid;
|
||||
int low;
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
public WizLong (int value)
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
assert value >= 0 && value < MAX;
|
||||
|
||||
low = value;
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
public void addLong (WizLong other)
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
low += other.low;
|
||||
if (low >= MAX)
|
||||
{
|
||||
mid++;
|
||||
low -= MAX;
|
||||
}
|
||||
|
||||
mid += other.mid;
|
||||
if (mid >= MAX)
|
||||
{
|
||||
high++;
|
||||
mid -= MAX;
|
||||
}
|
||||
|
||||
high += other.high;
|
||||
if (high >= MAX)
|
||||
{
|
||||
high = MAX - 1;
|
||||
mid = MAX - 1;
|
||||
low = MAX - 1;
|
||||
}
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
public void subLong (WizLong other)
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
low -= other.low;
|
||||
if (low < 0)
|
||||
{
|
||||
mid--;
|
||||
low += MAX;
|
||||
}
|
||||
|
||||
mid -= other.mid;
|
||||
if (mid < 0)
|
||||
{
|
||||
high--;
|
||||
mid += MAX;
|
||||
}
|
||||
|
||||
high -= other.high;
|
||||
if (high < 0)
|
||||
{
|
||||
high = 0;
|
||||
mid = 0;
|
||||
low = 0;
|
||||
}
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
public void multLong (int multiplier)
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
BCD bcd = long2bcd ();
|
||||
|
||||
for (int digit = 12; digit >= 1; digit--)
|
||||
{
|
||||
bcd.value[digit] *= multiplier;
|
||||
}
|
||||
|
||||
for (int digit = 12; digit >= 1; digit--)
|
||||
{
|
||||
if (bcd.value[digit] > 9)
|
||||
{
|
||||
bcd.value[digit - 1] += bcd.value[digit] / 10;
|
||||
bcd.value[digit] %= 10;
|
||||
}
|
||||
}
|
||||
bcd2long (bcd);
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
public void divLong (WizLong other)
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
public BCD long2bcd ()
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
BCD bcd = new BCD ();
|
||||
|
||||
bcd.value[0] = 0;
|
||||
|
||||
int2bcd (high, 1, bcd);
|
||||
int2bcd (mid, 5, bcd);
|
||||
int2bcd (low, 9, bcd);
|
||||
|
||||
return bcd;
|
||||
}
|
||||
|
||||
private static void int2bcd (int part, int digit, BCD bcd)
|
||||
{
|
||||
bcd.value[digit++] = part / 1000;
|
||||
part %= 1000;
|
||||
bcd.value[digit++] = part / 100;
|
||||
part %= 100;
|
||||
bcd.value[digit++] = part / 10;
|
||||
part %= 10;
|
||||
bcd.value[digit++] = part;
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
public void bcd2long (BCD other)
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
high = mid = low = 0;
|
||||
|
||||
high = bcd2int (1, other);
|
||||
mid = bcd2int (5, other);
|
||||
low = bcd2int (9, other);
|
||||
}
|
||||
|
||||
private static int bcd2int (int digit, BCD bcd)
|
||||
{
|
||||
int val = bcd.value[digit++] * 1000;
|
||||
val += bcd.value[digit++] * 100;
|
||||
val += bcd.value[digit++] * 10;
|
||||
val += bcd.value[digit];
|
||||
|
||||
return val;
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
public int testLong (WizLong other)
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
if (high == other.high)
|
||||
if (mid == other.mid)
|
||||
if (low == other.low)
|
||||
return 0;
|
||||
else
|
||||
return low > other.low ? 1 : -1;
|
||||
else
|
||||
return mid > other.mid ? 1 : -1;
|
||||
else
|
||||
return high > other.high ? 1 : -1;
|
||||
}
|
||||
|
||||
public int value ()
|
||||
{
|
||||
return high * 10000 * 10000 + mid * 10000 + low;
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
public void printLong ()
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
BCD bcd = long2bcd ();
|
||||
int digit = 1;
|
||||
|
||||
while (digit < 12 && bcd.value[digit] == 0)
|
||||
{
|
||||
System.out.print (' ');
|
||||
digit++;
|
||||
}
|
||||
|
||||
while (digit <= 12)
|
||||
System.out.print (bcd.value[digit++]);
|
||||
|
||||
System.out.println ();
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
class BCD
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
int[] value = new int[14];
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
private static void multAddKX (WizLong killExp, int multiply, int amount)
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
if (multiply == 0)
|
||||
return;
|
||||
|
||||
WizLong killExpx = new WizLong (amount);
|
||||
|
||||
while (multiply > 1)
|
||||
{
|
||||
multiply--;
|
||||
killExpx.addLong (killExpx); // double the value
|
||||
}
|
||||
|
||||
killExp.addLong (killExpx); // add to running total
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------------//
|
||||
public static void main (String[] args)
|
||||
// ---------------------------------------------------------------------------------//
|
||||
{
|
||||
// Earth Giant
|
||||
int hpSides = 1;
|
||||
int hpLevel = 1;
|
||||
int ac = 9;
|
||||
int recsn = 2;
|
||||
int drain = 0;
|
||||
int mageSpells = 0;
|
||||
int priestSpells = 0;
|
||||
int heal = 0;
|
||||
int breathe = 0;
|
||||
int unaffect = 85;
|
||||
int wepsty = 0x40;
|
||||
int sppc = 0;
|
||||
|
||||
// Werdna
|
||||
// int hpSides = 10;
|
||||
// int hpLevel = 10;
|
||||
// int ac = -7;
|
||||
// int recsn = 2;
|
||||
// int drain = 4;
|
||||
// int mageSpells = 7;
|
||||
// int priestSpells = 7;
|
||||
// int heal = 5;
|
||||
// int breathe = 0;
|
||||
// int unaffect = 70;
|
||||
// int wepsty = 0x0E;
|
||||
// int sppc = 0x0F;
|
||||
|
||||
// Will O Wisp
|
||||
// int hpSides = 10;
|
||||
// int hpLevel = 8;
|
||||
// int ac = -8;
|
||||
// int recsn = 1;
|
||||
// int drain = 0;
|
||||
// int mageSpells = 0;
|
||||
// int priestSpells = 0;
|
||||
// int heal = 0;
|
||||
// int breathe = 0;
|
||||
// int unaffect = 95;
|
||||
// int wepsty = 0;
|
||||
// int sppc = 0;
|
||||
|
||||
WizLong killExp = new WizLong (0); // running total
|
||||
|
||||
WizLong killExpx = new WizLong (hpLevel * hpSides);
|
||||
killExpx.multLong (breathe == 0 ? 20 : 40);
|
||||
killExp.addLong (killExpx);
|
||||
|
||||
killExp.printLong ();
|
||||
|
||||
multAddKX (killExp, mageSpells, 35);
|
||||
multAddKX (killExp, priestSpells, 35);
|
||||
multAddKX (killExp, drain, 200);
|
||||
multAddKX (killExp, heal, 90);
|
||||
killExp.printLong ();
|
||||
|
||||
killExpx = new WizLong (40 * (11 - ac));
|
||||
killExp.addLong (killExpx);
|
||||
killExp.printLong ();
|
||||
|
||||
if (recsn > 1)
|
||||
multAddKX (killExp, recsn, 30);
|
||||
killExp.printLong ();
|
||||
|
||||
if (unaffect > 0)
|
||||
multAddKX (killExp, (unaffect / 10 + 1), 40);
|
||||
killExp.printLong ();
|
||||
|
||||
multAddKX (killExp, Integer.bitCount (wepsty & 0x7E), 35); // 6 bits
|
||||
// System.out.println (Integer.bitCount (wepsty));
|
||||
multAddKX (killExp, Integer.bitCount (sppc & 0x7F), 40); // 7 bits
|
||||
|
||||
killExp.printLong ();
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user