Jump to content

Minutiae


Wisp

Recommended Posts

But my suspicion is that going through chunks of five-year-old code in Fixpack and recoding it is an absolute recipe for introducing embarrassing bugs.

I don't know how much of a problem that'd be in this case. Fixpack is installed as one of the first mods, so you don't have complicated installation orders to account for. Additionally, since the goal would be equivalency, it would be straightforward to compare the new code to the old code by diffing the output (and thus ensure the new code is, at least, no buggier than the old code).

Since you have diffing to guard against regressions I wouldn't be surprised if a recode would result in fewer bugs. Fixpack's rather large and most of the bugs are found when one of us spelunkers accidentally trip over it. It stands to reason there are a few more in there, that no one's tripped over yet. Recoding (rethinking) the fixes are the best way of finding them.

I suspect it would also result in shorter and/or more manageable code, since TP2 is more powerful today.

Link to comment

Anywho, the fixes:

 

Code for correcting weights and speeds on items:

ACTION_CLEAR_ARRAY fl#speed_item
ACTION_DEFINE_ASSOCIATIVE_ARRAY fl#speed_item BEGIN
 AEGIS	=> 1  //Aegis Fang
 AEGIS2   => 1  //Aegis Fang
 AX1H07   => 7  //Bala's Axe
 BOW25	=> 4  //Long Bow +3
 DART01   => 2  //Dart
 MISC4U   => 2  //Embarl's Dagger
 MISC9Q   => 5  //Scimitar
 SPER03   => 6  //Spear +3, Backbiter
 SPER12   => 1  //Ixil's Spike +6
 STAF04   => 4  //Quarterstaff
 STAF05   => 1  //Staff of Striking
 STAF11   => 3  //Staff of the Magi
 STAF13   => 2  //Staff of Thunder and Lightning
 SW1H26   => 2  //Ilbratha +1
 SW1H53   => 4  //Sword of Flame +1
 SW1H69   => 1  //Spectral Brand +5
 SW2H03   => 10 //Cursed Berserking Sword +3
END

ACTION_PHP_EACH fl#speed_item AS item => speed BEGIN
 ACTION_IF FILE_EXISTS_IN_GAME "%item%.itm" BEGIN
COPY_EXISTING "%item%.itm" override
  READ_LONG 0x64 ao
  FOR (i=0;i<SHORT_AT 0x68;++i) BEGIN
	READ_BYTE ao + 0x38*i type
	PATCH_IF type = 1 OR type = 2 OR type = 4 BEGIN
	  WRITE_SHORT ao + 0x38*i + 0x12 speed
	END
  END
BUT_ONLY
 END
END

ACTION_CLEAR_ARRAY fl#weight_item
ACTION_DEFINE_ASSOCIATIVE_ARRAY fl#weight_item BEGIN
 BRAC15   => 2  //Bracers of Defense AC 3
 CLCK13   => 4  //Traveller's Robe
 DAGG05   => 1  //Throwing Dagger
 DWCHAN02 => 12 //Drow Adamantine Chain +5
 DWSHLD01 => 7  //Drow Shield +3
 SHLD23   => 3  //Fortress Shield +3
 SPER06   => 3  //Spear +3
 STAF04   => 4  //Quarterstaff
 STAF08   => 4  //Martial Staff +3
 STAF10   => 4  //Staff of Curing
 STAF11   => 4  //Staff of the Magi
 STAF13   => 4  //Staff of Thunder and Lightning
 STAF20   => 3  //Staff of Rynn +4
 SW1H15   => 4  //Scimitar +3, Frostbrand
 SW1H16   => 4  //Scimitar +5, Defender
 SW1H23   => 4  //Scimitar +2, Rashad's Talon
 SW1H32   => 3  //Dragonslayer
 SW2H03   => 15 //Cursed Berserking Sword +3
 SW2H12   => 10 //Flame Of The North
 SW2H15   => 15 //Silver Sword
END

ACTION_PHP_EACH fl#weight_item AS item => weight BEGIN
 ACTION_IF FILE_EXISTS_IN_GAME "%item%.itm" BEGIN
COPY_EXISTING "%item%.itm" override
  WRITE_LONG 0x4c weight
BUT_ONLY
 END
END

In the interest of keeping it all in one place, I absorbed the current weight and speed fixes, except for the weight fix to bow06. I was also brash enough to use the speed values I prefer for sper12 and staf11, but that's easy enough to change.

 

Correct strength requirement for Adjatha, in diff form:

@@ -17437,8 +17441,9 @@
 WRITE_BYTE  ("%fx_off%" + 0x0d) 2	// not dispel/not bypass
 WRITE_BYTE  ("%fx_off%" + 0x12) 100  // probability


