И так, система снаряда с настройками, что она включает в себя
- Настраивымый урон, можно так же улучшать за каждый уровень (Дальность, скорость, урон, радиус урона, умножитель)
- Настраивымый урон от характеристик можно Включить\Отключить
- Настройка умножителся урона от характеристик тоже можно Включить\Отключить
- Настройка урона в виде Включить\Отключить доп.характеристики(зеленые)
- Оглушение, она не требует доп.дамми юнита с абилкой стана(стан через триггер сделан)
- Возможность создавать эффекты при полете так же можно Включить\Отключить
- Возможность создавать эффект из дамми юнитов можно Включить\Отключить
- Возможность создать эффект прикрепленный к юниту(врагу\союзнику) можно Включить\Отключить
- Возможность настроить урон под себя (Атака, урон, оружие)
- выбирать цель Враг\Союзник
- наносить урон или лечить можно включить обеих
- Возможность настроить длительность подготовки спела(каст тайм)
- Возможность изменять создавамые эффект в точ числе и эффект оглушения
- Возможность изменять точку крепления
- Возможность Включить\Отключить лечение самого героя
Утечек нет, и багов не нашел пока сам проверял, если хотите изменить систему под себя пишите в лс
Система очень гибкая и очень легко настроить под себя
Код
library MissleSystem initializer Init
/*
PerLevel_Stats - Улучшает характеристики способности с каждым новым уровнем
AddPercentage - Умножает характеристик героя при урон\лечении
includeBonus - Добавляет к значению урона\лечении характеристики, если AddPercentage включен то добавляет с умножителем
Condition_Enemy - Способность выбирает юнита если он враг
Condition_Ally - Способность выбирает юнита если он союзник
DummyEffect - На данном примере я использовал дамми юнита как эффект если вы не делаете этого отключите
FlyEffect - Создает эффект на земле с ним нельзя что либо сделать
AllyEffectPosition - Создает эффект на позиции союзника который попал под способность
AllyEffectTarget - Создает эффект на теле союзника который попал под способность. Пример: "origin" = у ног, "overhead" = над головой
EnemyEffectPosition - Создает эффект на позиции врага который попал под способность
EnemyEffectTarget - Создает эффект на теле врага который попал под способность. Пример: "origin" = у ног, "overhead" = над головой
HealHero - По умолчанию способность не лечит самого героя - кастера если это включено то будет лечить
*/
globals
private constant hashtable Hash = InitHashtable()
private integer SpellId = 'A000' //Способность пустышка
private integer DummyId = 'd000' //Дамми Стрела
private integer DummyEffectId = 'd001' //Эффект Волна
private boolean PerLevel_Stats = true //Включать ли? Улучшение хар-ик способности за уровень || Да - true || Нет - false||
private boolean AddPercentage = false //Включать ли? Умножитель хар-ик для героя урона || Да - true || Нет - false||
private boolean includeBonus = false //Включать ли? Дополнительный урон от хар-ик героя || Да - true || Нет - false||
private real Default_Damage = 60.0 //Урон по умолчанию
private real Default_Percentage = 4.50 //Умножитель хар-ик героя по умолчанию
private real Default_Range = 1200.0 //Дальность по умолчанию
private real Default_Speed = 30.0 //Скорость по умолчанию
private real Default_Radius = 150.0 //Радиус урона по умолчанию
private real PerLevel_Damage = 60.0 //Дополнительный урон за уровень
private real PerLevel_Percentage = 0.00 //Умножитель хар-ик героя за уровень
private real PerLevel_Range = 100.0 //Дополнительная дальность за уровень
private real PerLevel_Speed = 0.0 //Дополнительная скорость за уровень
private real PerLevel_Radius = 0.0 //Дополнительная дистанция урона за уровень
private boolean includeStr = false //Включать ли? Силу героя для урона || Да - true || Нет - false||
private boolean includeAgi = false //Включать ли? Ловкость героя для урона || Да - true || Нет - false||
private boolean includeInt = false //Включать ли? Интеллект героя для урона || Да - true || Нет - false||
private boolean includeStrAdd = false //Включать ли? Дополнительную силу(зеленую) || Да - true || Нет - false||
private boolean includeAgiAdd = false //Включать ли? Дополнительную ловкость(зеленую) || Да - true || Нет - false||
private boolean includeIntAdd = false //Включать ли? Дополнительную интеллект(зеленую) || Да - true || Нет - false||
private attacktype AttackType = ATTACK_TYPE_MAGIC //Тип атаки
private damagetype DamageType = DAMAGE_TYPE_MAGIC //Тип урона
private weapontype WeaponType = WEAPON_TYPE_WHOKNOWS //Тип оружия
private boolean Condition_Enemy = true //Цель Враг? || Да - true || Нет - false||
private boolean Condition_Ally = true //Цель Союзник? || Да - true || Нет - false||
private boolean DamageType_Heal = true //Лечить союзников? || Да - true || Нет - false||
private boolean DamageType_Damage = true //Наносить урон врагам? || Да - true || Нет - false||
private boolean DummyEffect = true //Эффект сделан из Дамми юнита? || Да - true || Нет - false||
private real DummyEffectLifeTime = 1.5 //Время жизни Дамми юнита если он эффект
private boolean FlyEffect = false //Вкличить ли? Эффект полета || Да - true || Нет - false||
private string FlyEffectName = "Abilities\\Spells\\Human\\FlakCannons\\FlakTarget.mdl" //Название эффекта полета. Внимание! Должно быть 2х "\"
private boolean AllyEffectPosition = false //Создать ли? На позиции || Да - true || Нет - false||
private boolean AllyEffectTarget = true //Крепить ли? К телу || Да - true || Нет - false||
private string AllyEffectName = "Abilities\\Spells\\Human\\HolyBolt\\HolyBoltSpecialArt.mdl" //Название эффекта лечения. Внимание! Должно быть 2х "\"
private string AllyEffectAttachmentPoint = "origin" //Название точки крипления эффекта
private boolean EnemyEffectPosition = false //Создать ли? На позиции || Да - true || Нет - false||
private boolean EnemyEffectTarget = true //Крепить ли? К телу || Да - true || Нет - false||
private string EnemyEffectName = "Abilities\\Spells\\Undead\\DeathCoil\\DeathCoilSpecialArt.mdl"//Название эффекта урона. Внимание! Должно быть 2х "\"
private string EnemyEffectAttachmentPoint = "chest" //Название точки крипления эффекта
private boolean HealHero = false //Лечить ли самого героя?
private real CastTime = 0.10 //Длительность применения способности
private unit TempCaster
private unit TempUnit
private real TempDamage
private group TempGroup = CreateGroup()
private group SecondGroup
private trigger MissleSystem = CreateTrigger( )
endglobals
private function MissleSystem_Filter_Units takes nothing returns boolean
return GetWidgetLife(GetFilterUnit()) > 0.405 and not IsUnitInGroup(GetFilterUnit(),SecondGroup)
endfunction
private function MissleSystem_Action_Damage takes nothing returns nothing
local unit Enum = GetEnumUnit()
if DamageType_Heal and IsUnitAlly(Enum,GetOwningPlayer(TempCaster)) and Condition_Ally and not (Enum == TempCaster) then
if HealHero then
call SetUnitState(TempCaster,UNIT_STATE_LIFE,GetWidgetLife(Enum) + TempDamage)
endif
call SetUnitState(Enum,UNIT_STATE_LIFE,GetWidgetLife(Enum) + TempDamage)
if AllyEffectName != "" then
if AllyEffectPosition then
call DestroyEffect(AddSpecialEffect(AllyEffectName,GetUnitX(Enum),GetUnitY(Enum)))
elseif AllyEffectTarget then
call DestroyEffect(AddSpecialEffectTarget(AllyEffectName,Enum,AllyEffectAttachmentPoint))
endif
endif
endif
if DamageType_Damage and not IsUnitAlly(Enum,GetOwningPlayer(TempCaster)) and Condition_Enemy then
call UnitDamageTarget(TempCaster,Enum,TempDamage,false,false,ATTACK_TYPE_MAGIC,DAMAGE_TYPE_MAGIC,null)
if EnemyEffectName != "" then
if EnemyEffectPosition then
call DestroyEffect(AddSpecialEffect(EnemyEffectName,GetUnitX(Enum),GetUnitY(Enum)))
elseif EnemyEffectTarget then
call DestroyEffect(AddSpecialEffectTarget(EnemyEffectName,Enum,EnemyEffectAttachmentPoint))
endif
endif
endif
call GroupAddUnit(SecondGroup,Enum)
set Enum = null
endfunction
private function MissleSystem_Action_Flyig takes nothing returns nothing
local timer Timer = GetExpiredTimer()
local integer HandleId = GetHandleId(Timer)
local unit Caster = LoadUnitHandle(Hash,HandleId,StringHash("Caster"))
local unit Dummy = LoadUnitHandle(Hash,HandleId,StringHash("Dummy"))
local real Angle = LoadReal(Hash,HandleId,StringHash("Angle"))
local real Distance = LoadReal(Hash,HandleId,StringHash("Distance"))
local real Speed = LoadReal(Hash,HandleId,StringHash("Speed"))
local real Radius = LoadReal(Hash,HandleId,StringHash("Radius"))
local real Damage = LoadReal(Hash,HandleId,StringHash("Damage"))
local group Group = LoadGroupHandle(Hash,HandleId,StringHash("Group"))
local real xDummy = GetUnitX(Dummy)
local real yDummy = GetUnitY(Dummy)
local real xCondition = xDummy + Speed * Cos(Angle)
local real yCondition = yDummy + Speed * Sin(Angle)
if Distance > 50 and not IsTerrainPathable(xCondition,yCondition,PATHING_TYPE_FLYABILITY)
set TempCaster = Caster
set TempDamage = Damage
set SecondGroup = Group
call GroupEnumUnitsInRange(TempGroup,xDummy,yDummy,Radius,Condition(function MissleSystem_Filter_Units))
call ForGroup(TempGroup,function MissleSystem_Action_Damage)
call GroupClear(TempGroup)
if DummyEffect then
set bj_lastCreatedUnit = CreateUnit(GetOwningPlayer(Caster),DummyEffectId,xDummy,yDummy,Rad2Deg(Angle))
call UnitApplyTimedLife(bj_lastCreatedUnit, 'BTLF', DummyEffectLifeTime)
endif
call SetUnitX(Dummy,xDummy + Speed * Cos(Angle))
call SetUnitY(Dummy,yDummy + Speed * Sin(Angle))
call SaveReal(Hash,HandleId,StringHash("Distance"),Distance - Speed)
else
call PauseTimer(Timer)
call DestroyGroup(Group)
call KillUnit(Dummy)
call FlushChildHashtable(Hash,HandleId)
call DestroyTimer(Timer)
endif
set Timer = null
set Caster = null
set Dummy = null
set Group = null
endfunction
private function MissleSystem_Action_Init takes nothing returns nothing
local timer Timer = CreateTimer()
local integer HandleId = GetHandleId(Timer)
local unit Caster = GetTriggerUnit()
local group Group = CreateGroup()
local real xCaster = GetUnitX(Caster)
local real yCaster = GetUnitY(Caster)
local real xPoint = GetSpellTargetX()
local real yPoint = GetSpellTargetY()
local real Angle = Atan2(yPoint - yCaster, xPoint - xCaster)
local unit Dummy = CreateUnit(GetOwningPlayer(Caster),DummyId,xCaster,yCaster,Rad2Deg(Angle))
local integer Level = GetUnitAbilityLevel(Caster,SpellId)
local real Damage
local real Distance
local real Speed
local real Radius
local real Percentage
if PerLevel_Stats then
set Damage = Default_Damage + (PerLevel_Damage * Level)
set Percentage = Default_Percentage + (PerLevel_Percentage * Level)
set Distance = Default_Range + (PerLevel_Range * Level)
set Speed = Default_Speed + (PerLevel_Speed * Level)
set Radius = Default_Radius + (PerLevel_Radius * Level)
else
set Distance = Default_Range
set Speed = Default_Speed
set Radius = Default_Radius
set Damage = Default_Damage
endif
if includeBonus then
//===========================================================================
if includeStr then
if AddPercentage then
set Damage = Damage + (GetHeroStr(Caster,includeStrAdd) * Percentage )
else
set Damage = Damage + GetHeroStr(Caster,includeStrAdd)
endif
endif
//===========================================================================
if includeAgi then
if AddPercentage then
set Damage = Damage + (GetHeroAgi(Caster,includeAgiAdd) * Percentage )
else
set Damage = Damage + GetHeroAgi(Caster,includeAgiAdd)
endif
endif
//===========================================================================
if includeInt then
if AddPercentage then
set Damage = Damage + (GetHeroInt(Caster,includeIntAdd) * Percentage )
else
set Damage = Damage + GetHeroInt(Caster,includeIntAdd)
endif
endif
//===========================================================================
endif
call SetUnitVertexColor(Dummy,255,255,255,0)
call SaveUnitHandle(Hash,HandleId,StringHash("Caster"),Caster)
call SaveUnitHandle(Hash,HandleId,StringHash("Dummy"),Dummy)
call SaveReal(Hash,HandleId,StringHash("Angle"),Angle)
call SaveReal(Hash,HandleId,StringHash("Distance"),Distance)
call SaveReal(Hash,HandleId,StringHash("Speed"),Speed)
call SaveReal(Hash,HandleId,StringHash("Damage"),Damage)
call SaveReal(Hash,HandleId,StringHash("Radius"),Radius)
call SaveGroupHandle(Hash,HandleId,StringHash("Group"),Group)
call TriggerSleepAction(CastTime)
call SetUnitVertexColor(Dummy,255,255,255,255)
call TimerStart(Timer,0.015625,true,function MissleSystem_Action_Flyig)
set Timer = null
set Caster = null
set Dummy = null
set Group = null
endfunction
private function MissleSystem_Condition takes nothing returns boolean
return GetSpellAbilityId() == SpellId
endfunction
private function Init takes nothing returns nothing
local integer index = 0
loop
call TriggerRegisterPlayerUnitEvent(MissleSystem, Player(index), EVENT_PLAYER_UNIT_SPELL_EFFECT, null)
set index = index + 1
exitwhen index == bj_MAX_PLAYER_SLOTS
endloop
call TriggerAddCondition( MissleSystem, Condition( function MissleSystem_Condition ) )
call TriggerAddAction( MissleSystem, function MissleSystem_Action_Init )
endfunction
endlibrary