XGM Forum
Сайт - Статьи - Проекты - Ресурсы - Блоги

Форуме в режиме ТОЛЬКО ЧТЕНИЕ. Вы можете задать вопросы в Q/A на сайте, либо создать свой проект или ресурс.
Вернуться   XGM Forum > Warcraft> Академия: форум для вопросов> Jass
Ник
Пароль
Войти через VK в один клик
Сайт использует только имя.

Закрытая тема
 
ELForcer
Сижу only Hard & Soft
offline
Опыт: 1,593
Активность:
Интересная загвоздка с PolledWait
Есть следующий код.
Код:
function KillCurUnit takes unit CurUnit returns nothing
local unit NeedKillUnit = CurUnit
 call PolledWait( 0.5 )
call DisplayTextToForce( GetPlayersAll(), " Выстрел " +  GetUnitName(GetTriggerUnit()) + " в " + GetUnitName(NeedKillUnit) )
call UnitDamageTargetBJ( GetTriggerUnit(), NeedKillUnit, ( I2R(GetHeroStatBJ(bj_HEROSTAT_INT, GetTriggerUnit(), true)) * ( I2R(GetUnitAbilityLevelSwapped('A051', GetTriggerUnit())) * 10.00 ) ), ATTACK_TYPE_NORMAL, DAMAGE_TYPE_NORMAL )
call DisplayTextToForce( GetPlayersAll(), ( I2S(( GetHeroStatBJ(bj_HEROSTAT_INT, GetTriggerUnit(), true) * ( ( GetUnitAbilityLevelSwapped('A051', GetTriggerUnit()) * 10 ) * 1 ) )) + " " ) )
   
endfunction

function Trig_Drago4a_Func003Func001A takes nothing returns nothing
    if ( Trig_Drago4a_Func003Func001Func001C() ) then
    local unit Dummy
    local unit NeedKillUnit
        call CreateNUnitsAtLoc( 1, 'u007', GetTriggerPlayer(), GetUnitLoc(GetTriggerUnit()), bj_UNIT_FACING )
        set Dummy = GetLastCreatedUnit()
        set NeedKillUnit = GetEnumUnit()
        call UnitAddAbilityBJ( 'A052', Dummy)
        call IssueTargetOrderBJ( Dummy, "fingerofdeath", NeedKillUnit )

         call KillCurUnit(NeedKillUnit)
        
        call RemoveUnit( Dummy )
        set Dummy = null
    else
    endif
endfunction


Есть спелл на основе Заклинания крови который ежесекундно рандомно поражает ближайшего юнита и наносит урон в зависимости от разума героя и прокачки спелла. Собственно это всё видно в коде.

Проблема в 1ой функции KillCurUnit, которая отвечает за задержку перед кастом пустышки заклинания для анимации урона и непосредственное поражения. Если из неё убрать call PolledWait( 0.5 ) Функция сработает до конца, но не будет видно анимации урона если этот урон добьет юнита. Если её оставить то функция не отработает до конца и не будет нанесен урон (даже информационного сообщения перед уроном). То есть будет фактически проигрываться чисто анимация атаки.
Целые числа тоже не катят, хотя та же функция задержки спокойно работает в цикле.

Неохота делать другую процедуру проигрывания анимации. Может кто то знает в чем проблема.
Старый 27.06.2010, 00:17
ScorpioT1000
Работаем
online
Опыт: отключен
GetTriggerUnit() после вейта не пашет. пиши в локалки. вобще все Get... из текущего триггера не работают после вейта, это логично и пора бы уже знать)
ScorpioT1002 добавил:
и да, юзай этот полед вейт:
function Sleep takes real duration returns nothing
    local timer t
    local real y
    if (duration>0.1) then
        set y = duration-0.1
        set t=CreateTimer()
        call TimerStart(t,y,false,null)
        loop
            exitwhen (TimerGetRemaining(t)<=0.0)
            call TriggerSleepAction(0.01)
        endloop
        call DestroyTimer(t)
        set t=null
    else
        call TriggerSleepAction(duration)
    endif
endfunction
Старый 27.06.2010, 00:24
ELForcer
Сижу only Hard & Soft
offline
Опыт: 1,593
Активность:
Спасибо. Щас попробую.

GetTriggerUnit() у меня всегда стабильно пашет хоть после 1000 вейтов.. Первый раз щас такое.
Старый 27.06.2010, 00:29
ScorpioT1000
Работаем
online
Опыт: отключен
попробуй) возможно, он когда-то пашет с вейтами...
Старый 27.06.2010, 00:33
ELForcer
Сижу only Hard & Soft
offline
Опыт: 1,593
Активность:
Совет не помог. Воткнул GetTriggerUnit() в переменные. Воткнул твою функцию Sleep, проблема осталась. Если без задержек урон наносится но тогда нет анимации урона.