-// adjatha's healing does not bypass MR
+// adjatha's healing does not bypass MR and the sword has an incorrect strength requirement
COPY_EXISTING ~sw1h35.itm~ ~override~
+  WRITE_BYTE 0x26 6
  READ_LONG  0x64 "abil_off"
  READ_SHORT 0x68 "abil_num"
  READ_LONG  0x6a "fx_off"

 

 

Code for generating updated descriptions in the comfort of your own home:

//Reads the description from the item, corrects the value and prints the corrected description to the file fldesc.tra. The accompanying line for STRING_SET is printed to fldesc.tpa.

OUTER_SPRINT DIR test //The output is copied to this directory. Change to wherever you're running the code from.

<<<<<<<< ...blank


>>>>>>>>

ACTION_DEFINE_ASSOCIATIVE_ARRAY weight_desc BEGIN
 BAG06	=> 2  //Bags of Holding weigh 5. All other bags weigh 2.
 BAG06B   => 2
 BAG06C   => 2
 BAG06D   => 2
 BLUN03   => 13 //Consistent with weight trend
 BLUN35   => 7  //Consistent with weight trend
 BOW11	=> 8  //Consistent with weight trend for other bows
 HLOLTH   => 7  //Consistent with weight trend
 KUOBOLT  => 0  //No other ammunition weigh anything
 MISC5T   => 4  //Fixpack also alters speed to be consistent with that of an unenchanted staff
 SHLD27   => 4  //Consistent with weight trend among medium shields
 WA2SHIEL => 4
END

ACTION_DEFINE_ASSOCIATIVE_ARRAY speed_desc BEGIN
 BLUN14D  => 5
 BLUN14E  => 5
 BLUN14F  => 5
 BLUN35   => 3
 BOW11	=> 5
 BOW25	=> 4
 HALB04   => 6
 MISC4U   => 2
 MISC5T   => 4
 NPSTAF   => 2
 NPSW05   => 1
 NPSW06   => 1
 SPER11   => 2
 SPER12   => 1
 STAF10   => 3
 STAF11   => 3
 STAF13   => 2
 STAF15   => 2
 STAF16   => 2
 STAF17   => 2
 STAF18   => 2
 STAF23   => 2
 SW1H52   => 2
 SW1H60   => 1
 SW2H15   => 7
 TELSWD   => 2
 WA2HALB  => 6
END

COPY "...blank" "override/fldesc.tra"
 "...blank" "override/fldesc.tpa"

ACTION_PHP_EACH weight_desc AS item => weight BEGIN
 COPY_EXISTING "%item%.itm" override
off = (BYTE_AT 0x18 BAND BIT6) = BIT6 ? 0x54 : 0x50
READ_LONG off strref
READ_STRREF off desc
SPRINT tra "@1"
FOR (i=0;i< 6 - STRING_LENGTH "%strref%";++i) BEGIN
  SPRINT tra "%tra%0"
END
SPRINT tra "%tra%%strref%"
INNER_PATCH_SAVE desc "%desc%" BEGIN
  REPLACE_TEXTUALLY CASE_INSENSITIVE "Weight:\( +\)[0-9]+" "Weight:\1%weight%"
END
SPRINT $desc("%tra%") "%desc%"
 BUT_ONLY
END  

ACTION_PHP_EACH speed_desc AS item => speed BEGIN
 COPY_EXISTING "%item%.itm" override
off = (BYTE_AT 0x18 BAND BIT6) = BIT6 ? 0x54 : 0x50
READ_LONG off strref
READ_STRREF off desc
SPRINT tra "@1"
FOR (i=0;i< 6 - STRING_LENGTH "%strref%";++i) BEGIN
  SPRINT tra "%tra%0"
END
SPRINT tra "%tra%%strref%"
PATCH_IF VARIABLE_IS_SET $desc("%tra%") BEGIN
  SPRINT desc $desc("%tra%")
END
INNER_PATCH_SAVE desc "%desc%" BEGIN
  REPLACE_TEXTUALLY CASE_INSENSITIVE "Speed Factor:\( +\)[0-9]+" "Speed Factor:\1%speed%"
END
 BUT_ONLY
 APPEND fldesc.tra "%tra% = ~%desc%~%LNL%%LNL%" KEEP_CRLF
 APPEND fldesc.tpa "%strref% %tra%"
END

COPY_EXISTING fldesc.tra "%DIR%"
		  fldesc.tpa "%DIR%"

 

And some lovingly handcrafted strings for the left-overs:

1764  @1001764
21957 @1021957
32186 @1032186
32187 @1032187
39461 @1039461			  


@1001764 = ~Battle Axe +3

