local ____lualib = require("lualib_bundle") local __TS__Class = ____lualib.__TS__Class local __TS__ClassExtends = ____lualib.__TS__ClassExtends local __TS__Decorate = ____lualib.__TS__Decorate local ____exports = {} local ____dota_ts_adapter = require("lib.dota_ts_adapter") local BaseItem = ____dota_ts_adapter.BaseItem local BaseModifier = ____dota_ts_adapter.BaseModifier local registerAbility = ____dota_ts_adapter.registerAbility local registerModifier = ____dota_ts_adapter.registerModifier local ____incoming_damage_reduction_combine = require("utils.incoming_damage_reduction_combine") local removeIncomingDamageReductionSource = ____incoming_damage_reduction_combine.removeIncomingDamageReductionSource local setIncomingDamageReductionSource = ____incoming_damage_reduction_combine.setIncomingDamageReductionSource local MJOLNIR_ACTIVE_INCOMING_SOURCE = "modifier_item_mjolnir_active" ____exports.item_mjolnir_custom = __TS__Class() local item_mjolnir_custom = ____exports.item_mjolnir_custom item_mjolnir_custom.name = "item_mjolnir_custom" item_mjolnir_custom.____file_path = "scripts/vscripts/items/default_items/item_mjolnir_custom.lua" __TS__ClassExtends(item_mjolnir_custom, BaseItem) function item_mjolnir_custom.prototype.GetIntrinsicModifierName(self) return "modifier_item_mjolnir_custom" end function item_mjolnir_custom.prototype.OnSpellStart(self) local target = self:GetCursorTarget() if not target then return end target:EmitSound("DOTA_Item.Mjollnir.Activate") target:AddNewModifier( self:GetCaster(), self, "modifier_item_mjolnir_active", {duration = self:GetSpecialValueFor("duration")} ) end item_mjolnir_custom = __TS__Decorate( item_mjolnir_custom, item_mjolnir_custom, {registerAbility(nil)}, {kind = "class", name = "item_mjolnir_custom"} ) ____exports.item_mjolnir_custom = item_mjolnir_custom ____exports.modifier_item_mjolnir_active = __TS__Class() local modifier_item_mjolnir_active = ____exports.modifier_item_mjolnir_active modifier_item_mjolnir_active.name = "modifier_item_mjolnir_active" modifier_item_mjolnir_active.____file_path = "scripts/vscripts/items/default_items/item_mjolnir_custom.lua" __TS__ClassExtends(modifier_item_mjolnir_active, BaseModifier) function modifier_item_mjolnir_active.prototype.GetEffectName(self) return "particles/econ/events/ti6/mjollnir_shield_ti6.vpcf" end function modifier_item_mjolnir_active.prototype.GetEffectAttachType(self) return PATTACH_ABSORIGIN_FOLLOW end function modifier_item_mjolnir_active.prototype.DeclareFunctions(self) return {MODIFIER_PROPERTY_DAMAGEOUTGOING_PERCENTAGE} end function modifier_item_mjolnir_active.prototype.OnCreated(self) if not IsServer() then return end setIncomingDamageReductionSource( nil, self:GetParent(), MJOLNIR_ACTIVE_INCOMING_SOURCE, function() local ability = self:GetAbility() if not ability then return 0 end return math.max( 0, ability:GetSpecialValueFor("incoming_pct") ) end ) end function modifier_item_mjolnir_active.prototype.OnDestroy(self) if not IsServer() then return end removeIncomingDamageReductionSource( nil, self:GetParent(), MJOLNIR_ACTIVE_INCOMING_SOURCE ) end function modifier_item_mjolnir_active.prototype.GetModifierDamageOutgoing_Percentage(self, event) return self:GetAbility():GetSpecialValueFor("outgoing_pct") end function modifier_item_mjolnir_active.prototype.GetTexture(self) return "item_mjollnir" end modifier_item_mjolnir_active = __TS__Decorate( modifier_item_mjolnir_active, modifier_item_mjolnir_active, {registerModifier(nil)}, {kind = "class", name = "modifier_item_mjolnir_active"} ) ____exports.modifier_item_mjolnir_active = modifier_item_mjolnir_active ____exports.modifier_item_mjolnir_custom = __TS__Class() local modifier_item_mjolnir_custom = ____exports.modifier_item_mjolnir_custom modifier_item_mjolnir_custom.name = "modifier_item_mjolnir_custom" modifier_item_mjolnir_custom.____file_path = "scripts/vscripts/items/default_items/item_mjolnir_custom.lua" __TS__ClassExtends(modifier_item_mjolnir_custom, BaseModifier) function modifier_item_mjolnir_custom.prototype.____constructor(self, ...) BaseModifier.prototype.____constructor(self, ...) self.bonus_damage = 0 self.bonus_attack_speed = 0 self.chain_chance = 0 self.chain_cooldown = 0 self.bChainCooldown = false end function modifier_item_mjolnir_custom.prototype.IsHidden(self) return true end function modifier_item_mjolnir_custom.prototype.IsPurgable(self) return false end function modifier_item_mjolnir_custom.prototype.RemoveOnDeath(self) return false end function modifier_item_mjolnir_custom.prototype.GetAttributes(self) return MODIFIER_ATTRIBUTE_MULTIPLE end function modifier_item_mjolnir_custom.prototype.OnCreated(self, params) if IsServer() then if not self:GetAbility() then self:Destroy() return end end local ability = self:GetAbility() if ability then self.bonus_damage = ability:GetSpecialValueFor("bonus_damage") self.bonus_attack_speed = ability:GetSpecialValueFor("bonus_attack_speed") self.chain_chance = ability:GetSpecialValueFor("chain_chance") self.chain_cooldown = ability:GetSpecialValueFor("chain_cooldown") else self.bonus_damage = 0 self.bonus_attack_speed = 0 self.chain_chance = 0 self.chain_cooldown = 0 end self.bChainCooldown = false end function modifier_item_mjolnir_custom.prototype.OnIntervalThink(self) self.bChainCooldown = false self:StartIntervalThink(-1) end function modifier_item_mjolnir_custom.prototype.DeclareFunctions(self) return {MODIFIER_PROPERTY_PREATTACK_BONUS_DAMAGE, MODIFIER_PROPERTY_ATTACKSPEED_BONUS_CONSTANT, MODIFIER_EVENT_ON_ATTACK_LANDED, MODIFIER_EVENT_ON_ORDER} end function modifier_item_mjolnir_custom.prototype.GetModifierPreAttack_BonusDamage(self) return self.bonus_damage end function modifier_item_mjolnir_custom.prototype.GetModifierAttackSpeedBonus_Constant(self) return self.bonus_attack_speed end function modifier_item_mjolnir_custom.prototype.OnAttackLanded(self, event) if IsServer() and event.attacker == self:GetParent() and self:GetParent():IsAlive() and not self.bChainCooldown and not self:GetParent():IsIllusion() and not event.target:IsMagicImmune() and not event.target:IsBuilding() and not event.target:IsOther() and self:GetParent():GetTeamNumber() ~= event.target:GetTeamNumber() and RollPseudoRandomPercentage( self.chain_chance, 4, self:GetParent() ) then self:GetParent():EmitSound("Item.Maelstrom.Chain_Lightning") self:GetParent():AddNewModifier( self:GetCaster(), self:GetAbility(), "modifier_chain_lightning", {starting_unit_entindex = event.target:entindex()} ) self.bChainCooldown = true self:StartIntervalThink(self.chain_cooldown) end end modifier_item_mjolnir_custom = __TS__Decorate( modifier_item_mjolnir_custom, modifier_item_mjolnir_custom, {registerModifier(nil)}, {kind = "class", name = "modifier_item_mjolnir_custom"} ) ____exports.modifier_item_mjolnir_custom = modifier_item_mjolnir_custom ____exports.modifier_chain_lightning = __TS__Class() local modifier_chain_lightning = ____exports.modifier_chain_lightning modifier_chain_lightning.name = "modifier_chain_lightning" modifier_chain_lightning.____file_path = "scripts/vscripts/items/default_items/item_mjolnir_custom.lua" __TS__ClassExtends(modifier_chain_lightning, BaseModifier) function modifier_chain_lightning.prototype.____constructor(self, ...) BaseModifier.prototype.____constructor(self, ...) self.bonus_damage = 0 self.chain_damage = 0 self.chain_damage_self = 0 self.chain_strikes = 0 self.chain_radius = 0 self.chain_delay = 0 self.units_affected = {} self.unit_counter = 0 self.zapped = false end function modifier_chain_lightning.prototype.IsHidden(self) return true end function modifier_chain_lightning.prototype.IsDebuff(self) return false end function modifier_chain_lightning.prototype.IsPurgable(self) return false end function modifier_chain_lightning.prototype.RemoveOnDeath(self) return false end function modifier_chain_lightning.prototype.GetAttributes(self) return MODIFIER_ATTRIBUTE_MULTIPLE end function modifier_chain_lightning.prototype.OnCreated(self, params) if IsServer() then if not self:GetAbility() then self:Destroy() return end end if not IsServer() then return end local ability = self:GetAbility() if ability then self.bonus_damage = ability:GetSpecialValueFor("bonus_damage") self.chain_damage = ability:GetSpecialValueFor("chain_damage") self.chain_damage_self = ability:GetSpecialValueFor("chain_damage_self") self.chain_strikes = ability:GetSpecialValueFor("chain_strikes") self.chain_radius = ability:GetSpecialValueFor("chain_radius") self.chain_delay = ability:GetSpecialValueFor("chain_delay") end self.starting_unit_entindex = params.starting_unit_entindex if self.starting_unit_entindex then local unit = EntIndexToHScript(self.starting_unit_entindex) if unit and unit:IsBaseNPC() then self.current_unit = unit else self:Destroy() return end else self:Destroy() return end self.units_affected = {} self.unit_counter = 0 self:OnIntervalThink() self:StartIntervalThink(self.chain_delay) end function modifier_chain_lightning.prototype.OnIntervalThink(self) self.zapped = false local caster = self:GetCaster() if not self.current_unit or not caster then return end local enemies = FindUnitsInRadius( caster:GetTeamNumber(), self.current_unit:GetAbsOrigin(), nil, self.chain_radius, DOTA_UNIT_TARGET_TEAM_ENEMY, DOTA_UNIT_TARGET_HERO + DOTA_UNIT_TARGET_BASIC, DOTA_UNIT_TARGET_FLAG_FOW_VISIBLE + DOTA_UNIT_TARGET_FLAG_NO_INVIS, FIND_CLOSEST, false ) for ____, enemy in ipairs(enemies) do if not self.units_affected[enemy:entindex()] then enemy:EmitSound("Item.Maelstrom.Chain_Lightning.Jump") local zap_particle = ParticleManager:CreateParticle("particles/items_fx/chain_lightning.vpcf", PATTACH_ABSORIGIN_FOLLOW, self.current_unit) if self.unit_counter == 0 then ParticleManager:SetParticleControlEnt( zap_particle, 0, self:GetParent(), PATTACH_POINT_FOLLOW, "attach_hitloc", self:GetParent():GetAbsOrigin(), true ) else ParticleManager:SetParticleControlEnt( zap_particle, 0, self.current_unit, PATTACH_POINT_FOLLOW, "attach_hitloc", self.current_unit:GetAbsOrigin(), true ) end ParticleManager:SetParticleControlEnt( zap_particle, 1, enemy, PATTACH_POINT_FOLLOW, "attach_hitloc", enemy:GetAbsOrigin(), true ) ParticleManager:SetParticleControl( zap_particle, 2, Vector(1, 1, 1) ) ParticleManager:ReleaseParticleIndex(zap_particle) self.unit_counter = self.unit_counter + 1 self.current_unit = enemy self.units_affected[self.current_unit:entindex()] = true self.zapped = true local damage = caster:GetAverageTrueAttackDamage(caster) * (self.chain_damage_self / 100) + self.chain_damage ApplyDamage({ victim = enemy, damage = damage, damage_type = DAMAGE_TYPE_MAGICAL, damage_flags = DOTA_DAMAGE_FLAG_NONE, attacker = caster, ability = self:GetAbility() }) break end end if self.unit_counter >= self.chain_strikes and self.chain_strikes > 0 or not self.zapped then self:StartIntervalThink(-1) self:Destroy() end end modifier_chain_lightning = __TS__Decorate( modifier_chain_lightning, modifier_chain_lightning, {registerModifier(nil)}, {kind = "class", name = "modifier_chain_lightning"} ) ____exports.modifier_chain_lightning = modifier_chain_lightning return ____exports