| 07-20-2007, 08:55 AM | #1 |
Well, I'm still trying to simulate sleep (like the Dreadlord ability), and I haven't had much luck. It seems that adding the "sleeping" classification does nothing. DioD also mentioned that sleep has a hidden integer-only orderid, but I've not had any luck. Through testing, I've discovered that when a unit is slept by a spell, it is issued the point-target order 851973. At first I did not believe it to be the right order, but it evidently is because when a unit is sleept, its current order is 851973. So, I tried ordering units to do that order at its current location, like so: But the units weren't being affected by this order, so I re-initiated my other trigger to see if it was actually being issued the order, and it wasn't. I've also tried call IssueImmediateOrderById(GetEnumUnit(), 851973), but the unit was ordered to stop instead. I know that this is not the order for stop or hold position, as those are 851972 and 851993 respectively. Any ideas on how to order a unit to manually sleep? Additionally, I could simply use a simulation of sleep, which would follow these guidelines:
So... who's got the solution? Feel fry to try out my testmap. Pressing escape will order all currently selected units to 851973 (point-target), and the Dreadlord's sleep can be cast on your own units. |
| 07-20-2007, 12:57 PM | #2 |
Even though I'm 100% sure you are intentionally not using this method, I have to ask, why are you not using a dummy caster? |
| 07-20-2007, 01:32 PM | #3 |
I think that 851973 orderid thingy is a smart order. |
| 07-20-2007, 05:27 PM | #4 | |
Quote:
|
| 07-20-2007, 05:33 PM | #5 | |
Quote:
That's how the buff system in DoE works. You also might consider issuing the order without a target. Like... JASS:call IssueImmediateOrderById(GetEnumUnit(), 851973) |
| 07-24-2007, 07:07 AM | #6 | ||
Been on vacation for 3 days, but I'm back now with more questions :D Quote:
Quote:
|
| 07-24-2007, 10:07 AM | #7 |
Just check if a unit who is sleeping is sleep-ed again, then if it is just add how X seconds on the remaining duration of the sleep buff. I was trying to make the same effects of the condition system in DoE.. Here's what I did.. JASS:
struct ailmentdata
unit poisonsource
unit bleedsource
unit burnsource
unit blindsource
unit cripplesource
unit poisoncaster
unit bleedcaster
unit burncaster
unit blindcaster
unit cripplecaster
unit poisontarget
unit bleedtarget
unit burntarget
unit blindtarget
unit crippletarget
real poisondur
real bleeddur
real burndur
real blinddur
real crippledur
integer poison = 0
integer bleed = 0
integer burn = 0
integer cripple = 0
integer blind = 0
endstruct
function RemoveStatusAilment takes unit u, integer WhichAilment returns nothing
local ailmentdata dat
if GetUnitUserData(u) != 0 then
set dat = ailmentdata(GetUnitUserData(u))
if WhichAilment == 0 then
set dat.poisondur = 0
elseif WhichAilment == 1 then
set dat.bleeddur = 0
elseif WhichAilment == 2 then
set dat.burndur = 0
elseif WhichAilment == 3 then
set dat.crippledur = 0
elseif WhichAilment == 4 then
set dat.blinddur = 0
endif
endif
endfunction
function StatusAilment_Callback takes nothing returns nothing
local timer t = GetExpiredTimer()
local ailmentdata dat = ailmentdata(GetAttachedInt(t, "dat"))
if dat.poison != 0 then
if dat.poison > 0 and GetWidgetLife(dat.poisontarget) > .405 then
call DamageUnitByOptions(dat.bleedsource, dat.bleedtarget, .8, DamageTypes(ATTACK_TYPE_CHAOS, DAMAGE_TYPE_POISON)+DamageIgnore(UNIT_TYPE_MECHANICAL))
set dat.poisondur = dat.poisondur - 0.10
else
call UnitRemoveAbility(dat.bleedtarget, 'B000')
set dat.poison = 0
endif
endif
if dat.bleed != 0 and GetWidgetLife(dat.bleedtarget) > .405 then
if dat.bleeddur > 0 then
call DamageUnitByOptions(dat.bleedsource, dat.bleedtarget, 1.2, DamageTypes(ATTACK_TYPE_CHAOS, DAMAGE_TYPE_NORMAL)+DamageIgnore(UNIT_TYPE_MECHANICAL))
set dat.bleeddur = dat.bleeddur - 0.10
else
call UnitRemoveAbility(dat.bleedtarget, 'B001')
set dat.bleed = 0
endif
endif
if dat.burn != 0 then
if dat.burndur > 0 and GetWidgetLife(dat.burntarget) > .405 then
call DamageUnitByOptions(dat.burnsource, dat.burntarget, 1.6, DamageTypes(ATTACK_TYPE_CHAOS, DAMAGE_TYPE_NORMAL)+DamageIgnore(UNIT_TYPE_MECHANICAL))
set dat.burndur = dat.burndur - 0.10
else
call UnitRemoveAbility(dat.burntarget, 'B002')
set dat.burn = 0
endif
endif
if dat.cripple != 0 then
if dat.crippledur > 0 and GetWidgetLife(dat.crippletarget) > .405 then
set dat.crippledur = dat.crippledur - 0.10
else
call UnitRemoveAbility(dat.crippletarget, 'B003')
set dat.cripple = 0
endif
endif
if dat.blind != 0 and GetWidgetLife(dat.blindtarget) > .405 then
if dat.blinddur > 0 then
set dat.blinddur = dat.blinddur - 0.10
else
call UnitRemoveAbility(dat.blindtarget, 'B004')
set dat.blind = 0
endif
endif
if dat.bleed == 0 and dat.burn == 0 and dat.cripple == 0 and dat.blind == 0 then
call CleanAttachedVars(t)
call ReleaseTimer(t)
call ailmentdata.destroy(dat)
endif
endfunction
function ApplyStatusAilment takes unit source, unit target, integer WhatAilment, real dur returns nothing
local ailmentdata dat
local unit caster
local timer t
local integer i = GetUnitUserData(target)
if i == 0 then
set dat = ailmentdata.create()
call SetUnitUserData(target, dat)
else
set dat = ailmentdata(i)
endif
if dat.bleed == 0 or dat.burn == 0 or dat.cripple == 0 or dat.blind == 0 then
set t = NewTimer()
call AttachInt(t, "dat", dat)
if WhatAilment == 0 then
if dat.poison == 0 then
call CasterCastAbilityLevel(GetOwningPlayer(source), 'A000', 1, "slow", target, true)
set dat.poisontarget = target
set dat.poisonsource = source
set dat.poisondur = dur
set dat.poison = 1
endif
elseif WhatAilment == 1 then
if dat.bleed == 0 then
call CasterCastAbilityLevel(GetOwningPlayer(source), 'A001', 1, "innerfire", target, true)
set dat.bleedtarget = target
set dat.bleedsource = source
set dat.bleeddur = dur
set dat.bleed = 1
endif
elseif WhatAilment == 2 then
if dat.burn == 0 then
call CasterCastAbilityLevel(GetOwningPlayer(source), 'A002', 1, "acidbomb", target, true)
set dat.burntarget = target
set dat.burnsource = source
set dat.burndur = dur
set dat.burn = 1
endif
elseif WhatAilment == 3 then
if dat.cripple == 0 then
call CasterCastAbilityLevel(GetOwningPlayer(source), 'A003', 1, "cripple", target, true)
set dat.crippletarget = target
set dat.cripplesource = source
set dat.crippledur = dur
set dat.cripple = 1
endif
elseif WhatAilment == 4 then
if dat.blind == 0 then
call CasterCastAbilityLevel(GetOwningPlayer(source), 'A004', 1, "curse", target, true)
set dat.blindtarget = target
set dat.blindsource = source
set dat.blinddur = dur
set dat.blind = 1
endif
endif
call TimerStart(t, 0.10, true, function StatusAilment_Callback)
else
if WhatAilment == 0 then
set ailmentdata(i).poisondur = ailmentdata(i).poisondur + dur
elseif WhatAilment == 1 then
set ailmentdata(i).bleeddur = ailmentdata(i).bleeddur + dur
elseif WhatAilment == 2 then
set ailmentdata(i).burndur = ailmentdata(i).burndur + dur
elseif WhatAilment == 3 then
set ailmentdata(i).crippledur = ailmentdata(i).crippledur + dur
elseif WhatAilment == 4 then
set ailmentdata(i).blinddur = ailmentdata(i).blinddur + dur
endif
endif
endfunction
There I can modify the duration of buffs by checking if it has the buff. EDIT: Oh shit, you're on a Mac.. I forgot >_> |
| 07-24-2007, 01:04 PM | #8 |
Adding duration would be pretty bad for buffs as you get perfect stacking (especially of say, stun). The way it's done in DoE is using a timer for buff applied to a unit. When you apply a buff, you check the time remaining on the timer. If the time remaining is less, you start it with your new time, otherwise do nothing. Timers are the easiest way to implement stacking duration like that. Oh and btw Toink I'm pretty sure that system is bugged. |
| 07-24-2007, 06:58 PM | #9 |
Funny... the way the Sleep mechanic works in Melee games is that it overrides any previous cast no matter the duration. I'm building my own sleep functions to have 2 boolean options that can cause the 4 possible outcomes I need:
|
| 07-25-2007, 10:02 AM | #10 |
@blu: Yeh I just tested it, so I recoded it. But it still works the same way... I just use GetUnitAbilityLevel() to check if a unit has the buff then just add the duration, if it doesn't it applies the buff. But I like how your method works.. How do you get the remaining time of a timer? |
| 07-25-2007, 03:12 PM | #11 |
TimerGetRemaining(t) And TimerGetElapsed for already-passed time. |
| 07-26-2007, 08:55 AM | #12 |
Thanks for that blu! :) So you check if the unit has the buff to check whether it is crippled, etc,. then just access the timer to extend the duration? |
| 07-26-2007, 09:30 AM | #13 |
Yes, that is the basis of it. |
