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 BaseModifier = ____dota_ts_adapter.BaseModifier local registerModifier = ____dota_ts_adapter.registerModifier local ____modifier_general_arc = require("abilities.modifiers.modifier_general_arc") local modifier_general_arc = ____modifier_general_arc.modifier_general_arc ____exports.KITTY_FLEX_CATAKEET_MODEL = "models/items/courier/catakeet/catakeet_head_curious.vmdl" --- Декоративная головка-курьер для эффекта kitty_flex: без выделения, урона и коллизий. ____exports.modifier_kitty_flex_catakeet = __TS__Class() local modifier_kitty_flex_catakeet = ____exports.modifier_kitty_flex_catakeet modifier_kitty_flex_catakeet.name = "modifier_kitty_flex_catakeet" modifier_kitty_flex_catakeet.____file_path = "scripts/vscripts/abilities/modifiers/modifier_kitty_flex_catakeet.lua" __TS__ClassExtends(modifier_kitty_flex_catakeet, BaseModifier) function modifier_kitty_flex_catakeet.prototype.____constructor(self, ...) BaseModifier.prototype.____constructor(self, ...) self.bounceRadiusMin = 80 self.bounceRadiusMax = 360 self.bounceHeightMin = 110 self.bounceHeightMax = 220 self.bounceIntervalMin = 0.55 self.bounceIntervalMax = 1 self.lookIntervalMin = 0.35 self.lookIntervalMax = 0.75 self.nextLookAt = 0 self.nextJumpAt = 0 end function modifier_kitty_flex_catakeet.prototype.IsHidden(self) return true end function modifier_kitty_flex_catakeet.prototype.IsPurgable(self) return false end function modifier_kitty_flex_catakeet.prototype.RemoveOnDeath(self) return false end function modifier_kitty_flex_catakeet.prototype.OnCreated(self, params) if not IsServer() then return end self.bounceRadiusMin = params.bounce_radius_min or self.bounceRadiusMin self.bounceRadiusMax = params.bounce_radius_max or self.bounceRadiusMax self.bounceHeightMin = params.bounce_height_min or self.bounceHeightMin self.bounceHeightMax = params.bounce_height_max or self.bounceHeightMax self.bounceIntervalMin = params.bounce_interval_min or self.bounceIntervalMin self.bounceIntervalMax = params.bounce_interval_max or self.bounceIntervalMax self.lookIntervalMin = params.look_interval_min or self.lookIntervalMin self.lookIntervalMax = params.look_interval_max or self.lookIntervalMax local parent = self:GetParent() parent:SetModel(____exports.KITTY_FLEX_CATAKEET_MODEL) parent:SetOriginalModel(____exports.KITTY_FLEX_CATAKEET_MODEL) parent:SetModelScale(1.35) parent:SetHullRadius(1) parent:SetControllableByPlayer(-1, false) parent:SetMoveCapability(DOTA_UNIT_CAP_MOVE_GROUND) parent:SetAttackCapability(DOTA_UNIT_CAP_NO_ATTACK) local now = GameRules:GetGameTime() self.nextLookAt = now + RandomFloat(0.05, 0.25) self.nextJumpAt = now + RandomFloat(self.bounceIntervalMin, self.bounceIntervalMax) self:StartIntervalThink(0.1) end function modifier_kitty_flex_catakeet.prototype.OnIntervalThink(self) if not IsServer() then return end local parent = self:GetParent() if not parent or parent:IsNull() or not IsValidEntity(parent) then return end local hero = self:GetCaster() local now = GameRules:GetGameTime() if now >= self.nextLookAt and hero and IsValidEntity(hero) and not hero:IsNull() then parent:FaceTowards(hero:GetAbsOrigin()) self.nextLookAt = now + RandomFloat(self.lookIntervalMin, self.lookIntervalMax) end if now < self.nextJumpAt or parent:HasModifier(modifier_general_arc.name) then return end self:performBounceJumpNearHero(parent, hero) self.nextJumpAt = now + RandomFloat(self.bounceIntervalMin, self.bounceIntervalMax) end function modifier_kitty_flex_catakeet.prototype.performBounceJumpNearHero(self, parent, hero) local parentOrigin = parent:GetAbsOrigin() local targetPos = parentOrigin if hero and IsValidEntity(hero) and not hero:IsNull() then local heroOrigin = hero:GetAbsOrigin() local angle = RandomFloat(0, 2 * math.pi) local distance = RandomFloat(self.bounceRadiusMin, self.bounceRadiusMax) targetPos = Vector( heroOrigin.x + math.cos(angle) * distance, heroOrigin.y + math.sin(angle) * distance, heroOrigin.z ) targetPos = GetGroundPosition(targetPos, parent) else local randomOffset = RandomVector(RandomFloat(self.bounceRadiusMin * 0.4, self.bounceRadiusMax * 0.6)) targetPos = GetGroundPosition( parentOrigin + Vector(randomOffset.x, randomOffset.y, 0), parent ) end local jumpDirection = targetPos - parentOrigin if jumpDirection:Length2D() > 16 then parent:SetForwardVector(jumpDirection:Normalized()) end local jumpDistance = jumpDirection:Length2D() modifier_general_arc:apply( parent, hero or parent, nil, { x = targetPos.x, y = targetPos.y, z = targetPos.z, duration = RandomFloat(0.28, 0.42), distance = jumpDistance, height = RandomFloat(self.bounceHeightMin, self.bounceHeightMax), isFlail = true } ) end function modifier_kitty_flex_catakeet.prototype.OnDestroy(self) if not IsServer() then return end local parent = self:GetParent() if parent and IsValidEntity(parent) and not parent:IsNull() then UTIL_Remove(parent) end end function modifier_kitty_flex_catakeet.prototype.CheckState(self) return { [MODIFIER_STATE_INVULNERABLE] = true, [MODIFIER_STATE_UNSELECTABLE] = true, [MODIFIER_STATE_UNTARGETABLE] = true, [MODIFIER_STATE_NO_HEALTH_BAR] = true, [MODIFIER_STATE_NOT_ON_MINIMAP] = true, [MODIFIER_STATE_NO_UNIT_COLLISION] = true, [MODIFIER_STATE_DISARMED] = true, [MODIFIER_STATE_COMMAND_RESTRICTED] = true, [MODIFIER_STATE_IGNORING_MOVE_AND_ATTACK_ORDERS] = true } end modifier_kitty_flex_catakeet = __TS__Decorate( modifier_kitty_flex_catakeet, modifier_kitty_flex_catakeet, {registerModifier(nil)}, {kind = "class", name = "modifier_kitty_flex_catakeet"} ) ____exports.modifier_kitty_flex_catakeet = modifier_kitty_flex_catakeet return ____exports