This is the axe of Bruenor Battlehammer, and a fine weapon it is. It has a formidable single-edged blade, and handles with the efficiency of a hand axe despite its size.

STATISTICS:

THAC0: +3 bonus
Damage:  3D8 + 3
Damage type:  slashing
Weight: 6
Speed Factor: 4
Proficiency Type: Axe
Type:  1-handed
Not Usable By:
Druid
Cleric
Mage 
Thief~


@1021957 = ~Bala's Axe - Wizard Slayer:
Bala was a foul-tempered prince of a gully dwarf clan, which was enslaved by a cruel elven mage in Thesk. Though Bala managed to escape the more cowardly traits of his race he was even more filthy and obnoxious than the average gully dwarf. Sickened of his enslavement, Bala crept into the mage's lair and cracked the elf's skull open. Although rumor has it that it was the dwarf's stench that overcame the mage, it was, in fact, his enchanted axe that dispelled the elf's magical defenses. It is obvious from the poor workmanship that Bala himself crafted the axe. The mystery lies in where its power originates. After a lengthy career of mage-slaying, Bala died, never having revealed his secret to those who were willing to risk a lice infestation by approaching him. Some say that the axe was powered by Bala's intense hatred of wizards. The axe gives the owner the ability to dispel magic once a day.

STATISTICS:

Damage:  1D8
Damage type:  slashing

Special:  Miscast Magic affects victim on each successful hit
Miscast Magic:	Any spellcasting creature that is affected by this spell has its casting ability severely disabled.  When the creature attempts to cast a spell it has an 80% chance of failure.  Creatures can save vs spells to avoid the affect, but do so at -2. 

Weight: 6
Speed Factor: 7
Proficiency Type: Axe
Type:  1-handed
Requires: 10 Strength
Not Usable By:
Druid
Cleric
Mage 
Thief~ 


@1032186 = ~Defender of Easthaven +3~ 


@1032187 = ~Defender of Easthaven +3
This flail was created a century ago to commerate the defeat of the demon Balhifet.  It was meant to always remain within the town of Easthaven to remind the people of the great evil that had been barely defeated.	

STATISTICS:

Equipped Abilities:
+1 AC bonus
+20% resistance to slashing, piercing, and blunt damage
THACO:  +3 bonus
Damage:  1D6 + 4
Damage type:  crushing
Weight: 12
Speed Factor: 5
Proficiency Type: Flail/Morningstar
Type:  1-handed
Requires: 13 Strength
Not Usable By:
Druid
Mage 
Thief~


@1039461 = ~Blade of Roses, Long Sword +3
This blade possesses an unearthly splendor, and it is likely that Sune, the goddess of beauty and passion, had a hand in its creation.  The effect it has on the wielder is immediate, and more than once in its history has this sword has been the secret behind a lackluster soldier's sudden elevation at court.

STATISTICS:

Equipped Abilities: 
Charisma: +2 bonus
THACO:  +3 bonus
Damage:  1D8 + 3
Damage type:  slashing
Weight: 3
Speed Factor: 2
Proficiency Type: Long sword
Type:  1-handed
Requires: 6 Strength
Not Usable By:
Druid
Cleric
Mage~

I also included corrections for Defender of Easthaven, which I forgot about before. The name incorrectly claims the weapon is +2 and the description claims the weapon has +2 to THACO and damage, while a +3 flail should have (and does have) +3 and +4, respectively.

Link to comment

Do you plan to have any code compatible for foreign languages?

 

"Weight:" and "Speed factor:" together with some pattern matching as search and replace strings are not going to work for other languages.

 

In Level 1 NPC, there was something similar for updating class restrictions if you installed the part to change them. I proposed some pattern matching strings for French, as the mod anticipated for foreign languages and had set variables for pattern search and replace strings. Would you include such thing in the Fixpack?

 

Otherwise, I'll have to go back to Baldurdash or stick to v9. :)

Link to comment

The code I posted for generating updated descriptions wasn't intended to be run at install time. The intention was that someone would run it before the release of v10 and include the output in setup.tra. As such, there shouldn't be any incompatibility with the non-English games of players (at least not once setup.tra has been fully translated).

Link to comment

Thanks for clarification. I failed to figure out that there were two completely different parts in your code.

 

I believe some translators might like to use your code (third block) to "translate" the changes easily too. At least I would if I had to.

Link to comment
I believe some translators might like to use your code (third block) to "translate" the changes easily too. At least I would if I had to.

By all means.

I expect it is simply a matter of replacing "Weight" and "Speed Factor" with something that works for your language (and adding BACKUP, AUTHOR and BEGIN ~component name~).

Link to comment
I believe some translators might like to use your code (third block) to "translate" the changes easily too. At least I would if I had to.

