"Бафф" в ковычках, т.к. мне требуется только таймер, и ссылка на функцию.
Что то вроде:
код
есть родительский класс бафф
инициализация чилд классов
BuffIni(){
Buff(1,func)
Buff(2,func)
..//ид класса, функция
}
функция добавления бафа юниту:
AddBuff(integer unitid, integer buffid, real time){
если юнит имеет бафф то продлеваем жизнь таймера
if IsUnitHasBuff(unitid,buffid) {
добавить время таймеру
}else{
создать бафф с таймером
создать эффект и привязать к ид юнита (юзер дата)
выполнить функцию бафа
}
Функция удаления
DestroyBuff(integer unitid, integer buffid){
выполнить функциию удаления бафа
}
Использую подобную системку, слегка кривую.. для способностей, реализованную через хеш и массив триггеров с передачей аргументов через глобалки.

Баффов же у меня было до этого былр немного, и использовались примитивные заглушки. Однако в последнее время их кол-во стало разрастается, поэтому появилась необходимость в нормальной системе.

Отсюда вопрос. Может я велосипед изобретаю, и есть ли готовые решения?

Не особо смотрел раньше в сторону структур, хотя может и зря, но проблема то в основном с ссылкой на функцию, так как тип code с массивом не работает.

Нет универсальных решений нет и врятли будут, тут все надо своими руками, лучше для некоторых баффов юзать триггеры чтобы отследить смерть событием TriggerRegisterDeathEvent а так же применение диспелящих способностей на цель, либо самой целью.
`
ОЖИДАНИЕ РЕКЛАМЫ...

Показан только небольшой набор комментариев вокруг указанного. Перейти к актуальным.
23
Похожие вопросы:

ответ
Ты никак не заставишь одиноаковые заклинания стакнуться. Делай спеллы-пустышки, баффы вешай аурами, которые потом будешь удалять, эффекты заклинания делай триггерно. Иначе никак.
Единственное, что ещё, применимое именно к лечению - можно создавать несколько фонтанов жизни или юнитов с их способностью и регенить сильнее за счёт одной и той же способности.
ответ
Darknessay:
quq_CCCP:
что мешает юзнуть берсерк, манащит, канал, да хоть виндвалк?
Мешает то, что берсерк и виндвалк уже использованы, переключаемые абилки - хурма, а канал не моментальный.
Ты станишь юнита, какая тебе разница?
Канал пойдет с тем же успехом, юнит его кастанет в любом случае.
Переключаемые абилки работают нормально, если уметь немного искать и читать, как их юзать в качестве простых есть инфа в статьях на форуме.
Еще всякие вееры ножей, не сбивают приказ идти куда либо. Юзай его в качестве основы.
ответ
Pick every unit in range [250] matching condition [бафф спелла]
Всё что находится внутри данного блока произойдёт столько раз, сколько воинов находится внутри выбранной группы. Обратиться к воину можно через Picked Unit ( GetEnumUnit( ) ). Если Вам нужно добавить событие на смерть именно этих воинов, то прямо здесь внутри блока добавляете их в событие триггера, выбрав их через Picked Unit, или сохраняете их в переменные.

Также можно не сохранять каждого воина, а занести их в отдельную группу. А вместо проверки:
Условие: Dying unit = Aim [Integer A]
проверяете, находится ли воин в группе.
ответ
8gabriel8:
Это тот же принцип для второго пункта, мне казалось, что могут быть способы изящнее. Лучше по другим пунктам подскажите.
первый вопрос так и не понял, насчет третьего вопроса:
там весь прикол в ивентах, есть начало когда наводишь на цель, тогда даже анимация не проигрывается и мана не забирается.
Приводит в действие это уже когда ману сняло и проигралась анимация.
Где то был текст на всё это, но я не могу найти.
Ну а далее чекаешь уровень бафа у цели, если он больше 0 - значит хиляешь и удаляешь баф
Хотя возможно это я неправильно понял, можно просто отловить начало каста абилки и восстанавливать ману триггерно.

32
Нет универсальных решений нет и врятли будут, тут все надо своими руками, лучше для некоторых баффов юзать триггеры чтобы отследить смерть событием TriggerRegisterDeathEvent а так же применение диспелящих способностей на цель, либо самой целью.
Принятый ответ
21
Не особо смотрел раньше в сторону структур, хотя может и зря, но проблема то в основном с ссылкой на функцию, так как тип code с массивом не работает.
Можно использовать function interface вместо code array, в нём можно сохранять даже функции, которые требуют что-то.
28
Зависит от того, что тебе нужно от этой системы.
В карте, что я сейчас делаю, отличная система кастомных баффов (баффы WarCraft 3 я не использую вообще). Её я собираюсь выложить и рассказать, когда создам проект на XGM.
Система долго эволюционировала, потому человеку, который её никогда не видел, возможно будет сложно её понять.

Вкратце.
Есть структура MinionBuff, в ней есть следующие функции.
раскрыть
    stub method tickAction takes nothing returns boolean
        return true
    endmethod
    
    static method tickEnd takes nothing returns nothing
        local thistype this = GetCustomTimer()
        set currticks = currticks - 1
        if tickAction() then
            call destroy()
        endif
    endmethod
    
    method extendTicks takes integer addticks returns nothing
        set currticks = currticks + addticks
        if currticks > buffdata.maxticks then
            set currticks = buffdata.maxticks
        endif
    endmethod
    
    method startWithPeriod takes real period returns nothing
        set currticks = buffdata.startticks
        call UnitAddAbility(target.minion, buffdata.effectid)
        call TimerStart(t, period, buffdata.periodic, function thistype.tickEnd)
        call DebugMsgIf(isStopped(), "MinionBuff " + I2S(this) + " is started.")
        set isRunning = true
    endmethod
    
    method start takes nothing returns nothing
        call startWithPeriod(buffdata.period)
    endmethod
    
    method startPeriodic takes integer addticks returns nothing
        if isRunning then
            call extendTicks(addticks)
        else
            call start()
        endif
    endmethod
endstruct
Объект этой структуры не создаётся, создаются объекты конкретных баффов (которые тоже структуры). Есть два типа баффов - периодический (максимальное количество тиков больше 1) и непериодический. Я знаю, какой бафф периодический, а какой нет, потому периодические баффы стартуются функцией startPeriodic, а непериодические - start. Их таймер запускается в функцию tickEnd, где вызывается tickAction. Если у баффа эта функция перезаписана, то выполнится его версия функции. Если нет, то вернётся правда, и бафф будет удалён.
Примеры баффов.
раскрыть
struct BuffMultishotDoT extends MinionBuff
    method onCreate takes nothing returns nothing
        set node1 = target.buffs.addEoTBuff(this)
    endmethod
    
    method onDestroy takes nothing returns nothing
        call target.buffs.removeEoTBuff(node1)
    endmethod

    method tickAction takes nothing returns boolean
        local Tower dd
        if UnitExists(source) then
            set dd = GetUnitUserData(source)
            call dd.dealDamage(target, AbilMultishot(dd.abil).dot, AbilMultishot.dottype)
            return currticks == 0
        endif
        return true
    endmethod
    
    static method launch takes Minion m, Tower caster returns nothing
        //! runtextmacro InitBuff("m", "caster.tower", "caster.owner", "MultishotDoT", "true", "false", "false", "")
        call startPeriodic(buffdata.startticks)
    endmethod
endstruct

struct BuffMultishotSlow extends MinionBuff
    method onCreate takes nothing returns nothing
        set node1 = target.buffs.addMoveSpeedBuff(this)
    endmethod
    
    method onDestroy takes nothing returns nothing
        call target.buffs.removeMoveSpeedBuff(node1)
        call target.updateMoveSpeed()
    endmethod
    
    static method launch takes Minion m, Tower caster, real slow returns nothing
        //! runtextmacro InitBuff("m", "caster.tower", "caster.owner", "MultishotSlow", "true", "true", "false", "")
        call m.alterMoveSpeed(node1, slow)
        call start()
    endmethod
endstruct

Можешь использовать перезапись stub метода, а можешь использовать интерфейс функций, реализованы они одинаково: в обоих используется массив триггеров.
15
Есть два типа баффов - периодический (максимальное количество тиков больше 1) и непериодический.
Не проще было бы задавать бафф просто длительностью и интервалом между периодическим эффектом? В 6 секунд длительностью и 1.5 секундным интервалом срабатывает 4 раза. Вроде на порядок проще получается.
28
Не проще было бы задавать бафф просто длительностью и интервалом между периодическим эффектом? В 6 секунд длительностью и 1.5 секундным интервалом срабатывает 4 раза. Вроде на порядок проще получается.
Я задаю длительностью, максимальным количеством тиков и начальным количеством тиков. Период вычисляется делением длительности на начальное количество тиков. Такие параметры необходимы для того, что система позволяла создавать баффы, которые изначально имеют 1 тик, но при повторном наложении могут увеличивать кол-во тиков вплоть до указанного максимума.
Что же касается вопроса простоты и удобства - дело личное. Мне было удобнее сделать так.
Я не показал БД, где прописываются свойства баффов, потому что не посчитал это нужным. Вопрос ведь про готовые системы баффов. Я ответил, что наличие такой системы зависит от требований к ней. Также я хотел привести рабочий пример псевдомассива code, о чём также спрашивалось.
Показан только небольшой набор комментариев вокруг указанного. Перейти к актуальным.
Чтобы оставить комментарий, пожалуйста, войдите на сайт.