Код:
function KillCurUnit takes unit CurUnit returns nothing
local unit NeedKillUnit = CurUnit
local unit DragoUnit = GetTriggerUnit()
call Sleep(0.2) //Если без неё то работает до конца
call DisplayTextToForce( GetPlayersAll(), " Выстрел " +  GetUnitName(DragoUnit) + " в " + GetUnitName(NeedKillUnit) )
call UnitDamageTargetBJ( DragoUnit, NeedKillUnit, ( I2R(GetHeroStatBJ(bj_HEROSTAT_INT, DragoUnit, true)) * ( I2R(GetUnitAbilityLevelSwapped('A051', DragoUnit)) * 10.00 ) ), ATTACK_TYPE_NORMAL, DAMAGE_TYPE_NORMAL )
call DisplayTextToForce( GetPlayersAll(), ( I2S(( GetHeroStatBJ(bj_HEROSTAT_INT, DragoUnit, true) * ( ( GetUnitAbilityLevelSwapped('A051', DragoUnit) * 10 ) * 1 ) )) + " " ) )
   
endfunction

function Trig_Drago4a_Func003Func001A takes nothing returns nothing
    if ( Trig_Drago4a_Func003Func001Func001C() ) then
    local unit Dummy
    local unit NeedKillUnit
        call CreateNUnitsAtLoc( 1, 'u007', GetTriggerPlayer(), GetUnitLoc(GetTriggerUnit()), bj_UNIT_FACING )
        set Dummy = GetLastCreatedUnit()
        set NeedKillUnit = GetEnumUnit()
        call UnitAddAbilityBJ( 'A052', Dummy)
        call IssueTargetOrderBJ( Dummy, "fingerofdeath", NeedKillUnit )

         call KillCurUnit(NeedKillUnit)
        
        call RemoveUnit( Dummy )
        set Dummy = null
    else
    endif
endfunction
Старый 27.06.2010, 00:43
ScorpioT1000
Работаем
online
Опыт: отключен
что-то я не совсем понял с анимацией) распиши что у тебя происходит перед вызовом Trig_Drago4a_Func003Func001A и после.
и что должно происходить
Старый 27.06.2010, 00:50
ELForcer
Сижу only Hard & Soft
offline
Опыт: 1,593
Активность:
Дракончик превращается в конон (Заклинание крови) и ежесекундно поражает случайного врага в радиусе 1000 ярдов от себя.
Анимация проходит так: Создается дамми на позиции Дракончика и кастует "Перст боли" в выбранного юнита. Урон не наносится. Он наносится триггером KillCurUnit который вызывается после анимации, но не обрабатывается после нужной задержки.

Триггер пока не оптимизирован, поскольку я пока делаю на количество спеллов, а не на качество кода.
Код:
function Trig_Drago4a_Conditions takes nothing returns boolean
    if ( not ( GetSpellAbilityId() == 'A051' ) ) then
        return false
    endif
    return true
endfunction

function Trig_Drago4a_Func003Func001Func001Func008C takes nothing returns boolean
    if ( ( IsPlayerAlly(GetTriggerPlayer(), GetOwningPlayer(GetEnumUnit())) == false ) ) then
        return true
    endif
    return false
endfunction

function Trig_Drago4a_Func003Func001Func001C takes nothing returns boolean
    if ( not Trig_Drago4a_Func003Func001Func001Func008C() ) then
        return false
    endif
    return true
endfunction

function Sleep takes real duration returns nothing
    local timer t
    local real y
    if (duration>0.1) then
        set y = duration-0.1
        set t=CreateTimer()
        call TimerStart(t,y,false,null)
        loop
            exitwhen (TimerGetRemaining(t)<=0.0)
            call TriggerSleepAction(0.01)
        endloop
        call DestroyTimer(t)
        set t=null
    else
        call TriggerSleepAction(duration)
    endif
endfunction


function KillCurUnit takes unit CurUnit returns nothing
local unit NeedKillUnit = CurUnit
local unit DragoUnit = GetTriggerUnit()
 //call Sleep(0.2)
call DisplayTextToForce( GetPlayersAll(), " Выстрел " +  GetUnitName(DragoUnit) + " в " + GetUnitName(NeedKillUnit) )
call UnitDamageTargetBJ( DragoUnit, NeedKillUnit, ( I2R(GetHeroStatBJ(bj_HEROSTAT_INT, DragoUnit, true)) * ( I2R(GetUnitAbilityLevelSwapped('A051', DragoUnit)) * 10.00 ) ), ATTACK_TYPE_NORMAL, DAMAGE_TYPE_NORMAL )
call DisplayTextToForce( GetPlayersAll(), ( I2S(( GetHeroStatBJ(bj_HEROSTAT_INT, DragoUnit, true) * ( ( GetUnitAbilityLevelSwapped('A051', DragoUnit) * 10 ) * 1 ) )) + " " ) )
   
endfunction

