- Joined
- May 16, 2020
- Messages
- 660
It worked! This system is really useful - thanks!
(13 ratings)
function GetUnitBonus takes unit u, integer bonus_type returns real
-> Returns the specified bonus amount for the unit
-> Example: set amount = GetUnitBonus(GetTriggerUnit(), BONUS_AGILITY)
function SetUnitBonus takes unit u, integer bonus_type, real amount returns real
-> Set the specified bonus type to amount for the unit
-> Example: call SetUnitBonus(GetTriggerUnit(), BONUS_DAMAGE, 100)
function RemoveUnitBonus takes unit u, integer bonus_type returns nothing
-> Removes the Specified bonus type from unit
-> Example: call RemoveUnitBonus(GetTriggerUnit(), BONUS_AGILITY)
function AddUnitBonus takes unit u, integer bonus_type, real amount returns real
-> Add the specified amount for the specified bonus tyte for unit
-> Example: call AddUnitBonus(GetTriggerUnit(), BONUS_DAMAGE, 100)
function AddUnitBonusTimed takes unit u, integer bonus_type, real amount, real duration returns nothing
-> Add the specified amount for the specified bonus type for unit for a duration
-> Example: call AddUnitBonusTimed(GetTriggerUnit(), BONUS_ARMOR, 13, 10.5)
function LinkBonusToBuff takes unit u, integer bonus_type, real amount, integer buffId returns nothing
-> Links the bonus amount specified to a buff or ability. As long as the unit has the buff or
-> the ability represented by the parameter buffId the bonus is not removed.
-> Example: call LinkBonusToBuff(GetTriggerUnit(), BONUS_ARMOR, 10, 'B000')
function LinkBonusToItem takes unit u, integer bonus_type, real amount, item i returns nothing
-> Links the bonus amount specified to an item. As long as the unit has that item the bonus is not removed.
-> Note that it will work for items with the same id, because it takes as parameter the item object.
-> Example: call LinkBonusToItem(GetManipulatingUnit(), BONUS_ARMOR, 10, GetManipulatedItem())
function UnitCopyBonuses takes unit source, unit target returns nothing
-> Copy the source unit bonuses using the Add functionality to the target unit
-> Example: call UnitCopyBonuses(GetTriggerUnit(), GetSummonedUnit())
function UnitMirrorBonuses takes unit source, unit target returns nothing
-> Copy the source unit bonuses using the Set functionality to the target unit
-> Example: call UnitMirrorBonuses(GetTriggerUnit(), GetSummonedUnit())
function RegisterBonusEvent takes code c returns nothing
-> Register code to run when any unit bonus is modified
-> Example: RegisterBonusEvent(function YourFunction)
function RegisterBonusTypeEvent takes integer bonus, code c returns nothing
-> Register code to run when a specific unit bonus is modified
-> Example: RegisterBonusTypeEvent(BONUS_DAMAGE, function YourFunction)
function GetBonusUnit takes nothing returns unit
-> Call this function to get the bonus event unit
function GetBonusType takes nothing returns integer
-> Call this function to get the bonus event type
function SetBonusType takes integer bonus returns nothing
-> Call this function to set the bonus event type
function GetBonusAmount takes nothing returns real
-> Call this function to get the bonus event amount
function SetBonusAmount takes real amount returns nothing
-> Call this function to set the bonus event amount
function GetUnitBonus(unit, type)
-> Returns the specified bonus amount for the unit
-> Example: set amount = GetUnitBonus(GetTriggerUnit(), BONUS_AGILITY)
function SetUnitBonus(unit, type, value)
-> Set the specified bonus type to amount for the unit
-> Example: call SetUnitBonus(GetTriggerUnit(), BONUS_DAMAGE, 100)
function RemoveUnitBonus(unit, type)
-> Removes the Specified bonus type from unit
-> Example: call RemoveUnitBonus(GetTriggerUnit(), BONUS_AGILITY)
function AddUnitBonus(unit, type, value)
-> Add the specified amount for the specified bonus tyte for unit
-> Example: call AddUnitBonus(GetTriggerUnit(), BONUS_DAMAGE, 100)
function AddUnitBonusTimed(unit, type, amount, duration)
-> Add the specified amount for the specified bonus type for unit for a duration
-> Example: call AddUnitBonusTimed(GetTriggerUnit(), BONUS_ARMOR, 13, 10.5)
function LinkBonusToBuff(unit, type, amount, buff)
-> Links the bonus amount specified to a buff or ability. As long as the unit has the buff or
-> the ability represented by the parameter buffId the bonus is not removed.
-> Example: call LinkBonusToBuff(GetTriggerUnit(), BONUS_ARMOR, 10, 'B000')
function LinkBonusToItem(unit, type, amount, item)
-> Links the bonus amount specified to an item. As long as the unit has that item the bonus is not removed.
-> Note that it will work for items with the same id, because it takes as parameter the item object.
-> Example: call LinkBonusToItem(GetManipulatingUnit(), BONUS_ARMOR, 10, GetManipulatedItem())
function UnitCopyBonuses(source, target)
-> Copy the source unit bonuses using the Add functionality to the target unit
-> Example: call UnitCopyBonuses(GetTriggerUnit(), GetSummonedUnit())
function UnitMirrorBonuses(source, target)
-> Copy the source unit bonuses using the Set functionality to the target unit
-> Example: call UnitMirrorBonuses(GetTriggerUnit(), GetSummonedUnit())
function RegisterBonusEvent(code)
-> Register code to run when any unit bonus is modified
-> Example: RegisterBonusEvent(function() YourFunctionc end)
function RegisterBonusTypeEvent(type, code)
-> Register code to run when a specific unit bonus is modified
-> Example: RegisterBonusTypeEvent(BONUS_DAMAGE, function() YourFunction end)
function GetBonusUnit()
-> Call this function to get the bonus event unit
function GetBonusType()
-> Call this function to get the bonus event type
function SetBonusType(type)
-> Call this function to set the bonus event type
function GetBonusAmount()
-> Call this function to get the bonus event amount
function SetBonusAmount(real)
-> Call this function to set the bonus event amount
function UnitCopyBonuses takes unit source, unit target returns nothing
function UnitMirrorBonuses takes unit source, unit target returns nothing
Hi Chopinski, there is an error with the non-expanded version in 1.9. It says "Syntax Error, unexpected: end of line?
Hi Chopinski, not sure if it's a bug or an error on my side, but the BONUS_SIGHT_RANGE does not reverse with "call RemoveUnitBonus".
See the second trigger. There it should restore the original sight radius, but it doesn't happen:
Dark Ascension
Events
Unit - A unit Starts the effect of an ability
Conditions
(Ability being cast) Equal to Dark Ascension
Actions
Set VariableSet DarkAscension_Caster = (Triggering unit)
Set VariableSet DarkAscension_DamageBonus = (50 x (Level of Dark Ascension for DarkAscension_Caster))
Set VariableSet DarkAscension_PlayerGroup = (All enemies of (Owner of DarkAscension_Caster).)
Custom script: set udg_DarkAscension_GroupEnemies = CreateGroup()
-------- ADD DAMAGE --------
Custom script: call SetUnitBonus(udg_DarkAscension_Caster, BONUS_DAMAGE, udg_DarkAscension_DamageBonus)
-------- DENY VISION --------
Player Group - Make DarkAscension_PlayerGroup treat DarkAscension_PlayerGroup as an Ally
-------- REDUCE VISION --------
Player Group - Pick every player in DarkAscension_PlayerGroup and do (Actions)
Loop - Actions
Set VariableSet DarkAscension_GroupEnemies = (Units owned by (Picked player).)
Unit Group - Pick every unit in DarkAscension_GroupEnemies and do (Actions)
Loop - Actions
Set VariableSet DarkAscension_TempUnit = (Picked unit)
If (All Conditions are True) then do (Then Actions) else do (Else Actions)
If - Conditions
(DarkAscension_TempUnit is alive) Equal to True
(DarkAscension_TempUnit is A structure) Equal to False
Then - Actions
Set VariableSet DarkAscension_SightReduction = -250
Custom script: call SetUnitBonus(udg_DarkAscension_TempUnit, BONUS_SIGHT_RANGE, udg_DarkAscension_SightReduction)
Else - Actions
If (All Conditions are True) then do (Then Actions) else do (Else Actions)
If - Conditions
(Dark Ascension Timer <gen> is on) Equal to False
Then - Actions
Trigger - Turn on Dark Ascension Timer <gen>
Countdown Timer - Start DarkAscension_Timer as a One-shot timer that will expire in 10.00 seconds
Else - Actions
Dark Ascension Timer
Events
Time - DarkAscension_Timer expires
Conditions
Actions
-------- RESET DAMAGE --------
Custom script: call RemoveUnitBonus(udg_DarkAscension_Caster, BONUS_DAMAGE)
-------- RESTORE VISION --------
Player Group - Make DarkAscension_PlayerGroup treat DarkAscension_PlayerGroup as an Ally with shared vision
Unit Group - Pick every unit in DarkAscension_GroupEnemies and do (Actions)
Loop - Actions
Set VariableSet DarkAscension_TempUnit = (Picked unit)
Custom script: call RemoveUnitBonus(udg_DarkAscension_TempUnit, BONUS_SIGHT_RANGE)
-------- --------
Custom script: call DestroyGroup (udg_DarkAscension_GroupEnemies)
Countdown Timer - Pause DarkAscension_Timer
Game - Display to (All players) the text: Dark Ascension OFF
Trigger - Turn off (This trigger)
Can you post the object data for the latest version?
He already did this... New Bonus v2.0Can you post the object data for the latest version?
rightHe already did this... New Bonus v2.0
It says for v1.8, no object changes were made after that based on the changelog. right @chopinski ?
Hi Chopinski, not sure if it's a bug or an error on my side, but the BONUS_SIGHT_RANGE does not reverse with "call RemoveUnitBonus".
See the second trigger. There it should restore the original sight radius, but it doesn't happen:
Dark Ascension
Events
Unit - A unit Starts the effect of an ability
Conditions
(Ability being cast) Equal to Dark Ascension
Actions
Set VariableSet DarkAscension_Caster = (Triggering unit)
Set VariableSet DarkAscension_DamageBonus = (50 x (Level of Dark Ascension for DarkAscension_Caster))
Set VariableSet DarkAscension_PlayerGroup = (All enemies of (Owner of DarkAscension_Caster).)
Custom script: set udg_DarkAscension_GroupEnemies = CreateGroup()
-------- ADD DAMAGE --------
Custom script: call SetUnitBonus(udg_DarkAscension_Caster, BONUS_DAMAGE, udg_DarkAscension_DamageBonus)
-------- DENY VISION --------
Player Group - Make DarkAscension_PlayerGroup treat DarkAscension_PlayerGroup as an Ally
-------- REDUCE VISION --------
Player Group - Pick every player in DarkAscension_PlayerGroup and do (Actions)
Loop - Actions
Set VariableSet DarkAscension_GroupEnemies = (Units owned by (Picked player).)
Unit Group - Pick every unit in DarkAscension_GroupEnemies and do (Actions)
Loop - Actions
Set VariableSet DarkAscension_TempUnit = (Picked unit)
If (All Conditions are True) then do (Then Actions) else do (Else Actions)
If - Conditions
(DarkAscension_TempUnit is alive) Equal to True
(DarkAscension_TempUnit is A structure) Equal to False
Then - Actions
Set VariableSet DarkAscension_SightReduction = -250
Custom script: call SetUnitBonus(udg_DarkAscension_TempUnit, BONUS_SIGHT_RANGE, udg_DarkAscension_SightReduction)
Else - Actions
If (All Conditions are True) then do (Then Actions) else do (Else Actions)
If - Conditions
(Dark Ascension Timer <gen> is on) Equal to False
Then - Actions
Trigger - Turn on Dark Ascension Timer <gen>
Countdown Timer - Start DarkAscension_Timer as a One-shot timer that will expire in 10.00 seconds
Else - Actions
Dark Ascension Timer
Events
Time - DarkAscension_Timer expires
Conditions
Actions
-------- RESET DAMAGE --------
Custom script: call RemoveUnitBonus(udg_DarkAscension_Caster, BONUS_DAMAGE)
-------- RESTORE VISION --------
Player Group - Make DarkAscension_PlayerGroup treat DarkAscension_PlayerGroup as an Ally with shared vision
Unit Group - Pick every unit in DarkAscension_GroupEnemies and do (Actions)
Loop - Actions
Set VariableSet DarkAscension_TempUnit = (Picked unit)
Custom script: call RemoveUnitBonus(udg_DarkAscension_TempUnit, BONUS_SIGHT_RANGE)
-------- --------
Custom script: call DestroyGroup (udg_DarkAscension_GroupEnemies)
Countdown Timer - Pause DarkAscension_Timer
Game - Display to (All players) the text: Dark Ascension OFF
Trigger - Turn off (This trigger)
Mmm was just able to test it. A few things:
- You were right, for some reason not the right units were selected to remove the sight bonus. However:
- When I select the right units, the bonus removal still does not work. I'm using now:
and then
call AddUnitBonus(udg...
FYI: In your test map the Sight Range bonus does not work either (+100 does nothing, and removing does nothing)
call RemoveUnitBonus(udg...
It does work, i will send a GIF showing it working once i have a little more time. Sight Range takes 1 or 2 seconds to take effect and it works in tiles apparently, so if you bonus is to small it might not produce a visible change.
Hey man! Epic work in this great system! I got a request tho. So in my map, I want to make a crafting system, which will produce the same item-type but with different qualities, so different stats. I wondered if you could make possible that i link stats to a specific item, not item-type, and link it to the item not the unit, so as to work automatically when changing the unit carrying it
Hi Chopinski, you were right about the sight range. In your test map it does work. I didn't realize the change because 100 is too small of a change. But if I go down to -1400 and "null" the bonus, sight is restored indeed.
But in my map I'm still unable to restore sight for some reason, even though I pick the same units and use:
Can you please check the trigger? I really don't know what else could be wrong...
Custom script: call RemoveUnitBonus(udg_DarkAscension_TempUnit, BONUS_SIGHT_RANGE)
Dark Ascension
Events
Unit - A unit Starts the effect of an ability
Conditions
(Ability being cast) Equal to Dark Ascension
Actions
Game - Display to (All players) the text: Dark Ascension ON
Set VariableSet DarkAscension_Caster = (Triggering unit)
Set VariableSet DarkAscension_DamageBonus = (50 x (Level of Dark Ascension for DarkAscension_Caster))
Set VariableSet DarkAscension_GroupPlayer = (All enemies of (Owner of DarkAscension_Caster).)
Set VariableSet DarkAscension_SightReduction = -350
Custom script: set udg_DarkAscension_GroupTemp = CreateGroup()
-------- ADD DAMAGE --------
Custom script: call SetUnitBonus(udg_DarkAscension_Caster, BONUS_DAMAGE, udg_DarkAscension_DamageBonus)
-------- DENY VISION --------
Player Group - Make DarkAscension_GroupPlayer treat DarkAscension_GroupPlayer as an Ally
-------- REDUCE VISION --------
Player Group - Pick every player in DarkAscension_GroupPlayer and do (Actions)
Loop - Actions
Set VariableSet DarkAscension_GroupTemp = (Units owned by (Picked player).)
Custom script: set bj_wantDestroyGroup = true
Unit Group - Pick every unit in DarkAscension_GroupTemp and do (Actions)
Loop - Actions
Set VariableSet DarkAscension_TempUnit = (Picked unit)
If (All Conditions are True) then do (Then Actions) else do (Else Actions)
If - Conditions
(DarkAscension_TempUnit is alive) Equal to True
(DarkAscension_TempUnit is A structure) Equal to False
(Owner of DarkAscension_TempUnit) Not equal to Neutral Hostile
Then - Actions
Custom script: call AddUnitBonus(udg_DarkAscension_TempUnit, BONUS_SIGHT_RANGE, udg_DarkAscension_SightReduction)
Custom script: call AddUnitBonus(udg_DarkAscension_TempUnit, BONUS_DAMAGE, udg_DarkAscension_DamageBonus)
Unit Group - Add DarkAscension_TempUnit to DarkAscension_GroupVision
Else - Actions
Game - Display to (All players) the text: (String((Number of units in DarkAscension_GroupVision)))
If (All Conditions are True) then do (Then Actions) else do (Else Actions)
If - Conditions
(Dark Ascension Timer <gen> is on) Equal to False
Then - Actions
Trigger - Turn on Dark Ascension Timer <gen>
Countdown Timer - Start DarkAscension_Timer as a One-shot timer that will expire in 10.00 seconds
Else - Actions
Dark Ascension Timer
Events
Time - DarkAscension_Timer expires
Conditions
Actions
-------- RESET DAMAGE --------
Custom script: call RemoveUnitBonus(udg_DarkAscension_Caster, BONUS_DAMAGE)
-------- RESTORE SHARED VISION --------
Player Group - Make DarkAscension_GroupPlayer treat DarkAscension_GroupPlayer as an Ally with shared vision
Custom script: call DestroyForce (udg_DarkAscension_GroupPlayer)
-------- RESTORE VISION RANGE --------
Game - Display to (All players) the text: (String((Number of units in DarkAscension_GroupVision)))
Unit Group - Pick every unit in DarkAscension_GroupVision and do (Actions)
Loop - Actions
Set VariableSet DarkAscension_TempUnit = (Picked unit)
Custom script: call RemoveUnitBonus(udg_DarkAscension_TempUnit, BONUS_SIGHT_RANGE)
Custom script: call RemoveUnitBonus(udg_DarkAscension_TempUnit, BONUS_DAMAGE)
Custom script: call DestroyGroup (udg_DarkAscension_GroupVision)
-------- --------
Countdown Timer - Pause DarkAscension_Timer
Game - Display to (All players) the text: Dark Ascension OFF
Trigger - Turn off (This trigger)
Sure, this is what it should do:
- The ability is based on Moonstone ability to summon an artificial night
- Upon cast, the caster gets 50*ability level bonus damage for the duration of the ability
- Upon cast, all enemy units lose the shared vision gained from allies (= you can only see your own units) and have reduced sight radius of -350 for the duration of the ability
Ok, Do you wish for the debuff to be dispellable?
For the caster? no, should not be dispellable. If somehow possible, he should only retain the bonus damage as long as the the artificial night remains though.
For the units affected by vision impairment I wouldn't add a debuff. Probably adds too much lag when >100 units get added a debuff at the same time...
Wait, so.. if i'm still using 1.31.1 i need to copy paste anything and create the abilities fron here? Since the map can't be opened because it's fron 1.32?
Oh yeah sorry i just realized that, thanks.You can use the object data i provided and import it to a map and copy the codes from this thread. You dont need to copy ability by ability if you do this.
So.. i found a weird bug interaction with this system.
I wanna increase the armor of a unit that increase by some percentage of mana if they have a spesific buff by using the system api and another one that increase them by some percentage of strength using warcraft api. Like this :
Mana to Armor
Mana to Armor
Events
Time - Every 0.50 seconds of game time
Conditions
Actions
Set ArmorManaTempGroup = (Units in (Playable map area) matching ((Evaluate Condition <gen> conditions) Equal to True))
Unit Group - Pick every unit in ArmorManaTempGroup and do (Actions)
Loop - Actions
Set ArmorManaUnit = (Picked unit)
Set ArmorManaRealMana = (0.02 x (Max mana of ArmorManaUnit))
Custom script: call SetUnitBonus(udg_ArmorManaUnit, BONUS_ARMOR, R2I(udg_ArmorManaRealMana))
Custom script: call DestroyGroup(udg_ArmorManaTempGroup)
Str to armor
Strength to Armor
Events
Time - Every 0.50 seconds of game time
Conditions
Actions
Set ArmorSTRTempGroup = (Units in (Playable map area) matching (((Matching unit) is A Hero) Equal to True))
Unit Group - Pick every unit in ArmorSTRTempGroup and do (Actions)
Loop - Actions
Set ArmorSTRReal = (0.30 x (Real((Strength of (Picked unit) (Include bonuses)))))
Unit - Set Armor of (Picked unit) to ArmorSTRReal
Custom script: call DestroyGroup(udg_ArmorSTRTempGroup)
Each of them are working fine.
Except if you turn on both of them.
My unit's armor got decreased instead by the total amount of it gets from mana to armor value.
I really confused now. What am i do wrong here?
Here also the test map
It's not a bug. Your problem has nothing to do with the system but with how the SetArmor blizzard function works. That function takes in consideration the bonus (green value) armor amount, so when you set the armor amount of a unit that has a bonus value it compensates the White value to match the total amount, that's why you see a negative value when you learn your ability. To make it work how you want you have to make a few changes that you can see below. Basically you have to add to the amount that will be passed to the blizzard function the bonus amount that was set by this system. It's a weird behavior but that's how it works, that function does not take in consideration the white value only. I also fused the 2 triggers into one, so it's a bit more efficient and easier to read. Also on a side note I recommend you use the AddUnitBonusTimed function from my system instead of the SetUnitBonus. SetUnitBonus will overwrite any value previously set, so if at some point in some other trigger you change the unit armor the Set function will make that change almost impossible to recover.
Armor
Events
Time - Every 0.50 seconds of game time
Conditions
Actions
Set VariableSet Group = (Units in (Playable map area) matching (((Matching unit) is A Hero) Equal to True))
Unit Group - Pick every unit in Group and do (Actions)
Loop - Actions
Set VariableSet Unit = (Picked unit)
If (All Conditions are True) then do (Then Actions) else do (Else Actions)
If - Conditions
(Unit has buff Brilliance Aura) Equal to True
Then - Actions
Set VariableSet ManaArmor = (0.02 x (Max mana of Unit))
Set VariableSet Armor = ((0.30 x (Real((Strength of Unit (Include bonuses))))) + ManaArmor)
Unit - Set Armor of Unit to Armor
Custom script: call AddUnitBonusTimed(udg_Unit, BONUS_ARMOR, udg_ManaArmor, 0.501)
Else - Actions
Set VariableSet Armor = (0.30 x (Real((Strength of Unit (Include bonuses)))))
Unit - Set Armor of Unit to Armor
Custom script: call DestroyGroup(udg_Group)
Just FYI: You can edit the demon hunter's evasion ability's evasion chance with blzsetabilityreallevelfield thus you don't need to use damage interface to make evasion. Also implementing evasion this way prevents secondary effects from occurring when an attack misses where as damage engine or damage interface your unit will still get stunned from bash for example even if the damage is changed to 0.
edit: Could we have a demon hunter evasion based evasion chance bonus in the next new bonus release please?
private constant integer CRITICAL_STRIKE_ABILITY = 'Z00C'
private constant integer EVASION_ABILITY = 'Z00D'
private constant integer LIFE_STEAL_ABILITY = 'Z00E'
Yeah, it's because I CTRL + C, CTRL +V the configuration block block and only changed the types for the extended version. It's there but does nothing. Not worth the effort of reposting a new version since it's inoffensive.Your Extended version is not using 3 globals you declared (probably because of the non-extended version)
JASS:private constant integer CRITICAL_STRIKE_ABILITY = 'Z00C' private constant integer EVASION_ABILITY = 'Z00D' private constant integer LIFE_STEAL_ABILITY = 'Z00E'
No, it manipulates the ability directly and that's how it stacks.I noticed that magic resistance stacks additively (which is already a big improvement over the default WC3 behaviour) --> 20% magic resistance + 10% = 30%
Is it possible to make it multiplicative? --> (1- (1-0.2) * (1-0.1)) = 28%
No, it manipulates the ability directly and that's how it stacks.
You can create your own way of manipulating this bonus specifically, but that's a job for a separate system.OK, but can the ability manipulated in a way which calculates multiplicatively, and not additively?
Or maybe have a setting where you can choose how the stats should behave when adding up? (this would be useful for items specifically)
static method AddUnitBonus takes unit u, integer bonus_type, integer amount returns integer
local integer current_amount = GetUnitBonus(u, bonus_type)
// Added in version 1.5 to avoid overflow/underflow of the field value
if amount > 0 and current_amount > 2147483647 - amount then //Overflow
set amount = 2147483647 - current_amount
elseif amount < 0 and current_amount < -2147483648 - amount then //Underflow
set amount = -2147483648 - current_amount
endif
call SetUnitBonus(u, bonus_type, (current_amount + amount))
There's more to it than that. Take a look at my Cooldown Reduction system. It does basically what you want but for cooldown reduction. I don't recommend messing with the system code, you can create some unwanted behavior for other stuff. You will also need to know jass a little bit.Alright, thanks. Just some pointers: I guess this is the area which I have to adjust, right? (current_amount + amount):
JASS:static method AddUnitBonus takes unit u, integer bonus_type, integer amount returns integer local integer current_amount = GetUnitBonus(u, bonus_type) // Added in version 1.5 to avoid overflow/underflow of the field value if amount > 0 and current_amount > 2147483647 - amount then //Overflow set amount = 2147483647 - current_amount elseif amount < 0 and current_amount < -2147483648 - amount then //Underflow set amount = -2147483648 - current_amount endif call SetUnitBonus(u, bonus_type, (current_amount + amount))
GetUnitBonus returns -1 when an invalid bonus type is passed to the function, so check if you are writing the bonus type correctly. Check if the abilities match with the codes in the configuration. Check if you are passing the correct unit as well. I tested in the test map and the system manage to get the bonus attack speed fine so you either doing something wrong or you imported something incorrectly. I tested it in the latest version of the system in both vJASS and Lua.I'm having a problem with "GetUnitBonus". I can correctly grab the current BONUS_DAMAGE of a hero, but not BONUS_ATTACK_SPEED.
In the trigger below, the "Omnislash_AttackSpeed" (a Real variable) is always -1.000 in-game, even though I pick up several items which increase BONUS_ATTACK_SPEED.
Omnislash
Events
Unit - A unit Starts the effect of an ability
Conditions
(Ability being cast) Equal to Omnislash
Actions
Set VariableSet Omnislash_Index = (Omnislash_Index + 1)
Set VariableSet Omnislash_Caster[Omnislash_Index] = (Triggering unit)
Set VariableSet Omnislash_Target = (Target unit of ability being cast)
Set VariableSet Omnislash_Counter[Omnislash_Index] = 0
Set VariableSet Omnislash_CounterMax[Omnislash_Index] = (55 + (5 x (Level of Omnislash for Omnislash_Caster[Omnislash_Index])))
Set VariableSet Omnislash_CounterReal[Omnislash_Index] = 0.00
-------- --------
Custom script: set udg_Omnislash_AttackSpeed = GetUnitBonus(udg_Omnislash_Caster[udg_Omnislash_Index], BONUS_ATTACK_SPEED)
Game - Display to (All players) the text: (String(Omnislash_AttackSpeed))
-------- --------
Set VariableSet Omnislash_CounterRealMax[Omnislash_Index] = ((((Unit: (Triggering unit)'s Weapon Real Field: Attack Base Cooldown ('ua1c') at Index:0) x 100.00) / (100.00 + (Real((Unit: (Triggering unit)'s Integer Field: Agility (with Bonus) ('uagb')))))) / 1.50)
Game - Display to (All players) the text: (String(Omnislash_CounterRealMax[Omnislash_Index]))
Set VariableSet Omnislash_DamageBonus[Omnislash_Index] = (15 + (15 x (Level of Omnislash for Omnislash_Caster[Omnislash_Index])))
Set VariableSet Omnislash_Boolean[Omnislash_Index] = True
Special Effect - Create a special effect attached to the weapon of Omnislash_Caster[Omnislash_Index] using Abilities\Weapons\PhoenixMissile\Phoenix_Missile.mdl
Set VariableSet Omnislash_SFX[Omnislash_Index] = (Last created special effect)
-------- --------
Unit - Pause Omnislash_Caster[Omnislash_Index]
Unit - Make Omnislash_Caster[Omnislash_Index] Invulnerable
Animation - Change Omnislash_Caster[Omnislash_Index]'s vertex coloring to (40.00%, 40.00%, 40.00%) with 40.00% transparency
Animation - Change Omnislash_Caster[Omnislash_Index]'s animation speed to 200.00% of its original speed
-------- --------
Set VariableSet Omnislash_Point[1] = (Position of Omnislash_Target)
Set VariableSet Omnislash_Point[2] = (Omnislash_Point[1] offset by 50.00 towards (Random angle) degrees.)
Unit - Move Omnislash_Caster[Omnislash_Index] instantly to Omnislash_Point[2]
Unit - Make Omnislash_Caster[Omnislash_Index] face Omnislash_Point[1] over 0.00 seconds
-------- --------
Custom script: set udg_Omnislash_AttackDamage = GetUnitBonus(udg_Omnislash_Caster[udg_Omnislash_Index], BONUS_DAMAGE)
Game - Display to (All players) the text: (String(Omnislash_AttackDamage))
Set VariableSet Omnislash_Damage = (((Base Damage of Omnislash_Caster[Omnislash_Index] for weapon index 0) + (Omnislash_AttackDamage + Omnislash_DamageBonus[Omnislash_Index])) + (Random integer number between (Dice Number of Omnislash_Caster[Omnislash_Index] for weapon index 0) and (Dice Sides
Unit - Cause Omnislash_Caster[Omnislash_Index] to damage Omnislash_Target, dealing (Real(Omnislash_Damage)) damage of attack type Hero and damage type Normal
-------- --------
Animation - Play Omnislash_Caster[Omnislash_Index]'s attack animation
Special Effect - Create a special effect attached to the origin of Omnislash_Caster[Omnislash_Index] using Abilities\Spells\NightElf\Blink\BlinkCaster.mdl
Special Effect - Destroy (Last created special effect)
-------- --------
Custom script: call RemoveLocation(udg_Omnislash_Point[1])
Custom script: call RemoveLocation(udg_Omnislash_Point[2])
-------- --------
If (All Conditions are True) then do (Then Actions) else do (Else Actions)
If - Conditions
Omnislash_Index Equal to 1
Then - Actions
Countdown Timer - Start Omnislash_Timer as a Repeating timer that will expire in 0.05 seconds
Trigger - Turn on Omnislash Loop <gen>
Else - Actions
The items which I pick up also use your system, and correctly increase attack speed (I test this by attacking a dummy, and the hero does attack faster). For example, the following item:
elseif GetItemTypeId(i) == 'asbl' then
call LinkBonusToItem(u, BONUS_ARMOR, 10, i)
call LinkBonusToItem(u, BONUS_ATTACK_SPEED, 0.3, i)
Am I doing something wrong?
Edit (separate question):
In the NewBonusUtils is a timer, which runs at 0.03125 per second.
I assume that's the timer which is used when I call "AddUnitBonusTimed".
However, for my map, 0.25 per second is good enough.
Can I safely increase it, without destroying anything in the background?
Oh, you are using an older version of the system. In the latest version those functions with the Real in the end where removed and you can use one function for both real and integer bonus types.Thank you. Ah man, was a pretty easy fix: I just needed to add "GetUnitBonusReal".
You should be mindful when you are doing a lot of things every 0.03 seconds, but in this case it's just checking for an ability level and that is pretty fast even in JASS.Regarding the timer: I always read though that you should be mindful about using 0.03 sec triggers.
Is that just for old PCs that had troubles processing so many instances of events, and nowadays that's no longer an issue if you say that "you can have thousands of instances"?
Oh, you are using an older version of the system. In the latest version those functions with the Real in the end where removed and you can use one function for both real and integer bonus types.