Modifying a weapons damage with DECORATE

Ask about ACS, DECORATE, ZScript, or any other scripting questions here!

Moderator: GZDoom Developers

Forum rules
Before asking on how to use a ZDoom feature, read the ZDoom wiki first. If you still don't understand how to use a feature, then ask here.

Please bear in mind that the people helping you do not automatically know how much you know. You may be asked to upload your project file to look at. Don't be afraid to ask questions about what things mean, but also please be patient with the people trying to help you. (And helpers, please be patient with the person you're trying to help!)
ichxg0
Posts: 27
Joined: Mon Nov 18, 2024 3:08 pm

Modifying a weapons damage with DECORATE

Post by ichxg0 »

Sorry for yet another question... I did check the wiki - This seems like it should be pretty straightforward, but I don't see much related to weapons and DECORATE on the there, it's all Zscript. Which is fine for me too, as long as it's somewhat basic (ie: copy and pasting code.) But even under Zscript in all the actor/class properties I don't see anything related to damage... It's mostly inventory related stuff or sfx etc.

So.. How would I go about increasing damage output? Is it definable with actors?

EDIT:
Alright I found this:
Damage (expression)

For a projectile defines the damage it inflicts upon impact. The formula is random(1,8) * damage, or random(1,4) * damage if the STRIFEDAMAGE flag is set.
This also defines the damage for actors which attack like the Lost Soul. The formula for this is random(1,8) * damage.
damage is also used to define how many bullets are fired by the generic hitscan attack function A_BulletAttack.
But I'm still a little lost. does this mean where they say "damage" it's up to you to assign the amount? Or is it set to a static amount within GZDoom? Also, it says it's used to define # of bullets in a hit scan attack, but how? Is it 1 = 1?

I'm also not sure where to put the formula in decorate even if I understood it; Do you just create an actor and put it underneath?

EDIT: Nevermind, I guess you find it in the "states" section. Does this mean to increase damage I will have to redefine each state of an attack manually? Once I figure out what the numbers mean anyway
ichxg0
Posts: 27
Joined: Mon Nov 18, 2024 3:08 pm

Re: Modifying a weapons damage with DECORATE

Post by ichxg0 »

Going to leave this in a separate comment because the first one is getting confusing. Maybe it would be easier to show the exact code I'm working with; this is the ZScript entry for the heretic starting weapon:

Code: Select all

class GoldWand : HereticWeapon
{
	Default
	{
		+BLOODSPLATTER
		Weapon.SelectionOrder 2000;
		Weapon.AmmoGive 25;
		Weapon.AmmoUse 1;
		Weapon.AmmoType "GoldWandAmmo";
		Weapon.SisterWeapon "GoldWandPowered";
		Weapon.YAdjust 5;
		Inventory.PickupMessage "$TXT_WPNGOLDWAND";
		Obituary "$OB_MPGOLDWAND";
		Tag "$TAG_GOLDWAND";
	}

	States
	{
	Spawn:
		GWAN A -1;
		Stop;
	Ready:
		GWND A 1 A_WeaponReady;
		Loop;
	Deselect:
		GWND A 1 A_Lower;
		Loop;
	Select:
		GWND A 1 A_Raise;
		Loop;
	Fire:
		GWND B 3;
		GWND C 5 A_FireGoldWandPL1;
		GWND D 3;
		GWND D 0 A_ReFire;
		Goto Ready;
	}
	

	//----------------------------------------------------------------------------
	//
	// PROC A_FireGoldWandPL1
	//
	//----------------------------------------------------------------------------

	action void A_FireGoldWandPL1 ()
	{
		if (player == null)
		{
			return;
		}

		Weapon weapon = player.ReadyWeapon;
		if (weapon != null)
		{
			if (!weapon.DepleteAmmo (weapon.bAltFire))
				return;
		}
		double pitch = BulletSlope();
		int damage = random[FireGoldWand](7, 14);
		double ang = angle;
		if (player.refire)
		{
			ang += Random2[FireGoldWand]() * (5.625 / 256);

			if (GetCVar ("vertspread") && !sv_novertspread)
			{
				pitch += Random2[FireGoldWand]() * (3.549 / 256);
			}
		}
		LineAttack(ang, PLAYERMISSILERANGE, pitch, damage, 'Hitscan', "GoldWandPuff1");
		A_StartSound("weapons/wandhit", CHAN_WEAPON);
	}
	
}
Now I see where they define "A_FireGoldWandPL1, and I see the int damage formula; Two questions:

1. What do the two numbers (7, 14) mean

2. How would I write this up in decorate as a patch to load? Since this is all from the GZDoom pk3 I don't want to directly modify it..
User avatar
Player701
 
 
Posts: 1694
Joined: Wed May 13, 2009 3:15 am
Graphics Processor: nVidia with Vulkan support

Re: Modifying a weapons damage with DECORATE

Post by Player701 »