function Trig_Drago4a_Func003Func001A takes nothing returns nothing
    if ( Trig_Drago4a_Func003Func001Func001C() ) then
    local unit Dummy
    local unit NeedKillUnit
        call CreateNUnitsAtLoc( 1, 'u007', GetTriggerPlayer(), GetUnitLoc(GetTriggerUnit()), bj_UNIT_FACING )
        set Dummy = GetLastCreatedUnit()
        set NeedKillUnit = GetEnumUnit()
        call UnitAddAbilityBJ( 'A052', Dummy)
        call IssueTargetOrderBJ( Dummy, "fingerofdeath", NeedKillUnit )

         call KillCurUnit(NeedKillUnit)
        
        call RemoveUnit( Dummy )
        set Dummy = null
    else
    endif
endfunction

function Trig_Drago4a_Actions takes nothing returns nothing
    
    call DisplayTextToForce( GetPlayersAll(), "TRIGSTR_3130" )
    set udg_DragoAttack[GetConvertedPlayerId( GetTriggerPlayer(  ) )] = 1
    loop
        exitwhen udg_DragoAttack[GetConvertedPlayerId( GetTriggerPlayer(  ) )] > 100
        call PolledWait( 0.5 )
        call ForGroupBJ( GetRandomSubGroup(1, GetUnitsInRangeOfLocAll(1000.00, GetUnitLoc(GetTriggerUnit()))), function Trig_Drago4a_Func003Func001A )
        call PolledWait( 0.5 )
        set udg_DragoAttack[GetConvertedPlayerId( GetTriggerPlayer(  ) )] = udg_DragoAttack[GetConvertedPlayerId( GetTriggerPlayer(  ) )] + 1
    endloop
endfunction

//===========================================================================
function InitTrig_Drago4a takes nothing returns nothing
    set gg_trg_Drago4a = CreateTrigger(  )
    call TriggerRegisterAnyUnitEventBJ( gg_trg_Drago4a, EVENT_PLAYER_UNIT_SPELL_CAST )
    call TriggerAddCondition( gg_trg_Drago4a, Condition( function Trig_Drago4a_Conditions ) )
    call TriggerAddAction( gg_trg_Drago4a, function Trig_Drago4a_Actions )
endfunction
Старый 27.06.2010, 01:13
ScorpioT1000
Работаем
online
Опыт: отключен
а дыг если у тебя в enum-е слип вызывается, то энум обрывает поток после слипа. вызывай в отдельном потоке:
//глобалка unit xxx
//глобалка unit yyy

function KillCurUnit_NewThread takes nothing returns nothing
local unit NeedKillUnit = xxx
local unit DragoUnit = yyy
call Sleep(0.2)
call DisplayTextToForce( GetPlayersAll(), " Выстрел " +  GetUnitName(DragoUnit) + " в " + GetUnitName(NeedKillUnit) )
call UnitDamageTargetBJ( DragoUnit, NeedKillUnit, ( I2R(GetHeroStatBJ(bj_HEROSTAT_INT, DragoUnit, true)) * ( I2R(GetUnitAbilityLevelSwapped('A051', DragoUnit)) * 10.00 ) ), ATTACK_TYPE_NORMAL, DAMAGE_TYPE_NORMAL )
call DisplayTextToForce( GetPlayersAll(), ( I2S(( GetHeroStatBJ(bj_HEROSTAT_INT, DragoUnit, true) * ( ( GetUnitAbilityLevelSwapped('A051', DragoUnit) * 10 ) * 1 ) )) + " " ) )
   
endfunction

function KillCurUnit takes unit CurUnit returns nothing
set xxx = CurUnit
set yyy = GetTriggerUnit()
call ExecuteFunc("KillCurUnit_NewThread")
endfunction
вызываешь KillCurUnit
Старый 27.06.2010, 01:19
AlexKARASb
Learning cpp
offline
Опыт: 22,103
Активность:
function Trig_Drago4a_Actions takes nothing returns nothing
В этой функции цикл замени на таймер с периодом в 0.50с и все.
Старый 27.06.2010, 01:19
ELForcer
Сижу only Hard & Soft
offline
Опыт: 1,593
Активность:
Короче проще оптимизировать триг. Там и Polled заработает :)
Старый 27.06.2010, 01:24
ScorpioT1000
Работаем
online
Опыт: отключен
попробуй мой способ)
Старый 27.06.2010, 01:38
Toadcop

offline
Опыт: 54,313
Активность:
Цитата:
GetTriggerUnit() после вейта не пашет

он как раз и пашет m-| другие "Get*Unit()" не пашут...
Старый 27.06.2010, 16:07
ScorpioT1000
Работаем
online
Опыт: отключен
ясно ) не помню уже
Старый 27.06.2010, 17:49
ELForcer
Сижу only Hard & Soft
offline
Опыт: 1,593
Активность:
Тему можно закрыть. Нанесение урона я поставил в конец цикла, за пределы IF после этого всё заработало..
Старый 28.06.2010, 00:11
Закрытая тема

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск

Ваши права в разделе
Вы не можете создавать темы
Вы не можете отвечать на сообщения
Вы не можете прикреплять файлы
Вы можете скачивать файлы

BB-коды Вкл.
[IMG] код Вкл.
HTML код Выкл.
Быстрый переход



Часовой пояс GMT +3, время: 16:48.