By all means.

I expect it is simply a matter of replacing "Weight" and "Speed Factor" with something that works for your language (and adding BACKUP, AUTHOR and BEGIN ~component name~).

You're right about how easy it is to update the values.

 

But since all we'll get is a tra file to translate, including the modified texts in english (about 30 to 40), the initial work will be to locate where the corresponding description lies in the dialog.tlk, in order to recover it in the local language. Then we can apply the fix to weight or speed factor value.

If the corresponding location is not given in the english tra file, I think that using your code to generate the localized tra file as you're going to generate the english one would be a huge help, instead of browsing the whole dialog.tlk file for the descriptions.

 

Anyway, to each his own way of making it as easy as possible, I believe.

Link to comment

I'm with you on everything except:

 

Bruenor's axe--the damage is so far outside the range of regular damages I'd say we need to fix the damage. Otherwise it raises Bruenor's axe (only +3) to do nearly quadruple damage over plain axes; by contrast Ixil's Spike +6 does less then triple damage over a regular spear. Drizzt has a munchkin item for his weapon but it's not droppable, and the rest of the crew have reasonable weapons.

 

Staff of the Magi--this is treated as a +5 weapon pretty much everywhere, and I'd rather see the speed kept at 1 and the description updated to match. The original fix here was clearly wrong.

Link to comment

I just rechecked the changes made to the speed factors and also found myself nodding all the way, except for two things:

 

 

1. Cursed weapons (concerns sper03 and sw2h03 in Wisp's review)

 

There is a better, more logical way to determine whether to go with the item values or the description values here. In the entire game, there are only four cursed weapons, so this is not complicated at all.

 

blun09.itm: Kiel's Morningstar

- unenchanted morning stars have: 7

- enchantment is: +3

- item value is: 4

- description says: 4

 

sper03.itm: Backbiter

- unenchanted spears have: 6

- enchantment is: +3

- item value is: 3

- description says: 6

 

sw1h19.itm: The Vampire's Revenge

- unenchanted long swords have: 5

- enchantment is: +1

- item value is: 4

- description says: 4

 

sw2h03.itm: Berserking Sword

- unenchanted two-handed swords have: 10

- enchantment is: +3

- item value is: 7

- description says: 10

 

Hence, the speed factors of all cursed weapons actually comply perfectly with the respective enchantments, and it's just two of the descriptions that are wrong.

 

 

2. Weapons reaching speed factor 0

 

The reasonably consistent* exception is for highly enchanted weapons, which mostly have a speed of 1, even though s = b - e would have given them speed 0.

 

*At least if you squint, tilt your head and want it to be consistent.

 

We don't need to squint anymore. Again, I've done some research, this time across all weapons. The seemingly arbitrary behavior of having speed = 0 or speed = 1 is easily explained, once you recognize the simple and surprisingly obvious pattern:

 

One-handed weapons max out at speed = 0.

Two-handed weapons are limited to speed = 1.

 

This is likely to ensure that "at the end of the flagpole", where highly enchanted weapons of all kinds would all end up at the same speed = 0, at least one general distinction is upheld, with the lighter one-handed weapons going before the bulkier two-handed weapons in combat.

 

So, Wisp was led astray here. In practice, the power/enchantment of a weapon doesn't have anything to do with the matter. You can go through the items and will find that all two-handed weapons are consistently limited to speed = 1, regardless of enchantment. This is the reason why

 

- Ixil's Spike +6,

- the Staff of the Magi +5 and every other staff +4 or better,

- and the light crossbow Firetooth +5

 

all indeed have speed = 1, and correctly so, even when the s = b - e formula predicts speed = 0. If you go back to sper12.itm and staf11.itm now, you realize there never was any controversy. The given, vanilla speed values are fine, and it's the descriptions that need to be corrected, not the other way around.

 

Luckily, the Fixpack's current (v9.22) treatment of sper12.itm and staf11.itm is correct by accident. However, in terms of implementation:

  • SPER12 must be removed from the speed fix array, because currently the speed gets set ... to what it already is by default! :D SPER12 shouldn't appear there at all.
  • The description for the Staff of the Magi that the Fixpack applies still says speed = 3 due to Wisp's review, this must be 1. The item value is already back to vanilla thanks to CamDawg's remark above, but the "// STAF11 => 3" also better not appear at all in that array.

 

With respect to one-handed weapons, we have one case where the new insights lead to a different conclusion than in Wisp's review: The default speed = 0 for Spectral Brand +5 is actually correct. We need to change the erroneous description, and take the setting of speed = 1 out of the Fixpack code.

Link to comment

Archived

This topic is now archived and is closed to further replies.

×
×
  • Create New...