ichxg0 wrote: Sun Dec 01, 2024 12:32 pm Does this mean to increase damage I will have to redefine each state of an attack manually?
Unfortunately, yes, because for hitscan weapons the damage usually depends on the function that gets called from the attack state sequence. And in this particular case, the damage is also hardcoded in the function itself:
ichxg0 wrote: Sun Dec 01, 2024 2:45 pm What do the two numbers (7, 14) mean
Yes, here it is. In context, which is random[FireGoldWand](7, 14), it represents a uniformly distributed random integer value from 7 to 14 inclusive. Note that the wiki claims the damage is "1d8+6", but it actually means the same thing: "d8" is a reference to an eight-sided die commonly used in tabletop RPGs - by rolling it, you get a random value from 1 to 8 inclusive, then you add 6... and there is your (7, 14).
ichxg0 wrote: Sun Dec 01, 2024 2:45 pm How would I write this up in decorate as a patch to load? Since this is all from the GZDoom pk3 I don't want to directly modify it..
Since A_FireGoldWandPL1 does not accept any parameters, and you also cannot write custom functions In DECORATE, you'll have to resort to A_FireBullets instead. The article on A_FireGoldWandPL1 provides a reference point to start from:
ZDoom Wiki wrote:The behavior of this function can be recreated by using A_FireBullets:

Code: Select all

A_FireBullets(random(5, 6), 0, 1, random(2, 3), "GoldWandPuff1")
I have my doubts that the behavior recreated is exact, at least in regard to damage - by default, the damage parameter passed to A_FireBullets is multiplied by random(1, 3); the damage value used here is random(2, 3), which means the final damage will be from 2 to 9 inclusive, and also not uniformly distributed - definitely not the same as in the original function. Better just turn off that extra randomization with the FBF_NORANDOM flag and pass the correct damage range directly. Also, you will need to define an AttackSound for your weapon because A_FireGoldWandPL1 has it hardcoded.

Here's the final code:

Code: Select all

actor MyWand : GoldWand
{
    AttackSound "weapons/wandhit"

    States
    {
        Fire:
            GWND B 3 
            GWND C 5 A_FireBullets(random(5, 6), 0, 1, random(7, 14), "GoldWandPuff1", FBF_NORANDOM|FBF_USEAMMO)
            GWND D 3
            GWND D 0 A_ReFire
            Goto Ready
    }
}
Now you can adjust the damage to your liking by changing the fourth argument passed to A_FireBullets - in the above example it is random(7, 14), which corresponds to the original damage formula. You can even get rid of random and use a fixed value instead.
ichxg0
Posts: 27
Joined: Mon Nov 18, 2024 3:08 pm

Re: Modifying a weapons damage with DECORATE

Post by ichxg0 »

Whoa, thank you for the super thought out answer! So I think I'm with you, mostly, but one thing that still kinda throws me for a loop is the long strings of numbers I see in expressions; I understand the random(7, 14) but it starts with

Code: Select all

GWND C 5 A_FireBullets(random(5, 6), 0, 1,
where do those numbers come from; it's all well and good now that I recognize the 7,14 from the gold wand formula, but in general, how would I know which range of numbers to change? The "random(5, 6)" and the "0, 1," what are those numbers doing? I don't understand their role in the formula.
User avatar
Player701
 
 
Posts: 1694
Joined: Wed May 13, 2009 3:15 am
Graphics Processor: nVidia with Vulkan support

Re: Modifying a weapons damage with DECORATE

Post by Player701 »

ichxg0 wrote: Thu Dec 05, 2024 5:55 am The "random(5, 6)" and the "0, 1," what are those numbers doing? I don't understand their role in the formula.
The meaning of the arguments is explained in the wiki article:
ZDoom Wiki wrote:action void A_FireBullets(double spread_xy, double spread_z, int numbullets, int damageperbullet, ...)
The first one is the horizontal spread: while it is already randomized, the value used here is random(5, 6), which means either 5 or 6 with a 50% chance. The final spread is thus going to be a random value in the range of either -5 to 5, or -6 to 6, with a 50% chance of each. Not sure if this is an unnecessary complication or whether it is actually needed: while it claims to replicate the behavior of A_FireGoldWandPL1, I cannot vouch for its accuracy as I wasn't the one who wrote the article on the latter - and we've already established that at least in terms of damage the proposed "replication" is not the same as the original.

The rest should be self-explanatory, really. Vertical spread is zero, and exactly one bulet is fired. Then we have the damage, which we have already discussed before.

I strongly recommend to read the wiki article thoroughly in case you have any further questions. Although you cannot trust it to be 100% accurate since it's written by humans, and all humans make mistakes, it could still be a very useful source of information at times.
ichxg0
Posts: 27
Joined: Mon Nov 18, 2024 3:08 pm

Re: Modifying a weapons damage with DECORATE

Post by ichxg0 »

Ahh, of course, it would be in the wiki. I think I just look in the wrong places.. Just need to dig a little deeper. It makes more sense now that I'm reading it... aha :geek:
User avatar
SPZ1
Posts: 367
Joined: Wed Aug 02, 2017 3:01 pm
Location: Illinois

Re: Modifying a weapons damage with DECORATE

Post by SPZ1 »

The way I've leveled up my weapons is simply by using an inventory item and checking for it in the fire sequence.

Return to “Scripting”